UNPKG

ember-legacy-class-transform

Version:
405 lines (326 loc) 43.1 kB
function _defaults(obj, defaults) { var keys = Object.getOwnPropertyNames(defaults); for (var i = 0; i < keys.length; i++) { var key = keys[i]; var value = Object.getOwnPropertyDescriptor(defaults, key); if (value && value.configurable && obj[key] === undefined) { Object.defineProperty(obj, key, value); } } return obj; } function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } } function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; } function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : _defaults(subClass, superClass); } import { Meta, PropertyReference } from '@glimmer/object-reference'; import { dict, assign, initializeGuid } from '@glimmer/util'; import { extend as extendClass, toMixin, relinkSubclasses, wrapMethod } from './mixin'; var isArray = Array.isArray; import { ROOT } from './utils'; export var EMPTY_CACHE = function EMPTY_CACHE() {}; var CLASS_META = "df8be4c8-4e89-44e2-a8f9-550c8dacdca7"; export function turbocharge(obj) { // function Dummy() {} // Dummy.prototype = obj; return obj; } var SealedMeta = function (_Meta) { _inherits(SealedMeta, _Meta); function SealedMeta() { _classCallCheck(this, SealedMeta); return _possibleConstructorReturn(this, _Meta.apply(this, arguments)); } SealedMeta.prototype.addReferenceTypeFor = function addReferenceTypeFor() { throw new Error("Cannot modify reference types on a sealed meta"); }; return SealedMeta; }(Meta); export var ClassMeta = function () { function ClassMeta() { _classCallCheck(this, ClassMeta); this.referenceTypes = dict(); this.propertyMetadata = dict(); this.concatenatedProperties = dict(); this.hasConcatenatedProperties = false; this.mergedProperties = dict(); this.hasMergedProperties = false; this.mixins = []; this.appliedMixins = []; this.staticMixins = []; this.subclasses = []; this.slots = []; this.InstanceMetaConstructor = null; } ClassMeta.fromParent = function fromParent(parent) { var meta = new this(); meta.reset(parent); return meta; }; ClassMeta.for = function _for(object) { if (CLASS_META in object) return object[CLASS_META];else if (object.constructor) return object.constructor[CLASS_META] || null;else return null; }; ClassMeta.prototype.init = function init(object, attrs) { if (typeof attrs !== 'object' || attrs === null) return; if (this.hasConcatenatedProperties) { var concatProps = this.concatenatedProperties; for (var prop in concatProps) { if (prop in attrs) { var concat = concatProps[prop].slice(); object[prop] = concat.concat(attrs[prop]); } } } if (this.hasMergedProperties) { var mergedProps = this.mergedProperties; for (var _prop in mergedProps) { if (_prop in attrs) { var merged = assign({}, mergedProps[_prop]); object[_prop] = assign(merged, attrs[_prop]); } } } }; ClassMeta.prototype.addStaticMixin = function addStaticMixin(mixin) { this.staticMixins.push(mixin); }; ClassMeta.prototype.addMixin = function addMixin(mixin) { this.mixins.push(mixin); }; ClassMeta.prototype.getStaticMixins = function getStaticMixins() { return this.staticMixins; }; ClassMeta.prototype.getMixins = function getMixins() { return this.mixins; }; ClassMeta.prototype.addAppliedMixin = function addAppliedMixin(mixin) { this.appliedMixins.push(mixin); }; ClassMeta.prototype.hasAppliedMixin = function hasAppliedMixin(mixin) { return this.appliedMixins.indexOf(mixin) !== -1; }; ClassMeta.prototype.getAppliedMixins = function getAppliedMixins() { return this.appliedMixins; }; ClassMeta.prototype.hasStaticMixin = function hasStaticMixin(mixin) { return this.staticMixins.indexOf(mixin) !== -1; }; ClassMeta.applyAllMixins = function applyAllMixins(Subclass, Parent) { Subclass[CLASS_META].getMixins().forEach(function (m) { return m.extendPrototypeOnto(Subclass, Parent); }); Subclass[CLASS_META].getStaticMixins().forEach(function (m) { return m.extendStatic(Subclass); }); Subclass[CLASS_META].seal(); }; ClassMeta.prototype.addSubclass = function addSubclass(constructor) { this.subclasses.push(constructor); }; ClassMeta.prototype.getSubclasses = function getSubclasses() { return this.subclasses; }; ClassMeta.prototype.addPropertyMetadata = function addPropertyMetadata(property, value) { this.propertyMetadata[property] = value; }; ClassMeta.prototype.metadataForProperty = function metadataForProperty(property) { return this.propertyMetadata[property]; }; ClassMeta.prototype.addReferenceTypeFor = function addReferenceTypeFor(property, type) { this.referenceTypes[property] = type; }; ClassMeta.prototype.addSlotFor = function addSlotFor(property) { this.slots.push(property); }; ClassMeta.prototype.hasConcatenatedProperty = function hasConcatenatedProperty(property) { if (!this.hasConcatenatedProperties) return false; return property in this.concatenatedProperties; }; ClassMeta.prototype.getConcatenatedProperty = function getConcatenatedProperty(property) { return this.concatenatedProperties[property]; }; ClassMeta.prototype.getConcatenatedProperties = function getConcatenatedProperties() { return Object.keys(this.concatenatedProperties); }; ClassMeta.prototype.addConcatenatedProperty = function addConcatenatedProperty(property, value) { this.hasConcatenatedProperties = true; if (property in this.concatenatedProperties) { var val = this.concatenatedProperties[property].concat(value); this.concatenatedProperties[property] = val; } else { this.concatenatedProperties[property] = value; } }; ClassMeta.prototype.hasMergedProperty = function hasMergedProperty(property) { if (!this.hasMergedProperties) return false; return property in this.mergedProperties; }; ClassMeta.prototype.getMergedProperty = function getMergedProperty(property) { return this.mergedProperties[property]; }; ClassMeta.prototype.getMergedProperties = function getMergedProperties() { return Object.keys(this.mergedProperties); }; ClassMeta.prototype.addMergedProperty = function addMergedProperty(property, value) { this.hasMergedProperties = true; if (isArray(value)) { throw new Error('You passed in `' + JSON.stringify(value) + '` as the value for `foo` but `foo` cannot be an Array'); } if (property in this.mergedProperties && this.mergedProperties[property] && value) { this.mergedProperties[property] = mergeMergedProperties(value, this.mergedProperties[property]); } else { value = value === null ? value : value || {}; this.mergedProperties[property] = value; } }; ClassMeta.prototype.getReferenceTypes = function getReferenceTypes() { return this.referenceTypes; }; ClassMeta.prototype.getPropertyMetadata = function getPropertyMetadata() { return this.propertyMetadata; }; ClassMeta.prototype.reset = function reset(parent) { this.referenceTypes = dict(); this.propertyMetadata = dict(); this.concatenatedProperties = dict(); this.mergedProperties = dict(); if (parent) { this.hasConcatenatedProperties = parent.hasConcatenatedProperties; for (var prop in parent.concatenatedProperties) { this.concatenatedProperties[prop] = parent.concatenatedProperties[prop].slice(); } this.hasMergedProperties = parent.hasMergedProperties; for (var _prop2 in parent.mergedProperties) { this.mergedProperties[_prop2] = assign({}, parent.mergedProperties[_prop2]); } assign(this.referenceTypes, parent.referenceTypes); assign(this.propertyMetadata, parent.propertyMetadata); } }; ClassMeta.prototype.reseal = function reseal(obj) { var meta = Meta.for(obj); var fresh = new this.InstanceMetaConstructor(obj, {}); var referenceTypes = meta.getReferenceTypes(); var slots = meta.getSlots(); turbocharge(assign(referenceTypes, this.referenceTypes)); turbocharge(assign(slots, fresh.getSlots())); }; ClassMeta.prototype.seal = function seal() { var referenceTypes = turbocharge(assign({}, this.referenceTypes)); turbocharge(this.concatenatedProperties); turbocharge(this.mergedProperties); if (!this.hasMergedProperties && !this.hasConcatenatedProperties) { this.init = function () {}; } var slots = this.slots; var Slots = function Slots() { var _this2 = this; _classCallCheck(this, Slots); slots.forEach(function (name) { _this2[name] = EMPTY_CACHE; }); }; this.InstanceMetaConstructor = function (_SealedMeta) { _inherits(_class, _SealedMeta); function _class() { _classCallCheck(this, _class); var _this3 = _possibleConstructorReturn(this, _SealedMeta.apply(this, arguments)); _this3.slots = new Slots(); _this3.referenceTypes = referenceTypes; return _this3; } _class.prototype.getReferenceTypes = function getReferenceTypes() { return this.referenceTypes; }; _class.prototype.referenceTypeFor = function referenceTypeFor(property) { return this.referenceTypes[property] || PropertyReference; }; _class.prototype.getSlots = function getSlots() { return this.slots; }; return _class; }(SealedMeta); turbocharge(this); }; return ClassMeta; }(); function mergeMergedProperties(attrs, parent) { var merged = assign({}, parent); for (var prop in attrs) { if (prop in parent && typeof parent[prop] === 'function' && typeof attrs[prop] === 'function') { var wrapped = wrapMethod(parent, prop, attrs[prop]); merged[prop] = wrapped; } else { merged[prop] = attrs[prop]; } } return merged; } export var InstanceMeta = function (_ClassMeta) { _inherits(InstanceMeta, _ClassMeta); function InstanceMeta() { _classCallCheck(this, InstanceMeta); var _this4 = _possibleConstructorReturn(this, _ClassMeta.apply(this, arguments)); _this4["df8be4c8-4e89-44e2-a8f9-550c8dacdca7"] = ClassMeta.fromParent(null); return _this4; } InstanceMeta.fromParent = function fromParent(parent) { return _ClassMeta.fromParent.call(this, parent); }; InstanceMeta.prototype.reset = function reset(parent) { _ClassMeta.prototype.reset.call(this, parent); if (parent) this[CLASS_META].reset(parent[CLASS_META]); }; InstanceMeta.prototype.seal = function seal() { _ClassMeta.prototype.seal.call(this); this[CLASS_META].seal(); }; return InstanceMeta; }(ClassMeta); var GlimmerObject = function () { function GlimmerObject(attrs) { _classCallCheck(this, GlimmerObject); this._super = ROOT; this._meta = null; if (attrs) assign(this, attrs); this.constructor[CLASS_META].init(this, attrs || null); this._super = ROOT; initializeGuid(this); this.init(); } GlimmerObject.extend = function extend() { for (var _len = arguments.length, extensions = Array(_len), _key = 0; _key < _len; _key++) { extensions[_key] = arguments[_key]; } return extendClass.apply(undefined, [this].concat(extensions)); }; GlimmerObject.create = function create(attrs) { return new this(attrs); }; GlimmerObject.reopen = function reopen(extensions) { toMixin(extensions).extendPrototype(this); this[CLASS_META].seal(); relinkSubclasses(this); }; GlimmerObject.reopenClass = function reopenClass(extensions) { toMixin(extensions).extendStatic(this); this[CLASS_META].seal(); }; GlimmerObject.metaForProperty = function metaForProperty(property) { var value = this[CLASS_META].metadataForProperty(property); if (!value) throw new Error('metaForProperty() could not find a computed property with key \'' + property + '\'.'); return value; }; GlimmerObject.eachComputedProperty = function eachComputedProperty(callback) { var metadata = this[CLASS_META].getPropertyMetadata(); if (!metadata) return; for (var prop in metadata) { callback(prop, metadata[prop]); } }; GlimmerObject.prototype.init = function init() {}; GlimmerObject.prototype.get = function get(key) { return this[key]; }; GlimmerObject.prototype.set = function set(key, value) { this[key] = value; }; GlimmerObject.prototype.setProperties = function setProperties(attrs) { assign(this, attrs); }; GlimmerObject.prototype.destroy = function destroy() {}; return GlimmerObject; }(); export default GlimmerObject; GlimmerObject["df8be4c8-4e89-44e2-a8f9-550c8dacdca7"] = InstanceMeta.fromParent(null); GlimmerObject.isClass = true; //# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbImxpYi9vYmplY3QuanMiXSwibmFtZXMiOlsiTWV0YSIsIlByb3BlcnR5UmVmZXJlbmNlIiwiZGljdCIsImFzc2lnbiIsImluaXRpYWxpemVHdWlkIiwiZXh0ZW5kIiwiZXh0ZW5kQ2xhc3MiLCJ0b01peGluIiwicmVsaW5rU3ViY2xhc3NlcyIsIndyYXBNZXRob2QiLCJpc0FycmF5IiwiQXJyYXkiLCJST09UIiwiRU1QVFlfQ0FDSEUiLCJDTEFTU19NRVRBIiwidHVyYm9jaGFyZ2UiLCJvYmoiLCJTZWFsZWRNZXRhIiwiYWRkUmVmZXJlbmNlVHlwZUZvciIsIkVycm9yIiwiQ2xhc3NNZXRhIiwicmVmZXJlbmNlVHlwZXMiLCJwcm9wZXJ0eU1ldGFkYXRhIiwiY29uY2F0ZW5hdGVkUHJvcGVydGllcyIsImhhc0NvbmNhdGVuYXRlZFByb3BlcnRpZXMiLCJtZXJnZWRQcm9wZXJ0aWVzIiwiaGFzTWVyZ2VkUHJvcGVydGllcyIsIm1peGlucyIsImFwcGxpZWRNaXhpbnMiLCJzdGF0aWNNaXhpbnMiLCJzdWJjbGFzc2VzIiwic2xvdHMiLCJJbnN0YW5jZU1ldGFDb25zdHJ1Y3RvciIsImZyb21QYXJlbnQiLCJwYXJlbnQiLCJtZXRhIiwicmVzZXQiLCJmb3IiLCJvYmplY3QiLCJjb25zdHJ1Y3RvciIsImluaXQiLCJhdHRycyIsImNvbmNhdFByb3BzIiwicHJvcCIsImNvbmNhdCIsInNsaWNlIiwibWVyZ2VkUHJvcHMiLCJtZXJnZWQiLCJhZGRTdGF0aWNNaXhpbiIsIm1peGluIiwicHVzaCIsImFkZE1peGluIiwiZ2V0U3RhdGljTWl4aW5zIiwiZ2V0TWl4aW5zIiwiYWRkQXBwbGllZE1peGluIiwiaGFzQXBwbGllZE1peGluIiwiaW5kZXhPZiIsImdldEFwcGxpZWRNaXhpbnMiLCJoYXNTdGF0aWNNaXhpbiIsImFwcGx5QWxsTWl4aW5zIiwiU3ViY2xhc3MiLCJQYXJlbnQiLCJmb3JFYWNoIiwibSIsImV4dGVuZFByb3RvdHlwZU9udG8iLCJleHRlbmRTdGF0aWMiLCJzZWFsIiwiYWRkU3ViY2xhc3MiLCJnZXRTdWJjbGFzc2VzIiwiYWRkUHJvcGVydHlNZXRhZGF0YSIsInByb3BlcnR5IiwidmFsdWUiLCJtZXRhZGF0YUZvclByb3BlcnR5IiwidHlwZSIsImFkZFNsb3RGb3IiLCJoYXNDb25jYXRlbmF0ZWRQcm9wZXJ0eSIsImdldENvbmNhdGVuYXRlZFByb3BlcnR5IiwiZ2V0Q29uY2F0ZW5hdGVkUHJvcGVydGllcyIsIk9iamVjdCIsImtleXMiLCJhZGRDb25jYXRlbmF0ZWRQcm9wZXJ0eSIsInZhbCIsImhhc01lcmdlZFByb3BlcnR5IiwiZ2V0TWVyZ2VkUHJvcGVydHkiLCJnZXRNZXJnZWRQcm9wZXJ0aWVzIiwiYWRkTWVyZ2VkUHJvcGVydHkiLCJKU09OIiwic3RyaW5naWZ5IiwibWVyZ2VNZXJnZWRQcm9wZXJ0aWVzIiwiZ2V0UmVmZXJlbmNlVHlwZXMiLCJnZXRQcm9wZXJ0eU1ldGFkYXRhIiwicmVzZWFsIiwiZnJlc2giLCJnZXRTbG90cyIsIlNsb3RzIiwibmFtZSIsImFyZ3VtZW50cyIsInJlZmVyZW5jZVR5cGVGb3IiLCJ3cmFwcGVkIiwiSW5zdGFuY2VNZXRhIiwiR2xpbW1lck9iamVjdCIsIl9zdXBlciIsIl9tZXRhIiwiZXh0ZW5zaW9ucyIsImNyZWF0ZSIsInJlb3BlbiIsImV4dGVuZFByb3RvdHlwZSIsInJlb3BlbkNsYXNzIiwibWV0YUZvclByb3BlcnR5IiwiZWFjaENvbXB1dGVkUHJvcGVydHkiLCJjYWxsYmFjayIsIm1ldGFkYXRhIiwiZ2V0Iiwia2V5Iiwic2V0Iiwic2V0UHJvcGVydGllcyIsImRlc3Ryb3kiLCJpc0NsYXNzIl0sIm1hcHBpbmdzIjoiOzs7Ozs7OztBQUFBLFNBQVNBLElBQVQsRUFBZUMsaUJBQWYsUUFBd0MsMkJBQXhDO0FBQ0EsU0FBU0MsSUFBVCxFQUFlQyxNQUFmLEVBQXVCQyxjQUF2QixRQUE2QyxlQUE3QztBQUNBLFNBQVNDLFVBQVVDLFdBQW5CLEVBQWdDQyxPQUFoQyxFQUF5Q0MsZ0JBQXpDLEVBQTJEQyxVQUEzRCxRQUE2RSxTQUE3RTtJQUNRQyxPLEdBQVlDLEssQ0FBWkQsTzs7QUFDUixTQUFTRSxJQUFULFFBQXFCLFNBQXJCO0FBQ0EsT0FBTyxJQUFNQyxjQUFjLFNBQVNBLFdBQVQsR0FBdUIsQ0FBRSxDQUE3QztBQUNQLElBQU1DLGFBQWEsc0NBQW5CO0FBQ0EsT0FBTyxTQUFTQyxXQUFULENBQXFCQyxHQUFyQixFQUEwQjtBQUM3QjtBQUNBO0FBQ0EsV0FBT0EsR0FBUDtBQUNIOztJQUNLQyxVOzs7Ozs7Ozs7eUJBQ0ZDLG1CLGtDQUE4QjtBQUMxQixjQUFNLElBQUlDLEtBQUosQ0FBVSxnREFBVixDQUFOO0FBQ0gsSzs7O0VBSG9CbkIsSTs7QUFLekIsV0FBYW9CLFNBQWI7QUFDSSx5QkFBYztBQUFBOztBQUNWLGFBQUtDLGNBQUwsR0FBc0JuQixNQUF0QjtBQUNBLGFBQUtvQixnQkFBTCxHQUF3QnBCLE1BQXhCO0FBQ0EsYUFBS3FCLHNCQUFMLEdBQThCckIsTUFBOUI7QUFDQSxhQUFLc0IseUJBQUwsR0FBaUMsS0FBakM7QUFDQSxhQUFLQyxnQkFBTCxHQUF3QnZCLE1BQXhCO0FBQ0EsYUFBS3dCLG1CQUFMLEdBQTJCLEtBQTNCO0FBQ0EsYUFBS0MsTUFBTCxHQUFjLEVBQWQ7QUFDQSxhQUFLQyxhQUFMLEdBQXFCLEVBQXJCO0FBQ0EsYUFBS0MsWUFBTCxHQUFvQixFQUFwQjtBQUNBLGFBQUtDLFVBQUwsR0FBa0IsRUFBbEI7QUFDQSxhQUFLQyxLQUFMLEdBQWEsRUFBYjtBQUNBLGFBQUtDLHVCQUFMLEdBQStCLElBQS9CO0FBQ0g7O0FBZEwsY0FlV0MsVUFmWCx1QkFlc0JDLE1BZnRCLEVBZThCO0FBQ3RCLFlBQUlDLE9BQU8sSUFBSSxJQUFKLEVBQVg7QUFDQUEsYUFBS0MsS0FBTCxDQUFXRixNQUFYO0FBQ0EsZUFBT0MsSUFBUDtBQUNILEtBbkJMOztBQUFBLGNBb0JXRSxHQXBCWCxpQkFvQmVDLE1BcEJmLEVBb0J1QjtBQUNmLFlBQUl4QixjQUFjd0IsTUFBbEIsRUFBMEIsT0FBT0EsT0FBT3hCLFVBQVAsQ0FBUCxDQUExQixLQUF5RCxJQUFJd0IsT0FBT0MsV0FBWCxFQUF3QixPQUFPRCxPQUFPQyxXQUFQLENBQW1CekIsVUFBbkIsS0FBa0MsSUFBekMsQ0FBeEIsS0FBMkUsT0FBTyxJQUFQO0FBQ3ZJLEtBdEJMOztBQUFBLHdCQXVCSTBCLElBdkJKLGlCQXVCU0YsTUF2QlQsRUF1QmlCRyxLQXZCakIsRUF1QndCO0FBQ2hCLFlBQUksT0FBT0EsS0FBUCxLQUFpQixRQUFqQixJQUE2QkEsVUFBVSxJQUEzQyxFQUFpRDtBQUNqRCxZQUFJLEtBQUtqQix5QkFBVCxFQUFvQztBQUNoQyxnQkFBSWtCLGNBQWMsS0FBS25CLHNCQUF2QjtBQUNBLGlCQUFLLElBQUlvQixJQUFULElBQWlCRCxXQUFqQixFQUE4QjtBQUMxQixvQkFBSUMsUUFBUUYsS0FBWixFQUFtQjtBQUNmLHdCQUFJRyxTQUFTRixZQUFZQyxJQUFaLEVBQWtCRSxLQUFsQixFQUFiO0FBQ0FQLDJCQUFPSyxJQUFQLElBQWVDLE9BQU9BLE1BQVAsQ0FBY0gsTUFBTUUsSUFBTixDQUFkLENBQWY7QUFDSDtBQUNKO0FBQ0o7QUFDRCxZQUFJLEtBQUtqQixtQkFBVCxFQUE4QjtBQUMxQixnQkFBSW9CLGNBQWMsS0FBS3JCLGdCQUF2QjtBQUNBLGlCQUFLLElBQUlrQixLQUFULElBQWlCRyxXQUFqQixFQUE4QjtBQUMxQixvQkFBSUgsU0FBUUYsS0FBWixFQUFtQjtBQUNmLHdCQUFJTSxTQUFTNUMsT0FBTyxFQUFQLEVBQVcyQyxZQUFZSCxLQUFaLENBQVgsQ0FBYjtBQUNBTCwyQkFBT0ssS0FBUCxJQUFleEMsT0FBTzRDLE1BQVAsRUFBZU4sTUFBTUUsS0FBTixDQUFmLENBQWY7QUFDSDtBQUNKO0FBQ0o7QUFDSixLQTNDTDs7QUFBQSx3QkE0Q0lLLGNBNUNKLDJCQTRDbUJDLEtBNUNuQixFQTRDMEI7QUFDbEIsYUFBS3BCLFlBQUwsQ0FBa0JxQixJQUFsQixDQUF1QkQsS0FBdkI7QUFDSCxLQTlDTDs7QUFBQSx3QkErQ0lFLFFBL0NKLHFCQStDYUYsS0EvQ2IsRUErQ29CO0FBQ1osYUFBS3RCLE1BQUwsQ0FBWXVCLElBQVosQ0FBaUJELEtBQWpCO0FBQ0gsS0FqREw7O0FBQUEsd0JBa0RJRyxlQWxESiw4QkFrRHNCO0FBQ2QsZUFBTyxLQUFLdkIsWUFBWjtBQUNILEtBcERMOztBQUFBLHdCQXFESXdCLFNBckRKLHdCQXFEZ0I7QUFDUixlQUFPLEtBQUsxQixNQUFaO0FBQ0gsS0F2REw7O0FBQUEsd0JBd0RJMkIsZUF4REosNEJBd0RvQkwsS0F4RHBCLEVBd0QyQjtBQUNuQixhQUFLckIsYUFBTCxDQUFtQnNCLElBQW5CLENBQXdCRCxLQUF4QjtBQUNILEtBMURMOztBQUFBLHdCQTJESU0sZUEzREosNEJBMkRvQk4sS0EzRHBCLEVBMkQyQjtBQUNuQixlQUFPLEtBQUtyQixhQUFMLENBQW1CNEIsT0FBbkIsQ0FBMkJQLEtBQTNCLE1BQXNDLENBQUMsQ0FBOUM7QUFDSCxLQTdETDs7QUFBQSx3QkE4RElRLGdCQTlESiwrQkE4RHVCO0FBQ2YsZUFBTyxLQUFLN0IsYUFBWjtBQUNILEtBaEVMOztBQUFBLHdCQWlFSThCLGNBakVKLDJCQWlFbUJULEtBakVuQixFQWlFMEI7QUFDbEIsZUFBTyxLQUFLcEIsWUFBTCxDQUFrQjJCLE9BQWxCLENBQTBCUCxLQUExQixNQUFxQyxDQUFDLENBQTdDO0FBQ0gsS0FuRUw7O0FBQUEsY0FvRVdVLGNBcEVYLDJCQW9FMEJDLFFBcEUxQixFQW9Fb0NDLE1BcEVwQyxFQW9FNEM7QUFDcENELGlCQUFTOUMsVUFBVCxFQUFxQnVDLFNBQXJCLEdBQWlDUyxPQUFqQyxDQUF5QztBQUFBLG1CQUFLQyxFQUFFQyxtQkFBRixDQUFzQkosUUFBdEIsRUFBZ0NDLE1BQWhDLENBQUw7QUFBQSxTQUF6QztBQUNBRCxpQkFBUzlDLFVBQVQsRUFBcUJzQyxlQUFyQixHQUF1Q1UsT0FBdkMsQ0FBK0M7QUFBQSxtQkFBS0MsRUFBRUUsWUFBRixDQUFlTCxRQUFmLENBQUw7QUFBQSxTQUEvQztBQUNBQSxpQkFBUzlDLFVBQVQsRUFBcUJvRCxJQUFyQjtBQUNILEtBeEVMOztBQUFBLHdCQXlFSUMsV0F6RUosd0JBeUVnQjVCLFdBekVoQixFQXlFNkI7QUFDckIsYUFBS1QsVUFBTCxDQUFnQm9CLElBQWhCLENBQXFCWCxXQUFyQjtBQUNILEtBM0VMOztBQUFBLHdCQTRFSTZCLGFBNUVKLDRCQTRFb0I7QUFDWixlQUFPLEtBQUt0QyxVQUFaO0FBQ0gsS0E5RUw7O0FBQUEsd0JBK0VJdUMsbUJBL0VKLGdDQStFd0JDLFFBL0V4QixFQStFa0NDLEtBL0VsQyxFQStFeUM7QUFDakMsYUFBS2pELGdCQUFMLENBQXNCZ0QsUUFBdEIsSUFBa0NDLEtBQWxDO0FBQ0gsS0FqRkw7O0FBQUEsd0JBa0ZJQyxtQkFsRkosZ0NBa0Z3QkYsUUFsRnhCLEVBa0ZrQztBQUMxQixlQUFPLEtBQUtoRCxnQkFBTCxDQUFzQmdELFFBQXRCLENBQVA7QUFDSCxLQXBGTDs7QUFBQSx3QkFxRklwRCxtQkFyRkosZ0NBcUZ3Qm9ELFFBckZ4QixFQXFGa0NHLElBckZsQyxFQXFGd0M7QUFDaEMsYUFBS3BELGNBQUwsQ0FBb0JpRCxRQUFwQixJQUFnQ0csSUFBaEM7QUFDSCxLQXZGTDs7QUFBQSx3QkF3RklDLFVBeEZKLHVCQXdGZUosUUF4RmYsRUF3RnlCO0FBQ2pCLGFBQUt2QyxLQUFMLENBQVdtQixJQUFYLENBQWdCb0IsUUFBaEI7QUFDSCxLQTFGTDs7QUFBQSx3QkEyRklLLHVCQTNGSixvQ0EyRjRCTCxRQTNGNUIsRUEyRnNDO0FBQzlCLFlBQUksQ0FBQyxLQUFLOUMseUJBQVYsRUFBcUMsT0FBTyxLQUFQO0FBQ3JDLGVBQU84QyxZQUFZLEtBQUsvQyxzQkFBeEI7QUFDSCxLQTlGTDs7QUFBQSx3QkErRklxRCx1QkEvRkosb0NBK0Y0Qk4sUUEvRjVCLEVBK0ZzQztBQUM5QixlQUFPLEtBQUsvQyxzQkFBTCxDQUE0QitDLFFBQTVCLENBQVA7QUFDSCxLQWpHTDs7QUFBQSx3QkFrR0lPLHlCQWxHSix3Q0FrR2dDO0FBQ3hCLGVBQU9DLE9BQU9DLElBQVAsQ0FBWSxLQUFLeEQsc0JBQWpCLENBQVA7QUFDSCxLQXBHTDs7QUFBQSx3QkFxR0l5RCx1QkFyR0osb0NBcUc0QlYsUUFyRzVCLEVBcUdzQ0MsS0FyR3RDLEVBcUc2QztBQUNyQyxhQUFLL0MseUJBQUwsR0FBaUMsSUFBakM7QUFDQSxZQUFJOEMsWUFBWSxLQUFLL0Msc0JBQXJCLEVBQTZDO0FBQ3pDLGdCQUFJMEQsTUFBTSxLQUFLMUQsc0JBQUwsQ0FBNEIrQyxRQUE1QixFQUFzQzFCLE1BQXRDLENBQTZDMkIsS0FBN0MsQ0FBVjtBQUNBLGlCQUFLaEQsc0JBQUwsQ0FBNEIrQyxRQUE1QixJQUF3Q1csR0FBeEM7QUFDSCxTQUhELE1BR087QUFDSCxpQkFBSzFELHNCQUFMLENBQTRCK0MsUUFBNUIsSUFBd0NDLEtBQXhDO0FBQ0g7QUFDSixLQTdHTDs7QUFBQSx3QkE4R0lXLGlCQTlHSiw4QkE4R3NCWixRQTlHdEIsRUE4R2dDO0FBQ3hCLFlBQUksQ0FBQyxLQUFLNUMsbUJBQVYsRUFBK0IsT0FBTyxLQUFQO0FBQy9CLGVBQU80QyxZQUFZLEtBQUs3QyxnQkFBeEI7QUFDSCxLQWpITDs7QUFBQSx3QkFrSEkwRCxpQkFsSEosOEJBa0hzQmIsUUFsSHRCLEVBa0hnQztBQUN4QixlQUFPLEtBQUs3QyxnQkFBTCxDQUFzQjZDLFFBQXRCLENBQVA7QUFDSCxLQXBITDs7QUFBQSx3QkFxSEljLG1CQXJISixrQ0FxSDBCO0FBQ2xCLGVBQU9OLE9BQU9DLElBQVAsQ0FBWSxLQUFLdEQsZ0JBQWpCLENBQVA7QUFDSCxLQXZITDs7QUFBQSx3QkF3SEk0RCxpQkF4SEosOEJBd0hzQmYsUUF4SHRCLEVBd0hnQ0MsS0F4SGhDLEVBd0h1QztBQUMvQixhQUFLN0MsbUJBQUwsR0FBMkIsSUFBM0I7QUFDQSxZQUFJaEIsUUFBUTZELEtBQVIsQ0FBSixFQUFvQjtBQUNoQixrQkFBTSxJQUFJcEQsS0FBSixxQkFBNkJtRSxLQUFLQyxTQUFMLENBQWVoQixLQUFmLENBQTdCLDJEQUFOO0FBQ0g7QUFDRCxZQUFJRCxZQUFZLEtBQUs3QyxnQkFBakIsSUFBcUMsS0FBS0EsZ0JBQUwsQ0FBc0I2QyxRQUF0QixDQUFyQyxJQUF3RUMsS0FBNUUsRUFBbUY7QUFDL0UsaUJBQUs5QyxnQkFBTCxDQUFzQjZDLFFBQXRCLElBQWtDa0Isc0JBQXNCakIsS0FBdEIsRUFBNkIsS0FBSzlDLGdCQUFMLENBQXNCNkMsUUFBdEIsQ0FBN0IsQ0FBbEM7QUFDSCxTQUZELE1BRU87QUFDSEMsb0JBQVFBLFVBQVUsSUFBVixHQUFpQkEsS0FBakIsR0FBeUJBLFNBQVMsRUFBMUM7QUFDQSxpQkFBSzlDLGdCQUFMLENBQXNCNkMsUUFBdEIsSUFBa0NDLEtBQWxDO0FBQ0g7QUFDSixLQW5JTDs7QUFBQSx3QkFvSUlrQixpQkFwSUosZ0NBb0l3QjtBQUNoQixlQUFPLEtBQUtwRSxjQUFaO0FBQ0gsS0F0SUw7O0FBQUEsd0JBdUlJcUUsbUJBdklKLGtDQXVJMEI7QUFDbEIsZUFBTyxLQUFLcEUsZ0JBQVo7QUFDSCxLQXpJTDs7QUFBQSx3QkEwSUljLEtBMUlKLGtCQTBJVUYsTUExSVYsRUEwSWtCO0FBQ1YsYUFBS2IsY0FBTCxHQUFzQm5CLE1BQXRCO0FBQ0EsYUFBS29CLGdCQUFMLEdBQXdCcEIsTUFBeEI7QUFDQSxhQUFLcUIsc0JBQUwsR0FBOEJyQixNQUE5QjtBQUNBLGFBQUt1QixnQkFBTCxHQUF3QnZCLE1BQXhCO0FBQ0EsWUFBSWdDLE1BQUosRUFBWTtBQUNSLGlCQUFLVix5QkFBTCxHQUFpQ1UsT0FBT1YseUJBQXhDO0FBQ0EsaUJBQUssSUFBSW1CLElBQVQsSUFBaUJULE9BQU9YLHNCQUF4QixFQUFnRDtBQUM1QyxxQkFBS0Esc0JBQUwsQ0FBNEJvQixJQUE1QixJQUFvQ1QsT0FBT1gsc0JBQVAsQ0FBOEJvQixJQUE5QixFQUFvQ0UsS0FBcEMsRUFBcEM7QUFDSDtBQUNELGlCQUFLbkIsbUJBQUwsR0FBMkJRLE9BQU9SLG1CQUFsQztBQUNBLGlCQUFLLElBQUlpQixNQUFULElBQWlCVCxPQUFPVCxnQkFBeEIsRUFBMEM7QUFDdEMscUJBQUtBLGdCQUFMLENBQXNCa0IsTUFBdEIsSUFBOEJ4QyxPQUFPLEVBQVAsRUFBVytCLE9BQU9ULGdCQUFQLENBQXdCa0IsTUFBeEIsQ0FBWCxDQUE5QjtBQUNIO0FBQ0R4QyxtQkFBTyxLQUFLa0IsY0FBWixFQUE0QmEsT0FBT2IsY0FBbkM7QUFDQWxCLG1CQUFPLEtBQUttQixnQkFBWixFQUE4QlksT0FBT1osZ0JBQXJDO0FBQ0g7QUFDSixLQTNKTDs7QUFBQSx3QkE0SklxRSxNQTVKSixtQkE0SlczRSxHQTVKWCxFQTRKZ0I7QUFDUixZQUFJbUIsT0FBT25DLEtBQUtxQyxHQUFMLENBQVNyQixHQUFULENBQVg7QUFDQSxZQUFJNEUsUUFBUSxJQUFJLEtBQUs1RCx1QkFBVCxDQUFpQ2hCLEdBQWpDLEVBQXNDLEVBQXRDLENBQVo7QUFDQSxZQUFJSyxpQkFBaUJjLEtBQUtzRCxpQkFBTCxFQUFyQjtBQUNBLFlBQUkxRCxRQUFRSSxLQUFLMEQsUUFBTCxFQUFaO0FBQ0E5RSxvQkFBWVosT0FBT2tCLGNBQVAsRUFBdUIsS0FBS0EsY0FBNUIsQ0FBWjtBQUNBTixvQkFBWVosT0FBTzRCLEtBQVAsRUFBYzZELE1BQU1DLFFBQU4sRUFBZCxDQUFaO0FBQ0gsS0FuS0w7O0FBQUEsd0JBb0tJM0IsSUFwS0osbUJBb0tXO0FBQ0gsWUFBSTdDLGlCQUFpQk4sWUFBWVosT0FBTyxFQUFQLEVBQVcsS0FBS2tCLGNBQWhCLENBQVosQ0FBckI7QUFDQU4sb0JBQVksS0FBS1Esc0JBQWpCO0FBQ0FSLG9CQUFZLEtBQUtVLGdCQUFqQjtBQUNBLFlBQUksQ0FBQyxLQUFLQyxtQkFBTixJQUE2QixDQUFDLEtBQUtGLHlCQUF2QyxFQUFrRTtBQUM5RCxpQkFBS2dCLElBQUwsR0FBWSxZQUFZLENBQUUsQ0FBMUI7QUFDSDtBQUNELFlBQUlULFFBQVEsS0FBS0EsS0FBakI7O0FBUEcsWUFRRytELEtBUkgsR0FTQyxpQkFBYztBQUFBOztBQUFBOztBQUNWL0Qsa0JBQU0rQixPQUFOLENBQWMsZ0JBQVE7QUFDbEIsdUJBQUtpQyxJQUFMLElBQWFsRixXQUFiO0FBQ0gsYUFGRDtBQUdILFNBYkY7O0FBZUgsYUFBS21CLHVCQUFMO0FBQUE7O0FBQ0ksOEJBQWM7QUFBQTs7QUFBQSw4REFDVix3QkFBU2dFLFNBQVQsQ0FEVTs7QUFFVix1QkFBS2pFLEtBQUwsR0FBYSxJQUFJK0QsS0FBSixFQUFiO0FBQ0EsdUJBQUt6RSxjQUFMLEdBQXNCQSxjQUF0QjtBQUhVO0FBSWI7O0FBTEwsNkJBTUlvRSxpQkFOSixnQ0FNd0I7QUFDaEIsdUJBQU8sS0FBS3BFLGNBQVo7QUFDSCxhQVJMOztBQUFBLDZCQVNJNEUsZ0JBVEosNkJBU3FCM0IsUUFUckIsRUFTK0I7QUFDdkIsdUJBQU8sS0FBS2pELGNBQUwsQ0FBb0JpRCxRQUFwQixLQUFpQ3JFLGlCQUF4QztBQUNILGFBWEw7O0FBQUEsNkJBWUk0RixRQVpKLHVCQVllO0FBQ1AsdUJBQU8sS0FBSzlELEtBQVo7QUFDSCxhQWRMOztBQUFBO0FBQUEsVUFBNkNkLFVBQTdDO0FBZ0JBRixvQkFBWSxJQUFaO0FBQ0gsS0FwTUw7O0FBQUE7QUFBQTtBQXNNQSxTQUFTeUUscUJBQVQsQ0FBK0IvQyxLQUEvQixFQUFzQ1AsTUFBdEMsRUFBOEM7QUFDMUMsUUFBSWEsU0FBUzVDLE9BQU8sRUFBUCxFQUFXK0IsTUFBWCxDQUFiO0FBQ0EsU0FBSyxJQUFJUyxJQUFULElBQWlCRixLQUFqQixFQUF3QjtBQUNwQixZQUFJRSxRQUFRVCxNQUFSLElBQWtCLE9BQU9BLE9BQU9TLElBQVAsQ0FBUCxLQUF3QixVQUExQyxJQUF3RCxPQUFPRixNQUFNRSxJQUFOLENBQVAsS0FBdUIsVUFBbkYsRUFBK0Y7QUFDM0YsZ0JBQUl1RCxVQUFVekYsV0FBV3lCLE1BQVgsRUFBbUJTLElBQW5CLEVBQXlCRixNQUFNRSxJQUFOLENBQXpCLENBQWQ7QUFDQUksbUJBQU9KLElBQVAsSUFBZXVELE9BQWY7QUFDSCxTQUhELE1BR087QUFDSG5ELG1CQUFPSixJQUFQLElBQWVGLE1BQU1FLElBQU4sQ0FBZjtBQUNIO0FBQ0o7QUFDRCxXQUFPSSxNQUFQO0FBQ0g7QUFDRCxXQUFhb0QsWUFBYjtBQUFBOztBQUNJLDRCQUFjO0FBQUE7O0FBQUEsc0RBQ1YsdUJBQVNILFNBQVQsQ0FEVTs7QUFFVixlQUFLLHNDQUFMLElBQStDNUUsVUFBVWEsVUFBVixDQUFxQixJQUFyQixDQUEvQztBQUZVO0FBR2I7O0FBSkwsaUJBS1dBLFVBTFgsdUJBS3NCQyxNQUx0QixFQUs4QjtBQUN0QixlQUFPLFdBQU1ELFVBQU4sWUFBaUJDLE1BQWpCLENBQVA7QUFDSCxLQVBMOztBQUFBLDJCQVFJRSxLQVJKLGtCQVFVRixNQVJWLEVBUWtCO0FBQ1YsNkJBQU1FLEtBQU4sWUFBWUYsTUFBWjtBQUNBLFlBQUlBLE1BQUosRUFBWSxLQUFLcEIsVUFBTCxFQUFpQnNCLEtBQWpCLENBQXVCRixPQUFPcEIsVUFBUCxDQUF2QjtBQUNmLEtBWEw7O0FBQUEsMkJBWUlvRCxJQVpKLG1CQVlXO0FBQ0gsNkJBQU1BLElBQU47QUFDQSxhQUFLcEQsVUFBTCxFQUFpQm9ELElBQWpCO0FBQ0gsS0FmTDs7QUFBQTtBQUFBLEVBQWtDOUMsU0FBbEM7O0lBaUJxQmdGLGE7QUFDakIsMkJBQVkzRCxLQUFaLEVBQW1CO0FBQUE7O0FBQ2YsYUFBSzRELE1BQUwsR0FBY3pGLElBQWQ7QUFDQSxhQUFLMEYsS0FBTCxHQUFhLElBQWI7QUFDQSxZQUFJN0QsS0FBSixFQUFXdEMsT0FBTyxJQUFQLEVBQWFzQyxLQUFiO0FBQ1gsYUFBS0YsV0FBTCxDQUFpQnpCLFVBQWpCLEVBQTZCMEIsSUFBN0IsQ0FBa0MsSUFBbEMsRUFBd0NDLFNBQVMsSUFBakQ7QUFDQSxhQUFLNEQsTUFBTCxHQUFjekYsSUFBZDtBQUNBUix1QkFBZSxJQUFmO0FBQ0EsYUFBS29DLElBQUw7QUFDSDs7a0JBQ01uQyxNLHFCQUFzQjtBQUFBLDBDQUFaa0csVUFBWTtBQUFaQSxzQkFBWTtBQUFBOztBQUN6QixlQUFPakcsOEJBQVksSUFBWixTQUFxQmlHLFVBQXJCLEVBQVA7QUFDSCxLOztrQkFDTUMsTSxtQkFBTy9ELEssRUFBTztBQUNqQixlQUFPLElBQUksSUFBSixDQUFTQSxLQUFULENBQVA7QUFDSCxLOztrQkFDTWdFLE0sbUJBQU9GLFUsRUFBWTtBQUN0QmhHLGdCQUFRZ0csVUFBUixFQUFvQkcsZUFBcEIsQ0FBb0MsSUFBcEM7QUFDQSxhQUFLNUYsVUFBTCxFQUFpQm9ELElBQWpCO0FBQ0ExRCx5QkFBaUIsSUFBakI7QUFDSCxLOztrQkFDTW1HLFcsd0JBQVlKLFUsRUFBWTtBQUMzQmhHLGdCQUFRZ0csVUFBUixFQUFvQnRDLFlBQXBCLENBQWlDLElBQWpDO0FBQ0EsYUFBS25ELFVBQUwsRUFBaUJvRCxJQUFqQjtBQUNILEs7O2tCQUNNMEMsZSw0QkFBZ0J0QyxRLEVBQVU7QUFDN0IsWUFBSUMsUUFBUSxLQUFLekQsVUFBTCxFQUFpQjBELG1CQUFqQixDQUFxQ0YsUUFBckMsQ0FBWjtBQUNBLFlBQUksQ0FBQ0MsS0FBTCxFQUFZLE1BQU0sSUFBSXBELEtBQUosc0VBQTRFbUQsUUFBNUUsU0FBTjtBQUNaLGVBQU9DLEtBQVA7QUFDSCxLOztrQkFDTXNDLG9CLGlDQUFxQkMsUSxFQUFVO0FBQ2xDLFlBQUlDLFdBQVcsS0FBS2pHLFVBQUwsRUFBaUI0RSxtQkFBakIsRUFBZjtBQUNBLFlBQUksQ0FBQ3FCLFFBQUwsRUFBZTtBQUNmLGFBQUssSUFBSXBFLElBQVQsSUFBaUJvRSxRQUFqQixFQUEyQjtBQUN2QkQscUJBQVNuRSxJQUFULEVBQWVvRSxTQUFTcEUsSUFBVCxDQUFmO0FBQ0g7QUFDSixLOzs0QkFDREgsSSxtQkFBTyxDQUFFLEM7OzRCQUNUd0UsRyxnQkFBSUMsRyxFQUFLO0FBQ0wsZUFBTyxLQUFLQSxHQUFMLENBQVA7QUFDSCxLOzs0QkFDREMsRyxnQkFBSUQsRyxFQUFLMUMsSyxFQUFPO0FBQ1osYUFBSzBDLEdBQUwsSUFBWTFDLEtBQVo7QUFDSCxLOzs0QkFDRDRDLGEsMEJBQWMxRSxLLEVBQU87QUFDakJ0QyxlQUFPLElBQVAsRUFBYXNDLEtBQWI7QUFDSCxLOzs0QkFDRDJFLE8sc0JBQVUsQ0FBRSxDOzs7OztlQS9DS2hCLGE7O0FBaURyQkEsY0FBYyxzQ0FBZCxJQUF3REQsYUFBYWxFLFVBQWIsQ0FBd0IsSUFBeEIsQ0FBeEQ7QUFDQW1FLGNBQWNpQixPQUFkLEdBQXdCLElBQXhCIiwiZmlsZSI6ImxpYi9vYmplY3QuanMiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBNZXRhLCBQcm9wZXJ0eVJlZmVyZW5jZSB9IGZyb20gJ0BnbGltbWVyL29iamVjdC1yZWZlcmVuY2UnO1xuaW1wb3J0IHsgZGljdCwgYXNzaWduLCBpbml0aWFsaXplR3VpZCB9IGZyb20gJ0BnbGltbWVyL3V0aWwnO1xuaW1wb3J0IHsgZXh0ZW5kIGFzIGV4dGVuZENsYXNzLCB0b01peGluLCByZWxpbmtTdWJjbGFzc2VzLCB3cmFwTWV0aG9kIH0gZnJvbSAnLi9taXhpbic7XG5jb25zdCB7IGlzQXJyYXkgfSA9IEFycmF5O1xuaW1wb3J0IHsgUk9PVCB9IGZyb20gJy4vdXRpbHMnO1xuZXhwb3J0IGNvbnN0IEVNUFRZX0NBQ0hFID0gZnVuY3Rpb24gRU1QVFlfQ0FDSEUoKSB7fTtcbmNvbnN0IENMQVNTX01FVEEgPSBcImRmOGJlNGM4LTRlODktNDRlMi1hOGY5LTU1MGM4ZGFjZGNhN1wiO1xuZXhwb3J0IGZ1bmN0aW9uIHR1cmJvY2hhcmdlKG9iaikge1xuICAgIC8vIGZ1bmN0aW9uIER1bW15KCkge31cbiAgICAvLyBEdW1teS5wcm90b3R5cGUgPSBvYmo7XG4gICAgcmV0dXJuIG9iajtcbn1cbmNsYXNzIFNlYWxlZE1ldGEgZXh0ZW5kcyBNZXRhIHtcbiAgICBhZGRSZWZlcmVuY2VUeXBlRm9yKC4uLl9hcmdzKSB7XG4gICAgICAgIHRocm93IG5ldyBFcnJvcihcIkNhbm5vdCBtb2RpZnkgcmVmZXJlbmNlIHR5cGVzIG9uIGEgc2VhbGVkIG1ldGFcIik7XG4gICAgfVxufVxuZXhwb3J0IGNsYXNzIENsYXNzTWV0YSB7XG4gICAgY29uc3RydWN0b3IoKSB7XG4gICAgICAgIHRoaXMucmVmZXJlbmNlVHlwZXMgPSBkaWN0KCk7XG4gICAgICAgIHRoaXMucHJvcGVydHlNZXRhZGF0YSA9IGRpY3QoKTtcbiAgICAgICAgdGhpcy5jb25jYXRlbmF0ZWRQcm9wZXJ0aWVzID0gZGljdCgpO1xuICAgICAgICB0aGlzLmhhc0NvbmNhdGVuYXRlZFByb3BlcnRpZXMgPSBmYWxzZTtcbiAgICAgICAgdGhpcy5tZXJnZWRQcm9wZXJ0aWVzID0gZGljdCgpO1xuICAgICAgICB0aGlzLmhhc01lcmdlZFByb3BlcnRpZXMgPSBmYWxzZTtcbiAgICAgICAgdGhpcy5taXhpbnMgPSBbXTtcbiAgICAgICAgdGhpcy5hcHBsaWVkTWl4aW5zID0gW107XG4gICAgICAgIHRoaXMuc3RhdGljTWl4aW5zID0gW107XG4gICAgICAgIHRoaXMuc3ViY2xhc3NlcyA9IFtdO1xuICAgICAgICB0aGlzLnNsb3RzID0gW107XG4gICAgICAgIHRoaXMuSW5zdGFuY2VNZXRhQ29uc3RydWN0b3IgPSBudWxsO1xuICAgIH1cbiAgICBzdGF0aWMgZnJvbVBhcmVudChwYXJlbnQpIHtcbiAgICAgICAgbGV0IG1ldGEgPSBuZXcgdGhpcygpO1xuICAgICAgICBtZXRhLnJlc2V0KHBhcmVudCk7XG4gICAgICAgIHJldHVybiBtZXRhO1xuICAgIH1cbiAgICBzdGF0aWMgZm9yKG9iamVjdCkge1xuICAgICAgICBpZiAoQ0xBU1NfTUVUQSBpbiBvYmplY3QpIHJldHVybiBvYmplY3RbQ0xBU1NfTUVUQV07ZWxzZSBpZiAob2JqZWN0LmNvbnN0cnVjdG9yKSByZXR1cm4gb2JqZWN0LmNvbnN0cnVjdG9yW0NMQVNTX01FVEFdIHx8IG51bGw7ZWxzZSByZXR1cm4gbnVsbDtcbiAgICB9XG4gICAgaW5pdChvYmplY3QsIGF0dHJzKSB7XG4gICAgICAgIGlmICh0eXBlb2YgYXR0cnMgIT09ICdvYmplY3QnIHx8IGF0dHJzID09PSBudWxsKSByZXR1cm47XG4gICAgICAgIGlmICh0aGlzLmhhc0NvbmNhdGVuYXRlZFByb3BlcnRpZXMpIHtcbiAgICAgICAgICAgIGxldCBjb25jYXRQcm9wcyA9IHRoaXMuY29uY2F0ZW5hdGVkUHJvcGVydGllcztcbiAgICAgICAgICAgIGZvciAobGV0IHByb3AgaW4gY29uY2F0UHJvcHMpIHtcbiAgICAgICAgICAgICAgICBpZiAocHJvcCBpbiBhdHRycykge1xuICAgICAgICAgICAgICAgICAgICBsZXQgY29uY2F0ID0gY29uY2F0UHJvcHNbcHJvcF0uc2xpY2UoKTtcbiAgICAgICAgICAgICAgICAgICAgb2JqZWN0W3Byb3BdID0gY29uY2F0LmNvbmNhdChhdHRyc1twcm9wXSk7XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgfVxuICAgICAgICB9XG4gICAgICAgIGlmICh0aGlzLmhhc01lcmdlZFByb3BlcnRpZXMpIHtcbiAgICAgICAgICAgIGxldCBtZXJnZWRQcm9wcyA9IHRoaXMubWVyZ2VkUHJvcGVydGllcztcbiAgICAgICAgICAgIGZvciAobGV0IHByb3AgaW4gbWVyZ2VkUHJvcHMpIHtcbiAgICAgICAgICAgICAgICBpZiAocHJvcCBpbiBhdHRycykge1xuICAgICAgICAgICAgICAgICAgICBsZXQgbWVyZ2VkID0gYXNzaWduKHt9LCBtZXJnZWRQcm9wc1twcm9wXSk7XG4gICAgICAgICAgICAgICAgICAgIG9iamVjdFtwcm9wXSA9IGFzc2lnbihtZXJnZWQsIGF0dHJzW3Byb3BdKTtcbiAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICB9XG4gICAgICAgIH1cbiAgICB9XG4gICAgYWRkU3RhdGljTWl4aW4obWl4aW4pIHtcbiAgICAgICAgdGhpcy5zdGF0aWNNaXhpbnMucHVzaChtaXhpbik7XG4gICAgfVxuICAgIGFkZE1peGluKG1peGluKSB7XG4gICAgICAgIHRoaXMubWl4aW5zLnB1c2gobWl4aW4pO1xuICAgIH1cbiAgICBnZXRTdGF0aWNNaXhpbnMoKSB7XG4gICAgICAgIHJldHVybiB0aGlzLnN0YXRpY01peGlucztcbiAgICB9XG4gICAgZ2V0TWl4aW5zKCkge1xuICAgICAgICByZXR1cm4gdGhpcy5taXhpbnM7XG4gICAgfVxuICAgIGFkZEFwcGxpZWRNaXhpbihtaXhpbikge1xuICAgICAgICB0aGlzLmFwcGxpZWRNaXhpbnMucHVzaChtaXhpbik7XG4gICAgfVxuICAgIGhhc0FwcGxpZWRNaXhpbihtaXhpbikge1xuICAgICAgICByZXR1cm4gdGhpcy5hcHBsaWVkTWl4aW5zLmluZGV4T2YobWl4aW4pICE9PSAtMTtcbiAgICB9XG4gICAgZ2V0QXBwbGllZE1peGlucygpIHtcbiAgICAgICAgcmV0dXJuIHRoaXMuYXBwbGllZE1peGlucztcbiAgICB9XG4gICAgaGFzU3RhdGljTWl4aW4obWl4aW4pIHtcbiAgICAgICAgcmV0dXJuIHRoaXMuc3RhdGljTWl4aW5zLmluZGV4T2YobWl4aW4pICE9PSAtMTtcbiAgICB9XG4gICAgc3RhdGljIGFwcGx5QWxsTWl4aW5zKFN1YmNsYXNzLCBQYXJlbnQpIHtcbiAgICAgICAgU3ViY2xhc3NbQ0xBU1NfTUVUQV0uZ2V0TWl4aW5zKCkuZm9yRWFjaChtID0+IG0uZXh0ZW5kUHJvdG90eXBlT250byhTdWJjbGFzcywgUGFyZW50KSk7XG4gICAgICAgIFN1YmNsYXNzW0NMQVNTX01FVEFdLmdldFN0YXRpY01peGlucygpLmZvckVhY2gobSA9PiBtLmV4dGVuZFN0YXRpYyhTdWJjbGFzcykpO1xuICAgICAgICBTdWJjbGFzc1tDTEFTU19NRVRBXS5zZWFsKCk7XG4gICAgfVxuICAgIGFkZFN1YmNsYXNzKGNvbnN0cnVjdG9yKSB7XG4gICAgICAgIHRoaXMuc3ViY2xhc3Nlcy5wdXNoKGNvbnN0cnVjdG9yKTtcbiAgICB9XG4gICAgZ2V0U3ViY2xhc3NlcygpIHtcbiAgICAgICAgcmV0dXJuIHRoaXMuc3ViY2xhc3NlcztcbiAgICB9XG4gICAgYWRkUHJvcGVydHlNZXRhZGF0YShwcm9wZXJ0eSwgdmFsdWUpIHtcbiAgICAgICAgdGhpcy5wcm9wZXJ0eU1ldGFkYXRhW3Byb3BlcnR5XSA9IHZhbHVlO1xuICAgIH1cbiAgICBtZXRhZGF0YUZvclByb3BlcnR5KHByb3BlcnR5KSB7XG4gICAgICAgIHJldHVybiB0aGlzLnByb3BlcnR5TWV0YWRhdGFbcHJvcGVydHldO1xuICAgIH1cbiAgICBhZGRSZWZlcmVuY2VUeXBlRm9yKHByb3BlcnR5LCB0eXBlKSB7XG4gICAgICAgIHRoaXMucmVmZXJlbmNlVHlwZXNbcHJvcGVydHldID0gdHlwZTtcbiAgICB9XG4gICAgYWRkU2xvdEZvcihwcm9wZXJ0eSkge1xuICAgICAgICB0aGlzLnNsb3RzLnB1c2gocHJvcGVydHkpO1xuICAgIH1cbiAgICBoYXNDb25jYXRlbmF0ZWRQcm9wZXJ0eShwcm9wZXJ0eSkge1xuICAgICAgICBpZiAoIXRoaXMuaGFzQ29uY2F0ZW5hdGVkUHJvcGVydGllcykgcmV0dXJuIGZhbHNlO1xuICAgICAgICByZXR1cm4gcHJvcGVydHkgaW4gdGhpcy5jb25jYXRlbmF0ZWRQcm9wZXJ0aWVzO1xuICAgIH1cbiAgICBnZXRDb25jYXRlbmF0ZWRQcm9wZXJ0eShwcm9wZXJ0eSkge1xuICAgICAgICByZXR1cm4gdGhpcy5jb25jYXRlbmF0ZWRQcm9wZXJ0aWVzW3Byb3BlcnR5XTtcbiAgICB9XG4gICAgZ2V0Q29uY2F0ZW5hdGVkUHJvcGVydGllcygpIHtcbiAgICAgICAgcmV0dXJuIE9iamVjdC5rZXlzKHRoaXMuY29uY2F0ZW5hdGVkUHJvcGVydGllcyk7XG4gICAgfVxuICAgIGFkZENvbmNhdGVuYXRlZFByb3BlcnR5KHByb3BlcnR5LCB2YWx1ZSkge1xuICAgICAgICB0aGlzLmhhc0NvbmNhdGVuYXRlZFByb3BlcnRpZXMgPSB0cnVlO1xuICAgICAgICBpZiAocHJvcGVydHkgaW4gdGhpcy5jb25jYXRlbmF0ZWRQcm9wZXJ0aWVzKSB7XG4gICAgICAgICAgICBsZXQgdmFsID0gdGhpcy5jb25jYXRlbmF0ZWRQcm9wZXJ0aWVzW3Byb3BlcnR5XS5jb25jYXQodmFsdWUpO1xuICAgICAgICAgICAgdGhpcy5jb25jYXRlbmF0ZWRQcm9wZXJ0aWVzW3Byb3BlcnR5XSA9IHZhbDtcbiAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICAgIHRoaXMuY29uY2F0ZW5hdGVkUHJvcGVydGllc1twcm9wZXJ0eV0gPSB2YWx1ZTtcbiAgICAgICAgfVxuICAgIH1cbiAgICBoYXNNZXJnZWRQcm9wZXJ0eShwcm9wZXJ0eSkge1xuICAgICAgICBpZiAoIXRoaXMuaGFzTWVyZ2VkUHJvcGVydGllcykgcmV0dXJuIGZhbHNlO1xuICAgICAgICByZXR1cm4gcHJvcGVydHkgaW4gdGhpcy5tZXJnZWRQcm9wZXJ0aWVzO1xuICAgIH1cbiAgICBnZXRNZXJnZWRQcm9wZXJ0eShwcm9wZXJ0eSkge1xuICAgICAgICByZXR1cm4gdGhpcy5tZXJnZWRQcm9wZXJ0aWVzW3Byb3BlcnR5XTtcbiAgICB9XG4gICAgZ2V0TWVyZ2VkUHJvcGVydGllcygpIHtcbiAgICAgICAgcmV0dXJuIE9iamVjdC5rZXlzKHRoaXMubWVyZ2VkUHJvcGVydGllcyk7XG4gICAgfVxuICAgIGFkZE1lcmdlZFByb3BlcnR5KHByb3BlcnR5LCB2YWx1ZSkge1xuICAgICAgICB0aGlzLmhhc01lcmdlZFByb3BlcnRpZXMgPSB0cnVlO1xuICAgICAgICBpZiAoaXNBcnJheSh2YWx1ZSkpIHtcbiAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcihgWW91IHBhc3NlZCBpbiBcXGAke0pTT04uc3RyaW5naWZ5KHZhbHVlKX1cXGAgYXMgdGhlIHZhbHVlIGZvciBcXGBmb29cXGAgYnV0IFxcYGZvb1xcYCBjYW5ub3QgYmUgYW4gQXJyYXlgKTtcbiAgICAgICAgfVxuICAgICAgICBpZiAocHJvcGVydHkgaW4gdGhpcy5tZXJnZWRQcm9wZXJ0aWVzICYmIHRoaXMubWVyZ2VkUHJvcGVydGllc1twcm9wZXJ0eV0gJiYgdmFsdWUpIHtcbiAgICAgICAgICAgIHRoaXMubWVyZ2VkUHJvcGVydGllc1twcm9wZXJ0eV0gPSBtZXJnZU1lcmdlZFByb3BlcnRpZXModmFsdWUsIHRoaXMubWVyZ2VkUHJvcGVydGllc1twcm9wZXJ0eV0pO1xuICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgdmFsdWUgPSB2YWx1ZSA9PT0gbnVsbCA/IHZhbHVlIDogdmFsdWUgfHwge307XG4gICAgICAgICAgICB0aGlzLm1lcmdlZFByb3BlcnRpZXNbcHJvcGVydHldID0gdmFsdWU7XG4gICAgICAgIH1cbiAgICB9XG4gICAgZ2V0UmVmZXJlbmNlVHlwZXMoKSB7XG4gICAgICAgIHJldHVybiB0aGlzLnJlZmVyZW5jZVR5cGVzO1xuICAgIH1cbiAgICBnZXRQcm9wZXJ0eU1ldGFkYXRhKCkge1xuICAgICAgICByZXR1cm4gdGhpcy5wcm9wZXJ0eU1ldGFkYXRhO1xuICAgIH1cbiAgICByZXNldChwYXJlbnQpIHtcbiAgICAgICAgdGhpcy5yZWZlcmVuY2VUeXBlcyA9IGRpY3QoKTtcbiAgICAgICAgdGhpcy5wcm9wZXJ0eU1ldGFkYXRhID0gZGljdCgpO1xuICAgICAgICB0aGlzLmNvbmNhdGVuYXRlZFByb3BlcnRpZXMgPSBkaWN0KCk7XG4gICAgICAgIHRoaXMubWVyZ2VkUHJvcGVydGllcyA9IGRpY3QoKTtcbiAgICAgICAgaWYgKHBhcmVudCkge1xuICAgICAgICAgICAgdGhpcy5oYXNDb25jYXRlbmF0ZWRQcm9wZXJ0aWVzID0gcGFyZW50Lmhhc0NvbmNhdGVuYXRlZFByb3BlcnRpZXM7XG4gICAgICAgICAgICBmb3IgKGxldCBwcm9wIGluIHBhcmVudC5jb25jYXRlbmF0ZWRQcm9wZXJ0aWVzKSB7XG4gICAgICAgICAgICAgICAgdGhpcy5jb25jYXRlbmF0ZWRQcm9wZXJ0aWVzW3Byb3BdID0gcGFyZW50LmNvbmNhdGVuYXRlZFByb3BlcnRpZXNbcHJvcF0uc2xpY2UoKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICAgIHRoaXMuaGFzTWVyZ2VkUHJvcGVydGllcyA9IHBhcmVudC5oYXNNZXJnZWRQcm9wZXJ0aWVzO1xuICAgICAgICAgICAgZm9yIChsZXQgcHJvcCBpbiBwYXJlbnQubWVyZ2VkUHJvcGVydGllcykge1xuICAgICAgICAgICAgICAgIHRoaXMubWVyZ2VkUHJvcGVydGllc1twcm9wXSA9IGFzc2lnbih7fSwgcGFyZW50Lm1lcmdlZFByb3BlcnRpZXNbcHJvcF0pO1xuICAgICAgICAgICAgfVxuICAgICAgICAgICAgYXNzaWduKHRoaXMucmVmZXJlbmNlVHlwZXMsIHBhcmVudC5yZWZlcmVuY2VUeXBlcyk7XG4gICAgICAgICAgICBhc3NpZ24odGhpcy5wcm9wZXJ0eU1ldGFkYXRhLCBwYXJlbnQucHJvcGVydHlNZXRhZGF0YSk7XG4gICAgICAgIH1cbiAgICB9XG4gICAgcmVzZWFsKG9iaikge1xuICAgICAgICBsZXQgbWV0YSA9IE1ldGEuZm9yKG9iaik7XG4gICAgICAgIGxldCBmcmVzaCA9IG5ldyB0aGlzLkluc3RhbmNlTWV0YUNvbnN0cnVjdG9yKG9iaiwge30pO1xuICAgICAgICBsZXQgcmVmZXJlbmNlVHlwZXMgPSBtZXRhLmdldFJlZmVyZW5jZVR5cGVzKCk7XG4gICAgICAgIGxldCBzbG90cyA9IG1ldGEuZ2V0U2xvdHMoKTtcbiAgICAgICAgdHVyYm9jaGFyZ2UoYXNzaWduKHJlZmVyZW5jZVR5cGVzLCB0aGlzLnJlZmVyZW5jZVR5cGVzKSk7XG4gICAgICAgIHR1cmJvY2hhcmdlKGFzc2lnbihzbG90cywgZnJlc2guZ2V0U2xvdHMoKSkpO1xuICAgIH1cbiAgICBzZWFsKCkge1xuICAgICAgICBsZXQgcmVmZXJlbmNlVHlwZXMgPSB0dXJib2NoYXJnZShhc3NpZ24oe30sIHRoaXMucmVmZXJlbmNlVHlwZXMpKTtcbiAgICAgICAgdHVyYm9jaGFyZ2UodGhpcy5jb25jYXRlbmF0ZWRQcm9wZXJ0aWVzKTtcbiAgICAgICAgdHVyYm9jaGFyZ2UodGhpcy5tZXJnZWRQcm9wZXJ0aWVzKTtcbiAgICAgICAgaWYgKCF0aGlzLmhhc01lcmdlZFByb3BlcnRpZXMgJiYgIXRoaXMuaGFzQ29uY2F0ZW5hdGVkUHJvcGVydGllcykge1xuICAgICAgICAgICAgdGhpcy5pbml0ID0gZnVuY3Rpb24gKCkge307XG4gICAgICAgIH1cbiAgICAgICAgbGV0IHNsb3RzID0gdGhpcy5zbG90cztcbiAgICAgICAgY2xhc3MgU2xvdHMge1xuICAgICAgICAgICAgY29uc3RydWN0b3IoKSB7XG4gICAgICAgICAgICAgICAgc2xvdHMuZm9yRWFjaChuYW1lID0+IHtcbiAgICAgICAgICAgICAgICAgICAgdGhpc1tuYW1lXSA9IEVNUFRZX0NBQ0hFO1xuICAgICAgICAgICAgICAgIH0pO1xuICAgICAgICAgICAgfVxuICAgICAgICB9XG4gICAgICAgIHRoaXMuSW5zdGFuY2VNZXRhQ29uc3RydWN0b3IgPSBjbGFzcyBleHRlbmRzIFNlYWxlZE1ldGEge1xuICAgICAgICAgICAgY29uc3RydWN0b3IoKSB7XG4gICAgICAgICAgICAgICAgc3VwZXIoLi4uYXJndW1lbnRzKTtcbiAgICAgICAgICAgICAgICB0aGlzLnNsb3RzID0gbmV3IFNsb3RzKCk7XG4gICAgICAgICAgICAgICAgdGhpcy5yZWZlcmVuY2VUeXBlcyA9IHJlZmVyZW5jZVR5cGVzO1xuICAgICAgICAgICAgfVxuICAgICAgICAgICAgZ2V0UmVmZXJlbmNlVHlwZXMoKSB7XG4gICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMucmVmZXJlbmNlVHlwZXM7XG4gICAgICAgICAgICB9XG4gICAgICAgICAgICByZWZlcmVuY2VUeXBlRm9yKHByb3BlcnR5KSB7XG4gICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMucmVmZXJlbmNlVHlwZXNbcHJvcGVydHldIHx8IFByb3BlcnR5UmVmZXJlbmNlO1xuICAgICAgICAgICAgfVxuICAgICAgICAgICAgZ2V0U2xvdHMoKSB7XG4gICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuc2xvdHM7XG4gICAgICAgICAgICB9XG4gICAgICAgIH07XG4gICAgICAgIHR1cmJvY2hhcmdlKHRoaXMpO1xuICAgIH1cbn1cbmZ1bmN0aW9uIG1lcmdlTWVyZ2VkUHJvcGVydGllcyhhdHRycywgcGFyZW50KSB7XG4gICAgbGV0IG1lcmdlZCA9IGFzc2lnbih7fSwgcGFyZW50KTtcbiAgICBmb3IgKGxldCBwcm9wIGluIGF0dHJzKSB7XG4gICAgICAgIGlmIChwcm9wIGluIHBhcmVudCAmJiB0eXBlb2YgcGFyZW50W3Byb3BdID09PSAnZnVuY3Rpb24nICYmIHR5cGVvZiBhdHRyc1twcm9wXSA9PT0gJ2Z1bmN0aW9uJykge1xuICAgICAgICAgICAgbGV0IHdyYXBwZWQgPSB3cmFwTWV0aG9kKHBhcmVudCwgcHJvcCwgYXR0cnNbcHJvcF0pO1xuICAgICAgICAgICAgbWVyZ2VkW3Byb3BdID0gd3JhcHBlZDtcbiAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICAgIG1lcmdlZFtwcm9wXSA9IGF0dHJzW3Byb3BdO1xuICAgICAgICB9XG4gICAgfVxuICAgIHJldHVybiBtZXJnZWQ7XG59XG5leHBvcnQgY2xhc3MgSW5zdGFuY2VNZXRhIGV4dGVuZHMgQ2xhc3NNZXRhIHtcbiAgICBjb25zdHJ1Y3RvcigpIHtcbiAgICAgICAgc3VwZXIoLi4uYXJndW1lbnRzKTtcbiAgICAgICAgdGhpc1tcImRmOGJlNGM4LTRlODktNDRlMi1hOGY5LTU1MGM4ZGFjZGNhN1wiXSA9IENsYXNzTWV0YS5mcm9tUGFyZW50KG51bGwpO1xuICAgIH1cbiAgICBzdGF0aWMgZnJvbVBhcmVudChwYXJlbnQpIHtcbiAgICAgICAgcmV0dXJuIHN1cGVyLmZyb21QYXJlbnQocGFyZW50KTtcbiAgICB9XG4gICAgcmVzZXQocGFyZW50KSB7XG4gICAgICAgIHN1cGVyLnJlc2V0KHBhcmVudCk7XG4gICAgICAgIGlmIChwYXJlbnQpIHRoaXNbQ0xBU1NfTUVUQV0ucmVzZXQocGFyZW50W0NMQVNTX01FVEFdKTtcbiAgICB9XG4gICAgc2VhbCgpIHtcbiAgICAgICAgc3VwZXIuc2VhbCgpO1xuICAgICAgICB0aGlzW0NMQVNTX01FVEFdLnNlYWwoKTtcbiAgICB9XG59XG5leHBvcnQgZGVmYXVsdCBjbGFzcyBHbGltbWVyT2JqZWN0IHtcbiAgICBjb25zdHJ1Y3RvcihhdHRycykge1xuICAgICAgICB0aGlzLl9zdXBlciA9IFJPT1Q7XG4gICAgICAgIHRoaXMuX21ldGEgPSBudWxsO1xuICAgICAgICBpZiAoYXR0cnMpIGFzc2lnbih0aGlzLCBhdHRycyk7XG4gICAgICAgIHRoaXMuY29uc3RydWN0b3JbQ0xBU1NfTUVUQV0uaW5pdCh0aGlzLCBhdHRycyB8fCBudWxsKTtcbiAgICAgICAgdGhpcy5fc3VwZXIgPSBST09UO1xuICAgICAgICBpbml0aWFsaXplR3VpZCh0aGlzKTtcbiAgICAgICAgdGhpcy5pbml0KCk7XG4gICAgfVxuICAgIHN0YXRpYyBleHRlbmQoLi4uZXh0ZW5zaW9ucykge1xuICAgICAgICByZXR1cm4gZXh0ZW5kQ2xhc3ModGhpcywgLi4uZXh0ZW5zaW9ucyk7XG4gICAgfVxuICAgIHN0YXRpYyBjcmVhdGUoYXR0cnMpIHtcbiAgICAgICAgcmV0dXJuIG5ldyB0aGlzKGF0dHJzKTtcbiAgICB9XG4gICAgc3RhdGljIHJlb3BlbihleHRlbnNpb25zKSB7XG4gICAgICAgIHRvTWl4aW4oZXh0ZW5zaW9ucykuZXh0ZW5kUHJvdG90eXBlKHRoaXMpO1xuICAgICAgICB0aGlzW0NMQVNTX01FVEFdLnNlYWwoKTtcbiAgICAgICAgcmVsaW5rU3ViY2xhc3Nlcyh0aGlzKTtcbiAgICB9XG4gICAgc3RhdGljIHJlb3BlbkNsYXNzKGV4dGVuc2lvbnMpIHtcbiAgICAgICAgdG9NaXhpbihleHRlbnNpb25zKS5leHRlbmRTdGF0aWModGhpcyk7XG4gICAgICAgIHRoaXNbQ0xBU1NfTUVUQV0uc2VhbCgpO1xuICAgIH1cbiAgICBzdGF0aWMgbWV0YUZvclByb3BlcnR5KHByb3BlcnR5KSB7XG4gICAgICAgIGxldCB2YWx1ZSA9IHRoaXNbQ0xBU1NfTUVUQV0ubWV0YWRhdGFGb3JQcm9wZXJ0eShwcm9wZXJ0eSk7XG4gICAgICAgIGlmICghdmFsdWUpIHRocm93IG5ldyBFcnJvcihgbWV0YUZvclByb3BlcnR5KCkgY291bGQgbm90IGZpbmQgYSBjb21wdXRlZCBwcm9wZXJ0eSB3aXRoIGtleSAnJHtwcm9wZXJ0eX0nLmApO1xuICAgICAgICByZXR1cm4gdmFsdWU7XG4gICAgfVxuICAgIHN0YXRpYyBlYWNoQ29tcHV0ZWRQcm9wZXJ0eShjYWxsYmFjaykge1xuICAgICAgICBsZXQgbWV0YWRhdGEgPSB0aGlzW0NMQVNTX01FVEFdLmdldFByb3BlcnR5TWV0YWRhdGEoKTtcbiAgICAgICAgaWYgKCFtZXRhZGF0YSkgcmV0dXJuO1xuICAgICAgICBmb3IgKGxldCBwcm9wIGluIG1ldGFkYXRhKSB7XG4gICAgICAgICAgICBjYWxsYmFjayhwcm9wLCBtZXRhZGF0YVtwcm9wXSk7XG4gICAgICAgIH1cbiAgICB9XG4gICAgaW5pdCgpIHt9XG4gICAgZ2V0KGtleSkge1xuICAgICAgICByZXR1cm4gdGhpc1trZXldO1xuICAgIH1cbiAgICBzZXQoa2V5LCB2YWx1ZSkge1xuICAgICAgICB0aGlzW2tleV0gPSB2YWx1ZTtcbiAgICB9XG4gICAgc2V0UHJvcGVydGllcyhhdHRycykge1xuICAgICAgICBhc3NpZ24odGhpcywgYXR0cnMpO1xuICAgIH1cbiAgICBkZXN0cm95KCkge31cbn1cbkdsaW1tZXJPYmplY3RbXCJkZjhiZTRjOC00ZTg5LTQ0ZTItYThmOS01NTBjOGRhY2RjYTdcIl0gPSBJbnN0YW5jZU1ldGEuZnJvbVBhcmVudChudWxsKTtcbkdsaW1tZXJPYmplY3QuaXNDbGFzcyA9IHRydWU7Il19