Current section

Files

Jump to
oaspec src oaspec@openapi@parser.erl
Raw

src/oaspec@openapi@parser.erl

-module(oaspec@openapi@parser).
-compile([no_auto_import, nowarn_unused_vars, nowarn_unused_function, nowarn_nomatch, inline]).
-define(FILEPATH, "src/oaspec/openapi/parser.gleam").
-export([parse_error_to_string/1, parse_schema_object/1, parse_schema_ref/1, parse_string/1, parse_file/1]).
-export_type([parse_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 parse_error() :: {file_error, binary()} |
{yaml_error, binary()} |
{missing_field, binary(), binary()} |
{invalid_value, binary(), binary()}.
-file("src/oaspec/openapi/parser.gleam", 77).
?DOC(" Parse the info object.\n").
-spec parse_info(yay:node_()) -> {ok, oaspec@openapi@spec:info()} |
{error, parse_error()}.
parse_info(Root) ->
gleam@result:'try'(
begin
_pipe = yay:select_sugar(Root, <<"info"/utf8>>),
gleam@result:map_error(
_pipe,
fun(_) -> {missing_field, <<""/utf8>>, <<"info"/utf8>>} end
)
end,
fun(Info_node) ->
gleam@result:'try'(
begin
_pipe@1 = yay:extract_string(Info_node, <<"title"/utf8>>),
gleam@result:map_error(
_pipe@1,
fun(_) ->
{missing_field, <<"info"/utf8>>, <<"title"/utf8>>}
end
)
end,
fun(Title) ->
gleam@result:'try'(
begin
_pipe@2 = yay:extract_string(
Info_node,
<<"version"/utf8>>
),
gleam@result:map_error(
_pipe@2,
fun(_) ->
{missing_field,
<<"info"/utf8>>,
<<"version"/utf8>>}
end
)
end,
fun(Version) ->
Description = begin
_pipe@3 = yay:extract_optional_string(
Info_node,
<<"description"/utf8>>
),
gleam@result:unwrap(_pipe@3, none)
end,
{ok, {info, Title, Description, Version}}
end
)
end
)
end
).
-file("src/oaspec/openapi/parser.gleam", 109).
?DOC(" Parse a single server object.\n").
-spec parse_server(yay:node_()) -> {ok, oaspec@openapi@spec:server()} |
{error, parse_error()}.
parse_server(Node) ->
gleam@result:'try'(
begin
_pipe = yay:extract_string(Node, <<"url"/utf8>>),
gleam@result:map_error(
_pipe,
fun(_) ->
{missing_field, <<"servers"/utf8>>, <<"url"/utf8>>}
end
)
end,
fun(Url) ->
Description = begin
_pipe@1 = yay:extract_optional_string(
Node,
<<"description"/utf8>>
),
gleam@result:unwrap(_pipe@1, none)
end,
{ok, {server, Url, Description}}
end
).
-file("src/oaspec/openapi/parser.gleam", 101).
?DOC(" Parse servers array.\n").
-spec parse_servers(yay:node_()) -> {ok, list(oaspec@openapi@spec:server())} |
{error, parse_error()}.
parse_servers(Root) ->
case yay:select_sugar(Root, <<"servers"/utf8>>) of
{ok, {node_seq, Items}} ->
gleam@list:try_map(Items, fun parse_server/1);
_ ->
{ok, []}
end.
-file("src/oaspec/openapi/parser.gleam", 333).
?DOC(" Resolve a $ref for a parameter by looking it up in components.\n").
-spec resolve_parameter_ref(
binary(),
gleam@option:option(oaspec@openapi@spec:components())
) -> {ok, oaspec@openapi@spec:parameter()} | {error, parse_error()}.
resolve_parameter_ref(Ref_str, Components) ->
Ref_name = begin
_pipe = Ref_str,
_pipe@1 = gleam@string:split(_pipe, <<"/"/utf8>>),
_pipe@2 = gleam@list:last(_pipe@1),
gleam@result:unwrap(_pipe@2, <<"unknown"/utf8>>)
end,
case Components of
{some, Comps} ->
case gleam_stdlib:map_get(erlang:element(3, Comps), Ref_name) of
{ok, Param} ->
{ok, Param};
{error, _} ->
{error,
{invalid_value,
<<"parameter.$ref"/utf8>>,
<<"Unresolved parameter reference: "/utf8,
Ref_str/binary>>}}
end;
none ->
{error,
{invalid_value,
<<"parameter.$ref"/utf8>>,
<<"No components to resolve reference: "/utf8,
Ref_str/binary>>}}
end.
-file("src/oaspec/openapi/parser.gleam", 362).
?DOC(" Resolve a $ref for a request body by looking it up in components.\n").
-spec resolve_request_body_ref(
binary(),
gleam@option:option(oaspec@openapi@spec:components())
) -> {ok, oaspec@openapi@spec:request_body()} | {error, parse_error()}.
resolve_request_body_ref(Ref_str, Components) ->
Ref_name = begin
_pipe = Ref_str,
_pipe@1 = gleam@string:split(_pipe, <<"/"/utf8>>),
_pipe@2 = gleam@list:last(_pipe@1),
gleam@result:unwrap(_pipe@2, <<"unknown"/utf8>>)
end,
case Components of
{some, Comps} ->
case gleam_stdlib:map_get(erlang:element(4, Comps), Ref_name) of
{ok, Rb} ->
{ok, Rb};
{error, _} ->
{error,
{invalid_value,
<<"requestBody.$ref"/utf8>>,
<<"Unresolved requestBody reference: "/utf8,
Ref_str/binary>>}}
end;
none ->
{error,
{invalid_value,
<<"requestBody.$ref"/utf8>>,
<<"No components to resolve reference: "/utf8,
Ref_str/binary>>}}
end.
-file("src/oaspec/openapi/parser.gleam", 391).
?DOC(" Resolve a $ref for a response by looking it up in components.\n").
-spec resolve_response_ref(
binary(),
gleam@option:option(oaspec@openapi@spec:components())
) -> {ok, oaspec@openapi@spec:response()} | {error, parse_error()}.
resolve_response_ref(Ref_str, Components) ->
Ref_name = begin
_pipe = Ref_str,
_pipe@1 = gleam@string:split(_pipe, <<"/"/utf8>>),
_pipe@2 = gleam@list:last(_pipe@1),
gleam@result:unwrap(_pipe@2, <<"unknown"/utf8>>)
end,
case Components of
{some, Comps} ->
case gleam_stdlib:map_get(erlang:element(5, Comps), Ref_name) of
{ok, Resp} ->
{ok, Resp};
{error, _} ->
{error,
{invalid_value,
<<"response.$ref"/utf8>>,
<<"Unresolved response reference: "/utf8,
Ref_str/binary>>}}
end;
none ->
{error,
{invalid_value,
<<"response.$ref"/utf8>>,
<<"No components to resolve reference: "/utf8,
Ref_str/binary>>}}
end.
-file("src/oaspec/openapi/parser.gleam", 420).
?DOC(" Parse parameter location string.\n").
-spec parse_parameter_in(binary()) -> {ok, oaspec@openapi@spec:parameter_in()} |
{error, parse_error()}.
parse_parameter_in(Value) ->
case Value of
<<"path"/utf8>> ->
{ok, in_path};
<<"query"/utf8>> ->
{ok, in_query};
<<"header"/utf8>> ->
{ok, in_header};
<<"cookie"/utf8>> ->
{ok, in_cookie};
_ ->
{error,
{invalid_value,
<<"parameter.in"/utf8>>,
<<<<"Unknown parameter location: "/utf8, Value/binary>>/binary,
". Must be one of: path, query, header, cookie"/utf8>>}}
end.
-file("src/oaspec/openapi/parser.gleam", 843).
?DOC(" Parse discriminator from a node.\n").
-spec parse_discriminator(yay:node_()) -> {ok,
oaspec@openapi@schema:discriminator()} |
{error, parse_error()}.
parse_discriminator(Node) ->
gleam@result:'try'(
begin
_pipe = yay:select_sugar(Node, <<"discriminator"/utf8>>),
gleam@result:map_error(
_pipe,
fun(_) ->
{missing_field, <<"schema"/utf8>>, <<"discriminator"/utf8>>}
end
)
end,
fun(Disc_node) ->
gleam@result:'try'(
begin
_pipe@1 = yay:extract_string(
Disc_node,
<<"propertyName"/utf8>>
),
gleam@result:map_error(
_pipe@1,
fun(_) ->
{missing_field,
<<"discriminator"/utf8>>,
<<"propertyName"/utf8>>}
end
)
end,
fun(Property_name) ->
Mapping = case yay:extract_string_map(
Disc_node,
<<"mapping"/utf8>>
) of
{ok, M} ->
M;
_ ->
maps:new()
end,
{ok, {discriminator, Property_name, Mapping}}
end
)
end
).
-file("src/oaspec/openapi/parser.gleam", 867).
?DOC(" Convert a parse error to a human-readable string.\n").
-spec parse_error_to_string(parse_error()) -> binary().
parse_error_to_string(Error) ->
case Error of
{file_error, Detail} ->
Detail;
{yaml_error, Detail@1} ->
Detail@1;
{missing_field, Path, Field} ->
<<<<<<"Missing field '"/utf8, Field/binary>>/binary, "' at "/utf8>>/binary,
Path/binary>>;
{invalid_value, Path@1, Detail@2} ->
<<<<<<"Invalid value at "/utf8, Path@1/binary>>/binary, ": "/utf8>>/binary,
Detail@2/binary>>
end.
-file("src/oaspec/openapi/parser.gleam", 878).
?DOC(" Convert a YAML error to a string.\n").
-spec yaml_error_to_string(yay:yaml_error()) -> binary().
yaml_error_to_string(Error) ->
case Error of
unexpected_parsing_error ->
<<"Unexpected parsing error"/utf8>>;
{parsing_error, Msg, _} ->
Msg
end.
-file("src/oaspec/openapi/parser.gleam", 670).
?DOC(" Parse a schema object.\n").
-spec parse_schema_object(yay:node_()) -> {ok,
oaspec@openapi@schema:schema_object()} |
{error, parse_error()}.
parse_schema_object(Node) ->
Nullable = begin
_pipe = yay:extract_optional_bool(Node, <<"nullable"/utf8>>),
_pipe@1 = gleam@result:unwrap(_pipe, none),
gleam@option:unwrap(_pipe@1, false)
end,
Description = begin
_pipe@2 = yay:extract_optional_string(Node, <<"description"/utf8>>),
gleam@result:unwrap(_pipe@2, none)
end,
case yay:select_sugar(Node, <<"allOf"/utf8>>) of
{ok, {node_seq, Items}} ->
gleam@result:'try'(
gleam@list:try_map(Items, fun parse_schema_ref/1),
fun(Schemas) -> {ok, {all_of_schema, Description, Schemas}} end
);
_ ->
case yay:select_sugar(Node, <<"oneOf"/utf8>>) of
{ok, {node_seq, Items@1}} ->
gleam@result:'try'(
gleam@list:try_map(Items@1, fun parse_schema_ref/1),
fun(Schemas@1) ->
Discriminator = begin
_pipe@3 = parse_discriminator(Node),
gleam@option:from_result(_pipe@3)
end,
{ok,
{one_of_schema,
Description,
Schemas@1,
Discriminator}}
end
);
_ ->
case yay:select_sugar(Node, <<"anyOf"/utf8>>) of
{ok, {node_seq, Items@2}} ->
gleam@result:'try'(
gleam@list:try_map(
Items@2,
fun parse_schema_ref/1
),
fun(Schemas@2) ->
{ok,
{any_of_schema, Description, Schemas@2}}
end
);
_ ->
parse_typed_schema(Node, Description, Nullable)
end
end
end.
-file("src/oaspec/openapi/parser.gleam", 706).
?DOC(" Parse a typed schema (string, integer, number, boolean, array, object).\n").
-spec parse_typed_schema(yay:node_(), gleam@option:option(binary()), boolean()) -> {ok,
oaspec@openapi@schema:schema_object()} |
{error, parse_error()}.
parse_typed_schema(Node, Description, Nullable) ->
Type_str = begin
_pipe = yay:extract_optional_string(Node, <<"type"/utf8>>),
_pipe@1 = gleam@result:unwrap(_pipe, none),
gleam@option:unwrap(_pipe@1, <<"object"/utf8>>)
end,
Format = begin
_pipe@2 = yay:extract_optional_string(Node, <<"format"/utf8>>),
gleam@result:unwrap(_pipe@2, none)
end,
case Type_str of
<<"string"/utf8>> ->
Enum_values = case yay:extract_string_list(Node, <<"enum"/utf8>>) of
{ok, Values} ->
Values;
_ ->
[]
end,
Min_length = begin
_pipe@3 = yay:extract_optional_int(Node, <<"minLength"/utf8>>),
gleam@result:unwrap(_pipe@3, none)
end,
Max_length = begin
_pipe@4 = yay:extract_optional_int(Node, <<"maxLength"/utf8>>),
gleam@result:unwrap(_pipe@4, none)
end,
Pattern = begin
_pipe@5 = yay:extract_optional_string(Node, <<"pattern"/utf8>>),
gleam@result:unwrap(_pipe@5, none)
end,
{ok,
{string_schema,
Description,
Format,
Enum_values,
Min_length,
Max_length,
Pattern,
Nullable}};
<<"integer"/utf8>> ->
Minimum = begin
_pipe@6 = yay:extract_optional_int(Node, <<"minimum"/utf8>>),
gleam@result:unwrap(_pipe@6, none)
end,
Maximum = begin
_pipe@7 = yay:extract_optional_int(Node, <<"maximum"/utf8>>),
gleam@result:unwrap(_pipe@7, none)
end,
{ok,
{integer_schema,
Description,
Format,
Minimum,
Maximum,
Nullable}};
<<"number"/utf8>> ->
Minimum@1 = begin
_pipe@8 = yay:extract_optional_float(Node, <<"minimum"/utf8>>),
gleam@result:unwrap(_pipe@8, none)
end,
Maximum@1 = begin
_pipe@9 = yay:extract_optional_float(Node, <<"maximum"/utf8>>),
gleam@result:unwrap(_pipe@9, none)
end,
{ok,
{number_schema,
Description,
Format,
Minimum@1,
Maximum@1,
Nullable}};
<<"boolean"/utf8>> ->
{ok, {boolean_schema, Description, Nullable}};
<<"array"/utf8>> ->
Items = case yay:select_sugar(Node, <<"items"/utf8>>) of
{ok, Items_node} ->
_pipe@10 = parse_schema_ref(Items_node),
gleam@result:unwrap(
_pipe@10,
{inline,
{string_schema,
none,
none,
[],
none,
none,
none,
false}}
);
_ ->
{inline,
{string_schema, none, none, [], none, none, none, false}}
end,
Min_items = begin
_pipe@11 = yay:extract_optional_int(Node, <<"minItems"/utf8>>),
gleam@result:unwrap(_pipe@11, none)
end,
Max_items = begin
_pipe@12 = yay:extract_optional_int(Node, <<"maxItems"/utf8>>),
gleam@result:unwrap(_pipe@12, none)
end,
{ok,
{array_schema,
Description,
Items,
Min_items,
Max_items,
Nullable}};
_ ->
Properties = begin
_pipe@13 = parse_properties(Node),
gleam@result:unwrap(_pipe@13, maps:new())
end,
Required = case yay:extract_string_list(Node, <<"required"/utf8>>) of
{ok, R} ->
R;
_ ->
[]
end,
{Additional_properties, Additional_properties_untyped} = case yay:select_sugar(
Node,
<<"additionalProperties"/utf8>>
) of
{ok, {node_bool, true}} ->
{none, true};
{ok, {node_bool, false}} ->
{none, false};
{ok, Ap_node} ->
{begin
_pipe@14 = parse_schema_ref(Ap_node),
gleam@option:from_result(_pipe@14)
end,
false};
_ ->
{none, false}
end,
{ok,
{object_schema,
Description,
Properties,
Required,
Additional_properties,
Additional_properties_untyped,
Nullable}}
end.
-file("src/oaspec/openapi/parser.gleam", 822).
?DOC(" Parse properties map from an object schema.\n").
-spec parse_properties(yay:node_()) -> {ok,
gleam@dict:dict(binary(), oaspec@openapi@schema:schema_ref())} |
{error, parse_error()}.
parse_properties(Node) ->
case yay:select_sugar(Node, <<"properties"/utf8>>) of
{ok, {node_map, Entries}} ->
gleam@list:try_fold(
Entries,
maps:new(),
fun(Acc, Entry) ->
{Key_node, Value_node} = Entry,
case Key_node of
{node_str, Name} ->
gleam@result:'try'(
parse_schema_ref(Value_node),
fun(Schema_ref) ->
{ok,
gleam@dict:insert(Acc, Name, Schema_ref)}
end
);
_ ->
{ok, Acc}
end
end
);
_ ->
{ok, maps:new()}
end.
-file("src/oaspec/openapi/parser.gleam", 659).
?DOC(" Parse a schema reference (either $ref or inline schema).\n").
-spec parse_schema_ref(yay:node_()) -> {ok, oaspec@openapi@schema:schema_ref()} |
{error, parse_error()}.
parse_schema_ref(Node) ->
case yay:extract_optional_string(Node, <<"$ref"/utf8>>) of
{ok, {some, Ref}} ->
{ok, {reference, Ref}};
_ ->
gleam@result:'try'(
parse_schema_object(Node),
fun(Schema_obj) -> {ok, {inline, Schema_obj}} end
)
end.
-file("src/oaspec/openapi/parser.gleam", 267).
?DOC(" Parse a single parameter.\n").
-spec parse_parameter(
yay:node_(),
gleam@option:option(oaspec@openapi@spec:components())
) -> {ok, oaspec@openapi@spec:parameter()} | {error, parse_error()}.
parse_parameter(Node, Components) ->
case yay:extract_optional_string(Node, <<"$ref"/utf8>>) of
{ok, {some, Ref_str}} ->
resolve_parameter_ref(Ref_str, Components);
_ ->
gleam@result:'try'(
begin
_pipe = yay:extract_string(Node, <<"name"/utf8>>),
gleam@result:map_error(
_pipe,
fun(_) ->
{missing_field,
<<"parameter"/utf8>>,
<<"name"/utf8>>}
end
)
end,
fun(Name) ->
gleam@result:'try'(
begin
_pipe@1 = yay:extract_string(Node, <<"in"/utf8>>),
gleam@result:map_error(
_pipe@1,
fun(_) ->
{missing_field,
<<"parameter."/utf8, Name/binary>>,
<<"in"/utf8>>}
end
)
end,
fun(In_str) ->
gleam@result:'try'(
parse_parameter_in(In_str),
fun(In_) ->
Description = begin
_pipe@2 = yay:extract_optional_string(
Node,
<<"description"/utf8>>
),
gleam@result:unwrap(_pipe@2, none)
end,
Required = begin
_pipe@3 = yay:extract_optional_bool(
Node,
<<"required"/utf8>>
),
_pipe@4 = gleam@result:unwrap(
_pipe@3,
none
),
gleam@option:unwrap(_pipe@4, case In_ of
in_path ->
true;
_ ->
false
end)
end,
Deprecated = begin
_pipe@5 = yay:extract_optional_bool(
Node,
<<"deprecated"/utf8>>
),
_pipe@6 = gleam@result:unwrap(
_pipe@5,
none
),
gleam@option:unwrap(_pipe@6, false)
end,
Param_schema = case yay:select_sugar(
Node,
<<"schema"/utf8>>
) of
{ok, Schema_node} ->
_pipe@7 = parse_schema_ref(
Schema_node
),
gleam@option:from_result(_pipe@7);
_ ->
none
end,
Style = begin
_pipe@8 = yay:extract_optional_string(
Node,
<<"style"/utf8>>
),
gleam@result:unwrap(_pipe@8, none)
end,
{ok,
{parameter,
Name,
In_,
Description,
Required,
Param_schema,
Style,
Deprecated}}
end
)
end
)
end
)
end.
-file("src/oaspec/openapi/parser.gleam", 255).
?DOC(" Parse parameters list from a node.\n").
-spec parse_parameters_list(
yay:node_(),
gleam@option:option(oaspec@openapi@spec:components())
) -> {ok, list(oaspec@openapi@spec:parameter())} | {error, parse_error()}.
parse_parameters_list(Node, Components) ->
case yay:select_sugar(Node, <<"parameters"/utf8>>) of
{ok, {node_seq, Items}} ->
gleam@list:try_map(
Items,
fun(Item) -> parse_parameter(Item, Components) end
);
_ ->
{ok, []}
end.
-file("src/oaspec/openapi/parser.gleam", 476).
?DOC(" Parse content map (media type -> schema).\n").
-spec parse_content(yay:node_(), binary()) -> {ok,
gleam@dict:dict(binary(), oaspec@openapi@spec:media_type())} |
{error, parse_error()}.
parse_content(Node, _) ->
case yay:select_sugar(Node, <<"content"/utf8>>) of
{ok, {node_map, Entries}} ->
gleam@list:try_fold(
Entries,
maps:new(),
fun(Acc, Entry) ->
{Key_node, Value_node} = Entry,
case Key_node of
{node_str, Media_type_name} ->
Mt_schema = case yay:select_sugar(
Value_node,
<<"schema"/utf8>>
) of
{ok, Schema_node} ->
_pipe = parse_schema_ref(Schema_node),
gleam@option:from_result(_pipe);
_ ->
none
end,
{ok,
gleam@dict:insert(
Acc,
Media_type_name,
{media_type, Mt_schema}
)};
_ ->
{ok, Acc}
end
end
);
_ ->
{ok, maps:new()}
end.
-file("src/oaspec/openapi/parser.gleam", 457).
?DOC(" Parse a request body object.\n").
-spec parse_request_body(yay:node_(), binary()) -> {ok,
oaspec@openapi@spec:request_body()} |
{error, parse_error()}.
parse_request_body(Node, Context) ->
Description = begin
_pipe = yay:extract_optional_string(Node, <<"description"/utf8>>),
gleam@result:unwrap(_pipe, none)
end,
Required = begin
_pipe@1 = yay:extract_optional_bool(Node, <<"required"/utf8>>),
_pipe@2 = gleam@result:unwrap(_pipe@1, none),
gleam@option:unwrap(_pipe@2, false)
end,
Content = begin
_pipe@3 = parse_content(Node, Context),
gleam@result:unwrap(_pipe@3, maps:new())
end,
{ok, {request_body, Description, Content, Required}}.
-file("src/oaspec/openapi/parser.gleam", 437).
?DOC(" Parse requestBody from a node.\n").
-spec parse_request_body_at(
yay:node_(),
binary(),
gleam@option:option(oaspec@openapi@spec:components())
) -> {ok, oaspec@openapi@spec:request_body()} | {error, parse_error()}.
parse_request_body_at(Node, Context, Components) ->
gleam@result:'try'(
begin
_pipe = yay:select_sugar(Node, <<"requestBody"/utf8>>),
gleam@result:map_error(
_pipe,
fun(_) -> {missing_field, Context, <<"requestBody"/utf8>>} end
)
end,
fun(Rb_node) ->
case yay:extract_optional_string(Rb_node, <<"$ref"/utf8>>) of
{ok, {some, Ref_str}} ->
resolve_request_body_ref(Ref_str, Components);
_ ->
parse_request_body(Rb_node, Context)
end
end
).
-file("src/oaspec/openapi/parser.gleam", 532).
?DOC(" Parse a single response object.\n").
-spec parse_response(
yay:node_(),
gleam@option:option(oaspec@openapi@spec:components())
) -> {ok, oaspec@openapi@spec:response()} | {error, parse_error()}.
parse_response(Node, Components) ->
case yay:extract_optional_string(Node, <<"$ref"/utf8>>) of
{ok, {some, Ref_str}} ->
resolve_response_ref(Ref_str, Components);
_ ->
Description = begin
_pipe = yay:extract_optional_string(
Node,
<<"description"/utf8>>
),
gleam@result:unwrap(_pipe, none)
end,
Content = begin
_pipe@1 = parse_content(Node, <<"response"/utf8>>),
gleam@result:unwrap(_pipe@1, maps:new())
end,
{ok, {response, Description, Content}}
end.
-file("src/oaspec/openapi/parser.gleam", 504).
?DOC(" Parse responses object.\n").
-spec parse_responses(
yay:node_(),
binary(),
gleam@option:option(oaspec@openapi@spec:components())
) -> {ok, gleam@dict:dict(binary(), oaspec@openapi@spec:response())} |
{error, parse_error()}.
parse_responses(Node, _, Components) ->
case yay:select_sugar(Node, <<"responses"/utf8>>) of
{ok, {node_map, Entries}} ->
gleam@list:try_fold(
Entries,
maps:new(),
fun(Acc, Entry) ->
{Key_node, Value_node} = Entry,
case Key_node of
{node_str, Status_code} ->
gleam@result:'try'(
parse_response(Value_node, Components),
fun(Resp) ->
{ok,
gleam@dict:insert(
Acc,
Status_code,
Resp
)}
end
);
{node_int, Code} ->
gleam@result:'try'(
parse_response(Value_node, Components),
fun(Resp@1) ->
Code_str = gleam@string:inspect(Code),
{ok,
gleam@dict:insert(Acc, Code_str, Resp@1)}
end
);
_ ->
{ok, Acc}
end
end
);
_ ->
{ok, maps:new()}
end.
-file("src/oaspec/openapi/parser.gleam", 209).
?DOC(" Parse a single operation.\n").
-spec parse_operation(
yay:node_(),
binary(),
gleam@option:option(oaspec@openapi@spec:components())
) -> {ok, oaspec@openapi@spec:operation()} | {error, parse_error()}.
parse_operation(Node, Context, Components) ->
Operation_id = begin
_pipe = yay:extract_optional_string(Node, <<"operationId"/utf8>>),
gleam@result:unwrap(_pipe, none)
end,
Summary = begin
_pipe@1 = yay:extract_optional_string(Node, <<"summary"/utf8>>),
gleam@result:unwrap(_pipe@1, none)
end,
Description = begin
_pipe@2 = yay:extract_optional_string(Node, <<"description"/utf8>>),
gleam@result:unwrap(_pipe@2, none)
end,
Tags = case yay:extract_string_list(Node, <<"tags"/utf8>>) of
{ok, T} ->
T;
_ ->
[]
end,
Deprecated = begin
_pipe@3 = yay:extract_optional_bool(Node, <<"deprecated"/utf8>>),
_pipe@4 = gleam@result:unwrap(_pipe@3, none),
gleam@option:unwrap(_pipe@4, false)
end,
Parameters = begin
_pipe@5 = parse_parameters_list(Node, Components),
gleam@result:unwrap(_pipe@5, [])
end,
Request_body = begin
_pipe@6 = parse_request_body_at(Node, Context, Components),
gleam@option:from_result(_pipe@6)
end,
Responses = begin
_pipe@7 = parse_responses(Node, Context, Components),
gleam@result:unwrap(_pipe@7, maps:new())
end,
{ok,
{operation,
Operation_id,
Summary,
Description,
Tags,
Parameters,
Request_body,
Responses,
Deprecated}}.
-file("src/oaspec/openapi/parser.gleam", 193).
?DOC(" Parse an operation at a specific HTTP method key.\n").
-spec parse_operation_at(
yay:node_(),
binary(),
binary(),
oaspec@openapi@spec:http_method(),
gleam@option:option(oaspec@openapi@spec:components())
) -> {ok, oaspec@openapi@spec:operation()} | {error, parse_error()}.
parse_operation_at(Node, Method_key, Path, _, Components) ->
gleam@result:'try'(
begin
_pipe = yay:select_sugar(Node, Method_key),
gleam@result:map_error(
_pipe,
fun(_) -> {missing_field, Path, Method_key} end
)
end,
fun(Op_node) ->
parse_operation(
Op_node,
<<<<Path/binary, "."/utf8>>/binary, Method_key/binary>>,
Components
)
end
).
-file("src/oaspec/openapi/parser.gleam", 149).
?DOC(" Parse a single path item.\n").
-spec parse_path_item(
yay:node_(),
binary(),
gleam@option:option(oaspec@openapi@spec:components())
) -> {ok, oaspec@openapi@spec:path_item()} | {error, parse_error()}.
parse_path_item(Node, Path, Components) ->
Summary = begin
_pipe = yay:extract_optional_string(Node, <<"summary"/utf8>>),
gleam@result:unwrap(_pipe, none)
end,
Description = begin
_pipe@1 = yay:extract_optional_string(Node, <<"description"/utf8>>),
gleam@result:unwrap(_pipe@1, none)
end,
Get = begin
_pipe@2 = parse_operation_at(
Node,
<<"get"/utf8>>,
Path,
get,
Components
),
gleam@option:from_result(_pipe@2)
end,
Post = begin
_pipe@3 = parse_operation_at(
Node,
<<"post"/utf8>>,
Path,
post,
Components
),
gleam@option:from_result(_pipe@3)
end,
Put = begin
_pipe@4 = parse_operation_at(
Node,
<<"put"/utf8>>,
Path,
put,
Components
),
gleam@option:from_result(_pipe@4)
end,
Delete = begin
_pipe@5 = parse_operation_at(
Node,
<<"delete"/utf8>>,
Path,
delete,
Components
),
gleam@option:from_result(_pipe@5)
end,
Patch = begin
_pipe@6 = parse_operation_at(
Node,
<<"patch"/utf8>>,
Path,
patch,
Components
),
gleam@option:from_result(_pipe@6)
end,
Parameters = begin
_pipe@7 = parse_parameters_list(Node, Components),
gleam@result:unwrap(_pipe@7, [])
end,
{ok,
{path_item,
Summary,
Description,
Get,
Post,
Put,
Delete,
Patch,
Parameters}}.
-file("src/oaspec/openapi/parser.gleam", 123).
?DOC(" Parse the paths object.\n").
-spec parse_paths(
yay:node_(),
gleam@option:option(oaspec@openapi@spec:components())
) -> {ok, gleam@dict:dict(binary(), oaspec@openapi@spec:path_item())} |
{error, parse_error()}.
parse_paths(Root, Components) ->
case yay:select_sugar(Root, <<"paths"/utf8>>) of
{ok, {node_map, Entries}} ->
gleam@list:try_fold(
Entries,
maps:new(),
fun(Acc, Entry) ->
{Key_node, Value_node} = Entry,
case Key_node of
{node_str, Path} ->
gleam@result:'try'(
parse_path_item(Value_node, Path, Components),
fun(Path_item) ->
{ok,
gleam@dict:insert(Acc, Path, Path_item)}
end
);
_ ->
{ok, Acc}
end
end
);
_ ->
{ok, maps:new()}
end.
-file("src/oaspec/openapi/parser.gleam", 570).
?DOC(" Parse the schemas map from components.\n").
-spec parse_schemas_map(yay:node_()) -> {ok,
gleam@dict:dict(binary(), oaspec@openapi@schema:schema_ref())} |
{error, parse_error()}.
parse_schemas_map(Components_node) ->
case yay:select_sugar(Components_node, <<"schemas"/utf8>>) of
{ok, {node_map, Entries}} ->
gleam@list:try_fold(
Entries,
maps:new(),
fun(Acc, Entry) ->
{Key_node, Value_node} = Entry,
case Key_node of
{node_str, Name} ->
gleam@result:'try'(
parse_schema_ref(Value_node),
fun(Schema_ref) ->
{ok,
gleam@dict:insert(Acc, Name, Schema_ref)}
end
);
_ ->
{ok, Acc}
end
end
);
_ ->
{ok, maps:new()}
end.
-file("src/oaspec/openapi/parser.gleam", 591).
?DOC(" Parse the parameters map from components.\n").
-spec parse_parameters_map(yay:node_()) -> {ok,
gleam@dict:dict(binary(), oaspec@openapi@spec:parameter())} |
{error, parse_error()}.
parse_parameters_map(Components_node) ->
case yay:select_sugar(Components_node, <<"parameters"/utf8>>) of
{ok, {node_map, Entries}} ->
gleam@list:try_fold(
Entries,
maps:new(),
fun(Acc, Entry) ->
{Key_node, Value_node} = Entry,
case Key_node of
{node_str, Name} ->
gleam@result:'try'(
parse_parameter(Value_node, none),
fun(Param) ->
{ok, gleam@dict:insert(Acc, Name, Param)}
end
);
_ ->
{ok, Acc}
end
end
);
_ ->
{ok, maps:new()}
end.
-file("src/oaspec/openapi/parser.gleam", 613).
?DOC(" Parse the requestBodies map from components.\n").
-spec parse_request_bodies_map(yay:node_()) -> {ok,
gleam@dict:dict(binary(), oaspec@openapi@spec:request_body())} |
{error, parse_error()}.
parse_request_bodies_map(Components_node) ->
case yay:select_sugar(Components_node, <<"requestBodies"/utf8>>) of
{ok, {node_map, Entries}} ->
gleam@list:try_fold(
Entries,
maps:new(),
fun(Acc, Entry) ->
{Key_node, Value_node} = Entry,
case Key_node of
{node_str, Name} ->
gleam@result:'try'(
parse_request_body(
Value_node,
<<"components.requestBodies."/utf8,
Name/binary>>
),
fun(Rb) ->
{ok, gleam@dict:insert(Acc, Name, Rb)}
end
);
_ ->
{ok, Acc}
end
end
);
_ ->
{ok, maps:new()}
end.
-file("src/oaspec/openapi/parser.gleam", 637).
?DOC(" Parse the responses map from components.\n").
-spec parse_responses_map(yay:node_()) -> {ok,
gleam@dict:dict(binary(), oaspec@openapi@spec:response())} |
{error, parse_error()}.
parse_responses_map(Components_node) ->
case yay:select_sugar(Components_node, <<"responses"/utf8>>) of
{ok, {node_map, Entries}} ->
gleam@list:try_fold(
Entries,
maps:new(),
fun(Acc, Entry) ->
{Key_node, Value_node} = Entry,
case Key_node of
{node_str, Name} ->
gleam@result:'try'(
parse_response(Value_node, none),
fun(Resp) ->
{ok, gleam@dict:insert(Acc, Name, Resp)}
end
);
_ ->
{ok, Acc}
end
end
);
_ ->
{ok, maps:new()}
end.
-file("src/oaspec/openapi/parser.gleam", 552).
?DOC(" Parse the components section.\n").
-spec parse_components(yay:node_()) -> {ok, oaspec@openapi@spec:components()} |
{error, parse_error()}.
parse_components(Root) ->
gleam@result:'try'(
begin
_pipe = yay:select_sugar(Root, <<"components"/utf8>>),
gleam@result:map_error(
_pipe,
fun(_) ->
{missing_field, <<""/utf8>>, <<"components"/utf8>>}
end
)
end,
fun(Components_node) ->
Schemas = begin
_pipe@1 = parse_schemas_map(Components_node),
gleam@result:unwrap(_pipe@1, maps:new())
end,
Parameters = begin
_pipe@2 = parse_parameters_map(Components_node),
gleam@result:unwrap(_pipe@2, maps:new())
end,
Request_bodies = begin
_pipe@3 = parse_request_bodies_map(Components_node),
gleam@result:unwrap(_pipe@3, maps:new())
end,
Responses = begin
_pipe@4 = parse_responses_map(Components_node),
gleam@result:unwrap(_pipe@4, maps:new())
end,
{ok, {components, Schemas, Parameters, Request_bodies, Responses}}
end
).
-file("src/oaspec/openapi/parser.gleam", 59).
?DOC(" Parse the root OpenAPI object.\n").
-spec parse_root(yay:node_()) -> {ok, oaspec@openapi@spec:open_api_spec()} |
{error, parse_error()}.
parse_root(Node) ->
gleam@result:'try'(
begin
_pipe = yay:extract_string(Node, <<"openapi"/utf8>>),
gleam@result:map_error(
_pipe,
fun(_) -> {missing_field, <<""/utf8>>, <<"openapi"/utf8>>} end
)
end,
fun(Openapi) ->
gleam@result:'try'(
parse_info(Node),
fun(Info) ->
Components = begin
_pipe@1 = parse_components(Node),
gleam@option:from_result(_pipe@1)
end,
gleam@result:'try'(
parse_paths(Node, Components),
fun(Paths) ->
Servers = begin
_pipe@2 = parse_servers(Node),
gleam@result:unwrap(_pipe@2, [])
end,
{ok,
{open_api_spec,
Openapi,
Info,
Paths,
Components,
Servers}}
end
)
end
)
end
).
-file("src/oaspec/openapi/parser.gleam", 43).
?DOC(" Parse an OpenAPI spec from a YAML/JSON string.\n").
-spec parse_string(binary()) -> {ok, oaspec@openapi@spec:open_api_spec()} |
{error, parse_error()}.
parse_string(Content) ->
gleam@result:'try'(
begin
_pipe = yaml_ffi:parse_string(Content),
gleam@result:map_error(
_pipe,
fun(E) -> {yaml_error, yaml_error_to_string(E)} end
)
end,
fun(Docs) -> gleam@result:'try'(case Docs of
[First | _] ->
{ok, First};
[] ->
{error, {yaml_error, <<"Empty document"/utf8>>}}
end, fun(Doc) ->
Root = yay:document_root(Doc),
parse_root(Root)
end) end
).
-file("src/oaspec/openapi/parser.gleam", 31).
?DOC(
" Parse an OpenAPI spec from a file path.\n"
" Supports both YAML (.yaml, .yml) and JSON (.json) files.\n"
).
-spec parse_file(binary()) -> {ok, oaspec@openapi@spec:open_api_spec()} |
{error, parse_error()}.
parse_file(Path) ->
gleam@result:'try'(
begin
_pipe = simplifile:read(Path),
gleam@result:map_error(
_pipe,
fun(_) ->
{file_error, <<"Cannot read file: "/utf8, Path/binary>>}
end
)
end,
fun(Content) -> parse_string(Content) end
).