Add rule to simplify boolean enum (#14764)

* add rule to simplify boolean enum

* update doc
This commit is contained in:
William Cheng 2023-02-21 14:06:24 +08:00 committed by GitHub
parent b215f67b2e
commit c9958e12b8
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 109 additions and 3 deletions

View File

@ -477,3 +477,10 @@ Example:
``` ```
java -jar modules/openapi-generator-cli/target/openapi-generator-cli.jar generate -g java -i modules/openapi-generator/src/test/resources/3_0/simplifyAnyOfStringAndEnumString_test.yaml -o /tmp/java-okhttp/ --openapi-normalizer SIMPLIFY_ANYOF_STRING_AND_ENUM_STRING=true java -jar modules/openapi-generator-cli/target/openapi-generator-cli.jar generate -g java -i modules/openapi-generator/src/test/resources/3_0/simplifyAnyOfStringAndEnumString_test.yaml -o /tmp/java-okhttp/ --openapi-normalizer SIMPLIFY_ANYOF_STRING_AND_ENUM_STRING=true
``` ```
- `SIMPLIFY_BOOLEAN_ENUM`: when set to `true`, convert boolean enum to just enum.
Example:
```
java -jar modules/openapi-generator-cli/target/openapi-generator-cli.jar generate -g java -i modules/openapi-generator/src/test/resources/3_0/simplifyBooleanEnum_test.yaml -o /tmp/java-okhttp/ --openapi-normalizer SIMPLIFY_BOOLEAN_ENUM=true
```

View File

@ -63,6 +63,10 @@ public class OpenAPINormalizer {
final String SIMPLIFY_ANYOF_STRING_AND_ENUM_STRING = "SIMPLIFY_ANYOF_STRING_AND_ENUM_STRING"; final String SIMPLIFY_ANYOF_STRING_AND_ENUM_STRING = "SIMPLIFY_ANYOF_STRING_AND_ENUM_STRING";
boolean simplifyAnyOfStringAndEnumString; boolean simplifyAnyOfStringAndEnumString;
// when set to true, boolean enum will be converted to just boolean
final String SIMPLIFY_BOOLEAN_ENUM = "SIMPLIFY_BOOLEAN_ENUM";
boolean simplifyBooleanEnum;
// ============= end of rules ============= // ============= end of rules =============
/** /**
@ -106,6 +110,10 @@ public class OpenAPINormalizer {
if (enableAll || "true".equalsIgnoreCase(rules.get(SIMPLIFY_ANYOF_STRING_AND_ENUM_STRING))) { if (enableAll || "true".equalsIgnoreCase(rules.get(SIMPLIFY_ANYOF_STRING_AND_ENUM_STRING))) {
simplifyAnyOfStringAndEnumString = true; simplifyAnyOfStringAndEnumString = true;
} }
if (enableAll || "true".equalsIgnoreCase(rules.get(SIMPLIFY_BOOLEAN_ENUM))) {
simplifyBooleanEnum = true;
}
} }
/** /**
@ -301,11 +309,11 @@ public class OpenAPINormalizer {
visitedSchemas.add(schema); visitedSchemas.add(schema);
} }
if (schema instanceof ArraySchema) { if (schema instanceof ArraySchema) { // array
normalizeSchema(schema.getItems(), visitedSchemas); normalizeSchema(schema.getItems(), visitedSchemas);
} else if (schema.getAdditionalProperties() instanceof Schema) { // map } else if (schema.getAdditionalProperties() instanceof Schema) { // map
normalizeSchema((Schema) schema.getAdditionalProperties(), visitedSchemas); normalizeSchema((Schema) schema.getAdditionalProperties(), visitedSchemas);
} else if (ModelUtils.isComposedSchema(schema)) { } else if (ModelUtils.isComposedSchema(schema)) { // composed schema
ComposedSchema cs = (ComposedSchema) schema; ComposedSchema cs = (ComposedSchema) schema;
if (ModelUtils.isComplexComposedSchema(cs)) { if (ModelUtils.isComplexComposedSchema(cs)) {
@ -337,6 +345,8 @@ public class OpenAPINormalizer {
normalizeSchema(schema.getNot(), visitedSchemas); normalizeSchema(schema.getNot(), visitedSchemas);
} else if (schema.getProperties() != null && !schema.getProperties().isEmpty()) { } else if (schema.getProperties() != null && !schema.getProperties().isEmpty()) {
normalizeProperties(schema.getProperties(), visitedSchemas); normalizeProperties(schema.getProperties(), visitedSchemas);
} else if (schema instanceof BooleanSchema) {
normalizeBooleanSchema(schema, visitedSchemas);
} else if (schema instanceof Schema) { } else if (schema instanceof Schema) {
normalizeSchemaWithOnlyProperties(schema, visitedSchemas); normalizeSchemaWithOnlyProperties(schema, visitedSchemas);
} else { } else {
@ -346,6 +356,10 @@ public class OpenAPINormalizer {
return schema; return schema;
} }
private void normalizeBooleanSchema(Schema schema, Set<Schema> visitedSchemas) {
processSimplifyBooleanEnum(schema);
}
private void normalizeSchemaWithOnlyProperties(Schema schema, Set<Schema> visitedSchemas) { private void normalizeSchemaWithOnlyProperties(Schema schema, Set<Schema> visitedSchemas) {
// normalize non-composed schema (e.g. schema with only properties) // normalize non-composed schema (e.g. schema with only properties)
} }
@ -476,7 +490,6 @@ public class OpenAPINormalizer {
* @param schema Schema * @param schema Schema
*/ */
private void processRemoveAnyOfOneOfAndKeepPropertiesOnly(Schema schema) { private void processRemoveAnyOfOneOfAndKeepPropertiesOnly(Schema schema) {
if (!removeAnyOfOneOfAndKeepPropertiesOnly && !enableAll) { if (!removeAnyOfOneOfAndKeepPropertiesOnly && !enableAll) {
return; return;
} }
@ -528,5 +541,25 @@ public class OpenAPINormalizer {
} }
} }
/**
* If the schema is boolean and its enum is defined,
* then simply it to just boolean.
*
* @param schema Schema
* @return Schema
*/
private void processSimplifyBooleanEnum(Schema schema) {
if (!simplifyBooleanEnum && !enableAll) {
return;
}
if (schema instanceof BooleanSchema) {
BooleanSchema bs = (BooleanSchema) schema;
if (bs.getEnum() != null && !bs.getEnum().isEmpty()) { // enum defined
bs.setEnum(null);
}
}
}
// ===================== end of rules ===================== // ===================== end of rules =====================
} }

View File

@ -4394,4 +4394,27 @@ public class DefaultCodegenTest {
assertNull(schema3.getAnyOf()); assertNull(schema3.getAnyOf());
assertTrue(schema3 instanceof StringSchema); assertTrue(schema3 instanceof StringSchema);
} }
@Test
public void testOpenAPINormalizerSimplifyBooleanEnum() {
// to test the rule SIMPLIFY_BOOLEAN_ENUM
OpenAPI openAPI = TestUtils.parseSpec("src/test/resources/3_0/simplifyBooleanEnum_test.yaml");
Schema schema = openAPI.getComponents().getSchemas().get("BooleanEnumTest");
assertEquals(schema.getProperties().size(), 3);
assertTrue(schema.getProperties().get("boolean_enum") instanceof BooleanSchema);
BooleanSchema bs = (BooleanSchema) schema.getProperties().get("boolean_enum");
assertEquals(bs.getEnum().size(), 2);
Map<String, String> options = new HashMap<>();
options.put("SIMPLIFY_BOOLEAN_ENUM", "true");
OpenAPINormalizer openAPINormalizer = new OpenAPINormalizer(openAPI, options);
openAPINormalizer.normalize();
Schema schema3 = openAPI.getComponents().getSchemas().get("BooleanEnumTest");
assertEquals(schema.getProperties().size(), 3);
assertTrue(schema.getProperties().get("boolean_enum") instanceof BooleanSchema);
BooleanSchema bs2 = (BooleanSchema) schema.getProperties().get("boolean_enum");
assertNull(bs2.getEnum()); //ensure the enum has been erased
}
} }

View File

@ -0,0 +1,43 @@
openapi: 3.0.1
info:
version: 1.0.0
title: Example
license:
name: MIT
servers:
- url: http://api.example.xyz/v1
paths:
/person/display/{personId}:
get:
parameters:
- name: personId
in: path
required: true
description: The id of the person to retrieve
schema:
type: string
operationId: list
responses:
'200':
description: OK
content:
application/json:
schema:
$ref: "#/components/schemas/BooleanEnumTest"
components:
schemas:
BooleanEnumTest:
description: a model to with boolean enum property
type: object
properties:
id:
type: integer
format: int64
name:
type: string
pattern: '^[a-zA-Z0-9]+[a-zA-Z0-9\.\-_]*[a-zA-Z0-9]+$'
boolean_enum:
type: boolean
enum:
- true
- false