Files
e-tib.com/.next/dev/server/vendor-chunks/@lexical+extension@0.41.0.js
Marc Mintel d14122005d Initial commit: E-TIB production hardening & E2E foundation
Former-commit-id: ef04fca3d76375630c05aac117bf586953f3b657
2026-04-28 19:11:38 +02:00

25 lines
159 KiB
JavaScript

"use strict";
/*
* ATTENTION: An "eval-source-map" devtool has been used.
* This devtool is neither made for production nor for readable output files.
* It uses "eval()" calls to create a separate source file with attached SourceMaps in the browser devtools.
* If you are trying to read the output file, select a different devtool (https://webpack.js.org/configuration/devtool/)
* or disable the default devtool with "devtool: false".
* If you are looking for production-ready output files, see mode: "production" (https://webpack.js.org/configuration/mode/).
*/
exports.id = "vendor-chunks/@lexical+extension@0.41.0";
exports.ids = ["vendor-chunks/@lexical+extension@0.41.0"];
exports.modules = {
/***/ "(rsc)/./node_modules/.pnpm/@lexical+extension@0.41.0/node_modules/@lexical/extension/LexicalExtension.dev.mjs":
/*!***************************************************************************************************************!*\
!*** ./node_modules/.pnpm/@lexical+extension@0.41.0/node_modules/@lexical/extension/LexicalExtension.dev.mjs ***!
\***************************************************************************************************************/
/***/ ((__unused_webpack___webpack_module__, __webpack_exports__, __webpack_require__) => {
eval("__webpack_require__.r(__webpack_exports__);\n/* harmony export */ __webpack_require__.d(__webpack_exports__, {\n/* harmony export */ $createHorizontalRuleNode: () => (/* binding */ $createHorizontalRuleNode),\n/* harmony export */ $isDecoratorTextNode: () => (/* binding */ $isDecoratorTextNode),\n/* harmony export */ $isHorizontalRuleNode: () => (/* binding */ $isHorizontalRuleNode),\n/* harmony export */ AutoFocusExtension: () => (/* binding */ AutoFocusExtension),\n/* harmony export */ ClearEditorExtension: () => (/* binding */ ClearEditorExtension),\n/* harmony export */ DecoratorTextExtension: () => (/* binding */ DecoratorTextExtension),\n/* harmony export */ DecoratorTextNode: () => (/* binding */ DecoratorTextNode),\n/* harmony export */ EditorStateExtension: () => (/* binding */ EditorStateExtension),\n/* harmony export */ HorizontalRuleExtension: () => (/* binding */ HorizontalRuleExtension),\n/* harmony export */ HorizontalRuleNode: () => (/* binding */ HorizontalRuleNode),\n/* harmony export */ INSERT_HORIZONTAL_RULE_COMMAND: () => (/* binding */ INSERT_HORIZONTAL_RULE_COMMAND),\n/* harmony export */ InitialStateExtension: () => (/* binding */ InitialStateExtension),\n/* harmony export */ LexicalBuilder: () => (/* binding */ LexicalBuilder),\n/* harmony export */ NodeSelectionExtension: () => (/* binding */ NodeSelectionExtension),\n/* harmony export */ TabIndentationExtension: () => (/* binding */ TabIndentationExtension),\n/* harmony export */ applyFormatFromStyle: () => (/* binding */ applyFormatFromStyle),\n/* harmony export */ applyFormatToDom: () => (/* binding */ applyFormatToDom),\n/* harmony export */ batch: () => (/* binding */ o),\n/* harmony export */ buildEditorFromExtensions: () => (/* binding */ buildEditorFromExtensions),\n/* harmony export */ computed: () => (/* binding */ w),\n/* harmony export */ configExtension: () => (/* reexport safe */ lexical__WEBPACK_IMPORTED_MODULE_0__.configExtension),\n/* harmony export */ declarePeerDependency: () => (/* reexport safe */ lexical__WEBPACK_IMPORTED_MODULE_0__.declarePeerDependency),\n/* harmony export */ defineExtension: () => (/* reexport safe */ lexical__WEBPACK_IMPORTED_MODULE_0__.defineExtension),\n/* harmony export */ effect: () => (/* binding */ E),\n/* harmony export */ getExtensionDependencyFromEditor: () => (/* binding */ getExtensionDependencyFromEditor),\n/* harmony export */ getKnownTypesAndNodes: () => (/* binding */ getKnownTypesAndNodes),\n/* harmony export */ getPeerDependencyFromEditor: () => (/* binding */ getPeerDependencyFromEditor),\n/* harmony export */ getPeerDependencyFromEditorOrThrow: () => (/* binding */ getPeerDependencyFromEditorOrThrow),\n/* harmony export */ namedSignals: () => (/* binding */ namedSignals),\n/* harmony export */ registerClearEditor: () => (/* binding */ registerClearEditor),\n/* harmony export */ registerTabIndentation: () => (/* binding */ registerTabIndentation),\n/* harmony export */ safeCast: () => (/* reexport safe */ lexical__WEBPACK_IMPORTED_MODULE_0__.safeCast),\n/* harmony export */ shallowMergeConfig: () => (/* reexport safe */ lexical__WEBPACK_IMPORTED_MODULE_0__.shallowMergeConfig),\n/* harmony export */ signal: () => (/* binding */ d),\n/* harmony export */ untracked: () => (/* binding */ h),\n/* harmony export */ watchedSignal: () => (/* binding */ watchedSignal)\n/* harmony export */ });\n/* harmony import */ var lexical__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! lexical */ \"(rsc)/./node_modules/.pnpm/lexical@0.41.0/node_modules/lexical/Lexical.dev.mjs\");\n/* harmony import */ var _lexical_utils__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! @lexical/utils */ \"(rsc)/./node_modules/.pnpm/@lexical+utils@0.41.0/node_modules/@lexical/utils/LexicalUtils.dev.mjs\");\n/**\n * Copyright (c) Meta Platforms, Inc. and affiliates.\n *\n * This source code is licensed under the MIT license found in the\n * LICENSE file in the root directory of this source tree.\n *\n */\n\n\n\n\n\nconst i=Symbol.for(\"preact-signals\");function t(){if(r>1){r--;return}let i,t=false;while(void 0!==s){let o=s;s=void 0;f++;while(void 0!==o){const n=o.o;o.o=void 0;o.f&=-3;if(!(8&o.f)&&v(o))try{o.c();}catch(o){if(!t){i=o;t=true;}}o=n;}}f=0;r--;if(t)throw i}function o(i){if(r>0)return i();r++;try{return i()}finally{t();}}let n,s;function h(i){const t=n;n=void 0;try{return i()}finally{n=t;}}let r=0,f=0,e=0;function u(i){if(void 0===n)return;let t=i.n;if(void 0===t||t.t!==n){t={i:0,S:i,p:n.s,n:void 0,t:n,e:void 0,x:void 0,r:t};if(void 0!==n.s)n.s.n=t;n.s=t;i.n=t;if(32&n.f)i.S(t);return t}else if(-1===t.i){t.i=0;if(void 0!==t.n){t.n.p=t.p;if(void 0!==t.p)t.p.n=t.n;t.p=n.s;t.n=void 0;n.s.n=t;n.s=t;}return t}}function c(i,t){this.v=i;this.i=0;this.n=void 0;this.t=void 0;this.W=null==t?void 0:t.watched;this.Z=null==t?void 0:t.unwatched;this.name=null==t?void 0:t.name;}c.prototype.brand=i;c.prototype.h=function(){return true};c.prototype.S=function(i){const t=this.t;if(t!==i&&void 0===i.e){i.x=t;this.t=i;if(void 0!==t)t.e=i;else h(()=>{var i;null==(i=this.W)||i.call(this);});}};c.prototype.U=function(i){if(void 0!==this.t){const t=i.e,o=i.x;if(void 0!==t){t.x=o;i.e=void 0;}if(void 0!==o){o.e=t;i.x=void 0;}if(i===this.t){this.t=o;if(void 0===o)h(()=>{var i;null==(i=this.Z)||i.call(this);});}}};c.prototype.subscribe=function(i){return E(()=>{const t=this.value,o=n;n=void 0;try{i(t);}finally{n=o;}},{name:\"sub\"})};c.prototype.valueOf=function(){return this.value};c.prototype.toString=function(){return this.value+\"\"};c.prototype.toJSON=function(){return this.value};c.prototype.peek=function(){const i=n;n=void 0;try{return this.value}finally{n=i;}};Object.defineProperty(c.prototype,\"value\",{get(){const i=u(this);if(void 0!==i)i.i=this.i;return this.v},set(i){if(i!==this.v){if(f>100)throw new Error(\"Cycle detected\");this.v=i;this.i++;e++;r++;try{for(let i=this.t;void 0!==i;i=i.x)i.t.N();}finally{t();}}}});function d(i,t){return new c(i,t)}function v(i){for(let t=i.s;void 0!==t;t=t.n)if(t.S.i!==t.i||!t.S.h()||t.S.i!==t.i)return true;return false}function l(i){for(let t=i.s;void 0!==t;t=t.n){const o=t.S.n;if(void 0!==o)t.r=o;t.S.n=t;t.i=-1;if(void 0===t.n){i.s=t;break}}}function y(i){let t,o=i.s;while(void 0!==o){const i=o.p;if(-1===o.i){o.S.U(o);if(void 0!==i)i.n=o.n;if(void 0!==o.n)o.n.p=i;}else t=o;o.S.n=o.r;if(void 0!==o.r)o.r=void 0;o=i;}i.s=t;}function a(i,t){c.call(this,void 0);this.x=i;this.s=void 0;this.g=e-1;this.f=4;this.W=null==t?void 0:t.watched;this.Z=null==t?void 0:t.unwatched;this.name=null==t?void 0:t.name;}a.prototype=new c;a.prototype.h=function(){this.f&=-3;if(1&this.f)return false;if(32==(36&this.f))return true;this.f&=-5;if(this.g===e)return true;this.g=e;this.f|=1;if(this.i>0&&!v(this)){this.f&=-2;return true}const i=n;try{l(this);n=this;const i=this.x();if(16&this.f||this.v!==i||0===this.i){this.v=i;this.f&=-17;this.i++;}}catch(i){this.v=i;this.f|=16;this.i++;}n=i;y(this);this.f&=-2;return true};a.prototype.S=function(i){if(void 0===this.t){this.f|=36;for(let i=this.s;void 0!==i;i=i.n)i.S.S(i);}c.prototype.S.call(this,i);};a.prototype.U=function(i){if(void 0!==this.t){c.prototype.U.call(this,i);if(void 0===this.t){this.f&=-33;for(let i=this.s;void 0!==i;i=i.n)i.S.U(i);}}};a.prototype.N=function(){if(!(2&this.f)){this.f|=6;for(let i=this.t;void 0!==i;i=i.x)i.t.N();}};Object.defineProperty(a.prototype,\"value\",{get(){if(1&this.f)throw new Error(\"Cycle detected\");const i=u(this);this.h();if(void 0!==i)i.i=this.i;if(16&this.f)throw this.v;return this.v}});function w(i,t){return new a(i,t)}function _(i){const o=i.u;i.u=void 0;if(\"function\"==typeof o){r++;const s=n;n=void 0;try{o();}catch(t){i.f&=-2;i.f|=8;b(i);throw t}finally{n=s;t();}}}function b(i){for(let t=i.s;void 0!==t;t=t.n)t.S.U(t);i.x=void 0;i.s=void 0;_(i);}function g(i){if(n!==this)throw new Error(\"Out-of-order effect\");y(this);n=i;this.f&=-2;if(8&this.f)b(this);t();}function p(i,t){this.x=i;this.u=void 0;this.s=void 0;this.o=void 0;this.f=32;this.name=null==t?void 0:t.name;}p.prototype.c=function(){const i=this.S();try{if(8&this.f)return;if(void 0===this.x)return;const t=this.x();if(\"function\"==typeof t)this.u=t;}finally{i();}};p.prototype.S=function(){if(1&this.f)throw new Error(\"Cycle detected\");this.f|=1;this.f&=-9;_(this);l(this);r++;const i=n;n=this;return g.bind(this,i)};p.prototype.N=function(){if(!(2&this.f)){this.f|=2;this.o=s;s=this;}};p.prototype.d=function(){this.f|=8;if(!(1&this.f))b(this);};p.prototype.dispose=function(){this.d();};function E(i,t){const o=new p(i,t);try{o.c();}catch(i){o.d();throw i}const n=o.d.bind(o);n[Symbol.dispose]=n;return n}\n\n/**\n * Copyright (c) Meta Platforms, Inc. and affiliates.\n *\n * This source code is licensed under the MIT license found in the\n * LICENSE file in the root directory of this source tree.\n *\n */\n/**\n * @experimental\n * Return an object with the same shape as `defaults` with a {@link Signal}\n * for each value. If specified, the second `opts` argument is a partial\n * of overrides to the defaults and will be used as the initial value.\n *\n * Typically used to make a reactive version of some subset of the\n * configuration of an extension, so it can be reconfigured at runtime.\n *\n * @param defaults The object with default values\n * @param opts Overrides to those default values\n * @returns An object with signals initialized with the default values\n */\nfunction namedSignals(defaults, opts = {}) {\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n const initial = {};\n for (const k in defaults) {\n const v = opts[k];\n const store = d(v === undefined ? defaults[k] : v);\n initial[k] = store;\n }\n return initial;\n}\n\n/**\n * Copyright (c) Meta Platforms, Inc. and affiliates.\n *\n * This source code is licensed under the MIT license found in the\n * LICENSE file in the root directory of this source tree.\n *\n */\n\n/**\n * An Extension to focus the LexicalEditor when the root element is set\n * (typically only when the editor is first created).\n */\nconst AutoFocusExtension = (0,lexical__WEBPACK_IMPORTED_MODULE_0__.defineExtension)({\n build: (editor, config, state) => {\n return namedSignals(config);\n },\n config: (0,lexical__WEBPACK_IMPORTED_MODULE_0__.safeCast)({\n defaultSelection: 'rootEnd',\n disabled: false\n }),\n name: '@lexical/extension/AutoFocus',\n register(editor, config, state) {\n const stores = state.getOutput();\n return E(() => stores.disabled.value ? undefined : editor.registerRootListener(rootElement => {\n editor.focus(() => {\n // If we try and move selection to the same point with setBaseAndExtent, it won't\n // trigger a re-focus on the element. So in the case this occurs, we'll need to correct it.\n // Normally this is fine, Selection API !== Focus API, but fore the intents of the naming\n // of this plugin, which should preserve focus too.\n const activeElement = document.activeElement;\n if (rootElement !== null && (activeElement === null || !rootElement.contains(activeElement))) {\n // Note: preventScroll won't work in Webkit.\n rootElement.focus({\n preventScroll: true\n });\n }\n }, {\n defaultSelection: stores.defaultSelection.peek()\n });\n }));\n }\n});\n\n/**\n * Copyright (c) Meta Platforms, Inc. and affiliates.\n *\n * This source code is licensed under the MIT license found in the\n * LICENSE file in the root directory of this source tree.\n *\n */\n\nfunction $defaultOnClear() {\n const root = (0,lexical__WEBPACK_IMPORTED_MODULE_0__.$getRoot)();\n const selection = (0,lexical__WEBPACK_IMPORTED_MODULE_0__.$getSelection)();\n const paragraph = (0,lexical__WEBPACK_IMPORTED_MODULE_0__.$createParagraphNode)();\n root.clear();\n root.append(paragraph);\n if (selection !== null) {\n paragraph.select();\n }\n if ((0,lexical__WEBPACK_IMPORTED_MODULE_0__.$isRangeSelection)(selection)) {\n selection.format = 0;\n }\n}\nfunction registerClearEditor(editor, $onClear = $defaultOnClear) {\n return editor.registerCommand(lexical__WEBPACK_IMPORTED_MODULE_0__.CLEAR_EDITOR_COMMAND, payload => {\n editor.update($onClear);\n return true;\n }, lexical__WEBPACK_IMPORTED_MODULE_0__.COMMAND_PRIORITY_EDITOR);\n}\n\n/**\n * An extension to provide an implementation of {@link CLEAR_EDITOR_COMMAND}\n */\nconst ClearEditorExtension = (0,lexical__WEBPACK_IMPORTED_MODULE_0__.defineExtension)({\n build(editor, config, state) {\n return namedSignals(config);\n },\n config: (0,lexical__WEBPACK_IMPORTED_MODULE_0__.safeCast)({\n $onClear: $defaultOnClear\n }),\n name: '@lexical/extension/ClearEditor',\n register(editor, config, state) {\n const {\n $onClear\n } = state.getOutput();\n return E(() => registerClearEditor(editor, $onClear.value));\n }\n});\n\n/**\n * Copyright (c) Meta Platforms, Inc. and affiliates.\n *\n * This source code is licensed under the MIT license found in the\n * LICENSE file in the root directory of this source tree.\n *\n */\n\n/**\n * @experimental\n * Get the sets of nodes and types registered in the\n * {@link InitialEditorConfig}. This is to be used when an extension\n * needs to register optional behavior if some node or type is present.\n *\n * @param config The InitialEditorConfig (accessible from an extension's init)\n * @returns The known types and nodes as Sets\n */\nfunction getKnownTypesAndNodes(config) {\n const types = new Set();\n const nodes = new Set();\n for (const klassOrReplacement of getNodeConfig(config)) {\n const klass = typeof klassOrReplacement === 'function' ? klassOrReplacement : klassOrReplacement.replace;\n types.add(klass.getType());\n nodes.add(klass);\n }\n return {\n nodes,\n types\n };\n}\nfunction getNodeConfig(config) {\n return (typeof config.nodes === 'function' ? config.nodes() : config.nodes) || [];\n}\n\n/**\n * Copyright (c) Meta Platforms, Inc. and affiliates.\n *\n * This source code is licensed under the MIT license found in the\n * LICENSE file in the root directory of this source tree.\n *\n */\n\nconst formatState = (0,lexical__WEBPACK_IMPORTED_MODULE_0__.createState)('format', {\n parse: value => typeof value === 'number' ? value : 0\n});\nclass DecoratorTextNode extends lexical__WEBPACK_IMPORTED_MODULE_0__.DecoratorNode {\n $config() {\n return this.config('decorator-text', {\n extends: lexical__WEBPACK_IMPORTED_MODULE_0__.DecoratorNode,\n stateConfigs: [{\n flat: true,\n stateConfig: formatState\n }]\n });\n }\n getFormat() {\n return (0,lexical__WEBPACK_IMPORTED_MODULE_0__.$getState)(this, formatState);\n }\n getFormatFlags(type, alignWithFormat) {\n return (0,lexical__WEBPACK_IMPORTED_MODULE_0__.toggleTextFormatType)(this.getFormat(), type, alignWithFormat);\n }\n hasFormat(type) {\n const formatFlag = lexical__WEBPACK_IMPORTED_MODULE_0__.TEXT_TYPE_TO_FORMAT[type];\n return (this.getFormat() & formatFlag) !== 0;\n }\n setFormat(type) {\n return (0,lexical__WEBPACK_IMPORTED_MODULE_0__.$setState)(this, formatState, type);\n }\n toggleFormat(type) {\n const format = this.getFormat();\n const newFormat = (0,lexical__WEBPACK_IMPORTED_MODULE_0__.toggleTextFormatType)(format, type, null);\n return this.setFormat(newFormat);\n }\n isInline() {\n return true;\n }\n createDOM() {\n return document.createElement('span');\n }\n updateDOM() {\n return false;\n }\n}\nfunction $isDecoratorTextNode(node) {\n return node instanceof DecoratorTextNode;\n}\n\n/**\n * Applies formatting to the node based on the properties in the passed style object.\n * By default, properties are checked according to the values set\n * when importing content from Google Docs.\n * This algorithm is identical to the TextNode import.\n\n * @param lexicalNode The node to which the format will apply\n * @param style CSS style object\n * @param shouldApply format to apply if it is not in style\n * @returns lexicalNode\n */\nfunction applyFormatFromStyle(lexicalNode, style, shouldApply) {\n const fontWeight = style.fontWeight;\n const textDecoration = style.textDecoration.split(' ');\n // Google Docs uses span tags + font-weight for bold text\n const hasBoldFontWeight = fontWeight === '700' || fontWeight === 'bold';\n // Google Docs uses span tags + text-decoration: line-through for strikethrough text\n const hasLinethroughTextDecoration = textDecoration.includes('line-through');\n // Google Docs uses span tags + font-style for italic text\n const hasItalicFontStyle = style.fontStyle === 'italic';\n // Google Docs uses span tags + text-decoration: underline for underline text\n const hasUnderlineTextDecoration = textDecoration.includes('underline');\n // Google Docs uses span tags + vertical-align to specify subscript and superscript\n const verticalAlign = style.verticalAlign;\n if (hasBoldFontWeight && !lexicalNode.hasFormat('bold')) {\n lexicalNode.toggleFormat('bold');\n }\n if (hasLinethroughTextDecoration && !lexicalNode.hasFormat('strikethrough')) {\n lexicalNode.toggleFormat('strikethrough');\n }\n if (hasItalicFontStyle && !lexicalNode.hasFormat('italic')) {\n lexicalNode.toggleFormat('italic');\n }\n if (hasUnderlineTextDecoration && !lexicalNode.hasFormat('underline')) {\n lexicalNode.toggleFormat('underline');\n }\n if (verticalAlign === 'sub' && !lexicalNode.hasFormat('subscript')) {\n lexicalNode.toggleFormat('subscript');\n }\n if (verticalAlign === 'super' && !lexicalNode.hasFormat('superscript')) {\n lexicalNode.toggleFormat('superscript');\n }\n if (shouldApply && !lexicalNode.hasFormat(shouldApply)) {\n lexicalNode.toggleFormat(shouldApply);\n }\n return lexicalNode;\n}\n\n/**\n * The function wraps the passed DOM node in semantic tags depending on the node format.\n *\n * @param lexicalNode The node where the format is checked\n * @param domNode DOM that will be wrapped in tags\n * @param tagNameToFormat Tag name and format mapping\n * @returns domNode\n */\nfunction applyFormatToDom(lexicalNode, domNode, tagNameToFormat = DEFAULT_TAG_NAME_TO_FORMAT) {\n for (const [tag, format] of Object.entries(tagNameToFormat)) {\n if (lexicalNode.hasFormat(format)) {\n domNode = wrapElementWith(domNode, tag);\n }\n }\n return domNode;\n}\nfunction wrapElementWith(element, tag) {\n const el = document.createElement(tag);\n el.appendChild(element);\n return el;\n}\nconst DEFAULT_TAG_NAME_TO_FORMAT = {\n b: 'bold',\n code: 'code',\n em: 'italic',\n i: 'italic',\n mark: 'highlight',\n s: 'strikethrough',\n strong: 'bold',\n sub: 'subscript',\n sup: 'superscript',\n u: 'underline'\n};\n\n/**\n * An extension for DecoratorTextNode that sets the format for the node and CSS classes for the DOM container.\n * The base class is always set, and the focus class is set when the node is selected.\n */\nconst DecoratorTextExtension = (0,lexical__WEBPACK_IMPORTED_MODULE_0__.defineExtension)({\n name: '@lexical/extension/DecoratorText',\n nodes: () => [DecoratorTextNode],\n register(editor, config, state) {\n return editor.registerCommand(lexical__WEBPACK_IMPORTED_MODULE_0__.FORMAT_TEXT_COMMAND, formatType => {\n const selection = (0,lexical__WEBPACK_IMPORTED_MODULE_0__.$getSelection)();\n if ((0,lexical__WEBPACK_IMPORTED_MODULE_0__.$isNodeSelection)(selection) || (0,lexical__WEBPACK_IMPORTED_MODULE_0__.$isRangeSelection)(selection)) {\n for (const node of selection.getNodes()) {\n if ($isDecoratorTextNode(node)) {\n node.toggleFormat(formatType);\n }\n }\n }\n return false;\n }, lexical__WEBPACK_IMPORTED_MODULE_0__.COMMAND_PRIORITY_LOW);\n }\n});\n\n/**\n * Copyright (c) Meta Platforms, Inc. and affiliates.\n *\n * This source code is licensed under the MIT license found in the\n * LICENSE file in the root directory of this source tree.\n *\n */\n\n/**\n * @experimental\n * Create a Signal that will subscribe to a value from an external store when watched, similar to\n * React's [useSyncExternalStore](https://react.dev/reference/react/useSyncExternalStore).\n *\n * @param getSnapshot Used to get the initial value of the signal when created and when first watched.\n * @param register A callback that will subscribe to some external store and update the signal, must return a dispose function.\n * @returns The signal\n */\nfunction watchedSignal(getSnapshot, register) {\n let dispose;\n return d(getSnapshot(), {\n unwatched() {\n if (dispose) {\n dispose();\n dispose = undefined;\n }\n },\n watched() {\n this.value = getSnapshot();\n dispose = register(this);\n }\n });\n}\n\n/**\n * Copyright (c) Meta Platforms, Inc. and affiliates.\n *\n * This source code is licensed under the MIT license found in the\n * LICENSE file in the root directory of this source tree.\n *\n */\n\n/**\n * An extension to provide the current EditorState as a signal\n */\nconst EditorStateExtension = (0,lexical__WEBPACK_IMPORTED_MODULE_0__.defineExtension)({\n build(editor) {\n return watchedSignal(() => editor.getEditorState(), editorStateSignal => editor.registerUpdateListener(payload => {\n editorStateSignal.value = payload.editorState;\n }));\n },\n name: '@lexical/extension/EditorState'\n});\n\n/**\n * Copyright (c) Meta Platforms, Inc. and affiliates.\n *\n * This source code is licensed under the MIT license found in the\n * LICENSE file in the root directory of this source tree.\n *\n */\n\n// Do not require this module directly! Use normal `invariant` calls.\n\nfunction formatDevErrorMessage(message) {\n throw new Error(message);\n}\n\n/**\n * Copyright (c) Meta Platforms, Inc. and affiliates.\n *\n * This source code is licensed under the MIT license found in the\n * LICENSE file in the root directory of this source tree.\n *\n */\n\n/**\n * Recursively merge the given theme configuration in-place.\n *\n * @returns If `a` and `b` are both objects (and `b` is not an Array) then\n * all keys in `b` are merged into `a` then `a` is returned.\n * Otherwise `b` is returned.\n *\n * @example\n * ```ts\n * const a = { a: \"a\", nested: { a: 1 } };\n * const b = { b: \"b\", nested: { b: 2 } };\n * const rval = deepThemeMergeInPlace(a, b);\n * expect(a).toBe(rval);\n * expect(a).toEqual({ a: \"a\", b: \"b\", nested: { a: 1, b: 2 } });\n * ```\n */\nfunction deepThemeMergeInPlace(a, b) {\n if (a && b && !Array.isArray(b) && typeof a === 'object' && typeof b === 'object') {\n const aObj = a;\n const bObj = b;\n for (const k in bObj) {\n aObj[k] = deepThemeMergeInPlace(aObj[k], bObj[k]);\n }\n return a;\n }\n return b;\n}\n\nconst ExtensionRepStateIds = {\n /* eslint-disable sort-keys-fix/sort-keys-fix */\n unmarked: 0,\n temporary: 1,\n permanent: 2,\n configured: 3,\n initialized: 4,\n built: 5,\n registered: 6,\n afterRegistration: 7\n /* eslint-enable sort-keys-fix/sort-keys-fix */\n};\nfunction isExactlyUnmarkedExtensionRepState(state) {\n return state.id === ExtensionRepStateIds.unmarked;\n}\nfunction isExactlyTemporaryExtensionRepState(state) {\n return state.id === ExtensionRepStateIds.temporary;\n}\nfunction isExactlyPermanentExtensionRepState(state) {\n return state.id === ExtensionRepStateIds.permanent;\n}\nfunction isConfiguredExtensionRepState(state) {\n return state.id >= ExtensionRepStateIds.configured;\n}\nfunction isInitializedExtensionRepState(state) {\n return state.id >= ExtensionRepStateIds.initialized;\n}\nfunction isBuiltExtensionRepState(state) {\n return state.id >= ExtensionRepStateIds.built;\n}\nfunction isAfterRegistrationState(state) {\n return state.id >= ExtensionRepStateIds.afterRegistration;\n}\nfunction applyTemporaryMark(state) {\n if (!isExactlyUnmarkedExtensionRepState(state)) {\n formatDevErrorMessage(`LexicalBuilder: Can not apply a temporary mark from state id ${String(state.id)} (expected ${String(ExtensionRepStateIds.unmarked)} unmarked)`);\n }\n return Object.assign(state, {\n id: ExtensionRepStateIds.temporary\n });\n}\nfunction applyPermanentMark(state) {\n if (!isExactlyTemporaryExtensionRepState(state)) {\n formatDevErrorMessage(`LexicalBuilder: Can not apply a permanent mark from state id ${String(state.id)} (expected ${String(ExtensionRepStateIds.temporary)} temporary)`);\n }\n return Object.assign(state, {\n id: ExtensionRepStateIds.permanent\n });\n}\nfunction applyConfiguredState(state, config, registerState) {\n return Object.assign(state, {\n config,\n id: ExtensionRepStateIds.configured,\n registerState\n });\n}\nfunction applyInitializedState(state, initResult, registerState) {\n return Object.assign(state, {\n id: ExtensionRepStateIds.initialized,\n initResult,\n registerState\n });\n}\nfunction applyBuiltState(state, output, registerState) {\n return Object.assign(state, {\n id: ExtensionRepStateIds.built,\n output,\n registerState\n });\n}\nfunction applyRegisteredState(state) {\n return Object.assign(state, {\n id: ExtensionRepStateIds.registered\n });\n}\nfunction applyAfterRegistrationState(state) {\n return Object.assign(state, {\n id: ExtensionRepStateIds.afterRegistration\n });\n}\nfunction rollbackToBuiltState(state) {\n return Object.assign(state, {\n id: ExtensionRepStateIds.built\n });\n}\nconst emptySet = new Set();\n\n/**\n * @internal\n */\nclass ExtensionRep {\n builder;\n configs;\n _dependency;\n _peerNameSet;\n extension;\n state;\n _signal;\n constructor(builder, extension) {\n this.builder = builder;\n this.extension = extension;\n this.configs = new Set();\n this.state = {\n id: ExtensionRepStateIds.unmarked\n };\n }\n mergeConfigs() {\n // eslint-disable-next-line @typescript-eslint/no-unsafe-assignment -- LexicalExtensionConfig<Extension> is any\n let config = this.extension.config || {};\n const mergeConfig = this.extension.mergeConfig ? this.extension.mergeConfig.bind(this.extension) : lexical__WEBPACK_IMPORTED_MODULE_0__.shallowMergeConfig;\n for (const cfg of this.configs) {\n // eslint-disable-next-line @typescript-eslint/no-unsafe-assignment -- LexicalExtensionConfig<Extension> is any\n config = mergeConfig(config, cfg);\n }\n // eslint-disable-next-line @typescript-eslint/no-unsafe-return -- any\n return config;\n }\n init(editorConfig) {\n const initialState = this.state;\n if (!isExactlyPermanentExtensionRepState(initialState)) {\n formatDevErrorMessage(`ExtensionRep: Can not configure from state id ${String(initialState.id)}`);\n }\n const initState = {\n getDependency: this.getInitDependency.bind(this),\n getDirectDependentNames: this.getDirectDependentNames.bind(this),\n getPeer: this.getInitPeer.bind(this),\n getPeerNameSet: this.getPeerNameSet.bind(this)\n };\n const buildState = {\n ...initState,\n getDependency: this.getDependency.bind(this),\n getInitResult: this.getInitResult.bind(this),\n getPeer: this.getPeer.bind(this)\n };\n const state = applyConfiguredState(initialState, this.mergeConfigs(), initState);\n this.state = state;\n let initResult;\n if (this.extension.init) {\n initResult = this.extension.init(editorConfig, state.config, initState);\n }\n // eslint-disable-next-line @typescript-eslint/no-unnecessary-type-assertion -- false positive\n this.state = applyInitializedState(state, initResult, buildState);\n }\n build(editor) {\n const state = this.state;\n if (!(state.id === ExtensionRepStateIds.initialized)) {\n formatDevErrorMessage(`ExtensionRep: register called in state id ${String(state.id)} (expected ${String(ExtensionRepStateIds.built)} initialized)`);\n }\n let output;\n if (this.extension.build) {\n output = this.extension.build(editor, state.config, state.registerState);\n }\n const registerState = {\n ...state.registerState,\n getOutput: () => output,\n getSignal: this.getSignal.bind(this)\n };\n this.state = applyBuiltState(state, output, registerState);\n }\n register(editor, signal) {\n this._signal = signal;\n const state = this.state;\n if (!(state.id === ExtensionRepStateIds.built)) {\n formatDevErrorMessage(`ExtensionRep: register called in state id ${String(state.id)} (expected ${String(ExtensionRepStateIds.built)} built)`);\n }\n const cleanup = this.extension.register && this.extension.register(editor, state.config, state.registerState);\n this.state = applyRegisteredState(state);\n return () => {\n const afterRegistrationState = this.state;\n if (!(afterRegistrationState.id === ExtensionRepStateIds.afterRegistration)) {\n formatDevErrorMessage(`ExtensionRep: rollbackToBuiltState called in state id ${String(state.id)} (expected ${String(ExtensionRepStateIds.afterRegistration)} afterRegistration)`);\n }\n this.state = rollbackToBuiltState(afterRegistrationState);\n if (cleanup) {\n cleanup();\n }\n };\n }\n afterRegistration(editor) {\n const state = this.state;\n if (!(state.id === ExtensionRepStateIds.registered)) {\n formatDevErrorMessage(`ExtensionRep: afterRegistration called in state id ${String(state.id)} (expected ${String(ExtensionRepStateIds.registered)} registered)`);\n }\n let rval;\n if (this.extension.afterRegistration) {\n rval = this.extension.afterRegistration(editor, state.config, state.registerState);\n }\n this.state = applyAfterRegistrationState(state);\n return rval;\n }\n getSignal() {\n if (!(this._signal !== undefined)) {\n formatDevErrorMessage(`ExtensionRep.getSignal() called before register`);\n }\n return this._signal;\n }\n getInitResult() {\n if (!(this.extension.init !== undefined)) {\n formatDevErrorMessage(`ExtensionRep: getInitResult() called for Extension ${this.extension.name} that does not define init`);\n }\n const state = this.state;\n if (!isInitializedExtensionRepState(state)) {\n formatDevErrorMessage(`ExtensionRep: getInitResult() called for ExtensionRep in state id ${String(state.id)} < ${String(ExtensionRepStateIds.initialized)} (initialized)`);\n } // eslint-disable-next-line @typescript-eslint/no-unsafe-return -- any\n return state.initResult;\n }\n getInitPeer(name) {\n const rep = this.builder.extensionNameMap.get(name);\n return rep ? rep.getExtensionInitDependency() : undefined;\n }\n getExtensionInitDependency() {\n const state = this.state;\n if (!isConfiguredExtensionRepState(state)) {\n formatDevErrorMessage(`ExtensionRep: getExtensionInitDependency called in state id ${String(state.id)} (expected >= ${String(ExtensionRepStateIds.configured)} configured)`);\n }\n return {\n config: state.config\n };\n }\n getPeer(name) {\n const rep = this.builder.extensionNameMap.get(name);\n return rep ? rep.getExtensionDependency() : undefined;\n }\n getInitDependency(dep) {\n const rep = this.builder.getExtensionRep(dep);\n if (!(rep !== undefined)) {\n formatDevErrorMessage(`LexicalExtensionBuilder: Extension ${this.extension.name} missing dependency extension ${dep.name} to be in registry`);\n }\n return rep.getExtensionInitDependency();\n }\n getDependency(dep) {\n const rep = this.builder.getExtensionRep(dep);\n if (!(rep !== undefined)) {\n formatDevErrorMessage(`LexicalExtensionBuilder: Extension ${this.extension.name} missing dependency extension ${dep.name} to be in registry`);\n }\n return rep.getExtensionDependency();\n }\n getState() {\n const state = this.state;\n if (!isAfterRegistrationState(state)) {\n formatDevErrorMessage(`ExtensionRep getState called in state id ${String(state.id)} (expected ${String(ExtensionRepStateIds.afterRegistration)} afterRegistration)`);\n }\n return state;\n }\n getDirectDependentNames() {\n return this.builder.incomingEdges.get(this.extension.name) || emptySet;\n }\n getPeerNameSet() {\n let s = this._peerNameSet;\n if (!s) {\n s = new Set((this.extension.peerDependencies || []).map(([name]) => name));\n this._peerNameSet = s;\n }\n return s;\n }\n getExtensionDependency() {\n if (!this._dependency) {\n const state = this.state;\n if (!isBuiltExtensionRepState(state)) {\n formatDevErrorMessage(`Extension ${this.extension.name} used as a dependency before build`);\n }\n this._dependency = {\n config: state.config,\n init: state.initResult,\n output: state.output\n };\n }\n return this._dependency;\n }\n}\n\n/**\n * Copyright (c) Meta Platforms, Inc. and affiliates.\n *\n * This source code is licensed under the MIT license found in the\n * LICENSE file in the root directory of this source tree.\n *\n */\n\nconst HISTORY_MERGE_OPTIONS = {\n tag: lexical__WEBPACK_IMPORTED_MODULE_0__.HISTORY_MERGE_TAG\n};\nfunction $defaultInitializer() {\n const root = (0,lexical__WEBPACK_IMPORTED_MODULE_0__.$getRoot)();\n if (root.isEmpty()) {\n root.append((0,lexical__WEBPACK_IMPORTED_MODULE_0__.$createParagraphNode)());\n }\n}\n/**\n * An extension to set the initial state of the editor from\n * a function or serialized JSON EditorState. This is\n * implicitly included with all editors built with\n * Lexical Extension. This happens in the `afterRegistration`\n * phase so your initial state may depend on registered commands,\n * but you should not call `editor.setRootElement` earlier than\n * this phase to avoid rendering an empty editor first.\n */\nconst InitialStateExtension = (0,lexical__WEBPACK_IMPORTED_MODULE_0__.defineExtension)({\n config: (0,lexical__WEBPACK_IMPORTED_MODULE_0__.safeCast)({\n setOptions: HISTORY_MERGE_OPTIONS,\n updateOptions: HISTORY_MERGE_OPTIONS\n }),\n init({\n $initialEditorState = $defaultInitializer\n }) {\n return {\n $initialEditorState,\n initialized: false\n };\n },\n // eslint-disable-next-line sort-keys-fix/sort-keys-fix -- typescript inference is order dependent here for some reason\n afterRegistration(editor, {\n updateOptions,\n setOptions\n }, state) {\n const initResult = state.getInitResult();\n if (!initResult.initialized) {\n initResult.initialized = true;\n const {\n $initialEditorState\n } = initResult;\n if ((0,lexical__WEBPACK_IMPORTED_MODULE_0__.$isEditorState)($initialEditorState)) {\n editor.setEditorState($initialEditorState, setOptions);\n } else if (typeof $initialEditorState === 'function') {\n editor.update(() => {\n $initialEditorState(editor);\n }, updateOptions);\n } else if ($initialEditorState && (typeof $initialEditorState === 'string' || typeof $initialEditorState === 'object')) {\n const parsedEditorState = editor.parseEditorState($initialEditorState);\n editor.setEditorState(parsedEditorState, setOptions);\n }\n }\n return () => {};\n },\n name: '@lexical/extension/InitialState',\n // These are automatically added by createEditor, we add them here so they are\n // visible during extensionRep.init so extensions can see all known types before the\n // editor is created.\n // (excluding ArtificialNode__DO_NOT_USE because it isn't really public API\n // and shouldn't change anything)\n nodes: [lexical__WEBPACK_IMPORTED_MODULE_0__.RootNode, lexical__WEBPACK_IMPORTED_MODULE_0__.TextNode, lexical__WEBPACK_IMPORTED_MODULE_0__.LineBreakNode, lexical__WEBPACK_IMPORTED_MODULE_0__.TabNode, lexical__WEBPACK_IMPORTED_MODULE_0__.ParagraphNode]\n});\n\n/** @internal Use a well-known symbol for dev tools purposes */\nconst builderSymbol = Symbol.for('@lexical/extension/LexicalBuilder');\n/**\n * Build a LexicalEditor by combining together one or more extensions, optionally\n * overriding some of their configuration.\n *\n * @param extensions - Extension arguments (extensions or extensions with config overrides)\n * @returns An editor handle\n *\n * @example\n * A single root extension with multiple dependencies\n *\n * ```ts\n * const editor = buildEditorFromExtensions(\n * defineExtension({\n * name: \"[root]\",\n * dependencies: [\n * RichTextExtension,\n * configExtension(EmojiExtension, { emojiBaseUrl: \"/assets/emoji\" }),\n * ],\n * register: (editor: LexicalEditor) => {\n * console.log(\"Editor Created\");\n * return () => console.log(\"Editor Disposed\");\n * },\n * }),\n * );\n * ```\n *\n * @example\n * A very similar minimal configuration without the register hook\n *\n * ```ts\n * const editor = buildEditorFromExtensions(\n * RichTextExtension,\n * configExtension(EmojiExtension, { emojiBaseUrl: \"/assets/emoji\" }),\n * );\n * ```\n */\nfunction buildEditorFromExtensions(...extensions) {\n return LexicalBuilder.fromExtensions(extensions).buildEditor();\n}\n\n/** @internal */\nfunction noop() {\n /*empty*/\n}\n\n/** Throw the given Error */\nfunction defaultOnError(err) {\n throw err;\n}\n/** @internal */\nfunction maybeWithBuilder(editor) {\n return editor;\n}\nfunction normalizeExtensionArgument(arg) {\n return Array.isArray(arg) ? arg : [arg];\n}\nconst PACKAGE_VERSION = \"0.41.0+dev.esm\";\n\n/** @internal */\nclass LexicalBuilder {\n roots;\n extensionNameMap;\n outgoingConfigEdges;\n incomingEdges;\n conflicts;\n _sortedExtensionReps;\n PACKAGE_VERSION;\n constructor(roots) {\n this.outgoingConfigEdges = new Map();\n this.incomingEdges = new Map();\n this.extensionNameMap = new Map();\n this.conflicts = new Map();\n this.PACKAGE_VERSION = PACKAGE_VERSION;\n this.roots = roots;\n for (const extension of roots) {\n this.addExtension(extension);\n }\n }\n static fromExtensions(extensions) {\n const roots = [normalizeExtensionArgument(InitialStateExtension)];\n for (const extension of extensions) {\n roots.push(normalizeExtensionArgument(extension));\n }\n return new LexicalBuilder(roots);\n }\n static maybeFromEditor(editor) {\n const builder = maybeWithBuilder(editor)[builderSymbol];\n if (builder) {\n // The dev tools variant of this will relax some of these invariants\n if (!(builder.PACKAGE_VERSION === PACKAGE_VERSION)) {\n formatDevErrorMessage(`LexicalBuilder.fromEditor: The given editor was created with LexicalBuilder ${builder.PACKAGE_VERSION} but this version is ${PACKAGE_VERSION}. A project should have exactly one copy of LexicalBuilder`);\n }\n if (!(builder instanceof LexicalBuilder)) {\n formatDevErrorMessage(`LexicalBuilder.fromEditor: There are multiple copies of the same version of LexicalBuilder in your project, and this editor was created with another one. Your project, or one of its dependencies, has its package.json and/or bundler configured incorrectly.`);\n }\n }\n return builder;\n }\n\n /** Look up the editor that was created by this LexicalBuilder or throw */\n static fromEditor(editor) {\n const builder = LexicalBuilder.maybeFromEditor(editor);\n if (!(builder !== undefined)) {\n formatDevErrorMessage(`LexicalBuilder.fromEditor: The given editor was not created with LexicalBuilder`);\n }\n return builder;\n }\n constructEditor() {\n const {\n $initialEditorState: _$initialEditorState,\n onError,\n ...editorConfig\n } = this.buildCreateEditorArgs();\n const editor = Object.assign((0,lexical__WEBPACK_IMPORTED_MODULE_0__.createEditor)({\n ...editorConfig,\n ...(onError ? {\n onError: err => {\n onError(err, editor);\n }\n } : {})\n }), {\n [builderSymbol]: this\n });\n for (const extensionRep of this.sortedExtensionReps()) {\n extensionRep.build(editor);\n }\n return editor;\n }\n buildEditor() {\n let disposeOnce = noop;\n function dispose() {\n try {\n disposeOnce();\n } finally {\n disposeOnce = noop;\n }\n }\n const editor = Object.assign(this.constructEditor(), {\n dispose,\n [Symbol.dispose]: dispose\n });\n disposeOnce = (0,lexical__WEBPACK_IMPORTED_MODULE_0__.mergeRegister)(this.registerEditor(editor), () => editor.setRootElement(null));\n return editor;\n }\n hasExtensionByName(name) {\n return this.extensionNameMap.has(name);\n }\n getExtensionRep(extension) {\n const rep = this.extensionNameMap.get(extension.name);\n if (rep) {\n if (!(rep.extension === extension)) {\n formatDevErrorMessage(`LexicalBuilder: A registered extension with name ${extension.name} exists but does not match the given extension`);\n }\n return rep;\n }\n }\n addEdge(fromExtensionName, toExtensionName, configs) {\n const outgoing = this.outgoingConfigEdges.get(fromExtensionName);\n if (outgoing) {\n outgoing.set(toExtensionName, configs);\n } else {\n this.outgoingConfigEdges.set(fromExtensionName, new Map([[toExtensionName, configs]]));\n }\n const incoming = this.incomingEdges.get(toExtensionName);\n if (incoming) {\n incoming.add(fromExtensionName);\n } else {\n this.incomingEdges.set(toExtensionName, new Set([fromExtensionName]));\n }\n }\n addExtension(arg) {\n if (!(this._sortedExtensionReps === undefined)) {\n formatDevErrorMessage(`LexicalBuilder: addExtension called after finalization`);\n }\n const normalized = normalizeExtensionArgument(arg);\n const [extension] = normalized;\n if (!(typeof extension.name === 'string')) {\n formatDevErrorMessage(`LexicalBuilder: extension name must be string, not ${typeof extension.name}`);\n }\n let extensionRep = this.extensionNameMap.get(extension.name);\n if (!(extensionRep === undefined || extensionRep.extension === extension)) {\n formatDevErrorMessage(`LexicalBuilder: Multiple extensions registered with name ${extension.name}, names must be unique`);\n }\n if (!extensionRep) {\n extensionRep = new ExtensionRep(this, extension);\n this.extensionNameMap.set(extension.name, extensionRep);\n const hasConflict = this.conflicts.get(extension.name);\n if (typeof hasConflict === 'string') {\n {\n formatDevErrorMessage(`LexicalBuilder: extension ${extension.name} conflicts with ${hasConflict}`);\n }\n }\n for (const name of extension.conflictsWith || []) {\n if (!!this.extensionNameMap.has(name)) {\n formatDevErrorMessage(`LexicalBuilder: extension ${extension.name} conflicts with ${name}`);\n }\n this.conflicts.set(name, extension.name);\n }\n for (const dep of extension.dependencies || []) {\n const normDep = normalizeExtensionArgument(dep);\n this.addEdge(extension.name, normDep[0].name, normDep.slice(1));\n this.addExtension(normDep);\n }\n for (const [depName, config] of extension.peerDependencies || []) {\n this.addEdge(extension.name, depName, config ? [config] : []);\n }\n }\n }\n sortedExtensionReps() {\n if (this._sortedExtensionReps) {\n return this._sortedExtensionReps;\n }\n // depth-first search based topological DAG sort\n // https://en.wikipedia.org/wiki/Topological_sorting\n const sortedExtensionReps = [];\n const visit = (rep, fromExtensionName) => {\n let mark = rep.state;\n if (isExactlyPermanentExtensionRepState(mark)) {\n return;\n }\n const extensionName = rep.extension.name;\n if (!isExactlyUnmarkedExtensionRepState(mark)) {\n formatDevErrorMessage(`LexicalBuilder: Circular dependency detected for Extension ${extensionName} from ${fromExtensionName || '[unknown]'}`);\n }\n mark = applyTemporaryMark(mark);\n rep.state = mark;\n const outgoingConfigEdges = this.outgoingConfigEdges.get(extensionName);\n if (outgoingConfigEdges) {\n for (const toExtensionName of outgoingConfigEdges.keys()) {\n const toRep = this.extensionNameMap.get(toExtensionName);\n // may be undefined for an optional peer dependency\n if (toRep) {\n visit(toRep, extensionName);\n }\n }\n }\n mark = applyPermanentMark(mark);\n rep.state = mark;\n sortedExtensionReps.push(rep);\n };\n for (const rep of this.extensionNameMap.values()) {\n if (isExactlyUnmarkedExtensionRepState(rep.state)) {\n visit(rep);\n }\n }\n for (const rep of sortedExtensionReps) {\n for (const [toExtensionName, configs] of this.outgoingConfigEdges.get(rep.extension.name) || []) {\n if (configs.length > 0) {\n const toRep = this.extensionNameMap.get(toExtensionName);\n if (toRep) {\n for (const config of configs) {\n // eslint-disable-next-line @typescript-eslint/no-unsafe-argument -- any\n toRep.configs.add(config);\n }\n }\n }\n }\n }\n for (const [extension, ...configs] of this.roots) {\n if (configs.length > 0) {\n const toRep = this.extensionNameMap.get(extension.name);\n if (!(toRep !== undefined)) {\n formatDevErrorMessage(`LexicalBuilder: Expecting existing ExtensionRep for ${extension.name}`);\n }\n for (const config of configs) {\n toRep.configs.add(config);\n }\n }\n }\n this._sortedExtensionReps = sortedExtensionReps;\n return this._sortedExtensionReps;\n }\n registerEditor(editor) {\n const extensionReps = this.sortedExtensionReps();\n const controller = new AbortController();\n const cleanups = [() => controller.abort()];\n const signal = controller.signal;\n for (const extensionRep of extensionReps) {\n const cleanup = extensionRep.register(editor, signal);\n if (cleanup) {\n cleanups.push(cleanup);\n }\n }\n for (const extensionRep of extensionReps) {\n const cleanup = extensionRep.afterRegistration(editor);\n if (cleanup) {\n cleanups.push(cleanup);\n }\n }\n return (0,lexical__WEBPACK_IMPORTED_MODULE_0__.mergeRegister)(...cleanups);\n }\n buildCreateEditorArgs() {\n const config = {};\n const nodes = new Set();\n const replacedNodes = new Map();\n const htmlExport = new Map();\n const htmlImport = {};\n const theme = {};\n const extensionReps = this.sortedExtensionReps();\n for (const extensionRep of extensionReps) {\n const {\n extension\n } = extensionRep;\n if (extension.onError !== undefined) {\n config.onError = extension.onError;\n }\n if (extension.disableEvents !== undefined) {\n config.disableEvents = extension.disableEvents;\n }\n if (extension.parentEditor !== undefined) {\n config.parentEditor = extension.parentEditor;\n }\n if (extension.editable !== undefined) {\n config.editable = extension.editable;\n }\n if (extension.namespace !== undefined) {\n config.namespace = extension.namespace;\n }\n if (extension.$initialEditorState !== undefined) {\n config.$initialEditorState = extension.$initialEditorState;\n }\n if (extension.nodes) {\n for (const node of getNodeConfig(extension)) {\n if (typeof node !== 'function') {\n const conflictExtension = replacedNodes.get(node.replace);\n if (conflictExtension) {\n {\n formatDevErrorMessage(`LexicalBuilder: Extension ${extension.name} can not register replacement for node ${node.replace.name} because ${conflictExtension.extension.name} already did`);\n }\n }\n replacedNodes.set(node.replace, extensionRep);\n }\n nodes.add(node);\n }\n }\n if (extension.html) {\n if (extension.html.export) {\n for (const [k, v] of extension.html.export.entries()) {\n htmlExport.set(k, v);\n }\n }\n if (extension.html.import) {\n Object.assign(htmlImport, extension.html.import);\n }\n }\n if (extension.theme) {\n deepThemeMergeInPlace(theme, extension.theme);\n }\n }\n if (Object.keys(theme).length > 0) {\n config.theme = theme;\n }\n if (nodes.size) {\n config.nodes = [...nodes];\n }\n const hasImport = Object.keys(htmlImport).length > 0;\n const hasExport = htmlExport.size > 0;\n if (hasImport || hasExport) {\n config.html = {};\n if (hasImport) {\n config.html.import = htmlImport;\n }\n if (hasExport) {\n config.html.export = htmlExport;\n }\n }\n for (const extensionRep of extensionReps) {\n extensionRep.init(config);\n }\n if (!config.onError) {\n config.onError = defaultOnError;\n }\n return config;\n }\n}\n\n/**\n * @experimental\n * Get the finalized config and output of an Extension that was used to build the editor.\n *\n * This is useful in the implementation of a LexicalNode or in other\n * situations where you have an editor reference but it's not easy to\n * pass the config or {@link ExtensionRegisterState} around.\n *\n * It will throw if the Editor was not built using this Extension.\n *\n * @param editor - The editor that was built using extension\n * @param extension - The concrete reference to an Extension used to build this editor\n * @returns The config and output for that Extension\n */\nfunction getExtensionDependencyFromEditor(editor, extension) {\n const builder = LexicalBuilder.fromEditor(editor);\n const rep = builder.getExtensionRep(extension);\n if (!(rep !== undefined)) {\n formatDevErrorMessage(`getExtensionDependencyFromEditor: Extension ${extension.name} was not built when creating this editor`);\n }\n return rep.getExtensionDependency();\n}\n\n/**\n * @experimental\n * Get the finalized config and output of an Extension that was used to build the\n * editor by name.\n *\n * This can be used from the implementation of a LexicalNode or in other\n * situation where you have an editor reference but it's not easy to pass the\n * config around. Use this version if you do not have a concrete reference to\n * the Extension for some reason (e.g. it is an optional peer dependency, or you\n * are avoiding a circular import).\n *\n * Both the explicit Extension type and the name are required.\n *\n * @example\n * ```tsx\n * import type { HistoryExtension } from \"@lexical/history\";\n * getPeerDependencyFromEditor<typeof HistoryExtension>(editor, \"@lexical/history/History\");\n * ```\n\n * @param editor - The editor that may have been built using extension\n * @param extensionName - The name of the Extension\n * @returns The config and output of the Extension or undefined\n */\nfunction getPeerDependencyFromEditor(editor, extensionName) {\n const builder = LexicalBuilder.fromEditor(editor);\n const peer = builder.extensionNameMap.get(extensionName);\n return peer ? peer.getExtensionDependency() : undefined;\n}\n\n/**\n * Get the finalized config and output of an Extension that was used to build the\n * editor by name.\n *\n * This can be used from the implementation of a LexicalNode or in other\n * situation where you have an editor reference but it's not easy to pass the\n * config around. Use this version if you do not have a concrete reference to\n * the Extension for some reason (e.g. it is an optional peer dependency, or you\n * are avoiding a circular import).\n *\n * Both the explicit Extension type and the name are required.\n *\n * @example\n * ```tsx\n * import type { EmojiExtension } from \"./EmojiExtension\";\n * export class EmojiNode extends TextNode {\n * // other implementation details not included\n * createDOM(\n * config: EditorConfig,\n * editor?: LexicalEditor | undefined\n * ): HTMLElement {\n * const dom = super.createDOM(config, editor);\n * addClassNamesToElement(\n * dom,\n * getPeerDependencyFromEditorOrThrow<typeof EmojiExtension>(\n * editor || $getEditor(),\n * \"@lexical/playground/emoji\",\n * ).config.emojiClass,\n * );\n * return dom;\n * }\n * }\n * ```\n\n * @param editor - The editor that may have been built using extension\n * @param extensionName - The name of the Extension\n * @returns The config and output of the Extension\n */\nfunction getPeerDependencyFromEditorOrThrow(editor, extensionName) {\n const dep = getPeerDependencyFromEditor(editor, extensionName);\n if (!(dep !== undefined)) {\n formatDevErrorMessage(`getPeerDependencyFromEditorOrThrow: Editor was not built with Extension ${extensionName}`);\n }\n return dep;\n}\n\n/**\n * Copyright (c) Meta Platforms, Inc. and affiliates.\n *\n * This source code is licensed under the MIT license found in the\n * LICENSE file in the root directory of this source tree.\n *\n */\n\nconst EMPTY_SET = new Set();\n\n/**\n * An extension that provides a `watchNodeKey` output that\n * returns a signal for the selection state of a node.\n *\n * Typically used for tracking whether a DecoratorNode is\n * currently selected or not. A framework independent\n * alternative to {@link useLexicalNodeSelection}.\n */\nconst NodeSelectionExtension = (0,lexical__WEBPACK_IMPORTED_MODULE_0__.defineExtension)({\n build(editor, config, state) {\n const editorStateStore = state.getDependency(EditorStateExtension).output;\n const watchedNodeStore = d({\n watchedNodeKeys: new Map()\n });\n const selectedNodeKeys = watchedSignal(() => undefined, () => E(() => {\n const prevSelectedNodeKeys = selectedNodeKeys.peek();\n const {\n watchedNodeKeys\n } = watchedNodeStore.value;\n let nextSelectedNodeKeys;\n let didChange = false;\n editorStateStore.value.read(() => {\n const selection = (0,lexical__WEBPACK_IMPORTED_MODULE_0__.$getSelection)();\n if (selection) {\n for (const [key, listeners] of watchedNodeKeys.entries()) {\n if (listeners.size === 0) {\n // We intentionally mutate this without firing a signal, to\n // avoid re-triggering this effect. There are no subscribers\n // so nothing can observe whether key was in the set or not\n watchedNodeKeys.delete(key);\n continue;\n }\n const node = (0,lexical__WEBPACK_IMPORTED_MODULE_0__.$getNodeByKey)(key);\n const isSelected = node && node.isSelected() || false;\n didChange = didChange || isSelected !== (prevSelectedNodeKeys ? prevSelectedNodeKeys.has(key) : false);\n if (isSelected) {\n nextSelectedNodeKeys = nextSelectedNodeKeys || new Set();\n nextSelectedNodeKeys.add(key);\n }\n }\n }\n });\n if (!(!didChange && nextSelectedNodeKeys && prevSelectedNodeKeys && nextSelectedNodeKeys.size === prevSelectedNodeKeys.size)) {\n selectedNodeKeys.value = nextSelectedNodeKeys;\n }\n }));\n function watchNodeKey(key) {\n const watcher = w(() => (selectedNodeKeys.value || EMPTY_SET).has(key));\n const {\n watchedNodeKeys\n } = watchedNodeStore.peek();\n let listeners = watchedNodeKeys.get(key);\n const hadListener = listeners !== undefined;\n listeners = listeners || new Set();\n listeners.add(watcher);\n if (!hadListener) {\n watchedNodeKeys.set(key, listeners);\n watchedNodeStore.value = {\n watchedNodeKeys\n };\n }\n return watcher;\n }\n return {\n watchNodeKey\n };\n },\n dependencies: [EditorStateExtension],\n name: '@lexical/extension/NodeSelection'\n});\n\n/**\n * Copyright (c) Meta Platforms, Inc. and affiliates.\n *\n * This source code is licensed under the MIT license found in the\n * LICENSE file in the root directory of this source tree.\n *\n */\n\nconst INSERT_HORIZONTAL_RULE_COMMAND = (0,lexical__WEBPACK_IMPORTED_MODULE_0__.createCommand)('INSERT_HORIZONTAL_RULE_COMMAND');\nclass HorizontalRuleNode extends lexical__WEBPACK_IMPORTED_MODULE_0__.DecoratorNode {\n static getType() {\n return 'horizontalrule';\n }\n static clone(node) {\n return new HorizontalRuleNode(node.__key);\n }\n static importJSON(serializedNode) {\n return $createHorizontalRuleNode().updateFromJSON(serializedNode);\n }\n static importDOM() {\n return {\n hr: () => ({\n conversion: $convertHorizontalRuleElement,\n priority: 0\n })\n };\n }\n exportDOM() {\n return {\n element: document.createElement('hr')\n };\n }\n createDOM(config) {\n const element = document.createElement('hr');\n (0,lexical__WEBPACK_IMPORTED_MODULE_0__.addClassNamesToElement)(element, config.theme.hr);\n return element;\n }\n getTextContent() {\n return '\\n';\n }\n isInline() {\n return false;\n }\n updateDOM() {\n return false;\n }\n}\nfunction $convertHorizontalRuleElement() {\n return {\n node: $createHorizontalRuleNode()\n };\n}\nfunction $createHorizontalRuleNode() {\n return (0,lexical__WEBPACK_IMPORTED_MODULE_0__.$create)(HorizontalRuleNode);\n}\nfunction $isHorizontalRuleNode(node) {\n return node instanceof HorizontalRuleNode;\n}\nfunction $toggleNodeSelection(node, shiftKey = false) {\n const selection = (0,lexical__WEBPACK_IMPORTED_MODULE_0__.$getSelection)();\n const wasSelected = node.isSelected();\n const key = node.getKey();\n let nodeSelection;\n if (shiftKey && (0,lexical__WEBPACK_IMPORTED_MODULE_0__.$isNodeSelection)(selection)) {\n nodeSelection = selection;\n } else {\n nodeSelection = (0,lexical__WEBPACK_IMPORTED_MODULE_0__.$createNodeSelection)();\n (0,lexical__WEBPACK_IMPORTED_MODULE_0__.$setSelection)(nodeSelection);\n }\n if (wasSelected) {\n nodeSelection.delete(key);\n } else {\n nodeSelection.add(key);\n }\n}\n\n/**\n * An extension for HorizontalRuleNode that provides an implementation that\n * works without any React dependency.\n */\nconst HorizontalRuleExtension = (0,lexical__WEBPACK_IMPORTED_MODULE_0__.defineExtension)({\n dependencies: [EditorStateExtension, NodeSelectionExtension],\n name: '@lexical/extension/HorizontalRule',\n nodes: () => [HorizontalRuleNode],\n register(editor, config, state) {\n const {\n watchNodeKey\n } = state.getDependency(NodeSelectionExtension).output;\n const nodeSelectionStore = d({\n nodeSelections: new Map()\n });\n const isSelectedClassName = editor._config.theme.hrSelected ?? 'selected';\n return (0,lexical__WEBPACK_IMPORTED_MODULE_0__.mergeRegister)(editor.registerCommand(lexical__WEBPACK_IMPORTED_MODULE_0__.CLICK_COMMAND, event => {\n if ((0,lexical__WEBPACK_IMPORTED_MODULE_0__.isDOMNode)(event.target)) {\n const node = (0,lexical__WEBPACK_IMPORTED_MODULE_0__.$getNodeFromDOMNode)(event.target);\n if ($isHorizontalRuleNode(node)) {\n $toggleNodeSelection(node, event.shiftKey);\n return true;\n }\n }\n return false;\n }, lexical__WEBPACK_IMPORTED_MODULE_0__.COMMAND_PRIORITY_LOW), editor.registerMutationListener(HorizontalRuleNode, (nodes, payload) => {\n o(() => {\n let didChange = false;\n const {\n nodeSelections\n } = nodeSelectionStore.peek();\n for (const [k, v] of nodes.entries()) {\n if (v === 'destroyed') {\n nodeSelections.delete(k);\n didChange = true;\n } else {\n const prev = nodeSelections.get(k);\n const dom = editor.getElementByKey(k);\n if (prev) {\n prev.domNode.value = dom;\n } else {\n didChange = true;\n nodeSelections.set(k, {\n domNode: d(dom),\n selectedSignal: watchNodeKey(k)\n });\n }\n }\n }\n if (didChange) {\n nodeSelectionStore.value = {\n nodeSelections\n };\n }\n });\n }), E(() => {\n const effects = [];\n for (const {\n domNode,\n selectedSignal\n } of nodeSelectionStore.value.nodeSelections.values()) {\n effects.push(E(() => {\n const dom = domNode.value;\n if (dom) {\n const isSelected = selectedSignal.value;\n if (isSelected) {\n (0,lexical__WEBPACK_IMPORTED_MODULE_0__.addClassNamesToElement)(dom, isSelectedClassName);\n } else {\n (0,lexical__WEBPACK_IMPORTED_MODULE_0__.removeClassNamesFromElement)(dom, isSelectedClassName);\n }\n }\n }));\n }\n return (0,lexical__WEBPACK_IMPORTED_MODULE_0__.mergeRegister)(...effects);\n }));\n }\n});\n\n/**\n * Copyright (c) Meta Platforms, Inc. and affiliates.\n *\n * This source code is licensed under the MIT license found in the\n * LICENSE file in the root directory of this source tree.\n *\n */\n\nfunction $indentOverTab(selection) {\n // const handled = new Set();\n const nodes = selection.getNodes();\n const canIndentBlockNodes = nodes.filter(node => (0,lexical__WEBPACK_IMPORTED_MODULE_0__.$isBlockElementNode)(node) && node.canIndent());\n // 1. If selection spans across canIndent block nodes: indent\n if (canIndentBlockNodes.length > 0) {\n return true;\n }\n // 2. If first (anchor/focus) is at block start: indent\n const anchor = selection.anchor;\n const focus = selection.focus;\n const first = focus.isBefore(anchor) ? focus : anchor;\n const firstNode = first.getNode();\n const firstBlock = (0,_lexical_utils__WEBPACK_IMPORTED_MODULE_1__.$getNearestBlockElementAncestorOrThrow)(firstNode);\n if (firstBlock.canIndent()) {\n const firstBlockKey = firstBlock.getKey();\n let selectionAtStart = (0,lexical__WEBPACK_IMPORTED_MODULE_0__.$createRangeSelection)();\n selectionAtStart.anchor.set(firstBlockKey, 0, 'element');\n selectionAtStart.focus.set(firstBlockKey, 0, 'element');\n selectionAtStart = (0,lexical__WEBPACK_IMPORTED_MODULE_0__.$normalizeSelection__EXPERIMENTAL)(selectionAtStart);\n if (selectionAtStart.anchor.is(first)) {\n return true;\n }\n }\n // 3. Else: tab\n return false;\n}\nfunction $defaultCanIndent(node) {\n return node.canBeEmpty();\n}\nfunction registerTabIndentation(editor, maxIndent, $canIndent = $defaultCanIndent) {\n return (0,lexical__WEBPACK_IMPORTED_MODULE_0__.mergeRegister)(editor.registerCommand(lexical__WEBPACK_IMPORTED_MODULE_0__.KEY_TAB_COMMAND, event => {\n const selection = (0,lexical__WEBPACK_IMPORTED_MODULE_0__.$getSelection)();\n if (!(0,lexical__WEBPACK_IMPORTED_MODULE_0__.$isRangeSelection)(selection)) {\n return false;\n }\n event.preventDefault();\n const command = $indentOverTab(selection) ? event.shiftKey ? lexical__WEBPACK_IMPORTED_MODULE_0__.OUTDENT_CONTENT_COMMAND : lexical__WEBPACK_IMPORTED_MODULE_0__.INDENT_CONTENT_COMMAND : lexical__WEBPACK_IMPORTED_MODULE_0__.INSERT_TAB_COMMAND;\n return editor.dispatchCommand(command, undefined);\n }, lexical__WEBPACK_IMPORTED_MODULE_0__.COMMAND_PRIORITY_EDITOR), editor.registerCommand(lexical__WEBPACK_IMPORTED_MODULE_0__.INDENT_CONTENT_COMMAND, () => {\n const currentMaxIndent = typeof maxIndent === 'number' ? maxIndent : maxIndent ? maxIndent.peek() : null;\n const selection = (0,lexical__WEBPACK_IMPORTED_MODULE_0__.$getSelection)();\n if (!(0,lexical__WEBPACK_IMPORTED_MODULE_0__.$isRangeSelection)(selection)) {\n return false;\n }\n const $currentCanIndent = typeof $canIndent === 'function' ? $canIndent : $canIndent.peek();\n return (0,_lexical_utils__WEBPACK_IMPORTED_MODULE_1__.$handleIndentAndOutdent)(block => {\n if ($currentCanIndent(block)) {\n const newIndent = block.getIndent() + 1;\n if (!currentMaxIndent || newIndent < currentMaxIndent) {\n block.setIndent(newIndent);\n }\n }\n });\n }, lexical__WEBPACK_IMPORTED_MODULE_0__.COMMAND_PRIORITY_CRITICAL));\n}\n/**\n * This extension adds the ability to indent content using the tab key. Generally, we don't\n * recommend using this plugin as it could negatively affect accessibility for keyboard\n * users, causing focus to become trapped within the editor.\n */\nconst TabIndentationExtension = (0,lexical__WEBPACK_IMPORTED_MODULE_0__.defineExtension)({\n build(editor, config, state) {\n return namedSignals(config);\n },\n config: (0,lexical__WEBPACK_IMPORTED_MODULE_0__.safeCast)({\n $canIndent: $defaultCanIndent,\n disabled: false,\n maxIndent: null\n }),\n name: '@lexical/extension/TabIndentation',\n register(editor, config, state) {\n const {\n disabled,\n maxIndent,\n $canIndent\n } = state.getOutput();\n return E(() => {\n if (!disabled.value) {\n return registerTabIndentation(editor, maxIndent, $canIndent);\n }\n });\n }\n});\n\n\n//# sourceURL=[module]\n//# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiKHJzYykvLi9ub2RlX21vZHVsZXMvLnBucG0vQGxleGljYWwrZXh0ZW5zaW9uQDAuNDEuMC9ub2RlX21vZHVsZXMvQGxleGljYWwvZXh0ZW5zaW9uL0xleGljYWxFeHRlbnNpb24uZGV2Lm1qcyIsIm1hcHBpbmdzIjoiOzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7OztBQUFBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBOztBQUU4ekI7QUFDOXNCO0FBQ2Y7O0FBRWpHLHFDQUFxQyxhQUFhLFFBQVEsSUFBSSxPQUFPLGNBQWMsa0JBQWtCLFFBQVEsU0FBUyxJQUFJLGtCQUFrQixZQUFZLFdBQVcsUUFBUSxzQkFBc0IsT0FBTyxTQUFTLE9BQU8sSUFBSSxTQUFTLE1BQU0sSUFBSSxJQUFJLGFBQWEsY0FBYyxrQkFBa0IsSUFBSSxJQUFJLFdBQVcsUUFBUSxNQUFNLFFBQVEsY0FBYyxVQUFVLFNBQVMsSUFBSSxXQUFXLFFBQVEsTUFBTSxnQkFBZ0IsY0FBYyxxQkFBcUIsVUFBVSx3QkFBd0IsR0FBRyxrREFBa0Qsd0JBQXdCLE1BQU0sTUFBTSxpQkFBaUIsU0FBUyxrQkFBa0IsTUFBTSxpQkFBaUIsVUFBVSwwQkFBMEIsUUFBUSxXQUFXLFFBQVEsT0FBTyxVQUFVLGdCQUFnQixTQUFTLFNBQVMsY0FBYyxjQUFjLGdDQUFnQyxrQ0FBa0MsaUNBQWlDLG9CQUFvQix5QkFBeUIsY0FBYywwQkFBMEIsZUFBZSx3QkFBd0IsTUFBTSxTQUFTLG9CQUFvQixZQUFZLE1BQU0sZ0NBQWdDLEtBQUssMEJBQTBCLG9CQUFvQixrQkFBa0IsZUFBZSxNQUFNLFlBQVksZUFBZSxNQUFNLFlBQVksZUFBZSxTQUFTLHFCQUFxQixNQUFNLGdDQUFnQyxNQUFNLGtDQUFrQyxjQUFjLHVCQUF1QixTQUFTLElBQUksTUFBTSxRQUFRLE1BQU0sRUFBRSxXQUFXLEdBQUcsK0JBQStCLG1CQUFtQixnQ0FBZ0Msc0JBQXNCLDhCQUE4QixtQkFBbUIsNEJBQTRCLFVB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QTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0EsNEZBQTRGLGVBQWUsT0FBTyxpQ0FBaUM7QUFDbko7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0EsdUZBQXVGLGVBQWU7QUFDdEc7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBLFdBQVcsc0RBQWE7QUFDeEI7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0EsUUFBUTtBQUNSO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBLG1FQUFtRSxnQkFBZ0Isd0NBQXdDLG1CQUFtQixVQUFVLGtDQUFrQztBQUMxTDtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FB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RUFBRSw4REFBeUI7QUFDOUI7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0EsZ0NBQWdDLHdEQUFlO0FBQy9DO0FBQ0E7QUFDQSxHQUFHO0FBQ0gsVUFBVSxpREFBUTtBQUNsQjtBQUNBO0FBQ0E7QUFDQSxHQUFHO0FBQ0g7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0EsTUFBTTtBQUNOO0FBQ0E7QUFDQTtBQUNBO0FBQ0EsS0FBSztBQUNMO0FBQ0EsQ0FBQzs7QUFFNnFCIiwic291cmNlcyI6WyIvVXNlcnMvbWFyY21pbnRlbC9Qcm9qZWN0cy9lLXRpYi5jb20vbm9kZV9tb2R1bGVzLy5wbnBtL0BsZXhpY2FsK2V4dGVuc2lvbkAwLjQxLjAvbm9kZV9tb2R1bGVzL0BsZXhpY2FsL2V4dGVuc2lvbi9MZXhpY2FsRXh0ZW5zaW9uLmRldi5tanMiXSwic291cmNlc0NvbnRlbnQiOlsiLyoqXG4gKiBDb3B5cmlnaHQgKGMpIE1ldGEgUGxhdGZvcm1zLCBJbmMuIGFuZCBhZmZpbGlhdGVzLlxuICpcbiAqIFRoaXMgc291cmNlIGNvZGUgaXMgbGljZW5zZWQgdW5kZXIgdGhlIE1JVCBsaWNlbnNlIGZvdW5kIGluIHRoZVxuICogTElDRU5TRSBmaWxlIGluIHRoZSByb290IGRpcmVjdG9yeSBvZiB0aGlzIHNvdXJjZSB0cmVlLlxuICpcbiAqL1xuXG5pbXBvcnQgeyBkZWZpbmVFeHRlbnNpb24sIHNhZmVDYXN0LCBDTEVBUl9FRElUT1JfQ09NTUFORCwgQ09NTUFORF9QUklPUklUWV9FRElUT1IsICRnZXRSb290LCAkZ2V0U2VsZWN0aW9uLCAkY3JlYXRlUGFyYWdyYXBoTm9kZSwgJGlzUmFuZ2VTZWxlY3Rpb24sIEZPUk1BVF9URVhUX0NPTU1BTkQsICRpc05vZGVTZWxlY3Rpb24sIENPTU1BTkRfUFJJT1JJVFlfTE9XLCBEZWNvcmF0b3JOb2RlLCBjcmVhdGVTdGF0ZSwgJGdldFN0YXRlLCB0b2dnbGVUZXh0Rm9ybWF0VHlwZSwgJHNldFN0YXRlLCBURVhUX1RZUEVfVE9fRk9STUFULCBzaGFsbG93TWVyZ2VDb25maWcsIFJvb3ROb2RlLCBUZXh0Tm9kZSwgTGluZUJyZWFrTm9kZSwgVGFiTm9kZSwgUGFyYWdyYXBoTm9kZSwgJGlzRWRpdG9yU3RhdGUsIEhJU1RPUllfTUVSR0VfVEFHLCBjcmVhdGVFZGl0b3IsIG1lcmdlUmVnaXN0ZXIsICRnZXROb2RlQnlLZXksIGNyZWF0ZUNvbW1hbmQsICRjcmVhdGUsIENMSUNLX0NPTU1BTkQsIGlzRE9NTm9kZSwgJGdldE5vZGVGcm9tRE9NTm9kZSwgYWRkQ2xhc3NOYW1lc1RvRWxlbWVudCwgJGNyZWF0ZU5vZGVTZWxlY3Rpb24sICRzZXRTZWxlY3Rpb24sIHJlbW92ZUNsYXNzTmFtZXNGcm9tRWxlbWVudCwgS0VZX1RBQl9DT01NQU5ELCBPVVRERU5UX0NPTlRFTlRfQ09NTUFORCwgSU5ERU5UX0NPTlRFTlRfQ09NTUFORCwgSU5TRVJUX1RBQl9DT01NQU5ELCBDT01NQU5EX1BSSU9SSVRZX0NSSVRJQ0FMLCAkaXNCbG9ja0VsZW1lbnROb2RlLCAkY3JlYXRlUmFuZ2VTZWxlY3Rpb24sICRub3JtYWxpemVTZWxlY3Rpb25fX0VYUEVSSU1FTlRBTCB9IGZyb20gJ2xleGljYWwnO1xuZXhwb3J0IHsgY29uZmlnRXh0ZW5zaW9uLCBkZWNsYXJlUGVlckRlcGVuZGVuY3ksIGRlZmluZUV4dGVuc2lvbiwgc2FmZUNhc3QsIHNoYWxsb3dNZXJnZUNvbmZpZyB9IGZyb20gJ2xleGljYWwnO1xuaW1wb3J0IHsgJGhhbmRsZUluZGVudEFuZE91dGRlbnQsICRnZXROZWFyZXN0QmxvY2tFbGVtZW50QW5jZXN0b3JPclRocm93IH0gZnJvbSAnQGxleGljYWwvdXRpbHMnO1xuXG5jb25zdCBpPVN5bWJvbC5mb3IoXCJwcmVhY3Qtc2lnbmFsc1wiKTtmdW5jdGlvbiB0KCl7aWYocj4xKXtyLS07cmV0dXJufWxldCBpLHQ9ZmFsc2U7d2hpbGUodm9pZCAwIT09cyl7bGV0IG89cztzPXZvaWQgMDtmKys7d2hpbGUodm9pZCAwIT09byl7Y29uc3Qgbj1vLm87by5vPXZvaWQgMDtvLmYmPS0zO2lmKCEoOCZvLmYpJiZ2KG8pKXRyeXtvLmMoKTt9Y2F0Y2gobyl7aWYoIXQpe2k9bzt0PXRydWU7fX1vPW47fX1mPTA7ci0tO2lmKHQpdGhyb3cgaX1mdW5jdGlvbiBvKGkpe2lmKHI+MClyZXR1cm4gaSgpO3IrKzt0cnl7cmV0dXJuIGkoKX1maW5hbGx5e3QoKTt9fWxldCBuLHM7ZnVuY3Rpb24gaChpKXtjb25zdCB0PW47bj12b2lkIDA7dHJ5e3JldHVybiBpKCl9ZmluYWxseXtuPXQ7fX1sZXQgcj0wLGY9MCxlPTA7ZnVuY3Rpb24gdShpKXtpZih2b2lkIDA9PT1uKXJldHVybjtsZXQgdD1pLm47aWYodm9pZCAwPT09dHx8dC50IT09bil7dD17aTowLFM6aSxwOm4ucyxuOnZvaWQgMCx0Om4sZTp2b2lkIDAseDp2b2lkIDAscjp0fTtpZih2b2lkIDAhPT1uLnMpbi5zLm49dDtuLnM9dDtpLm49dDtpZigzMiZuLmYpaS5TKHQpO3JldHVybiB0fWVsc2UgaWYoLTE9PT10Lmkpe3QuaT0wO2lmKHZvaWQgMCE9PXQubil7dC5uLnA9dC5wO2lmKHZvaWQgMCE9PXQucCl0LnAubj10Lm47dC5wPW4uczt0Lm49dm9pZCAwO24ucy5uPXQ7bi5zPXQ7fXJldHVybiB0fX1mdW5jdGlvbiBjKGksdCl7dGhpcy52PWk7dGhpcy5pPTA7dGhpcy5uPXZvaWQgMDt0aGlzLnQ9dm9pZCAwO3RoaXMuVz1udWxsPT10P3ZvaWQgMDp0LndhdGNoZWQ7dGhpcy5aPW51bGw9PXQ/dm9pZCAwOnQudW53YXRjaGVkO3RoaXMubmFtZT1udWxsPT10P3ZvaWQgMDp0Lm5hbWU7fWMucHJvdG90eXBlLmJyYW5kPWk7Yy5wcm90b3R5cGUuaD1mdW5jdGlvbigpe3JldHVybiAgdHJ1ZX07Yy5wcm90b3R5cGUuUz1mdW5jdGlvbihpKXtjb25zdCB0PXRoaXMudDtpZih0IT09aSYmdm9pZCAwPT09aS5lKXtpLng9dDt0aGlzLnQ9aTtpZih2b2lkIDAhPT10KXQuZT1pO2Vsc2UgaCgoKT0+e3ZhciBpO251bGw9PShpPXRoaXMuVyl8fGkuY2FsbCh0aGlzKTt9KTt9fTtjLnByb3RvdHlwZS5VPWZ1bmN0aW9uKGkpe2lmKHZvaWQgMCE9PXRoaXMudCl7Y29uc3QgdD1pLmUsbz1pLng7aWYodm9pZCAwIT09dCl7dC54PW87aS5lPXZvaWQgMDt9aWYodm9pZCAwIT09byl7by5lPXQ7aS54PXZvaWQgMDt9aWYoaT09PXRoaXMudCl7dGhpcy50PW87aWYodm9pZCAwPT09byloKCgpPT57dmFyIGk7bnVsbD09KGk9dGhpcy5aKXx8aS5jYWxsKHRoaXMpO30pO319fTtjLnByb3RvdHlwZS5zdWJzY3JpYmU9ZnVuY3Rpb24oaSl7cmV0dXJuIEUoKCk9Pntjb25zdCB0PXRoaXMudmFsdWUsbz1uO249dm9pZCAwO3RyeXtpKHQpO31maW5hbGx5e249bzt9fSx7bmFtZTpcInN1YlwifSl9O2MucHJvdG90eXBlLnZhbHVlT2Y9ZnVuY3Rpb24oKXtyZXR1cm4gdGhpcy52YWx1ZX07Yy5wcm90b3R5cGUudG9TdHJpbmc9ZnVuY3Rpb24oKXtyZXR1cm4gdGhpcy52YWx1ZStcIlwifTtjLnByb3RvdHlwZS50b0pTT049ZnVuY3Rpb24oKXtyZXR1cm4gdGhpcy52YWx1ZX07Yy5wcm90b3R5cGUucGVlaz1mdW5jdGlvbigpe2NvbnN0IGk9bjtuPXZvaWQgMDt0cnl7cmV0dXJuIHRoaXMudmFsdWV9ZmluYWxseXtuPWk7fX07T2JqZWN0LmRlZmluZVByb3BlcnR5KGMucHJvdG90eXBlLFwidmFsdWVcIix7Z2V0KCl7Y29uc3QgaT11KHRoaXMpO2lmKHZvaWQgMCE9PWkpaS5pPXRoaXMuaTtyZXR1cm4gdGhpcy52fSxzZXQoaSl7aWYoaSE9PXRoaXMudil7aWYoZj4xMDApdGhyb3cgbmV3IEVycm9yKFwiQ3ljbGUgZGV0ZWN0ZWRcIik7dGhpcy52PWk7dGhpcy5pKys7ZSsrO3IrKzt0cnl7Zm9yKGxldCBpPXRoaXMudDt2b2lkIDAhPT1pO2k9aS54KWkudC5OKCk7fWZpbmFsbHl7dCgpO319fX0pO2Z1bmN0aW9uIGQoaSx0KXtyZXR1cm4gbmV3IGMoaSx0KX1mdW5jdGlvbiB2KGkpe2ZvcihsZXQgdD1pLnM7dm9pZCAwIT09dDt0PXQubilpZih0LlMuaSE9PXQuaXx8IXQuUy5oKCl8fHQuUy5pIT09dC5pKXJldHVybiAgdHJ1ZTtyZXR1cm4gIGZhbHNlfWZ1bmN0aW9uIGwoaSl7Zm9yKGxldCB0PWkuczt2b2lkIDAhPT10O3Q9dC5uKXtjb25zdCBvPXQuUy5uO2lmKHZvaWQgMCE9PW8pdC5yPW87dC5TLm49dDt0Lmk9LTE7aWYodm9pZCAwPT09dC5uKXtpLnM9dDticmVha319fWZ1bmN0aW9uIHkoaSl7bGV0IHQsbz1pLnM7d2hpbGUodm9pZCAwIT09byl7Y29uc3QgaT1vLnA7aWYoLTE9PT1vLmkpe28uUy5VKG8pO2lmKHZvaWQgMCE9PWkpaS5uPW8ubjtpZih2b2lkIDAhPT1vLm4pby5uLnA9aTt9ZWxzZSB0PW87by5TLm49by5yO2lmKHZvaWQgMCE9PW8ucilvLnI9dm9pZCAwO289aTt9aS5zPXQ7fWZ1bmN0aW9uIGEoaSx0KXtjLmNhbGwodGhpcyx2b2lkIDApO3RoaXMueD1pO3RoaXMucz12b2lkIDA7dGhpcy5nPWUtMTt0aGlzLmY9NDt0aGlzLlc9bnVsbD09dD92b2lkIDA6dC53YXRjaGVkO3RoaXMuWj1udWxsPT10P3ZvaWQgMDp0LnVud2F0Y2hlZDt0aGlzLm5hbWU9bnVsbD09dD92b2lkIDA6dC5uYW1lO31hLnByb3RvdHlwZT1uZXcgYzthLnByb3RvdHlwZS5oPWZ1bmN0aW9uKCl7dGhpcy5mJj0tMztpZigxJnRoaXMuZilyZXR1cm4gIGZhbHNlO2lmKDMyPT0oMzYmdGhpcy5mKSlyZXR1cm4gIHRydWU7dGhpcy5mJj0tNTtpZih0aGlzLmc9PT1lKXJldHVybiAgdHJ1ZTt0aGlzLmc9ZTt0aGlzLmZ8PTE7aWYodGhpcy5pPjAmJiF2KHRoaXMpKXt0aGlzLmYmPS0yO3JldHVybiAgdHJ1ZX1jb25zdCBpPW47dHJ5e2wodGhpcyk7bj10aGlzO2NvbnN0IGk9dGhpcy54KCk7aWYoMTYmdGhpcy5mfHx0aGlzLnYhPT1pfHwwPT09dGhpcy5pKXt0aGlzLnY9aTt0aGlzLmYmPS0xNzt0aGlzLmkrKzt9fWNhdGNoKGkpe3RoaXMudj1pO3RoaXMuZnw9MTY7dGhpcy5pKys7fW49aTt5KHRoaXMpO3RoaXMuZiY9LTI7cmV0dXJuICB0cnVlfTthLnByb3RvdHlwZS5TPWZ1bmN0aW9uKGkpe2lmKHZvaWQgMD09PXRoaXMudCl7dGhpcy5mfD0zNjtmb3IobGV0IGk9dGhpcy5zO3ZvaWQgMCE9PWk7aT1pLm4paS5TLlMoaSk7fWMucHJvdG90eXBlLlMuY2FsbCh0aGlzLGkpO307YS5wcm90b3R5cGUuVT1mdW5jdGlvbihpKXtpZih2b2lkIDAhPT10aGlzLnQpe2MucHJvdG90eXBlLlUuY2FsbCh0aGlzLGkpO2lmKHZvaWQgMD09PXRoaXMudCl7dGhpcy5mJj0tMzM7Zm9yKGxldCBpPXRoaXMuczt2b2lkIDAhPT1pO2k9aS5uKWkuUy5VKGkpO319fTthLnByb3RvdHlwZS5OPWZ1bmN0aW9uKCl7aWYoISgyJnRoaXMuZikpe3RoaXMuZnw9Njtmb3IobGV0IGk9dGhpcy50O3ZvaWQgMCE9PWk7aT1pLngpaS50Lk4oKTt9fTtPYmplY3QuZGVmaW5lUHJvcGVydHkoYS5wcm90b3R5cGUsXCJ2YWx1ZVwiLHtnZXQoKXtpZigxJnRoaXMuZil0aHJvdyBuZXcgRXJyb3IoXCJDeWNsZSBkZXRlY3RlZFwiKTtjb25zdCBpPXUodGhpcyk7dGhpcy5oKCk7aWYodm9pZCAwIT09aSlpLmk9dGhpcy5pO2lmKDE2JnRoaXMuZil0aHJvdyB0aGlzLnY7cmV0dXJuIHRoaXMudn19KTtmdW5jdGlvbiB3KGksdCl7cmV0dXJuIG5ldyBhKGksdCl9ZnVuY3Rpb24gXyhpKXtjb25zdCBvPWkudTtpLnU9dm9pZCAwO2lmKFwiZnVuY3Rpb25cIj09dHlwZW9mIG8pe3IrKztjb25zdCBzPW47bj12b2lkIDA7dHJ5e28oKTt9Y2F0Y2godCl7aS5mJj0tMjtpLmZ8PTg7YihpKTt0aHJvdyB0fWZpbmFsbHl7bj1zO3QoKTt9fX1mdW5jdGlvbiBiKGkpe2ZvcihsZXQgdD1pLnM7dm9pZCAwIT09dDt0PXQubil0LlMuVSh0KTtpLng9dm9pZCAwO2kucz12b2lkIDA7XyhpKTt9ZnVuY3Rpb24gZyhpKXtpZihuIT09dGhpcyl0aHJvdyBuZXcgRXJyb3IoXCJPdXQtb2Ytb3JkZXIgZWZmZWN0XCIpO3kodGhpcyk7bj1pO3RoaXMuZiY9LTI7aWYoOCZ0aGlzLmYpYih0aGlzKTt0KCk7fWZ1bmN0aW9uIHAoaSx0KXt0aGlzLng9aTt0aGlzLnU9dm9pZCAwO3RoaXMucz12b2lkIDA7dGhpcy5vPXZvaWQgMDt0aGlzLmY9MzI7dGhpcy5uYW1lPW51bGw9PXQ/dm9pZCAwOnQubmFtZTt9cC5wcm90b3R5cGUuYz1mdW5jdGlvbigpe2NvbnN0IGk9dGhpcy5TKCk7dHJ5e2lmKDgmdGhpcy5mKXJldHVybjtpZih2b2lkIDA9PT10aGlzLngpcmV0dXJuO2NvbnN0IHQ9dGhpcy54KCk7aWYoXCJmdW5jdGlvblwiPT10eXBlb2YgdCl0aGlzLnU9dDt9ZmluYWxseXtpKCk7fX07cC5wcm90b3R5cGUuUz1mdW5jdGlvbigpe2lmKDEmdGhpcy5mKXRocm93IG5ldyBFcnJvcihcIkN5Y2xlIGRldGVjdGVkXCIpO3RoaXMuZnw9MTt0aGlzLmYmPS05O18odGhpcyk7bCh0aGlzKTtyKys7Y29uc3QgaT1uO249dGhpcztyZXR1cm4gZy5iaW5kKHRoaXMsaSl9O3AucHJvdG90eXBlLk49ZnVuY3Rpb24oKXtpZighKDImdGhpcy5mKSl7dGhpcy5mfD0yO3RoaXMubz1zO3M9dGhpczt9fTtwLnByb3RvdHlwZS5kPWZ1bmN0aW9uKCl7dGhpcy5mfD04O2lmKCEoMSZ0aGlzLmYpKWIodGhpcyk7fTtwLnByb3RvdHlwZS5kaXNwb3NlPWZ1bmN0aW9uKCl7dGhpcy5kKCk7fTtmdW5jdGlvbiBFKGksdCl7Y29uc3Qgbz1uZXcgcChpLHQpO3RyeXtvLmMoKTt9Y2F0Y2goaSl7by5kKCk7dGhyb3cgaX1jb25zdCBuPW8uZC5iaW5kKG8pO25bU3ltYm9sLmRpc3Bvc2VdPW47cmV0dXJuIG59XG5cbi8qKlxuICogQ29weXJpZ2h0IChjKSBNZXRhIFBsYXRmb3JtcywgSW5jLiBhbmQgYWZmaWxpYXRlcy5cbiAqXG4gKiBUaGlzIHNvdXJjZSBjb2RlIGlzIGxpY2Vuc2VkIHVuZGVyIHRoZSBNSVQgbGljZW5zZSBmb3VuZCBpbiB0aGVcbiAqIExJQ0VOU0UgZmlsZSBpbiB0aGUgcm9vdCBkaXJlY3Rvcnkgb2YgdGhpcyBzb3VyY2UgdHJlZS5cbiAqXG4gKi9cbi8qKlxuICogQGV4cGVyaW1lbnRhbFxuICogUmV0dXJuIGFuIG9iamVjdCB3aXRoIHRoZSBzYW1lIHNoYXBlIGFzIGBkZWZhdWx0c2Agd2l0aCBhIHtAbGluayBTaWduYWx9XG4gKiBmb3IgZWFjaCB2YWx1ZS4gSWYgc3BlY2lmaWVkLCB0aGUgc2Vjb25kIGBvcHRzYCBhcmd1bWVudCBpcyBhIHBhcnRpYWxcbiAqIG9mIG92ZXJyaWRlcyB0byB0aGUgZGVmYXVsdHMgYW5kIHdpbGwgYmUgdXNlZCBhcyB0aGUgaW5pdGlhbCB2YWx1ZS5cbiAqXG4gKiBUeXBpY2FsbHkgdXNlZCB0byBtYWtlIGEgcmVhY3RpdmUgdmVyc2lvbiBvZiBzb21lIHN1YnNldCBvZiB0aGVcbiAqIGNvbmZpZ3VyYXRpb24gb2YgYW4gZXh0ZW5zaW9uLCBzbyBpdCBjYW4gYmUgcmVjb25maWd1cmVkIGF0IHJ1bnRpbWUuXG4gKlxuICogQHBhcmFtIGRlZmF1bHRzIFRoZSBvYmplY3Qgd2l0aCBkZWZhdWx0IHZhbHVlc1xuICogQHBhcmFtIG9wdHMgT3ZlcnJpZGVzIHRvIHRob3NlIGRlZmF1bHQgdmFsdWVzXG4gKiBAcmV0dXJucyBBbiBvYmplY3Qgd2l0aCBzaWduYWxzIGluaXRpYWxpemVkIHdpdGggdGhlIGRlZmF1bHQgdmFsdWVzXG4gKi9cbmZ1bmN0aW9uIG5hbWVkU2lnbmFscyhkZWZhdWx0cywgb3B0cyA9IHt9KSB7XG4gIC8vIGVzbGludC1kaXNhYmxlLW5leHQtbGluZSBAdHlwZXNjcmlwdC1lc2xpbnQvbm8tZXhwbGljaXQtYW55XG4gIGNvbnN0IGluaXRpYWwgPSB7fTtcbiAgZm9yIChjb25zdCBrIGluIGRlZmF1bHRzKSB7XG4gICAgY29uc3QgdiA9IG9wdHNba107XG4gICAgY29uc3Qgc3RvcmUgPSBkKHYgPT09IHVuZGVmaW5lZCA/IGRlZmF1bHRzW2tdIDogdik7XG4gICAgaW5pdGlhbFtrXSA9IHN0b3JlO1xuICB9XG4gIHJldHVybiBpbml0aWFsO1xufVxuXG4vKipcbiAqIENvcHlyaWdodCAoYykgTWV0YSBQbGF0Zm9ybXMsIEluYy4gYW5kIGFmZmlsaWF0ZXMuXG4gKlxuICogVGhpcyBzb3VyY2UgY29kZSBpcyBsaWNlbnNlZCB1bmRlciB0aGUgTUlUIGxpY2Vuc2UgZm91bmQgaW4gdGhlXG4gKiBMSUNFTlNFIGZpbGUgaW4gdGhlIHJvb3QgZGlyZWN0b3J5IG9mIHRoaXMgc291cmNlIHRyZWUuXG4gKlxuICovXG5cbi8qKlxuICogQW4gRXh0ZW5zaW9uIHRvIGZvY3VzIHRoZSBMZXhpY2FsRWRpdG9yIHdoZW4gdGhlIHJvb3QgZWxlbWVudCBpcyBzZXRcbiAqICh0eXBpY2FsbHkgb25seSB3aGVuIHRoZSBlZGl0b3IgaXMgZmlyc3QgY3JlYXRlZCkuXG4gKi9cbmNvbnN0IEF1dG9Gb2N1c0V4dGVuc2lvbiA9IGRlZmluZUV4dGVuc2lvbih7XG4gIGJ1aWxkOiAoZWRpdG9yLCBjb25maWcsIHN0YXRlKSA9PiB7XG4gICAgcmV0dXJuIG5hbWVkU2lnbmFscyhjb25maWcpO1xuICB9LFxuICBjb25maWc6IHNhZmVDYXN0KHtcbiAgICBkZWZhdWx0U2VsZWN0aW9uOiAncm9vdEVuZCcsXG4gICAgZGlzYWJsZWQ6IGZhbHNlXG4gIH0pLFxuICBuYW1lOiAnQGxleGljYWwvZXh0ZW5zaW9uL0F1dG9Gb2N1cycsXG4gIHJlZ2lzdGVyKGVkaXRvciwgY29uZmlnLCBzdGF0ZSkge1xuICAgIGNvbnN0IHN0b3JlcyA9IHN0YXRlLmdldE91dHB1dCgpO1xuICAgIHJldHVybiBFKCgpID0+IHN0b3Jlcy5kaXNhYmxlZC52YWx1ZSA/IHVuZGVmaW5lZCA6IGVkaXRvci5yZWdpc3RlclJvb3RMaXN0ZW5lcihyb290RWxlbWVudCA9PiB7XG4gICAgICBlZGl0b3IuZm9jdXMoKCkgPT4ge1xuICAgICAgICAvLyBJZiB3ZSB0cnkgYW5kIG1vdmUgc2VsZWN0aW9uIHRvIHRoZSBzYW1lIHBvaW50IHdpdGggc2V0QmFzZUFuZEV4dGVudCwgaXQgd29uJ3RcbiAgICAgICAgLy8gdHJpZ2dlciBhIHJlLWZvY3VzIG9uIHRoZSBlbGVtZW50LiBTbyBpbiB0aGUgY2FzZSB0aGlzIG9jY3Vycywgd2UnbGwgbmVlZCB0byBjb3JyZWN0IGl0LlxuICAgICAgICAvLyBOb3JtYWxseSB0aGlzIGlzIGZpbmUsIFNlbGVjdGlvbiBBUEkgIT09IEZvY3VzIEFQSSwgYnV0IGZvcmUgdGhlIGludGVudHMgb2YgdGhlIG5hbWluZ1xuICAgICAgICAvLyBvZiB0aGlzIHBsdWdpbiwgd2hpY2ggc2hvdWxkIHByZXNlcnZlIGZvY3VzIHRvby5cbiAgICAgICAgY29uc3QgYWN0aXZlRWxlbWVudCA9IGRvY3VtZW50LmFjdGl2ZUVsZW1lbnQ7XG4gICAgICAgIGlmIChyb290RWxlbWVudCAhPT0gbnVsbCAmJiAoYWN0aXZlRWxlbWVudCA9PT0gbnVsbCB8fCAhcm9vdEVsZW1lbnQuY29udGFpbnMoYWN0aXZlRWxlbWVudCkpKSB7XG4gICAgICAgICAgLy8gTm90ZTogcHJldmVudFNjcm9sbCB3b24ndCB3b3JrIGluIFdlYmtpdC5cbiAgICAgICAgICByb290RWxlbWVudC5mb2N1cyh7XG4gICAgICAgICAgICBwcmV2ZW50U2Nyb2xsOiB0cnVlXG4gICAgICAgICAgfSk7XG4gICAgICAgIH1cbiAgICAgIH0sIHtcbiAgICAgICAgZGVmYXVsdFNlbGVjdGlvbjogc3RvcmVzLmRlZmF1bHRTZWxlY3Rpb24ucGVlaygpXG4gICAgICB9KTtcbiAgICB9KSk7XG4gIH1cbn0pO1xuXG4vKipcbiAqIENvcHlyaWdodCAoYykgTWV0YSBQbGF0Zm9ybXMsIEluYy4gYW5kIGFmZmlsaWF0ZXMuXG4gKlxuICogVGhpcyBzb3VyY2UgY29kZSBpcyBsaWNlbnNlZCB1bmRlciB0aGUgTUlUIGxpY2Vuc2UgZm91bmQgaW4gdGhlXG4gKiBMSUNFTlNFIGZpbGUgaW4gdGhlIHJvb3QgZGlyZWN0b3J5IG9mIHRoaXMgc291cmNlIHRyZWUuXG4gKlxuICovXG5cbmZ1bmN0aW9uICRkZWZhdWx0T25DbGVhcigpIHtcbiAgY29uc3Qgcm9vdCA9ICRnZXRSb290KCk7XG4gIGNvbnN0IHNlbGVjdGlvbiA9ICRnZXRTZWxlY3Rpb24oKTtcbiAgY29uc3QgcGFyYWdyYXBoID0gJGNyZWF0ZVBhcmFncmFwaE5vZGUoKTtcbiAgcm9vdC5jbGVhcigpO1xuICByb290LmFwcGVuZChwYXJhZ3JhcGgpO1xuICBpZiAoc2VsZWN0aW9uICE9PSBudWxsKSB7XG4gICAgcGFyYWdyYXBoLnNlbGVjdCgpO1xuICB9XG4gIGlmICgkaXNSYW5nZVNlbGVjdGlvbihzZWxlY3Rpb24pKSB7XG4gICAgc2VsZWN0aW9uLmZvcm1hdCA9IDA7XG4gIH1cbn1cbmZ1bmN0aW9uIHJlZ2lzdGVyQ2xlYXJFZGl0b3IoZWRpdG9yLCAkb25DbGVhciA9ICRkZWZhdWx0T25DbGVhcikge1xuICByZXR1cm4gZWRpdG9yLnJlZ2lzdGVyQ29tbWFuZChDTEVBUl9FRElUT1JfQ09NTUFORCwgcGF5bG9hZCA9PiB7XG4gICAgZWRpdG9yLnVwZGF0ZSgkb25DbGVhcik7XG4gICAgcmV0dXJuIHRydWU7XG4gIH0sIENPTU1BTkRfUFJJT1JJVFlfRURJVE9SKTtcbn1cblxuLyoqXG4gKiBBbiBleHRlbnNpb24gdG8gcHJvdmlkZSBhbiBpbXBsZW1lbnRhdGlvbiBvZiB7QGxpbmsgQ0xFQVJfRURJVE9SX0NPTU1BTkR9XG4gKi9cbmNvbnN0IENsZWFyRWRpdG9yRXh0ZW5zaW9uID0gZGVmaW5lRXh0ZW5zaW9uKHtcbiAgYnVpbGQoZWRpdG9yLCBjb25maWcsIHN0YXRlKSB7XG4gICAgcmV0dXJuIG5hbWVkU2lnbmFscyhjb25maWcpO1xuICB9LFxuICBjb25maWc6IHNhZmVDYXN0KHtcbiAgICAkb25DbGVhcjogJGRlZmF1bHRPbkNsZWFyXG4gIH0pLFxuICBuYW1lOiAnQGxleGljYWwvZXh0ZW5zaW9uL0NsZWFyRWRpdG9yJyxcbiAgcmVnaXN0ZXIoZWRpdG9yLCBjb25maWcsIHN0YXRlKSB7XG4gICAgY29uc3Qge1xuICAgICAgJG9uQ2xlYXJcbiAgICB9ID0gc3RhdGUuZ2V0T3V0cHV0KCk7XG4gICAgcmV0dXJuIEUoKCkgPT4gcmVnaXN0ZXJDbGVhckVkaXRvcihlZGl0b3IsICRvbkNsZWFyLnZhbHVlKSk7XG4gIH1cbn0pO1xuXG4vKipcbiAqIENvcHlyaWdodCAoYykgTWV0YSBQbGF0Zm9ybXMsIEluYy4gYW5kIGFmZmlsaWF0ZXMuXG4gKlxuICogVGhpcyBzb3VyY2UgY29kZSBpcyBsaWNlbnNlZCB1bmRlciB0aGUgTUlUIGxpY2Vuc2UgZm91bmQgaW4gdGhlXG4gKiBMSUNFTlNFIGZpbGUgaW4gdGhlIHJvb3QgZGlyZWN0b3J5IG9mIHRoaXMgc291cmNlIHRyZWUuXG4gKlxuICovXG5cbi8qKlxuICogQGV4cGVyaW1lbnRhbFxuICogR2V0IHRoZSBzZXRzIG9mIG5vZGVzIGFuZCB0eXBlcyByZWdpc3RlcmVkIGluIHRoZVxuICoge0BsaW5rIEluaXRpYWxFZGl0b3JDb25maWd9LiBUaGlzIGlzIHRvIGJlIHVzZWQgd2hlbiBhbiBleHRlbnNpb25cbiAqIG5lZWRzIHRvIHJlZ2lzdGVyIG9wdGlvbmFsIGJlaGF2aW9yIGlmIHNvbWUgbm9kZSBvciB0eXBlIGlzIHByZXNlbnQuXG4gKlxuICogQHBhcmFtIGNvbmZpZyBUaGUgSW5pdGlhbEVkaXRvckNvbmZpZyAoYWNjZXNzaWJsZSBmcm9tIGFuIGV4dGVuc2lvbidzIGluaXQpXG4gKiBAcmV0dXJucyBUaGUga25vd24gdHlwZXMgYW5kIG5vZGVzIGFzIFNldHNcbiAqL1xuZnVuY3Rpb24gZ2V0S25vd25UeXBlc0FuZE5vZGVzKGNvbmZpZykge1xuICBjb25zdCB0eXBlcyA9IG5ldyBTZXQoKTtcbiAgY29uc3Qgbm9kZXMgPSBuZXcgU2V0KCk7XG4gIGZvciAoY29uc3Qga2xhc3NPclJlcGxhY2VtZW50IG9mIGdldE5vZGVDb25maWcoY29uZmlnKSkge1xuICAgIGNvbnN0IGtsYXNzID0gdHlwZW9mIGtsYXNzT3JSZXBsYWNlbWVudCA9PT0gJ2Z1bmN0aW9uJyA/IGtsYXNzT3JSZXBsYWNlbWVudCA6IGtsYXNzT3JSZXBsYWNlbWVudC5yZXBsYWNlO1xuICAgIHR5cGVzLmFkZChrbGFzcy5nZXRUeXBlKCkpO1xuICAgIG5vZGVzLmFkZChrbGFzcyk7XG4gIH1cbiAgcmV0dXJuIHtcbiAgICBub2RlcyxcbiAgICB0eXBlc1xuICB9O1xufVxuZnVuY3Rpb24gZ2V0Tm9kZUNvbmZpZyhjb25maWcpIHtcbiAgcmV0dXJuICh0eXBlb2YgY29uZmlnLm5vZGVzID09PSAnZnVuY3Rpb24nID8gY29uZmlnLm5vZGVzKCkgOiBjb25maWcubm9kZXMpIHx8IFtdO1xufVxuXG4vKipcbiAqIENvcHlyaWdodCAoYykgTWV0YSBQbGF0Zm9ybXMsIEluYy4gYW5kIGFmZmlsaWF0ZXMuXG4gKlxuICogVGhpcyBzb3VyY2UgY29kZSBpcyBsaWNlbnNlZCB1bmRlciB0aGUgTUlUIGxpY2Vuc2UgZm91bmQgaW4gdGhlXG4gKiBMSUNFTlNFIGZpbGUgaW4gdGhlIHJvb3QgZGlyZWN0b3J5IG9mIHRoaXMgc291cmNlIHRyZWUuXG4gKlxuICovXG5cbmNvbnN0IGZvcm1hdFN0YXRlID0gY3JlYXRlU3RhdGUoJ2Zvcm1hdCcsIHtcbiAgcGFyc2U6IHZhbHVlID0+IHR5cGVvZiB2YWx1ZSA9PT0gJ251bWJlcicgPyB2YWx1ZSA6IDBcbn0pO1xuY2xhc3MgRGVjb3JhdG9yVGV4dE5vZGUgZXh0ZW5kcyBEZWNvcmF0b3JOb2RlIHtcbiAgJGNvbmZpZygpIHtcbiAgICByZXR1cm4gdGhpcy5jb25maWcoJ2RlY29yYXRvci10ZXh0Jywge1xuICAgICAgZXh0ZW5kczogRGVjb3JhdG9yTm9kZSxcbiAgICAgIHN0YXRlQ29uZmlnczogW3tcbiAgICAgICAgZmxhdDogdHJ1ZSxcbiAgICAgICAgc3RhdGVDb25maWc6IGZvcm1hdFN0YXRlXG4gICAgICB9XVxuICAgIH0pO1xuICB9XG4gIGdldEZvcm1hdCgpIHtcbiAgICByZXR1cm4gJGdldFN0YXRlKHRoaXMsIGZvcm1hdFN0YXRlKTtcbiAgfVxuICBnZXRGb3JtYXRGbGFncyh0eXBlLCBhbGlnbldpdGhGb3JtYXQpIHtcbiAgICByZXR1cm4gdG9nZ2xlVGV4dEZvcm1hdFR5cGUodGhpcy5nZXRGb3JtYXQoKSwgdHlwZSwgYWxpZ25XaXRoRm9ybWF0KTtcbiAgfVxuICBoYXNGb3JtYXQodHlwZSkge1xuICAgIGNvbnN0IGZvcm1hdEZsYWcgPSBURVhUX1RZUEVfVE9fRk9STUFUW3R5cGVdO1xuICAgIHJldHVybiAodGhpcy5nZXRGb3JtYXQoKSAmIGZvcm1hdEZsYWcpICE9PSAwO1xuICB9XG4gIHNldEZvcm1hdCh0eXBlKSB7XG4gICAgcmV0dXJuICRzZXRTdGF0ZSh0aGlzLCBmb3JtYXRTdGF0ZSwgdHlwZSk7XG4gIH1cbiAgdG9nZ2xlRm9ybWF0KHR5cGUpIHtcbiAgICBjb25zdCBmb3JtYXQgPSB0aGlzLmdldEZvcm1hdCgpO1xuICAgIGNvbnN0IG5ld0Zvcm1hdCA9IHRvZ2dsZVRleHRGb3JtYXRUeXBlKGZvcm1hdCwgdHlwZSwgbnVsbCk7XG4gICAgcmV0dXJuIHRoaXMuc2V0Rm9ybWF0KG5ld0Zvcm1hdCk7XG4gIH1cbiAgaXNJbmxpbmUoKSB7XG4gICAgcmV0dXJuIHRydWU7XG4gIH1cbiAgY3JlYXRlRE9NKCkge1xuICAgIHJldHVybiBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCdzcGFuJyk7XG4gIH1cbiAgdXBkYXRlRE9NKCkge1xuICAgIHJldHVybiBmYWxzZTtcbiAgfVxufVxuZnVuY3Rpb24gJGlzRGVjb3JhdG9yVGV4dE5vZGUobm9kZSkge1xuICByZXR1cm4gbm9kZSBpbnN0YW5jZW9mIERlY29yYXRvclRleHROb2RlO1xufVxuXG4vKipcbiAqIEFwcGxpZXMgZm9ybWF0dGluZyB0byB0aGUgbm9kZSBiYXNlZCBvbiB0aGUgcHJvcGVydGllcyBpbiB0aGUgcGFzc2VkIHN0eWxlIG9iamVjdC5cbiAqIEJ5IGRlZmF1bHQsIHByb3BlcnRpZXMgYXJlIGNoZWNrZWQgYWNjb3JkaW5nIHRvIHRoZSB2YWx1ZXMgc2V0XG4gKiB3aGVuIGltcG9ydGluZyBjb250ZW50IGZyb20gR29vZ2xlIERvY3MuXG4gKiBUaGlzIGFsZ29yaXRobSBpcyBpZGVudGljYWwgdG8gdGhlIFRleHROb2RlIGltcG9ydC5cblxuICogQHBhcmFtIGxleGljYWxOb2RlIFRoZSBub2RlIHRvIHdoaWNoIHRoZSBmb3JtYXQgd2lsbCBhcHBseVxuICogQHBhcmFtIHN0eWxlIENTUyBzdHlsZSBvYmplY3RcbiAqIEBwYXJhbSBzaG91bGRBcHBseSBmb3JtYXQgdG8gYXBwbHkgaWYgaXQgaXMgbm90IGluIHN0eWxlXG4gKiBAcmV0dXJucyBsZXhpY2FsTm9kZVxuICovXG5mdW5jdGlvbiBhcHBseUZvcm1hdEZyb21TdHlsZShsZXhpY2FsTm9kZSwgc3R5bGUsIHNob3VsZEFwcGx5KSB7XG4gIGNvbnN0IGZvbnRXZWlnaHQgPSBzdHlsZS5mb250V2VpZ2h0O1xuICBjb25zdCB0ZXh0RGVjb3JhdGlvbiA9IHN0eWxlLnRleHREZWNvcmF0aW9uLnNwbGl0KCcgJyk7XG4gIC8vIEdvb2dsZSBEb2NzIHVzZXMgc3BhbiB0YWdzICsgZm9udC13ZWlnaHQgZm9yIGJvbGQgdGV4dFxuICBjb25zdCBoYXNCb2xkRm9udFdlaWdodCA9IGZvbnRXZWlnaHQgPT09ICc3MDAnIHx8IGZvbnRXZWlnaHQgPT09ICdib2xkJztcbiAgLy8gR29vZ2xlIERvY3MgdXNlcyBzcGFuIHRhZ3MgKyB0ZXh0LWRlY29yYXRpb246IGxpbmUtdGhyb3VnaCBmb3Igc3RyaWtldGhyb3VnaCB0ZXh0XG4gIGNvbnN0IGhhc0xpbmV0aHJvdWdoVGV4dERlY29yYXRpb24gPSB0ZXh0RGVjb3JhdGlvbi5pbmNsdWRlcygnbGluZS10aHJvdWdoJyk7XG4gIC8vIEdvb2dsZSBEb2NzIHVzZXMgc3BhbiB0YWdzICsgZm9udC1zdHlsZSBmb3IgaXRhbGljIHRleHRcbiAgY29uc3QgaGFzSXRhbGljRm9udFN0eWxlID0gc3R5bGUuZm9udFN0eWxlID09PSAnaXRhbGljJztcbiAgLy8gR29vZ2xlIERvY3MgdXNlcyBzcGFuIHRhZ3MgKyB0ZXh0LWRlY29yYXRpb246IHVuZGVybGluZSBmb3IgdW5kZXJsaW5lIHRleHRcbiAgY29uc3QgaGFzVW5kZXJsaW5lVGV4dERlY29yYXRpb24gPSB0ZXh0RGVjb3JhdGlvbi5pbmNsdWRlcygndW5kZXJsaW5lJyk7XG4gIC8vIEdvb2dsZSBEb2NzIHVzZXMgc3BhbiB0YWdzICsgdmVydGljYWwtYWxpZ24gdG8gc3BlY2lmeSBzdWJzY3JpcHQgYW5kIHN1cGVyc2NyaXB0XG4gIGNvbnN0IHZlcnRpY2FsQWxpZ24gPSBzdHlsZS52ZXJ0aWNhbEFsaWduO1xuICBpZiAoaGFzQm9sZEZvbnRXZWlnaHQgJiYgIWxleGljYWxOb2RlLmhhc0Zvcm1hdCgnYm9sZCcpKSB7XG4gICAgbGV4aWNhbE5vZGUudG9nZ2xlRm9ybWF0KCdib2xkJyk7XG4gIH1cbiAgaWYgKGhhc0xpbmV0aHJvdWdoVGV4dERlY29yYXRpb24gJiYgIWxleGljYWxOb2RlLmhhc0Zvcm1hdCgnc3RyaWtldGhyb3VnaCcpKSB7XG4gICAgbGV4aWNhbE5vZGUudG9nZ2xlRm9ybWF0KCdzdHJpa2V0aHJvdWdoJyk7XG4gIH1cbiAgaWYgKGhhc0l0YWxpY0ZvbnRTdHlsZSAmJiAhbGV4aWNhbE5vZGUuaGFzRm9ybWF0KCdpdGFsaWMnKSkge1xuICAgIGxleGljYWxOb2RlLnRvZ2dsZUZvcm1hdCgnaXRhbGljJyk7XG4gIH1cbiAgaWYgKGhhc1VuZGVybGluZVRleHREZWNvcmF0aW9uICYmICFsZXhpY2FsTm9kZS5oYXNGb3JtYXQoJ3VuZGVybGluZScpKSB7XG4gICAgbGV4aWNhbE5vZGUudG9nZ2xlRm9ybWF0KCd1bmRlcmxpbmUnKTtcbiAgfVxuICBpZiAodmVydGljYWxBbGlnbiA9PT0gJ3N1YicgJiYgIWxleGljYWxOb2RlLmhhc0Zvcm1hdCgnc3Vic2NyaXB0JykpIHtcbiAgICBsZXhpY2FsTm9kZS50b2dnbGVGb3JtYXQoJ3N1YnNjcmlwdCcpO1xuICB9XG4gIGlmICh2ZXJ0aWNhbEFsaWduID09PSAnc3VwZXInICYmICFsZXhpY2FsTm9kZS5oYXNGb3JtYXQoJ3N1cGVyc2NyaXB0JykpIHtcbiAgICBsZXhpY2FsTm9kZS50b2dnbGVGb3JtYXQoJ3N1cGVyc2NyaXB0Jyk7XG4gIH1cbiAgaWYgKHNob3VsZEFwcGx5ICYmICFsZXhpY2FsTm9kZS5oYXNGb3JtYXQoc2hvdWxkQXBwbHkpKSB7XG4gICAgbGV4aWNhbE5vZGUudG9nZ2xlRm9ybWF0KHNob3VsZEFwcGx5KTtcbiAgfVxuICByZXR1cm4gbGV4aWNhbE5vZGU7XG59XG5cbi8qKlxuICogVGhlIGZ1bmN0aW9uIHdyYXBzIHRoZSBwYXNzZWQgRE9NIG5vZGUgaW4gc2VtYW50aWMgdGFncyBkZXBlbmRpbmcgb24gdGhlIG5vZGUgZm9ybWF0LlxuICpcbiAqIEBwYXJhbSBsZXhpY2FsTm9kZSBUaGUgbm9kZSB3aGVyZSB0aGUgZm9ybWF0IGlzIGNoZWNrZWRcbiAqIEBwYXJhbSBkb21Ob2RlIERPTSB0aGF0IHdpbGwgYmUgd3JhcHBlZCBpbiB0YWdzXG4gKiBAcGFyYW0gdGFnTmFtZVRvRm9ybWF0IFRhZyBuYW1lIGFuZCBmb3JtYXQgbWFwcGluZ1xuICogQHJldHVybnMgZG9tTm9kZVxuICovXG5mdW5jdGlvbiBhcHBseUZvcm1hdFRvRG9tKGxleGljYWxOb2RlLCBkb21Ob2RlLCB0YWdOYW1lVG9Gb3JtYXQgPSBERUZBVUxUX1RBR19OQU1FX1RPX0ZPUk1BVCkge1xuICBmb3IgKGNvbnN0IFt0YWcsIGZvcm1hdF0gb2YgT2JqZWN0LmVudHJpZXModGFnTmFtZVRvRm9ybWF0KSkge1xuICAgIGlmIChsZXhpY2FsTm9kZS5oYXNGb3JtYXQoZm9ybWF0KSkge1xuICAgICAgZG9tTm9kZSA9IHdyYXBFbGVtZW50V2l0aChkb21Ob2RlLCB0YWcpO1xuICAgIH1cbiAgfVxuICByZXR1cm4gZG9tTm9kZTtcbn1cbmZ1bmN0aW9uIHdyYXBFbGVtZW50V2l0aChlbGVtZW50LCB0YWcpIHtcbiAgY29uc3QgZWwgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KHRhZyk7XG4gIGVsLmFwcGVuZENoaWxkKGVsZW1lbnQpO1xuICByZXR1cm4gZWw7XG59XG5jb25zdCBERUZBVUxUX1RBR19OQU1FX1RPX0ZPUk1BVCA9IHtcbiAgYjogJ2JvbGQnLFxuICBjb2RlOiAnY29kZScsXG4gIGVtOiAnaXRhbGljJyxcbiAgaTogJ2l0YWxpYycsXG4gIG1hcms6ICdoaWdobGlnaHQnLFxuICBzOiAnc3RyaWtldGhyb3VnaCcsXG4gIHN0cm9uZzogJ2JvbGQnLFxuICBzdWI6ICdzdWJzY3JpcHQnLFxuICBzdXA6ICdzdXBlcnNjcmlwdCcsXG4gIHU6ICd1bmRlcmxpbmUnXG59O1xuXG4vKipcbiAqIEFuIGV4dGVuc2lvbiBmb3IgRGVjb3JhdG9yVGV4dE5vZGUgdGhhdCBzZXRzIHRoZSBmb3JtYXQgZm9yIHRoZSBub2RlIGFuZCBDU1MgY2xhc3NlcyBmb3IgdGhlIERPTSBjb250YWluZXIuXG4gKiBUaGUgYmFzZSBjbGFzcyBpcyBhbHdheXMgc2V0LCBhbmQgdGhlIGZvY3VzIGNsYXNzIGlzIHNldCB3aGVuIHRoZSBub2RlIGlzIHNlbGVjdGVkLlxuICovXG5jb25zdCBEZWNvcmF0b3JUZXh0RXh0ZW5zaW9uID0gZGVmaW5lRXh0ZW5zaW9uKHtcbiAgbmFtZTogJ0BsZXhpY2FsL2V4dGVuc2lvbi9EZWNvcmF0b3JUZXh0JyxcbiAgbm9kZXM6ICgpID0+IFtEZWNvcmF0b3JUZXh0Tm9kZV0sXG4gIHJlZ2lzdGVyKGVkaXRvciwgY29uZmlnLCBzdGF0ZSkge1xuICAgIHJldHVybiBlZGl0b3IucmVnaXN0ZXJDb21tYW5kKEZPUk1BVF9URVhUX0NPTU1BTkQsIGZvcm1hdFR5cGUgPT4ge1xuICAgICAgY29uc3Qgc2VsZWN0aW9uID0gJGdldFNlbGVjdGlvbigpO1xuICAgICAgaWYgKCRpc05vZGVTZWxlY3Rpb24oc2VsZWN0aW9uKSB8fCAkaXNSYW5nZVNlbGVjdGlvbihzZWxlY3Rpb24pKSB7XG4gICAgICAgIGZvciAoY29uc3Qgbm9kZSBvZiBzZWxlY3Rpb24uZ2V0Tm9kZXMoKSkge1xuICAgICAgICAgIGlmICgkaXNEZWNvcmF0b3JUZXh0Tm9kZShub2RlKSkge1xuICAgICAgICAgICAgbm9kZS50b2dnbGVGb3JtYXQoZm9ybWF0VHlwZSk7XG4gICAgICAgICAgfVxuICAgICAgICB9XG4gICAgICB9XG4gICAgICByZXR1cm4gZmFsc2U7XG4gICAgfSwgQ09NTUFORF9QUklPUklUWV9MT1cpO1xuICB9XG59KTtcblxuLyoqXG4gKiBDb3B5cmlnaHQgKGMpIE1ldGEgUGxhdGZvcm1zLCBJbmMuIGFuZCBhZmZpbGlhdGVzLlxuICpcbiAqIFRoaXMgc291cmNlIGNvZGUgaXMgbGljZW5zZWQgdW5kZXIgdGhlIE1JVCBsaWNlbnNlIGZvdW5kIGluIHRoZVxuICogTElDRU5TRSBmaWxlIGluIHRoZSByb290IGRpcmVjdG9yeSBvZiB0aGlzIHNvdXJjZSB0cmVlLlxuICpcbiAqL1xuXG4vKipcbiAqIEBleHBlcmltZW50YWxcbiAqIENyZWF0ZSBhIFNpZ25hbCB0aGF0IHdpbGwgc3Vic2NyaWJlIHRvIGEgdmFsdWUgZnJvbSBhbiBleHRlcm5hbCBzdG9yZSB3aGVuIHdhdGNoZWQsIHNpbWlsYXIgdG9cbiAqIFJlYWN0J3MgW3VzZVN5bmNFeHRlcm5hbFN0b3JlXShodHRwczovL3JlYWN0LmRldi9yZWZlcmVuY2UvcmVhY3QvdXNlU3luY0V4dGVybmFsU3RvcmUpLlxuICpcbiAqIEBwYXJhbSBnZXRTbmFwc2hvdCBVc2VkIHRvIGdldCB0aGUgaW5pdGlhbCB2YWx1ZSBvZiB0aGUgc2lnbmFsIHdoZW4gY3JlYXRlZCBhbmQgd2hlbiBmaXJzdCB3YXRjaGVkLlxuICogQHBhcmFtIHJlZ2lzdGVyIEEgY2FsbGJhY2sgdGhhdCB3aWxsIHN1YnNjcmliZSB0byBzb21lIGV4dGVybmFsIHN0b3JlIGFuZCB1cGRhdGUgdGhlIHNpZ25hbCwgbXVzdCByZXR1cm4gYSBkaXNwb3NlIGZ1bmN0aW9uLlxuICogQHJldHVybnMgVGhlIHNpZ25hbFxuICovXG5mdW5jdGlvbiB3YXRjaGVkU2lnbmFsKGdldFNuYXBzaG90LCByZWdpc3Rlcikge1xuICBsZXQgZGlzcG9zZTtcbiAgcmV0dXJuIGQoZ2V0U25hcHNob3QoKSwge1xuICAgIHVud2F0Y2hlZCgpIHtcbiAgICAgIGlmIChkaXNwb3NlKSB7XG4gICAgICAgIGRpc3Bvc2UoKTtcbiAgICAgICAgZGlzcG9zZSA9IHVuZGVmaW5lZDtcbiAgICAgIH1cbiAgICB9LFxuICAgIHdhdGNoZWQoKSB7XG4gICAgICB0aGlzLnZhbHVlID0gZ2V0U25hcHNob3QoKTtcbiAgICAgIGRpc3Bvc2UgPSByZWdpc3Rlcih0aGlzKTtcbiAgICB9XG4gIH0pO1xufVxuXG4vKipcbiAqIENvcHlyaWdodCAoYykgTWV0YSBQbGF0Zm9ybXMsIEluYy4gYW5kIGFmZmlsaWF0ZXMuXG4gKlxuICogVGhpcyBzb3VyY2UgY29kZSBpcyBsaWNlbnNlZCB1bmRlciB0aGUgTUlUIGxpY2Vuc2UgZm91bmQgaW4gdGhlXG4gKiBMSUNFTlNFIGZpbGUgaW4gdGhlIHJvb3QgZGlyZWN0b3J5IG9mIHRoaXMgc291cmNlIHRyZWUuXG4gKlxuICovXG5cbi8qKlxuICogQW4gZXh0ZW5zaW9uIHRvIHByb3ZpZGUgdGhlIGN1cnJlbnQgRWRpdG9yU3RhdGUgYXMgYSBzaWduYWxcbiAqL1xuY29uc3QgRWRpdG9yU3RhdGVFeHRlbnNpb24gPSBkZWZpbmVFeHRlbnNpb24oe1xuICBidWlsZChlZGl0b3IpIHtcbiAgICByZXR1cm4gd2F0Y2hlZFNpZ25hbCgoKSA9PiBlZGl0b3IuZ2V0RWRpdG9yU3RhdGUoKSwgZWRpdG9yU3RhdGVTaWduYWwgPT4gZWRpdG9yLnJlZ2lzdGVyVXBkYXRlTGlzdGVuZXIocGF5bG9hZCA9PiB7XG4gICAgICBlZGl0b3JTdGF0ZVNpZ25hbC52YWx1ZSA9IHBheWxvYWQuZWRpdG9yU3RhdGU7XG4gICAgfSkpO1xuICB9LFxuICBuYW1lOiAnQGxleGljYWwvZXh0ZW5zaW9uL0VkaXRvclN0YXRlJ1xufSk7XG5cbi8qKlxuICogQ29weXJpZ2h0IChjKSBNZXRhIFBsYXRmb3JtcywgSW5jLiBhbmQgYWZmaWxpYXRlcy5cbiAqXG4gKiBUaGlzIHNvdXJjZSBjb2RlIGlzIGxpY2Vuc2VkIHVuZGVyIHRoZSBNSVQgbGljZW5zZSBmb3VuZCBpbiB0aGVcbiAqIExJQ0VOU0UgZmlsZSBpbiB0aGUgcm9vdCBkaXJlY3Rvcnkgb2YgdGhpcyBzb3VyY2UgdHJlZS5cbiAqXG4gKi9cblxuLy8gRG8gbm90IHJlcXVpcmUgdGhpcyBtb2R1bGUgZGlyZWN0bHkhIFVzZSBub3JtYWwgYGludmFyaWFudGAgY2FsbHMuXG5cbmZ1bmN0aW9uIGZvcm1hdERldkVycm9yTWVzc2FnZShtZXNzYWdlKSB7XG4gIHRocm93IG5ldyBFcnJvcihtZXNzYWdlKTtcbn1cblxuLyoqXG4gKiBDb3B5cmlnaHQgKGMpIE1ldGEgUGxhdGZvcm1zLCBJbmMuIGFuZCBhZmZpbGlhdGVzLlxuICpcbiAqIFRoaXMgc291cmNlIGNvZGUgaXMgbGljZW5zZWQgdW5kZXIgdGhlIE1JVCBsaWNlbnNlIGZvdW5kIGluIHRoZVxuICogTElDRU5TRSBmaWxlIGluIHRoZSByb290IGRpcmVjdG9yeSBvZiB0aGlzIHNvdXJjZSB0cmVlLlxuICpcbiAqL1xuXG4vKipcbiAqIFJlY3Vyc2l2ZWx5IG1lcmdlIHRoZSBnaXZlbiB0aGVtZSBjb25maWd1cmF0aW9uIGluLXBsYWNlLlxuICpcbiAqIEByZXR1cm5zIElmIGBhYCBhbmQgYGJgIGFyZSBib3RoIG9iamVjdHMgKGFuZCBgYmAgaXMgbm90IGFuIEFycmF5KSB0aGVuXG4gKiBhbGwga2V5cyBpbiBgYmAgYXJlIG1lcmdlZCBpbnRvIGBhYCB0aGVuIGBhYCBpcyByZXR1cm5lZC5cbiAqIE90aGVyd2lzZSBgYmAgaXMgcmV0dXJuZWQuXG4gKlxuICogQGV4YW1wbGVcbiAqIGBgYHRzXG4gKiBjb25zdCBhID0geyBhOiBcImFcIiwgbmVzdGVkOiB7IGE6IDEgfSB9O1xuICogY29uc3QgYiA9IHsgYjogXCJiXCIsIG5lc3RlZDogeyBiOiAyIH0gfTtcbiAqIGNvbnN0IHJ2YWwgPSBkZWVwVGhlbWVNZXJnZUluUGxhY2UoYSwgYik7XG4gKiBleHBlY3QoYSkudG9CZShydmFsKTtcbiAqIGV4cGVjdChhKS50b0VxdWFsKHsgYTogXCJhXCIsIGI6IFwiYlwiLCBuZXN0ZWQ6IHsgYTogMSwgYjogMiB9IH0pO1xuICogYGBgXG4gKi9cbmZ1bmN0aW9uIGRlZXBUaGVtZU1lcmdlSW5QbGFjZShhLCBiKSB7XG4gIGlmIChhICYmIGIgJiYgIUFycmF5LmlzQXJyYXkoYikgJiYgdHlwZW9mIGEgPT09ICdvYmplY3QnICYmIHR5cGVvZiBiID09PSAnb2JqZWN0Jykge1xuICAgIGNvbnN0IGFPYmogPSBhO1xuICAgIGNvbnN0IGJPYmogPSBiO1xuICAgIGZvciAoY29uc3QgayBpbiBiT2JqKSB7XG4gICAgICBhT2JqW2tdID0gZGVlcFRoZW1lTWVyZ2VJblBsYWNlKGFPYmpba10sIGJPYmpba10pO1xuICAgIH1cbiAgICByZXR1cm4gYTtcbiAgfVxuICByZXR1cm4gYjtcbn1cblxuY29uc3QgRXh0ZW5zaW9uUmVwU3RhdGVJZHMgPSB7XG4gIC8qIGVzbGludC1kaXNhYmxlIHNvcnQta2V5cy1maXgvc29ydC1rZXlzLWZpeCAqL1xuICB1bm1hcmtlZDogMCxcbiAgdGVtcG9yYXJ5OiAxLFxuICBwZXJtYW5lbnQ6IDIsXG4gIGNvbmZpZ3VyZWQ6IDMsXG4gIGluaXRpYWxpemVkOiA0LFxuICBidWlsdDogNSxcbiAgcmVnaXN0ZXJlZDogNixcbiAgYWZ0ZXJSZWdpc3RyYXRpb246IDdcbiAgLyogZXNsaW50LWVuYWJsZSBzb3J0LWtleXMtZml4L3NvcnQta2V5cy1maXggKi9cbn07XG5mdW5jdGlvbiBpc0V4YWN0bHlVbm1hcmtlZEV4dGVuc2lvblJlcFN0YXRlKHN0YXRlKSB7XG4gIHJldHVybiBzdGF0ZS5pZCA9PT0gRXh0ZW5zaW9uUmVwU3RhdGVJZHMudW5tYXJrZWQ7XG59XG5mdW5jdGlvbiBpc0V4YWN0bHlUZW1wb3JhcnlFeHRlbnNpb25SZXBTdGF0ZShzdGF0ZSkge1xuICByZXR1cm4gc3RhdGUuaWQgPT09IEV4dGVuc2lvblJlcFN0YXRlSWRzLnRlbXBvcmFyeTtcbn1cbmZ1bmN0aW9uIGlzRXhhY3RseVBlcm1hbmVudEV4dGVuc2lvblJlcFN0YXRlKHN0YXRlKSB7XG4gIHJldHVybiBzdGF0ZS5pZCA9PT0gRXh0ZW5zaW9uUmVwU3RhdGVJZHMucGVybWFuZW50O1xufVxuZnVuY3Rpb24gaXNDb25maWd1cmVkRXh0ZW5zaW9uUmVwU3RhdGUoc3RhdGUpIHtcbiAgcmV0dXJuIHN0YXRlLmlkID49IEV4dGVuc2lvblJlcFN0YXRlSWRzLmNvbmZpZ3VyZWQ7XG59XG5mdW5jdGlvbiBpc0luaXRpYWxpemVkRXh0ZW5zaW9uUmVwU3RhdGUoc3RhdGUpIHtcbiAgcmV0dXJuIHN0YXRlLmlkID49IEV4dGVuc2lvblJlcFN0YXRlSWRzLmluaXRpYWxpemVkO1xufVxuZnVuY3Rpb24gaXNCdWlsdEV4dGVuc2lvblJlcFN0YXRlKHN0YXRlKSB7XG4gIHJldHVybiBzdGF0ZS5pZCA+PSBFeHRlbnNpb25SZXBTdGF0ZUlkcy5idWlsdDtcbn1cbmZ1bmN0aW9uIGlzQWZ0ZXJSZWdpc3RyYXRpb25TdGF0ZShzdGF0ZSkge1xuICByZXR1cm4gc3RhdGUuaWQgPj0gRXh0ZW5zaW9uUmVwU3RhdGVJZHMuYWZ0ZXJSZWdpc3RyYXRpb247XG59XG5mdW5jdGlvbiBhcHBseVRlbXBvcmFyeU1hcmsoc3RhdGUpIHtcbiAgaWYgKCFpc0V4YWN0bHlVbm1hcmtlZEV4dGVuc2lvblJlcFN0YXRlKHN0YXRlKSkge1xuICAgIGZvcm1hdERldkVycm9yTWVzc2FnZShgTGV4aWNhbEJ1aWxkZXI6IENhbiBub3QgYXBwbHkgYSB0ZW1wb3JhcnkgbWFyayBmcm9tIHN0YXRlIGlkICR7U3RyaW5nKHN0YXRlLmlkKX0gKGV4cGVjdGVkICR7U3RyaW5nKEV4dGVuc2lvblJlcFN0YXRlSWRzLnVubWFya2VkKX0gdW5tYXJrZWQpYCk7XG4gIH1cbiAgcmV0dXJuIE9iamVjdC5hc3NpZ24oc3RhdGUsIHtcbiAgICBpZDogRXh0ZW5zaW9uUmVwU3RhdGVJZHMudGVtcG9yYXJ5XG4gIH0pO1xufVxuZnVuY3Rpb24gYXBwbHlQZXJtYW5lbnRNYXJrKHN0YXRlKSB7XG4gIGlmICghaXNFeGFjdGx5VGVtcG9yYXJ5RXh0ZW5zaW9uUmVwU3RhdGUoc3RhdGUpKSB7XG4gICAgZm9ybWF0RGV2RXJyb3JNZXNzYWdlKGBMZXhpY2FsQnVpbGRlcjogQ2FuIG5vdCBhcHBseSBhIHBlcm1hbmVudCBtYXJrIGZyb20gc3RhdGUgaWQgJHtTdHJpbmcoc3RhdGUuaWQpfSAoZXhwZWN0ZWQgJHtTdHJpbmcoRXh0ZW5zaW9uUmVwU3RhdGVJZHMudGVtcG9yYXJ5KX0gdGVtcG9yYXJ5KWApO1xuICB9XG4gIHJldHVybiBPYmplY3QuYXNzaWduKHN0YXRlLCB7XG4gICAgaWQ6IEV4dGVuc2lvblJlcFN0YXRlSWRzLnBlcm1hbmVudFxuICB9KTtcbn1cbmZ1bmN0aW9uIGFwcGx5Q29uZmlndXJlZFN0YXRlKHN0YXRlLCBjb25maWcsIHJlZ2lzdGVyU3RhdGUpIHtcbiAgcmV0dXJuIE9iamVjdC5hc3NpZ24oc3RhdGUsIHtcbiAgICBjb25maWcsXG4gICAgaWQ6IEV4dGVuc2lvblJlcFN0YXRlSWRzLmNvbmZpZ3VyZWQsXG4gICAgcmVnaXN0ZXJTdGF0ZVxuICB9KTtcbn1cbmZ1bmN0aW9uIGFwcGx5SW5pdGlhbGl6ZWRTdGF0ZShzdGF0ZSwgaW5pdFJlc3VsdCwgcmVnaXN0ZXJTdGF0ZSkge1xuICByZXR1cm4gT2JqZWN0LmFzc2lnbihzdGF0ZSwge1xuICAgIGlkOiBFeHRlbnNpb25SZXBTdGF0ZUlkcy5pbml0aWFsaXplZCxcbiAgICBpbml0UmVzdWx0LFxuICAgIHJlZ2lzdGVyU3RhdGVcbiAgfSk7XG59XG5mdW5jdGlvbiBhcHBseUJ1aWx0U3RhdGUoc3RhdGUsIG91dHB1dCwgcmVnaXN0ZXJTdGF0ZSkge1xuICByZXR1cm4gT2JqZWN0LmFzc2lnbihzdGF0ZSwge1xuICAgIGlkOiBFeHRlbnNpb25SZXBTdGF0ZUlkcy5idWlsdCxcbiAgICBvdXRwdXQsXG4gICAgcmVnaXN0ZXJTdGF0ZVxuICB9KTtcbn1cbmZ1bmN0aW9uIGFwcGx5UmVnaXN0ZXJlZFN0YXRlKHN0YXRlKSB7XG4gIHJldHVybiBPYmplY3QuYXNzaWduKHN0YXRlLCB7XG4gICAgaWQ6IEV4dGVuc2lvblJlcFN0YXRlSWRzLnJlZ2lzdGVyZWRcbiAgfSk7XG59XG5mdW5jdGlvbiBhcHBseUFmdGVyUmVnaXN0cmF0aW9uU3RhdGUoc3RhdGUpIHtcbiAgcmV0dXJuIE9iamVjdC5hc3NpZ24oc3RhdGUsIHtcbiAgICBpZDogRXh0ZW5zaW9uUmVwU3RhdGVJZHMuYWZ0ZXJSZWdpc3RyYXRpb25cbiAgfSk7XG59XG5mdW5jdGlvbiByb2xsYmFja1RvQnVpbHRTdGF0ZShzdGF0ZSkge1xuICByZXR1cm4gT2JqZWN0LmFzc2lnbihzdGF0ZSwge1xuICAgIGlkOiBFeHRlbnNpb25SZXBTdGF0ZUlkcy5idWlsdFxuICB9KTtcbn1cbmNvbnN0IGVtcHR5U2V0ID0gbmV3IFNldCgpO1xuXG4vKipcbiAqIEBpbnRlcm5hbFxuICovXG5jbGFzcyBFeHRlbnNpb25SZXAge1xuICBidWlsZGVyO1xuICBjb25maWdzO1xuICBfZGVwZW5kZW5jeTtcbiAgX3BlZXJOYW1lU2V0O1xuICBleHRlbnNpb247XG4gIHN0YXRlO1xuICBfc2lnbmFsO1xuICBjb25zdHJ1Y3RvcihidWlsZGVyLCBleHRlbnNpb24pIHtcbiAgICB0aGlzLmJ1aWxkZXIgPSBidWlsZGVyO1xuICAgIHRoaXMuZXh0ZW5zaW9uID0gZXh0ZW5zaW9uO1xuICAgIHRoaXMuY29uZmlncyA9IG5ldyBTZXQoKTtcbiAgICB0aGlzLnN0YXRlID0ge1xuICAgICAgaWQ6IEV4dGVuc2lvblJlcFN0YXRlSWRzLnVubWFya2VkXG4gICAgfTtcbiAgfVxuICBtZXJnZUNvbmZpZ3MoKSB7XG4gICAgLy8gZXNsaW50LWRpc2FibGUtbmV4dC1saW5lIEB0eXBlc2NyaXB0LWVzbGludC9uby11bnNhZmUtYXNzaWdubWVudCAtLSBMZXhpY2FsRXh0ZW5zaW9uQ29uZmlnPEV4dGVuc2lvbj4gaXMgYW55XG4gICAgbGV0IGNvbmZpZyA9IHRoaXMuZXh0ZW5zaW9uLmNvbmZpZyB8fCB7fTtcbiAgICBjb25zdCBtZXJnZUNvbmZpZyA9IHRoaXMuZXh0ZW5zaW9uLm1lcmdlQ29uZmlnID8gdGhpcy5leHRlbnNpb24ubWVyZ2VDb25maWcuYmluZCh0aGlzLmV4dGVuc2lvbikgOiBzaGFsbG93TWVyZ2VDb25maWc7XG4gICAgZm9yIChjb25zdCBjZmcgb2YgdGhpcy5jb25maWdzKSB7XG4gICAgICAvLyBlc2xpbnQtZGlzYWJsZS1uZXh0LWxpbmUgQHR5cGVzY3JpcHQtZXNsaW50L25vLXVuc2FmZS1hc3NpZ25tZW50IC0tIExleGljYWxFeHRlbnNpb25Db25maWc8RXh0ZW5zaW9uPiBpcyBhbnlcbiAgICAgIGNvbmZpZyA9IG1lcmdlQ29uZmlnKGNvbmZpZywgY2ZnKTtcbiAgICB9XG4gICAgLy8gZXNsaW50LWRpc2FibGUtbmV4dC1saW5lIEB0eXBlc2NyaXB0LWVzbGludC9uby11bnNhZmUtcmV0dXJuIC0tIGFueVxuICAgIHJldHVybiBjb25maWc7XG4gIH1cbiAgaW5pdChlZGl0b3JDb25maWcpIHtcbiAgICBjb25zdCBpbml0aWFsU3RhdGUgPSB0aGlzLnN0YXRlO1xuICAgIGlmICghaXNFeGFjdGx5UGVybWFuZW50RXh0ZW5zaW9uUmVwU3RhdGUoaW5pdGlhbFN0YXRlKSkge1xuICAgICAgZm9ybWF0RGV2RXJyb3JNZXNzYWdlKGBFeHRlbnNpb25SZXA6IENhbiBub3QgY29uZmlndXJlIGZyb20gc3RhdGUgaWQgJHtTdHJpbmcoaW5pdGlhbFN0YXRlLmlkKX1gKTtcbiAgICB9XG4gICAgY29uc3QgaW5pdFN0YXRlID0ge1xuICAgICAgZ2V0RGVwZW5kZW5jeTogdGhpcy5nZXRJbml0RGVwZW5kZW5jeS5iaW5kKHRoaXMpLFxuICAgICAgZ2V0RGlyZWN0RGVwZW5kZW50TmFtZXM6IHRoaXMuZ2V0RGlyZWN0RGVwZW5kZW50TmFtZXMuYmluZCh0aGlzKSxcbiAgICAgIGdldFBlZXI6IHRoaXMuZ2V0SW5pdFBlZXIuYmluZCh0aGlzKSxcbiAgICAgIGdldFBlZXJOYW1lU2V0OiB0aGlzLmdldFBlZXJOYW1lU2V0LmJpbmQodGhpcylcbiAgICB9O1xuICAgIGNvbnN0IGJ1aWxkU3RhdGUgPSB7XG4gICAgICAuLi5pbml0U3RhdGUsXG4gICAgICBnZXREZXBlbmRlbmN5OiB0aGlzLmdldERlcGVuZGVuY3kuYmluZCh0aGlzKSxcbiAgICAgIGdldEluaXRSZXN1bHQ6IHRoaXMuZ2V0SW5pdFJlc3VsdC5iaW5kKHRoaXMpLFxuICAgICAgZ2V0UGVlcjogdGhpcy5nZXRQZWVyLmJpbmQodGhpcylcbiAgICB9O1xuICAgIGNvbnN0IHN0YXRlID0gYXBwbHlDb25maWd1cmVkU3RhdGUoaW5pdGlhbFN0YXRlLCB0aGlzLm1lcmdlQ29uZmlncygpLCBpbml0U3RhdGUpO1xuICAgIHRoaXMuc3RhdGUgPSBzdGF0ZTtcbiAgICBsZXQgaW5pdFJlc3VsdDtcbiAgICBpZiAodGhpcy5leHRlbnNpb24uaW5pdCkge1xuICAgICAgaW5pdFJlc3VsdCA9IHRoaXMuZXh0ZW5zaW9uLmluaXQoZWRpdG9yQ29uZmlnLCBzdGF0ZS5jb25maWcsIGluaXRTdGF0ZSk7XG4gICAgfVxuICAgIC8vIGVzbGludC1kaXNhYmxlLW5leHQtbGluZSBAdHlwZXNjcmlwdC1lc2xpbnQvbm8tdW5uZWNlc3NhcnktdHlwZS1hc3NlcnRpb24gLS0gZmFsc2UgcG9zaXRpdmVcbiAgICB0aGlzLnN0YXRlID0gYXBwbHlJbml0aWFsaXplZFN0YXRlKHN0YXRlLCBpbml0UmVzdWx0LCBidWlsZFN0YXRlKTtcbiAgfVxuICBidWlsZChlZGl0b3IpIHtcbiAgICBjb25zdCBzdGF0ZSA9IHRoaXMuc3RhdGU7XG4gICAgaWYgKCEoc3RhdGUuaWQgPT09IEV4dGVuc2lvblJlcFN0YXRlSWRzLmluaXRpYWxpemVkKSkge1xuICAgICAgZm9ybWF0RGV2RXJyb3JNZXNzYWdlKGBFeHRlbnNpb25SZXA6IHJlZ2lzdGVyIGNhbGxlZCBpbiBzdGF0ZSBpZCAke1N0cmluZyhzdGF0ZS5pZCl9IChleHBlY3RlZCAke1N0cmluZyhFeHRlbnNpb25SZXBTdGF0ZUlkcy5idWlsdCl9IGluaXRpYWxpemVkKWApO1xuICAgIH1cbiAgICBsZXQgb3V0cHV0O1xuICAgIGlmICh0aGlzLmV4dGVuc2lvbi5idWlsZCkge1xuICAgICAgb3V0cHV0ID0gdGhpcy5leHRlbnNpb24uYnVpbGQoZWRpdG9yLCBzdGF0ZS5jb25maWcsIHN0YXRlLnJlZ2lzdGVyU3RhdGUpO1xuICAgIH1cbiAgICBjb25zdCByZWdpc3RlclN0YXRlID0ge1xuICAgICAgLi4uc3RhdGUucmVnaXN0ZXJTdGF0ZSxcbiAgICAgIGdldE91dHB1dDogKCkgPT4gb3V0cHV0LFxuICAgICAgZ2V0U2lnbmFsOiB0aGlzLmdldFNpZ25hbC5iaW5kKHRoaXMpXG4gICAgfTtcbiAgICB0aGlzLnN0YXRlID0gYXBwbHlCdWlsdFN0YXRlKHN0YXRlLCBvdXRwdXQsIHJlZ2lzdGVyU3RhdGUpO1xuICB9XG4gIHJlZ2lzdGVyKGVkaXRvciwgc2lnbmFsKSB7XG4gICAgdGhpcy5fc2lnbmFsID0gc2lnbmFsO1xuICAgIGNvbnN0IHN0YXRlID0gdGhpcy5zdGF0ZTtcbiAgICBpZiAoIShzdGF0ZS5pZCA9PT0gRXh0ZW5zaW9uUmVwU3RhdGVJZHMuYnVpbHQpKSB7XG4gICAgICBmb3JtYXREZXZFcnJvck1lc3NhZ2UoYEV4dGVuc2lvblJlcDogcmVnaXN0ZXIgY2FsbGVkIGluIHN0YXRlIGlkICR7U3RyaW5nKHN0YXRlLmlkKX0gKGV4cGVjdGVkICR7U3RyaW5nKEV4dGVuc2lvblJlcFN0YXRlSWRzLmJ1aWx0KX0gYnVpbHQpYCk7XG4gICAgfVxuICAgIGNvbnN0IGNsZWFudXAgPSB0aGlzLmV4dGVuc2lvbi5yZWdpc3RlciAmJiB0aGlzLmV4dGVuc2lvbi5yZWdpc3RlcihlZGl0b3IsIHN0YXRlLmNvbmZpZywgc3RhdGUucmVnaXN0ZXJTdGF0ZSk7XG4gICAgdGhpcy5zdGF0ZSA9IGFwcGx5UmVnaXN0ZXJlZFN0YXRlKHN0YXRlKTtcbiAgICByZXR1cm4gKCkgPT4ge1xuICAgICAgY29uc3QgYWZ0ZXJSZWdpc3RyYXRpb25TdGF0ZSA9IHRoaXMuc3RhdGU7XG4gICAgICBpZiAoIShhZnRlclJlZ2lzdHJhdGlvblN0YXRlLmlkID09PSBFeHRlbnNpb25SZXBTdGF0ZUlkcy5hZnRlclJlZ2lzdHJhdGlvbikpIHtcbiAgICAgICAgZm9ybWF0RGV2RXJyb3JNZXNzYWdlKGBFeHRlbnNpb25SZXA6IHJvbGxiYWNrVG9CdWlsdFN0YXRlIGNhbGxlZCBpbiBzdGF0ZSBpZCAke1N0cmluZyhzdGF0ZS5pZCl9IChleHBlY3RlZCAke1N0cmluZyhFeHRlbnNpb25SZXBTdGF0ZUlkcy5hZnRlclJlZ2lzdHJhdGlvbil9IGFmdGVyUmVnaXN0cmF0aW9uKWApO1xuICAgICAgfVxuICAgICAgdGhpcy5zdGF0ZSA9IHJvbGxiYWNrVG9CdWlsdFN0YXRlKGFmdGVyUmVnaXN0cmF0aW9uU3RhdGUpO1xuICAgICAgaWYgKGNsZWFudXApIHtcbiAgICAgICAgY2xlYW51cCgpO1xuICAgICAgfVxuICAgIH07XG4gIH1cbiAgYWZ0ZXJSZWdpc3RyYXRpb24oZWRpdG9yKSB7XG4gICAgY29uc3Qgc3RhdGUgPSB0aGlzLnN0YXRlO1xuICAgIGlmICghKHN0YXRlLmlkID09PSBFeHRlbnNpb25SZXBTdGF0ZUlkcy5yZWdpc3RlcmVkKSkge1xuICAgICAgZm9ybWF0RGV2RXJyb3JNZXNzYWdlKGBFeHRlbnNpb25SZXA6IGFmdGVyUmVnaXN0cmF0aW9uIGNhbGxlZCBpbiBzdGF0ZSBpZCAke1N0cmluZyhzdGF0ZS5pZCl9IChleHBlY3RlZCAke1N0cmluZyhFeHRlbnNpb25SZXBTdGF0ZUlkcy5yZWdpc3RlcmVkKX0gcmVnaXN0ZXJlZClgKTtcbiAgICB9XG4gICAgbGV0IHJ2YWw7XG4gICAgaWYgKHRoaXMuZXh0ZW5zaW9uLmFmdGVyUmVnaXN0cmF0aW9uKSB7XG4gICAgICBydmFsID0gdGhpcy5leHRlbnNpb24uYWZ0ZXJSZWdpc3RyYXRpb24oZWRpdG9yLCBzdGF0ZS5jb25maWcsIHN0YXRlLnJlZ2lzdGVyU3RhdGUpO1xuICAgIH1cbiAgICB0aGlzLnN0YXRlID0gYXBwbHlBZnRlclJlZ2lzdHJhdGlvblN0YXRlKHN0YXRlKTtcbiAgICByZXR1cm4gcnZhbDtcbiAgfVxuICBnZXRTaWduYWwoKSB7XG4gICAgaWYgKCEodGhpcy5fc2lnbmFsICE9PSB1bmRlZmluZWQpKSB7XG4gICAgICBmb3JtYXREZXZFcnJvck1lc3NhZ2UoYEV4dGVuc2lvblJlcC5nZXRTaWduYWwoKSBjYWxsZWQgYmVmb3JlIHJlZ2lzdGVyYCk7XG4gICAgfVxuICAgIHJldHVybiB0aGlzLl9zaWduYWw7XG4gIH1cbiAgZ2V0SW5pdFJlc3VsdCgpIHtcbiAgICBpZiAoISh0aGlzLmV4dGVuc2lvbi5pbml0ICE9PSB1bmRlZmluZWQpKSB7XG4gICAgICBmb3JtYXREZXZFcnJvck1lc3NhZ2UoYEV4dGVuc2lvblJlcDogZ2V0SW5pdFJlc3VsdCgpIGNhbGxlZCBmb3IgRXh0ZW5zaW9uICR7dGhpcy5leHRlbnNpb24ubmFtZX0gdGhhdCBkb2VzIG5vdCBkZWZpbmUgaW5pdGApO1xuICAgIH1cbiAgICBjb25zdCBzdGF0ZSA9IHRoaXMuc3RhdGU7XG4gICAgaWYgKCFpc0luaXRpYWxpemVkRXh0ZW5zaW9uUmVwU3RhdGUoc3RhdGUpKSB7XG4gICAgICBmb3JtYXREZXZFcnJvck1lc3NhZ2UoYEV4dGVuc2lvblJlcDogZ2V0SW5pdFJlc3VsdCgpIGNhbGxlZCBmb3IgRXh0ZW5zaW9uUmVwIGluIHN0YXRlIGlkICR7U3RyaW5nKHN0YXRlLmlkKX0gPCAke1N0cmluZyhFeHRlbnNpb25SZXBTdGF0ZUlkcy5pbml0aWFsaXplZCl9IChpbml0aWFsaXplZClgKTtcbiAgICB9IC8vIGVzbGludC1kaXNhYmxlLW5leHQtbGluZSBAdHlwZXNjcmlwdC1lc2xpbnQvbm8tdW5zYWZlLXJldHVybiAtLSBhbnlcbiAgICByZXR1cm4gc3RhdGUuaW5pdFJlc3VsdDtcbiAgfVxuICBnZXRJbml0UGVlcihuYW1lKSB7XG4gICAgY29uc3QgcmVwID0gdGhpcy5idWlsZGVyLmV4dGVuc2lvbk5hbWVNYXAuZ2V0KG5hbWUpO1xuICAgIHJldHVybiByZXAgPyByZXAuZ2V0RXh0ZW5zaW9uSW5pdERlcGVuZGVuY3koKSA6IHVuZGVmaW5lZDtcbiAgfVxuICBnZXRFeHRlbnNpb25Jbml0RGVwZW5kZW5jeSgpIHtcbiAgICBjb25zdCBzdGF0ZSA9IHRoaXMuc3RhdGU7XG4gICAgaWYgKCFpc0NvbmZpZ3VyZWRFeHRlbnNpb25SZXBTdGF0ZShzdGF0ZSkpIHtcbiAgICAgIGZvcm1hdERldkVycm9yTWVzc2FnZShgRXh0ZW5zaW9uUmVwOiBnZXRFeHRlbnNpb25Jbml0RGVwZW5kZW5jeSBjYWxsZWQgaW4gc3RhdGUgaWQgJHtTdHJpbmcoc3RhdGUuaWQpfSAoZXhwZWN0ZWQgPj0gJHtTdHJpbmcoRXh0ZW5zaW9uUmVwU3RhdGVJZHMuY29uZmlndXJlZCl9IGNvbmZpZ3VyZWQpYCk7XG4gICAgfVxuICAgIHJldHVybiB7XG4gICAgICBjb25maWc6IHN0YXRlLmNvbmZpZ1xuICAgIH07XG4gIH1cbiAgZ2V0UGVlcihuYW1lKSB7XG4gICAgY29uc3QgcmVwID0gdGhpcy5idWlsZGVyLmV4dGVuc2lvbk5hbWVNYXAuZ2V0KG5hbWUpO1xuICAgIHJldHVybiByZXAgPyByZXAuZ2V0RXh0ZW5zaW9uRGVwZW5kZW5jeSgpIDogdW5kZWZpbmVkO1xuICB9XG4gIGdldEluaXREZXBlbmRlbmN5KGRlcCkge1xuICAgIGNvbnN0IHJlcCA9IHRoaXMuYnVpbGRlci5nZXRFeHRlbnNpb25SZXAoZGVwKTtcbiAgICBpZiAoIShyZXAgIT09IHVuZGVmaW5lZCkpIHtcbiAgICAgIGZvcm1hdERldkVycm9yTWVzc2FnZShgTGV4aWNhbEV4dGVuc2lvbkJ1aWxkZXI6IEV4dGVuc2lvbiAke3RoaXMuZXh0ZW5zaW9uLm5hbWV9IG1pc3NpbmcgZGVwZW5kZW5jeSBleHRlbnNpb24gJHtkZXAubmFtZX0gdG8gYmUgaW4gcmVnaXN0cnlgKTtcbiAgICB9XG4gICAgcmV0dXJuIHJlcC5nZXRFeHRlbnNpb25Jbml0RGVwZW5kZW5jeSgpO1xuICB9XG4gIGdldERlcGVuZGVuY3koZGVwKSB7XG4gICAgY29uc3QgcmVwID0gdGhpcy5idWlsZGVyLmdldEV4dGVuc2lvblJlcChkZXApO1xuICAgIGlmICghKHJlcCAhPT0gdW5kZWZpbmVkKSkge1xuICAgICAgZm9ybWF0RGV2RXJyb3JNZXNzYWdlKGBMZXhpY2FsRXh0ZW5zaW9uQnVpbGRlcjogRXh0ZW5zaW9uICR7dGhpcy5leHRlbnNpb24ubmFtZX0gbWlzc2luZyBkZXBlbmRlbmN5IGV4dGVuc2lvbiAke2RlcC5uYW1lfSB0byBiZSBpbiByZWdpc3RyeWApO1xuICAgIH1cbiAgICByZXR1cm4gcmVwLmdldEV4dGVuc2lvbkRlcGVuZGVuY3koKTtcbiAgfVxuICBnZXRTdGF0ZSgpIHtcbiAgICBjb25zdCBzdGF0ZSA9IHRoaXMuc3RhdGU7XG4gICAgaWYgKCFpc0FmdGVyUmVnaXN0cmF0aW9uU3RhdGUoc3RhdGUpKSB7XG4gICAgICBmb3JtYXREZXZFcnJvck1lc3NhZ2UoYEV4dGVuc2lvblJlcCBnZXRTdGF0ZSBjYWxsZWQgaW4gc3RhdGUgaWQgJHtTdHJpbmcoc3RhdGUuaWQpfSAoZXhwZWN0ZWQgJHtTdHJpbmcoRXh0ZW5zaW9uUmVwU3RhdGVJZHMuYWZ0ZXJSZWdpc3RyYXRpb24pfSBhZnRlclJlZ2lzdHJhdGlvbilgKTtcbiAgICB9XG4gICAgcmV0dXJuIHN0YXRlO1xuICB9XG4gIGdldERpcmVjdERlcGVuZGVudE5hbWVzKCkge1xuICAgIHJldHVybiB0aGlzLmJ1aWxkZXIuaW5jb21pbmdFZGdlcy5nZXQodGhpcy5leHRlbnNpb24ubmFtZSkgfHwgZW1wdHlTZXQ7XG4gIH1cbiAgZ2V0UGVlck5hbWVTZXQoKSB7XG4gICAgbGV0IHMgPSB0aGlzLl9wZWVyTmFtZVNldDtcbiAgICBpZiAoIXMpIHtcbiAgICAgIHMgPSBuZXcgU2V0KCh0aGlzLmV4dGVuc2lvbi5wZWVyRGVwZW5kZW5jaWVzIHx8IFtdKS5tYXAoKFtuYW1lXSkgPT4gbmFtZSkpO1xuICAgICAgdGhpcy5fcGVlck5hbWVTZXQgPSBzO1xuICAgIH1cbiAgICByZXR1cm4gcztcbiAgfVxuICBnZXRFeHRlbnNpb25EZXBlbmRlbmN5KCkge1xuICAgIGlmICghdGhpcy5fZGVwZW5kZW5jeSkge1xuICAgICAgY29uc3Qgc3RhdGUgPSB0aGlzLnN0YXRlO1xuICAgICAgaWYgKCFpc0J1aWx0RXh0ZW5zaW9uUmVwU3RhdGUoc3RhdGUpKSB7XG4gICAgICAgIGZvcm1hdERldkVycm9yTWVzc2FnZShgRXh0ZW5zaW9uICR7dGhpcy5leHRlbnNpb24ubmFtZX0gdXNlZCBhcyBhIGRlcGVuZGVuY3kgYmVmb3JlIGJ1aWxkYCk7XG4gICAgICB9XG4gICAgICB0aGlzLl9kZXBlbmRlbmN5ID0ge1xuICAgICAgICBjb25maWc6IHN0YXRlLmNvbmZpZyxcbiAgICAgICAgaW5pdDogc3RhdGUuaW5pdFJlc3VsdCxcbiAgICAgICAgb3V0cHV0OiBzdGF0ZS5vdXRwdXRcbiAgICAgIH07XG4gICAgfVxuICAgIHJldHVybiB0aGlzLl9kZXBlbmRlbmN5O1xuICB9XG59XG5cbi8qKlxuICogQ29weXJpZ2h0IChjKSBNZXRhIFBsYXRmb3JtcywgSW5jLiBhbmQgYWZmaWxpYXRlcy5cbiAqXG4gKiBUaGlzIHNvdXJjZSBjb2RlIGlzIGxpY2Vuc2VkIHVuZGVyIHRoZSBNSVQgbGljZW5zZSBmb3VuZCBpbiB0aGVcbiAqIExJQ0VOU0UgZmlsZSBpbiB0aGUgcm9vdCBkaXJlY3Rvcnkgb2YgdGhpcyBzb3VyY2UgdHJlZS5cbiAqXG4gKi9cblxuY29uc3QgSElTVE9SWV9NRVJHRV9PUFRJT05TID0ge1xuICB0YWc6IEhJU1RPUllfTUVSR0VfVEFHXG59O1xuZnVuY3Rpb24gJGRlZmF1bHRJbml0aWFsaXplcigpIHtcbiAgY29uc3Qgcm9vdCA9ICRnZXRSb290KCk7XG4gIGlmIChyb290LmlzRW1wdHkoKSkge1xuICAgIHJvb3QuYXBwZW5kKCRjcmVhdGVQYXJhZ3JhcGhOb2RlKCkpO1xuICB9XG59XG4vKipcbiAqIEFuIGV4dGVuc2lvbiB0byBzZXQgdGhlIGluaXRpYWwgc3RhdGUgb2YgdGhlIGVkaXRvciBmcm9tXG4gKiBhIGZ1bmN0aW9uIG9yIHNlcmlhbGl6ZWQgSlNPTiBFZGl0b3JTdGF0ZS4gVGhpcyBpc1xuICogaW1wbGljaXRseSBpbmNsdWRlZCB3aXRoIGFsbCBlZGl0b3JzIGJ1aWx0IHdpdGhcbiAqIExleGljYWwgRXh0ZW5zaW9uLiBUaGlzIGhhcHBlbnMgaW4gdGhlIGBhZnRlclJlZ2lzdHJhdGlvbmBcbiAqIHBoYXNlIHNvIHlvdXIgaW5pdGlhbCBzdGF0ZSBtYXkgZGVwZW5kIG9uIHJlZ2lzdGVyZWQgY29tbWFuZHMsXG4gKiBidXQgeW91IHNob3VsZCBub3QgY2FsbCBgZWRpdG9yLnNldFJvb3RFbGVtZW50YCBlYXJsaWVyIHRoYW5cbiAqIHRoaXMgcGhhc2UgdG8gYXZvaWQgcmVuZGVyaW5nIGFuIGVtcHR5IGVkaXRvciBmaXJzdC5cbiAqL1xuY29uc3QgSW5pdGlhbFN0YXRlRXh0ZW5zaW9uID0gZGVmaW5lRXh0ZW5zaW9uKHtcbiAgY29uZmlnOiBzYWZlQ2FzdCh7XG4gICAgc2V0T3B0aW9uczogSElTVE9SWV9NRVJHRV9PUFRJT05TLFxuICAgIHVwZGF0ZU9wdGlvbnM6IEhJU1RPUllfTUVSR0VfT1BUSU9OU1xuICB9KSxcbiAgaW5pdCh7XG4gICAgJGluaXRpYWxFZGl0b3JTdGF0ZSA9ICRkZWZhdWx0SW5pdGlhbGl6ZXJcbiAgfSkge1xuICAgIHJldHVybiB7XG4gICAgICAkaW5pdGlhbEVkaXRvclN0YXRlLFxuICAgICAgaW5pdGlhbGl6ZWQ6IGZhbHNlXG4gICAgfTtcbiAgfSxcbiAgLy8gZXNsaW50LWRpc2FibGUtbmV4dC1saW5lIHNvcnQta2V5cy1maXgvc29ydC1rZXlzLWZpeCAtLSB0eXBlc2NyaXB0IGluZmVyZW5jZSBpcyBvcmRlciBkZXBlbmRlbnQgaGVyZSBmb3Igc29tZSByZWFzb25cbiAgYWZ0ZXJSZWdpc3RyYXRpb24oZWRpdG9yLCB7XG4gICAgdXBkYXRlT3B0aW9ucyxcbiAgICBzZXRPcHRpb25zXG4gIH0sIHN0YXRlKSB7XG4gICAgY29uc3QgaW5pdFJlc3VsdCA9IHN0YXRlLmdldEluaXRSZXN1bHQoKTtcbiAgICBpZiAoIWluaXRSZXN1bHQuaW5pdGlhbGl6ZWQpIHtcbiAgICAgIGluaXRSZXN1bHQuaW5pdGlhbGl6ZWQgPSB0cnVlO1xuICAgICAgY29uc3Qge1xuICAgICAgICAkaW5pdGlhbEVkaXRvclN0YXRlXG4gICAgICB9ID0gaW5pdFJlc3VsdDtcbiAgICAgIGlmICgkaXNFZGl0b3JTdGF0ZSgkaW5pdGlhbEVkaXRvclN0YXRlKSkge1xuICAgICAgICBlZGl0b3Iuc2V0RWRpdG9yU3RhdGUoJGluaXRpYWxFZGl0b3JTdGF0ZSwgc2V0T3B0aW9ucyk7XG4gICAgICB9IGVsc2UgaWYgKHR5cGVvZiAkaW5pdGlhbEVkaXRvclN0YXRlID09PSAnZnVuY3Rpb24nKSB7XG4gICAgICAgIGVkaXRvci51cGRhdGUoKCkgPT4ge1xuICAgICAgICAgICRpbml0aWFsRWRpdG9yU3RhdGUoZWRpdG9yKTtcbiAgICAgICAgfSwgdXBkYXRlT3B0aW9ucyk7XG4gICAgICB9IGVsc2UgaWYgKCRpbml0aWFsRWRpdG9yU3RhdGUgJiYgKHR5cGVvZiAkaW5pdGlhbEVkaXRvclN0YXRlID09PSAnc3RyaW5nJyB8fCB0eXBlb2YgJGluaXRpYWxFZGl0b3JTdGF0ZSA9PT0gJ29iamVjdCcpKSB7XG4gICAgICAgIGNvbnN0IHBhcnNlZEVkaXRvclN0YXRlID0gZWRpdG9yLnBhcnNlRWRpdG9yU3RhdGUoJGluaXRpYWxFZGl0b3JTdGF0ZSk7XG4gICAgICAgIGVkaXRvci5zZXRFZGl0b3JTdGF0ZShwYXJzZWRFZGl0b3JTdGF0ZSwgc2V0T3B0aW9ucyk7XG4gICAgICB9XG4gICAgfVxuICAgIHJldHVybiAoKSA9PiB7fTtcbiAgfSxcbiAgbmFtZTogJ0BsZXhpY2FsL2V4dGVuc2lvbi9Jbml0aWFsU3RhdGUnLFxuICAvLyBUaGVzZSBhcmUgYXV0b21hdGljYWxseSBhZGRlZCBieSBjcmVhdGVFZGl0b3IsIHdlIGFkZCB0aGVtIGhlcmUgc28gdGhleSBhcmVcbiAgLy8gdmlzaWJsZSBkdXJpbmcgZXh0ZW5zaW9uUmVwLmluaXQgc28gZXh0ZW5zaW9ucyBjYW4gc2VlIGFsbCBrbm93biB0eXBlcyBiZWZvcmUgdGhlXG4gIC8vIGVkaXRvciBpcyBjcmVhdGVkLlxuICAvLyAoZXhjbHVkaW5nIEFydGlmaWNpYWxOb2RlX19ET19OT1RfVVNFIGJlY2F1c2UgaXQgaXNuJ3QgcmVhbGx5IHB1YmxpYyBBUElcbiAgLy8gYW5kIHNob3VsZG4ndCBjaGFuZ2UgYW55dGhpbmcpXG4gIG5vZGVzOiBbUm9vdE5vZGUsIFRleHROb2RlLCBMaW5lQnJlYWtOb2RlLCBUYWJOb2RlLCBQYXJhZ3JhcGhOb2RlXVxufSk7XG5cbi8qKiBAaW50ZXJuYWwgVXNlIGEgd2VsbC1rbm93biBzeW1ib2wgZm9yIGRldiB0b29scyBwdXJwb3NlcyAqL1xuY29uc3QgYnVpbGRlclN5bWJvbCA9IFN5bWJvbC5mb3IoJ0BsZXhpY2FsL2V4dGVuc2lvbi9MZXhpY2FsQnVpbGRlcicpO1xuLyoqXG4gKiBCdWlsZCBhIExleGljYWxFZGl0b3IgYnkgY29tYmluaW5nIHRvZ2V0aGVyIG9uZSBvciBtb3JlIGV4dGVuc2lvbnMsIG9wdGlvbmFsbHlcbiAqIG92ZXJyaWRpbmcgc29tZSBvZiB0aGVpciBjb25maWd1cmF0aW9uLlxuICpcbiAqIEBwYXJhbSBleHRlbnNpb25zIC0gRXh0ZW5zaW9uIGFyZ3VtZW50cyAoZXh0ZW5zaW9ucyBvciBleHRlbnNpb25zIHdpdGggY29uZmlnIG92ZXJyaWRlcylcbiAqIEByZXR1cm5zIEFuIGVkaXRvciBoYW5kbGVcbiAqXG4gKiBAZXhhbXBsZVxuICogQSBzaW5nbGUgcm9vdCBleHRlbnNpb24gd2l0aCBtdWx0aXBsZSBkZXBlbmRlbmNpZXNcbiAqXG4gKiBgYGB0c1xuICogY29uc3QgZWRpdG9yID0gYnVpbGRFZGl0b3JGcm9tRXh0ZW5zaW9ucyhcbiAqICAgZGVmaW5lRXh0ZW5zaW9uKHtcbiAqICAgICBuYW1lOiBcIltyb290XVwiLFxuICogICAgIGRlcGVuZGVuY2llczogW1xuICogICAgICAgUmljaFRleHRFeHRlbnNpb24sXG4gKiAgICAgICBjb25maWdFeHRlbnNpb24oRW1vamlFeHRlbnNpb24sIHsgZW1vamlCYXNlVXJsOiBcIi9hc3NldHMvZW1vamlcIiB9KSxcbiAqICAgICBdLFxuICogICAgIHJlZ2lzdGVyOiAoZWRpdG9yOiBMZXhpY2FsRWRpdG9yKSA9PiB7XG4gKiAgICAgICBjb25zb2xlLmxvZyhcIkVkaXRvciBDcmVhdGVkXCIpO1xuICogICAgICAgcmV0dXJuICgpID0+IGNvbnNvbGUubG9nKFwiRWRpdG9yIERpc3Bvc2VkXCIpO1xuICogICAgIH0sXG4gKiAgIH0pLFxuICogKTtcbiAqIGBgYFxuICpcbiAqIEBleGFtcGxlXG4gKiBBIHZlcnkgc2ltaWxhciBtaW5pbWFsIGNvbmZpZ3VyYXRpb24gd2l0aG91dCB0aGUgcmVnaXN0ZXIgaG9va1xuICpcbiAqIGBgYHRzXG4gKiBjb25zdCBlZGl0b3IgPSBidWlsZEVkaXRvckZyb21FeHRlbnNpb25zKFxuICogICBSaWNoVGV4dEV4dGVuc2lvbixcbiAqICAgY29uZmlnRXh0ZW5zaW9uKEVtb2ppRXh0ZW5zaW9uLCB7IGVtb2ppQmFzZVVybDogXCIvYXNzZXRzL2Vtb2ppXCIgfSksXG4gKiApO1xuICogYGBgXG4gKi9cbmZ1bmN0aW9uIGJ1aWxkRWRpdG9yRnJvbUV4dGVuc2lvbnMoLi4uZXh0ZW5zaW9ucykge1xuICByZXR1cm4gTGV4aWNhbEJ1aWxkZXIuZnJvbUV4dGVuc2lvbnMoZXh0ZW5zaW9ucykuYnVpbGRFZGl0b3IoKTtcbn1cblxuLyoqIEBpbnRlcm5hbCAqL1xuZnVuY3Rpb24gbm9vcCgpIHtcbiAgLyplbXB0eSovXG59XG5cbi8qKiBUaHJvdyB0aGUgZ2l2ZW4gRXJyb3IgKi9cbmZ1bmN0aW9uIGRlZmF1bHRPbkVycm9yKGVycikge1xuICB0aHJvdyBlcnI7XG59XG4vKiogQGludGVybmFsICovXG5mdW5jdGlvbiBtYXliZVdpdGhCdWlsZGVyKGVkaXRvcikge1xuICByZXR1cm4gZWRpdG9yO1xufVxuZnVuY3Rpb24gbm9ybWFsaXplRXh0ZW5zaW9uQXJndW1lbnQoYXJnKSB7XG4gIHJldHVybiBBcnJheS5pc0FycmF5KGFyZykgPyBhcmcgOiBbYXJnXTtcbn1cbmNvbnN0IFBBQ0tBR0VfVkVSU0lPTiA9IFwiMC40MS4wK2Rldi5lc21cIjtcblxuLyoqIEBpbnRlcm5hbCAqL1xuY2xhc3MgTGV4aWNhbEJ1aWxkZXIge1xuICByb290cztcbiAgZXh0ZW5zaW9uTmFtZU1hcDtcbiAgb3V0Z29pbmdDb25maWdFZGdlcztcbiAgaW5jb21pbmdFZGdlcztcbiAgY29uZmxpY3RzO1xuICBfc29ydGVkRXh0ZW5zaW9uUmVwcztcbiAgUEFDS0FHRV9WRVJTSU9OO1xuICBjb25zdHJ1Y3Rvcihyb290cykge1xuICAgIHRoaXMub3V0Z29pbmdDb25maWdFZGdlcyA9IG5ldyBNYXAoKTtcbiAgICB0aGlzLmluY29taW5nRWRnZXMgPSBuZXcgTWFwKCk7XG4gICAgdGhpcy5leHRlbnNpb25OYW1lTWFwID0gbmV3IE1hcCgpO1xuICAgIHRoaXMuY29uZmxpY3RzID0gbmV3IE1hcCgpO1xuICAgIHRoaXMuUEFDS0FHRV9WRVJTSU9OID0gUEFDS0FHRV9WRVJTSU9OO1xuICAgIHRoaXMucm9vdHMgPSByb290cztcbiAgICBmb3IgKGNvbnN0IGV4dGVuc2lvbiBvZiByb290cykge1xuICAgICAgdGhpcy5hZGRFeHRlbnNpb24oZXh0ZW5zaW9uKTtcbiAgICB9XG4gIH1cbiAgc3RhdGljIGZyb21FeHRlbnNpb25zKGV4dGVuc2lvbnMpIHtcbiAgICBjb25zdCByb290cyA9IFtub3JtYWxpemVFeHRlbnNpb25Bcmd1bWVudChJbml0aWFsU3RhdGVFeHRlbnNpb24pXTtcbiAgICBmb3IgKGNvbnN0IGV4dGVuc2lvbiBvZiBleHRlbnNpb25zKSB7XG4gICAgICByb290cy5wdXNoKG5vcm1hbGl6ZUV4dGVuc2lvbkFyZ3VtZW50KGV4dGVuc2lvbikpO1xuICAgIH1cbiAgICByZXR1cm4gbmV3IExleGljYWxCdWlsZGVyKHJvb3RzKTtcbiAgfVxuICBzdGF0aWMgbWF5YmVGcm9tRWRpdG9yKGVkaXRvcikge1xuICAgIGNvbnN0IGJ1aWxkZXIgPSBtYXliZVdpdGhCdWlsZGVyKGVkaXRvcilbYnVpbGRlclN5bWJvbF07XG4gICAgaWYgKGJ1aWxkZXIpIHtcbiAgICAgIC8vIFRoZSBkZXYgdG9vbHMgdmFyaWFudCBvZiB0aGlzIHdpbGwgcmVsYXggc29tZSBvZiB0aGVzZSBpbnZhcmlhbnRzXG4gICAgICBpZiAoIShidWlsZGVyLlBBQ0tBR0VfVkVSU0lPTiA9PT0gUEFDS0FHRV9WRVJTSU9OKSkge1xuICAgICAgICBmb3JtYXREZXZFcnJvck1lc3NhZ2UoYExleGljYWxCdWlsZGVyLmZyb21FZGl0b3I6IFRoZSBnaXZlbiBlZGl0b3Igd2FzIGNyZWF0ZWQgd2l0aCBMZXhpY2FsQnVpbGRlciAke2J1aWxkZXIuUEFDS0FHRV9WRVJTSU9OfSBidXQgdGhpcyB2ZXJzaW9uIGlzICR7UEFDS0FHRV9WRVJTSU9OfS4gQSBwcm9qZWN0IHNob3VsZCBoYXZlIGV4YWN0bHkgb25lIGNvcHkgb2YgTGV4aWNhbEJ1aWxkZXJgKTtcbiAgICAgIH1cbiAgICAgIGlmICghKGJ1aWxkZXIgaW5zdGFuY2VvZiBMZXhpY2FsQnVpbGRlcikpIHtcbiAgICAgICAgZm9ybWF0RGV2RXJyb3JNZXNzYWdlKGBMZXhpY2FsQnVpbGRlci5mcm9tRWRpdG9yOiBUaGVyZSBhcmUgbXVsdGlwbGUgY29waWVzIG9mIHRoZSBzYW1lIHZlcnNpb24gb2YgTGV4aWNhbEJ1aWxkZXIgaW4geW91ciBwcm9qZWN0LCBhbmQgdGhpcyBlZGl0b3Igd2FzIGNyZWF0ZWQgd2l0aCBhbm90aGVyIG9uZS4gWW91ciBwcm9qZWN0LCBvciBvbmUgb2YgaXRzIGRlcGVuZGVuY2llcywgaGFzIGl0cyBwYWNrYWdlLmpzb24gYW5kL29yIGJ1bmRsZXIgY29uZmlndXJlZCBpbmNvcnJlY3RseS5gKTtcbiAgICAgIH1cbiAgICB9XG4gICAgcmV0dXJuIGJ1aWxkZXI7XG4gIH1cblxuICAvKiogTG9vayB1cCB0aGUgZWRpdG9yIHRoYXQgd2FzIGNyZWF0ZWQgYnkgdGhpcyBMZXhpY2FsQnVpbGRlciBvciB0aHJvdyAqL1xuICBzdGF0aWMgZnJvbUVkaXRvcihlZGl0b3IpIHtcbiAgICBjb25zdCBidWlsZGVyID0gTGV4aWNhbEJ1aWxkZXIubWF5YmVGcm9tRWRpdG9yKGVkaXRvcik7XG4gICAgaWYgKCEoYnVpbGRlciAhPT0gdW5kZWZpbmVkKSkge1xuICAgICAgZm9ybWF0RGV2RXJyb3JNZXNzYWdlKGBMZXhpY2FsQnVpbGRlci5mcm9tRWRpdG9yOiBUaGUgZ2l2ZW4gZWRpdG9yIHdhcyBub3QgY3JlYXRlZCB3aXRoIExleGljYWxCdWlsZGVyYCk7XG4gICAgfVxuICAgIHJldHVybiBidWlsZGVyO1xuICB9XG4gIGNvbnN0cnVjdEVkaXRvcigpIHtcbiAgICBjb25zdCB7XG4gICAgICAkaW5pdGlhbEVkaXRvclN0YXRlOiBfJGluaXRpYWxFZGl0b3JTdGF0ZSxcbiAgICAgIG9uRXJyb3IsXG4gICAgICAuLi5lZGl0b3JDb25maWdcbiAgICB9ID0gdGhpcy5idWlsZENyZWF0ZUVkaXRvckFyZ3MoKTtcbiAgICBjb25zdCBlZGl0b3IgPSBPYmplY3QuYXNzaWduKGNyZWF0ZUVkaXRvcih7XG4gICAgICAuLi5lZGl0b3JDb25maWcsXG4gICAgICAuLi4ob25FcnJvciA/IHtcbiAgICAgICAgb25FcnJvcjogZXJyID0+IHtcbiAgICAgICAgICBvbkVycm9yKGVyciwgZWRpdG9yKTtcbiAgICAgICAgfVxuICAgICAgfSA6IHt9KVxuICAgIH0pLCB7XG4gICAgICBbYnVpbGRlclN5bWJvbF06IHRoaXNcbiAgICB9KTtcbiAgICBmb3IgKGNvbnN0IGV4dGVuc2lvblJlcCBvZiB0aGlzLnNvcnRlZEV4dGVuc2lvblJlcHMoKSkge1xuICAgICAgZXh0ZW5zaW9uUmVwLmJ1aWxkKGVkaXRvcik7XG4gICAgfVxuICAgIHJldHVybiBlZGl0b3I7XG4gIH1cbiAgYnVpbGRFZGl0b3IoKSB7XG4gICAgbGV0IGRpc3Bvc2VPbmNlID0gbm9vcDtcbiAgICBmdW5jdGlvbiBkaXNwb3NlKCkge1xuICAgICAgdHJ5IHtcbiAgICAgICAgZGlzcG9zZU9uY2UoKTtcbiAgICAgIH0gZmluYWxseSB7XG4gICAgICAgIGRpc3Bvc2VPbmNlID0gbm9vcDtcbiAgICAgIH1cbiAgICB9XG4gICAgY29uc3QgZWRpdG9yID0gT2JqZWN0LmFzc2lnbih0aGlzLmNvbnN0cnVjdEVkaXRvcigpLCB7XG4gICAgICBkaXNwb3NlLFxuICAgICAgW1N5bWJvbC5kaXNwb3NlXTogZGlzcG9zZVxuICAgIH0pO1xuICAgIGRpc3Bvc2VPbmNlID0gbWVyZ2VSZWdpc3Rlcih0aGlzLnJlZ2lzdGVyRWRpdG9yKGVkaXRvciksICgpID0+IGVkaXRvci5zZXRSb290RWxlbWVudChudWxsKSk7XG4gICAgcmV0dXJuIGVkaXRvcjtcbiAgfVxuICBoYXNFeHRlbnNpb25CeU5hbWUobmFtZSkge1xuICAgIHJldHVybiB0aGlzLmV4dGVuc2lvbk5hbWVNYXAuaGFzKG5hbWUpO1xuICB9XG4gIGdldEV4dGVuc2lvblJlcChleHRlbnNpb24pIHtcbiAgICBjb25zdCByZXAgPSB0aGlzLmV4dGVuc2lvbk5hbWVNYXAuZ2V0KGV4dGVuc2lvbi5uYW1lKTtcbiAgICBpZiAocmVwKSB7XG4gICAgICBpZiAoIShyZXAuZXh0ZW5zaW9uID09PSBleHRlbnNpb24pKSB7XG4gICAgICAgIGZvcm1hdERldkVycm9yTWVzc2FnZShgTGV4aWNhbEJ1aWxkZXI6IEEgcmVnaXN0ZXJlZCBleHRlbnNpb24gd2l0aCBuYW1lICR7ZXh0ZW5zaW9uLm5hbWV9IGV4aXN0cyBidXQgZG9lcyBub3QgbWF0Y2ggdGhlIGdpdmVuIGV4dGVuc2lvbmApO1xuICAgICAgfVxuICAgICAgcmV0dXJuIHJlcDtcbiAgICB9XG4gIH1cbiAgYWRkRWRnZShmcm9tRXh0ZW5zaW9uTmFtZSwgdG9FeHRlbnNpb25OYW1lLCBjb25maWdzKSB7XG4gICAgY29uc3Qgb3V0Z29pbmcgPSB0aGlzLm91dGdvaW5nQ29uZmlnRWRnZXMuZ2V0KGZyb21FeHRlbnNpb25OYW1lKTtcbiAgICBpZiAob3V0Z29pbmcpIHtcbiAgICAgIG91dGdvaW5nLnNldCh0b0V4dGVuc2lvbk5hbWUsIGNvbmZpZ3MpO1xuICAgIH0gZWxzZSB7XG4gICAgICB0aGlzLm91dGdvaW5nQ29uZmlnRWRnZXMuc2V0KGZyb21FeHRlbnNpb25OYW1lLCBuZXcgTWFwKFtbdG9FeHRlbnNpb25OYW1lLCBjb25maWdzXV0pKTtcbiAgICB9XG4gICAgY29uc3QgaW5jb21pbmcgPSB0aGlzLmluY29taW5nRWRnZXMuZ2V0KHRvRXh0ZW5zaW9uTmFtZSk7XG4gICAgaWYgKGluY29taW5nKSB7XG4gICAgICBpbmNvbWluZy5hZGQoZnJvbUV4dGVuc2lvbk5hbWUpO1xuICAgIH0gZWxzZSB7XG4gICAgICB0aGlzLmluY29taW5nRWRnZXMuc2V0KHRvRXh0ZW5zaW9uTmFtZSwgbmV3IFNldChbZnJvbUV4dGVuc2lvbk5hbWVdKSk7XG4gICAgfVxuICB9XG4gIGFkZEV4dGVuc2lvbihhcmcpIHtcbiAgICBpZiAoISh0aGlzLl9zb3J0ZWRFeHRlbnNpb25SZXBzID09PSB1bmRlZmluZWQpKSB7XG4gICAgICBmb3JtYXREZXZFcnJvck1lc3NhZ2UoYExleGljYWxCdWlsZGVyOiBhZGRFeHRlbnNpb24gY2FsbGVkIGFmdGVyIGZpbmFsaXphdGlvbmApO1xuICAgIH1cbiAgICBjb25zdCBub3JtYWxpemVkID0gbm9ybWFsaXplRXh0ZW5zaW9uQXJndW1lbnQoYXJnKTtcbiAgICBjb25zdCBbZXh0ZW5zaW9uXSA9IG5vcm1hbGl6ZWQ7XG4gICAgaWYgKCEodHlwZW9mIGV4dGVuc2lvbi5uYW1lID09PSAnc3RyaW5nJykpIHtcbiAgICAgIGZvcm1hdERldkVycm9yTWVzc2FnZShgTGV4aWNhbEJ1aWxkZXI6IGV4dGVuc2lvbiBuYW1lIG11c3QgYmUgc3RyaW5nLCBub3QgJHt0eXBlb2YgZXh0ZW5zaW9uLm5hbWV9YCk7XG4gICAgfVxuICAgIGxldCBleHRlbnNpb25SZXAgPSB0aGlzLmV4dGVuc2lvbk5hbWVNYXAuZ2V0KGV4dGVuc2lvbi5uYW1lKTtcbiAgICBpZiAoIShleHRlbnNpb25SZXAgPT09IHVuZGVmaW5lZCB8fCBleHRlbnNpb25SZXAuZXh0ZW5zaW9uID09PSBleHRlbnNpb24pKSB7XG4gICAgICBmb3JtYXREZXZFcnJvck1lc3NhZ2UoYExleGljYWxCdWlsZGVyOiBNdWx0aXBsZSBleHRlbnNpb25zIHJlZ2lzdGVyZWQgd2l0aCBuYW1lICR7ZXh0ZW5zaW9uLm5hbWV9LCBuYW1lcyBtdXN0IGJlIHVuaXF1ZWApO1xuICAgIH1cbiAgICBpZiAoIWV4dGVuc2lvblJlcCkge1xuICAgICAgZXh0ZW5zaW9uUmVwID0gbmV3IEV4dGVuc2lvblJlcCh0aGlzLCBleHRlbnNpb24pO1xuICAgICAgdGhpcy5leHRlbnNpb25OYW1lTWFwLnNldChleHRlbnNpb24ubmFtZSwgZXh0ZW5zaW9uUmVwKTtcbiAgICAgIGNvbnN0IGhhc0NvbmZsaWN0ID0gdGhpcy5jb25mbGljdHMuZ2V0KGV4dGVuc2lvbi5uYW1lKTtcbiAgICAgIGlmICh0eXBlb2YgaGFzQ29uZmxpY3QgPT09ICdzdHJpbmcnKSB7XG4gICAgICAgIHtcbiAgICAgICAgICBmb3JtYXREZXZFcnJvck1lc3NhZ2UoYExleGljYWxCdWlsZGVyOiBleHRlbnNpb24gJHtleHRlbnNpb24ubmFtZX0gY29uZmxpY3RzIHdpdGggJHtoYXNDb25mbGljdH1gKTtcbiAgICAgICAgfVxuICAgICAgfVxuICAgICAgZm9yIChjb25zdCBuYW1lIG9mIGV4dGVuc2lvbi5jb25mbGljdHNXaXRoIHx8IFtdKSB7XG4gICAgICAgIGlmICghIXRoaXMuZXh0ZW5zaW9uTmFtZU1hcC5oYXMobmFtZSkpIHtcbiAgICAgICAgICBmb3JtYXREZXZFcnJvck1lc3NhZ2UoYExleGljYWxCdWlsZGVyOiBleHRlbnNpb24gJHtleHRlbnNpb24ubmFtZX0gY29uZmxpY3RzIHdpdGggJHtuYW1lfWApO1xuICAgICAgICB9XG4gICAgICAgIHRoaXMuY29uZmxpY3RzLnNldChuYW1lLCBleHRlbnNpb24ubmFtZSk7XG4gICAgICB9XG4gICAgICBmb3IgKGNvbnN0IGRlcCBvZiBleHRlbnNpb24uZGVwZW5kZW5jaWVzIHx8IFtdKSB7XG4gICAgICAgIGNvbnN0IG5vcm1EZXAgPSBub3JtYWxpemVFeHRlbnNpb25Bcmd1bWVudChkZXApO1xuICAgICAgICB0aGlzLmFkZEVkZ2UoZXh0ZW5zaW9uLm5hbWUsIG5vcm1EZXBbMF0ubmFtZSwgbm9ybURlcC5zbGljZSgxKSk7XG4gICAgICAgIHRoaXMuYWRkRXh0ZW5zaW9uKG5vcm1EZXApO1xuICAgICAgfVxuICAgICAgZm9yIChjb25zdCBbZGVwTmFtZSwgY29uZmlnXSBvZiBleHRlbnNpb24ucGVlckRlcGVuZGVuY2llcyB8fCBbXSkge1xuICAgICAgICB0aGlzLmFkZEVkZ2UoZXh0ZW5zaW9uLm5hbWUsIGRlcE5hbWUsIGNvbmZpZyA/IFtjb25maWddIDogW10pO1xuICAgICAgfVxuICAgIH1cbiAgfVxuICBzb3J0ZWRFeHRlbnNpb25SZXBzKCkge1xuICAgIGlmICh0aGlzLl9zb3J0ZWRFeHRlbnNpb25SZXBzKSB7XG4gICAgICByZXR1cm4gdGhpcy5fc29ydGVkRXh0ZW5zaW9uUmVwcztcbiAgICB9XG4gICAgLy8gZGVwdGgtZmlyc3Qgc2VhcmNoIGJhc2VkIHRvcG9sb2dpY2FsIERBRyBzb3J0XG4gICAgLy8gaHR0cHM6Ly9lbi53aWtpcGVkaWEub3JnL3dpa2kvVG9wb2xvZ2ljYWxfc29ydGluZ1xuICAgIGNvbnN0IHNvcnRlZEV4dGVuc2lvblJlcHMgPSBbXTtcbiAgICBjb25zdCB2aXNpdCA9IChyZXAsIGZyb21FeHRlbnNpb25OYW1lKSA9PiB7XG4gICAgICBsZXQgbWFyayA9IHJlcC5zdGF0ZTtcbiAgICAgIGlmIChpc0V4YWN0bHlQZXJtYW5lbnRFeHRlbnNpb25SZXBTdGF0ZShtYXJrKSkge1xuICAgICAgICByZXR1cm47XG4gICAgICB9XG4gICAgICBjb25zdCBleHRlbnNpb25OYW1lID0gcmVwLmV4dGVuc2lvbi5uYW1lO1xuICAgICAgaWYgKCFpc0V4YWN0bHlVbm1hcmtlZEV4dGVuc2lvblJlcFN0YXRlKG1hcmspKSB7XG4gICAgICAgIGZvcm1hdERldkVycm9yTWVzc2FnZShgTGV4aWNhbEJ1aWxkZXI6IENpcmN1bGFyIGRlcGVuZGVuY3kgZGV0ZWN0ZWQgZm9yIEV4dGVuc2lvbiAke2V4dGVuc2lvbk5hbWV9IGZyb20gJHtmcm9tRXh0ZW5zaW9uTmFtZSB8fCAnW3Vua25vd25dJ31gKTtcbiAgICAgIH1cbiAgICAgIG1hcmsgPSBhcHBseVRlbXBvcmFyeU1hcmsobWFyayk7XG4gICAgICByZXAuc3RhdGUgPSBtYXJrO1xuICAgICAgY29uc3Qgb3V0Z29pbmdDb25maWdFZGdlcyA9IHRoaXMub3V0Z29pbmdDb25maWdFZGdlcy5nZXQoZXh0ZW5zaW9uTmFtZSk7XG4gICAgICBpZiAob3V0Z29pbmdDb25maWdFZGdlcykge1xuICAgICAgICBmb3IgKGNvbnN0IHRvRXh0ZW5zaW9uTmFtZSBvZiBvdXRnb2luZ0NvbmZpZ0VkZ2VzLmtleXMoKSkge1xuICAgICAgICAgIGNvbnN0IHRvUmVwID0gdGhpcy5leHRlbnNpb25OYW1lTWFwLmdldCh0b0V4dGVuc2lvbk5hbWUpO1xuICAgICAgICAgIC8vIG1heSBiZSB1bmRlZmluZWQgZm9yIGFuIG9wdGlvbmFsIHBlZXIgZGVwZW5kZW5jeVxuICAgICAgICAgIGlmICh0b1JlcCkge1xuICAgICAgICAgICAgdmlzaXQodG9SZXAsIGV4dGVuc2lvbk5hbWUpO1xuICAgICAgICAgIH1cbiAgICAgICAgfVxuICAgICAgfVxuICAgICAgbWFyayA9IGFwcGx5UGVybWFuZW50TWFyayhtYXJrKTtcbiAgICAgIHJlcC5zdGF0ZSA9IG1hcms7XG4gICAgICBzb3J0ZWRFeHRlbnNpb25SZXBzLnB1c2gocmVwKTtcbiAgICB9O1xuICAgIGZvciAoY29uc3QgcmVwIG9mIHRoaXMuZXh0ZW5zaW9uTmFtZU1hcC52YWx1ZXMoKSkge1xuICAgICAgaWYgKGlzRXhhY3RseVVubWFya2VkRXh0ZW5zaW9uUmVwU3RhdGUocmVwLnN0YXRlKSkge1xuICAgICAgICB2aXNpdChyZXApO1xuICAgICAgfVxuICAgIH1cbiAgICBmb3IgKGNvbnN0IHJlcCBvZiBzb3J0ZWRFeHRlbnNpb25SZXBzKSB7XG4gICAgICBmb3IgKGNvbnN0IFt0b0V4dGVuc2lvbk5hbWUsIGNvbmZpZ3NdIG9mIHRoaXMub3V0Z29pbmdDb25maWdFZGdlcy5nZXQocmVwLmV4dGVuc2lvbi5uYW1lKSB8fCBbXSkge1xuICAgICAgICBpZiAoY29uZmlncy5sZW5ndGggPiAwKSB7XG4gICAgICAgICAgY29uc3QgdG9SZXAgPSB0aGlzLmV4dGVuc2lvbk5hbWVNYXAuZ2V0KHRvRXh0ZW5zaW9uTmFtZSk7XG4gICAgICAgICAgaWYgKHRvUmVwKSB7XG4gICAgICAgICAgICBmb3IgKGNvbnN0IGNvbmZpZyBvZiBjb25maWdzKSB7XG4gICAgICAgICAgICAgIC8vIGVzbGludC1kaXNhYmxlLW5leHQtbGluZSBAdHlwZXNjcmlwdC1lc2xpbnQvbm8tdW5zYWZlLWFyZ3VtZW50IC0tIGFueVxuICAgICAgICAgICAgICB0b1JlcC5jb25maWdzLmFkZChjb25maWcpO1xuICAgICAgICAgICAgfVxuICAgICAgICAgIH1cbiAgICAgICAgfVxuICAgICAgfVxuICAgIH1cbiAgICBmb3IgKGNvbnN0IFtleHRlbnNpb24sIC4uLmNvbmZpZ3NdIG9mIHRoaXMucm9vdHMpIHtcbiAgICAgIGlmIChjb25maWdzLmxlbmd0aCA+IDApIHtcbiAgICAgICAgY29uc3QgdG9SZXAgPSB0aGlzLmV4dGVuc2lvbk5hbWVNYXAuZ2V0KGV4dGVuc2lvbi5uYW1lKTtcbiAgICAgICAgaWYgKCEodG9SZXAgIT09IHVuZGVmaW5lZCkpIHtcbiAgICAgICAgICBmb3JtYXREZXZFcnJvck1lc3NhZ2UoYExleGljYWxCdWlsZGVyOiBFeHBlY3RpbmcgZXhpc3RpbmcgRXh0ZW5zaW9uUmVwIGZvciAke2V4dGVuc2lvbi5uYW1lfWApO1xuICAgICAgICB9XG4gICAgICAgIGZvciAoY29uc3QgY29uZmlnIG9mIGNvbmZpZ3MpIHtcbiAgICAgICAgICB0b1JlcC5jb25maWdzLmFkZChjb25maWcpO1xuICAgICAgICB9XG4gICAgICB9XG4gICAgfVxuICAgIHRoaXMuX3NvcnRlZEV4dGVuc2lvblJlcHMgPSBzb3J0ZWRFeHRlbnNpb25SZXBzO1xuICAgIHJldHVybiB0aGlzLl9zb3J0ZWRFeHRlbnNpb25SZXBzO1xuICB9XG4gIHJlZ2lzdGVyRWRpdG9yKGVkaXRvcikge1xuICAgIGNvbnN0IGV4dGVuc2lvblJlcHMgPSB0aGlzLnNvcnRlZEV4dGVuc2lvblJlcHMoKTtcbiAgICBjb25zdCBjb250cm9sbGVyID0gbmV3IEFib3J0Q29udHJvbGxlcigpO1xuICAgIGNvbnN0IGNsZWFudXBzID0gWygpID0+IGNvbnRyb2xsZXIuYWJvcnQoKV07XG4gICAgY29uc3Qgc2lnbmFsID0gY29udHJvbGxlci5zaWduYWw7XG4gICAgZm9yIChjb25zdCBleHRlbnNpb25SZXAgb2YgZXh0ZW5zaW9uUmVwcykge1xuICAgICAgY29uc3QgY2xlYW51cCA9IGV4dGVuc2lvblJlcC5yZWdpc3RlcihlZGl0b3IsIHNpZ25hbCk7XG4gICAgICBpZiAoY2xlYW51cCkge1xuICAgICAgICBjbGVhbnVwcy5wdXNoKGNsZWFudXApO1xuICAgICAgfVxuICAgIH1cbiAgICBmb3IgKGNvbnN0IGV4dGVuc2lvblJlcCBvZiBleHRlbnNpb25SZXBzKSB7XG4gICAgICBjb25zdCBjbGVhbnVwID0gZXh0ZW5zaW9uUmVwLmFmdGVyUmVnaXN0cmF0aW9uKGVkaXRvcik7XG4gICAgICBpZiAoY2xlYW51cCkge1xuICAgICAgICBjbGVhbnVwcy5wdXNoKGNsZWFudXApO1xuICAgICAgfVxuICAgIH1cbiAgICByZXR1cm4gbWVyZ2VSZWdpc3RlciguLi5jbGVhbnVwcyk7XG4gIH1cbiAgYnVpbGRDcmVhdGVFZGl0b3JBcmdzKCkge1xuICAgIGNvbnN0IGNvbmZpZyA9IHt9O1xuICAgIGNvbnN0IG5vZGVzID0gbmV3IFNldCgpO1xuICAgIGNvbnN0IHJlcGxhY2VkTm9kZXMgPSBuZXcgTWFwKCk7XG4gICAgY29uc3QgaHRtbEV4cG9ydCA9IG5ldyBNYXAoKTtcbiAgICBjb25zdCBodG1sSW1wb3J0ID0ge307XG4gICAgY29uc3QgdGhlbWUgPSB7fTtcbiAgICBjb25zdCBleHRlbnNpb25SZXBzID0gdGhpcy5zb3J0ZWRFeHRlbnNpb25SZXBzKCk7XG4gICAgZm9yIChjb25zdCBleHRlbnNpb25SZXAgb2YgZXh0ZW5zaW9uUmVwcykge1xuICAgICAgY29uc3Qge1xuICAgICAgICBleHRlbnNpb25cbiAgICAgIH0gPSBleHRlbnNpb25SZXA7XG4gICAgICBpZiAoZXh0ZW5zaW9uLm9uRXJyb3IgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICBjb25maWcub25FcnJvciA9IGV4dGVuc2lvbi5vbkVycm9yO1xuICAgICAgfVxuICAgICAgaWYgKGV4dGVuc2lvbi5kaXNhYmxlRXZlbnRzICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgY29uZmlnLmRpc2FibGVFdmVudHMgPSBleHRlbnNpb24uZGlzYWJsZUV2ZW50cztcbiAgICAgIH1cbiAgICAgIGlmIChleHRlbnNpb24ucGFyZW50RWRpdG9yICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgY29uZmlnLnBhcmVudEVkaXRvciA9IGV4dGVuc2lvbi5wYXJlbnRFZGl0b3I7XG4gICAgICB9XG4gICAgICBpZiAoZXh0ZW5zaW9uLmVkaXRhYmxlICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgY29uZmlnLmVkaXRhYmxlID0gZXh0ZW5zaW9uLmVkaXRhYmxlO1xuICAgICAgfVxuICAgICAgaWYgKGV4dGVuc2lvbi5uYW1lc3BhY2UgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICBjb25maWcubmFtZXNwYWNlID0gZXh0ZW5zaW9uLm5hbWVzcGFjZTtcbiAgICAgIH1cbiAgICAgIGlmIChleHRlbnNpb24uJGluaXRpYWxFZGl0b3JTdGF0ZSAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgIGNvbmZpZy4kaW5pdGlhbEVkaXRvclN0YXRlID0gZXh0ZW5zaW9uLiRpbml0aWFsRWRpdG9yU3RhdGU7XG4gICAgICB9XG4gICAgICBpZiAoZXh0ZW5zaW9uLm5vZGVzKSB7XG4gICAgICAgIGZvciAoY29uc3Qgbm9kZSBvZiBnZXROb2RlQ29uZmlnKGV4dGVuc2lvbikpIHtcbiAgICAgICAgICBpZiAodHlwZW9mIG5vZGUgIT09ICdmdW5jdGlvbicpIHtcbiAgICAgICAgICAgIGNvbnN0IGNvbmZsaWN0RXh0ZW5zaW9uID0gcmVwbGFjZWROb2Rlcy5nZXQobm9kZS5yZXBsYWNlKTtcbiAgICAgICAgICAgIGlmIChjb25mbGljdEV4dGVuc2lvbikge1xuICAgICAgICAgICAgICB7XG4gICAgICAgICAgICAgICAgZm9ybWF0RGV2RXJyb3JNZXNzYWdlKGBMZXhpY2FsQnVpbGRlcjogRXh0ZW5zaW9uICR7ZXh0ZW5zaW9uLm5hbWV9IGNhbiBub3QgcmVnaXN0ZXIgcmVwbGFjZW1lbnQgZm9yIG5vZGUgJHtub2RlLnJlcGxhY2UubmFtZX0gYmVjYXVzZSAke2NvbmZsaWN0RXh0ZW5zaW9uLmV4dGVuc2lvbi5uYW1lfSBhbHJlYWR5IGRpZGApO1xuICAgICAgICAgICAgICB9XG4gICAgICAgICAgICB9XG4gICAgICAgICAgICByZXBsYWNlZE5vZGVzLnNldChub2RlLnJlcGxhY2UsIGV4dGVuc2lvblJlcCk7XG4gICAgICAgICAgfVxuICAgICAgICAgIG5vZGVzLmFkZChub2RlKTtcbiAgICAgICAgfVxuICAgICAgfVxuICAgICAgaWYgKGV4dGVuc2lvbi5odG1sKSB7XG4gICAgICAgIGlmIChleHRlbnNpb24uaHRtbC5leHBvcnQpIHtcbiAgICAgICAgICBmb3IgKGNvbnN0IFtrLCB2XSBvZiBleHRlbnNpb24uaHRtbC5leHBvcnQuZW50cmllcygpKSB7XG4gICAgICAgICAgICBodG1sRXhwb3J0LnNldChrLCB2KTtcbiAgICAgICAgICB9XG4gICAgICAgIH1cbiAgICAgICAgaWYgKGV4dGVuc2lvbi5odG1sLmltcG9ydCkge1xuICAgICAgICAgIE9iamVjdC5hc3NpZ24oaHRtbEltcG9ydCwgZXh0ZW5zaW9uLmh0bWwuaW1wb3J0KTtcbiAgICAgICAgfVxuICAgICAgfVxuICAgICAgaWYgKGV4dGVuc2lvbi50aGVtZSkge1xuICAgICAgICBkZWVwVGhlbWVNZXJnZUluUGxhY2UodGhlbWUsIGV4dGVuc2lvbi50aGVtZSk7XG4gICAgICB9XG4gICAgfVxuICAgIGlmIChPYmplY3Qua2V5cyh0aGVtZSkubGVuZ3RoID4gMCkge1xuICAgICAgY29uZmlnLnRoZW1lID0gdGhlbWU7XG4gICAgfVxuICAgIGlmIChub2Rlcy5zaXplKSB7XG4gICAgICBjb25maWcubm9kZXMgPSBbLi4ubm9kZXNdO1xuICAgIH1cbiAgICBjb25zdCBoYXNJbXBvcnQgPSBPYmplY3Qua2V5cyhodG1sSW1wb3J0KS5sZW5ndGggPiAwO1xuICAgIGNvbnN0IGhhc0V4cG9ydCA9IGh0bWxFeHBvcnQuc2l6ZSA+IDA7XG4gICAgaWYgKGhhc0ltcG9ydCB8fCBoYXNFeHBvcnQpIHtcbiAgICAgIGNvbmZpZy5odG1sID0ge307XG4gICAgICBpZiAoaGFzSW1wb3J0KSB7XG4gICAgICAgIGNvbmZpZy5odG1sLmltcG9ydCA9IGh0bWxJbXBvcnQ7XG4gICAgICB9XG4gICAgICBpZiAoaGFzRXhwb3J0KSB7XG4gICAgICAgIGNvbmZpZy5odG1sLmV4cG9ydCA9IGh0bWxFeHBvcnQ7XG4gICAgICB9XG4gICAgfVxuICAgIGZvciAoY29uc3QgZXh0ZW5zaW9uUmVwIG9mIGV4dGVuc2lvblJlcHMpIHtcbiAgICAgIGV4dGVuc2lvblJlcC5pbml0KGNvbmZpZyk7XG4gICAgfVxuICAgIGlmICghY29uZmlnLm9uRXJyb3IpIHtcbiAgICAgIGNvbmZpZy5vbkVycm9yID0gZGVmYXVsdE9uRXJyb3I7XG4gICAgfVxuICAgIHJldHVybiBjb25maWc7XG4gIH1cbn1cblxuLyoqXG4gKiBAZXhwZXJpbWVudGFsXG4gKiBHZXQgdGhlIGZpbmFsaXplZCBjb25maWcgYW5kIG91dHB1dCBvZiBhbiBFeHRlbnNpb24gdGhhdCB3YXMgdXNlZCB0byBidWlsZCB0aGUgZWRpdG9yLlxuICpcbiAqIFRoaXMgaXMgdXNlZnVsIGluIHRoZSBpbXBsZW1lbnRhdGlvbiBvZiBhIExleGljYWxOb2RlIG9yIGluIG90aGVyXG4gKiBzaXR1YXRpb25zIHdoZXJlIHlvdSBoYXZlIGFuIGVkaXRvciByZWZlcmVuY2UgYnV0IGl0J3Mgbm90IGVhc3kgdG9cbiAqIHBhc3MgdGhlIGNvbmZpZyBvciB7QGxpbmsgRXh0ZW5zaW9uUmVnaXN0ZXJTdGF0ZX0gYXJvdW5kLlxuICpcbiAqIEl0IHdpbGwgdGhyb3cgaWYgdGhlIEVkaXRvciB3YXMgbm90IGJ1aWx0IHVzaW5nIHRoaXMgRXh0ZW5zaW9uLlxuICpcbiAqIEBwYXJhbSBlZGl0b3IgLSBUaGUgZWRpdG9yIHRoYXQgd2FzIGJ1aWx0IHVzaW5nIGV4dGVuc2lvblxuICogQHBhcmFtIGV4dGVuc2lvbiAtIFRoZSBjb25jcmV0ZSByZWZlcmVuY2UgdG8gYW4gRXh0ZW5zaW9uIHVzZWQgdG8gYnVpbGQgdGhpcyBlZGl0b3JcbiAqIEByZXR1cm5zIFRoZSBjb25maWcgYW5kIG91dHB1dCBmb3IgdGhhdCBFeHRlbnNpb25cbiAqL1xuZnVuY3Rpb24gZ2V0RXh0ZW5zaW9uRGVwZW5kZW5jeUZyb21FZGl0b3IoZWRpdG9yLCBleHRlbnNpb24pIHtcbiAgY29uc3QgYnVpbGRlciA9IExleGljYWxCdWlsZGVyLmZyb21FZGl0b3IoZWRpdG9yKTtcbiAgY29uc3QgcmVwID0gYnVpbGRlci5nZXRFeHRlbnNpb25SZXAoZXh0ZW5zaW9uKTtcbiAgaWYgKCEocmVwICE9PSB1bmRlZmluZWQpKSB7XG4gICAgZm9ybWF0RGV2RXJyb3JNZXNzYWdlKGBnZXRFeHRlbnNpb25EZXBlbmRlbmN5RnJvbUVkaXRvcjogRXh0ZW5zaW9uICR7ZXh0ZW5zaW9uLm5hbWV9IHdhcyBub3QgYnVpbHQgd2hlbiBjcmVhdGluZyB0aGlzIGVkaXRvcmApO1xuICB9XG4gIHJldHVybiByZXAuZ2V0RXh0ZW5zaW9uRGVwZW5kZW5jeSgpO1xufVxuXG4vKipcbiAqIEBleHBlcmltZW50YWxcbiAqIEdldCB0aGUgZmluYWxpemVkIGNvbmZpZyBhbmQgb3V0cHV0IG9mIGFuIEV4dGVuc2lvbiB0aGF0IHdhcyB1c2VkIHRvIGJ1aWxkIHRoZVxuICogZWRpdG9yIGJ5IG5hbWUuXG4gKlxuICogVGhpcyBjYW4gYmUgdXNlZCBmcm9tIHRoZSBpbXBsZW1lbnRhdGlvbiBvZiBhIExleGljYWxOb2RlIG9yIGluIG90aGVyXG4gKiBzaXR1YXRpb24gd2hlcmUgeW91IGhhdmUgYW4gZWRpdG9yIHJlZmVyZW5jZSBidXQgaXQncyBub3QgZWFzeSB0byBwYXNzIHRoZVxuICogY29uZmlnIGFyb3VuZC4gVXNlIHRoaXMgdmVyc2lvbiBpZiB5b3UgZG8gbm90IGhhdmUgYSBjb25jcmV0ZSByZWZlcmVuY2UgdG9cbiAqIHRoZSBFeHRlbnNpb24gZm9yIHNvbWUgcmVhc29uIChlLmcuIGl0IGlzIGFuIG9wdGlvbmFsIHBlZXIgZGVwZW5kZW5jeSwgb3IgeW91XG4gKiBhcmUgYXZvaWRpbmcgYSBjaXJjdWxhciBpbXBvcnQpLlxuICpcbiAqIEJvdGggdGhlIGV4cGxpY2l0IEV4dGVuc2lvbiB0eXBlIGFuZCB0aGUgbmFtZSBhcmUgcmVxdWlyZWQuXG4gKlxuICogIEBleGFtcGxlXG4gKiBgYGB0c3hcbiAqIGltcG9ydCB0eXBlIHsgSGlzdG9yeUV4dGVuc2lvbiB9IGZyb20gXCJAbGV4aWNhbC9oaXN0b3J5XCI7XG4gKiBnZXRQZWVyRGVwZW5kZW5jeUZyb21FZGl0b3I8dHlwZW9mIEhpc3RvcnlFeHRlbnNpb24+KGVkaXRvciwgXCJAbGV4aWNhbC9oaXN0b3J5L0hpc3RvcnlcIik7XG4gKiBgYGBcblxuICogQHBhcmFtIGVkaXRvciAtIFRoZSBlZGl0b3IgdGhhdCBtYXkgaGF2ZSBiZWVuIGJ1aWx0IHVzaW5nIGV4dGVuc2lvblxuICogQHBhcmFtIGV4dGVuc2lvbk5hbWUgLSBUaGUgbmFtZSBvZiB0aGUgRXh0ZW5zaW9uXG4gKiBAcmV0dXJucyBUaGUgY29uZmlnIGFuZCBvdXRwdXQgb2YgdGhlIEV4dGVuc2lvbiBvciB1bmRlZmluZWRcbiAqL1xuZnVuY3Rpb24gZ2V0UGVlckRlcGVuZGVuY3lGcm9tRWRpdG9yKGVkaXRvciwgZXh0ZW5zaW9uTmFtZSkge1xuICBjb25zdCBidWlsZGVyID0gTGV4aWNhbEJ1aWxkZXIuZnJvbUVkaXRvcihlZGl0b3IpO1xuICBjb25zdCBwZWVyID0gYnVpbGRlci5leHRlbnNpb25OYW1lTWFwLmdldChleHRlbnNpb25OYW1lKTtcbiAgcmV0dXJuIHBlZXIgPyBwZWVyLmdldEV4dGVuc2lvbkRlcGVuZGVuY3koKSA6IHVuZGVmaW5lZDtcbn1cblxuLyoqXG4gKiBHZXQgdGhlIGZpbmFsaXplZCBjb25maWcgYW5kIG91dHB1dCBvZiBhbiBFeHRlbnNpb24gdGhhdCB3YXMgdXNlZCB0byBidWlsZCB0aGVcbiAqIGVkaXRvciBieSBuYW1lLlxuICpcbiAqIFRoaXMgY2FuIGJlIHVzZWQgZnJvbSB0aGUgaW1wbGVtZW50YXRpb24gb2YgYSBMZXhpY2FsTm9kZSBvciBpbiBvdGhlclxuICogc2l0dWF0aW9uIHdoZXJlIHlvdSBoYXZlIGFuIGVkaXRvciByZWZlcmVuY2UgYnV0IGl0J3Mgbm90IGVhc3kgdG8gcGFzcyB0aGVcbiAqIGNvbmZpZyBhcm91bmQuIFVzZSB0aGlzIHZlcnNpb24gaWYgeW91IGRvIG5vdCBoYXZlIGEgY29uY3JldGUgcmVmZXJlbmNlIHRvXG4gKiB0aGUgRXh0ZW5zaW9uIGZvciBzb21lIHJlYXNvbiAoZS5nLiBpdCBpcyBhbiBvcHRpb25hbCBwZWVyIGRlcGVuZGVuY3ksIG9yIHlvdVxuICogYXJlIGF2b2lkaW5nIGEgY2lyY3VsYXIgaW1wb3J0KS5cbiAqXG4gKiBCb3RoIHRoZSBleHBsaWNpdCBFeHRlbnNpb24gdHlwZSBhbmQgdGhlIG5hbWUgYXJlIHJlcXVpcmVkLlxuICpcbiAqICBAZXhhbXBsZVxuICogYGBgdHN4XG4gKiBpbXBvcnQgdHlwZSB7IEVtb2ppRXh0ZW5zaW9uIH0gZnJvbSBcIi4vRW1vamlFeHRlbnNpb25cIjtcbiAqIGV4cG9ydCBjbGFzcyBFbW9qaU5vZGUgZXh0ZW5kcyBUZXh0Tm9kZSB7XG4gKiAgIC8vIG90aGVyIGltcGxlbWVudGF0aW9uIGRldGFpbHMgbm90IGluY2x1ZGVkXG4gKiAgIGNyZWF0ZURPTShcbiAqICAgICBjb25maWc6IEVkaXRvckNvbmZpZyxcbiAqICAgICBlZGl0b3I/OiBMZXhpY2FsRWRpdG9yIHwgdW5kZWZpbmVkXG4gKiAgICk6IEhUTUxFbGVtZW50IHtcbiAqICAgICBjb25zdCBkb20gPSBzdXBlci5jcmVhdGVET00oY29uZmlnLCBlZGl0b3IpO1xuICogICAgIGFkZENsYXNzTmFtZXNUb0VsZW1lbnQoXG4gKiAgICAgICBkb20sXG4gKiAgICAgICBnZXRQZWVyRGVwZW5kZW5jeUZyb21FZGl0b3JPclRocm93PHR5cGVvZiBFbW9qaUV4dGVuc2lvbj4oXG4gKiAgICAgICAgIGVkaXRvciB8fCAkZ2V0RWRpdG9yKCksXG4gKiAgICAgICAgIFwiQGxleGljYWwvcGxheWdyb3VuZC9lbW9qaVwiLFxuICogICAgICAgKS5jb25maWcuZW1vamlDbGFzcyxcbiAqICAgICApO1xuICogICAgIHJldHVybiBkb207XG4gKiAgIH1cbiAqIH1cbiAqIGBgYFxuXG4gKiBAcGFyYW0gZWRpdG9yIC0gVGhlIGVkaXRvciB0aGF0IG1heSBoYXZlIGJlZW4gYnVpbHQgdXNpbmcgZXh0ZW5zaW9uXG4gKiBAcGFyYW0gZXh0ZW5zaW9uTmFtZSAtIFRoZSBuYW1lIG9mIHRoZSBFeHRlbnNpb25cbiAqIEByZXR1cm5zIFRoZSBjb25maWcgYW5kIG91dHB1dCBvZiB0aGUgRXh0ZW5zaW9uXG4gKi9cbmZ1bmN0aW9uIGdldFBlZXJEZXBlbmRlbmN5RnJvbUVkaXRvck9yVGhyb3coZWRpdG9yLCBleHRlbnNpb25OYW1lKSB7XG4gIGNvbnN0IGRlcCA9IGdldFBlZXJEZXBlbmRlbmN5RnJvbUVkaXRvcihlZGl0b3IsIGV4dGVuc2lvbk5hbWUpO1xuICBpZiAoIShkZXAgIT09IHVuZGVmaW5lZCkpIHtcbiAgICBmb3JtYXREZXZFcnJvck1lc3NhZ2UoYGdldFBlZXJEZXBlbmRlbmN5RnJvbUVkaXRvck9yVGhyb3c6IEVkaXRvciB3YXMgbm90IGJ1aWx0IHdpdGggRXh0ZW5zaW9uICR7ZXh0ZW5zaW9uTmFtZX1gKTtcbiAgfVxuICByZXR1cm4gZGVwO1xufVxuXG4vKipcbiAqIENvcHlyaWdodCAoYykgTWV0YSBQbGF0Zm9ybXMsIEluYy4gYW5kIGFmZmlsaWF0ZXMuXG4gKlxuICogVGhpcyBzb3VyY2UgY29kZSBpcyBsaWNlbnNlZCB1bmRlciB0aGUgTUlUIGxpY2Vuc2UgZm91bmQgaW4gdGhlXG4gKiBMSUNFTlNFIGZpbGUgaW4gdGhlIHJvb3QgZGlyZWN0b3J5IG9mIHRoaXMgc291cmNlIHRyZWUuXG4gKlxuICovXG5cbmNvbnN0IEVNUFRZX1NFVCA9IG5ldyBTZXQoKTtcblxuLyoqXG4gKiBBbiBleHRlbnNpb24gdGhhdCBwcm92aWRlcyBhIGB3YXRjaE5vZGVLZXlgIG91dHB1dCB0aGF0XG4gKiByZXR1cm5zIGEgc2lnbmFsIGZvciB0aGUgc2VsZWN0aW9uIHN0YXRlIG9mIGEgbm9kZS5cbiAqXG4gKiBUeXBpY2FsbHkgdXNlZCBmb3IgdHJhY2tpbmcgd2hldGhlciBhIERlY29yYXRvck5vZGUgaXNcbiAqIGN1cnJlbnRseSBzZWxlY3RlZCBvciBub3QuIEEgZnJhbWV3b3JrIGluZGVwZW5kZW50XG4gKiBhbHRlcm5hdGl2ZSB0byB7QGxpbmsgdXNlTGV4aWNhbE5vZGVTZWxlY3Rpb259LlxuICovXG5jb25zdCBOb2RlU2VsZWN0aW9uRXh0ZW5zaW9uID0gZGVmaW5lRXh0ZW5zaW9uKHtcbiAgYnVpbGQoZWRpdG9yLCBjb25maWcsIHN0YXRlKSB7XG4gICAgY29uc3QgZWRpdG9yU3RhdGVTdG9yZSA9IHN0YXRlLmdldERlcGVuZGVuY3koRWRpdG9yU3RhdGVFeHRlbnNpb24pLm91dHB1dDtcbiAgICBjb25zdCB3YXRjaGVkTm9kZVN0b3JlID0gZCh7XG4gICAgICB3YXRjaGVkTm9kZUtleXM6IG5ldyBNYXAoKVxuICAgIH0pO1xuICAgIGNvbnN0IHNlbGVjdGVkTm9kZUtleXMgPSB3YXRjaGVkU2lnbmFsKCgpID0+IHVuZGVmaW5lZCwgKCkgPT4gRSgoKSA9PiB7XG4gICAgICBjb25zdCBwcmV2U2VsZWN0ZWROb2RlS2V5cyA9IHNlbGVjdGVkTm9kZUtleXMucGVlaygpO1xuICAgICAgY29uc3Qge1xuICAgICAgICB3YXRjaGVkTm9kZUtleXNcbiAgICAgIH0gPSB3YXRjaGVkTm9kZVN0b3JlLnZhbHVlO1xuICAgICAgbGV0IG5leHRTZWxlY3RlZE5vZGVLZXlzO1xuICAgICAgbGV0IGRpZENoYW5nZSA9IGZhbHNlO1xuICAgICAgZWRpdG9yU3RhdGVTdG9yZS52YWx1ZS5yZWFkKCgpID0+IHtcbiAgICAgICAgY29uc3Qgc2VsZWN0aW9uID0gJGdldFNlbGVjdGlvbigpO1xuICAgICAgICBpZiAoc2VsZWN0aW9uKSB7XG4gICAgICAgICAgZm9yIChjb25zdCBba2V5LCBsaXN0ZW5lcnNdIG9mIHdhdGNoZWROb2RlS2V5cy5lbnRyaWVzKCkpIHtcbiAgICAgICAgICAgIGlmIChsaXN0ZW5lcnMuc2l6ZSA9PT0gMCkge1xuICAgICAgICAgICAgICAvLyBXZSBpbnRlbnRpb25hbGx5IG11dGF0ZSB0aGlzIHdpdGhvdXQgZmlyaW5nIGEgc2lnbmFsLCB0b1xuICAgICAgICAgICAgICAvLyBhdm9pZCByZS10cmlnZ2VyaW5nIHRoaXMgZWZmZWN0LiBUaGVyZSBhcmUgbm8gc3Vic2NyaWJlcnNcbiAgICAgICAgICAgICAgLy8gc28gbm90aGluZyBjYW4gb2JzZXJ2ZSB3aGV0aGVyIGtleSB3YXMgaW4gdGhlIHNldCBvciBub3RcbiAgICAgICAgICAgICAgd2F0Y2hlZE5vZGVLZXlzLmRlbGV0ZShrZXkpO1xuICAgICAgICAgICAgICBjb250aW51ZTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICAgIGNvbnN0IG5vZGUgPSAkZ2V0Tm9kZUJ5S2V5KGtleSk7XG4gICAgICAgICAgICBjb25zdCBpc1NlbGVjdGVkID0gbm9kZSAmJiBub2RlLmlzU2VsZWN0ZWQoKSB8fCBmYWxzZTtcbiAgICAgICAgICAgIGRpZENoYW5nZSA9IGRpZENoYW5nZSB8fCBpc1NlbGVjdGVkICE9PSAocHJldlNlbGVjdGVkTm9kZUtleXMgPyBwcmV2U2VsZWN0ZWROb2RlS2V5cy5oYXMoa2V5KSA6IGZhbHNlKTtcbiAgICAgICAgICAgIGlmIChpc1NlbGVjdGVkKSB7XG4gICAgICAgICAgICAgIG5leHRTZWxlY3RlZE5vZGVLZXlzID0gbmV4dFNlbGVjdGVkTm9kZUtleXMgfHwgbmV3IFNldCgpO1xuICAgICAgICAgICAgICBuZXh0U2VsZWN0ZWROb2RlS2V5cy5hZGQoa2V5KTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICB9XG4gICAgICAgIH1cbiAgICAgIH0pO1xuICAgICAgaWYgKCEoIWRpZENoYW5nZSAmJiBuZXh0U2VsZWN0ZWROb2RlS2V5cyAmJiBwcmV2U2VsZWN0ZWROb2RlS2V5cyAmJiBuZXh0U2VsZWN0ZWROb2RlS2V5cy5zaXplID09PSBwcmV2U2VsZWN0ZWROb2RlS2V5cy5zaXplKSkge1xuICAgICAgICBzZWxlY3RlZE5vZGVLZXlzLnZhbHVlID0gbmV4dFNlbGVjdGVkTm9kZUtleXM7XG4gICAgICB9XG4gICAgfSkpO1xuICAgIGZ1bmN0aW9uIHdhdGNoTm9kZUtleShrZXkpIHtcbiAgICAgIGNvbnN0IHdhdGNoZXIgPSB3KCgpID0+IChzZWxlY3RlZE5vZGVLZXlzLnZhbHVlIHx8IEVNUFRZX1NFVCkuaGFzKGtleSkpO1xuICAgICAgY29uc3Qge1xuICAgICAgICB3YXRjaGVkTm9kZUtleXNcbiAgICAgIH0gPSB3YXRjaGVkTm9kZVN0b3JlLnBlZWsoKTtcbiAgICAgIGxldCBsaXN0ZW5lcnMgPSB3YXRjaGVkTm9kZUtleXMuZ2V0KGtleSk7XG4gICAgICBjb25zdCBoYWRMaXN0ZW5lciA9IGxpc3RlbmVycyAhPT0gdW5kZWZpbmVkO1xuICAgICAgbGlzdGVuZXJzID0gbGlzdGVuZXJzIHx8IG5ldyBTZXQoKTtcbiAgICAgIGxpc3RlbmVycy5hZGQod2F0Y2hlcik7XG4gICAgICBpZiAoIWhhZExpc3RlbmVyKSB7XG4gICAgICAgIHdhdGNoZWROb2RlS2V5cy5zZXQoa2V5LCBsaXN0ZW5lcnMpO1xuICAgICAgICB3YXRjaGVkTm9kZVN0b3JlLnZhbHVlID0ge1xuICAgICAgICAgIHdhdGNoZWROb2RlS2V5c1xuICAgICAgICB9O1xuICAgICAgfVxuICAgICAgcmV0dXJuIHdhdGNoZXI7XG4gICAgfVxuICAgIHJldHVybiB7XG4gICAgICB3YXRjaE5vZGVLZXlcbiAgICB9O1xuICB9LFxuICBkZXBlbmRlbmNpZXM6IFtFZGl0b3JTdGF0ZUV4dGVuc2lvbl0sXG4gIG5hbWU6ICdAbGV4aWNhbC9leHRlbnNpb24vTm9kZVNlbGVjdGlvbidcbn0pO1xuXG4vKipcbiAqIENvcHlyaWdodCAoYykgTWV0YSBQbGF0Zm9ybXMsIEluYy4gYW5kIGFmZmlsaWF0ZXMuXG4gKlxuICogVGhpcyBzb3VyY2UgY29kZSBpcyBsaWNlbnNlZCB1bmRlciB0aGUgTUlUIGxpY2Vuc2UgZm91bmQgaW4gdGhlXG4gKiBMSUNFTlNFIGZpbGUgaW4gdGhlIHJvb3QgZGlyZWN0b3J5IG9mIHRoaXMgc291cmNlIHRyZWUuXG4gKlxuICovXG5cbmNvbnN0IElOU0VSVF9IT1JJWk9OVEFMX1JVTEVfQ09NTUFORCA9IGNyZWF0ZUNvbW1hbmQoJ0lOU0VSVF9IT1JJWk9OVEFMX1JVTEVfQ09NTUFORCcpO1xuY2xhc3MgSG9yaXpvbnRhbFJ1bGVOb2RlIGV4dGVuZHMgRGVjb3JhdG9yTm9kZSB7XG4gIHN0YXRpYyBnZXRUeXBlKCkge1xuICAgIHJldHVybiAnaG9yaXpvbnRhbHJ1bGUnO1xuICB9XG4gIHN0YXRpYyBjbG9uZShub2RlKSB7XG4gICAgcmV0dXJuIG5ldyBIb3Jpem9udGFsUnVsZU5vZGUobm9kZS5fX2tleSk7XG4gIH1cbiAgc3RhdGljIGltcG9ydEpTT04oc2VyaWFsaXplZE5vZGUpIHtcbiAgICByZXR1cm4gJGNyZWF0ZUhvcml6b250YWxSdWxlTm9kZSgpLnVwZGF0ZUZyb21KU09OKHNlcmlhbGl6ZWROb2RlKTtcbiAgfVxuICBzdGF0aWMgaW1wb3J0RE9NKCkge1xuICAgIHJldHVybiB7XG4gICAgICBocjogKCkgPT4gKHtcbiAgICAgICAgY29udmVyc2lvbjogJGNvbnZlcnRIb3Jpem9udGFsUnVsZUVsZW1lbnQsXG4gICAgICAgIHByaW9yaXR5OiAwXG4gICAgICB9KVxuICAgIH07XG4gIH1cbiAgZXhwb3J0RE9NKCkge1xuICAgIHJldHVybiB7XG4gICAgICBlbGVtZW50OiBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCdocicpXG4gICAgfTtcbiAgfVxuICBjcmVhdGVET00oY29uZmlnKSB7XG4gICAgY29uc3QgZWxlbWVudCA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ2hyJyk7XG4gICAgYWRkQ2xhc3NOYW1lc1RvRWxlbWVudChlbGVtZW50LCBjb25maWcudGhlbWUuaHIpO1xuICAgIHJldHVybiBlbGVtZW50O1xuICB9XG4gIGdldFRleHRDb250ZW50KCkge1xuICAgIHJldHVybiAnXFxuJztcbiAgfVxuICBpc0lubGluZSgpIHtcbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cbiAgdXBkYXRlRE9NKCkge1xuICAgIHJldHVybiBmYWxzZTtcbiAgfVxufVxuZnVuY3Rpb24gJGNvbnZlcnRIb3Jpem9udGFsUnVsZUVsZW1lbnQoKSB7XG4gIHJldHVybiB7XG4gICAgbm9kZTogJGNyZWF0ZUhvcml6b250YWxSdWxlTm9kZSgpXG4gIH07XG59XG5mdW5jdGlvbiAkY3JlYXRlSG9yaXpvbnRhbFJ1bGVOb2RlKCkge1xuICByZXR1cm4gJGNyZWF0ZShIb3Jpem9udGFsUnVsZU5vZGUpO1xufVxuZnVuY3Rpb24gJGlzSG9yaXpvbnRhbFJ1bGVOb2RlKG5vZGUpIHtcbiAgcmV0dXJuIG5vZGUgaW5zdGFuY2VvZiBIb3Jpem9udGFsUnVsZU5vZGU7XG59XG5mdW5jdGlvbiAkdG9nZ2xlTm9kZVNlbGVjdGlvbihub2RlLCBzaGlmdEtleSA9IGZhbHNlKSB7XG4gIGNvbnN0IHNlbGVjdGlvbiA9ICRnZXRTZWxlY3Rpb24oKTtcbiAgY29uc3Qgd2FzU2VsZWN0ZWQgPSBub2RlLmlzU2VsZWN0ZWQoKTtcbiAgY29uc3Qga2V5ID0gbm9kZS5nZXRLZXkoKTtcbiAgbGV0IG5vZGVTZWxlY3Rpb247XG4gIGlmIChzaGlmdEtleSAmJiAkaXNOb2RlU2VsZWN0aW9uKHNlbGVjdGlvbikpIHtcbiAgICBub2RlU2VsZWN0aW9uID0gc2VsZWN0aW9uO1xuICB9IGVsc2Uge1xuICAgIG5vZGVTZWxlY3Rpb24gPSAkY3JlYXRlTm9kZVNlbGVjdGlvbigpO1xuICAgICRzZXRTZWxlY3Rpb24obm9kZVNlbGVjdGlvbik7XG4gIH1cbiAgaWYgKHdhc1NlbGVjdGVkKSB7XG4gICAgbm9kZVNlbGVjdGlvbi5kZWxldGUoa2V5KTtcbiAgfSBlbHNlIHtcbiAgICBub2RlU2VsZWN0aW9uLmFkZChrZXkpO1xuICB9XG59XG5cbi8qKlxuICogQW4gZXh0ZW5zaW9uIGZvciBIb3Jpem9udGFsUnVsZU5vZGUgdGhhdCBwcm92aWRlcyBhbiBpbXBsZW1lbnRhdGlvbiB0aGF0XG4gKiB3b3JrcyB3aXRob3V0IGFueSBSZWFjdCBkZXBlbmRlbmN5LlxuICovXG5jb25zdCBIb3Jpem9udGFsUnVsZUV4dGVuc2lvbiA9IGRlZmluZUV4dGVuc2lvbih7XG4gIGRlcGVuZGVuY2llczogW0VkaXRvclN0YXRlRXh0ZW5zaW9uLCBOb2RlU2VsZWN0aW9uRXh0ZW5zaW9uXSxcbiAgbmFtZTogJ0BsZXhpY2FsL2V4dGVuc2lvbi9Ib3Jpem9udGFsUnVsZScsXG4gIG5vZGVzOiAoKSA9PiBbSG9yaXpvbnRhbFJ1bGVOb2RlXSxcbiAgcmVnaXN0ZXIoZWRpdG9yLCBjb25maWcsIHN0YXRlKSB7XG4gICAgY29uc3Qge1xuICAgICAgd2F0Y2hOb2RlS2V5XG4gICAgfSA9IHN0YXRlLmdldERlcGVuZGVuY3koTm9kZVNlbGVjdGlvbkV4dGVuc2lvbikub3V0cHV0O1xuICAgIGNvbnN0IG5vZGVTZWxlY3Rpb25TdG9yZSA9IGQoe1xuICAgICAgbm9kZVNlbGVjdGlvbnM6IG5ldyBNYXAoKVxuICAgIH0pO1xuICAgIGNvbnN0IGlzU2VsZWN0ZWRDbGFzc05hbWUgPSBlZGl0b3IuX2NvbmZpZy50aGVtZS5oclNlbGVjdGVkID8/ICdzZWxlY3RlZCc7XG4gICAgcmV0dXJuIG1lcmdlUmVnaXN0ZXIoZWRpdG9yLnJlZ2lzdGVyQ29tbWFuZChDTElDS19DT01NQU5ELCBldmVudCA9PiB7XG4gICAgICBpZiAoaXNET01Ob2RlKGV2ZW50LnRhcmdldCkpIHtcbiAgICAgICAgY29uc3Qgbm9kZSA9ICRnZXROb2RlRnJvbURPTU5vZGUoZXZlbnQudGFyZ2V0KTtcbiAgICAgICAgaWYgKCRpc0hvcml6b250YWxSdWxlTm9kZShub2RlKSkge1xuICAgICAgICAgICR0b2dnbGVOb2RlU2VsZWN0aW9uKG5vZGUsIGV2ZW50LnNoaWZ0S2V5KTtcbiAgICAgICAgICByZXR1cm4gdHJ1ZTtcbiAgICAgICAgfVxuICAgICAgfVxuICAgICAgcmV0dXJuIGZhbHNlO1xuICAgIH0sIENPTU1BTkRfUFJJT1JJVFlfTE9XKSwgZWRpdG9yLnJlZ2lzdGVyTXV0YXRpb25MaXN0ZW5lcihIb3Jpem9udGFsUnVsZU5vZGUsIChub2RlcywgcGF5bG9hZCkgPT4ge1xuICAgICAgbygoKSA9PiB7XG4gICAgICAgIGxldCBkaWRDaGFuZ2UgPSBmYWxzZTtcbiAgICAgICAgY29uc3Qge1xuICAgICAgICAgIG5vZGVTZWxlY3Rpb25zXG4gICAgICAgIH0gPSBub2RlU2VsZWN0aW9uU3RvcmUucGVlaygpO1xuICAgICAgICBmb3IgKGNvbnN0IFtrLCB2XSBvZiBub2Rlcy5lbnRyaWVzKCkpIHtcbiAgICAgICAgICBpZiAodiA9PT0gJ2Rlc3Ryb3llZCcpIHtcbiAgICAgICAgICAgIG5vZGVTZWxlY3Rpb25zLmRlbGV0ZShrKTtcbiAgICAgICAgICAgIGRpZENoYW5nZSA9IHRydWU7XG4gICAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICAgIGNvbnN0IHByZXYgPSBub2RlU2VsZWN0aW9ucy5nZXQoayk7XG4gICAgICAgICAgICBjb25zdCBkb20gPSBlZGl0b3IuZ2V0RWxlbWVudEJ5S2V5KGspO1xuICAgICAgICAgICAgaWYgKHByZXYpIHtcbiAgICAgICAgICAgICAgcHJldi5kb21Ob2RlLnZhbHVlID0gZG9tO1xuICAgICAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICAgICAgZGlkQ2hhbmdlID0gdHJ1ZTtcbiAgICAgICAgICAgICAgbm9kZVNlbGVjdGlvbnMuc2V0KGssIHtcbiAgICAgICAgICAgICAgICBkb21Ob2RlOiBkKGRvbSksXG4gICAgICAgICAgICAgICAgc2VsZWN0ZWRTaWduYWw6IHdhdGNoTm9kZUtleShrKVxuICAgICAgICAgICAgICB9KTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICB9XG4gICAgICAgIH1cbiAgICAgICAgaWYgKGRpZENoYW5nZSkge1xuICAgICAgICAgIG5vZGVTZWxlY3Rpb25TdG9yZS52YWx1ZSA9IHtcbiAgICAgICAgICAgIG5vZGVTZWxlY3Rpb25zXG4gICAgICAgICAgfTtcbiAgICAgICAgfVxuICAgICAgfSk7XG4gICAgfSksIEUoKCkgPT4ge1xuICAgICAgY29uc3QgZWZmZWN0cyA9IFtdO1xuICAgICAgZm9yIChjb25zdCB7XG4gICAgICAgIGRvbU5vZGUsXG4gICAgICAgIHNlbGVjdGVkU2lnbmFsXG4gICAgICB9IG9mIG5vZGVTZWxlY3Rpb25TdG9yZS52YWx1ZS5ub2RlU2VsZWN0aW9ucy52YWx1ZXMoKSkge1xuICAgICAgICBlZmZlY3RzLnB1c2goRSgoKSA9PiB7XG4gICAgICAgICAgY29uc3QgZG9tID0gZG9tTm9kZS52YWx1ZTtcbiAgICAgICAgICBpZiAoZG9tKSB7XG4gICAgICAgICAgICBjb25zdCBpc1NlbGVjdGVkID0gc2VsZWN0ZWRTaWduYWwudmFsdWU7XG4gICAgICAgICAgICBpZiAoaXNTZWxlY3RlZCkge1xuICAgICAgICAgICAgICBhZGRDbGFzc05hbWVzVG9FbGVtZW50KGRvbSwgaXNTZWxlY3RlZENsYXNzTmFtZSk7XG4gICAgICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgICByZW1vdmVDbGFzc05hbWVzRnJvbUVsZW1lbnQoZG9tLCBpc1NlbGVjdGVkQ2xhc3NOYW1lKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICB9XG4gICAgICAgIH0pKTtcbiAgICAgIH1cbiAgICAgIHJldHVybiBtZXJnZVJlZ2lzdGVyKC4uLmVmZmVjdHMpO1xuICAgIH0pKTtcbiAgfVxufSk7XG5cbi8qKlxuICogQ29weXJpZ2h0IChjKSBNZXRhIFBsYXRmb3JtcywgSW5jLiBhbmQgYWZmaWxpYXRlcy5cbiAqXG4gKiBUaGlzIHNvdXJjZSBjb2RlIGlzIGxpY2Vuc2VkIHVuZGVyIHRoZSBNSVQgbGljZW5zZSBmb3VuZCBpbiB0aGVcbiAqIExJQ0VOU0UgZmlsZSBpbiB0aGUgcm9vdCBkaXJlY3Rvcnkgb2YgdGhpcyBzb3VyY2UgdHJlZS5cbiAqXG4gKi9cblxuZnVuY3Rpb24gJGluZGVudE92ZXJUYWIoc2VsZWN0aW9uKSB7XG4gIC8vIGNvbnN0IGhhbmRsZWQgPSBuZXcgU2V0KCk7XG4gIGNvbnN0IG5vZGVzID0gc2VsZWN0aW9uLmdldE5vZGVzKCk7XG4gIGNvbnN0IGNhbkluZGVudEJsb2NrTm9kZXMgPSBub2Rlcy5maWx0ZXIobm9kZSA9PiAkaXNCbG9ja0VsZW1lbnROb2RlKG5vZGUpICYmIG5vZGUuY2FuSW5kZW50KCkpO1xuICAvLyAxLiBJZiBzZWxlY3Rpb24gc3BhbnMgYWNyb3NzIGNhbkluZGVudCBibG9jayBub2RlczogaW5kZW50XG4gIGlmIChjYW5JbmRlbnRCbG9ja05vZGVzLmxlbmd0aCA+IDApIHtcbiAgICByZXR1cm4gdHJ1ZTtcbiAgfVxuICAvLyAyLiBJZiBmaXJzdCAoYW5jaG9yL2ZvY3VzKSBpcyBhdCBibG9jayBzdGFydDogaW5kZW50XG4gIGNvbnN0IGFuY2hvciA9IHNlbGVjdGlvbi5hbmNob3I7XG4gIGNvbnN0IGZvY3VzID0gc2VsZWN0aW9uLmZvY3VzO1xuICBjb25zdCBmaXJzdCA9IGZvY3VzLmlzQmVmb3JlKGFuY2hvcikgPyBmb2N1cyA6IGFuY2hvcjtcbiAgY29uc3QgZmlyc3ROb2RlID0gZmlyc3QuZ2V0Tm9kZSgpO1xuICBjb25zdCBmaXJzdEJsb2NrID0gJGdldE5lYXJlc3RCbG9ja0VsZW1lbnRBbmNlc3Rvck9yVGhyb3coZmlyc3ROb2RlKTtcbiAgaWYgKGZpcnN0QmxvY2suY2FuSW5kZW50KCkpIHtcbiAgICBjb25zdCBmaXJzdEJsb2NrS2V5ID0gZmlyc3RCbG9jay5nZXRLZXkoKTtcbiAgICBsZXQgc2VsZWN0aW9uQXRTdGFydCA9ICRjcmVhdGVSYW5nZVNlbGVjdGlvbigpO1xuICAgIHNlbGVjdGlvbkF0U3RhcnQuYW5jaG9yLnNldChmaXJzdEJsb2NrS2V5LCAwLCAnZWxlbWVudCcpO1xuICAgIHNlbGVjdGlvbkF0U3RhcnQuZm9jdXMuc2V0KGZpcnN0QmxvY2tLZXksIDAsICdlbGVtZW50Jyk7XG4gICAgc2VsZWN0aW9uQXRTdGFydCA9ICRub3JtYWxpemVTZWxlY3Rpb25fX0VYUEVSSU1FTlRBTChzZWxlY3Rpb25BdFN0YXJ0KTtcbiAgICBpZiAoc2VsZWN0aW9uQXRTdGFydC5hbmNob3IuaXMoZmlyc3QpKSB7XG4gICAgICByZXR1cm4gdHJ1ZTtcbiAgICB9XG4gIH1cbiAgLy8gMy4gRWxzZTogdGFiXG4gIHJldHVybiBmYWxzZTtcbn1cbmZ1bmN0aW9uICRkZWZhdWx0Q2FuSW5kZW50KG5vZGUpIHtcbiAgcmV0dXJuIG5vZGUuY2FuQmVFbXB0eSgpO1xufVxuZnVuY3Rpb24gcmVnaXN0ZXJUYWJJbmRlbnRhdGlvbihlZGl0b3IsIG1heEluZGVudCwgJGNhbkluZGVudCA9ICRkZWZhdWx0Q2FuSW5kZW50KSB7XG4gIHJldHVybiBtZXJnZVJlZ2lzdGVyKGVkaXRvci5yZWdpc3RlckNvbW1hbmQoS0VZX1RBQl9DT01NQU5ELCBldmVudCA9PiB7XG4gICAgY29uc3Qgc2VsZWN0aW9uID0gJGdldFNlbGVjdGlvbigpO1xuICAgIGlmICghJGlzUmFuZ2VTZWxlY3Rpb24oc2VsZWN0aW9uKSkge1xuICAgICAgcmV0dXJuIGZhbHNlO1xuICAgIH1cbiAgICBldmVudC5wcmV2ZW50RGVmYXVsdCgpO1xuICAgIGNvbnN0IGNvbW1hbmQgPSAkaW5kZW50T3ZlclRhYihzZWxlY3Rpb24pID8gZXZlbnQuc2hpZnRLZXkgPyBPVVRERU5UX0NPTlRFTlRfQ09NTUFORCA6IElOREVOVF9DT05URU5UX0NPTU1BTkQgOiBJTlNFUlRfVEFCX0NPTU1BTkQ7XG4gICAgcmV0dXJuIGVkaXRvci5kaXNwYXRjaENvbW1hbmQoY29tbWFuZCwgdW5kZWZpbmVkKTtcbiAgfSwgQ09NTUFORF9QUklPUklUWV9FRElUT1IpLCBlZGl0b3IucmVnaXN0ZXJDb21tYW5kKElOREVOVF9DT05URU5UX0NPTU1BTkQsICgpID0+IHtcbiAgICBjb25zdCBjdXJyZW50TWF4SW5kZW50ID0gdHlwZW9mIG1heEluZGVudCA9PT0gJ251bWJlcicgPyBtYXhJbmRlbnQgOiBtYXhJbmRlbnQgPyBtYXhJbmRlbnQucGVlaygpIDogbnVsbDtcbiAgICBjb25zdCBzZWxlY3Rpb24gPSAkZ2V0U2VsZWN0aW9uKCk7XG4gICAgaWYgKCEkaXNSYW5nZVNlbGVjdGlvbihzZWxlY3Rpb24pKSB7XG4gICAgICByZXR1cm4gZmFsc2U7XG4gICAgfVxuICAgIGNvbnN0ICRjdXJyZW50Q2FuSW5kZW50ID0gdHlwZW9mICRjYW5JbmRlbnQgPT09ICdmdW5jdGlvbicgPyAkY2FuSW5kZW50IDogJGNhbkluZGVudC5wZWVrKCk7XG4gICAgcmV0dXJuICRoYW5kbGVJbmRlbnRBbmRPdXRkZW50KGJsb2NrID0+IHtcbiAgICAgIGlmICgkY3VycmVudENhbkluZGVudChibG9jaykpIHtcbiAgICAgICAgY29uc3QgbmV3SW5kZW50ID0gYmxvY2suZ2V0SW5kZW50KCkgKyAxO1xuICAgICAgICBpZiAoIWN1cnJlbnRNYXhJbmRlbnQgfHwgbmV3SW5kZW50IDwgY3VycmVudE1heEluZGVudCkge1xuICAgICAgICAgIGJsb2NrLnNldEluZGVudChuZXdJbmRlbnQpO1xuICAgICAgICB9XG4gICAgICB9XG4gICAgfSk7XG4gIH0sIENPTU1BTkRfUFJJT1JJVFlfQ1JJVElDQUwpKTtcbn1cbi8qKlxuICogVGhpcyBleHRlbnNpb24gYWRkcyB0aGUgYWJpbGl0eSB0byBpbmRlbnQgY29udGVudCB1c2luZyB0aGUgdGFiIGtleS4gR2VuZXJhbGx5LCB3ZSBkb24ndFxuICogcmVjb21tZW5kIHVzaW5nIHRoaXMgcGx1Z2luIGFzIGl0IGNvdWxkIG5lZ2F0aXZlbHkgYWZmZWN0IGFjY2Vzc2liaWxpdHkgZm9yIGtleWJvYXJkXG4gKiB1c2VycywgY2F1c2luZyBmb2N1cyB0byBiZWNvbWUgdHJhcHBlZCB3aXRoaW4gdGhlIGVkaXRvci5cbiAqL1xuY29uc3QgVGFiSW5kZW50YXRpb25FeHRlbnNpb24gPSBkZWZpbmVFeHRlbnNpb24oe1xuICBidWlsZChlZGl0b3IsIGNvbmZpZywgc3RhdGUpIHtcbiAgICByZXR1cm4gbmFtZWRTaWduYWxzKGNvbmZpZyk7XG4gIH0sXG4gIGNvbmZpZzogc2FmZUNhc3Qoe1xuICAgICRjYW5JbmRlbnQ6ICRkZWZhdWx0Q2FuSW5kZW50LFxuICAgIGRpc2FibGVkOiBmYWxzZSxcbiAgICBtYXhJbmRlbnQ6IG51bGxcbiAgfSksXG4gIG5hbWU6ICdAbGV4aWNhbC9leHRlbnNpb24vVGFiSW5kZW50YXRpb24nLFxuICByZWdpc3RlcihlZGl0b3IsIGNvbmZpZywgc3RhdGUpIHtcbiAgICBjb25zdCB7XG4gICAgICBkaXNhYmxlZCxcbiAgICAgIG1heEluZGVudCxcbiAgICAgICRjYW5JbmRlbnRcbiAgICB9ID0gc3RhdGUuZ2V0T3V0cHV0KCk7XG4gICAgcmV0dXJuIEUoKCkgPT4ge1xuICAgICAgaWYgKCFkaXNhYmxlZC52YWx1ZSkge1xuICAgICAgICByZXR1cm4gcmVnaXN0ZXJUYWJJbmRlbnRhdGlvbihlZGl0b3IsIG1heEluZGVudCwgJGNhbkluZGVudCk7XG4gICAgICB9XG4gICAgfSk7XG4gIH1cbn0pO1xuXG5leHBvcnQgeyAkY3JlYXRlSG9yaXpvbnRhbFJ1bGVOb2RlLCAkaXNEZWNvcmF0b3JUZXh0Tm9kZSwgJGlzSG9yaXpvbnRhbFJ1bGVOb2RlLCBBdXRvRm9jdXNFeHRlbnNpb24sIENsZWFyRWRpdG9yRXh0ZW5zaW9uLCBEZWNvcmF0b3JUZXh0RXh0ZW5zaW9uLCBEZWNvcmF0b3JUZXh0Tm9kZSwgRWRpdG9yU3RhdGVFeHRlbnNpb24sIEhvcml6b250YWxSdWxlRXh0ZW5zaW9uLCBIb3Jpem9udGFsUnVsZU5vZGUsIElOU0VSVF9IT1JJWk9OVEFMX1JVTEVfQ09NTUFORCwgSW5pdGlhbFN0YXRlRXh0ZW5zaW9uLCBMZXhpY2FsQnVpbGRlciwgTm9kZVNlbGVjdGlvbkV4dGVuc2lvbiwgVGFiSW5kZW50YXRpb25FeHRlbnNpb24sIGFwcGx5Rm9ybWF0RnJvbVN0eWxlLCBhcHBseUZvcm1hdFRvRG9tLCBvIGFzIGJhdGNoLCBidWlsZEVkaXRvckZyb21FeHRlbnNpb25zLCB3IGFzIGNvbXB1dGVkLCBFIGFzIGVmZmVjdCwgZ2V0RXh0ZW5zaW9uRGVwZW5kZW5jeUZyb21FZGl0b3IsIGdldEtub3duVHlwZXNBbmROb2RlcywgZ2V0UGVlckRlcGVuZGVuY3lGcm9tRWRpdG9yLCBnZXRQZWVyRGVwZW5kZW5jeUZyb21FZGl0b3JPclRocm93LCBuYW1lZFNpZ25hbHMsIHJlZ2lzdGVyQ2xlYXJFZGl0b3IsIHJlZ2lzdGVyVGFiSW5kZW50YXRpb24sIGQgYXMgc2lnbmFsLCBoIGFzIHVudHJhY2tlZCwgd2F0Y2hlZFNpZ25hbCB9O1xuIl0sIm5hbWVzIjpbXSwiaWdub3JlTGlzdCI6WzBdLCJzb3VyY2VSb290IjoiIn0=\n//# sourceURL=webpack-internal:///(rsc)/./node_modules/.pnpm/@lexical+extension@0.41.0/node_modules/@lexical/extension/LexicalExtension.dev.mjs\n");
/***/ })
};
;