UNPKG

@glimmer/compiler

Version:
563 lines (452 loc) 55.1 kB
var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }(); 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 _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); } function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } } import { assert } from '@glimmer/util'; import { Stack, DictSet } from '@glimmer/util'; import { isArgument, isAttribute, isFlushElement } from '@glimmer/wire-format'; export var Block = function () { function Block() { _classCallCheck(this, Block); this.statements = []; } Block.prototype.push = function push(statement) { this.statements.push(statement); }; return Block; }(); export var InlineBlock = function (_Block) { _inherits(InlineBlock, _Block); function InlineBlock(table) { _classCallCheck(this, InlineBlock); var _this = _possibleConstructorReturn(this, _Block.call(this)); _this.table = table; return _this; } InlineBlock.prototype.toJSON = function toJSON() { return { statements: this.statements, parameters: this.table.slots }; }; return InlineBlock; }(Block); export var NamedBlock = function (_InlineBlock) { _inherits(NamedBlock, _InlineBlock); function NamedBlock(name, table) { _classCallCheck(this, NamedBlock); var _this2 = _possibleConstructorReturn(this, _InlineBlock.call(this, table)); _this2.name = name; return _this2; } return NamedBlock; }(InlineBlock); export var TemplateBlock = function (_Block2) { _inherits(TemplateBlock, _Block2); function TemplateBlock(symbolTable) { _classCallCheck(this, TemplateBlock); var _this3 = _possibleConstructorReturn(this, _Block2.call(this)); _this3.symbolTable = symbolTable; _this3.type = 'template'; _this3.yields = new DictSet(); _this3.named = new DictSet(); _this3.blocks = []; _this3.hasEval = false; return _this3; } TemplateBlock.prototype.push = function push(statement) { this.statements.push(statement); }; TemplateBlock.prototype.toJSON = function toJSON() { return { symbols: this.symbolTable.symbols, statements: this.statements, hasEval: this.hasEval, upvars: this.symbolTable.freeVariables }; }; return TemplateBlock; }(Block); export var ComponentBlock = function (_Block3) { _inherits(ComponentBlock, _Block3); function ComponentBlock(tag, table, selfClosing) { _classCallCheck(this, ComponentBlock); var _this4 = _possibleConstructorReturn(this, _Block3.call(this)); _this4.tag = tag; _this4.table = table; _this4.selfClosing = selfClosing; _this4.attributes = []; _this4.arguments = []; _this4.inParams = true; _this4.positionals = []; _this4.blocks = []; return _this4; } ComponentBlock.prototype.push = function push(statement) { if (this.inParams) { if (isFlushElement(statement)) { this.inParams = false; } else if (isArgument(statement)) { this.arguments.push(statement); } else if (isAttribute(statement)) { this.attributes.push(statement); } else { throw new Error('Compile Error: only parameters allowed before flush-element'); } } else { this.statements.push(statement); } }; ComponentBlock.prototype.pushBlock = function pushBlock(name, block) { this.blocks.push([name, block]); }; ComponentBlock.prototype.toJSON = function toJSON() { var blocks = void 0; var args = this.arguments; var keys = args.map(function (arg) { return arg[1]; }); var values = args.map(function (arg) { return arg[2]; }); if (this.selfClosing) { blocks = null; } else if (this.blocks.length > 0) { var _keys = []; var _values = []; for (var i = 0; i < this.blocks.length; i++) { var _blocks$i = this.blocks[i], key = _blocks$i[0], value = _blocks$i[1]; _keys.push(key.slice(1)); _values.push(value); } blocks = [_keys, _values]; } else { blocks = [['default'], [{ statements: this.statements, parameters: this.table.slots }]]; } return [this.tag, this.attributes, [keys, values], blocks]; }; return ComponentBlock; }(Block); export var Template = function () { function Template(symbols) { _classCallCheck(this, Template); this.block = new TemplateBlock(symbols); } Template.prototype.toJSON = function toJSON() { return this.block.toJSON(); }; return Template; }(); var JavaScriptCompiler = function () { function JavaScriptCompiler(opcodes, symbols, locations, options) { _classCallCheck(this, JavaScriptCompiler); this.locations = locations; this.blocks = new Stack(); this.values = []; this.location = null; this.locationStack = []; this.opcodes = opcodes; this.template = new Template(symbols); this.options = options; } JavaScriptCompiler.process = function process(opcodes, locations, symbols, options) { var compiler = new JavaScriptCompiler(opcodes, symbols, locations, options); return compiler.process(); }; JavaScriptCompiler.prototype.process = function process() { var _this5 = this; this.opcodes.forEach(function (op, i) { var opcode = op[0]; _this5.location = _this5.locations[i]; var arg = op[1]; if (!_this5[opcode]) { throw new Error('unimplemented ' + opcode + ' on JavaScriptCompiler'); } _this5[opcode](arg); }); return this.template; }; /// Nesting JavaScriptCompiler.prototype.startBlock = function startBlock(program) { this.startInlineBlock(program.symbols); }; JavaScriptCompiler.prototype.endBlock = function endBlock() { var block = this.endInlineBlock(); this.template.block.blocks.push(block); }; JavaScriptCompiler.prototype.startProgram = function startProgram() { this.blocks.push(this.template.block); }; JavaScriptCompiler.prototype.endProgram = function endProgram() {}; /// Statements JavaScriptCompiler.prototype.text = function text(content) { this.push([1 /* Append */, 1, 0, 0, content]); }; JavaScriptCompiler.prototype.append = function append(trusted) { this.push([1 /* Append */, +trusted, 0, 0, this.popValue()]); }; JavaScriptCompiler.prototype.comment = function comment(value) { this.push([2 /* Comment */, value]); }; JavaScriptCompiler.prototype.modifier = function modifier() { var name = this.popValue(); var params = this.popValue(); var hash = this.popValue(); this.push([3 /* Modifier */, 0, 0, name, params, hash]); }; JavaScriptCompiler.prototype.block = function block(_ref) { var template = _ref[0], inverse = _ref[1]; var head = this.popValue(); var params = this.popValue(); var hash = this.popValue(); var blocks = this.template.block.blocks; false && assert(typeof template !== 'number' || blocks[template] !== null, 'missing block in the compiler'); false && assert(typeof inverse !== 'number' || blocks[inverse] !== null, 'missing block in the compiler'); var namedBlocks = void 0; if (template === null && inverse === null) { namedBlocks = null; } else if (inverse === null) { namedBlocks = [['default'], [blocks[template]]]; } else { namedBlocks = [['default', 'else'], [blocks[template], blocks[inverse]]]; } // assert(head[]); this.push([5 /* Block */, head, params, hash, namedBlocks]); }; JavaScriptCompiler.prototype.openComponent = function openComponent(element) { var tag = this.options && this.options.customizeComponentName ? this.options.customizeComponentName(element.tag) : element.tag; var component = new ComponentBlock(tag, element.symbols, element.selfClosing); this.blocks.push(component); }; JavaScriptCompiler.prototype.openNamedBlock = function openNamedBlock(element) { var block = new NamedBlock(element.tag, element.symbols); this.blocks.push(block); }; JavaScriptCompiler.prototype.openElement = function openElement(_ref2) { var element = _ref2[0], simple = _ref2[1]; var tag = element.tag; if (element.blockParams.length > 0) { throw new Error('Compile Error: <' + element.tag + '> is not a component and doesn\'t support block parameters'); } else { this.push([9 /* OpenElement */, tag, simple]); } }; JavaScriptCompiler.prototype.flushElement = function flushElement() { this.push([10 /* FlushElement */]); }; JavaScriptCompiler.prototype.closeComponent = function closeComponent(_element) { var _endComponent = this.endComponent(), tag = _endComponent[0], attrs = _endComponent[1], args = _endComponent[2], blocks = _endComponent[3]; this.push([7 /* Component */, tag, attrs, args, blocks]); }; JavaScriptCompiler.prototype.closeNamedBlock = function closeNamedBlock(_element) { var blocks = this.blocks; var block = blocks.pop(); this.currentComponent.pushBlock(block.name, block.toJSON()); }; JavaScriptCompiler.prototype.closeDynamicComponent = function closeDynamicComponent(_element) { var _endComponent2 = this.endComponent(), attrs = _endComponent2[1], args = _endComponent2[2], block = _endComponent2[3]; this.push([7 /* Component */, this.popValue(), attrs, args, block]); }; JavaScriptCompiler.prototype.closeElement = function closeElement(_element) { this.push([11 /* CloseElement */]); }; JavaScriptCompiler.prototype.staticAttr = function staticAttr(_ref3) { var name = _ref3[0], namespace = _ref3[1]; var value = this.popValue(); this.push([12 /* StaticAttr */, name, value, namespace]); }; JavaScriptCompiler.prototype.dynamicAttr = function dynamicAttr(_ref4) { var name = _ref4[0], namespace = _ref4[1]; var value = this.popValue(); this.push([13 /* DynamicAttr */, name, value, namespace]); }; JavaScriptCompiler.prototype.componentAttr = function componentAttr(_ref5) { var name = _ref5[0], namespace = _ref5[1]; var value = this.popValue(); this.push([14 /* ComponentAttr */, name, value, namespace]); }; JavaScriptCompiler.prototype.trustingAttr = function trustingAttr(_ref6) { var name = _ref6[0], namespace = _ref6[1]; var value = this.popValue(); this.push([20 /* TrustingDynamicAttr */, name, value, namespace]); }; JavaScriptCompiler.prototype.trustingComponentAttr = function trustingComponentAttr(_ref7) { var name = _ref7[0], namespace = _ref7[1]; var value = this.popValue(); this.push([21 /* TrustingComponentAttr */, name, value, namespace]); }; JavaScriptCompiler.prototype.staticArg = function staticArg(name) { var value = this.popValue(); this.push([19 /* StaticArg */, name, value]); }; JavaScriptCompiler.prototype.dynamicArg = function dynamicArg(name) { var value = this.popValue(); this.push([18 /* DynamicArg */, name, value]); }; JavaScriptCompiler.prototype.yield = function _yield(to) { var params = this.popValue(); this.push([16 /* Yield */, to, params]); }; JavaScriptCompiler.prototype.attrSplat = function attrSplat(to) { // consume (and disregard) the value pushed for the // ...attributes attribute this.popValue(); this.push([15 /* AttrSplat */, to]); }; JavaScriptCompiler.prototype.debugger = function _debugger(evalInfo) { this.push([22 /* Debugger */, evalInfo]); this.template.block.hasEval = true; }; JavaScriptCompiler.prototype.hasBlock = function hasBlock(name) { this.pushValue([28 /* HasBlock */, [24 /* GetSymbol */, name]]); }; JavaScriptCompiler.prototype.hasBlockParams = function hasBlockParams(name) { this.pushValue([29 /* HasBlockParams */ , [24 /* GetSymbol */, name]]); }; JavaScriptCompiler.prototype.partial = function partial(evalInfo) { var params = this.popValue(); this.push([17 /* Partial */, params[0], evalInfo]); this.template.block.hasEval = true; }; /// Expressions JavaScriptCompiler.prototype.literal = function literal(value) { if (value === undefined) { this.pushValue([30 /* Undefined */]); } else { this.pushValue(value); } }; JavaScriptCompiler.prototype.getPath = function getPath(rest) { var head = this.popValue(); this.pushValue([27 /* GetPath */, head, rest]); }; JavaScriptCompiler.prototype.getSymbol = function getSymbol(head) { this.pushValue([24 /* GetSymbol */, head]); }; JavaScriptCompiler.prototype.getFree = function getFree(head) { this.pushValue([25 /* GetFree */, head]); }; JavaScriptCompiler.prototype.getFreeWithContext = function getFreeWithContext(_ref8) { var head = _ref8[0], context = _ref8[1]; this.pushValue([26 /* GetContextualFree */, head, context]); }; JavaScriptCompiler.prototype.concat = function concat() { this.pushValue([32 /* Concat */, this.popValue()]); }; JavaScriptCompiler.prototype.helper = function helper() { var _popLocatedValue = this.popLocatedValue(), head = _popLocatedValue.value, location = _popLocatedValue.location; var params = this.popValue(); var hash = this.popValue(); this.pushValue([31 /* Call */ , start(location), end(location), head, params, hash]); }; /// Stack Management Opcodes JavaScriptCompiler.prototype.prepareArray = function prepareArray(size) { var values = []; for (var i = 0; i < size; i++) { values.push(this.popValue()); } this.pushValue(values); }; JavaScriptCompiler.prototype.prepareObject = function prepareObject(size) { false && assert(this.values.length >= size, 'Expected ' + size + ' values on the stack, found ' + this.values.length); var keys = new Array(size); var values = new Array(size); for (var i = 0; i < size; i++) { keys[i] = this.popValue(); values[i] = this.popValue(); } this.pushValue([keys, values]); }; /// Utilities JavaScriptCompiler.prototype.endComponent = function endComponent() { var component = this.blocks.pop(); false && assert(component instanceof ComponentBlock, 'Compiler bug: endComponent() should end a component'); return component.toJSON(); }; JavaScriptCompiler.prototype.startInlineBlock = function startInlineBlock(symbols) { var block = new InlineBlock(symbols); this.blocks.push(block); }; JavaScriptCompiler.prototype.endInlineBlock = function endInlineBlock() { var blocks = this.blocks; var block = blocks.pop(); return block.toJSON(); }; JavaScriptCompiler.prototype.push = function push(args) { this.currentBlock.push(args); }; JavaScriptCompiler.prototype.pushValue = function pushValue(val) { this.values.push(val); this.locationStack.push(this.location); }; JavaScriptCompiler.prototype.popLocatedValue = function popLocatedValue() { false && assert(this.values.length, 'No expression found on stack'); var value = this.values.pop(); var location = this.locationStack.pop(); if (location === undefined) { throw new Error('Unbalanced location push and pop'); } return { value: value, location: location }; }; JavaScriptCompiler.prototype.popValue = function popValue() { return this.popLocatedValue().value; }; _createClass(JavaScriptCompiler, [{ key: 'currentBlock', get: function get() { return this.blocks.current; } }, { key: 'currentComponent', get: function get() { var block = this.currentBlock; if (block instanceof ComponentBlock) { return block; } else { throw new Error('Expected ComponentBlock on stack, found ' + block.constructor.name); } } }]); return JavaScriptCompiler; }(); export default JavaScriptCompiler; function start(location) { if (location) { return location.start; } else { return -1; } } function end(location) { if (location) { return location.end - location.start; } else { return -1; } } //# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi4uLy4uLy4uLy4uL3BhY2thZ2VzL0BnbGltbWVyL2NvbXBpbGVyL2xpYi9qYXZhc2NyaXB0LWNvbXBpbGVyLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7Ozs7Ozs7Ozs7QUFBQSxTQUFBLE1BQUEsUUFBQSxlQUFBO0FBQ0EsU0FBQSxLQUFBLEVBQUEsT0FBQSxRQUFBLGVBQUE7QUFHQSxTQUFBLFVBQUEsRUFBQSxXQUFBLEVBQUEsY0FBQSxRQUFBLHNCQUFBO0FBc0JBLFdBQU0sS0FBTjtBQUFBLHFCQUFBO0FBQUE7O0FBQ1MsYUFBQSxVQUFBLEdBQUEsRUFBQTtBQU9SOztBQVJELG9CQUtFLElBTEYsaUJBS0UsU0FMRixFQUtzQztBQUNsQyxhQUFBLFVBQUEsQ0FBQSxJQUFBLENBQUEsU0FBQTtBQUNELEtBUEg7O0FBQUE7QUFBQTtBQVVBLFdBQU0sV0FBTjtBQUFBOztBQUNFLHlCQUFBLEtBQUEsRUFBMEM7QUFBQTs7QUFBQSxxREFDeEMsaUJBRHdDOztBQUF2QixjQUFBLEtBQUEsR0FBQSxLQUFBO0FBQXVCO0FBRXpDOztBQUhILDBCQUtFLE1BTEYscUJBS1E7QUFDSixlQUFPO0FBQ0wsd0JBQVksS0FEUCxVQUFBO0FBRUwsd0JBQVksS0FBQSxLQUFBLENBQVc7QUFGbEIsU0FBUDtBQUlELEtBVkg7O0FBQUE7QUFBQSxFQUFNLEtBQU47QUFhQSxXQUFNLFVBQU47QUFBQTs7QUFDRSx3QkFBQSxJQUFBLEVBQUEsS0FBQSxFQUF3RDtBQUFBOztBQUFBLHNEQUN0RCx3QkFBQSxLQUFBLENBRHNEOztBQUFyQyxlQUFBLElBQUEsR0FBQSxJQUFBO0FBQXFDO0FBRXZEOztBQUhIO0FBQUEsRUFBTSxXQUFOO0FBTUEsV0FBTSxhQUFOO0FBQUE7O0FBT0UsMkJBQUEsV0FBQSxFQUFtRDtBQUFBOztBQUFBLHNEQUNqRCxrQkFEaUQ7O0FBQS9CLGVBQUEsV0FBQSxHQUFBLFdBQUE7QUFOYixlQUFBLElBQUEsR0FBQSxVQUFBO0FBQ0EsZUFBQSxNQUFBLEdB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IGZyb20gJ0BnbGltbWVyL3V0aWwnO1xuaW1wb3J0IHsgU3RhY2ssIERpY3RTZXQsIE9wdGlvbiwgZXhwZWN0IH0gZnJvbSAnQGdsaW1tZXIvdXRpbCc7XG5pbXBvcnQgeyBBU1QgfSBmcm9tICdAZ2xpbW1lci9zeW50YXgnO1xuaW1wb3J0IHsgQ29tcGlsZU9wdGlvbnMgfSBmcm9tICcuL3RlbXBsYXRlLWNvbXBpbGVyJztcbmltcG9ydCB7IGlzQXJndW1lbnQsIGlzQXR0cmlidXRlLCBpc0ZsdXNoRWxlbWVudCB9IGZyb20gJ0BnbGltbWVyL3dpcmUtZm9ybWF0JztcbmltcG9ydCB7IFByb2Nlc3NvciwgSmF2YVNjcmlwdENvbXBpbGVyT3BzLCBPcHMsIFNvdXJjZUxvY2F0aW9uIH0gZnJvbSAnLi9jb21waWxlci1vcHMnO1xuaW1wb3J0IHtcbiAgV2lyZUZvcm1hdCxcbiAgU2VyaWFsaXplZElubGluZUJsb2NrLFxuICBTdGF0ZW1lbnQsXG4gIFNlcmlhbGl6ZWRUZW1wbGF0ZUJsb2NrLFxuICBTdGF0ZW1lbnRzLFxuICBTZXhwT3Bjb2RlcyxcbiAgRXhwcmVzc2lvbixcbiAgRXhwcmVzc2lvbnMsXG4gIEV4cHJlc3Npb25Db250ZXh0LFxufSBmcm9tICdAZ2xpbW1lci9pbnRlcmZhY2VzJztcblxuZXhwb3J0IHR5cGUgc3RyID0gc3RyaW5nO1xuaW1wb3J0IENvcmUgPSBXaXJlRm9ybWF0LkNvcmU7XG5leHBvcnQgdHlwZSBQYXJhbXMgPSBXaXJlRm9ybWF0LkNvcmUuUGFyYW1zO1xuZXhwb3J0IHR5cGUgQ29uY2F0UGFyYW1zID0gV2lyZUZvcm1hdC5Db3JlLkNvbmNhdFBhcmFtcztcbmV4cG9ydCB0eXBlIEhhc2ggPSBXaXJlRm9ybWF0LkNvcmUuSGFzaDtcbmV4cG9ydCB0eXBlIFBhdGggPSBXaXJlRm9ybWF0LkNvcmUuUGF0aDtcbmV4cG9ydCB0eXBlIFN0YWNrVmFsdWUgPSBXaXJlRm9ybWF0LkV4cHJlc3Npb24gfCBQYXJhbXMgfCBIYXNoIHwgc3RyO1xuXG5leHBvcnQgYWJzdHJhY3QgY2xhc3MgQmxvY2sge1xuICBwdWJsaWMgc3RhdGVtZW50czogV2lyZUZvcm1hdC5TdGF0ZW1lbnRbXSA9IFtdO1xuXG4gIGFic3RyYWN0IHRvSlNPTigpOiBPYmplY3Q7XG5cbiAgcHVzaChzdGF0ZW1lbnQ6IFdpcmVGb3JtYXQuU3RhdGVtZW50KSB7XG4gICAgdGhpcy5zdGF0ZW1lbnRzLnB1c2goc3RhdGVtZW50KTtcbiAgfVxufVxuXG5leHBvcnQgY2xhc3MgSW5saW5lQmxvY2sgZXh0ZW5kcyBCbG9jayB7XG4gIGNvbnN0cnVjdG9yKHB1YmxpYyB0YWJsZTogQVNULkJsb2NrU3ltYm9scykge1xuICAgIHN1cGVyKCk7XG4gIH1cblxuICB0b0pTT04oKTogU2VyaWFsaXplZElubGluZUJsb2NrIHtcbiAgICByZXR1cm4ge1xuICAgICAgc3RhdGVtZW50czogdGhpcy5zdGF0ZW1lbnRzLFxuICAgICAgcGFyYW1ldGVyczogdGhpcy50YWJsZS5zbG90cyxcbiAgICB9O1xuICB9XG59XG5cbmV4cG9ydCBjbGFzcyBOYW1lZEJsb2NrIGV4dGVuZHMgSW5saW5lQmxvY2sge1xuICBjb25zdHJ1Y3RvcihwdWJsaWMgbmFtZTogc3RyaW5nLCB0YWJsZTogQVNULkJsb2NrU3ltYm9scykge1xuICAgIHN1cGVyKHRhYmxlKTtcbiAgfVxufVxuXG5leHBvcnQgY2xhc3MgVGVtcGxhdGVCbG9jayBleHRlbmRzIEJsb2NrIHtcbiAgcHVibGljIHR5cGUgPSAndGVtcGxhdGUnO1xuICBwdWJsaWMgeWllbGRzID0gbmV3IERpY3RTZXQ8c3RyaW5nPigpO1xuICBwdWJsaWMgbmFtZWQgPSBuZXcgRGljdFNldDxzdHJpbmc+KCk7XG4gIHB1YmxpYyBibG9ja3M6IFNlcmlhbGl6ZWRJbmxpbmVCbG9ja1tdID0gW107XG4gIHB1YmxpYyBoYXNFdmFsID0gZmFsc2U7XG5cbiAgY29uc3RydWN0b3IocHJpdmF0ZSBzeW1ib2xUYWJsZTogQVNULlByb2dyYW1TeW1ib2xzKSB7XG4gICAgc3VwZXIoKTtcbiAgfVxuXG4gIHB1c2goc3RhdGVtZW50OiBTdGF0ZW1lbnQpIHtcbiAgICB0aGlzLnN0YXRlbWVudHMucHVzaChzdGF0ZW1lbnQpO1xuICB9XG5cbiAgdG9KU09OKCk6IFNlcmlhbGl6ZWRUZW1wbGF0ZUJsb2NrIHtcbiAgICByZXR1cm4ge1xuICAgICAgc3ltYm9sczogdGhpcy5zeW1ib2xUYWJsZS5zeW1ib2xzLFxuICAgICAgc3RhdGVtZW50czogdGhpcy5zdGF0ZW1lbnRzLFxuICAgICAgaGFzRXZhbDogdGhpcy5oYXNFdmFsLFxuICAgICAgdXB2YXJzOiB0aGlzLnN5bWJvbFRhYmxlLmZyZWVWYXJpYWJsZXMsXG4gICAgfTtcbiAgfVxufVxuXG5leHBvcnQgY2xhc3MgQ29tcG9uZW50QmxvY2sgZXh0ZW5kcyBCbG9jayB7XG4gIHB1YmxpYyBhdHRyaWJ1dGVzOiBTdGF0ZW1lbnRzLkF0dHJpYnV0ZVtdID0gW107XG4gIHB1YmxpYyBhcmd1bWVudHM6IFN0YXRlbWVudHMuQXJndW1lbnRbXSA9IFtdO1xuICBwcml2YXRlIGluUGFyYW1zID0gdHJ1ZTtcbiAgcHVibGljIHBvc2l0aW9uYWxzOiBudW1iZXJbXSA9IFtdO1xuICBwdWJsaWMgYmxvY2tzOiBBcnJheTxbc3RyaW5nLCBTZXJpYWxpemVkSW5saW5lQmxvY2tdPiA9IFtdO1xuXG4gIGNvbnN0cnVjdG9yKHByaXZhdGUgdGFnOiBzdHJpbmcsIHByaXZhdGUgdGFibGU6IEFTVC5CbG9ja1N5bWJvbHMsIHByaXZhdGUgc2VsZkNsb3Npbmc6IGJvb2xlYW4pIHtcbiAgICBzdXBlcigpO1xuICB9XG5cbiAgcHVzaChzdGF0ZW1lbnQ6IFN0YXRlbWVudCkge1xuICAgIGlmICh0aGlzLmluUGFyYW1zKSB7XG4gICAgICBpZiAoaXNGbHVzaEVsZW1lbnQoc3RhdGVtZW50KSkge1xuICAgICAgICB0aGlzLmluUGFyYW1zID0gZmFsc2U7XG4gICAgICB9IGVsc2UgaWYgKGlzQXJndW1lbnQoc3RhdGVtZW50KSkge1xuICAgICAgICB0aGlzLmFyZ3VtZW50cy5wdXNoKHN0YXRlbWVudCk7XG4gICAgICB9IGVsc2UgaWYgKGlzQXR0cmlidXRlKHN0YXRlbWVudCkpIHtcbiAgICAgICAgdGhpcy5hdHRyaWJ1dGVzLnB1c2goc3RhdGVtZW50KTtcbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIHRocm93IG5ldyBFcnJvcignQ29tcGlsZSBFcnJvcjogb25seSBwYXJhbWV0ZXJzIGFsbG93ZWQgYmVmb3JlIGZsdXNoLWVsZW1lbnQnKTtcbiAgICAgIH1cbiAgICB9IGVsc2Uge1xuICAgICAgdGhpcy5zdGF0ZW1lbnRzLnB1c2goc3RhdGVtZW50KTtcbiAgICB9XG4gIH1cblxuICBwdXNoQmxvY2sobmFtZTogc3RyaW5nLCBibG9jazogU2VyaWFsaXplZElubGluZUJsb2NrKSB7XG4gICAgdGhpcy5ibG9ja3MucHVzaChbbmFtZSwgYmxvY2tdKTtcbiAgfVxuXG4gIHRvSlNPTigpOiBbc3RyaW5nLCBTdGF0ZW1lbnRzLkF0dHJpYnV0ZVtdLCBDb3JlLkhhc2gsIENvcmUuQmxvY2tzXSB7XG4gICAgbGV0IGJsb2NrczogQ29yZS5CbG9ja3M7XG4gICAgbGV0IGFyZ3MgPSB0aGlzLmFyZ3VtZW50cztcbiAgICBsZXQga2V5cyA9IGFyZ3MubWFwKGFyZyA9PiBhcmdbMV0pO1xuICAgIGxldCB2YWx1ZXMgPSBhcmdzLm1hcChhcmcgPT4gYXJnWzJdKTtcblxuICAgIGlmICh0aGlzLnNlbGZDbG9zaW5nKSB7XG4gICAgICBibG9ja3MgPSBudWxsO1xuICAgIH0gZWxzZSBpZiAodGhpcy5ibG9ja3MubGVuZ3RoID4gMCkge1xuICAgICAgbGV0IGtleXM6IHN0cmluZ1tdID0gW107XG4gICAgICBsZXQgdmFsdWVzOiBTZXJpYWxpemVkSW5saW5lQmxvY2tbXSA9IFtdO1xuXG4gICAgICBmb3IgKGxldCBpID0gMDsgaSA8IHRoaXMuYmxvY2tzLmxlbmd0aDsgaSsrKSB7XG4gICAgICAgIGxldCBba2V5LCB2YWx1ZV0gPSB0aGlzLmJsb2Nrc1tpXTtcbiAgICAgICAga2V5cy5wdXNoKGtleS5zbGljZSgxKSk7XG4gICAgICAgIHZhbHVlcy5wdXNoKHZhbHVlKTtcbiAgICAgIH1cbiAgICAgIGJsb2NrcyA9IFtrZXlzLCB2YWx1ZXNdO1xuICAgIH0gZWxzZSB7XG4gICAgICBibG9ja3MgPSBbXG4gICAgICAgIFsnZGVmYXVsdCddLFxuICAgICAgICBbXG4gICAgICAgICAge1xuICAgICAgICAgICAgc3RhdGVtZW50czogdGhpcy5zdGF0ZW1lbnRzLFxuICAgICAgICAgICAgcGFyYW1ldGVyczogdGhpcy50YWJsZS5zbG90cyxcbiAgICAgICAgICB9LFxuICAgICAgICBdLFxuICAgICAgXTtcbiAgICB9XG5cbiAgICByZXR1cm4gW3RoaXMudGFnLCB0aGlzLmF0dHJpYnV0ZXMsIFtrZXlzLCB2YWx1ZXNdLCBibG9ja3NdO1xuICB9XG59XG5cbmV4cG9ydCBjbGFzcyBUZW1wbGF0ZSB7XG4gIHB1YmxpYyBibG9jazogVGVtcGxhdGVCbG9jaztcblxuICBjb25zdHJ1Y3RvcihzeW1ib2xzOiBBU1QuUHJvZ3JhbVN5bWJvbHMpIHtcbiAgICB0aGlzLmJsb2NrID0gbmV3IFRlbXBsYXRlQmxvY2soc3ltYm9scyk7XG4gIH1cblxuICB0b0pTT04oKTogU2VyaWFsaXplZFRlbXBsYXRlQmxvY2sge1xuICAgIHJldHVybiB0aGlzLmJsb2NrLnRvSlNPTigpO1xuICB9XG59XG5cbnR5cGUgSW5wdXQgPSByZWFkb25seSBPcHM8SmF2YVNjcmlwdENvbXBpbGVyT3BzPltdO1xuXG5leHBvcnQgZGVmYXVsdCBjbGFzcyBKYXZhU2NyaXB0Q29tcGlsZXIgaW1wbGVtZW50cyBQcm9jZXNzb3I8SmF2YVNjcmlwdENvbXBpbGVyT3BzPiB7XG4gIHN0YXRpYyBwcm9jZXNzKFxuICAgIG9wY29kZXM6IElucHV0LFxuICAgIGxvY2F0aW9uczogcmVhZG9ubHkgT3B0aW9uPFNvdXJjZUxvY2F0aW9uPltdLFxuICAgIHN5bWJvbHM6IEFTVC5Qcm9ncmFtU3ltYm9scyxcbiAgICBvcHRpb25zPzogQ29tcGlsZU9wdGlvbnNcbiAgKTogVGVtcGxhdGUge1xuICAgIGxldCBjb21waWxlciA9IG5ldyBKYXZhU2NyaXB0Q29tcGlsZXIob3Bjb2Rlcywgc3ltYm9scywgbG9jYXRpb25zLCBvcHRpb25zKTtcbiAgICByZXR1cm4gY29tcGlsZXIucHJvY2VzcygpO1xuICB9XG5cbiAgcHJpdmF0ZSByZWFkb25seSB0ZW1wbGF0ZTogVGVtcGxhdGU7XG4gIHByaXZhdGUgcmVhZG9ubHkgYmxvY2tzID0gbmV3IFN0YWNrPEJsb2NrPigpO1xuICBwcml2YXRlIHJlYWRvbmx5IG9wY29kZXM6IHJlYWRvbmx5IE9wczxKYXZhU2NyaXB0Q29tcGlsZXJPcHM+W107XG4gIHByaXZhdGUgcmVhZG9ubHkgdmFsdWVzOiBTdGFja1ZhbHVlW10gPSBbXTtcbiAgcHJpdmF0ZSByZWFkb25seSBvcHRpb25zOiBDb21waWxlT3B0aW9ucyB8IHVuZGVmaW5lZDtcbiAgcHJpdmF0ZSBsb2NhdGlvbjogT3B0aW9uPFNvdXJjZUxvY2F0aW9uPiA9IG51bGw7XG4gIHByaXZhdGUgbG9jYXRpb25TdGFjazogT3B0aW9uPFNvdXJjZUxvY2F0aW9uPltdID0gW107XG5cbiAgY29uc3RydWN0b3IoXG4gICAgb3Bjb2RlczogSW5wdXQsXG4gICAgc3ltYm9sczogQVNULlByb2dyYW1TeW1ib2xzLFxuICAgIHByaXZhdGUgbG9jYXRpb25zOiByZWFkb25seSBPcHRpb248U291cmNlTG9jYXRpb24+W10sXG4gICAgb3B0aW9ucz86IENvbXBpbGVPcHRpb25zXG4gICkge1xuICAgIHRoaXMub3Bjb2RlcyA9IG9wY29kZXM7XG4gICAgdGhpcy50ZW1wbGF0ZSA9IG5ldyBUZW1wbGF0ZShzeW1ib2xzKTtcbiAgICB0aGlzLm9wdGlvbnMgPSBvcHRpb25zO1xuICB9XG5cbiAgZ2V0IGN1cnJlbnRCbG9jaygpOiBCbG9jayB7XG4gICAgcmV0dXJuIGV4cGVjdCh0aGlzLmJsb2Nrcy5jdXJyZW50LCAnRXhwZWN0ZWQgYSBibG9jayBvbiB0aGUgc3RhY2snKTtcbiAgfVxuXG4gIGdldCBjdXJyZW50Q29tcG9uZW50KCk6IENvbXBvbmVudEJsb2NrIHtcbiAgICBsZXQgYmxvY2sgPSB0aGlzLmN1cnJlbnRCbG9jaztcblxuICAgIGlmIChibG9jayBpbnN0YW5jZW9mIENvbXBvbmVudEJsb2NrKSB7XG4gICAgICByZXR1cm4gYmxvY2s7XG4gICAgfSBlbHNlIHtcbiAgICAgIHRocm93IG5ldyBFcnJvcihgRXhwZWN0ZWQgQ29tcG9uZW50QmxvY2sgb24gc3RhY2ssIGZvdW5kICR7YmxvY2suY29uc3RydWN0b3IubmFtZX1gKTtcbiAgICB9XG4gIH1cblxuICBwcm9jZXNzKCk6IFRlbXBsYXRlIHtcbiAgICB0aGlzLm9wY29kZXMuZm9yRWFjaCgob3AsIGkpID0+IHtcbiAgICAgIGxldCBvcGNvZGUgPSBvcFswXTtcbiAgICAgIHRoaXMubG9jYXRpb24gPSB0aGlzLmxvY2F0aW9uc1tpXTtcblxuICAgICAgbGV0IGFyZyA9IG9wWzFdO1xuXG4gICAgICBpZiAoIXRoaXNbb3Bjb2RlXSkge1xuICAgICAgICB0aHJvdyBuZXcgRXJyb3IoYHVuaW1wbGVtZW50ZWQgJHtvcGNvZGV9IG9uIEphdmFTY3JpcHRDb21waWxlcmApO1xuICAgICAgfVxuICAgICAgKHRoaXNbb3Bjb2RlXSBhcyBhbnkpKGFyZyk7XG4gICAgfSk7XG4gICAgcmV0dXJuIHRoaXMudGVtcGxhdGU7XG4gIH1cblxuICAvLy8gTmVzdGluZ1xuXG4gIHN0YXJ0QmxvY2socHJvZ3JhbTogQVNULkJsb2NrKSB7XG4gICAgdGhpcy5zdGFydElubGluZUJsb2NrKHByb2dyYW0uc3ltYm9scyEpO1xuICB9XG5cbiAgZW5kQmxvY2soKSB7XG4gICAgbGV0IGJsb2NrID0gdGhpcy5lbmRJbmxpbmVCbG9jaygpO1xuICAgIHRoaXMudGVtcGxhdGUuYmxvY2suYmxvY2tzLnB1c2goYmxvY2spO1xuICB9XG5cbiAgc3RhcnRQcm9ncmFtKCkge1xuICAgIHRoaXMuYmxvY2tzLnB1c2godGhpcy50ZW1wbGF0ZS5ibG9jayk7XG4gIH1cblxuICBlbmRQcm9ncmFtKCkge31cblxuICAvLy8gU3RhdGVtZW50c1xuXG4gIHRleHQoY29udGVudDogc3RyaW5nKSB7XG4gICAgdGhpcy5wdXNoKFtTZXhwT3Bjb2Rlcy5BcHBlbmQsIDEsIDAsIDAsIGNvbnRlbnRdKTtcbiAgfVxuXG4gIGFwcGVuZCh0cnVzdGVkOiBib29sZWFuKSB7XG4gICAgdGhpcy5wdXNoKFtTZXhwT3Bjb2Rlcy5BcHBlbmQsICt0cnVzdGVkLCAwLCAwLCB0aGlzLnBvcFZhbHVlPEV4cHJlc3Npb24+KCldKTtcbiAgfVxuXG4gIGNvbW1lbnQodmFsdWU6IHN0cmluZykge1xuICAgIHRoaXMucHVzaChbU2V4cE9wY29kZXMuQ29tbWVudCwgdmFsdWVdKTtcbiAgfVxuXG4gIG1vZGlmaWVyKCkge1xuICAgIGxldCBuYW1lID0gdGhpcy5wb3BWYWx1ZTxFeHByZXNzaW9uPigpO1xuICAgIGxldCBwYXJhbXMgPSB0aGlzLnBvcFZhbHVlPFBhcmFtcz4oKTtcbiAgICBsZXQgaGFzaCA9IHRoaXMucG9wVmFsdWU8SGFzaD4oKTtcbiAgICB0aGlzLnB1c2goW1NleHBPcGNvZGVzLk1vZGlmaWVyLCAwLCAwLCBuYW1lLCBwYXJhbXMsIGhhc2hdKTtcbiAgfVxuXG4gIGJsb2NrKFt0ZW1wbGF0ZSwgaW52ZXJzZV06IFtudW1iZXIsIE9wdGlvbjxudW1iZXI+XSkge1xuICAgIGxldCBoZWFkID0gdGhpcy5wb3BWYWx1ZTxFeHByZXNzaW9uPigpO1xuICAgIGxldCBwYXJhbXMgPSB0aGlzLnBvcFZhbHVlPFBhcmFtcz4oKTtcbiAgICBsZXQgaGFzaCA9IHRoaXMucG9wVmFsdWU8SGFzaD4oKTtcblxuICAgIGxldCBibG9ja3MgPSB0aGlzLnRlbXBsYXRlLmJsb2NrLmJsb2NrcztcbiAgICBhc3NlcnQoXG4gICAgICB0eXBlb2YgdGVtcGxhdGUgIT09ICdudW1iZXInIHx8IGJsb2Nrc1t0ZW1wbGF0ZV0gIT09IG51bGwsXG4gICAgICAnbWlzc2luZyBibG9jayBpbiB0aGUgY29tcGlsZXInXG4gICAgKTtcbiAgICBhc3NlcnQoXG4gICAgICB0eXBlb2YgaW52ZXJzZSAhPT0gJ251bWJlcicgfHwgYmxvY2tzW2ludmVyc2VdICE9PSBudWxsLFxuICAgICAgJ21pc3NpbmcgYmxvY2sgaW4gdGhlIGNvbXBpbGVyJ1xuICAgICk7XG5cbiAgICBsZXQgbmFtZWRCbG9ja3M6IE9wdGlvbjxDb3JlLkJsb2Nrcz47XG5cbiAgICBpZiAodGVtcGxhdGUgPT09IG51bGwgJiYgaW52ZXJzZSA9PT0gbnVsbCkge1xuICAgICAgbmFtZWRCbG9ja3MgPSBudWxsO1xuICAgIH0gZWxzZSBpZiAoaW52ZXJzZSA9PT0gbnVsbCkge1xuICAgICAgbmFtZWRCbG9ja3MgPSBbWydkZWZhdWx0J10sIFtibG9ja3NbdGVtcGxhdGVdXV07XG4gICAgfSBlbHNlIHtcbiAgICAgIG5hbWVkQmxvY2tzID0gW1snZGVmYXVsdCcsICdlbHNlJ10sIFtibG9ja3NbdGVtcGxhdGVdLCBibG9ja3NbaW52ZXJzZV1dXTtcbiAgICB9XG5cbiAgICAvLyBhc3NlcnQoaGVhZFtdKTtcblxuICAgIHRoaXMucHVzaChbU2V4cE9wY29kZXMuQmxvY2ssIGhlYWQsIHBhcmFtcywgaGFzaCwgbmFtZWRCbG9ja3NdKTtcbiAgfVxuXG4gIG9wZW5Db21wb25lbnQoZWxlbWVudDogQVNULkVsZW1lbnROb2RlKSB7XG4gICAgbGV0IHRhZyA9XG4gICAgICB0aGlzLm9wdGlvbnMgJiYgdGhpcy5vcHRpb25zLmN1c3RvbWl6ZUNvbXBvbmVudE5hbWVcbiAgICAgICAgPyB0aGlzLm9wdGlvbnMuY3VzdG9taXplQ29tcG9uZW50TmFtZShlbGVtZW50LnRhZylcbiAgICAgICAgOiBlbGVtZW50LnRhZztcbiAgICBsZXQgY29tcG9uZW50ID0gbmV3IENvbXBvbmVudEJsb2NrKHRhZywgZWxlbWVudC5zeW1ib2xzISwgZWxlbWVudC5zZWxmQ2xvc2luZyk7XG4gICAgdGhpcy5ibG9ja3MucHVzaChjb21wb25lbnQpO1xuICB9XG5cbiAgb3Blbk5hbWVkQmxvY2soZWxlbWVudDogQVNULkVsZW1lbnROb2RlKSB7XG4gICAgbGV0IGJsb2NrOiBCbG9jayA9IG5ldyBOYW1lZEJsb2NrKGVsZW1lbnQudGFnLCBlbGVtZW50LnN5bWJvbHMhKTtcbiAgICB0aGlzLmJsb2Nrcy5wdXNoKGJsb2NrKTtcbiAgfVxuXG4gIG9wZW5FbGVtZW50KFtlbGVtZW50LCBzaW1wbGVdOiBbQVNULkVsZW1lbnROb2RlLCBib29sZWFuXSkge1xuICAgIGxldCB0YWcgPSBlbGVtZW50LnRhZztcblxuICAgIGlmIChlbGVtZW50LmJsb2NrUGFyYW1zLmxlbmd0aCA+IDApIHtcbiAgICAgIHRocm93IG5ldyBFcnJvcihcbiAgICAgICAgYENvbXBpbGUgRXJyb3I6IDwke2VsZW1lbnQudGFnfT4gaXMgbm90IGEgY29tcG9uZW50IGFuZCBkb2Vzbid0IHN1cHBvcnQgYmxvY2sgcGFyYW1ldGVyc2BcbiAgICAgICk7XG4gICAgfSBlbHNlIHtcbiAgICAgIHRoaXMucHVzaChbU2V4cE9wY29kZXMuT3BlbkVsZW1lbnQsIHRhZywgc2ltcGxlXSk7XG4gICAgfVxuICB9XG5cbiAgZmx1c2hFbGVtZW50KCkge1xuICAgIHRoaXMucHVzaChbU2V4cE9wY29kZXMuRmx1c2hFbGVtZW50XSk7XG4gIH1cblxuICBjbG9zZUNvbXBvbmVudChfZWxlbWVudDogQVNULkVsZW1lbnROb2RlKSB7XG4gICAgbGV0IFt0YWcsIGF0dHJzLCBhcmdzLCBibG9ja3NdID0gdGhpcy5lbmRDb21wb25lbnQoKTtcblxuICAgIHRoaXMucHVzaChbU2V4cE9wY29kZXMuQ29tcG9uZW50LCB0YWcsIGF0dHJzLCBhcmdzLCBibG9ja3NdKTtcbiAgfVxuXG4gIGNsb3NlTmFtZWRCbG9jayhfZWxlbWVudDogQVNULkVsZW1lbnROb2RlKSB7XG4gICAgbGV0IHsgYmxvY2tzIH0gPSB0aGlzO1xuICAgIGxldCBibG9jayA9IGV4cGVjdChibG9ja3MucG9wKCksIGBFeHBlY3RlZCBhIG5hbWVkIGJsb2NrIG9uIHRoZSBzdGFja2ApIGFzIE5hbWVkQmxvY2s7XG5cbiAgICB0aGlzLmN1cnJlbnRDb21wb25lbnQucHVzaEJsb2NrKGJsb2NrLm5hbWUsIGJsb2NrLnRvSlNPTigpKTtcbiAgfVxuXG4gIGNsb3NlRHluYW1pY0NvbXBvbmVudChfZWxlbWVudDogQVNULkVsZW1lbnROb2RlKSB7XG4gICAgbGV0IFssIGF0dHJzLCBhcmdzLCBibG9ja10gPSB0aGlzLmVuZENvbXBvbmVudCgpO1xuXG4gICAgdGhpcy5wdXNoKFtTZXhwT3Bjb2Rlcy5Db21wb25lbnQsIHRoaXMucG9wVmFsdWU8RXhwcmVzc2lvbj4oKSwgYXR0cnMsIGFyZ3MsIGJsb2NrXSk7XG4gIH1cblxuICBjbG9zZUVsZW1lbnQoX2VsZW1lbnQ6IEFTVC5FbGVtZW50Tm9kZSkge1xuICAgIHRoaXMucHVzaChbU2V4cE9wY29kZXMuQ2xvc2VFbGVtZW50XSk7XG4gIH1cblxuICBzdGF0aWNBdHRyKFtuYW1lLCBuYW1lc3BhY2VdOiBbc3RyaW5nLCBPcHRpb248c3RyaW5nPl0pIHtcbiAgICBsZXQgdmFsdWUgPSB0aGlzLnBvcFZhbHVlPHN0cmluZz4oKTtcbiAgICB0aGlzLnB1c2goW1NleHBPcGNvZGVzLlN0YXRpY0F0dHIsIG5hbWUsIHZhbHVlLCBuYW1lc3BhY2VdKTtcbiAgfVxuXG4gIGR5bmFtaWNBdHRyKFtuYW1lLCBuYW1lc3BhY2VdOiBbc3RyaW5nLCBPcHRpb248c3RyaW5nPl0pIHtcbiAgICBsZXQgdmFsdWUgPSB0aGlzLnBvcFZhbHVlPEV4cHJlc3Npb24+KCk7XG4gICAgdGhpcy5wdXNoKFtTZXhwT3Bjb2Rlcy5EeW5hbWljQXR0ciwgbmFtZSwgdmFsdWUsIG5hbWVzcGFjZV0pO1xuICB9XG5cbiAgY29tcG9uZW50QXR0cihbbmFtZSwgbmFtZXNwYWNlXTogW3N0cmluZywgT3B0aW9uPHN0cmluZz5dKSB7XG4gICAgbGV0IHZhbHVlID0gdGhpcy5wb3BWYWx1ZTxFeHByZXNzaW9uPigpO1xuICAgIHRoaXMucHVzaChbU2V4cE9wY29kZXMuQ29tcG9uZW50QXR0ciwgbmFtZSwgdmFsdWUsIG5hbWVzcGFjZV0pO1xuICB9XG5cbiAgdHJ1c3RpbmdBdHRyKFtuYW1lLCBuYW1lc3BhY2VdOiBbc3RyaW5nLCBPcHRpb248c3RyaW5nPl0pIHtcbiAgICBsZXQgdmFsdWUgPSB0aGlzLnBvcFZhbHVlPEV4cHJlc3Npb24+KCk7XG4gICAgdGhpcy5wdXNoKFtTZXhwT3Bjb2Rlcy5UcnVzdGluZ0R5bmFtaWNBdHRyLCBuYW1lLCB2YWx1ZSwgbmFtZXNwYWNlIV0pO1xuICB9XG5cbiAgdHJ1c3RpbmdDb21wb25lbnRBdHRyKFtuYW1lLCBuYW1lc3BhY2VdOiBbc3RyaW5nLCBPcHRpb248c3RyaW5nPl0pIHtcbiAgICBsZXQgdmFsdWUgPSB0aGlzLnBvcFZhbHVlPEV4cHJlc3Npb24+KCk7XG4gICAgdGhpcy5wdXNoKFtTZXhwT3Bjb2Rlcy5UcnVzdGluZ0NvbXBvbmVudEF0dHIsIG5hbWUsIHZhbHVlLCBuYW1lc3BhY2UhXSk7XG4gIH1cblxuICBzdGF0aWNBcmcobmFtZTogc3RyKSB7XG4gICAgbGV0IHZhbHVlID0gdGhpcy5wb3BWYWx1ZTxFeHByZXNzaW9uPigpO1xuICAgIHRoaXMucHVzaChbU2V4cE9wY29kZXMuU3RhdGljQXJnLCBuYW1lLCB2YWx1ZV0pO1xuICB9XG5cbiAgZHluYW1pY0FyZyhuYW1lOiBzdHIpIHtcbiAgICBsZXQgdmFsdWUgPSB0aGlzLnBvcFZhbHVlPEV4cHJlc3Npb24+KCk7XG4gICAgdGhpcy5wdXNoKFtTZXhwT3Bjb2Rlcy5EeW5hbWljQXJnLCBuYW1lLCB2YWx1ZV0pO1xuICB9XG5cbiAgeWllbGQodG86IG51bWJlcikge1xuICAgIGxldCBwYXJhbXMgPSB0aGlzLnBvcFZhbHVlPFBhcmFtcz4oKTtcbiAgICB0aGlzLnB1c2goW1NleHBPcGNvZGVzLllpZWxkLCB0bywgcGFyYW1zXSk7XG4gIH1cblxuICBhdHRyU3BsYXQodG86IE9wdGlvbjxudW1iZXI+KSB7XG4gICAgLy8gY29uc3VtZSAoYW5kIGRpc3JlZ2FyZCkgdGhlIHZhbHVlIHB1c2hlZCBmb3IgdGhlXG4gICAgLy8gLi4uYXR0cmlidXRlcyBhdHRyaWJ1dGVcbiAgICB0aGlzLnBvcFZhbHVlKCk7XG4gICAgdGhpcy5wdXNoKFtTZXhwT3Bjb2Rlcy5BdHRyU3BsYXQsIHRvIV0pO1xuICB9XG5cbiAgZGVidWdnZXIoZXZhbEluZm86IE9wdGlvbjxDb3JlLkV2YWxJbmZvPikge1xuICAgIHRoaXMucHVzaChbU2V4cE9wY29kZXMuRGVidWdnZXIsIGV2YWxJbmZvIV0pO1xuICAgIHRoaXMudGVtcGxhdGUuYmxvY2suaGFzRXZhbCA9IHRydWU7XG4gIH1cblxuICBoYXNCbG9jayhuYW1lOiBudW1iZXIpIHtcbiAgICB0aGlzLnB1c2hWYWx1ZTxFeHByZXNzaW9ucy5IYXNCbG9jaz4oW1NleHBPcGNvZGVzLkhhc0Jsb2NrLCBbU2V4cE9wY29kZXMuR2V0U3ltYm9sLCBuYW1lXV0pO1xuICB9XG5cbiAgaGFzQmxvY2tQYXJhbXMobmFtZTogbnVtYmVyKSB7XG4gICAgdGhpcy5wdXNoVmFsdWU8RXhwcmVzc2lvbnMuSGFzQmxvY2tQYXJhbXM+KFtcbiAgICAgIFNleHBPc