import { __assign } from "/_nuxt/node_modules/tslib/tslib.es6.js?v=e4f18c29"; import { Trie } from "/_nuxt/node_modules/@wry/trie/lib/index.js?v=e4f18c29"; import { canUseWeakMap, canUseWeakSet, isNonNullObject as isObjectOrArray, } from "/_nuxt/node_modules/@apollo/client/utilities/index.js?v=e4f18c29"; import { isArray } from "/_nuxt/node_modules/@apollo/client/cache/inmemory/helpers.js?v=e4f18c29"; function shallowCopy(value) { if (isObjectOrArray(value)) { return isArray(value) ? value.slice(0) : __assign({ __proto__: Object.getPrototypeOf(value) }, value); } return value; } // When programmers talk about the "canonical form" of an object, they // usually have the following meaning in mind, which I've copied from // https://en.wiktionary.org/wiki/canonical_form: // // 1. A standard or normal presentation of a mathematical entity [or // object]. A canonical form is an element of a set of representatives // of equivalence classes of forms such that there is a function or // procedure which projects every element of each equivalence class // onto that one element, the canonical form of that equivalence // class. The canonical form is expected to be simpler than the rest of // the forms in some way. // // That's a long-winded way of saying any two objects that have the same // canonical form may be considered equivalent, even if they are !==, // which usually means the objects are structurally equivalent (deeply // equal), but don't necessarily use the same memory. // // Like a literary or musical canon, this ObjectCanon class represents a // collection of unique canonical items (JavaScript objects), with the // important property that canon.admit(a) === canon.admit(b) if a and b // are deeply equal to each other. In terms of the definition above, the // canon.admit method is the "function or procedure which projects every" // object "onto that one element, the canonical form." // // In the worst case, the canonicalization process may involve looking at // every property in the provided object tree, so it takes the same order // of time as deep equality checking. Fortunately, already-canonicalized // objects are returned immediately from canon.admit, so the presence of // canonical subtrees tends to speed up canonicalization. // // Since consumers of canonical objects can check for deep equality in // constant time, canonicalizing cache results can massively improve the // performance of application code that skips re-rendering unchanged // results, such as "pure" UI components in a framework like React. // // Of course, since canonical objects may be shared widely between // unrelated consumers, it's important to think of them as immutable, even // though they are not actually frozen with Object.freeze in production, // due to the extra performance overhead that comes with frozen objects. // // Custom scalar objects whose internal class name is neither Array nor // Object can be included safely in the admitted tree, but they will not // be replaced with a canonical version (to put it another way, they are // assumed to be canonical already). // // If we ignore custom objects, no detection of cycles or repeated object // references is currently required by the StoreReader class, since // GraphQL result objects are JSON-serializable trees (and thus contain // neither cycles nor repeated subtrees), so we can avoid the complexity // of keeping track of objects we've already seen during the recursion of // the admit method. // // In the future, we may consider adding additional cases to the switch // statement to handle other common object types, such as "[object Date]" // objects, as needed. var ObjectCanon = /** @class */ (function () { function ObjectCanon() { // Set of all canonical objects this ObjectCanon has admitted, allowing // canon.admit to return previously-canonicalized objects immediately. this.known = new (canUseWeakSet ? WeakSet : Set)(); // Efficient storage/lookup structure for canonical objects. this.pool = new Trie(canUseWeakMap); // Make the ObjectCanon assume this value has already been // canonicalized. this.passes = new WeakMap(); // Arrays that contain the same elements in a different order can share // the same SortedKeysInfo object, to save memory. this.keysByJSON = new Map(); // This has to come last because it depends on keysByJSON. this.empty = this.admit({}); } ObjectCanon.prototype.isKnown = function (value) { return isObjectOrArray(value) && this.known.has(value); }; ObjectCanon.prototype.pass = function (value) { if (isObjectOrArray(value)) { var copy = shallowCopy(value); this.passes.set(copy, value); return copy; } return value; }; ObjectCanon.prototype.admit = function (value) { var _this = this; if (isObjectOrArray(value)) { var original = this.passes.get(value); if (original) return original; var proto = Object.getPrototypeOf(value); switch (proto) { case Array.prototype: { if (this.known.has(value)) return value; var array = value.map(this.admit, this); // Arrays are looked up in the Trie using their recursively // canonicalized elements, and the known version of the array is // preserved as node.array. var node = this.pool.lookupArray(array); if (!node.array) { this.known.add((node.array = array)); // Since canonical arrays may be shared widely between // unrelated consumers, it's important to regard them as // immutable, even if they are not frozen in production. if (globalThis.__DEV__ !== false) { Object.freeze(array); } } return node.array; } case null: case Object.prototype: { if (this.known.has(value)) return value; var proto_1 = Object.getPrototypeOf(value); var array_1 = [proto_1]; var keys = this.sortedKeys(value); array_1.push(keys.json); var firstValueIndex_1 = array_1.length; keys.sorted.forEach(function (key) { array_1.push(_this.admit(value[key])); }); // Objects are looked up in the Trie by their prototype (which // is *not* recursively canonicalized), followed by a JSON // representation of their (sorted) keys, followed by the // sequence of recursively canonicalized values corresponding to // those keys. To keep the final results unambiguous with other // sequences (such as arrays that just happen to contain [proto, // keys.json, value1, value2, ...]), the known version of the // object is stored as node.object. var node = this.pool.lookupArray(array_1); if (!node.object) { var obj_1 = (node.object = Object.create(proto_1)); this.known.add(obj_1); keys.sorted.forEach(function (key, i) { obj_1[key] = array_1[firstValueIndex_1 + i]; }); // Since canonical objects may be shared widely between // unrelated consumers, it's important to regard them as // immutable, even if they are not frozen in production. if (globalThis.__DEV__ !== false) { Object.freeze(obj_1); } } return node.object; } } } return value; }; // It's worthwhile to cache the sorting of arrays of strings, since the // same initial unsorted arrays tend to be encountered many times. // Fortunately, we can reuse the Trie machinery to look up the sorted // arrays in linear time (which is faster than sorting large arrays). ObjectCanon.prototype.sortedKeys = function (obj) { var keys = Object.keys(obj); var node = this.pool.lookupArray(keys); if (!node.keys) { keys.sort(); var json = JSON.stringify(keys); if (!(node.keys = this.keysByJSON.get(json))) { this.keysByJSON.set(json, (node.keys = { sorted: keys, json: json })); } } return node.keys; }; return ObjectCanon; }()); export { ObjectCanon }; //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoib2JqZWN0LWNhbm9uLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vc3JjL2NhY2hlL2lubWVtb3J5L29iamVjdC1jYW5vbi50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiO0FBQUEsT0FBTyxFQUFFLElBQUksRUFBRSxNQUFNLFdBQVcsQ0FBQztBQUNqQyxPQUFPLEVBQ0wsYUFBYSxFQUNiLGFBQWEsRUFDYixlQUFlLElBQUksZUFBZSxHQUNuQyxNQUFNLDBCQUEwQixDQUFDO0FBQ2xDLE9BQU8sRUFBRSxPQUFPLEVBQUUsTUFBTSxjQUFjLENBQUM7QUFFdkMsU0FBUyxXQUFXLENBQUksS0FBUTtJQUM5QixJQUFJLGVBQWUsQ0FBQyxLQUFLLENBQUMsRUFBRSxDQUFDO1FBQzNCLE9BQU8sT0FBTyxDQUFDLEtBQUssQ0FBQyxDQUFDLENBQUM7WUFDbEIsS0FBSyxDQUFDLEtBQUssQ0FBQyxDQUFDLENBQWM7WUFDOUIsQ0FBQyxZQUFHLFNBQVMsRUFBRSxNQUFNLENBQUMsY0FBYyxDQUFDLEtBQUssQ0FBQyxJQUFLLEtBQUssQ0FBRSxDQUFDO0lBQzVELENBQUM7SUFDRCxPQUFPLEtBQUssQ0FBQztBQUNmLENBQUM7QUFFRCxzRUFBc0U7QUFDdEUscUVBQXFFO0FBQ3JFLGlEQUFpRDtBQUNqRCxFQUFFO0FBQ0Ysb0VBQW9FO0FBQ3BFLHlFQUF5RTtBQUN6RSxzRUFBc0U7QUFDdEUsc0VBQXNFO0FBQ3RFLG1FQUFtRTtBQUNuRSwwRUFBMEU7QUFDMUUsNEJBQTRCO0FBQzVCLEVBQUU7QUFDRix3RUFBd0U7QUFDeEUscUVBQXFFO0FBQ3JFLHNFQUFzRTtBQUN0RSxxREFBcUQ7QUFDckQsRUFBRTtBQUNGLHdFQUF3RTtBQUN4RSxzRUFBc0U7QUFDdEUsdUVBQXVFO0FBQ3ZFLHdFQUF3RTtBQUN4RSx5RUFBeUU7QUFDekUsc0RBQXNEO0FBQ3RELEVBQUU7QUFDRix5RUFBeUU7QUFDekUseUVBQXlFO0FBQ3pFLHdFQUF3RTtBQUN4RSx3RUFB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QUcsQ0FBQyxJQUFJLENBQUMsQ0FBQyxFQUFFLENBQUM7Z0JBQzdDLElBQUksQ0FBQyxVQUFVLENBQUMsR0FBRyxDQUFDLElBQUksRUFBRSxDQUFDLElBQUksQ0FBQyxJQUFJLEdBQUcsRUFBRSxNQUFNLEVBQUUsSUFBSSxFQUFFLElBQUksTUFBQSxFQUFFLENBQUMsQ0FBQyxDQUFDO1lBQ2xFLENBQUM7UUFDSCxDQUFDO1FBQ0QsT0FBTyxJQUFJLENBQUMsSUFBSSxDQUFDO0lBQ25CLENBQUM7SUFPSCxrQkFBQztBQUFELENBQUMsQUF2SEQsSUF1SEMiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBUcmllIH0gZnJvbSBcIkB3cnkvdHJpZVwiO1xuaW1wb3J0IHtcbiAgY2FuVXNlV2Vha01hcCxcbiAgY2FuVXNlV2Vha1NldCxcbiAgaXNOb25OdWxsT2JqZWN0IGFzIGlzT2JqZWN0T3JBcnJheSxcbn0gZnJvbSBcIi4uLy4uL3V0aWxpdGllcy9pbmRleC5qc1wiO1xuaW1wb3J0IHsgaXNBcnJheSB9IGZyb20gXCIuL2hlbHBlcnMuanNcIjtcblxuZnVuY3Rpb24gc2hhbGxvd0NvcHk8VD4odmFsdWU6IFQpOiBUIHtcbiAgaWYgKGlzT2JqZWN0T3JBcnJheSh2YWx1ZSkpIHtcbiAgICByZXR1cm4gaXNBcnJheSh2YWx1ZSkgP1xuICAgICAgICAodmFsdWUuc2xpY2UoMCkgYXMgYW55IGFzIFQpXG4gICAgICA6IHsgX19wcm90b19fOiBPYmplY3QuZ2V0UHJvdG90eXBlT2YodmFsdWUpLCAuLi52YWx1ZSB9O1xuICB9XG4gIHJldHVybiB2YWx1ZTtcbn1cblxuLy8gV2hlbiBwcm9ncmFtbWVycyB0YWxrIGFib3V0IHRoZSBcImNhbm9uaWNhbCBmb3JtXCIgb2YgYW4gb2JqZWN0LCB0aGV5XG4vLyB1c3VhbGx5IGhhdmUgdGhlIGZvbGxvd2luZyBtZWFuaW5nIGluIG1pbmQsIHdoaWNoIEkndmUgY29waWVkIGZyb21cbi8vIGh0dHBzOi8vZW4ud2lrdGlvbmFyeS5vcmcvd2lraS9jYW5vbmljYWxfZm9ybTpcbi8vXG4vLyAxLiBBIHN0YW5kYXJkIG9yIG5vcm1hbCBwcmVzZW50YXRpb24gb2YgYSBtYXRoZW1hdGljYWwgZW50aXR5IFtvclxuLy8gICAgb2JqZWN0XS4gQSBjYW5vbmljYWwgZm9ybSBpcyBhbiBlbGVtZW50IG9mIGEgc2V0IG9mIHJlcHJlc2VudGF0aXZlc1xuLy8gICAgb2YgZXF1aXZhbGVuY2UgY2xhc3NlcyBvZiBmb3JtcyBzdWNoIHRoYXQgdGhlcmUgaXMgYSBmdW5jdGlvbiBvclxuLy8gICAgcHJvY2VkdXJlIHdoaWNoIHByb2plY3RzIGV2ZXJ5IGVsZW1lbnQgb2YgZWFjaCBlcXVpdmFsZW5jZSBjbGFzc1xuLy8gICAgb250byB0aGF0IG9uZSBlbGVtZW50LCB0aGUgY2Fub25pY2FsIGZvcm0gb2YgdGhhdCBlcXVpdmFsZW5jZVxuLy8gICAgY2xhc3MuIFRoZSBjYW5vbmljYWwgZm9ybSBpcyBleHBlY3RlZCB0byBiZSBzaW1wbGVyIHRoYW4gdGhlIHJlc3Qgb2Zcbi8vICAgIHRoZSBmb3JtcyBpbiBzb21lIHdheS5cbi8vXG4vLyBUaGF0J3MgYSBsb25nLXdpbmRlZCB3YXkgb2Ygc2F5aW5nIGFueSB0d28gb2JqZWN0cyB0aGF0IGhhdmUgdGhlIHNhbWVcbi8vIGNhbm9uaWNhbCBmb3JtIG1heSBiZSBjb25zaWRlcmVkIGVxdWl2YWxlbnQsIGV2ZW4gaWYgdGhleSBhcmUgIT09LFxuLy8gd2hpY2ggdXN1YWxseSBtZWFucyB0aGUgb2JqZWN0cyBhcmUgc3RydWN0dXJhbGx5IGVxdWl2YWxlbnQgKGRlZXBseVxuLy8gZXF1YWwpLCBidXQgZG9uJ3QgbmVjZXNzYXJpbHkgdXNlIHRoZSBzYW1lIG1lbW9yeS5cbi8vXG4vLyBMaWtlIGEgbGl0ZXJhcnkgb3IgbXVzaWNhbCBjYW5vbiwgdGhpcyBPYmplY3RDYW5vbiBjbGFzcyByZXByZXNlbnRzIGFcbi8vIGNvbGxlY3Rpb24gb2YgdW5pcXVlIGNhbm9uaWNhbCBpdGVtcyAoSmF2YVNjcmlwdCBvYmplY3RzKSwgd2l0aCB0aGVcbi8vIGltcG9ydGFudCBwcm9wZXJ0eSB0aGF0IGNhbm9uLmFkbWl0KGEpID09PSBjYW5vbi5hZG1pdChiKSBpZiBhIGFuZCBiXG4vLyBhcmUgZGVlcGx5IGVxdWFsIHRvIGVhY2ggb3RoZXIuIEluIHRlcm1zIG9mIHRoZSBkZWZpbml0aW9uIGFib3ZlLCB0aGVcbi8vIGNhbm9uLmFkbWl0IG1ldGhvZCBpcyB0aGUgXCJmdW5jdGlvbiBvciBwcm9jZWR1cmUgd2hpY2ggcHJvamVjdHMgZXZlcnlcIlxuLy8gb2JqZWN0IFwib250byB0aGF0IG9uZSBlbGVtZW50LCB0aGUgY2Fub25pY2FsIGZvcm0uXCJcbi8vXG4vLyBJbiB0aGUgd29yc3QgY2FzZSwgdGhlIGNhbm9uaWNhbGl6YXRpb24gcHJvY2VzcyBtYXkgaW52b2x2ZSBsb29raW5nIGF0XG4vLyBldmVyeSBwcm9wZXJ0eSBpbiB0aGUgcHJvdmlkZWQgb2JqZWN0IHRyZWUsIHNvIGl0IHRha2VzIHRoZSBzYW1lIG9yZGVyXG4vLyBvZiB0aW1lIGFzIGRlZXAgZXF1YWxpdHkgY2hlY2tpbmcuIEZvcnR1bmF0ZWx5LCBhbHJlYWR5LWNhbm9uaWNhbGl6ZWRcbi8vIG9iamVjdHMgYXJlIHJldHVybmVkIGltbWVkaWF0ZWx5IGZyb20gY2Fub24uYWRtaXQsIHNvIHRoZSBwcmVzZW5jZSBvZlxuLy8gY2Fub25pY2FsIHN1YnRyZWVzIHRlbmRzIHRvIHNwZWVkIHVwIGNhbm9uaWNhbGl6YXRpb24uXG4vL1xuLy8gU2luY2UgY29uc3VtZXJzIG9mIGNhbm9uaWNhbCBvYmplY3RzIGNhbiBjaGVjayBmb3IgZGVlcCBlcXVhbGl0eSBpblxuLy8gY29uc3RhbnQgdGltZSwgY2Fub25pY2FsaXppbmcgY2FjaGUgcmVzdWx0cyBjYW4gbWFzc2l2ZWx5IGltcHJvdmUgdGhlXG4vLyBwZXJmb3JtYW5jZSBvZiBhcHBsaWNhdGlvbiBjb2RlIHRoYXQgc2tpcHMgcmUtcmVuZGVyaW5nIHVuY2hhbmdlZFxuLy8gcmVzdWx0cywgc3VjaCBhcyBcInB1cmVcIiBVSSBjb21wb25lbnRzIGluIGEgZnJhbWV3b3JrIGxpa2UgUmVhY3QuXG4vL1xuLy8gT2YgY291cnNlLCBzaW5jZSBjYW5vbmljYWwgb2JqZWN0cyBtYXkgYmUgc2hhcmVkIHdpZGVseSBiZXR3ZWVuXG4vLyB1bnJlbGF0ZWQgY29uc3VtZXJzLCBpdCdzIGltcG9ydGFudCB0byB0aGluayBvZiB0aGVtIGFzIGltbXV0YWJsZSwgZXZlblxuLy8gdGhvdWdoIHRoZXkgYXJlIG5vdCBhY3R1YWxseSBmcm96ZW4gd2l0aCBPYmplY3QuZnJlZXplIGluIHByb2R1Y3Rpb24sXG4vLyBkdWUgdG8gdGhlIGV4dHJhIHBlcmZvcm1hbmNlIG92ZXJoZWFkIHRoYXQgY29tZXMgd2l0aCBmcm96ZW4gb2JqZWN0cy5cbi8vXG4vLyBDdXN0b20gc2NhbGFyIG9iamVjdHMgd2hvc2UgaW50ZXJuYWwgY2xhc3MgbmFtZSBpcyBuZWl0aGVyIEFycmF5IG5vclxuLy8gT2JqZWN0IGNhbiBiZSBpbmNsdWRlZCBzYWZlbHkgaW4gdGhlIGFkbWl0dGVkIHRyZWUsIGJ1dCB0aGV5IHdpbGwgbm90XG4vLyBiZSByZXBsYWNlZCB3aXRoIGEgY2Fub25pY2FsIHZlcnNpb24gKHRvIHB1dCBpdCBhbm90aGVyIHdheSwgdGhleSBhcmVcbi8vIGFzc3VtZWQgdG8gYmUgY2Fub25pY2FsIGFscmVhZHkpLlxuLy9cbi8vIElmIHdlIGlnbm9yZSBjdXN0b20gb2JqZWN0cywgbm8gZGV0ZWN0aW9uIG9mIGN5Y2xlcyBvciByZXBlYXRlZCBvYmplY3Rcbi8vIHJlZmVyZW5jZXMgaXMgY3VycmVudGx5IHJlcXVpcmVkIGJ5IHRoZSBTdG9yZVJlYWRlciBjbGFzcywgc2luY2Vcbi8vIEdyYXBoUUwgcmVzdWx0IG9iamVjdHMgYXJlIEpTT04tc2VyaWFsaXphYmxlIHRyZWVzIChhbmQgdGh1cyBjb250YWluXG4vLyBuZWl0aGVyIGN5Y2xlcyBub3IgcmVwZWF0ZWQgc3VidHJlZXMpLCBzbyB3ZSBjYW4gYXZvaWQgdGhlIGNvbXBsZXhpdHlcbi8vIG9mIGtlZXBpbmcgdHJhY2sgb2Ygb2JqZWN0cyB3ZSd2ZSBhbHJlYWR5IHNlZW4gZHVyaW5nIHRoZSByZWN1cnNpb24gb2Zcbi8vIHRoZSBhZG1pdCBtZXRob2QuXG4vL1xuLy8gSW4gdGhlIGZ1dHVyZSwgd2UgbWF5IGNvbnNpZGVyIGFkZGluZyBhZGRpdGlvbmFsIGNhc2VzIHRvIHRoZSBzd2l0Y2hcbi8vIHN0YXRlbWVudCB0byBoYW5kbGUgb3RoZXIgY29tbW9uIG9iamVjdCB0eXBlcywgc3VjaCBhcyBcIltvYmplY3QgRGF0ZV1cIlxuLy8gb2JqZWN0cywgYXMgbmVlZGVkLlxuZXhwb3J0IGNsYXNzIE9iamVjdENhbm9uIHtcbiAgLy8gU2V0IG9mIGFsbCBjYW5vbmljYWwgb2JqZWN0cyB0aGlzIE9iamVjdENhbm9uIGhhcyBhZG1pdHRlZCwgYWxsb3dpbmdcbiAgLy8gY2Fub24uYWRtaXQgdG8gcmV0dXJuIHByZXZpb3VzbHktY2Fub25pY2FsaXplZCBvYmplY3RzIGltbWVkaWF0ZWx5LlxuICBwcml2YXRlIGtub3duID0gbmV3IChjYW5Vc2VXZWFrU2V0ID8gV2Vha1NldCA6IFNldCk8b2JqZWN0PigpO1xuXG4gIC8vIEVmZmljaWVudCBzdG9yYWdlL2xvb2t1cCBzdHJ1Y3R1cmUgZm9yIGNhbm9uaWNhbCBvYmplY3RzLlxuICBwcml2YXRlIHBvb2wgPSBuZXcgVHJpZTx7XG4gICAgYXJyYXk/OiBhbnlbXTtcbiAgICBvYmplY3Q/OiBSZWNvcmQ8c3RyaW5nLCBhbnk+O1xuICAgIGtleXM/OiBTb3J0ZWRLZXlzSW5mbztcbiAgfT4oY2FuVXNlV2Vha01hcCk7XG5cbiAgcHVibGljIGlzS25vd24odmFsdWU6IGFueSk6IGJvb2xlYW4ge1xuICAgIHJldHVybiBpc09iamVjdE9yQXJyYXkodmFsdWUpICYmIHRoaXMua25vd24uaGFzKHZhbHVlKTtcbiAgfVxuXG4gIC8vIE1ha2UgdGhlIE9iamVjdENhbm9uIGFzc3VtZSB0aGlzIHZhbHVlIGhhcyBhbHJlYWR5IGJlZW5cbiAgLy8gY2Fub25pY2FsaXplZC5cbiAgcHJpdmF0ZSBwYXNzZXMgPSBuZXcgV2Vha01hcDxvYmplY3QsIG9iamVjdD4oKTtcbiAgcHVibGljIHBhc3M8VD4odmFsdWU6IFQpOiBUO1xuICBwdWJsaWMgcGFzcyh2YWx1ZTogYW55KSB7XG4gICAgaWYgKGlzT2JqZWN0T3JBcnJheSh2YWx1ZSkpIHtcbiAgICAgIGNvbnN0IGNvcHkgPSBzaGFsbG93Q29weSh2YWx1ZSk7XG4gICAgICB0aGlzLnBhc3Nlcy5zZXQoY29weSwgdmFsdWUpO1xuICAgICAgcmV0dXJuIGNvcHk7XG4gICAgfVxuICAgIHJldHVybiB2YWx1ZTtcbiAgfVxuXG4gIC8vIFJldHVybnMgdGhlIGNhbm9uaWNhbCB2ZXJzaW9uIG9mIHZhbHVlLlxuICBwdWJsaWMgYWRtaXQ8VD4odmFsdWU6IFQpOiBUO1xuICBwdWJsaWMgYWRtaXQodmFsdWU6IGFueSkge1xuICAgIGlmIChpc09iamVjdE9yQXJyYXkodmFsdWUpKSB7XG4gICAgICBjb25zdCBvcmlnaW5hbCA9IHRoaXMucGFzc2VzLmdldCh2YWx1ZSk7XG4gICAgICBpZiAob3JpZ2luYWwpIHJldHVybiBvcmlnaW5hbDtcblxuICAgICAgY29uc3QgcHJvdG8gPSBPYmplY3QuZ2V0UHJvdG90eXBlT2YodmFsdWUpO1xuICAgICAgc3dpdGNoIChwcm90bykge1xuICAgICAgICBjYXNlIEFycmF5LnByb3RvdHlwZToge1xuICAgICAgICAgIGlmICh0aGlzLmtub3duLmhhcyh2YWx1ZSkpIHJldHVybiB2YWx1ZTtcbiAgICAgICAgICBjb25zdCBhcnJheTogYW55W10gPSAodmFsdWUgYXMgYW55W10pLm1hcCh0aGlzLmFkbWl0LCB0aGlzKTtcbiAgICAgICAgICAvLyBBcnJheXMgYXJlIGxvb2tlZCB1cCBpbiB0aGUgVHJpZSB1c2luZyB0aGVpciByZWN1cnNpdmVseVxuICAgICAgICAgIC8vIGNhbm9uaWNhbGl6ZWQgZWxlbWVudHMsIGFuZCB0aGUga25vd24gdmVyc2lvbiBvZiB0aGUgYXJyYXkgaXNcbiAgICAgICAgICAvLyBwcmVzZXJ2ZWQgYXMgbm9kZS5hcnJheS5cbiAgICAgICAgICBjb25zdCBub2RlID0gdGhpcy5wb29sLmxvb2t1cEFycmF5KGFycmF5KTtcbiAgICAgICAgICBpZiAoIW5vZGUuYXJyYXkpIHtcbiAgICAgICAgICAgIHRoaXMua25vd24uYWRkKChub2RlLmFycmF5ID0gYXJyYXkpKTtcbiAgICAgICAgICAgIC8vIFNpbmNlIGNhbm9uaWNhbCBhcnJheXMgbWF5IGJlIHNoYXJlZCB3aWRlbHkgYmV0d2VlblxuICAgICAgICAgICAgLy8gdW5yZWxhdGVkIGNvbnN1bWVycywgaXQncyBpbXBvcnRhbnQgdG8gcmVnYXJkIHRoZW0gYXNcbiAgICAgICAgICAgIC8vIGltbXV0YWJsZSwgZXZlbiBpZiB0aGV5IGFyZSBub3QgZnJvemVuIGluIHByb2R1Y3Rpb24uXG4gICAgICAgICAgICBpZiAoX19ERVZfXykge1xuICAgICAgICAgICAgICBPYmplY3QuZnJlZXplKGFycmF5KTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICB9XG4gICAgICAgICAgcmV0dXJuIG5vZGUuYXJyYXk7XG4gICAgICAgIH1cblxuICAgICAgICBjYXNlIG51bGw6XG4gICAgICAgIGNhc2UgT2JqZWN0LnByb3RvdHlwZToge1xuICAgICAgICAgIGlmICh0aGlzLmtub3duLmhhcyh2YWx1ZSkpIHJldHVybiB2YWx1ZTtcbiAgICAgICAgICBjb25zdCBwcm90byA9IE9iamVjdC5nZXRQcm90b3R5cGVPZih2YWx1ZSk7XG4gICAgICAgICAgY29uc3QgYXJyYXkgPSBbcHJvdG9dO1xuICAgICAgICAgIGNvbnN0IGtleXMgPSB0aGlzLnNvcnRlZEtleXModmFsdWUpO1xuICAgICAgICAgIGFycmF5LnB1c2goa2V5cy5qc29uKTtcbiAgICAgICAgICBjb25zdCBmaXJzdFZhbHVlSW5kZXggPSBhcnJheS5sZW5ndGg7XG4gICAgICAgICAga2V5cy5zb3J0ZWQuZm9yRWFjaCgoa2V5KSA9PiB7XG4gICAgICAgICAgICBhcnJheS5wdXNoKHRoaXMuYWRtaXQoKHZhbHVlIGFzIGFueSlba2V5XSkpO1xuICAgICAgICAgIH0pO1xuICAgICAgICAgIC8vIE9iamVjdHMgYXJlIGxvb2tlZCB1cCBpbiB0aGUgVHJpZSBieSB0aGVpciBwcm90b3R5cGUgKHdoaWNoXG4gICAgICAgICAgLy8gaXMgKm5vdCogcmVjdXJzaXZlbHkgY2Fub25pY2FsaXplZCksIGZvbGxvd2VkIGJ5IGEgSlNPTlxuICAgICAgICAgIC8vIHJlcHJlc2VudGF0aW9uIG9mIHRoZWlyIChzb3J0ZWQpIGtleXMsIGZvbGxvd2VkIGJ5IHRoZVxuICAgICAgICAgIC8vIHNlcXVlbmNlIG9mIHJlY3Vyc2l2ZWx5IGNhbm9uaWNhbGl6ZWQgdmFsdWVzIGNvcnJlc3BvbmRpbmcgdG9cbiAgICAgICAgICAvLyB0aG9zZSBrZXlzLiBUbyBrZWVwIHRoZSBmaW5hbCByZXN1bHRzIHVuYW1iaWd1b3VzIHdpdGggb3RoZXJcbiAgICAgICAgICAvLyBzZXF1ZW5jZXMgKHN1Y2ggYXMgYXJyYXlzIHRoYXQganVzdCBoYXBwZW4gdG8gY29udGFpbiBbcHJvdG8sXG4gICAgICAgICAgLy8ga2V5cy5qc29uLCB2YWx1ZTEsIHZhbHVlMiwgLi4uXSksIHRoZSBrbm93biB2ZXJzaW9uIG9mIHRoZVxuICAgICAgICAgIC8vIG9iamVjdCBpcyBzdG9yZWQgYXMgbm9kZS5vYmplY3QuXG4gICAgICAgICAgY29uc3Qgbm9kZSA9IHRoaXMucG9vbC5sb29rdXBBcnJheShhcnJheSk7XG4gICAgICAgICAgaWYgKCFub2RlLm9iamVjdCkge1xuICAgICAgICAgICAgY29uc3Qgb2JqID0gKG5vZGUub2JqZWN0ID0gT2JqZWN0LmNyZWF0ZShwcm90bykpO1xuICAgICAgICAgICAgdGhpcy5rbm93bi5hZGQob2JqKTtcbiAgICAgICAgICAgIGtleXMuc29ydGVkLmZvckVhY2goKGtleSwgaSkgPT4ge1xuICAgICAgICAgICAgICBvYmpba2V5XSA9IGFycmF5W2ZpcnN0VmFsdWVJbmRleCArIGldO1xuICAgICAgICAgICAgfSk7XG4gICAgICAgICAgICAvLyBTaW5jZSBjYW5vbmljYWwgb2JqZWN0cyBtYXkgYmUgc2hhcmVkIHdpZGVseSBiZXR3ZWVuXG4gICAgICAgICAgICAvLyB1bnJlbGF0ZWQgY29uc3VtZXJzLCBpdCdzIGltcG9ydGFudCB0byByZWdhcmQgdGhlbSBhc1xuICAgICAgICAgICAgLy8gaW1tdXRhYmxlLCBldmVuIGlmIHRoZXkgYXJlIG5vdCBmcm96ZW4gaW4gcHJvZHVjdGlvbi5cbiAgICAgICAgICAgIGlmIChfX0RFVl9fKSB7XG4gICAgICAgICAgICAgIE9iamVjdC5mcmVlemUob2JqKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICB9XG4gICAgICAgICAgcmV0dXJuIG5vZGUub2JqZWN0O1xuICAgICAgICB9XG4gICAgICB9XG4gICAgfVxuICAgIHJldHVybiB2YWx1ZTtcbiAgfVxuXG4gIC8vIEl0J3Mgd29ydGh3aGlsZSB0byBjYWNoZSB0aGUgc29ydGluZyBvZiBhcnJheXMgb2Ygc3RyaW5ncywgc2luY2UgdGhlXG4gIC8vIHNhbWUgaW5pdGlhbCB1bnNvcnRlZCBhcnJheXMgdGVuZCB0byBiZSBlbmNvdW50ZXJlZCBtYW55IHRpbWVzLlxuICAvLyBGb3J0dW5hdGVseSwgd2UgY2FuIHJldXNlIHRoZSBUcmllIG1hY2hpbmVyeSB0byBsb29rIHVwIHRoZSBzb3J0ZWRcbiAgLy8gYXJyYXlzIGluIGxpbmVhciB0aW1lICh3aGljaCBpcyBmYXN0ZXIgdGhhbiBzb3J0aW5nIGxhcmdlIGFycmF5cykuXG4gIHByaXZhdGUgc29ydGVkS2V5cyhvYmo6IG9iamVjdCkge1xuICAgIGNvbnN0IGtleXMgPSBPYmplY3Qua2V5cyhvYmopO1xuICAgIGNvbnN0IG5vZGUgPSB0aGlzLnBvb2wubG9va3VwQXJyYXkoa2V5cyk7XG4gICAgaWYgKCFub2RlLmtleXMpIHtcbiAgICAgIGtleXMuc29ydCgpO1xuICAgICAgY29uc3QganNvbiA9IEpTT04uc3RyaW5naWZ5KGtleXMpO1xuICAgICAgaWYgKCEobm9kZS5rZXlzID0gdGhpcy5rZXlzQnlKU09OLmdldChqc29uKSkpIHtcbiAgICAgICAgdGhpcy5rZXlzQnlKU09OLnNldChqc29uLCAobm9kZS5rZXlzID0geyBzb3J0ZWQ6IGtleXMsIGpzb24gfSkpO1xuICAgICAgfVxuICAgIH1cbiAgICByZXR1cm4gbm9kZS5rZXlzO1xuICB9XG4gIC8vIEFycmF5cyB0aGF0IGNvbnRhaW4gdGhlIHNhbWUgZWxlbWVudHMgaW4gYSBkaWZmZXJlbnQgb3JkZXIgY2FuIHNoYXJlXG4gIC8vIHRoZSBzYW1lIFNvcnRlZEtleXNJbmZvIG9iamVjdCwgdG8gc2F2ZSBtZW1vcnkuXG4gIHByaXZhdGUga2V5c0J5SlNPTiA9IG5ldyBNYXA8c3RyaW5nLCBTb3J0ZWRLZXlzSW5mbz4oKTtcblxuICAvLyBUaGlzIGhhcyB0byBjb21lIGxhc3QgYmVjYXVzZSBpdCBkZXBlbmRzIG9uIGtleXNCeUpTT04uXG4gIHB1YmxpYyByZWFkb25seSBlbXB0eSA9IHRoaXMuYWRtaXQoe30pO1xufVxuXG50eXBlIFNvcnRlZEtleXNJbmZvID0ge1xuICBzb3J0ZWQ6IHN0cmluZ1tdO1xuICBqc29uOiBzdHJpbmc7XG59O1xuIl0sInhfZ29vZ2xlX2lnbm9yZUxpc3QiOlswXX0=