-module(oaspec@cli).
-compile([no_auto_import, nowarn_unused_vars, nowarn_unused_function, nowarn_nomatch, inline]).
-define(FILEPATH, "src/oaspec/cli.gleam").
-export([app/0]).
-export_type([load_config_error/0]).
-if(?OTP_RELEASE >= 27).
-define(MODULEDOC(Str), -moduledoc(Str)).
-define(DOC(Str), -doc(Str)).
-else.
-define(MODULEDOC(Str), -compile([])).
-define(DOC(Str), -compile([])).
-endif.
-type load_config_error() :: {config_load_error, oaspec@config:config_error()} |
{mode_parse_error, oaspec@config:config_error()} |
{output_validation_error, oaspec@config:config_error()}.
-file("src/oaspec/cli.gleam", 28).
?DOC(
" Apply colour styling only when stdout is a terminal and NO_COLOR is unset,\n"
" per and the CLIG \"colorize when stdout is a TTY only\"\n"
" guideline. When either check fails, glint keeps its `pretty_help` as `None`\n"
" and emits plain text.\n"
).
-spec maybe_pretty_help(glint:glint(WZQ)) -> glint:glint(WZQ).
maybe_pretty_help(Glint) ->
case {oaspec_ffi:is_stdout_tty(), oaspec_ffi:no_color_set()} of
{true, false} ->
glint:pretty_help(Glint, glint:default_pretty_help());
{_, _} ->
Glint
end.
-file("src/oaspec/cli.gleam", 58).
?DOC(" The version command definition.\n").
-spec version_command() -> glint:command(nil).
version_command() ->
glint:command_help(
<<"Print the oaspec version and exit"/utf8>>,
fun() ->
glint:command(
fun(_, _, _) ->
gleam_stdlib:println(
<<"oaspec v"/utf8, (<<"0.24.0"/utf8>>)/binary>>
)
end
)
end
).
-file("src/oaspec/cli.gleam", 328).
?DOC(
" Issue #284: when the generated code imports a Gleam stdlib module\n"
" whose package is not a direct dep of the consumer's project (today,\n"
" only `gleam/regexp` for pattern validation), `gleam build` warns\n"
" about the transitive import and a future Gleam release turns this\n"
" into a hard error. Print an actionable hint so the user adds the\n"
" missing dep — we deliberately do not rewrite the consumer's\n"
" `gleam.toml` because modifying user-managed config invisibly is\n"
" surprising.\n"
).
-spec print_dep_hints(list(oaspec@codegen@context:generated_file())) -> nil.
print_dep_hints(Files) ->
Needs_regexp = gleam@list:any(
Files,
fun(F) ->
gleam_stdlib:contains_string(
erlang:element(3, F),
<<"import gleam/regexp"/utf8>>
)
end
),
case Needs_regexp of
true ->
gleam_stdlib:println(<<""/utf8>>),
gleam_stdlib:println(
<<"Note: generated code imports gleam/regexp for pattern validation."/utf8>>
),
gleam_stdlib:println(
<<" Run 'gleam add gleam_regexp' in your project before 'gleam build'."/utf8>>
);
false ->
nil
end.
-file("src/oaspec/cli.gleam", 471).
-spec unique_id() -> binary().
unique_id() ->
Integer_value = erlang:unique_integer(),
case Integer_value < 0 of
true ->
<<"n"/utf8, (erlang:integer_to_binary(- Integer_value))/binary>>;
false ->
erlang:integer_to_binary(Integer_value)
end.
-file("src/oaspec/cli.gleam", 419).
?DOC(
" Format resolved content by writing to a temp directory, running gleam format,\n"
" and reading back the formatted content.\n"
).
-spec format_resolved_content(list({binary(), binary()})) -> list({binary(),
binary()}).
format_resolved_content(Resolved) ->
Temp_dir = <<"/tmp/oaspec_check_"/utf8, (unique_id())/binary>>,
case simplifile:create_directory_all(Temp_dir) of
{error, _} ->
Resolved;
{ok, nil} ->
Temp_entries = gleam@list:index_map(
Resolved,
fun(Entry, Idx) ->
{Original_path, Content} = Entry,
Temp_path = <<<<<>/binary,
(erlang:integer_to_binary(Idx))/binary>>/binary,
".gleam"/utf8>>,
_ = simplifile:write(Temp_path, Content),
{Original_path, Temp_path}
end
),
Temp_paths = gleam@list:map(
Temp_entries,
fun(Entry@1) -> erlang:element(2, Entry@1) end
),
Formatted_resolved = case oaspec@formatter:format_files(Temp_paths) of
{ok, nil} ->
gleam@list:map(
Temp_entries,
fun(Entry@2) ->
{Original_path@1, Temp_path@1} = Entry@2,
case simplifile:read(Temp_path@1) of
{ok, Formatted} ->
{Original_path@1, Formatted};
{error, _} ->
Content@1 = begin
_pipe = gleam@list:find(
Resolved,
fun(R) ->
erlang:element(1, R) =:= Original_path@1
end
),
_pipe@1 = gleam@result:map(
_pipe,
fun(R@1) ->
erlang:element(2, R@1)
end
),
gleam@result:unwrap(
_pipe@1,
<<""/utf8>>
)
end,
{Original_path@1, Content@1}
end
end
);
{error, _} ->
Resolved
end,
_ = simplifile_erl:delete(Temp_dir),
Formatted_resolved
end.
-file("src/oaspec/cli.gleam", 515).
?DOC(" Format a `LoadConfigError` into a user-facing message.\n").
-spec load_config_error_to_string(load_config_error()) -> binary().
load_config_error_to_string(Error) ->
Detail = case Error of
{config_load_error, Error@1} ->
oaspec@config:error_to_string(Error@1);
{mode_parse_error, Error@2} ->
oaspec@config:error_to_string(Error@2);
{output_validation_error, Error@3} ->
oaspec@config:error_to_string(Error@3)
end,
<<"Error: "/utf8, Detail/binary>>.
-file("src/oaspec/cli.gleam", 525).
?DOC(" Pure config loading and validation pipeline.\n").
-spec load_config(
binary(),
gleam@option:option(binary()),
gleam@option:option(binary())
) -> {ok, oaspec@config:config()} | {error, load_config_error()}.
load_config(Config_path, Mode_opt, Output_opt) ->
gleam@result:'try'(
begin
_pipe = oaspec@config:load(Config_path),
gleam@result:map_error(
_pipe,
fun(Field@0) -> {config_load_error, Field@0} end
)
end,
fun(Cfg) -> gleam@result:'try'(case Mode_opt of
none ->
{ok, Cfg};
{some, Mode_str} ->
_pipe@1 = oaspec@config:parse_mode(Mode_str),
_pipe@2 = gleam@result:map(
_pipe@1,
fun(Parsed) ->
oaspec@config:with_mode(Cfg, Parsed)
end
),
gleam@result:map_error(
_pipe@2,
fun(Field@0) -> {mode_parse_error, Field@0} end
)
end, fun(Cfg@1) ->
Cfg@2 = case Output_opt of
none ->
Cfg@1;
{some, Path} ->
oaspec@config:with_output(Cfg@1, {some, Path})
end,
_pipe@3 = oaspec@config:validate_output_package_match(Cfg@2),
_pipe@4 = gleam@result:map(_pipe@3, fun(_) -> Cfg@2 end),
gleam@result:map_error(
_pipe@4,
fun(Field@0) -> {output_validation_error, Field@0} end
)
end) end
).
-file("src/oaspec/cli.gleam", 567).
?DOC(" Format a GenerateError into a printable error message.\n").
-spec format_generate_error(oaspec@generate:generate_error()) -> binary().
format_generate_error(Err) ->
{validation_errors, Errors} = Err,
<<"Error: OpenAPI spec contains unsupported features:\n"/utf8,
(gleam@string:join(
gleam@list:map(
Errors,
fun(Validation_error) ->
<<" - "/utf8,
(oaspec@openapi@diagnostic:to_short_string(
Validation_error
))/binary>>
end
),
<<"\n"/utf8>>
))/binary>>.
-file("src/oaspec/cli.gleam", 580).
?DOC(
" Print warnings if any exist. Warnings are diagnostics, so they go to stderr\n"
" to keep stdout reserved for requested output.\n"
).
-spec print_warnings(list(oaspec@openapi@diagnostic:diagnostic())) -> nil.
print_warnings(Warnings) ->
case Warnings of
[] ->
nil;
_ ->
gleam_stdlib:println_error(<<"Warnings:"/utf8>>),
gleam@list:each(
Warnings,
fun(W) ->
gleam_stdlib:println_error(
<<" - "/utf8,
(oaspec@openapi@diagnostic:to_short_string(W))/binary>>
)
end
)
end.
-file("src/oaspec/cli.gleam", 196).
?DOC(" Create a config file template.\n").
-spec run_init(binary()) -> nil.
run_init(Path) ->
Template = <<"# oaspec configuration file
# See https://github.com/nao1215/oaspec for documentation.
# Path to your OpenAPI 3.x specification (YAML or JSON).
input: openapi.yaml
# Gleam module namespace for generated code.
# Generated imports will be `import /types`, etc.
package: api
# Generation mode: server, client, or both (default: both).
# mode: both
# Enable guard validation in generated server/client code.
# Default: true for mode: server / both (fail-closed: server handlers
# should not receive schema-invalid input by default), false for
# mode: client (clients pre-validating before sending is nice but
# optional). When enabled, generated routers validate request bodies
# against schema constraints and return 422 on failure. Generated
# clients validate request bodies before sending. Set explicitly to
# override the mode-dependent default.
# validate: true
# Output settings (optional).
# output:
# dir: ./gen # Base directory; default paths are
# # server -> /
# # client -> /_client
# # so a single `gleam build` rooted at
# # picks up both.
# server: ./gen/api # Override server output path
# client: ./gen/api_client # Override client output path
"/utf8>>,
case simplifile_erl:is_file(Path) of
{ok, true} ->
gleam_stdlib:println_error(
<<<<"Error: "/utf8, Path/binary>>/binary,
" already exists"/utf8>>
),
erlang:halt(1);
_ ->
case simplifile:write(Path, Template) of
{ok, _} ->
gleam_stdlib:println(<<"Created "/utf8, Path/binary>>);
{error, Write_err} ->
gleam_stdlib:println_error(
<<<<<<"Error: failed to write "/utf8, Path/binary>>/binary,
": "/utf8>>/binary,
(simplifile:describe_error(Write_err))/binary>>
),
erlang:halt(1)
end
end.
-file("src/oaspec/cli.gleam", 178).
?DOC(" The init command definition.\n").
-spec init_command() -> glint:command(nil).
init_command() ->
begin
glint:flag(
begin
_pipe = glint:string_flag(<<"output"/utf8>>),
_pipe@1 = glint:flag_default(_pipe, <<"./oaspec.yaml"/utf8>>),
glint:flag_help(
_pipe@1,
<<"Output path for the config file"/utf8>>
)
end,
fun(Output_path) ->
glint:command_help(
<<"Create a oaspec.yaml config file"/utf8>>,
fun() ->
glint:command(
fun(_, _, Flags) ->
Path = begin
_pipe@2 = Output_path(Flags),
gleam@result:unwrap(
_pipe@2,
<<"./oaspec.yaml"/utf8>>
)
end,
run_init(Path)
end
)
end
)
end
)
end.
-file("src/oaspec/cli.gleam", 352).
?DOC(
" Check that generated code matches existing files on disk.\n"
" Exits 0 if all files match, exits 1 if any differ, missing, or orphaned.\n"
"\n"
" Issue #247: user-owned `handlers.gleam` (`SkipIfExists`) is dropped from\n"
" the byte-comparison list (`resolve_paths` does that filtering) but kept in\n"
" the expected-paths list so orphan detection still recognises it as a known\n"
" generator output instead of flagging it as an orphan.\n"
).
-spec run_check(
list(oaspec@codegen@context:generated_file()),
oaspec@config:config()
) -> nil.
run_check(Files, Cfg) ->
gleam_stdlib:println(
<<"Checking generated code against existing files..."/utf8>>
),
Resolved = oaspec@codegen@writer:resolve_paths(Files, Cfg),
Expected_paths = oaspec@codegen@writer:expected_paths(Files, Cfg),
Resolved@1 = format_resolved_content(Resolved),
Diffs = gleam@list:filter_map(
Resolved@1,
fun(Entry) ->
{Path, Content} = Entry,
case simplifile:read(Path) of
{error, _} ->
{ok, <>};
{ok, Existing} ->
case gleam@string:compare(Existing, Content) of
eq ->
{error, nil};
_ ->
{ok, <>}
end
end
end
),
Output_dirs = oaspec@codegen@writer:output_dirs(Cfg),
Orphans = gleam@list:flat_map(
Output_dirs,
fun(Dir) -> case simplifile_erl:read_directory(Dir) of
{error, _} ->
[];
{ok, Entries} ->
gleam@list:filter_map(
Entries,
fun(Name) ->
case gleam_stdlib:string_ends_with(
Name,
<<".gleam"/utf8>>
) of
false ->
{error, nil};
true ->
Full_path = <<<>/binary,
Name/binary>>,
case gleam@list:contains(
Expected_paths,
Full_path
) of
true ->
{error, nil};
false ->
{ok,
<>}
end
end
end
)
end end
),
All_issues = lists:append(Diffs, Orphans),
case All_issues of
[] ->
gleam_stdlib:println(<<""/utf8>>),
gleam_stdlib:println(<<"All files up to date, check passed."/utf8>>);
_ ->
gleam_stdlib:println_error(<<""/utf8>>),
gleam@list:each(
All_issues,
fun(D) ->
gleam_stdlib:println_error(<<" "/utf8, D/binary>>)
end
),
gleam_stdlib:println_error(
<<<<"\n"/utf8,
(erlang:integer_to_binary(erlang:length(All_issues)))/binary>>/binary,
" file(s) out of date. Run 'oaspec generate' to update."/utf8>>
),
erlang:halt(1)
end.
-file("src/oaspec/cli.gleam", 552).
?DOC(
" Unwrap a Result or print the error message and exit.\n"
" Designed for use with `use value <- require(result, to_message)`.\n"
).
-spec require(
{ok, XAK} | {error, XAL},
fun((XAL) -> binary()),
fun((XAK) -> nil)
) -> nil.
require(Result, To_message, Continue) ->
case Result of
{ok, Value} ->
Continue(Value);
{error, Err} ->
gleam_stdlib:println_error(To_message(Err)),
erlang:halt(1)
end.
-file("src/oaspec/cli.gleam", 301).
?DOC(" Write generated files to disk, format them, and print summary.\n").
-spec write_files(
list(oaspec@codegen@context:generated_file()),
oaspec@config:config()
) -> nil.
write_files(Files, Cfg) ->
gleam_stdlib:println(<<"Generating code..."/utf8>>),
require(
oaspec@codegen@writer:write_all(
Files,
Cfg,
fun(Path) ->
gleam_stdlib:println(<<" Generated: "/utf8, Path/binary>>)
end
),
fun(E) ->
<<"Error: "/utf8,
(oaspec@codegen@writer:error_to_string(E))/binary>>
end,
fun(Written) ->
require(
oaspec@formatter:format_files(
oaspec@codegen@writer:output_dirs(Cfg)
),
fun(E@1) ->
<<"Error: "/utf8,
(oaspec@formatter:error_to_string(E@1))/binary>>
end,
fun(_) ->
gleam_stdlib:println(<<" Formatted generated code"/utf8>>),
gleam_stdlib:println(<<""/utf8>>),
gleam_stdlib:println(
<<<<"Successfully generated "/utf8,
(erlang:integer_to_binary(
erlang:length(Written)
))/binary>>/binary,
" files"/utf8>>
),
print_dep_hints(Files)
end
)
end
).
-file("src/oaspec/cli.gleam", 257).
?DOC(
" Execute the generation pipeline.\n"
" Handles IO (printing, exit codes) while delegating pure logic to\n"
" generate.generate and load_config.\n"
).
-spec run_generate(
binary(),
gleam@option:option(binary()),
gleam@option:option(binary()),
boolean(),
boolean(),
boolean()
) -> nil.
run_generate(
Config_path,
Mode_opt,
Output_opt,
Check_mode,
Fail_on_warnings,
Validate_mode
) ->
gleam_stdlib:println(<<"oaspec v"/utf8, (<<"0.24.0"/utf8>>)/binary>>),
gleam_stdlib:println(<<"Loading config from: "/utf8, Config_path/binary>>),
require(
load_config(Config_path, Mode_opt, Output_opt),
fun load_config_error_to_string/1,
fun(Cfg) ->
Cfg@1 = case Validate_mode of
true ->
oaspec@config:with_validate(Cfg, true);
false ->
Cfg
end,
gleam_stdlib:println(
<<"Parsing OpenAPI spec: "/utf8,
(oaspec@config:input(Cfg@1))/binary>>
),
require(
oaspec@openapi@parser:parse_file(oaspec@config:input(Cfg@1)),
fun(E) ->
<<"Error: "/utf8,
(oaspec@openapi@parser:parse_error_to_string(E))/binary>>
end,
fun(Spec) ->
require(
oaspec@generate:generate(Spec, Cfg@1),
fun format_generate_error/1,
fun(Summary) ->
gleam_stdlib:println(
<<"Spec loaded: "/utf8,
(erlang:element(3, Summary))/binary>>
),
print_warnings(erlang:element(4, Summary)),
case Fail_on_warnings andalso (erlang:element(
4,
Summary
)
/= []) of
true ->
gleam_stdlib:println_error(<<""/utf8>>),
gleam_stdlib:println_error(
<<"Error: warnings present and --fail-on-warnings is set."/utf8>>
),
erlang:halt(1);
false ->
nil
end,
case Check_mode of
true ->
run_check(erlang:element(2, Summary), Cfg@1);
false ->
write_files(
erlang:element(2, Summary),
Cfg@1
)
end
end
)
end
)
end
).
-file("src/oaspec/cli.gleam", 67).
?DOC(" The generate command definition.\n").
-spec generate_command() -> glint:command(nil).
generate_command() ->
begin
glint:flag(
begin
_pipe = glint:string_flag(<<"config"/utf8>>),
_pipe@1 = glint:flag_default(_pipe, <<"./oaspec.yaml"/utf8>>),
glint:flag_help(_pipe@1, <<"Path to config file"/utf8>>)
end,
fun(Config_path) ->
glint:flag(
begin
_pipe@2 = glint:string_flag(<<"mode"/utf8>>),
_pipe@3 = glint:flag_default(_pipe@2, <<""/utf8>>),
glint:flag_help(
_pipe@3,
<<"Generation mode: server, client, or both (overrides config)"/utf8>>
)
end,
fun(Mode) ->
glint:flag(
begin
_pipe@4 = glint:string_flag(<<"output"/utf8>>),
_pipe@5 = glint:flag_default(
_pipe@4,
<<""/utf8>>
),
glint:flag_help(
_pipe@5,
<<"Output directory override"/utf8>>
)
end,
fun(Output) ->
glint:flag(
begin
_pipe@6 = glint:bool_flag(
<<"check"/utf8>>
),
_pipe@7 = glint:flag_default(
_pipe@6,
false
),
glint:flag_help(
_pipe@7,
<<"Check that generated code matches existing files without writing"/utf8>>
)
end,
fun(Check) ->
glint:flag(
begin
_pipe@8 = glint:bool_flag(
<<"fail-on-warnings"/utf8>>
),
_pipe@9 = glint:flag_default(
_pipe@8,
false
),
glint:flag_help(
_pipe@9,
<<"Treat warnings as errors"/utf8>>
)
end,
fun(Fail_on_warnings) ->
glint:flag(
begin
_pipe@10 = glint:bool_flag(
<<"validate"/utf8>>
),
_pipe@11 = glint:flag_default(
_pipe@10,
false
),
glint:flag_help(
_pipe@11,
<<"Enable guard validation in generated server/client code"/utf8>>
)
end,
fun(Validate) ->
glint:command_help(
<<"Generate Gleam code from an OpenAPI specification"/utf8>>,
fun() ->
glint:command(
fun(
_,
_,
Flags
) ->
Config_path@1 = begin
_pipe@12 = Config_path(
Flags
),
gleam@result:unwrap(
_pipe@12,
<<"./oaspec.yaml"/utf8>>
)
end,
Mode_opt = case begin
_pipe@13 = Mode(
Flags
),
gleam@result:unwrap(
_pipe@13,
<<""/utf8>>
)
end of
<<""/utf8>> ->
none;
S ->
{some,
S}
end,
Output_opt = case begin
_pipe@14 = Output(
Flags
),
gleam@result:unwrap(
_pipe@14,
<<""/utf8>>
)
end of
<<""/utf8>> ->
none;
S@1 ->
{some,
S@1}
end,
Check_mode = begin
_pipe@15 = Check(
Flags
),
gleam@result:unwrap(
_pipe@15,
false
)
end,
Fail_on_warnings_mode = begin
_pipe@16 = Fail_on_warnings(
Flags
),
gleam@result:unwrap(
_pipe@16,
false
)
end,
Validate_mode = begin
_pipe@17 = Validate(
Flags
),
gleam@result:unwrap(
_pipe@17,
false
)
end,
run_generate(
Config_path@1,
Mode_opt,
Output_opt,
Check_mode,
Fail_on_warnings_mode,
Validate_mode
)
end
)
end
)
end
)
end
)
end
)
end
)
end
)
end
)
end.
-file("src/oaspec/cli.gleam", 480).
?DOC(" Execute the validation-only pipeline.\n").
-spec run_validate(binary(), gleam@option:option(binary())) -> nil.
run_validate(Config_path, Mode_opt) ->
gleam_stdlib:println(<<"oaspec v"/utf8, (<<"0.24.0"/utf8>>)/binary>>),
gleam_stdlib:println(<<"Loading config from: "/utf8, Config_path/binary>>),
require(
load_config(Config_path, Mode_opt, none),
fun load_config_error_to_string/1,
fun(Cfg) ->
gleam_stdlib:println(
<<"Parsing OpenAPI spec: "/utf8,
(oaspec@config:input(Cfg))/binary>>
),
require(
oaspec@openapi@parser:parse_file(oaspec@config:input(Cfg)),
fun(E) ->
<<"Error: "/utf8,
(oaspec@openapi@parser:parse_error_to_string(E))/binary>>
end,
fun(Spec) ->
require(
oaspec@generate:validate_only(Spec, Cfg),
fun format_generate_error/1,
fun(Summary) ->
gleam_stdlib:println(
<<"Spec loaded: "/utf8,
(erlang:element(2, Summary))/binary>>
),
print_warnings(erlang:element(3, Summary)),
gleam_stdlib:println(<<""/utf8>>),
gleam_stdlib:println(<<"Validation passed."/utf8>>)
end
)
end
)
end
).
-file("src/oaspec/cli.gleam", 144).
?DOC(" The validate command definition.\n").
-spec validate_command() -> glint:command(nil).
validate_command() ->
begin
glint:flag(
begin
_pipe = glint:string_flag(<<"config"/utf8>>),
_pipe@1 = glint:flag_default(_pipe, <<"./oaspec.yaml"/utf8>>),
glint:flag_help(_pipe@1, <<"Path to config file"/utf8>>)
end,
fun(Config_path) ->
glint:flag(
begin
_pipe@2 = glint:string_flag(<<"mode"/utf8>>),
_pipe@3 = glint:flag_default(_pipe@2, <<""/utf8>>),
glint:flag_help(
_pipe@3,
<<"Generation mode: server, client, or both (overrides config)"/utf8>>
)
end,
fun(Mode) ->
glint:command_help(
<<"Validate an OpenAPI specification without generating code"/utf8>>,
fun() ->
glint:command(
fun(_, _, Flags) ->
Config_path@1 = begin
_pipe@4 = Config_path(Flags),
gleam@result:unwrap(
_pipe@4,
<<"./oaspec.yaml"/utf8>>
)
end,
Mode_opt = case begin
_pipe@5 = Mode(Flags),
gleam@result:unwrap(
_pipe@5,
<<""/utf8>>
)
end of
<<""/utf8>> ->
none;
S ->
{some, S}
end,
run_validate(Config_path@1, Mode_opt)
end
)
end
)
end
)
end
)
end.
-file("src/oaspec/cli.gleam", 44).
?DOC(" Set up the CLI application.\n").
-spec app() -> glint:glint(nil).
app() ->
_pipe = glint:new(),
_pipe@1 = glint:with_name(_pipe, <<"oaspec"/utf8>>),
_pipe@2 = glint:global_help(
_pipe@1,
<<"Generate Gleam code from OpenAPI 3.x specifications\n\nCommands:\n init Create a default oaspec.yaml config file\n generate Generate Gleam code from an OpenAPI spec\n validate Validate an OpenAPI spec without generating code\n version Print the oaspec version and exit\n\nRun 'oaspec --help' for more information.\nUse 'oaspec --version' for a flag-style version check."/utf8>>
),
_pipe@3 = maybe_pretty_help(_pipe@2),
_pipe@4 = glint:add(_pipe@3, [<<"init"/utf8>>], init_command()),
_pipe@5 = glint:add(_pipe@4, [<<"generate"/utf8>>], generate_command()),
_pipe@6 = glint:add(_pipe@5, [<<"validate"/utf8>>], validate_command()),
glint:add(_pipe@6, [<<"version"/utf8>>], version_command()).