@orbit/jsonapi
Version:
JSON:API support for Orbit.
210 lines • 30.2 kB
JavaScript
Object.defineProperty(exports, "__esModule", { value: true });
exports.JSONAPIResourceSerializer = void 0;
const utils_1 = require("@orbit/utils");
const core_1 = require("@orbit/core");
const jsonapi_base_serializer_1 = require("./jsonapi-base-serializer");
const { deprecate } = core_1.Orbit;
class JSONAPIResourceSerializer extends jsonapi_base_serializer_1.JSONAPIBaseSerializer {
serialize(record) {
const resource = this.identitySerializer.serialize(record);
const model = this.schema.getModel(record.type);
this.serializeAttributes(resource, record, model);
this.serializeRelationships(resource, record, model);
this.serializeLinks(resource, record, model);
this.serializeMeta(resource, record, model);
return resource;
}
deserialize(resource, customOptions) {
const options = this.buildDeserializationOptions(customOptions);
options.includeKeys = true;
const record = this.identitySerializer.deserialize(resource, options);
const model = this.schema.getModel(record.type);
this.deserializeAttributes(record, resource, model);
this.deserializeRelationships(record, resource, model);
this.deserializeLinks(record, resource, model);
this.deserializeMeta(record, resource, model);
return record;
}
serializeAttributes(resource, record, model) {
if (record.attributes) {
for (let field of Object.keys(record.attributes)) {
this.serializeAttribute(resource, record, field, model);
}
}
}
serializeAttribute(resource, record, field, model) {
var _a, _b, _c, _d;
const value = (_a = record.attributes) === null || _a === void 0 ? void 0 : _a[field];
if (value === undefined) {
return;
}
const fieldOptions = (_b = model.attributes) === null || _b === void 0 ? void 0 : _b[field];
if (fieldOptions === undefined) {
return;
}
let resValue;
if (value === null) {
resValue = null;
}
else {
const type = (_c = fieldOptions.type) !== null && _c !== void 0 ? _c : 'unknown';
const serializer = this.serializerFor(type);
if (serializer) {
const serializationOptions = (_d = fieldOptions.serialization) !== null && _d !== void 0 ? _d : fieldOptions.serializationOptions;
if (fieldOptions.serializationOptions !== undefined) {
// TODO: Remove in v0.18
deprecate(`The attribute '${field}' for '${record.type}' has been assigned \`serializationOptions\` in the schema. Use \`serialization\` instead.`);
}
resValue = serializer.serialize(value, serializationOptions);
}
else {
throw new core_1.Assertion(`Serializer could not be found for attribute type '${type}'`);
}
}
const resField = this.fieldSerializer.serialize(field, {
type: record.type
});
(0, utils_1.deepSet)(resource, ['attributes', resField], resValue);
}
serializeRelationships(resource, record, model) {
if (record.relationships) {
for (let field of Object.keys(record.relationships)) {
this.serializeRelationship(resource, record, field, model);
}
}
}
serializeRelationship(resource, record, field, model) {
var _a, _b;
const value = (_a = record.relationships) === null || _a === void 0 ? void 0 : _a[field].data;
if (value === undefined) {
return;
}
if (((_b = model.relationships) === null || _b === void 0 ? void 0 : _b[field]) === undefined) {
return;
}
let resValue;
if (value === null) {
resValue = null;
}
else {
const identitySerializer = this.identitySerializer;
if (Array.isArray(value)) {
resValue = value.map((identity) => identitySerializer.serialize(identity));
}
else {
resValue = identitySerializer.serialize(value);
}
}
const resField = this.fieldSerializer.serialize(field, {
type: record.type
});
(0, utils_1.deepSet)(resource, ['relationships', resField, 'data'], resValue);
}
/* eslint-disable @typescript-eslint/no-unused-vars */
serializeLinks(resource, record, model) { }
serializeMeta(resource, record, model) { }
/* eslint-enable @typescript-eslint/no-unused-vars */
deserializeAttributes(record, resource, model) {
if (resource.attributes) {
for (let resField of Object.keys(resource.attributes)) {
this.deserializeAttribute(record, resource, resField, model);
}
}
}
deserializeAttribute(record, resource, resField, model) {
var _a, _b, _c;
const resValue = (_a = resource.attributes) === null || _a === void 0 ? void 0 : _a[resField];
if (resValue === undefined) {
return;
}
const field = this.fieldSerializer.deserialize(resField, {
type: record.type
});
const fieldOptions = (_b = model.attributes) === null || _b === void 0 ? void 0 : _b[field];
if (fieldOptions === undefined) {
return;
}
let value;
if (resValue === null) {
value = null;
}
else {
const type = fieldOptions.type || 'unknown';
const serializer = this.serializerFor(type);
if (serializer) {
const deserializationOptions = (_c = fieldOptions.deserialization) !== null && _c !== void 0 ? _c : fieldOptions.deserializationOptions;
if (fieldOptions.deserializationOptions !== undefined) {
// TODO: Remove in v0.18
deprecate(`The attribute '${field}' for '${record.type}' has been assigned \`deserializationOptions\` in the schema. Use \`deserialization\` instead.`);
}
value = serializer.deserialize(resValue, deserializationOptions);
}
else {
throw new core_1.Assertion(`Serializer could not be found for attribute type '${type}'`);
}
}
(0, utils_1.deepSet)(record, ['attributes', field], value);
}
deserializeRelationships(record, resource, model) {
if (resource.relationships) {
for (let resField of Object.keys(resource.relationships)) {
this.deserializeRelationship(record, resource, resField, model);
}
}
}
deserializeRelationship(record, resource, resField, model) {
var _a, _b;
const resValue = (_a = resource.relationships) === null || _a === void 0 ? void 0 : _a[resField];
if (!resValue) {
return;
}
const field = this.fieldSerializer.deserialize(resField, {
type: record.type
});
const fieldOptions = (_b = model.relationships) === null || _b === void 0 ? void 0 : _b[field];
if (fieldOptions === undefined) {
return;
}
let resData = resValue.data;
if (resData !== undefined) {
let data;
if (resData === null) {
data = null;
}
else {
const identitySerializer = this.identitySerializer;
if (Array.isArray(resData)) {
data = resData.map((resourceIdentity) => identitySerializer.deserialize(resourceIdentity));
}
else {
data = identitySerializer.deserialize(resData);
}
}
(0, utils_1.deepSet)(record, ['relationships', field, 'data'], data);
}
let { links, meta } = resValue;
if (links !== undefined) {
(0, utils_1.deepSet)(record, ['relationships', field, 'links'], links);
}
if (meta !== undefined) {
(0, utils_1.deepSet)(record, ['relationships', field, 'meta'], meta);
}
}
deserializeLinks(record, resource,
/* eslint-disable-next-line @typescript-eslint/no-unused-vars */
model) {
if (resource.links) {
record.links = resource.links;
}
}
deserializeMeta(record, resource,
/* eslint-disable-next-line @typescript-eslint/no-unused-vars */
model) {
if (resource.meta) {
record.meta = resource.meta;
}
}
}
exports.JSONAPIResourceSerializer = JSONAPIResourceSerializer;
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoianNvbmFwaS1yZXNvdXJjZS1zZXJpYWxpemVyLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vc3JjL3NlcmlhbGl6ZXJzL2pzb25hcGktcmVzb3VyY2Utc2VyaWFsaXplci50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiOzs7QUFBQSx3Q0FBdUM7QUFDdkMsc0NBQStDO0FBTy9DLHVFQUFrRTtBQUdsRSxNQUFNLEVBQUUsU0FBUyxFQUFFLEdBQUcsWUFBSyxDQUFDO0FBQzVCLE1BQWEseUJBQTBCLFNBQVEsK0NBSzlDO0lBQ0MsU0FBUyxDQUFDLE1BQXlCO1FBQ2pDLE1BQU0sUUFBUSxHQUFhLElBQUksQ0FBQyxrQkFBa0IsQ0FBQyxTQUFTLENBQUMsTUFBTSxDQUFDLENBQUM7UUFDckUsTUFBTSxLQUFLLEdBQW9CLElBQUksQ0FBQyxNQUFNLENBQUMsUUFBUSxDQUFDLE1BQU0sQ0FBQyxJQUFJLENBQUMsQ0FBQztRQUVqRSxJQUFJLENBQUMsbUJBQW1CLENBQUMsUUFBUSxFQUFFLE1BQU0sRUFBRSxLQUFLLENBQUMsQ0FBQztRQUNsRCxJQUFJLENBQUMsc0JBQXNCLENBQUMsUUFBUSxFQUFFLE1BQU0sRUFBRSxLQUFLLENBQUMsQ0FBQztRQUNyRCxJQUFJLENBQUMsY0FBYyxDQUFDLFFBQVEsRUFBRSxNQUFNLEVBQUUsS0FBSyxDQUFDLENBQUM7UUFDN0MsSUFBSSxDQUFDLGFBQWEsQ0FBQyxRQUFRLEVBQUUsTUFBTSxFQUFFLEtBQUssQ0FBQyxDQUFDO1FBRTVDLE9BQU8sUUFBUSxDQUFDO0lBQ2xCLENBQUM7SUFFRCxXQUFXLENBQ1QsUUFBa0IsRUFDbEIsYUFBNkQ7UUFFN0QsTUFBTSxPQUFPLEdBQUcsSUFBSSxDQUFDLDJCQUEyQixDQUFDLGFBQWEsQ0FBQyxDQUFDO1FBQ2hFLE9BQU8sQ0FBQyxXQUFXLEdBQUcsSUFBSSxDQUFDO1FBQzNCLE1BQU0sTUFBTSxHQUFzQixJQUFJLENBQUMsa0JBQWtCLENBQUMsV0FBVyxDQUNu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RUFBQyxNQUFNLEVBQUUsQ0FBQyxlQUFlLEVBQUUsS0FBSyxFQUFFLE9BQU8sQ0FBQyxFQUFFLEtBQUssQ0FBQyxDQUFDO1NBQzNEO1FBRUQsSUFBSSxJQUFJLEtBQUssU0FBUyxFQUFFO1lBQ3RCLElBQUEsZUFBTyxFQUFDLE1BQU0sRUFBRSxDQUFDLGVBQWUsRUFBRSxLQUFLLEVBQUUsTUFBTSxDQUFDLEVBQUUsSUFBSSxDQUFDLENBQUM7U0FDekQ7SUFDSCxDQUFDO0lBRVMsZ0JBQWdCLENBQ3hCLE1BQXlCLEVBQ3pCLFFBQWtCO0lBQ2xCLGdFQUFnRTtJQUNoRSxLQUFzQjtRQUV0QixJQUFJLFFBQVEsQ0FBQyxLQUFLLEVBQUU7WUFDbEIsTUFBTSxDQUFDLEtBQUssR0FBRyxRQUFRLENBQUMsS0FBSyxDQUFDO1NBQy9CO0lBQ0gsQ0FBQztJQUVTLGVBQWUsQ0FDdkIsTUFBeUIsRUFDekIsUUFBa0I7SUFDbEIsZ0VBQWdFO0lBQ2hFLEtBQXNCO1FBRXRCLElBQUksUUFBUSxDQUFDLElBQUksRUFBRTtZQUNqQixNQUFNLENBQUMsSUFBSSxHQUFHLFFBQVEsQ0FBQyxJQUFJLENBQUM7U0FDN0I7SUFDSCxDQUFDO0NBQ0Y7QUF0VEQsOERBc1RDIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgZGVlcFNldCB9IGZyb20gJ0BvcmJpdC91dGlscyc7XG5pbXBvcnQgeyBBc3NlcnRpb24sIE9yYml0IH0gZnJvbSAnQG9yYml0L2NvcmUnO1xuaW1wb3J0IHtcbiAgSW5pdGlhbGl6ZWRSZWNvcmQsXG4gIFJlY29yZElkZW50aXR5LFxuICBNb2RlbERlZmluaXRpb25cbn0gZnJvbSAnQG9yYml0L3JlY29yZHMnO1xuaW1wb3J0IHsgUmVzb3VyY2UsIFJlc291cmNlSWRlbnRpdHkgfSBmcm9tICcuLi9yZXNvdXJjZS1kb2N1bWVudCc7XG5pbXBvcnQgeyBKU09OQVBJQmFzZVNlcmlhbGl6ZXIgfSBmcm9tICcuL2pzb25hcGktYmFzZS1zZXJpYWxpemVyJztcbmltcG9ydCB7IEpTT05BUElSZXNvdXJjZUlkZW50aXR5RGVzZXJpYWxpemF0aW9uT3B0aW9ucyB9IGZyb20gJy4vanNvbmFwaS1yZXNvdXJjZS1pZGVudGl0eS1zZXJpYWxpemVyJztcblxuY29uc3QgeyBkZXByZWNhdGUgfSA9IE9yYml0O1xuZXhwb3J0IGNsYXNzIEpTT05BUElSZXNvdXJjZVNlcmlhbGl6ZXIgZXh0ZW5kcyBKU09OQVBJQmFzZVNlcmlhbGl6ZXI8XG4gIEluaXRpYWxpemVkUmVjb3JkLFxuICBSZXNvdXJjZSxcbiAgdW5rbm93bixcbiAgSlNPTkFQSVJlc291cmNlSWRlbnRpdHlEZXNlcmlhbGl6YXRpb25PcHRpb25zXG4+IHtcbiAgc2VyaWFsaXplKHJlY29yZDogSW5pdGlhbGl6ZWRSZWNvcmQpOiBSZXNvdXJjZSB7XG4gICAgY29uc3QgcmVzb3VyY2U6IFJlc291cmNlID0gdGhpcy5pZGVudGl0eVNlcmlhbGl6ZXIuc2VyaWFsaXplKHJlY29yZCk7XG4gICAgY29uc3QgbW9kZWw6IE1vZGVsRGVmaW5pdGlvbiA9IHRoaXMuc2NoZW1hLmdldE1vZGVsKHJlY29yZC50eXBlKTtcblxuICAgIHRoaXMuc2VyaWFsaXplQXR0cmlidXRlcyhyZXNvdXJjZSwgcmVjb3JkLCBtb2RlbCk7XG4gICAgdGhpcy5zZXJpYWxpemVSZWxhdGlvbnNoaXBzKHJlc291cmNlLCByZWNvcmQsIG1vZGVsKTtcbiAgICB0aGlzLnNlcmlhbGl6ZUxpbmtzKHJlc291cmNlLCByZWNvcmQsIG1vZGVsKTtcbiAgICB0aGlzLnNlcmlhbGl6ZU1ldGEocmVzb3VyY2UsIHJlY29yZCwgbW9kZWwpO1xuXG4gICAgcmV0dXJuIHJlc291cmNlO1xuICB9XG5cbiAgZGVzZXJpYWxpemUoXG4gICAgcmVzb3VyY2U6IFJlc291cmNlLFxuICAgIGN1c3RvbU9wdGlvbnM/OiBKU09OQVBJUmVzb3VyY2VJZGVudGl0eURlc2VyaWFsaXphdGlvbk9wdGlvbnNcbiAgKTogSW5pdGlhbGl6ZWRSZWNvcmQge1xuICAgIGNvbnN0IG9wdGlvbnMgPSB0aGlzLmJ1aWxkRGVzZXJpYWxpemF0aW9uT3B0aW9ucyhjdXN0b21PcHRpb25zKTtcbiAgICBvcHRpb25zLmluY2x1ZGVLZXlzID0gdHJ1ZTtcbiAgICBjb25zdCByZWNvcmQ6IEluaXRpYWxpemVkUmVjb3JkID0gdGhpcy5pZGVudGl0eVNlcmlhbGl6ZXIuZGVzZXJpYWxpemUoXG4gICAgICByZXNvdXJjZSBhcyBSZXNvdXJjZUlkZW50aXR5LFxuICAgICAgb3B0aW9uc1xuICAgICk7XG4gICAgY29uc3QgbW9kZWw6IE1vZGVsRGVmaW5pdGlvbiA9IHRoaXMuc2NoZW1hLmdldE1vZGVsKHJlY29yZC50eXBlKTtcblxuICAgIHRoaXMuZGVzZXJpYWxpemVBdHRyaWJ1dGVzKHJlY29yZCwgcmVzb3VyY2UsIG1vZGVsKTtcbiAgICB0aGlzLmRlc2VyaWFsaXplUmVsYXRpb25zaGlwcyhyZWNvcmQsIHJlc291cmNlLCBtb2RlbCk7XG4gICAgdGhpcy5kZXNlcmlhbGl6ZUxpbmtzKHJlY29yZCwgcmVzb3VyY2UsIG1vZGVsKTtcbiAgICB0aGlzLmRlc2VyaWFsaXplTWV0YShyZWNvcmQsIHJlc291cmNlLCBtb2RlbCk7XG5cbiAgICByZXR1cm4gcmVjb3JkO1xuICB9XG5cbiAgcHJvdGVjdGVkIHNlcmlhbGl6ZUF0dHJpYnV0ZXMoXG4gICAgcmVzb3VyY2U6IFJlc291cmNlLFxuICAgIHJlY29yZDogSW5pdGlhbGl6ZWRSZWNvcmQsXG4gICAgbW9kZWw6IE1vZGVsRGVmaW5pdGlvblxuICApOiB2b2lkIHtcbiAgICBpZiAocmVjb3JkLmF0dHJpYnV0ZXMpIHtcbiAgICAgIGZvciAobGV0IGZpZWxkIG9mIE9iamVjdC5rZXlzKHJlY29yZC5hdHRyaWJ1dGVzKSkge1xuICAgICAgICB0aGlzLnNlcmlhbGl6ZUF0dHJpYnV0ZShyZXNvdXJjZSwgcmVjb3JkLCBmaWVsZCwgbW9kZWwpO1xuICAgICAgfVxuICAgIH1cbiAgfVxuXG4gIHByb3RlY3RlZCBzZXJpYWxpemVBdHRyaWJ1dGUoXG4gICAgcmVzb3VyY2U6IFJlc291cmNlLFxuICAgIHJlY29yZDogSW5pdGlhbGl6ZWRSZWNvcmQsXG4gICAgZmllbGQ6IHN0cmluZyxcbiAgICBtb2RlbDogTW9kZWxEZWZpbml0aW9uXG4gICk6IHZvaWQge1xuICAgIGNvbnN0IHZhbHVlID0gcmVjb3JkLmF0dHJpYnV0ZXM/LltmaWVsZF07XG4gICAgaWYgKHZhbHVlID09PSB1bmRlZmluZWQpIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICBjb25zdCBmaWVsZE9wdGlvbnMgPSBtb2RlbC5hdHRyaWJ1dGVzPy5bZmllbGRdO1xuICAgIGlmIChmaWVsZE9wdGlvbnMgPT09IHVuZGVmaW5lZCkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIGxldCByZXNWYWx1ZTogdW5rbm93bjtcbiAgICBpZiAodmFsdWUgPT09IG51bGwpIHtcbiAgICAgIHJlc1ZhbHVlID0gbnVsbDtcbiAgICB9IGVsc2Uge1xuICAgICAgY29uc3QgdHlwZSA9IGZpZWxkT3B0aW9ucy50eXBlID8/ICd1bmtub3duJztcbiAgICAgIGNvbnN0IHNlcmlhbGl6ZXIgPSB0aGlzLnNlcmlhbGl6ZXJGb3IodHlwZSk7XG4gICAgICBpZiAoc2VyaWFsaXplcikge1xuICAgICAgICBjb25zdCBzZXJpYWxpemF0aW9uT3B0aW9ucyA9XG4gICAgICAgICAgZmllbGRPcHRpb25zLnNlcmlhbGl6YXRpb24gPz9cbiAgICAgICAgICAoZmllbGRPcHRpb25zIGFzIGFueSkuc2VyaWFsaXphdGlvbk9wdGlvbnM7XG5cbiAgICAgICAgaWYgKChmaWVsZE9wdGlvbnMgYXMgYW55KS5zZXJpYWxpemF0aW9uT3B0aW9ucyAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgICAgLy8gVE9ETzogUmVtb3ZlIGluIHYwLjE4XG4gICAgICAgICAgZGVwcmVjYXRlKFxuICAgICAgICAgICAgYFRoZSBhdHRyaWJ1dGUgJyR7ZmllbGR9JyBmb3IgJyR7cmVjb3JkLnR5cGV9JyBoYXMgYmVlbiBhc3NpZ25lZCBcXGBzZXJpYWxpemF0aW9uT3B0aW9uc1xcYCBpbiB0aGUgc2NoZW1hLiBVc2UgXFxgc2VyaWFsaXphdGlvblxcYCBpbnN0ZWFkLmBcbiAgICAgICAgICApO1xuICAgICAgICB9XG5cbiAgICAgICAgcmVzVmFsdWUgPSBzZXJpYWxpemVyLnNlcmlhbGl6ZSh2YWx1ZSwgc2VyaWFsaXphdGlvbk9wdGlvbnMpO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgdGhyb3cgbmV3IEFzc2VydGlvbihcbiAgICAgICAgICBgU2VyaWFsaXplciBjb3VsZCBub3QgYmUgZm91bmQgZm9yIGF0dHJpYnV0ZSB0eXBlICcke3R5cGV9J2BcbiAgICAgICAgKTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICBjb25zdCByZXNGaWVsZCA9IHRoaXMuZmllbGRTZXJpYWxpemVyLnNlcmlhbGl6ZShmaWVsZCwge1xuICAgICAgdHlwZTogcmVjb3JkLnR5cGVcbiAgICB9KSBhcyBzdHJpbmc7XG5cbiAgICBkZWVwU2V0KHJlc291cmNlLCBbJ2F0dHJpYnV0ZXMnLCByZXNGaWVsZF0sIHJlc1ZhbHVlKTtcbiAgfVxuXG4gIHByb3RlY3RlZCBzZXJpYWxpemVSZWxhdGlvbnNoaXBzKFxuICAgIHJlc291cmNlOiBSZXNvdXJjZSxcbiAgICByZWNvcmQ6IEluaXRpYWxpemVkUmVjb3JkLFxuICAgIG1vZGVsOiBNb2RlbERlZmluaXRpb25cbiAgKTogdm9pZCB7XG4gICAgaWYgKHJlY29yZC5yZWxhdGlvbnNoaXBzKSB7XG4gICAgICBmb3IgKGxldCBmaWVsZCBvZiBPYmplY3Qua2V5cyhyZWNvcmQucmVsYXRpb25zaGlwcykpIHtcbiAgICAgICAgdGhpcy5zZXJpYWxpemVSZWxhdGlvbnNoaXAocmVzb3VyY2UsIHJlY29yZCwgZmllbGQsIG1vZGVsKTtcbiAgICAgIH1cbiAgICB9XG4gIH1cblxuICBwcm90ZWN0ZWQgc2VyaWFsaXplUmVsYXRpb25zaGlwKFxuICAgIHJlc291cmNlOiBSZXNvdXJjZSxcbiAgICByZWNvcmQ6IEluaXRpYWxpemVkUmVjb3JkLFxuICAgIGZpZWxkOiBzdHJpbmcsXG4gICAgbW9kZWw6IE1vZGVsRGVmaW5pdGlvblxuICApOiB2b2lkIHtcbiAgICBjb25zdCB2YWx1ZSA9IHJlY29yZC5yZWxhdGlvbnNoaXBzPy5bZmllbGRdLmRhdGE7XG5cbiAgICBpZiAodmFsdWUgPT09IHVuZGVmaW5lZCkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cbiAgICBpZiAobW9kZWwucmVsYXRpb25zaGlwcz8uW2ZpZWxkXSA9PT0gdW5kZWZpbmVkKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgbGV0IHJlc1ZhbHVlO1xuXG4gICAgaWYgKHZhbHVlID09PSBudWxsKSB7XG4gICAgICByZXNWYWx1ZSA9IG51bGw7XG4gICAgfSBlbHNlIHtcbiAgICAgIGNvbnN0IGlkZW50aXR5U2VyaWFsaXplciA9IHRoaXMuaWRlbnRpdHlTZXJpYWxpemVyO1xuXG4gICAgICBpZiAoQXJyYXkuaXNBcnJheSh2YWx1ZSkpIHtcbiAgICAgICAgcmVzVmFsdWUgPSAodmFsdWUgYXMgUmVjb3JkSWRlbnRpdHlbXSkubWFwKChpZGVudGl0eSkgPT5cbiAgICAgICAgICBpZGVudGl0eVNlcmlhbGl6ZXIuc2VyaWFsaXplKGlkZW50aXR5KVxuICAgICAgICApO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgcmVzVmFsdWUgPSBpZGVudGl0eVNlcmlhbGl6ZXIuc2VyaWFsaXplKHZhbHVlKTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICBjb25zdCByZXNGaWVsZCA9IHRoaXMuZmllbGRTZXJpYWxpemVyLnNlcmlhbGl6ZShmaWVsZCwge1xuICAgICAgdHlwZTogcmVjb3JkLnR5cGVcbiAgICB9KSBhcyBzdHJpbmc7XG5cbiAgICBkZWVwU2V0KHJlc291cmNlLCBbJ3JlbGF0aW9uc2hpcHMnLCByZXNGaWVsZCwgJ2RhdGEnXSwgcmVzVmFsdWUpO1xuICB9XG5cbiAgLyogZXNsaW50LWRpc2FibGUgQHR5cGVzY3JpcHQtZXNsaW50L25vLXVudXNlZC12YXJzICovXG4gIHByb3RlY3RlZCBzZXJpYWxpemVMaW5rcyhcbiAgICByZXNvdXJjZTogUmVzb3VyY2UsXG4gICAgcmVjb3JkOiBJbml0aWFsaXplZFJlY29yZCxcbiAgICBtb2RlbDogTW9kZWxEZWZpbml0aW9uXG4gICk6IHZvaWQge31cblxuICBwcm90ZWN0ZWQgc2VyaWFsaXplTWV0YShcbiAgICByZXNvdXJjZTogUmVzb3VyY2UsXG4gICAgcmVjb3JkOiBJbml0aWFsaXplZFJlY29yZCxcbiAgICBtb2RlbDogTW9kZWxEZWZpbml0aW9uXG4gICk6IHZvaWQge31cbiAgLyogZXNsaW50LWVuYWJsZSBAdHlwZXNjcmlwdC1lc2xpbnQvbm8tdW51c2VkLXZhcnMgKi9cblxuICBwcm90ZWN0ZWQgZGVzZXJpYWxpemVBdHRyaWJ1dGVzKFxuICAgIHJlY29yZDogSW5pdGlhbGl6ZWRSZWNvcmQsXG4gICAgcmVzb3VyY2U6IFJlc291cmNlLFxuICAgIG1vZGVsOiBNb2RlbERlZmluaXRpb25cbiAgKTogdm9pZCB7XG4gICAgaWYgKHJlc291cmNlLmF0dHJpYnV0ZXMpIHtcbiAgICAgIGZvciAobGV0IHJlc0ZpZWxkIG9mIE9iamVjdC5rZXlzKHJlc291cmNlLmF0dHJpYnV0ZXMpKSB7XG4gICAgICAgIHRoaXMuZGVzZXJpYWxpemVBdHRyaWJ1dGUocmVjb3JkLCByZXNvdXJjZSwgcmVzRmllbGQsIG1vZGVsKTtcbiAgICAgIH1cbiAgICB9XG4gIH1cblxuICBwcm90ZWN0ZWQgZGVzZXJpYWxpemVBdHRyaWJ1dGUoXG4gICAgcmVjb3JkOiBJbml0aWFsaXplZFJlY29yZCxcbiAgICByZXNvdXJjZTogUmVzb3VyY2UsXG4gICAgcmVzRmllbGQ6IHN0cmluZyxcbiAgICBtb2RlbDogTW9kZWxEZWZpbml0aW9uXG4gICk6IHZvaWQge1xuICAgIGNvbnN0IHJlc1ZhbHVlOiBhbnkgPSByZXNvdXJjZS5hdHRyaWJ1dGVzPy5bcmVzRmllbGRdO1xuICAgIGlmIChyZXNWYWx1ZSA9PT0gdW5kZWZpbmVkKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgY29uc3QgZmllbGQgPSB0aGlzLmZpZWxkU2VyaWFsaXplci5kZXNlcmlhbGl6ZShyZXNGaWVsZCwge1xuICAgICAgdHlwZTogcmVjb3JkLnR5cGVcbiAgICB9KSBhcyBzdHJpbmc7XG5cbiAgICBjb25zdCBmaWVsZE9wdGlvbnMgPSBtb2RlbC5hdHRyaWJ1dGVzPy5bZmllbGRdO1xuICAgIGlmIChmaWVsZE9wdGlvbnMgPT09IHVuZGVmaW5lZCkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIGxldCB2YWx1ZTogdW5rbm93bjtcbiAgICBpZiAocmVzVmFsdWUgPT09IG51bGwpIHtcbiAgICAgIHZhbHVlID0gbnVsbDtcbiAgICB9IGVsc2Uge1xuICAgICAgY29uc3QgdHlwZSA9IGZpZWxkT3B0aW9ucy50eXBlIHx8ICd1bmtub3duJztcbiAgICAgIGNvbnN0IHNlcmlhbGl6ZXIgPSB0aGlzLnNlcmlhbGl6ZXJGb3IodHlwZSk7XG4gICAgICBpZiAoc2VyaWFsaXplcikge1xuICAgICAgICBjb25zdCBkZXNlcmlhbGl6YXRpb25PcHRpb25zID1cbiAgICAgICAgICBmaWVsZE9wdGlvbnMuZGVzZXJpYWxpemF0aW9uID8/XG4gICAgICAgICAgKGZpZWxkT3B0aW9ucyBhcyBhbnkpLmRlc2VyaWFsaXphdGlvbk9wdGlvbnM7XG5cbiAgICAgICAgaWYgKChmaWVsZE9wdGlvbnMgYXMgYW55KS5kZXNlcmlhbGl6YXRpb25PcHRpb25zICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgICAvLyBUT0RPOiBSZW1vdmUgaW4gdjAuMThcbiAgICAgICAgICBkZXByZWNhdGUoXG4gICAgICAgICAgICBgVGhlIGF0dHJpYnV0ZSAnJHtmaWVsZH0nIGZvciAnJHtyZWNvcmQudHlwZX0nIGhhcyBiZWVuIGFzc2lnbmVkIFxcYGRlc2VyaWFsaXphdGlvbk9wdGlvbnNcXGAgaW4gdGhlIHNjaGVtYS4gVXNlIFxcYGRlc2VyaWFsaXphdGlvblxcYCBpbnN0ZWFkLmBcbiAgICAgICAgICApO1xuICAgICAgICB9XG5cbiAgICAgICAgdmFsdWUgPSBzZXJpYWxpemVyLmRlc2VyaWFsaXplKHJlc1ZhbHVlLCBkZXNlcmlhbGl6YXRpb25PcHRpb25zKTtcbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIHRocm93IG5ldyBBc3NlcnRpb24oXG4gICAgICAgICAgYFNlcmlhbGl6ZXIgY291bGQgbm90IGJlIGZvdW5kIGZvciBhdHRyaWJ1dGUgdHlwZSAnJHt0eXBlfSdgXG4gICAgICAgICk7XG4gICAgICB9XG4gICAgfVxuXG4gICAgZGVlcFNldChyZWNvcmQsIFsnYXR0cmlidXRlcycsIGZpZWxkXSwgdmFsdWUpO1xuICB9XG5cbiAgcHJvdGVjdGVkIGRlc2VyaWFsaXplUmVsYXRpb25zaGlwcyhcbiAgICByZWNvcmQ6IEluaXRpYWxpemVkUmVjb3JkLFxuICAgIHJlc291cmNlOiBSZXNvdXJjZSxcbiAgICBtb2RlbDogTW9kZWxEZWZpbml0aW9uXG4gICk6IHZvaWQge1xuICAgIGlmIChyZXNvdXJjZS5yZWxhdGlvbnNoaXBzKSB7XG4gICAgICBmb3IgKGxldCByZXNGaWVsZCBvZiBPYmplY3Qua2V5cyhyZXNvdXJjZS5yZWxhdGlvbnNoaXBzKSkge1xuICAgICAgICB0aGlzLmRlc2VyaWFsaXplUmVsYXRpb25zaGlwKHJlY29yZCwgcmVzb3VyY2UsIHJlc0ZpZWxkLCBtb2RlbCk7XG4gICAgICB9XG4gICAgfVxuICB9XG5cbiAgcHJvdGVjdGVkIGRlc2VyaWFsaXplUmVsYXRpb25zaGlwKFxuICAgIHJlY29yZDogSW5pdGlhbGl6ZWRSZWNvcmQsXG4gICAgcmVzb3VyY2U6IFJlc291cmNlLFxuICAgIHJlc0ZpZWxkOiBzdHJpbmcsXG4gICAgbW9kZWw6IE1vZGVsRGVmaW5pdGlvblxuICApOiB2b2lkIHtcbiAgICBjb25zdCByZXNWYWx1ZTogYW55ID0gcmVzb3VyY2UucmVsYXRpb25zaGlwcz8uW3Jlc0ZpZWxkXTtcbiAgICBpZiAoIXJlc1ZhbHVlKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgY29uc3QgZmllbGQgPSB0aGlzLmZpZWxkU2VyaWFsaXplci5kZXNlcmlhbGl6ZShyZXNGaWVsZCwge1xuICAgICAgdHlwZTogcmVjb3JkLnR5cGVcbiAgICB9KSBhcyBzdHJpbmc7XG5cbiAgICBjb25zdCBmaWVsZE9wdGlvbnMgPSBtb2RlbC5yZWxhdGlvbnNoaXBzPy5bZmllbGRdO1xuICAgIGlmIChmaWVsZE9wdGlvbnMgPT09IHVuZGVmaW5lZCkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIGxldCByZXNEYXRhID0gcmVzVmFsdWUuZGF0YTtcblxuICAgIGlmIChyZXNEYXRhICE9PSB1bmRlZmluZWQpIHtcbiAgICAgIGxldCBkYXRhO1xuXG4gICAgICBpZiAocmVzRGF0YSA9PT0gbnVsbCkge1xuICAgICAgICBkYXRhID0gbnVsbDtcbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIGNvbnN0IGlkZW50aXR5U2VyaWFsaXplciA9IHRoaXMuaWRlbnRpdHlTZXJpYWxpemVyO1xuXG4gICAgICAgIGlmIChBcnJheS5pc0FycmF5KHJlc0RhdGEpKSB7XG4gICAgICAgICAgZGF0YSA9IChyZXNEYXRhIGFzIFJlc291cmNlSWRlbnRpdHlbXSkubWFwKChyZXNvdXJjZUlkZW50aXR5KSA9PlxuICAgICAgICAgICAgaWRlbnRpdHlTZXJpYWxpemVyLmRlc2VyaWFsaXplKHJlc291cmNlSWRlbnRpdHkpXG4gICAgICAgICAgKTtcbiAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICBkYXRhID0gaWRlbnRpdHlTZXJpYWxpemVyLmRlc2VyaWFsaXplKHJlc0RhdGEgYXMgUmVzb3VyY2VJZGVudGl0eSk7XG4gICAgICAgIH1cbiAgICAgIH1cblxuICAgICAgZGVlcFNldChyZWNvcmQsIFsncmVsYXRpb25zaGlwcycsIGZpZWxkLCAnZGF0YSddLCBkYXRhKTtcbiAgICB9XG5cbiAgICBsZXQgeyBsaW5rcywgbWV0YSB9ID0gcmVzVmFsdWU7XG5cbiAgICBpZiAobGlua3MgIT09IHVuZGVmaW5lZCkge1xuICAgICAgZGVlcFNldChyZWNvcmQsIFsncmVsYXRpb25zaGlwcycsIGZpZWxkLCAnbGlua3MnXSwgbGlua3MpO1xuICAgIH1cblxuICAgIGlmIChtZXRhICE9PSB1bmRlZmluZWQpIHtcbiAgICAgIGRlZXBTZXQocmVjb3JkLCBbJ3JlbGF0aW9uc2hpcHMnLCBmaWVsZCwgJ21ldGEnXSwgbWV0YSk7XG4gICAgfVxuICB9XG5cbiAgcHJvdGVjdGVkIGRlc2VyaWFsaXplTGlua3MoXG4gICAgcmVjb3JkOiBJbml0aWFsaXplZFJlY29yZCxcbiAgICByZXNvdXJjZTogUmVzb3VyY2UsXG4gICAgLyogZXNsaW50LWRpc2FibGUtbmV4dC1saW5lIEB0eXBlc2NyaXB0LWVzbGludC9uby11bnVzZWQtdmFycyAqL1xuICAgIG1vZGVsOiBNb2RlbERlZmluaXRpb25cbiAgKTogdm9pZCB7XG4gICAgaWYgKHJlc291cmNlLmxpbmtzKSB7XG4gICAgICByZWNvcmQubGlua3MgPSByZXNvdXJjZS5saW5rcztcbiAgICB9XG4gIH1cblxuICBwcm90ZWN0ZWQgZGVzZXJpYWxpemVNZXRhKFxuICAgIHJlY29yZDogSW5pdGlhbGl6ZWRSZWNvcmQsXG4gICAgcmVzb3VyY2U6IFJlc291cmNlLFxuICAgIC8qIGVzbGludC1kaXNhYmxlLW5leHQtbGluZSBAdHlwZXNjcmlwdC1lc2xpbnQvbm8tdW51c2VkLXZhcnMgKi9cbiAgICBtb2RlbDogTW9kZWxEZWZpbml0aW9uXG4gICk6IHZvaWQge1xuICAgIGlmIChyZXNvdXJjZS5tZXRhKSB7XG4gICAgICByZWNvcmQubWV0YSA9IHJlc291cmNlLm1ldGE7XG4gICAgfVxuICB9XG59XG4iXX0=
;