Packages
oaspec
0.24.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@codegen@schema_utils.erl
-module(oaspec@codegen@schema_utils).
-compile([no_auto_import, nowarn_unused_vars, nowarn_unused_function, nowarn_nomatch, inline]).
-define(FILEPATH, "src/oaspec/codegen/schema_utils.gleam").
-export([schema_has_additional_properties/2, schema_has_untyped_additional_properties/2, constant_property_value/3, schema_ref_is_nullable/2, schema_has_optional_fields/2, schema_ref_is_read_only/2, schema_ref_is_write_only/2, filter_read_only_properties/2, filter_write_only_properties/2]).
-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/codegen/schema_utils.gleam", 15).
?DOC(" Check if a schema has typed or untyped additionalProperties that would need Dict.\n").
-spec schema_has_additional_properties(
oaspec@openapi@schema:schema_ref(),
oaspec@codegen@context:context()
) -> boolean().
schema_has_additional_properties(Schema_ref, Ctx) ->
case Schema_ref of
{inline, {object_schema, _, _, _, {typed, _}, _, _}} ->
true;
{inline, {object_schema, _, _, _, untyped, _, _}} ->
true;
{inline, {all_of_schema, _, Schemas}} ->
gleam@list:any(
Schemas,
fun(S) -> schema_has_additional_properties(S, Ctx) end
);
{reference, _, _} ->
case oaspec@openapi@resolver:resolve_schema_ref(
Schema_ref,
oaspec@codegen@context:spec(Ctx)
) of
{ok, Schema_obj} ->
schema_has_additional_properties({inline, Schema_obj}, Ctx);
{error, _} ->
false
end;
_ ->
false
end.
-file("src/oaspec/codegen/schema_utils.gleam", 36).
?DOC(" Check if a schema has untyped additionalProperties (needs Dynamic import).\n").
-spec schema_has_untyped_additional_properties(
oaspec@openapi@schema:schema_ref(),
oaspec@codegen@context:context()
) -> boolean().
schema_has_untyped_additional_properties(Schema_ref, Ctx) ->
case Schema_ref of
{inline, {object_schema, _, _, _, untyped, _, _}} ->
true;
{inline, {all_of_schema, _, Schemas}} ->
gleam@list:any(
Schemas,
fun(S) -> schema_has_untyped_additional_properties(S, Ctx) end
);
{reference, _, _} ->
case oaspec@openapi@resolver:resolve_schema_ref(
Schema_ref,
oaspec@codegen@context:spec(Ctx)
) of
{ok, Schema_obj} ->
schema_has_untyped_additional_properties(
{inline, Schema_obj},
Ctx
);
{error, _} ->
false
end;
_ ->
false
end.
-file("src/oaspec/codegen/schema_utils.gleam", 92).
?DOC(
" Issue #309: detect a property that is fully determined by the\n"
" schema — an inline string-enum with exactly one allowed value that\n"
" the parent schema lists as required. Such a property is a constant\n"
" marker on the wire (e.g. a `kind: type: string, enum: [text]`\n"
" discriminator on a oneOf variant): the only legal value is known\n"
" at codegen time, so the generated record drops the field, the\n"
" encoder emits the constant, and the decoder validates it.\n"
"\n"
" Returns `Some(value)` for an elidable constant property; `None`\n"
" otherwise (including `$ref`s, multi-value enums, optional\n"
" properties, and non-string schemas — those keep their current\n"
" record-field shape).\n"
).
-spec constant_property_value(
oaspec@openapi@schema:schema_ref(),
binary(),
list(binary())
) -> gleam@option:option(binary()).
constant_property_value(Prop_ref, Prop_name, Required) ->
case {gleam@list:contains(Required, Prop_name), Prop_ref} of
{true, {inline, {string_schema, _, _, [Single_value], _, _, _}}} ->
{some, Single_value};
{_, _} ->
none
end.
-file("src/oaspec/codegen/schema_utils.gleam", 105).
?DOC(" Check if a SchemaRef is nullable, resolving $ref if needed.\n").
-spec schema_ref_is_nullable(
oaspec@openapi@schema:schema_ref(),
oaspec@codegen@context:context()
) -> boolean().
schema_ref_is_nullable(Ref, Ctx) ->
case Ref of
{inline, Inline_schema} ->
oaspec@openapi@schema:is_nullable(Inline_schema);
{reference, _, _} ->
case oaspec@openapi@resolver:resolve_schema_ref(
Ref,
oaspec@codegen@context:spec(Ctx)
) of
{ok, Resolved} ->
oaspec@openapi@schema:is_nullable(Resolved);
{error, _} ->
false
end
end.
-file("src/oaspec/codegen/schema_utils.gleam", 58).
?DOC(" Check if a schema has any optional or nullable fields that would need Option.\n").
-spec schema_has_optional_fields(
oaspec@openapi@schema:schema_ref(),
oaspec@codegen@context:context()
) -> boolean().
schema_has_optional_fields(Schema_ref, Ctx) ->
case Schema_ref of
{inline, {object_schema, _, Properties, Required, _, _, _}} ->
_pipe = maps:to_list(Properties),
gleam@list:any(
_pipe,
fun(Entry) ->
{Prop_name, Prop_ref} = Entry,
not gleam@list:contains(Required, Prop_name) orelse schema_ref_is_nullable(
Prop_ref,
Ctx
)
end
);
{inline, {all_of_schema, _, Schemas}} ->
gleam@list:any(
Schemas,
fun(S) -> schema_has_optional_fields(S, Ctx) end
);
{reference, _, _} ->
case oaspec@openapi@resolver:resolve_schema_ref(
Schema_ref,
oaspec@codegen@context:spec(Ctx)
) of
{ok, Schema_obj} ->
schema_has_optional_fields({inline, Schema_obj}, Ctx);
{error, _} ->
false
end;
_ ->
false
end.
-file("src/oaspec/codegen/schema_utils.gleam", 118).
?DOC(" Check if a SchemaRef has readOnly metadata, resolving $ref if needed.\n").
-spec schema_ref_is_read_only(
oaspec@openapi@schema:schema_ref(),
oaspec@codegen@context:context()
) -> boolean().
schema_ref_is_read_only(Ref, Ctx) ->
case Ref of
{inline, Inline_schema} ->
erlang:element(6, oaspec@openapi@schema:get_metadata(Inline_schema));
{reference, _, _} ->
case oaspec@openapi@resolver:resolve_schema_ref(
Ref,
oaspec@codegen@context:spec(Ctx)
) of
{ok, Resolved} ->
erlang:element(
6,
oaspec@openapi@schema:get_metadata(Resolved)
);
{error, _} ->
false
end
end.
-file("src/oaspec/codegen/schema_utils.gleam", 131).
?DOC(" Check if a SchemaRef has writeOnly metadata, resolving $ref if needed.\n").
-spec schema_ref_is_write_only(
oaspec@openapi@schema:schema_ref(),
oaspec@codegen@context:context()
) -> boolean().
schema_ref_is_write_only(Ref, Ctx) ->
case Ref of
{inline, Inline_schema} ->
erlang:element(7, oaspec@openapi@schema:get_metadata(Inline_schema));
{reference, _, _} ->
case oaspec@openapi@resolver:resolve_schema_ref(
Ref,
oaspec@codegen@context:spec(Ctx)
) of
{ok, Resolved} ->
erlang:element(
7,
oaspec@openapi@schema:get_metadata(Resolved)
);
{error, _} ->
false
end
end.
-file("src/oaspec/codegen/schema_utils.gleam", 145).
?DOC(
" Filter readOnly properties from an ObjectSchema for request body context.\n"
" Returns a new schema with readOnly properties removed.\n"
).
-spec filter_read_only_properties(
oaspec@openapi@schema:schema_object(),
oaspec@codegen@context:context()
) -> oaspec@openapi@schema:schema_object().
filter_read_only_properties(Schema_obj, Ctx) ->
case Schema_obj of
{object_schema,
Metadata,
Properties,
Required,
Additional_properties,
Min_properties,
Max_properties} ->
Filtered_props = gleam@dict:filter(
Properties,
fun(_, Prop_ref) ->
not schema_ref_is_read_only(Prop_ref, Ctx)
end
),
Filtered_required = gleam@list:filter(
Required,
fun(Name) -> case gleam_stdlib:map_get(Filtered_props, Name) of
{ok, _} ->
true;
{error, _} ->
false
end end
),
{object_schema,
Metadata,
Filtered_props,
Filtered_required,
Additional_properties,
Min_properties,
Max_properties};
_ ->
Schema_obj
end.
-file("src/oaspec/codegen/schema_utils.gleam", 185).
?DOC(
" Filter writeOnly properties from an ObjectSchema for response body context.\n"
" Returns a new schema with writeOnly properties removed.\n"
).
-spec filter_write_only_properties(
oaspec@openapi@schema:schema_object(),
oaspec@codegen@context:context()
) -> oaspec@openapi@schema:schema_object().
filter_write_only_properties(Schema_obj, Ctx) ->
case Schema_obj of
{object_schema,
Metadata,
Properties,
Required,
Additional_properties,
Min_properties,
Max_properties} ->
Filtered_props = gleam@dict:filter(
Properties,
fun(_, Prop_ref) ->
not schema_ref_is_write_only(Prop_ref, Ctx)
end
),
Filtered_required = gleam@list:filter(
Required,
fun(Name) -> case gleam_stdlib:map_get(Filtered_props, Name) of
{ok, _} ->
true;
{error, _} ->
false
end end
),
{object_schema,
Metadata,
Filtered_props,
Filtered_required,
Additional_properties,
Min_properties,
Max_properties};
_ ->
Schema_obj
end.