Skip to content

Commit b14abd2

Browse files
authored
Merge pull request #791 from swagger-api/check-repeated-schemas
added option to rename repeated schema name
2 parents f66ff05 + 00b3c75 commit b14abd2

File tree

2 files changed

+109
-0
lines changed

2 files changed

+109
-0
lines changed

src/main/java/io/swagger/codegen/v3/generators/java/AbstractJavaCodegen.java

Lines changed: 108 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,13 +14,16 @@
1414
import io.swagger.v3.oas.models.OpenAPI;
1515
import io.swagger.v3.oas.models.Operation;
1616
import io.swagger.v3.oas.models.PathItem;
17+
import io.swagger.v3.oas.models.Paths;
1718
import io.swagger.v3.oas.models.media.ArraySchema;
1819
import io.swagger.v3.oas.models.media.IntegerSchema;
1920
import io.swagger.v3.oas.models.media.MapSchema;
21+
import io.swagger.v3.oas.models.media.MediaType;
2022
import io.swagger.v3.oas.models.media.NumberSchema;
2123
import io.swagger.v3.oas.models.media.ObjectSchema;
2224
import io.swagger.v3.oas.models.media.Schema;
2325
import io.swagger.v3.oas.models.media.StringSchema;
26+
import io.swagger.v3.oas.models.parameters.RequestBody;
2427
import io.swagger.v3.oas.models.responses.ApiResponse;
2528
import io.swagger.v3.parser.util.SchemaTypeUtil;
2629
import org.apache.commons.lang3.BooleanUtils;
@@ -37,6 +40,7 @@
3740
import java.util.ListIterator;
3841
import java.util.Map;
3942
import java.util.Objects;
43+
import java.util.Optional;
4044
import java.util.regex.Pattern;
4145

4246
import static io.swagger.codegen.v3.CodegenConstants.HAS_ENUMS_EXT_NAME;
@@ -53,6 +57,7 @@ public abstract class AbstractJavaCodegen extends DefaultCodegenConfig {
5357
public static final String WITH_XML = "withXml";
5458
public static final String SUPPORT_JAVA6 = "supportJava6";
5559
public static final String ERROR_ON_UNKNOWN_ENUM = "errorOnUnknownEnum";
60+
public static final String CHECK_DUPLICATED_MODEL_NAME = "checkDuplicatedModelName";
5661

5762
protected String dateLibrary = "threetenbp";
5863
protected boolean java8Mode = false;
@@ -173,6 +178,7 @@ public AbstractJavaCodegen() {
173178
java8ModeOptions.put("false", "Various third party libraries as needed");
174179
java8Mode.setEnum(java8ModeOptions);
175180
cliOptions.add(java8Mode);
181+
cliOptions.add(CliOption.newBoolean(CHECK_DUPLICATED_MODEL_NAME, "Check if there are duplicated model names (ignoring case)"));
176182
}
177183

178184
@Override
@@ -1065,6 +1071,11 @@ public void preprocessOpenAPI(OpenAPI openAPI) {
10651071
if (openAPI == null || openAPI.getPaths() == null){
10661072
return;
10671073
}
1074+
boolean checkDuplicatedModelName = Boolean.parseBoolean(additionalProperties.get(CHECK_DUPLICATED_MODEL_NAME) != null ? additionalProperties.get(CHECK_DUPLICATED_MODEL_NAME).toString() : "");
1075+
if (checkDuplicatedModelName) {
1076+
this.checkDuplicatedModelNameIgnoringCase(openAPI);
1077+
}
1078+
10681079
for (String pathname : openAPI.getPaths().keySet()) {
10691080
PathItem pathItem = openAPI.getPaths().get(pathname);
10701081

@@ -1123,6 +1134,103 @@ private static String getAccept(Operation operation) {
11231134
protected boolean needToImport(String type) {
11241135
return super.needToImport(type) && type.indexOf(".") < 0;
11251136
}
1137+
1138+
protected void checkDuplicatedModelNameIgnoringCase(OpenAPI openAPI) {
1139+
final Map<String, Schema> schemas = openAPI.getComponents().getSchemas();
1140+
final Map<String, Map<String, Schema>> schemasRepeated = new HashMap<>();
1141+
1142+
for (String schemaKey : schemas.keySet()) {
1143+
final Schema schema = schemas.get(schemaKey);
1144+
final String lowerKeyDefinition = schemaKey.toLowerCase();
1145+
1146+
if (schemasRepeated.containsKey(lowerKeyDefinition)) {
1147+
Map<String, Schema> modelMap = schemasRepeated.get(lowerKeyDefinition);
1148+
if (modelMap == null) {
1149+
modelMap = new HashMap<>();
1150+
schemasRepeated.put(lowerKeyDefinition, modelMap);
1151+
}
1152+
modelMap.put(schemaKey, schema);
1153+
} else {
1154+
schemasRepeated.put(lowerKeyDefinition, null);
1155+
}
1156+
}
1157+
for (String lowerKeyDefinition : schemasRepeated.keySet()) {
1158+
final Map<String, Schema> modelMap = schemasRepeated.get(lowerKeyDefinition);
1159+
if (modelMap == null) {
1160+
continue;
1161+
}
1162+
int index = 1;
1163+
for (String name : modelMap.keySet()) {
1164+
final Schema schema = modelMap.get(name);
1165+
final String newModelName = name + index;
1166+
schemas.put(newModelName, schema);
1167+
replaceDuplicatedInPaths(openAPI.getPaths(), name, newModelName);
1168+
replaceDuplicatedInModelProperties(schemas, name, newModelName);
1169+
schemas.remove(name);
1170+
index++;
1171+
}
1172+
}
1173+
}
1174+
1175+
protected void replaceDuplicatedInPaths(Paths paths, String modelName, String newModelName) {
1176+
if (paths == null || paths.isEmpty()) {
1177+
return;
1178+
}
1179+
paths.values().stream()
1180+
.flatMap(pathItem -> pathItem.readOperations().stream())
1181+
.filter(operation -> {
1182+
final RequestBody requestBody = operation.getRequestBody();
1183+
if (requestBody == null || requestBody.getContent() == null || requestBody.getContent().isEmpty()) {
1184+
return false;
1185+
}
1186+
final Optional<MediaType> mediaTypeOptional = requestBody.getContent().values().stream().findAny();
1187+
if (!mediaTypeOptional.isPresent()) {
1188+
return false;
1189+
}
1190+
final MediaType mediaType = mediaTypeOptional.get();
1191+
final Schema schema = mediaType.getSchema();
1192+
if (schema.get$ref() != null) {
1193+
return true;
1194+
}
1195+
return false;
1196+
})
1197+
.forEach(operation -> {
1198+
Schema schema = this.getSchemaFromBody(operation.getRequestBody());
1199+
schema.set$ref(schema.get$ref().replace(modelName, newModelName));
1200+
});
1201+
paths.values().stream()
1202+
.flatMap(path -> path.readOperations().stream())
1203+
.flatMap(operation -> operation.getResponses().values().stream())
1204+
.filter(response -> {
1205+
if (response.getContent() == null || response.getContent().isEmpty()) {
1206+
return false;
1207+
}
1208+
final Optional<MediaType> mediaTypeOptional = response.getContent().values().stream().findFirst();
1209+
if (!mediaTypeOptional.isPresent()) {
1210+
return false;
1211+
}
1212+
final MediaType mediaType = mediaTypeOptional.get();
1213+
final Schema schema = mediaType.getSchema();
1214+
if (schema.get$ref() != null) {
1215+
return true;
1216+
}
1217+
return false;
1218+
}).forEach(response -> {
1219+
final Optional<MediaType> mediaTypeOptional = response.getContent().values().stream().findFirst();
1220+
final Schema schema = mediaTypeOptional.get().getSchema();
1221+
schema.set$ref(schema.get$ref().replace(modelName, newModelName));
1222+
});
1223+
}
1224+
1225+
protected void replaceDuplicatedInModelProperties(Map<String, Schema> definitions, String modelName, String newModelName) {
1226+
definitions.values().stream()
1227+
.flatMap(model -> model.getProperties().values().stream())
1228+
.filter(property -> ((Schema) property).get$ref() != null)
1229+
.forEach(property -> {
1230+
final Schema schema = (Schema) property;
1231+
schema.set$ref(schema.get$ref().replace(modelName, newModelName));
1232+
});
1233+
}
11261234
/*
11271235
@Override
11281236
public String findCommonPrefixOfVars(List<String> vars) {

src/test/java/io/swagger/codegen/v3/generators/options/JavaOptionsProvider.java

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -74,6 +74,7 @@ public JavaOptionsProvider() {
7474
.put("hideGenerationTimestamp", "true")
7575
.put(CodegenConstants.ALLOW_UNICODE_IDENTIFIERS, ALLOW_UNICODE_IDENTIFIERS_VALUE)
7676
.put(CodegenConstants.USE_OAS2, "true")
77+
.put(JavaClientCodegen.CHECK_DUPLICATED_MODEL_NAME, "false")
7778
//.put("supportJava6", "true")
7879
.build();
7980
}

0 commit comments

Comments
 (0)