Packages
oaspec
0.61.0
0.68.0
0.67.0
0.66.0
0.65.0
0.64.0
0.63.0
0.62.0
0.61.0
0.60.0
0.59.0
0.58.1
0.58.0
0.57.0
0.56.0
0.55.0
0.54.0
0.53.0
0.52.0
0.51.0
0.50.0
0.49.0
0.48.0
0.47.0
0.46.0
0.45.0
0.44.0
0.43.0
0.42.0
0.41.0
0.40.0
0.39.0
0.38.0
0.37.0
0.36.0
0.35.0
0.34.0
0.33.0
0.32.0
0.31.0
0.30.0
0.29.0
0.28.0
0.27.0
0.26.0
0.25.0
0.24.0
0.23.0
0.22.0
0.21.0
0.20.0
0.19.0
0.18.0
0.17.0
0.16.0
0.15.0
0.14.0
0.13.0
0.12.0
0.11.0
0.10.0
0.9.0
0.8.0
0.7.0
0.6.3
0.6.1
0.6.0
0.5.0
0.4.0
0.3.0
0.1.3
Generate Gleam code from OpenAPI 3.x specifications
Current section
Files
Jump to
Current section
Files
src/oaspec@internal@openapi@external_loader_planner.erl
-module(oaspec@internal@openapi@external_loader_planner).
-compile([no_auto_import, nowarn_unused_vars, nowarn_unused_function, nowarn_nomatch, inline]).
-define(FILEPATH, "src/oaspec/internal/openapi/external_loader_planner.gleam").
-export([extract_external_component_ref/1, find_external_parameter/3, find_external_request_body/3, find_external_response/3, find_external_path_item/3, check_nested_local_collision/3, check_nested_cross_file_collision/3, check_local_collision/4, check_cross_file_collision/3, extract_external_ref/1, local_schema_names/1, local_schema_name_from_ref/1, find_schema_follow_alias/3, find_external_schema/3, base_dir_of/1]).
-if(?OTP_RELEASE >= 27).
-define(MODULEDOC(Str), -moduledoc(Str)).
-define(DOC(Str), -doc(Str)).
-else.
-define(MODULEDOC(Str), -compile([])).
-define(DOC(Str), -compile([])).
-endif.
?MODULEDOC(false).
-file("src/oaspec/internal/openapi/external_loader_planner.gleam", 59).
?DOC(false).
-spec try_component_prefix(binary(), binary(), list(binary())) -> gleam@option:option({binary(),
binary(),
binary()}).
try_component_prefix(File_path, Fragment, Prefixes) ->
case Prefixes of
[] ->
none;
[Prefix | Rest] ->
case gleam_stdlib:string_starts_with(Fragment, Prefix) of
true ->
Name = gleam@string:replace(Fragment, Prefix, <<""/utf8>>),
case {gleam_stdlib:contains_string(Name, <<"/"/utf8>>),
Name} of
{false, <<""/utf8>>} ->
none;
{false, _} ->
{some, {File_path, Prefix, Name}};
{true, _} ->
none
end;
false ->
try_component_prefix(File_path, Fragment, Rest)
end
end.
-file("src/oaspec/internal/openapi/external_loader_planner.gleam", 40).
?DOC(false).
-spec extract_external_component_ref(binary()) -> gleam@option:option({binary(),
binary(),
binary()}).
extract_external_component_ref(Ref_str) ->
Is_relative = gleam_stdlib:string_starts_with(Ref_str, <<"./"/utf8>>) orelse gleam_stdlib:string_starts_with(
Ref_str,
<<"../"/utf8>>
),
gleam@bool:guard(
not Is_relative,
none,
fun() -> case gleam@string:split_once(Ref_str, <<"#"/utf8>>) of
{ok, {File_path, Fragment}} ->
try_component_prefix(
File_path,
Fragment,
[<<"/components/parameters/"/utf8>>,
<<"/components/requestBodies/"/utf8>>,
<<"/components/responses/"/utf8>>,
<<"/components/pathItems/"/utf8>>]
);
_ ->
none
end end
).
-file("src/oaspec/internal/openapi/external_loader_planner.gleam", 82).
?DOC(false).
-spec find_external_parameter(
oaspec@internal@openapi@spec:open_api_spec(oaspec@internal@openapi@spec:unresolved()),
binary(),
binary()
) -> {ok,
oaspec@internal@openapi@spec:parameter(oaspec@internal@openapi@spec:unresolved())} |
{error, oaspec@openapi@diagnostic:diagnostic()}.
find_external_parameter(Loaded, Name, Source_path) ->
case erlang:element(5, Loaded) of
{some, Components} ->
case gleam_stdlib:map_get(erlang:element(3, Components), Name) of
{ok, {value, P}} ->
{ok, P};
{ok, {ref, _}} ->
{error,
oaspec@openapi@diagnostic:validation(
Source_path,
<<<<<<<<"External parameter '"/utf8, Name/binary>>/binary,
"' in '"/utf8>>/binary,
Source_path/binary>>/binary,
"' is itself a $ref; chained external refs are not supported."/utf8>>,
severity_error,
target_both,
{some,
<<"Inline the parameter in the external file or flatten the ref chain."/utf8>>}
)};
{error, nil} ->
{error,
oaspec@openapi@diagnostic:validation(
Source_path,
<<<<<<"External file '"/utf8, Source_path/binary>>/binary,
"' has no components.parameters."/utf8>>/binary,
Name/binary>>,
severity_error,
target_both,
{some,
<<"Verify the ref path and that the referenced file defines the parameter."/utf8>>}
)}
end;
none ->
{error,
oaspec@openapi@diagnostic:validation(
Source_path,
<<<<"External file '"/utf8, Source_path/binary>>/binary,
"' has no components block."/utf8>>,
severity_error,
target_both,
{some,
<<"Add a components.parameters section to the referenced file."/utf8>>}
)}
end.
-file("src/oaspec/internal/openapi/external_loader_planner.gleam", 133).
?DOC(false).
-spec find_external_request_body(
oaspec@internal@openapi@spec:open_api_spec(oaspec@internal@openapi@spec:unresolved()),
binary(),
binary()
) -> {ok,
oaspec@internal@openapi@spec:request_body(oaspec@internal@openapi@spec:unresolved())} |
{error, oaspec@openapi@diagnostic:diagnostic()}.
find_external_request_body(Loaded, Name, Source_path) ->
case erlang:element(5, Loaded) of
{some, Components} ->
case gleam_stdlib:map_get(erlang:element(4, Components), Name) of
{ok, {value, Rb}} ->
{ok, Rb};
{ok, {ref, _}} ->
{error,
oaspec@openapi@diagnostic:validation(
Source_path,
<<<<<<<<"External request body '"/utf8,
Name/binary>>/binary,
"' in '"/utf8>>/binary,
Source_path/binary>>/binary,
"' is itself a $ref; chained external refs are not supported."/utf8>>,
severity_error,
target_both,
{some,
<<"Inline the request body in the external file or flatten the ref chain."/utf8>>}
)};
{error, nil} ->
{error,
oaspec@openapi@diagnostic:validation(
Source_path,
<<<<<<"External file '"/utf8, Source_path/binary>>/binary,
"' has no components.requestBodies."/utf8>>/binary,
Name/binary>>,
severity_error,
target_both,
{some,
<<"Verify the ref path and that the referenced file defines the request body."/utf8>>}
)}
end;
none ->
{error,
oaspec@openapi@diagnostic:validation(
Source_path,
<<<<"External file '"/utf8, Source_path/binary>>/binary,
"' has no components block."/utf8>>,
severity_error,
target_both,
{some,
<<"Add a components.requestBodies section to the referenced file."/utf8>>}
)}
end.
-file("src/oaspec/internal/openapi/external_loader_planner.gleam", 184).
?DOC(false).
-spec find_external_response(
oaspec@internal@openapi@spec:open_api_spec(oaspec@internal@openapi@spec:unresolved()),
binary(),
binary()
) -> {ok,
oaspec@internal@openapi@spec:response(oaspec@internal@openapi@spec:unresolved())} |
{error, oaspec@openapi@diagnostic:diagnostic()}.
find_external_response(Loaded, Name, Source_path) ->
case erlang:element(5, Loaded) of
{some, Components} ->
case gleam_stdlib:map_get(erlang:element(5, Components), Name) of
{ok, {value, R}} ->
{ok, R};
{ok, {ref, _}} ->
{error,
oaspec@openapi@diagnostic:validation(
Source_path,
<<<<<<<<"External response '"/utf8, Name/binary>>/binary,
"' in '"/utf8>>/binary,
Source_path/binary>>/binary,
"' is itself a $ref; chained external refs are not supported."/utf8>>,
severity_error,
target_both,
{some,
<<"Inline the response in the external file or flatten the ref chain."/utf8>>}
)};
{error, nil} ->
{error,
oaspec@openapi@diagnostic:validation(
Source_path,
<<<<<<"External file '"/utf8, Source_path/binary>>/binary,
"' has no components.responses."/utf8>>/binary,
Name/binary>>,
severity_error,
target_both,
{some,
<<"Verify the ref path and that the referenced file defines the response."/utf8>>}
)}
end;
none ->
{error,
oaspec@openapi@diagnostic:validation(
Source_path,
<<<<"External file '"/utf8, Source_path/binary>>/binary,
"' has no components block."/utf8>>,
severity_error,
target_both,
{some,
<<"Add a components.responses section to the referenced file."/utf8>>}
)}
end.
-file("src/oaspec/internal/openapi/external_loader_planner.gleam", 233).
?DOC(false).
-spec find_external_path_item(
oaspec@internal@openapi@spec:open_api_spec(oaspec@internal@openapi@spec:unresolved()),
binary(),
binary()
) -> {ok,
oaspec@internal@openapi@spec:path_item(oaspec@internal@openapi@spec:unresolved())} |
{error, oaspec@openapi@diagnostic:diagnostic()}.
find_external_path_item(Loaded, Name, Source_path) ->
case erlang:element(5, Loaded) of
{some, Components} ->
case gleam_stdlib:map_get(erlang:element(7, Components), Name) of
{ok, {value, Pi}} ->
{ok, Pi};
{ok, {ref, _}} ->
{error,
oaspec@openapi@diagnostic:validation(
Source_path,
<<<<<<<<"External path item '"/utf8, Name/binary>>/binary,
"' in '"/utf8>>/binary,
Source_path/binary>>/binary,
"' is itself a $ref; chained external refs are not supported."/utf8>>,
severity_error,
target_both,
{some,
<<"Inline the path item in the external file or flatten the ref chain."/utf8>>}
)};
{error, nil} ->
{error,
oaspec@openapi@diagnostic:validation(
Source_path,
<<<<<<"External file '"/utf8, Source_path/binary>>/binary,
"' has no components.pathItems."/utf8>>/binary,
Name/binary>>,
severity_error,
target_both,
{some,
<<"Verify the ref path and that the referenced file defines the path item."/utf8>>}
)}
end;
none ->
{error,
oaspec@openapi@diagnostic:validation(
Source_path,
<<<<"External file '"/utf8, Source_path/binary>>/binary,
"' has no components block."/utf8>>,
severity_error,
target_both,
{some,
<<"Add a components.pathItems section to the referenced file."/utf8>>}
)}
end.
-file("src/oaspec/internal/openapi/external_loader_planner.gleam", 285).
?DOC(false).
-spec check_nested_local_collision(binary(), binary(), list(binary())) -> {ok,
nil} |
{error, oaspec@openapi@diagnostic:diagnostic()}.
check_nested_local_collision(Fragment_name, Source_path, Original_local_names) ->
gleam@bool:guard(
not gleam@list:contains(Original_local_names, Fragment_name),
{ok, nil},
fun() ->
{error,
oaspec@openapi@diagnostic:validation(
Source_path,
<<<<<<<<"Nested property $ref imports schema '"/utf8,
Fragment_name/binary>>/binary,
"' from '"/utf8>>/binary,
Source_path/binary>>/binary,
"', but a local schema with the same name is already defined."/utf8>>,
severity_error,
target_both,
{some,
<<"Rename one of the colliding schemas, or point the external ref at a file whose fragment name is unique."/utf8>>}
)}
end
).
-file("src/oaspec/internal/openapi/external_loader_planner.gleam", 312).
?DOC(false).
-spec check_nested_cross_file_collision(
binary(),
binary(),
gleam@dict:dict(binary(), {binary(),
oaspec@internal@openapi@schema:schema_ref()})
) -> {ok, nil} | {error, oaspec@openapi@diagnostic:diagnostic()}.
check_nested_cross_file_collision(Fragment_name, Resolved_path, Imports) ->
case gleam_stdlib:map_get(Imports, Fragment_name) of
{error, _} ->
{ok, nil};
{ok, {Prev_path, _}} ->
case Prev_path =:= Resolved_path of
true ->
{ok, nil};
false ->
{error,
oaspec@openapi@diagnostic:validation(
Resolved_path,
<<<<<<<<<<<<"Nested property $ref imports schema '"/utf8,
Fragment_name/binary>>/binary,
"' from '"/utf8>>/binary,
Resolved_path/binary>>/binary,
"', but the same name was already imported from '"/utf8>>/binary,
Prev_path/binary>>/binary,
"'."/utf8>>,
severity_error,
target_both,
{some,
<<"Rename one of the schemas in the source files so imports do not collide."/utf8>>}
)}
end
end.
-file("src/oaspec/internal/openapi/external_loader_planner.gleam", 348).
?DOC(false).
-spec check_local_collision(binary(), binary(), binary(), list(binary())) -> {ok,
nil} |
{error, oaspec@openapi@diagnostic:diagnostic()}.
check_local_collision(
Entry_name,
Fragment_name,
Source_path,
Original_local_names
) ->
gleam@bool:guard(
Entry_name =:= Fragment_name,
{ok, nil},
fun() ->
gleam@bool:guard(
not gleam@list:contains(Original_local_names, Fragment_name),
{ok, nil},
fun() ->
{error,
oaspec@openapi@diagnostic:validation(
Source_path,
<<<<<<<<"External $ref imports schema '"/utf8,
Fragment_name/binary>>/binary,
"' from '"/utf8>>/binary,
Source_path/binary>>/binary,
"', but a local schema with the same name is already defined."/utf8>>,
severity_error,
target_both,
{some,
<<"Rename one of the colliding schemas, or point the external ref at a file whose fragment name is unique."/utf8>>}
)}
end
)
end
).
-file("src/oaspec/internal/openapi/external_loader_planner.gleam", 377).
?DOC(false).
-spec check_cross_file_collision(
binary(),
binary(),
gleam@dict:dict(binary(), binary())
) -> {ok, nil} | {error, oaspec@openapi@diagnostic:diagnostic()}.
check_cross_file_collision(Fragment_name, Resolved_path, Imported) ->
case gleam_stdlib:map_get(Imported, Fragment_name) of
{error, _} ->
{ok, nil};
{ok, Prev_path} ->
case Prev_path =:= Resolved_path of
true ->
{ok, nil};
false ->
{error,
oaspec@openapi@diagnostic:validation(
Resolved_path,
<<<<<<<<<<<<"External $ref imports schema '"/utf8,
Fragment_name/binary>>/binary,
"' from '"/utf8>>/binary,
Resolved_path/binary>>/binary,
"', but the same name was already imported from '"/utf8>>/binary,
Prev_path/binary>>/binary,
"'."/utf8>>,
severity_error,
target_both,
{some,
<<"Rename one of the schemas in the source files so imports do not collide."/utf8>>}
)}
end
end.
-file("src/oaspec/internal/openapi/external_loader_planner.gleam", 411).
?DOC(false).
-spec extract_external_ref(oaspec@internal@openapi@schema:schema_ref()) -> gleam@option:option({binary(),
binary()}).
extract_external_ref(Schema_ref) ->
case Schema_ref of
{reference, Ref, _} ->
case gleam_stdlib:string_starts_with(Ref, <<"./"/utf8>>) orelse gleam_stdlib:string_starts_with(
Ref,
<<"../"/utf8>>
) of
true ->
case gleam@string:split_once(Ref, <<"#"/utf8>>) of
{ok, {File_path, Fragment}} ->
case gleam_stdlib:string_starts_with(
Fragment,
<<"/components/schemas/"/utf8>>
) of
true ->
Name = gleam@string:replace(
Fragment,
<<"/components/schemas/"/utf8>>,
<<""/utf8>>
),
case {gleam_stdlib:contains_string(
Name,
<<"/"/utf8>>
),
Name} of
{false, <<""/utf8>>} ->
none;
{false, _} ->
{some, {File_path, Name}};
{true, _} ->
none
end;
false ->
none
end;
_ ->
none
end;
false ->
none
end;
_ ->
none
end.
-file("src/oaspec/internal/openapi/external_loader_planner.gleam", 28).
?DOC(false).
-spec local_schema_names(
list({binary(), oaspec@internal@openapi@schema:schema_ref()})
) -> list(binary()).
local_schema_names(Entries) ->
gleam@list:filter_map(
Entries,
fun(Entry) -> case extract_external_ref(erlang:element(2, Entry)) of
{some, _} ->
{error, nil};
none ->
{ok, erlang:element(1, Entry)}
end end
).
-file("src/oaspec/internal/openapi/external_loader_planner.gleam", 530).
?DOC(false).
-spec local_schema_name_from_ref(binary()) -> gleam@option:option(binary()).
local_schema_name_from_ref(Ref) ->
Prefix = <<"#/components/schemas/"/utf8>>,
case gleam_stdlib:string_starts_with(Ref, Prefix) of
true ->
Name = gleam@string:replace(Ref, Prefix, <<""/utf8>>),
case {gleam_stdlib:contains_string(Name, <<"/"/utf8>>), Name} of
{false, <<""/utf8>>} ->
none;
{false, _} ->
{some, Name};
{true, _} ->
none
end;
false ->
none
end.
-file("src/oaspec/internal/openapi/external_loader_planner.gleam", 467).
?DOC(false).
-spec find_schema_follow_alias(
oaspec@internal@openapi@spec:components(oaspec@internal@openapi@spec:unresolved()),
binary(),
binary()
) -> {ok, oaspec@internal@openapi@schema:schema_ref()} |
{error, oaspec@openapi@diagnostic:diagnostic()}.
find_schema_follow_alias(Components, Name, Source_path) ->
case gleam_stdlib:map_get(erlang:element(2, Components), Name) of
{ok, {inline, _} = S} ->
{ok, S};
{ok, {reference, Ref, _}} ->
case local_schema_name_from_ref(Ref) of
{some, Aliased} ->
case gleam_stdlib:map_get(
erlang:element(2, Components),
Aliased
) of
{ok, {inline, _} = S@1} ->
{ok, S@1};
_ ->
{error,
oaspec@openapi@diagnostic:validation(
Source_path,
<<<<<<<<<<<<"External schema '"/utf8,
Name/binary>>/binary,
"' in '"/utf8>>/binary,
Source_path/binary>>/binary,
"' aliases '"/utf8>>/binary,
Aliased/binary>>/binary,
"', but the target is itself a $ref or missing; only a single level of aliasing inside the same file is supported."/utf8>>,
severity_error,
target_both,
{some,
<<"Flatten the alias chain in the external file so the target resolves to an inline schema."/utf8>>}
)}
end;
none ->
{error,
oaspec@openapi@diagnostic:validation(
Source_path,
<<<<<<<<"External schema '"/utf8, Name/binary>>/binary,
"' in '"/utf8>>/binary,
Source_path/binary>>/binary,
"' is itself a $ref pointing outside this file; chained external refs are not supported yet."/utf8>>,
severity_error,
target_both,
{some,
<<"Inline the external schema or flatten the ref to live inside the same file."/utf8>>}
)}
end;
{error, nil} ->
{error,
oaspec@openapi@diagnostic:validation(
Source_path,
<<<<<<"External file '"/utf8, Source_path/binary>>/binary,
"' has no components.schemas."/utf8>>/binary,
Name/binary>>,
severity_error,
target_both,
{some,
<<"Verify the ref path and that the referenced file defines the schema."/utf8>>}
)}
end.
-file("src/oaspec/internal/openapi/external_loader_planner.gleam", 442).
?DOC(false).
-spec find_external_schema(
oaspec@internal@openapi@spec:open_api_spec(oaspec@internal@openapi@spec:unresolved()),
binary(),
binary()
) -> {ok, oaspec@internal@openapi@schema:schema_ref()} |
{error, oaspec@openapi@diagnostic:diagnostic()}.
find_external_schema(Loaded, Name, Source_path) ->
case erlang:element(5, Loaded) of
{some, Components} ->
find_schema_follow_alias(Components, Name, Source_path);
none ->
{error,
oaspec@openapi@diagnostic:validation(
Source_path,
<<<<"External file '"/utf8, Source_path/binary>>/binary,
"' has no components block."/utf8>>,
severity_error,
target_both,
{some,
<<"Add a components.schemas section to the referenced file or inline the schema."/utf8>>}
)}
end.
-file("src/oaspec/internal/openapi/external_loader_planner.gleam", 549).
?DOC(false).
-spec base_dir_of(binary()) -> gleam@option:option(binary()).
base_dir_of(Path) ->
case filepath:directory_name(Path) of
<<""/utf8>> ->
{some, <<"."/utf8>>};
Dir ->
{some, Dir}
end.