Skip to content

Commit 7aca73d

Browse files
committed
Only resolve ids in known keywords
It looks like we were too permissive in: #71 This addresses issues from: - json-schema-org/JSON-Schema-Test-Suite#471 - json-schema-org/JSON-Schema-Test-Suite#484 The first issue is more important, I think. We were resolving `$id` in keywords like `enum` and `const`, which is unexpected since those values are literal. The second issue is a little trickier. It's possible people are using non-standard keys to store reference schemas, which will cause issues since this only looks in `definitions` now.
1 parent 4cec494 commit 7aca73d

File tree

2 files changed

+30
-24
lines changed

2 files changed

+30
-24
lines changed

lib/json_schemer/schema/base.rb

+14-6
Original file line numberDiff line numberDiff line change
@@ -663,13 +663,21 @@ def resolve_ids(schema, ids = {}, parent_uri = nil, pointer = '')
663663
elsif schema.is_a?(Hash)
664664
uri = join_uri(parent_uri, schema[id_keyword])
665665
schema.each do |key, value|
666-
if key == id_keyword && uri != parent_uri
667-
ids[uri.to_s] = {
668-
schema: schema,
669-
pointer: pointer
670-
}
666+
case key
667+
when id_keyword
668+
unless uri == parent_uri
669+
ids[uri.to_s] = {
670+
schema: schema,
671+
pointer: pointer
672+
}
673+
end
674+
when 'items', 'allOf', 'anyOf', 'oneOf', 'additionalItems', 'contains', 'additionalProperties', 'propertyNames', 'if', 'then', 'else', 'not'
675+
resolve_ids(value, ids, uri, "#{pointer}/#{key}")
676+
when 'properties', 'patternProperties', 'definitions', 'dependencies'
677+
value.each do |subkey, subvalue|
678+
resolve_ids(subvalue, ids, uri, "#{pointer}/#{key}/#{subkey}")
679+
end
671680
end
672-
resolve_ids(value, ids, uri, "#{pointer}/#{key}")
673681
end
674682
end
675683
ids

test/ref_test.rb

+16-18
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33
class RefTest < Minitest::Test
44
def test_can_refer_to_subschemas_inside_hashes
55
root = {
6-
'foo' => {
6+
'definitions' => {
77
'bar' => {
88
'$id' => '#bar',
99
'type' => 'string'
@@ -19,8 +19,8 @@ def test_can_refer_to_subschemas_inside_hashes
1919
{
2020
'data' => 42,
2121
'data_pointer' => '',
22-
'schema' => root['foo']['bar'],
23-
'schema_pointer' => '/foo/bar',
22+
'schema' => root['definitions']['bar'],
23+
'schema_pointer' => '/definitions/bar',
2424
'root_schema' => root,
2525
'type' => 'string'
2626
},
@@ -30,8 +30,8 @@ def test_can_refer_to_subschemas_inside_hashes
3030

3131
def test_can_refer_to_subschemas_inside_arrays
3232
root = {
33-
'foo' => [{
34-
'bar' => {
33+
'allOf' => [{
34+
'if' => {
3535
'$id' => '#bar',
3636
'type' => 'string'
3737
}
@@ -50,8 +50,8 @@ def test_can_refer_to_subschemas_inside_arrays
5050
{
5151
'data' => 1,
5252
'data_pointer' => '/a/x',
53-
'schema' => root['foo'].first['bar'],
54-
'schema_pointer' => '/foo/0/bar',
53+
'schema' => root['allOf'].first['if'],
54+
'schema_pointer' => '/allOf/0/if',
5555
'root_schema' => root,
5656
'type' => 'string'
5757
},
@@ -62,7 +62,7 @@ def test_can_refer_to_subschemas_inside_arrays
6262
def test_can_refer_to_subschemas_in_hash_with_remote_pointer
6363
ref_schema = {
6464
'$id' => 'http://example.com/ref_schema.json',
65-
'foo' => {
65+
'definitions' => {
6666
'bar' => {
6767
'$id' => '#bar',
6868
'type' => 'string'
@@ -87,8 +87,8 @@ def test_can_refer_to_subschemas_in_hash_with_remote_pointer
8787
{
8888
'data' => 1,
8989
'data_pointer' => '/a/x',
90-
'schema' => ref_schema['foo']['bar'],
91-
'schema_pointer' => '/foo/bar',
90+
'schema' => ref_schema['definitions']['bar'],
91+
'schema_pointer' => '/definitions/bar',
9292
'root_schema' => ref_schema,
9393
'type' => 'string'
9494
},
@@ -99,18 +99,16 @@ def test_can_refer_to_subschemas_in_hash_with_remote_pointer
9999
def test_can_refer_to_multiple_subschemas_in_hash
100100
ref_schema = {
101101
'$id' => 'http://example.com/ref_schema.json',
102-
'types' => {
102+
'definitions' => {
103103
'uuid' => {
104104
'$id' => "#uuid",
105105
'type' => 'string',
106106
'pattern' => "^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$"
107107
}
108108
},
109-
'foo' => {
110-
'bar' => {
111-
'$id' => '#bar',
112-
'allOf' => [{ "$ref" => "#uuid"}]
113-
}
109+
'not' => {
110+
'$id' => '#bar',
111+
'allOf' => [{ "$ref" => "#uuid"}]
114112
}
115113
}
116114
root = {
@@ -131,8 +129,8 @@ def test_can_refer_to_multiple_subschemas_in_hash
131129
{
132130
'data' => "1122-112",
133131
'data_pointer' => '/a/x',
134-
'schema' => ref_schema['types']['uuid'],
135-
'schema_pointer' => '/types/uuid',
132+
'schema' => ref_schema['definitions']['uuid'],
133+
'schema_pointer' => '/definitions/uuid',
136134
'root_schema' => ref_schema,
137135
'type' => 'pattern'
138136
},

0 commit comments

Comments
 (0)