Packages
glint
0.1.0
1.3.0
1.2.1
1.2.0
1.1.1
1.1.0
1.0.1
1.0.0
1.0.0-rc5
1.0.0-rc4
1.0.0-rc3
1.0.0-rc2
1.0.0-rc1
0.18.1
0.18.0
0.17.1
0.17.0
0.16.0
0.16.0-rc1
0.15.0
0.15.0-rc2
0.15.0-rc1
0.14.0
0.13.0
0.12.0
0.12.0-rc6
0.12.0-rc5
0.12.0-rc4
0.12.0-rc3
0.12.0-rc2
0.12.0-rc1
0.11.4
0.11.3
0.11.2
0.11.0
0.10.0
0.9.0
0.8.0
0.7.4
0.7.3
0.7.2
0.7.1
0.7.0
0.6.0
0.5.0
0.4.0
0.3.0
0.2.0
0.1.3
0.1.2
0.1.1
0.1.0
Gleam command-line argument parsing with flags and automated help text generation.
Current section
Files
Jump to
Current section
Files
src/glint.erl
-module(glint).
-compile(no_auto_import).
-export([new/0, add_command/4, execute/2, run/2]).
-export_type([command_input/0, command/0]).
-type command_input() :: {command_input,
list(binary()),
gleam@map:map_(binary(), glint@flag:flag_value())}.
-opaque command() :: {command,
gleam@option:option(fun((command_input()) -> nil)),
gleam@map:map_(binary(), command()),
gleam@map:map_(binary(), glint@flag:flag_value())}.
-spec new() -> command().
new() ->
{command, none, gleam@map:new(), gleam@map:new()}.
-spec add_command(
command(),
list(binary()),
fun((command_input()) -> nil),
list(glint@flag:flag())
) -> command().
add_command(Root, Path, F, Flags) ->
case Path of
[] ->
erlang:setelement(
4,
erlang:setelement(2, Root, {some, F}),
glint@flag:build_map(Flags)
);
[X | Xs] ->
erlang:setelement(
3,
Root,
gleam@map:update(
erlang:element(3, Root),
X,
fun(Node) -> case Node of
none ->
add_command(
{command,
none,
gleam@map:new(),
gleam@map:new()},
Xs,
F,
Flags
);
{some, Node@1} ->
add_command(Node@1, Xs, F, Flags)
end end
)
)
end.
-spec execute_root(command(), list(binary())) -> {ok, nil} |
{error, snag:snag()}.
execute_root(Cmd, Args) ->
case erlang:element(2, Cmd) of
{some, F} ->
{ok, F({command_input, Args, erlang:element(4, Cmd)})};
none ->
{error,
begin
_pipe = snag:new(<<"command not found"/utf8>>),
snag:layer(_pipe, <<"failed to run command"/utf8>>)
end}
end.
-spec execute(command(), list(binary())) -> {ok, nil} | {error, snag:snag()}.
execute(Cmd, Args) ->
case Args of
[] ->
execute_root(Cmd, []);
[Arg | Rest] ->
case gleam@string:starts_with(Arg, <<"-"/utf8>>) of
true ->
case begin
_pipe = glint@flag:update_flags(
erlang:element(4, Cmd),
gleam@string:drop_left(Arg, 1)
),
snag:context(_pipe, <<"failed to run command"/utf8>>)
end of
{error, _try} -> {error, _try};
{ok, New_flags} ->
execute(erlang:setelement(4, Cmd, New_flags), Rest)
end;
false ->
case gleam@map:get(erlang:element(3, Cmd), Arg) of
{ok, Cmd@1} ->
execute(Cmd@1, Rest);
{error, _@1} ->
execute_root(Cmd, Args)
end
end
end.
-spec run(command(), list(binary())) -> nil.
run(Cmd, Args) ->
case execute(Cmd, Args) of
{ok, nil} ->
nil;
{error, Err} ->
_pipe = Err,
_pipe@1 = snag:pretty_print(_pipe),
gleam@io:println(_pipe@1)
end.