diff --git a/core/src/main/java/org/everit/json/schema/ReferenceSchema.java b/core/src/main/java/org/everit/json/schema/ReferenceSchema.java index ad81b7d45..7a1704aad 100644 --- a/core/src/main/java/org/everit/json/schema/ReferenceSchema.java +++ b/core/src/main/java/org/everit/json/schema/ReferenceSchema.java @@ -27,6 +27,11 @@ public static class Builder extends Schema.Builder { */ private String refValue = ""; + /** + * Map to store retval and location + */ + private Map retvalMap = new HashMap<>(); + /** * This method caches its result, so multiple invocations will return referentially the same * {@link ReferenceSchema} instance. @@ -36,6 +41,10 @@ public ReferenceSchema build() { if (retval == null) { retval = new ReferenceSchema(this); } + // store it in the map, so we can retrieve appropriate retval based on schema location + if (retval.getLocation() != null) { + retvalMap.put(retval.getLocation(), retval); + } return retval; } @@ -46,6 +55,15 @@ public Builder refValue(String refValue) { @Override public ReferenceSchema.Builder unprocessedProperties(Map unprocessedProperties) { if (retval != null) { + // create brand new reference schema + ReferenceSchema brandNewRefSchema = new ReferenceSchema(this); + brandNewRefSchema.setReferredSchema(retval.getReferredSchema()); + // if schema exists return from the map. + if (retvalMap.containsKey(brandNewRefSchema.getLocation())) { + retval = retvalMap.get(brandNewRefSchema.getLocation()); + } else if (brandNewRefSchema.getReferredSchema() != null) { + retval = brandNewRefSchema; + } retval.unprocessedProperties = new HashMap<>(unprocessedProperties); } super.unprocessedProperties(unprocessedProperties); diff --git a/core/src/test/java/org/everit/json/schema/ReferenceSchemaTest.java b/core/src/test/java/org/everit/json/schema/ReferenceSchemaTest.java index 68456fd11..8cd332c1d 100644 --- a/core/src/test/java/org/everit/json/schema/ReferenceSchemaTest.java +++ b/core/src/test/java/org/everit/json/schema/ReferenceSchemaTest.java @@ -107,6 +107,7 @@ public void unprocessedPropertiesAfterSettingRefSchema() { public void unprocessedPropertiesAfterBuild() { Builder builder = ReferenceSchema.builder() .refValue("#/pointer"); + builder.schemaLocation(SchemaLocation.empty().addPointerSegment("key")); ReferenceSchema subject = builder .build(); subject.setReferredSchema(EmptySchema.builder().build()); @@ -114,6 +115,17 @@ public void unprocessedPropertiesAfterBuild() { assertEquals(UNPROC_PROPS, subject.getUnprocessedProperties()); } + @Test + public void unprocessedPropertiesAfterBuildWithNoLocation() { + Builder builder = ReferenceSchema.builder() + .refValue("#/pointer"); + ReferenceSchema subject = builder + .build(); + subject.setReferredSchema(EmptySchema.builder().build()); + builder.unprocessedProperties(UNPROC_PROPS); + assertTrue(subject.getUnprocessedProperties().isEmpty()); + } + @Test public void emptyUnprocessedProperties() { ReferenceSchema subject = ReferenceSchema.builder() diff --git a/core/src/test/java/org/everit/json/schema/loader/SchemaLoaderTest.java b/core/src/test/java/org/everit/json/schema/loader/SchemaLoaderTest.java index dd5f38a42..d419a2d6b 100644 --- a/core/src/test/java/org/everit/json/schema/loader/SchemaLoaderTest.java +++ b/core/src/test/java/org/everit/json/schema/loader/SchemaLoaderTest.java @@ -747,7 +747,8 @@ public void commonPropsAreNotUnprocessedProps() { @Test public void unprocessedPropertiesAreLoadedForRefElement() { - SchemaLoader loader = SchemaLoader.builder() + SchemaLoader loader = + SchemaLoader.builder() .draftV7Support() .useDefaults(true) .schemaJson(get("schemaRefWithUnprocessedProperties")) @@ -755,15 +756,34 @@ public void unprocessedPropertiesAreLoadedForRefElement() { ObjectSchema actual = (ObjectSchema) loader.load().build(); assertEquals(ImmutableMap.of( - "unproc8", false - ), ((ReferenceSchema) actual.getPropertySchemas().get("prop4")).getReferredSchema().getUnprocessedProperties()); + "unproc6", false + ), actual.getPropertySchemas().get("prop3").getUnprocessedProperties()); - assertEquals(ImmutableMap.of("unproc4", true, "unproc5", JSONObject.NULL), - actual.getPropertySchemas().get("prop2").getUnprocessedProperties()); + assertEquals( + ImmutableMap.of("unproc8", false), + ((ReferenceSchema) actual.getPropertySchemas().get("prop4")) + .getReferredSchema() + .getUnprocessedProperties()); - assertEquals(ImmutableMap.of( - "unproc7", JSONObject.NULL - ), actual.getPropertySchemas().get("prop4").getUnprocessedProperties()); + assertEquals( + ImmutableMap.of("unproc4", true, "unproc5", JSONObject.NULL), + actual.getPropertySchemas().get("prop2").getUnprocessedProperties()); + + assertEquals( + ImmutableMap.of("unproc7", JSONObject.NULL), + actual.getPropertySchemas().get("prop4").getUnprocessedProperties()); + + assertEquals( + ImmutableMap.of("unproc8", false), + ((ReferenceSchema) actual.getPropertySchemas().get("prop4")).getReferredSchema().getUnprocessedProperties()); + + assertEquals( + ImmutableMap.of("unproc9", ImmutableMap.of("unproc9-01",false)), + actual.getPropertySchemas().get("prop5").getUnprocessedProperties()); + + assertEquals( + ImmutableMap.of("unproc8", false), + ((ReferenceSchema) actual.getPropertySchemas().get("prop5")).getReferredSchema().getUnprocessedProperties()); } } diff --git a/core/src/test/resources/org/everit/jsonvalidator/testschemas.json b/core/src/test/resources/org/everit/jsonvalidator/testschemas.json index 0af2ce811..c2209affb 100644 --- a/core/src/test/resources/org/everit/jsonvalidator/testschemas.json +++ b/core/src/test/resources/org/everit/jsonvalidator/testschemas.json @@ -722,6 +722,12 @@ "prop4": { "$ref": "#/definitions/dateMonthDayYear", "unproc7": null + }, + "prop5": { + "$ref": "#/definitions/dateMonthDayYear", + "unproc9": { + "unproc9-01": false + } } } }