Current section

Files

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

src/oaspec@openapi@capability_check.erl

-module(oaspec@openapi@capability_check).
-compile([no_auto_import, nowarn_unused_vars, nowarn_unused_function, nowarn_nomatch, inline]).
-define(FILEPATH, "src/oaspec/openapi/capability_check.gleam").
-export([check/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.
-file("src/oaspec/openapi/capability_check.gleam", 102).
?DOC(" Check security schemes for unsupported types (e.g. mutualTLS).\n").
-spec check_security_schemes(
oaspec@openapi@spec:open_api_spec(oaspec@openapi@spec:spec_stage())
) -> list(oaspec@codegen@validate:validation_error()).
check_security_schemes(Spec) ->
case erlang:element(5, Spec) of
none ->
[];
{some, Components} ->
_pipe = maps:to_list(erlang:element(6, Components)),
gleam@list:filter_map(
_pipe,
fun(Entry) ->
{_, Ref_or} = Entry,
case Ref_or of
{value, _} ->
{error, nil};
_ ->
{error, nil}
end
end
)
end.
-file("src/oaspec/openapi/capability_check.gleam", 123).
?DOC(" Check for parsed-but-unused features using the capability registry.\n").
-spec check_scope(
oaspec@openapi@spec:open_api_spec(oaspec@openapi@spec:spec_stage())
) -> list(oaspec@codegen@validate:validation_error()).
check_scope(Spec) ->
Webhook_w = case gleam@dict:is_empty(erlang:element(8, Spec)) of
true ->
[];
false ->
[{validation_error,
<<"webhooks"/utf8>>,
<<"Webhooks are parsed but not used by code generation."/utf8>>,
severity_warning,
target_both}]
end,
External_docs_w = case erlang:element(10, Spec) of
{some, _} ->
[{validation_error,
<<"externalDocs"/utf8>>,
<<"External docs are parsed but not used by code generation."/utf8>>,
severity_warning,
target_both}];
none ->
[]
end,
Tags_w = case gleam@list:is_empty(erlang:element(9, Spec)) of
true ->
[];
false ->
[{validation_error,
<<"tags"/utf8>>,
<<"Top-level tags are parsed but not used by code generation."/utf8>>,
severity_warning,
target_both}]
end,
Server_w = begin
_pipe = maps:to_list(erlang:element(4, Spec)),
gleam@list:flat_map(
_pipe,
fun(Entry) ->
{Path, Ref_or} = Entry,
case Ref_or of
{value, Path_item} ->
Path_w = case gleam@list:is_empty(
erlang:element(13, Path_item)
) of
true ->
[];
false ->
[{validation_error,
<<<<"paths."/utf8, Path/binary>>/binary,
".servers"/utf8>>,
<<"Path-level servers are parsed but client uses only top-level server URL."/utf8>>,
severity_warning,
target_client}]
end,
Path_w;
_ ->
[]
end
end
)
end,
Comp_w = case erlang:element(5, Spec) of
{some, C} ->
H = case gleam@dict:is_empty(erlang:element(8, C)) of
true ->
[];
false ->
[{validation_error,
<<"components.headers"/utf8>>,
<<"Component headers are parsed but not used by code generation."/utf8>>,
severity_warning,
target_both}]
end,
L = case gleam@dict:is_empty(erlang:element(10, C)) of
true ->
[];
false ->
[{validation_error,
<<"components.links"/utf8>>,
<<"Component links are parsed but not used by code generation."/utf8>>,
severity_warning,
target_both}]
end,
lists:append(H, L);
none ->
[]
end,
lists:append([Webhook_w, External_docs_w, Tags_w, Server_w, Comp_w]).
-file("src/oaspec/openapi/capability_check.gleam", 48).
?DOC(" Check a single schema and recurse into children.\n").
-spec check_schema(binary(), oaspec@openapi@schema:schema_object()) -> list(oaspec@codegen@validate:validation_error()).
check_schema(Path, Schema_obj) ->
Metadata = oaspec@openapi@schema:get_metadata(Schema_obj),
Keyword_errors = case erlang:element(12, Metadata) of
[] ->
[];
Keywords ->
Keyword_list = gleam@string:join(Keywords, <<"', '"/utf8>>),
[{validation_error,
Path,
<<<<<<"Unsupported JSON Schema keyword '"/utf8,
Keyword_list/binary>>/binary,
"' found. Remove or model differently. See: "/utf8>>/binary,
(gleam@string:join(
gleam@list:filter_map(
Keywords,
fun(K) ->
_pipe = gleam@list:find(
oaspec@capability:registry(),
fun(C) -> erlang:element(2, C) =:= K end
),
gleam@result:map(
_pipe,
fun(C@1) -> erlang:element(5, C@1) end
)
end
),
<<"; "/utf8>>
))/binary>>,
severity_error,
target_both}]
end,
Child_errors = case Schema_obj of
{object_schema, _, Properties, _, Additional_properties, _, _, _} ->
Prop_errors = begin
_pipe@1 = maps:to_list(Properties),
gleam@list:flat_map(
_pipe@1,
fun(E) ->
check_schema_ref(
<<<<Path/binary, "."/utf8>>/binary,
(erlang:element(1, E))/binary>>,
erlang:element(2, E)
)
end
)
end,
Ap_errors = case Additional_properties of
{some, Ap} ->
check_schema_ref(
<<Path/binary, ".additionalProperties"/utf8>>,
Ap
);
none ->
[]
end,
lists:append(Prop_errors, Ap_errors);
{array_schema, _, Items, _, _, _} ->
check_schema_ref(<<Path/binary, ".items"/utf8>>, Items);
{all_of_schema, _, Schemas} ->
gleam@list:flat_map(
Schemas,
fun(S) ->
check_schema_ref(<<Path/binary, ".allOf"/utf8>>, S)
end
);
{one_of_schema, _, Schemas@1, _} ->
gleam@list:flat_map(
Schemas@1,
fun(S@1) ->
check_schema_ref(<<Path/binary, ".oneOf"/utf8>>, S@1)
end
);
{any_of_schema, _, Schemas@2, _} ->
gleam@list:flat_map(
Schemas@2,
fun(S@2) ->
check_schema_ref(<<Path/binary, ".anyOf"/utf8>>, S@2)
end
);
_ ->
[]
end,
lists:append(Keyword_errors, Child_errors).
-file("src/oaspec/openapi/capability_check.gleam", 40).
?DOC(" Check a SchemaRef recursively for unsupported keywords.\n").
-spec check_schema_ref(binary(), oaspec@openapi@schema:schema_ref()) -> list(oaspec@codegen@validate:validation_error()).
check_schema_ref(Path, Ref) ->
case Ref of
{reference, _, _} ->
[];
{inline, Schema_obj} ->
check_schema(Path, Schema_obj)
end.
-file("src/oaspec/openapi/capability_check.gleam", 27).
?DOC(" Check all schemas for unsupported keywords stored during lossless parse.\n").
-spec check_schemas(
oaspec@openapi@spec:open_api_spec(oaspec@openapi@spec:spec_stage())
) -> list(oaspec@codegen@validate:validation_error()).
check_schemas(Spec) ->
case erlang:element(5, Spec) of
none ->
[];
{some, Components} ->
_pipe = maps:to_list(erlang:element(2, Components)),
gleam@list:flat_map(
_pipe,
fun(Entry) ->
{Name, Schema_ref} = Entry,
check_schema_ref(
<<"components.schemas."/utf8, Name/binary>>,
Schema_ref
)
end
)
end.
-file("src/oaspec/openapi/capability_check.gleam", 19).
?DOC(
" Run capability checks on a resolved spec.\n"
" Returns errors for unsupported features and warnings for parsed-but-unused features.\n"
).
-spec check(oaspec@openapi@spec:open_api_spec(oaspec@openapi@spec:spec_stage())) -> list(oaspec@codegen@validate:validation_error()).
check(Spec) ->
Schema_errors = check_schemas(Spec),
Security_errors = check_security_schemes(Spec),
Scope_warnings = check_scope(Spec),
lists:append([Schema_errors, Security_errors, Scope_warnings]).