Skip to content

Commit faaa55f

Browse files
committed
feat: use typed ecto schemas in generated models
1 parent 9eefc09 commit faaa55f

59 files changed

Lines changed: 779 additions & 975 deletions

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

modules/openapi-generator/src/main/java/org/openapitools/codegen/languages/ElixirClientCodegen.java

Lines changed: 36 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -61,6 +61,7 @@ public class ElixirClientCodegen extends DefaultCodegen {
6161
List<String> extraApplications = Arrays.asList(":logger");
6262
List<String> deps = Arrays.asList(
6363
"{:tesla, \"~> 1.7\"}",
64+
"{:typed_ecto_schema, \"~> 0.4.1\"}",
6465
"{:ex_doc, \"~> 0.30\", only: :dev, runtime: false}",
6566
"{:dialyxir, \"~> 1.3\", only: [:dev, :test], runtime: false}");
6667

@@ -302,6 +303,12 @@ public void execute(Template.Fragment fragment, Writer writer) throws IOExceptio
302303
writer.write(text.toUpperCase(Locale.ROOT));
303304
}
304305
});
306+
additionalProperties.put("toEctoType", new Mustache.Lambda() {
307+
@Override
308+
public void execute(Template.Fragment fragment, Writer writer) throws IOException {
309+
writer.write(toEctoType(fragment.execute()));
310+
}
311+
});
305312

306313
if (additionalProperties.containsKey(CodegenConstants.INVOKER_PACKAGE)) {
307314
setModuleName((String) additionalProperties.get(CodegenConstants.INVOKER_PACKAGE));
@@ -336,10 +343,6 @@ public void preprocessOpenAPI(OpenAPI openAPI) {
336343
supportingFiles.add(new SupportingFile("request_builder.ex.mustache",
337344
sourceFolder(),
338345
"request_builder.ex"));
339-
340-
supportingFiles.add(new SupportingFile("deserializer.ex.mustache",
341-
sourceFolder(),
342-
"deserializer.ex"));
343346
}
344347

345348
@Override
@@ -439,6 +442,35 @@ private String atomized(String text) {
439442
return atom.toString();
440443
}
441444

445+
private String toEctoType(String baseType) {
446+
switch (baseType) {
447+
case "integer()":
448+
return ":integer";
449+
case "float()":
450+
return ":float";
451+
case "number()":
452+
return ":float";
453+
case "boolean()":
454+
return ":boolean";
455+
case "String.t":
456+
return ":string";
457+
case "Date.t":
458+
return ":date";
459+
case "DateTime.t":
460+
return ":utc_datetime";
461+
case "binary()":
462+
return ":binary";
463+
case "list()":
464+
return "{:array, :any}";
465+
case "map()":
466+
return ":map";
467+
case "nil":
468+
return ":any, virtual: true";
469+
default:
470+
return ":any, virtual: true";
471+
}
472+
}
473+
442474
/**
443475
* Escapes a reserved word as defined in the `reservedWords` array. Handle
444476
* escaping

modules/openapi-generator/src/main/resources/elixir/deserializer.ex.mustache

Lines changed: 0 additions & 114 deletions
This file was deleted.

modules/openapi-generator/src/main/resources/elixir/model.mustache

Lines changed: 20 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -3,34 +3,29 @@
33
@moduledoc """
44
{{&description}}
55
"""
6+
use TypedEctoSchema
67

7-
@derive JSON.Encoder
8-
defstruct [
9-
{{#vars}}{{#atom}}{{&baseName}}{{/atom}}{{^-last}},
10-
{{/-last}}{{/vars}}
11-
]
12-
13-
@type t :: %__MODULE__{
14-
{{#vars}}{{#atom}}{{&baseName}}{{/atom}} => {{{datatype}}}{{#isNullable}} | nil{{/isNullable}}{{^isNullable}}{{^required}} | nil{{/required}}{{/isNullable}}{{^-last}},
15-
{{/-last}}{{/vars}}
16-
}
17-
18-
{{#hasComplexVars}}
19-
alias {{&moduleName}}.Deserializer
20-
21-
def decode(value) do
22-
value
23-
{{#vars}}
8+
@derive {JSON.Encoder, only: [{{#vars}}{{#atom}}{{&baseName}}{{/atom}}{{^-last}}, {{/-last}}{{/vars}}]}
9+
@primary_key false
10+
typed_embedded_schema do
11+
{{#vars}}
12+
{{#isPrimitiveType}}
13+
field {{#atom}}{{&baseName}}{{/atom}}, {{#toEctoType}}{{{baseType}}}{{/toEctoType}}{{#required}}, null: false{{/required}}
14+
{{/isPrimitiveType}}
2415
{{^isPrimitiveType}}
25-
{{#baseType}} |> Deserializer.deserialize({{#atom}}{{&baseName}}{{/atom}}, {{#isArray}}:list, {{&moduleName}}.Model.{{{items.baseType}}}{{/isArray}}{{#isMap}}:map, {{&moduleName}}.Model.{{{items.baseType}}}{{/isMap}}{{#isDate}}:date, nil{{/isDate}}{{#isDateTime}}:datetime, nil{{/isDateTime}}{{^isDate}}{{^isDateTime}}{{^isMap}}{{^isArray}}:struct, {{moduleName}}.Model.{{baseType}}{{/isArray}}{{/isMap}}{{/isDateTime}}{{/isDate}})
26-
{{/baseType}}
16+
{{^isArray}}embeds_one{{/isArray}}{{#isArray}}embeds_many{{/isArray}} {{#atom}}{{&baseName}}{{/atom}}, {{&moduleName}}.Model.{{^isArray}}{{{baseType}}}{{/isArray}}{{#isArray}}{{{items.baseType}}}{{/isArray}}{{#isNullable}}, null: true{{/isNullable}}
2717
{{/isPrimitiveType}}
28-
{{/vars}}
29-
{{/hasComplexVars}}
30-
{{^hasComplexVars}}
31-
def decode(value) do
32-
value
33-
{{/hasComplexVars}}
18+
{{/vars}}
19+
end
20+
21+
@spec new(map()) :: t()
22+
def new(params) do
23+
%__MODULE__{}
24+
|> Ecto.Changeset.cast(params, [{{#vars}}{{#isPrimitiveType}}{{#atom}}{{&baseName}}{{/atom}}{{^-last}}, {{/-last}}{{/isPrimitiveType}}{{/vars}}])
25+
|> Ecto.Changeset.validate_required([{{#vars}}{{#isPrimitiveType}}{{#required}}{{#atom}}{{&baseName}}{{/atom}}{{^-last}}, {{/-last}}{{/required}}{{/isPrimitiveType}}{{/vars}}])
26+
{{#vars}}{{^isPrimitiveType}}
27+
|> Ecto.Changeset.cast_embed({{#atom}}{{&baseName}}{{/atom}}{{#required}}, required: true{{/required}})
28+
{{/isPrimitiveType}}{{/vars}} |> Ecto.Changeset.apply_action!(:insert)
3429
end
3530
end
3631
{{/model}}{{/models}}

modules/openapi-generator/src/main/resources/elixir/request_builder.ex.mustache

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -187,10 +187,12 @@ defmodule {{moduleName}}.RequestBuilder do
187187
defp decode(%Tesla.Env{} = env, false), do: {:ok, env}
188188

189189
defp decode(%Tesla.Env{body: body}, %{}) do
190-
{{moduleName}}.Deserializer.json_decode(body)
190+
JSON.decode!(body)
191191
end
192192

193193
defp decode(%Tesla.Env{body: body}, module) do
194-
{{moduleName}}.Deserializer.json_decode(body, module)
194+
body
195+
|> JSON.decode!
196+
|> module.new
195197
end
196198
end

samples/client/petstore/elixir/.openapi-generator/FILES

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,6 @@ lib/openapi_petstore/api/pet.ex
1111
lib/openapi_petstore/api/store.ex
1212
lib/openapi_petstore/api/user.ex
1313
lib/openapi_petstore/connection.ex
14-
lib/openapi_petstore/deserializer.ex
1514
lib/openapi_petstore/model/_foo_get_default_response.ex
1615
lib/openapi_petstore/model/_special_model_name_.ex
1716
lib/openapi_petstore/model/additional_properties_class.ex

samples/client/petstore/elixir/lib/openapi_petstore/deserializer.ex

Lines changed: 0 additions & 116 deletions
This file was deleted.

0 commit comments

Comments
 (0)