blob: 0bfaac512995e225e92855bc570a07061917023b [file] [log] [blame]
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
var tslib_1 = require("tslib");
require("cross-fetch/polyfill");
var debug_1 = tslib_1.__importDefault(require("debug"));
var utils_1 = require("../utils");
var jsonSchema_1 = require("./jsonSchema");
var schemaId_1 = tslib_1.__importDefault(require("./schemaId"));
var debug = debug_1.default('dtsgen');
var ReferenceResolver = (function () {
function ReferenceResolver() {
this.schemaCache = new Map();
this.referenceCache = new Map();
}
ReferenceResolver.prototype.dereference = function (refId) {
var result = this.referenceCache.get(refId);
if (result == null) {
throw new Error('Target reference is not found: ' + refId);
}
return result;
};
ReferenceResolver.prototype.getAllRegisteredSchema = function () {
return this.schemaCache.values();
};
ReferenceResolver.prototype.resolve = function () {
return tslib_1.__awaiter(this, void 0, void 0, function () {
var error, _a, _b, _c, key, schema, id, fileId, result, refSchema, e_1, rootSchema, targetSchema, e_2_1;
var e_2, _d;
return tslib_1.__generator(this, function (_e) {
switch (_e.label) {
case 0:
debug("resolve reference: reference schema count=" + this.referenceCache.size + ".");
error = [];
_e.label = 1;
case 1:
_e.trys.push([1, 10, 11, 12]);
_a = tslib_1.__values(this.referenceCache.entries()), _b = _a.next();
_e.label = 2;
case 2:
if (!!_b.done) return [3, 9];
_c = tslib_1.__read(_b.value, 2), key = _c[0], schema = _c[1];
if (schema != null) {
return [3, 8];
}
id = new schemaId_1.default(key);
fileId = id.getFileId();
result = this.schemaCache.get(id.getAbsoluteId());
if (!(result == null)) return [3, 7];
refSchema = this.schemaCache.get(fileId);
debug("get from schema cache, fileId=" + fileId + ", exists=" + (refSchema != null) + ", " + id.getAbsoluteId());
if (!(refSchema == null && id.isFetchable())) return [3, 6];
_e.label = 3;
case 3:
_e.trys.push([3, 5, , 6]);
debug("fetch remote schema: id=[" + fileId + "].");
return [4, this.registerRemoteSchema(fileId)];
case 4:
_e.sent();
return [3, 6];
case 5:
e_1 = _e.sent();
error.push("Fail to fetch the $ref target: " + id.getAbsoluteId() + ", " + e_1);
return [3, 8];
case 6:
result = this.schemaCache.get(id.getAbsoluteId());
_e.label = 7;
case 7:
debug("resolve reference: ref=[" + id.getAbsoluteId() + "]");
if (result != null) {
this.referenceCache.set(id.getAbsoluteId(), result);
}
else {
if (id.existsJsonPointerHash()) {
rootSchema = this.searchParentSchema(id);
if (rootSchema == null) {
error.push("The $ref targets root is not found: " + id.getAbsoluteId());
return [3, 8];
}
targetSchema = jsonSchema_1.getSubSchema(rootSchema, id.getJsonPointerHash(), id);
this.addSchema(targetSchema);
this.registerSchema(targetSchema);
this.referenceCache.set(id.getAbsoluteId(), targetSchema);
}
else {
error.push("The $ref target is not found: " + id.getAbsoluteId());
return [3, 8];
}
}
_e.label = 8;
case 8:
_b = _a.next();
return [3, 2];
case 9: return [3, 12];
case 10:
e_2_1 = _e.sent();
e_2 = { error: e_2_1 };
return [3, 12];
case 11:
try {
if (_b && !_b.done && (_d = _a.return)) _d.call(_a);
}
finally { if (e_2) throw e_2.error; }
return [7];
case 12:
if (error.length > 0) {
throw new Error(error.join('\n'));
}
return [2];
}
});
});
};
ReferenceResolver.prototype.searchParentSchema = function (id) {
var e_3, _a;
var fileId = id.getFileId();
var rootSchema = this.schemaCache.get(fileId);
if (rootSchema != null) {
return rootSchema;
}
var key = id.getAbsoluteId();
try {
for (var _b = tslib_1.__values(this.schemaCache.keys()), _c = _b.next(); !_c.done; _c = _b.next()) {
var k = _c.value;
if (key.startsWith(k)) {
var s = this.schemaCache.get(k);
if (s != null && s.rootSchema != null) {
return s.rootSchema;
}
}
}
}
catch (e_3_1) { e_3 = { error: e_3_1 }; }
finally {
try {
if (_c && !_c.done && (_a = _b.return)) _a.call(_b);
}
finally { if (e_3) throw e_3.error; }
}
return;
};
ReferenceResolver.prototype.registerRemoteSchema = function (url) {
return tslib_1.__awaiter(this, void 0, void 0, function () {
var res, body, content, schema;
return tslib_1.__generator(this, function (_a) {
switch (_a.label) {
case 0: return [4, fetch(url)];
case 1:
res = _a.sent();
return [4, res.text()];
case 2:
body = _a.sent();
if (!res.ok) {
throw new Error("Error on fetch from url(" + url + "): " + res.status + ", " + body);
}
content = utils_1.parseFileContent(body, url);
schema = jsonSchema_1.parseSchema(content, url);
this.registerSchema(schema);
return [2];
}
});
});
};
ReferenceResolver.prototype.registerSchema = function (schema) {
var _this = this;
debug("register schema: schemaId=[" + schema.id.getAbsoluteId() + "].");
jsonSchema_1.searchAllSubSchema(schema, function (subSchema) {
_this.addSchema(subSchema);
}, function (refId) {
_this.addReference(refId);
});
};
ReferenceResolver.prototype.addSchema = function (schema) {
var id = schema.id;
var key = id.getAbsoluteId();
if (!this.schemaCache.has(key)) {
debug(" add schema: id=" + key);
this.schemaCache.set(key, schema);
if (schema.rootSchema == null) {
var fileId = id.getFileId();
if (!this.schemaCache.has(fileId)) {
this.schemaCache.set(fileId, schema);
}
}
}
};
ReferenceResolver.prototype.addReference = function (refId) {
if (!this.referenceCache.has(refId.getAbsoluteId())) {
debug(" add reference: id=" + refId.getAbsoluteId());
this.referenceCache.set(refId.getAbsoluteId(), undefined);
}
};
ReferenceResolver.prototype.clear = function () {
debug('clear resolver cache.');
this.schemaCache.clear();
this.referenceCache.clear();
};
return ReferenceResolver;
}());
exports.default = ReferenceResolver;
//# sourceMappingURL=referenceResolver.js.map