oaspec/config

Types

Configuration for oaspec code generation.

Opaque: external callers construct via new/6 and read fields via the accessors below. Mutators (with_mode, with_validate, with_output, with_include) live in this module too, so every change to a Config value goes through an explicit function.

pub opaque type Config

Errors that can occur when loading config.

pub type ConfigError {
  FileNotFound(path: String)
  FileReadError(path: String, detail: String)
  ParseError(detail: String)
  MissingField(field: String)
  InvalidValue(field: String, detail: String)
}

Constructors

  • FileNotFound(path: String)
  • FileReadError(path: String, detail: String)
  • ParseError(detail: String)
  • MissingField(field: String)
  • InvalidValue(field: String, detail: String)

Generation mode.

pub type GenerateMode {
  Server
  Client
  Both
}

Constructors

  • Server
  • Client
  • Both

Issue #387: subset filter for codegen. When non-empty, only operations matching at least one of the listed tags or paths are kept; the others are dropped before capability check, hoist, and validate.

Path patterns may end in /** to match any path under a prefix ("/repos/**" matches /repos/foo, /repos/foo/bar, …); otherwise the pattern is compared by exact string equality.

tags and paths combine with OR semantics — an operation is kept if EITHER its tag list intersects Include.tags OR its path matches one of Include.paths. With both lists empty (the default), no filtering is applied.

pub type Include {
  Include(tags: List(String), paths: List(String))
}

Constructors

  • Include(tags: List(String), paths: List(String))

Values

pub fn empty_include() -> Include

The default include filter — matches everything. Equivalent to oaspec.yaml omitting the include: key entirely.

pub fn error_to_string(error: ConfigError) -> String

Convert config error to a human-readable string.

pub fn include(cfg: Config) -> Include

Operation include filter (tags / paths). Issue #387.

pub fn include_is_empty(include: Include) -> Bool

True when no filter is active (both tag and path lists empty).

pub fn input(cfg: Config) -> String

Path to the OpenAPI spec this config was built for.

pub fn load(path: String) -> Result(Config, ConfigError)

Load config from a YAML file.

Returns the single target the YAML declares. When the YAML has a targets: array with more than one entry, this errors out with a multi-target hint — callers that need to handle the multi- target case must use load_all/1 instead. For ordinary single-target configs (no targets: key, or a targets: array with exactly one entry) the result is the same as before.

pub fn load_all(
  path: String,
) -> Result(List(Config), ConfigError)

Load every target declared by an oaspec.yaml. A config without a targets: key is treated as a single implicit target whose fields come from the top-level package:, output:, and include: keys (the legacy single-target shape). A config with a targets: sequence yields one Config per element, each carrying its own package / output_* / include while sharing the top-level input:, mode:, and validate: values.

pub fn mode(cfg: Config) -> GenerateMode

Generation mode: server, client, or both.

pub fn new(
  input input: String,
  output_server output_server: String,
  output_client output_client: String,
  package package: String,
  mode mode: GenerateMode,
  validate validate: Bool,
) -> Config

Construct a new Config from its six required fields. Prefer load/1 in production code; new/6 is primarily for tests and ad-hoc tooling that assembles a config in memory. The include filter defaults to empty_include() (match everything); use with_include/2 to override.

pub fn output_client(cfg: Config) -> String

Output directory for client-side generated files.

pub fn output_server(cfg: Config) -> String

Output directory for server-side generated files.

pub fn package(cfg: Config) -> String

Gleam package name (module prefix) for generated files.

pub fn parse_mode(
  mode: String,
) -> Result(GenerateMode, ConfigError)

Parse a mode string into GenerateMode.

pub fn validate(cfg: Config) -> Bool

Whether guard-based runtime validation is enabled.

pub fn validate_output_dir_layout(
  config: Config,
) -> Result(Nil, ConfigError)

Validate the on-disk layout implied by output.dir.

Issue #319: when output.dir is something like ./src/gen, generated code lands at src/gen/<pkg>/types.gleam whose Gleam module path is gen/<pkg>/types — but oaspec emits import <pkg>/types, which the compiler can’t resolve. Catch this at config time so the user sees a clear error instead of a wall of Unknown module ... from gleam build.

Heuristic: in the path leading up to the package’s top-level directory, src must either be the immediate parent (the “

is the project’s src/” pattern) or be absent (the standalone- Gleam-project pattern). src in any other position is the foot-gun.

Nested packages (Issue #387): for a package like dco_check/github the “package directory” is the last 2 path segments, and the rule applies to whatever sits BEFORE that pair. So ./src/dco_check/github has parent chain [src] (immediate parent src → ok), and ./pkg/src/foo/dco_check/github has parent chain [pkg, src, foo] (last is foo and src appears earlier → bad).

pub fn validate_output_package_match(
  config: Config,
) -> Result(Nil, ConfigError)

Validate that output directory basenames are valid Gleam module names usable as import roots.

Server output must end in <package> so generated imports such as import <package>/types resolve. Client output may end in either <package> (when client lives in its own project) or <package>_client (the new default since Issue #248 — both server and client share the same <dir> and need distinct basenames). Anything else is a misconfigured package/output mismatch the user should be told about.

Nested packages (Issue #387): a package containing / such as dco_check/github declares an N-segment Gleam module path. The path tail compared against the package is N segments deep — the LAST N segments of the output path must equal the package’s segments. The _client suffix attaches to the LAST package segment only, matching the single-segment behaviour (dco_check/githubdco_check/github_client, never dco_check_client/github).

pub fn with_include(config: Config, include: Include) -> Config

Apply include-filter override (Issue #387). Useful for tests that build a Config in memory.

pub fn with_mode(config: Config, mode: GenerateMode) -> Config

Apply CLI overrides to a config.

pub fn with_output(
  config: Config,
  output: option.Option(String),
) -> Config

Apply output base directory override. Derives server/client paths as

/ and /_client in Both mode. In client-only mode the client path drops the suffix (Issue #262) so generated import <package>/... lines resolve.

The suffix decision reads config.mode at call time, so apply with_mode/2 before with_output/2 if both overrides are needed — otherwise the client path will reflect the previous mode’s default.

pub fn with_validate(config: Config, validate: Bool) -> Config

Apply validation mode override.

Search Document