@apidevtools/json-schema-ref-parser 9.0.6 → 9.0.7
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/lib/dereference.js +73 -36
- package/package.json +9 -9
package/lib/dereference.js
CHANGED
|
@@ -16,7 +16,7 @@ module.exports = dereference;
|
|
|
16
16
|
*/
|
|
17
17
|
function dereference (parser, options) {
|
|
18
18
|
// console.log('Dereferencing $ref pointers in %s', parser.$refs._root$Ref.path);
|
|
19
|
-
let dereferenced = crawl(parser.schema, parser.$refs._root$Ref.path, "#", [], parser.$refs, options);
|
|
19
|
+
let dereferenced = crawl(parser.schema, parser.$refs._root$Ref.path, "#", [], [], {}, parser.$refs, options);
|
|
20
20
|
parser.$refs.circular = dereferenced.circular;
|
|
21
21
|
parser.schema = dereferenced.value;
|
|
22
22
|
}
|
|
@@ -28,43 +28,38 @@ function dereference (parser, options) {
|
|
|
28
28
|
* @param {string} path - The full path of `obj`, possibly with a JSON Pointer in the hash
|
|
29
29
|
* @param {string} pathFromRoot - The path of `obj` from the schema root
|
|
30
30
|
* @param {object[]} parents - An array of the parent objects that have already been dereferenced
|
|
31
|
+
* @param {object[]} processedObjects - An array of all the objects that have already been processed
|
|
32
|
+
* @param {object} dereferencedCache - An map of all the dereferenced objects
|
|
31
33
|
* @param {$Refs} $refs
|
|
32
34
|
* @param {$RefParserOptions} options
|
|
33
35
|
* @returns {{value: object, circular: boolean}}
|
|
34
36
|
*/
|
|
35
|
-
function crawl (obj, path, pathFromRoot, parents, $refs, options) {
|
|
37
|
+
function crawl (obj, path, pathFromRoot, parents, processedObjects, dereferencedCache, $refs, options) {
|
|
36
38
|
let dereferenced;
|
|
37
39
|
let result = {
|
|
38
40
|
value: obj,
|
|
39
41
|
circular: false
|
|
40
42
|
};
|
|
41
43
|
|
|
42
|
-
if (
|
|
43
|
-
|
|
44
|
+
if (options.dereference.circular === "ignore" || processedObjects.indexOf(obj) === -1) {
|
|
45
|
+
if (obj && typeof obj === "object" && !ArrayBuffer.isView(obj)) {
|
|
46
|
+
parents.push(obj);
|
|
47
|
+
processedObjects.push(obj);
|
|
44
48
|
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
circular = dereferenced.circular;
|
|
60
|
-
// Avoid pointless mutations; breaks frozen objects to no profit
|
|
61
|
-
if (obj[key] !== dereferenced.value) {
|
|
62
|
-
obj[key] = dereferenced.value;
|
|
63
|
-
}
|
|
64
|
-
}
|
|
65
|
-
else {
|
|
66
|
-
if (parents.indexOf(value) === -1) {
|
|
67
|
-
dereferenced = crawl(value, keyPath, keyPathFromRoot, parents, $refs, options);
|
|
49
|
+
if ($Ref.isAllowed$Ref(obj, options)) {
|
|
50
|
+
dereferenced = dereference$Ref(obj, path, pathFromRoot, parents, processedObjects, dereferencedCache, $refs, options);
|
|
51
|
+
result.circular = dereferenced.circular;
|
|
52
|
+
result.value = dereferenced.value;
|
|
53
|
+
}
|
|
54
|
+
else {
|
|
55
|
+
for (let key of Object.keys(obj)) {
|
|
56
|
+
let keyPath = Pointer.join(path, key);
|
|
57
|
+
let keyPathFromRoot = Pointer.join(pathFromRoot, key);
|
|
58
|
+
let value = obj[key];
|
|
59
|
+
let circular = false;
|
|
60
|
+
|
|
61
|
+
if ($Ref.isAllowed$Ref(value, options)) {
|
|
62
|
+
dereferenced = dereference$Ref(value, keyPath, keyPathFromRoot, parents, processedObjects, dereferencedCache, $refs, options);
|
|
68
63
|
circular = dereferenced.circular;
|
|
69
64
|
// Avoid pointless mutations; breaks frozen objects to no profit
|
|
70
65
|
if (obj[key] !== dereferenced.value) {
|
|
@@ -72,16 +67,26 @@ function crawl (obj, path, pathFromRoot, parents, $refs, options) {
|
|
|
72
67
|
}
|
|
73
68
|
}
|
|
74
69
|
else {
|
|
75
|
-
|
|
70
|
+
if (parents.indexOf(value) === -1) {
|
|
71
|
+
dereferenced = crawl(value, keyPath, keyPathFromRoot, parents, processedObjects, dereferencedCache, $refs, options);
|
|
72
|
+
circular = dereferenced.circular;
|
|
73
|
+
// Avoid pointless mutations; breaks frozen objects to no profit
|
|
74
|
+
if (obj[key] !== dereferenced.value) {
|
|
75
|
+
obj[key] = dereferenced.value;
|
|
76
|
+
}
|
|
77
|
+
}
|
|
78
|
+
else {
|
|
79
|
+
circular = foundCircularReference(keyPath, $refs, options);
|
|
80
|
+
}
|
|
76
81
|
}
|
|
77
|
-
}
|
|
78
82
|
|
|
79
|
-
|
|
80
|
-
|
|
83
|
+
// Set the "isCircular" flag if this or any other property is circular
|
|
84
|
+
result.circular = result.circular || circular;
|
|
85
|
+
}
|
|
81
86
|
}
|
|
82
|
-
}
|
|
83
87
|
|
|
84
|
-
|
|
88
|
+
parents.pop();
|
|
89
|
+
}
|
|
85
90
|
}
|
|
86
91
|
|
|
87
92
|
return result;
|
|
@@ -94,14 +99,38 @@ function crawl (obj, path, pathFromRoot, parents, $refs, options) {
|
|
|
94
99
|
* @param {string} path - The full path of `$ref`, possibly with a JSON Pointer in the hash
|
|
95
100
|
* @param {string} pathFromRoot - The path of `$ref` from the schema root
|
|
96
101
|
* @param {object[]} parents - An array of the parent objects that have already been dereferenced
|
|
102
|
+
* @param {object[]} processedObjects - An array of all the objects that have already been dereferenced
|
|
103
|
+
* @param {object} dereferencedCache - An map of all the dereferenced objects
|
|
97
104
|
* @param {$Refs} $refs
|
|
98
105
|
* @param {$RefParserOptions} options
|
|
99
106
|
* @returns {{value: object, circular: boolean}}
|
|
100
107
|
*/
|
|
101
|
-
function dereference$Ref ($ref, path, pathFromRoot, parents, $refs, options) {
|
|
108
|
+
function dereference$Ref ($ref, path, pathFromRoot, parents, processedObjects, dereferencedCache, $refs, options) {
|
|
102
109
|
// console.log('Dereferencing $ref pointer "%s" at %s', $ref.$ref, path);
|
|
103
110
|
|
|
104
111
|
let $refPath = url.resolve(path, $ref.$ref);
|
|
112
|
+
|
|
113
|
+
if (dereferencedCache[$refPath]) {
|
|
114
|
+
const cache = dereferencedCache[$refPath];
|
|
115
|
+
|
|
116
|
+
const refKeys = Object.keys($ref);
|
|
117
|
+
if (refKeys.length > 1) {
|
|
118
|
+
const extraKeys = {};
|
|
119
|
+
for (let key of refKeys) {
|
|
120
|
+
if (key !== "$ref" && !(key in cache.value)) {
|
|
121
|
+
extraKeys[key] = $ref[key];
|
|
122
|
+
}
|
|
123
|
+
}
|
|
124
|
+
return {
|
|
125
|
+
circular: cache.circular,
|
|
126
|
+
value: Object.assign({}, cache.value, extraKeys),
|
|
127
|
+
};
|
|
128
|
+
}
|
|
129
|
+
|
|
130
|
+
return cache;
|
|
131
|
+
}
|
|
132
|
+
|
|
133
|
+
|
|
105
134
|
let pointer = $refs._resolve($refPath, path, options);
|
|
106
135
|
|
|
107
136
|
if (pointer === null) {
|
|
@@ -122,7 +151,7 @@ function dereference$Ref ($ref, path, pathFromRoot, parents, $refs, options) {
|
|
|
122
151
|
// Crawl the dereferenced value (unless it's circular)
|
|
123
152
|
if (!circular) {
|
|
124
153
|
// Determine if the dereferenced value is circular
|
|
125
|
-
let dereferenced = crawl(dereferencedValue, pointer.path, pathFromRoot, parents, $refs, options);
|
|
154
|
+
let dereferenced = crawl(dereferencedValue, pointer.path, pathFromRoot, parents, processedObjects, dereferencedCache, $refs, options);
|
|
126
155
|
circular = dereferenced.circular;
|
|
127
156
|
dereferencedValue = dereferenced.value;
|
|
128
157
|
}
|
|
@@ -138,10 +167,18 @@ function dereference$Ref ($ref, path, pathFromRoot, parents, $refs, options) {
|
|
|
138
167
|
dereferencedValue.$ref = pathFromRoot;
|
|
139
168
|
}
|
|
140
169
|
|
|
141
|
-
|
|
170
|
+
|
|
171
|
+
const dereferencedObject = {
|
|
142
172
|
circular,
|
|
143
173
|
value: dereferencedValue
|
|
144
174
|
};
|
|
175
|
+
|
|
176
|
+
// only cache if no extra properties than $ref
|
|
177
|
+
if (Object.keys($ref).length === 1) {
|
|
178
|
+
dereferencedCache[$refPath] = dereferencedObject;
|
|
179
|
+
}
|
|
180
|
+
|
|
181
|
+
return dereferencedObject;
|
|
145
182
|
}
|
|
146
183
|
|
|
147
184
|
/**
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@apidevtools/json-schema-ref-parser",
|
|
3
|
-
"version": "9.0.
|
|
3
|
+
"version": "9.0.7",
|
|
4
4
|
"description": "Parse, Resolve, and Dereference JSON Schema $ref pointers",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"json",
|
|
@@ -51,23 +51,23 @@
|
|
|
51
51
|
"release": "npm run upgrade && npm run clean && npm test && npm run bump"
|
|
52
52
|
},
|
|
53
53
|
"devDependencies": {
|
|
54
|
-
"@babel/polyfill": "^7.
|
|
54
|
+
"@babel/polyfill": "^7.12.1",
|
|
55
55
|
"@jsdevtools/eslint-config": "^1.0.7",
|
|
56
|
-
"@jsdevtools/host-environment": "^2.
|
|
56
|
+
"@jsdevtools/host-environment": "^2.1.2",
|
|
57
57
|
"@jsdevtools/karma-config": "^3.1.7",
|
|
58
|
-
"@jsdevtools/version-bump-prompt": "^6.0
|
|
59
|
-
"@types/json-schema": "^7.0.
|
|
60
|
-
"@types/node": "^14.
|
|
58
|
+
"@jsdevtools/version-bump-prompt": "^6.1.0",
|
|
59
|
+
"@types/json-schema": "^7.0.6",
|
|
60
|
+
"@types/node": "^14.14.21",
|
|
61
61
|
"chai": "^4.2.0",
|
|
62
62
|
"chai-subset": "^1.6.0",
|
|
63
|
-
"eslint": "^7.
|
|
63
|
+
"eslint": "^7.18.0",
|
|
64
64
|
"karma": "^5.0.2",
|
|
65
65
|
"karma-cli": "^2.0.0",
|
|
66
|
-
"mocha": "^8.
|
|
66
|
+
"mocha": "^8.2.1",
|
|
67
67
|
"npm-check": "^5.9.0",
|
|
68
68
|
"nyc": "^15.0.1",
|
|
69
69
|
"shx": "^0.3.2",
|
|
70
|
-
"typescript": "^
|
|
70
|
+
"typescript": "^4.0.5"
|
|
71
71
|
},
|
|
72
72
|
"dependencies": {
|
|
73
73
|
"@jsdevtools/ono": "^7.1.3",
|