Skip to content

Commit

Permalink
feat(client): support ability to disable boxed models
Browse files Browse the repository at this point in the history
Add new additional property `avoidBoxedModels` which can be configured to avoid `Box<..>` of models.

It's very nice to have such config, because it doesn't make a lot of sense for really simple models.
  • Loading branch information
DDtKey committed Feb 24, 2024
1 parent 6e11384 commit 026d393
Show file tree
Hide file tree
Showing 188 changed files with 3,834 additions and 39 deletions.
3 changes: 2 additions & 1 deletion bin/configs/rust-hyper-oneOf.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -4,5 +4,6 @@ library: hyper
inputSpec: modules/openapi-generator/src/test/resources/3_0/oneof_polymorphism_and_inheritance.yaml
templateDir: modules/openapi-generator/src/main/resources/rust
additionalProperties:
supportAsync: "false"
supportAsync: false
avoidBoxedModels: true
packageName: oneof-hyper
11 changes: 11 additions & 0 deletions bin/configs/rust-reqwest-petstore-avoid-box.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
generatorName: rust
outputDir: samples/client/petstore/rust/reqwest/petstore-avoid-box
library: reqwest
inputSpec: modules/openapi-generator/src/test/resources/3_0/rust/petstore.yaml
templateDir: modules/openapi-generator/src/main/resources/rust
additionalProperties:
supportAsync: true
supportMultipleResponses: true
avoidBoxedModels: true
packageName: petstore-reqwest-avoid-box
useSingleRequestParameter: true
1 change: 1 addition & 0 deletions docs/generators/rust.md
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@ These options may be applied as additional-properties (cli) or configOptions (pl

| Option | Description | Values | Default |
| ------ | ----------- | ------ | ------- |
|avoidBoxedModels|If set, `Box&lt;T&gt;` will not be used for models| |false|
|bestFitInt|Use best fitting integer type where minimum or maximum is set| |false|
|enumNameSuffix|Suffix that will be appended to all enum names.| ||
|hideGenerationTimestamp|Hides the generation timestamp when files are generated.| |true|
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,7 @@ public class RustClientCodegen extends AbstractRustCodegen implements CodegenCon
private boolean withAWSV4Signature = false;
private boolean preferUnsignedInt = false;
private boolean bestFitInt = false;
private boolean avoidBoxedModels = false;

public static final String PACKAGE_NAME = "packageName";
public static final String PACKAGE_VERSION = "packageVersion";
Expand All @@ -60,6 +61,7 @@ public class RustClientCodegen extends AbstractRustCodegen implements CodegenCon
public static final String SUPPORT_MULTIPLE_RESPONSES = "supportMultipleResponses";
public static final String PREFER_UNSIGNED_INT = "preferUnsignedInt";
public static final String BEST_FIT_INT = "bestFitInt";
public static final String AVOID_BOXED_MODELS = "avoidBoxedModels";

protected String packageName = "openapi";
protected String packageVersion = "1.0.0";
Expand Down Expand Up @@ -192,6 +194,8 @@ public RustClientCodegen() {
.defaultValue(Boolean.FALSE.toString()));
cliOptions.add(new CliOption(BEST_FIT_INT, "Use best fitting integer type where minimum or maximum is set", SchemaTypeUtil.BOOLEAN_TYPE)
.defaultValue(Boolean.FALSE.toString()));
cliOptions.add(new CliOption(AVOID_BOXED_MODELS, "If set, `Box<T>` will not be used for models", SchemaTypeUtil.BOOLEAN_TYPE)
.defaultValue(Boolean.FALSE.toString()));

supportedLibraries.put(HYPER_LIBRARY, "HTTP client: Hyper.");
supportedLibraries.put(REQWEST_LIBRARY, "HTTP client: Reqwest.");
Expand Down Expand Up @@ -341,6 +345,11 @@ public void processOpts() {
}
writePropertyBack(BEST_FIT_INT, getBestFitInt());

if (additionalProperties.containsKey(AVOID_BOXED_MODELS)) {
this.setAvoidBoxedModels(convertPropertyToBoolean(AVOID_BOXED_MODELS));
}
writePropertyBack(AVOID_BOXED_MODELS, getAvoidBoxedModels());

additionalProperties.put(CodegenConstants.PACKAGE_NAME, packageName);
additionalProperties.put(CodegenConstants.PACKAGE_VERSION, packageVersion);

Expand Down Expand Up @@ -437,6 +446,14 @@ private void setUseSingleRequestParameter(boolean useSingleRequestParameter) {
this.useSingleRequestParameter = useSingleRequestParameter;
}

public boolean getAvoidBoxedModels() {
return avoidBoxedModels;
}

public void setAvoidBoxedModels(boolean avoidBoxedModels) {
this.avoidBoxedModels = avoidBoxedModels;
}

@Override
public String apiFileFolder() {
return (outputFolder + File.separator + apiFolder).replace("/", File.separator);
Expand Down Expand Up @@ -602,5 +619,4 @@ public String toDefaultValue(Schema p) {
return null;
}
}

}
14 changes: 7 additions & 7 deletions modules/openapi-generator/src/main/resources/rust/model.mustache
Original file line number Diff line number Diff line change
Expand Up @@ -52,7 +52,7 @@ pub enum {{{classname}}} {
/// {{{.}}}
{{/description}}
#[serde(rename = "{{{baseName}}}"{{^required}}, skip_serializing_if = "Option::is_none"{{/required}})]
{{{name}}}: {{#required}}{{#isNullable}}Option<{{/isNullable}}{{/required}}{{^required}}Option<{{/required}}{{#isEnum}}{{{enumName}}}{{/isEnum}}{{^isEnum}}{{#isModel}}Box<{{{dataType}}}>{{/isModel}}{{^isModel}}{{{dataType}}}{{/isModel}}{{/isEnum}}{{#required}}{{#isNullable}}>{{/isNullable}}{{/required}}{{^required}}>{{/required}},
{{{name}}}: {{#required}}{{#isNullable}}Option<{{/isNullable}}{{/required}}{{^required}}Option<{{/required}}{{#isEnum}}{{{enumName}}}{{/isEnum}}{{^isEnum}}{{#isModel}}{{^avoidBoxedModels}}Box<{{/avoidBoxedModels}}{{{dataType}}}{{^avoidBoxedModels}}>{{/avoidBoxedModels}}{{/isModel}}{{^isModel}}{{{dataType}}}{{/isModel}}{{/isEnum}}{{#required}}{{#isNullable}}>{{/isNullable}}{{/required}}{{^required}}>{{/required}},
{{/vars}}
},
{{/mappedModels}}
Expand All @@ -65,7 +65,7 @@ pub enum {{{classname}}} {
{{#baseName}}
#[serde(rename="{{{.}}}")]
{{/baseName}}
{{{name}}}(Box<{{{dataType}}}>),
{{{name}}}({{#isModel}}{{^avoidBoxedModels}}Box<{{/avoidBoxedModels}}{{/isModel}}{{{dataType}}}{{#isModel}}{{^avoidBoxedModels}}>{{/avoidBoxedModels}}{{/isModel}}),
{{/composedSchemas.oneOf}}
{{/oneOf.isEmpty}}
}
Expand All @@ -77,7 +77,7 @@ impl Default for {{classname}} {
{{{name}}}: Default::default(),
{{/vars}}
}{{/-first}}{{/mappedModels}}
{{/oneOf}}{{^oneOf.isEmpty}}{{#composedSchemas.oneOf}}{{#-first}}Self::{{{name}}}(Box::default()){{/-first}}{{/composedSchemas.oneOf}}{{/oneOf.isEmpty}}
{{/oneOf}}{{^oneOf.isEmpty}}{{#composedSchemas.oneOf}}{{#-first}}Self::{{{name}}}(Default::default()){{/-first}}{{/composedSchemas.oneOf}}{{/oneOf.isEmpty}}
}
}

Expand All @@ -93,7 +93,7 @@ pub struct {{{classname}}} {
/// {{{.}}}
{{/description}}
#[serde(rename = "{{{baseName}}}"{{^required}}{{#isNullable}}, default, with = "::serde_with::rust::double_option"{{/isNullable}}{{/required}}{{^required}}, skip_serializing_if = "Option::is_none"{{/required}}{{#required}}{{#isNullable}}, deserialize_with = "Option::deserialize"{{/isNullable}}{{/required}})]
pub {{{name}}}: {{#isNullable}}Option<{{/isNullable}}{{^required}}Option<{{/required}}{{#isEnum}}{{#isArray}}{{#uniqueItems}}std::collections::HashSet<{{/uniqueItems}}{{^uniqueItems}}Vec<{{/uniqueItems}}{{/isArray}}{{{enumName}}}{{#isArray}}>{{/isArray}}{{/isEnum}}{{^isEnum}}{{#isModel}}Box<{{{dataType}}}>{{/isModel}}{{^isModel}}{{{dataType}}}{{/isModel}}{{/isEnum}}{{#isNullable}}>{{/isNullable}}{{^required}}>{{/required}},
pub {{{name}}}: {{#isNullable}}Option<{{/isNullable}}{{^required}}Option<{{/required}}{{#isEnum}}{{#isArray}}{{#uniqueItems}}std::collections::HashSet<{{/uniqueItems}}{{^uniqueItems}}Vec<{{/uniqueItems}}{{/isArray}}{{{enumName}}}{{#isArray}}>{{/isArray}}{{/isEnum}}{{^isEnum}}{{#isModel}}{{^avoidBoxedModels}}Box<{{/avoidBoxedModels}}{{{dataType}}}{{^avoidBoxedModels}}>{{/avoidBoxedModels}}{{/isModel}}{{^isModel}}{{{dataType}}}{{/isModel}}{{/isEnum}}{{#isNullable}}>{{/isNullable}}{{^required}}>{{/required}},
{{/vars}}
}

Expand All @@ -104,7 +104,7 @@ impl {{{classname}}} {
pub fn new({{#requiredVars}}{{{name}}}: {{#isNullable}}Option<{{/isNullable}}{{#isEnum}}{{#isArray}}{{#uniqueItems}}std::collections::HashSet<{{/uniqueItems}}{{^uniqueItems}}Vec<{{/uniqueItems}}{{/isArray}}{{{enumName}}}{{#isArray}}>{{/isArray}}{{/isEnum}}{{^isEnum}}{{{dataType}}}{{/isEnum}}{{#isNullable}}>{{/isNullable}}{{^-last}}, {{/-last}}{{/requiredVars}}) -> {{{classname}}} {
{{{classname}}} {
{{#vars}}
{{{name}}}{{^required}}: None{{/required}}{{#required}}{{#isModel}}: {{^isNullable}}Box::new({{{name}}}){{/isNullable}}{{#isNullable}}if let Some(x) = {{{name}}} {Some(Box::new(x))} else {None}{{/isNullable}}{{/isModel}}{{/required}},
{{{name}}}{{^required}}: None{{/required}}{{#required}}{{#isModel}}{{^avoidBoxedModels}}: {{^isNullable}}Box::new({{{name}}}){{/isNullable}}{{#isNullable}}if let Some(x) = {{{name}}} {Some(Box::new(x))} else {None}{{/isNullable}}{{/avoidBoxedModels}}{{/isModel}}{{/required}},
{{/vars}}
}
}
Expand All @@ -122,13 +122,13 @@ pub enum {{classname}} {
{{#description}}
/// {{{.}}}
{{/description}}
{{{name}}}(Box<{{{dataType}}}>),
{{{name}}}({{#isModel}}{{^avoidBoxedModels}}Box<{{/avoidBoxedModels}}{{/isModel}}{{{dataType}}}{{#isModel}}{{^avoidBoxedModels}}>{{/avoidBoxedModels}}{{/isModel}}),
{{/composedSchemas.oneOf}}
}

impl Default for {{classname}} {
fn default() -> Self {
{{#composedSchemas.oneOf}}{{#-first}}Self::{{{name}}}(Box::default()){{/-first}}{{/composedSchemas.oneOf}}
{{#composedSchemas.oneOf}}{{#-first}}Self::{{{name}}}(Default::default()){{/-first}}{{/composedSchemas.oneOf}}
}
}
{{/oneOf.isEmpty}}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,7 @@ public void testSettersForConfigValues() throws Exception {
codegen.setHideGenerationTimestamp(false);
codegen.setPreferUnsignedInt(true);
codegen.setBestFitInt(true);
codegen.setAvoidBoxedModels(true);
codegen.processOpts();

Assert.assertEquals(codegen.additionalProperties().get(CodegenConstants.HIDE_GENERATION_TIMESTAMP), Boolean.FALSE);
Expand All @@ -58,6 +59,9 @@ public void testSettersForConfigValues() throws Exception {

Assert.assertEquals(codegen.additionalProperties().get(RustClientCodegen.BEST_FIT_INT), Boolean.TRUE);
Assert.assertTrue(codegen.getBestFitInt());

Assert.assertEquals(codegen.additionalProperties().get(RustClientCodegen.AVOID_BOXED_MODELS), Boolean.TRUE);
Assert.assertTrue(codegen.getAvoidBoxedModels());
}

@Test
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ pub enum CreateStateRequest {

impl Default for CreateStateRequest {
fn default() -> Self {
Self::AType(Box::default())
Self::AType(Default::default())
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ pub enum CustomOneOfArraySchemaInner {

impl Default for CustomOneOfArraySchemaInner {
fn default() -> Self {
Self::AType(Box::default())
Self::AType(Default::default())
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ pub enum CustomOneOfSchema {

impl Default for CustomOneOfSchema {
fn default() -> Self {
Self::AType(Box::default())
Self::AType(Default::default())
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ pub enum GetState200Response {

impl Default for GetState200Response {
fn default() -> Self {
Self::AType(Box::default())
Self::AType(Default::default())
}
}

Expand Down
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
use crate::models;

/*
* oneOf test
*
Expand Down
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
use crate::models;

/*
* oneOf test
*
Expand Down
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
use crate::models;

/*
* oneOf test
*
Expand Down
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
use crate::models;

/*
* oneOf test
*
Expand Down
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
use crate::models;

/*
* EmptyObject
*
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,13 +13,13 @@ use crate::models;
#[derive(Clone, Debug, PartialEq, Serialize, Deserialize)]
#[serde(untagged)]
pub enum Fruit {
Apples(Box<std::collections::HashMap<String, models::Apple>>),
Grapes(Box<Vec<models::Grape>>),
Apples(std::collections::HashMap<String, models::Apple>),
Grapes(Vec<models::Grape>),
}

impl Default for Fruit {
fn default() -> Self {
Self::Apples(Box::default())
Self::Apples(Default::default())
}
}

Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ pub enum Fruit {

impl Default for Fruit {
fn default() -> Self {
Self::GreenApple(Box::default())
Self::GreenApple(Default::default())
}
}

Expand Down
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
use crate::models;

/*
* ByRefOrValue
*
Expand Down
2 changes: 2 additions & 0 deletions samples/client/others/rust/hyper/oneOf/src/models/apple.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
use crate::models;

/*
* ByRefOrValue
*
Expand Down
2 changes: 2 additions & 0 deletions samples/client/others/rust/hyper/oneOf/src/models/banana.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
use crate::models;

/*
* ByRefOrValue
*
Expand Down
4 changes: 3 additions & 1 deletion samples/client/others/rust/hyper/oneOf/src/models/bar.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
use crate::models;

/*
* ByRefOrValue
*
Expand All @@ -19,7 +21,7 @@ pub struct Bar {
#[serde(rename = "fooPropB", skip_serializing_if = "Option::is_none")]
pub foo_prop_b: Option<String>,
#[serde(rename = "foo", skip_serializing_if = "Option::is_none")]
pub foo: Option<Box<models::FooRefOrValue>>,
pub foo: Option<models::FooRefOrValue>,
/// Hyperlink reference
#[serde(rename = "href", skip_serializing_if = "Option::is_none")]
pub href: Option<String>,
Expand Down
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
use crate::models;

/*
* ByRefOrValue
*
Expand All @@ -17,7 +19,7 @@ pub struct BarCreate {
#[serde(rename = "fooPropB", skip_serializing_if = "Option::is_none")]
pub foo_prop_b: Option<String>,
#[serde(rename = "foo", skip_serializing_if = "Option::is_none")]
pub foo: Option<Box<models::FooRefOrValue>>,
pub foo: Option<models::FooRefOrValue>,
/// Hyperlink reference
#[serde(rename = "href", skip_serializing_if = "Option::is_none")]
pub href: Option<String>,
Expand Down
2 changes: 2 additions & 0 deletions samples/client/others/rust/hyper/oneOf/src/models/bar_ref.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
use crate::models;

/*
* ByRefOrValue
*
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,13 +13,13 @@ use crate::models;
#[derive(Clone, Debug, PartialEq, Serialize, Deserialize)]
#[serde(untagged)]
pub enum BarRefOrValue {
Bar(Box<models::Bar>),
BarRef(Box<models::BarRef>),
Bar(models::Bar),
BarRef(models::BarRef),
}

impl Default for BarRefOrValue {
fn default() -> Self {
Self::Bar(Box::default())
Self::Bar(Default::default())
}
}

2 changes: 2 additions & 0 deletions samples/client/others/rust/hyper/oneOf/src/models/entity.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
use crate::models;

/*
* ByRefOrValue
*
Expand Down
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
use crate::models;

/*
* ByRefOrValue
*
Expand Down
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
use crate::models;

/*
* ByRefOrValue
*
Expand Down
2 changes: 2 additions & 0 deletions samples/client/others/rust/hyper/oneOf/src/models/foo.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
use crate::models;

/*
* ByRefOrValue
*
Expand Down
2 changes: 2 additions & 0 deletions samples/client/others/rust/hyper/oneOf/src/models/foo_ref.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
use crate::models;

/*
* ByRefOrValue
*
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -14,14 +14,14 @@ use crate::models;
#[serde(tag = "@type")]
pub enum FooRefOrValue {
#[serde(rename="Foo")]
Foo(Box<models::Foo>),
Foo(models::Foo),
#[serde(rename="FooRef")]
FooRef(Box<models::FooRef>),
FooRef(models::FooRef),
}

impl Default for FooRefOrValue {
fn default() -> Self {
Self::Foo(Box::default())
Self::Foo(Default::default())
}
}

Expand Down
6 changes: 3 additions & 3 deletions samples/client/others/rust/hyper/oneOf/src/models/fruit.rs
Original file line number Diff line number Diff line change
Expand Up @@ -14,14 +14,14 @@ use crate::models;
#[serde(tag = "fruitType")]
pub enum Fruit {
#[serde(rename="APPLE")]
Apple(Box<models::Apple>),
Apple(models::Apple),
#[serde(rename="BANANA")]
Banana(Box<models::Banana>),
Banana(models::Banana),
}

impl Default for Fruit {
fn default() -> Self {
Self::Apple(Box::default())
Self::Apple(Default::default())
}
}

Expand Down
2 changes: 2 additions & 0 deletions samples/client/others/rust/hyper/oneOf/src/models/pasta.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
use crate::models;

/*
* ByRefOrValue
*
Expand Down
Loading

0 comments on commit 026d393

Please sign in to comment.