Skip to content

Commit 313b110

Browse files
committed
fix: empty media type schema
1 parent 8ab4ddd commit 313b110

File tree

6 files changed

+196
-74
lines changed

6 files changed

+196
-74
lines changed

src/main/java/com/qdesrame/openapi/diff/compare/SchemaDiff.java

Lines changed: 63 additions & 53 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,7 @@
11
package com.qdesrame.openapi.diff.compare;
22

3+
import static java.util.Optional.ofNullable;
4+
35
import com.qdesrame.openapi.diff.compare.schemadiffresult.ArraySchemaDiffResult;
46
import com.qdesrame.openapi.diff.compare.schemadiffresult.ComposedSchemaDiffResult;
57
import com.qdesrame.openapi.diff.compare.schemadiffresult.SchemaDiffResult;
@@ -15,11 +17,7 @@
1517

1618
public class SchemaDiff extends ReferenceDiffCache<Schema, ChangedSchema> {
1719

18-
private Components leftComponents;
19-
private Components rightComponents;
20-
private OpenApiDiff openApiDiff;
2120
private static RefPointer<Schema> refPointer = new RefPointer<>(RefType.SCHEMAS);
22-
2321
private static Map<Class<? extends Schema>, Class<? extends SchemaDiffResult>>
2422
schemaDiffResultClassMap = new LinkedHashMap<>();
2523

@@ -29,6 +27,22 @@ public class SchemaDiff extends ReferenceDiffCache<Schema, ChangedSchema> {
2927
schemaDiffResultClassMap.put(ComposedSchema.class, ComposedSchemaDiffResult.class);
3028
}
3129

30+
private Components leftComponents;
31+
private Components rightComponents;
32+
private OpenApiDiff openApiDiff;
33+
34+
public SchemaDiff(OpenApiDiff openApiDiff) {
35+
this.openApiDiff = openApiDiff;
36+
this.leftComponents =
37+
openApiDiff.getOldSpecOpenApi() != null
38+
? openApiDiff.getOldSpecOpenApi().getComponents()
39+
: null;
40+
this.rightComponents =
41+
openApiDiff.getNewSpecOpenApi() != null
42+
? openApiDiff.getNewSpecOpenApi().getComponents()
43+
: null;
44+
}
45+
3246
public static SchemaDiffResult getSchemaDiffResult(OpenApiDiff openApiDiff) {
3347
return getSchemaDiffResult(null, openApiDiff);
3448
}
@@ -54,55 +68,6 @@ public static SchemaDiffResult getSchemaDiffResult(
5468
}
5569
}
5670

57-
public SchemaDiff(OpenApiDiff openApiDiff) {
58-
this.openApiDiff = openApiDiff;
59-
this.leftComponents =
60-
openApiDiff.getOldSpecOpenApi() != null
61-
? openApiDiff.getOldSpecOpenApi().getComponents()
62-
: null;
63-
this.rightComponents =
64-
openApiDiff.getNewSpecOpenApi() != null
65-
? openApiDiff.getNewSpecOpenApi().getComponents()
66-
: null;
67-
}
68-
69-
public Optional<ChangedSchema> diff(
70-
HashSet<String> refSet, Schema left, Schema right, DiffContext context) {
71-
return cachedDiff(refSet, left, right, left.get$ref(), right.get$ref(), context);
72-
}
73-
74-
public Optional<ChangedSchema> getTypeChangedSchema(
75-
Schema left, Schema right, DiffContext context) {
76-
ChangedSchema changedSchema = SchemaDiff.getSchemaDiffResult(openApiDiff).getChangedSchema();
77-
changedSchema.setOldSchema(left);
78-
changedSchema.setNewSchema(right);
79-
changedSchema.setChangedType(true);
80-
changedSchema.setContext(context);
81-
return Optional.of(changedSchema);
82-
}
83-
84-
@Override
85-
protected Optional<ChangedSchema> computeDiff(
86-
HashSet<String> refSet, Schema left, Schema right, DiffContext context) {
87-
left = refPointer.resolveRef(this.leftComponents, left, left.get$ref());
88-
right = refPointer.resolveRef(this.rightComponents, right, right.get$ref());
89-
90-
left = resolveComposedSchema(leftComponents, left);
91-
right = resolveComposedSchema(rightComponents, right);
92-
93-
// If type of schemas are different, just set old & new schema, set changedType to true in
94-
// SchemaDiffResult and
95-
// return the object
96-
if (!Objects.equals(left.getType(), right.getType())
97-
|| !Objects.equals(left.getFormat(), right.getFormat())) {
98-
return getTypeChangedSchema(left, right, context);
99-
}
100-
101-
// If schema type is same then get specific SchemaDiffResult and compare the properties
102-
SchemaDiffResult result = SchemaDiff.getSchemaDiffResult(right.getClass(), openApiDiff);
103-
return result.diff(refSet, leftComponents, rightComponents, left, right, context);
104-
}
105-
10671
protected static Schema resolveComposedSchema(Components components, Schema schema) {
10772
if (schema instanceof ComposedSchema) {
10873
ComposedSchema composedSchema = (ComposedSchema) schema;
@@ -138,4 +103,49 @@ protected static Schema addSchema(Schema schema, Schema fromSchema) {
138103
// TODO copy other things from fromSchema
139104
return schema;
140105
}
106+
107+
private static String getSchemaRef(Schema schema) {
108+
return ofNullable(schema).map(Schema::get$ref).orElse(null);
109+
}
110+
111+
public Optional<ChangedSchema> diff(
112+
HashSet<String> refSet, Schema left, Schema right, DiffContext context) {
113+
if (left == null && right == null) {
114+
return Optional.empty();
115+
}
116+
return cachedDiff(refSet, left, right, getSchemaRef(left), getSchemaRef(right), context);
117+
}
118+
119+
public Optional<ChangedSchema> getTypeChangedSchema(
120+
Schema left, Schema right, DiffContext context) {
121+
ChangedSchema changedSchema = SchemaDiff.getSchemaDiffResult(openApiDiff).getChangedSchema();
122+
changedSchema.setOldSchema(left);
123+
changedSchema.setNewSchema(right);
124+
changedSchema.setChangedType(true);
125+
changedSchema.setContext(context);
126+
return Optional.of(changedSchema);
127+
}
128+
129+
@Override
130+
protected Optional<ChangedSchema> computeDiff(
131+
HashSet<String> refSet, Schema left, Schema right, DiffContext context) {
132+
left = refPointer.resolveRef(this.leftComponents, left, getSchemaRef(left));
133+
right = refPointer.resolveRef(this.rightComponents, right, getSchemaRef(right));
134+
135+
left = resolveComposedSchema(leftComponents, left);
136+
right = resolveComposedSchema(rightComponents, right);
137+
138+
// If type of schemas are different, just set old & new schema, set changedType to true in
139+
// SchemaDiffResult and
140+
// return the object
141+
if ((left == null || right == null)
142+
|| !Objects.equals(left.getType(), right.getType())
143+
|| !Objects.equals(left.getFormat(), right.getFormat())) {
144+
return getTypeChangedSchema(left, right, context);
145+
}
146+
147+
// If schema type is same then get specific SchemaDiffResult and compare the properties
148+
SchemaDiffResult result = SchemaDiff.getSchemaDiffResult(right.getClass(), openApiDiff);
149+
return result.diff(refSet, leftComponents, rightComponents, left, right, context);
150+
}
141151
}

src/main/java/com/qdesrame/openapi/diff/compare/schemadiffresult/SchemaDiffResult.java

Lines changed: 22 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -39,23 +39,23 @@ public Optional<ChangedSchema> diff(
3939
Schema left,
4040
Schema right,
4141
DiffContext context) {
42-
changedSchema.setContext(context);
43-
changedSchema.setOldSchema(left);
44-
changedSchema.setNewSchema(right);
45-
changedSchema.setChangeDeprecated(
46-
!Boolean.TRUE.equals(left.getDeprecated()) && Boolean.TRUE.equals(right.getDeprecated()));
47-
changedSchema.setChangeDescription(
48-
!Objects.equals(left.getDescription(), right.getDescription()));
49-
changedSchema.setChangeTitle(!Objects.equals(left.getTitle(), right.getTitle()));
50-
changedSchema.setChangeRequired(ListDiff.diff(left.getRequired(), right.getRequired()));
51-
changedSchema.setChangeDefault(!Objects.equals(left.getDefault(), right.getDefault()));
52-
changedSchema.setChangeEnum(ListDiff.diff(left.getEnum(), right.getEnum()));
53-
changedSchema.setChangeFormat(!Objects.equals(left.getFormat(), right.getFormat()));
54-
changedSchema.setChangedReadOnly(
55-
new ChangedReadOnly(context, left.getReadOnly(), right.getReadOnly()));
56-
changedSchema.setChangedWriteOnly(
57-
new ChangedWriteOnly(context, left.getWriteOnly(), right.getWriteOnly()));
58-
changedSchema.setChangedMaxLength(!Objects.equals(left.getMaxLength(), right.getMaxLength()));
42+
changedSchema
43+
.setContext(context)
44+
.setOldSchema(left)
45+
.setNewSchema(right)
46+
.setChangeDeprecated(
47+
!Boolean.TRUE.equals(left.getDeprecated())
48+
&& Boolean.TRUE.equals(right.getDeprecated()))
49+
.setChangeDescription(!Objects.equals(left.getDescription(), right.getDescription()))
50+
.setChangeTitle(!Objects.equals(left.getTitle(), right.getTitle()))
51+
.setChangeRequired(ListDiff.diff(left.getRequired(), right.getRequired()))
52+
.setChangeDefault(!Objects.equals(left.getDefault(), right.getDefault()))
53+
.setChangeEnum(ListDiff.diff(left.getEnum(), right.getEnum()))
54+
.setChangeFormat(!Objects.equals(left.getFormat(), right.getFormat()))
55+
.setChangedReadOnly(new ChangedReadOnly(context, left.getReadOnly(), right.getReadOnly()))
56+
.setChangedWriteOnly(
57+
new ChangedWriteOnly(context, left.getWriteOnly(), right.getWriteOnly()))
58+
.setChangedMaxLength(!Objects.equals(left.getMaxLength(), right.getMaxLength()));
5959
Optional<ChangedExtensions> changedExtensions =
6060
openApiDiff.getExtensionsDiff().diff(left.getExtensions(), right.getExtensions(), context);
6161
changedExtensions.ifPresent(changedSchema::setChangedExtensions);
@@ -134,10 +134,11 @@ private void compareAdditionalProperties(
134134
if ((left != null && left instanceof Schema) || (right != null && right instanceof Schema)) {
135135
Schema leftAdditionalSchema = (Schema) left;
136136
Schema rightAdditionalSchema = (Schema) right;
137-
ChangedSchema apChangedSchema = new ChangedSchema();
138-
apChangedSchema.setContext(context);
139-
apChangedSchema.setOldSchema(leftAdditionalSchema);
140-
apChangedSchema.setNewSchema(rightAdditionalSchema);
137+
ChangedSchema apChangedSchema =
138+
new ChangedSchema()
139+
.setContext(context)
140+
.setOldSchema(leftAdditionalSchema)
141+
.setNewSchema(rightAdditionalSchema);
141142
if (left != null && right != null) {
142143
Optional<ChangedSchema> addPropChangedSchemaOP =
143144
openApiDiff

src/main/java/com/qdesrame/openapi/diff/model/ChangedSchema.java

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,11 +9,13 @@
99
import java.util.Map;
1010
import lombok.Getter;
1111
import lombok.Setter;
12+
import lombok.experimental.Accessors;
1213
import org.apache.commons.collections4.CollectionUtils;
1314

1415
/** Created by adarsh.sharma on 22/12/17. */
1516
@Getter
1617
@Setter
18+
@Accessors(chain = true)
1719
public class ChangedSchema implements Changed {
1820
protected DiffContext context;
1921
protected Schema oldSchema;
Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
package com.qdesrame.openapi.test;
2+
3+
import com.qdesrame.openapi.diff.OpenApiCompare;
4+
import com.qdesrame.openapi.diff.model.ChangedOpenApi;
5+
import org.junit.Assert;
6+
import org.junit.Test;
7+
8+
public class ContentDiffTest {
9+
10+
private final String OPENAPI_DOC1 = "content_diff_1.yaml";
11+
private final String OPENAPI_DOC2 = "content_diff_2.yaml";
12+
13+
@Test
14+
public void testContentDiffWithOneEmptyMediaType() {
15+
ChangedOpenApi changedOpenApi = OpenApiCompare.fromLocations(OPENAPI_DOC1, OPENAPI_DOC2);
16+
Assert.assertTrue(changedOpenApi.isIncompatible());
17+
}
18+
19+
@Test
20+
public void testContentDiffWithEmptyMediaTypes() {
21+
ChangedOpenApi changedOpenApi = OpenApiCompare.fromLocations(OPENAPI_DOC1, OPENAPI_DOC1);
22+
Assert.assertTrue(changedOpenApi.isUnchanged());
23+
}
24+
25+
@Test
26+
public void testSameContentDiff() {
27+
ChangedOpenApi changedOpenApi = OpenApiCompare.fromLocations(OPENAPI_DOC2, OPENAPI_DOC2);
28+
Assert.assertTrue(changedOpenApi.isUnchanged());
29+
}
30+
}
Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
---
2+
openapi: "3.0.1"
3+
info:
4+
title: "Test title"
5+
description: "This is a test description"
6+
termsOfService: "http://test.com"
7+
contact:
8+
name: "Mark Snijder"
9+
url: "marksnijder.nl"
10+
email: "snijderd@gmail.com"
11+
license:
12+
name: "To be decided"
13+
url: "http://test.com"
14+
version: "version 1.0"
15+
paths:
16+
/pets/{id}:
17+
get:
18+
description: Returns a user based on a single ID, if the user does not have access to the pet
19+
operationId: find pet by id
20+
parameters:
21+
- name: id
22+
in: path
23+
description: ID of pet to fetch
24+
required: true
25+
schema:
26+
type: integer
27+
format: int64
28+
responses:
29+
'200':
30+
description: response
31+
content:
32+
application/json: {}
Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,47 @@
1+
---
2+
openapi: "3.0.1"
3+
info:
4+
title: "Test title"
5+
description: "This is a test description"
6+
termsOfService: "http://test.com"
7+
contact:
8+
name: "Mark Snijder"
9+
url: "marksnijder.nl"
10+
email: "snijderd@gmail.com"
11+
license:
12+
name: "To be decided"
13+
url: "http://test.com"
14+
version: "version 1.0"
15+
paths:
16+
/pets/{id}:
17+
get:
18+
description: Returns a user based on a single ID, if the user does not have access to the pet
19+
operationId: find pet by id
20+
parameters:
21+
- name: id
22+
in: path
23+
description: ID of pet to fetch
24+
required: true
25+
schema:
26+
type: integer
27+
format: int64
28+
responses:
29+
'200':
30+
description: response
31+
content:
32+
application/json:
33+
schema:
34+
$ref: '#/components/schemas/User'
35+
components:
36+
schemas:
37+
User:
38+
type: "object"
39+
properties:
40+
id:
41+
type: "integer"
42+
format: "int32"
43+
salary:
44+
type: "integer"
45+
format: "int32"
46+
name:
47+
type: "string"

0 commit comments

Comments
 (0)