@openmrs/esm-app-shell 11.0.1-pre.5799 → 11.0.1-pre.5825

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -831,7 +831,7 @@ eval("{__webpack_require__.r(__webpack_exports__);\n__webpack_require__.d(__webp
831
831
  },
832
832
  "../../framework/esm-styleguide/dist/workspaces2/active-workspace-window.component.js"(__unused_rspack_module, __webpack_exports__, __webpack_require__) {
833
833
  "use strict";
834
- eval("{__webpack_require__.r(__webpack_exports__);\n__webpack_require__.d(__webpack_exports__, {\n \"default\": () => (__rspack_default_export)\n});\n/* import */ var react_jsx_runtime__rspack_import_0 = __webpack_require__(\"../../../node_modules/react/jsx-runtime.js\");\n/* import */ var react__rspack_import_1 = __webpack_require__(\"webpack/sharing/consume/default/react/react\");\n/* import */ var react__rspack_import_1_default = /*#__PURE__*/__webpack_require__.n(react__rspack_import_1);\n/* import */ var classnames__rspack_import_2 = __webpack_require__(\"../../../node_modules/classnames/index.js\");\n/* import */ var classnames__rspack_import_2_default = /*#__PURE__*/__webpack_require__.n(classnames__rspack_import_2);\n/* import */ var single_spa_react_parcel__rspack_import_3 = __webpack_require__(\"../../../node_modules/single-spa-react/lib/esm/parcel.js\");\n/* import */ var _carbon_react__rspack_import_4 = __webpack_require__(\"webpack/sharing/consume/default/@carbon/react/@carbon/react\");\n/* import */ var _carbon_react__rspack_import_4_default = /*#__PURE__*/__webpack_require__.n(_carbon_react__rspack_import_4);\n/* import */ var _carbon_react_icons__rspack_import_12 = __webpack_require__(\"../../../node_modules/@carbon/icons-react/es/generated/bucket-11.js\");\n/* import */ var _carbon_react_icons__rspack_import_13 = __webpack_require__(\"../../../node_modules/@carbon/icons-react/es/generated/bucket-6.js\");\n/* import */ var _openmrs_esm_extensions__rspack_import_5 = __webpack_require__(\"../../framework/esm-extensions/dist/index.js\");\n/* import */ var _openmrs_esm_react_utils__rspack_import_6 = __webpack_require__(\"../../framework/esm-react-utils/dist/index.js\");\n/* import */ var _openmrs_esm_routes__rspack_import_11 = __webpack_require__(\"../../framework/esm-routes/dist/loaders/load-lifecycles.js\");\n/* import */ var _openmrs_esm_translations__rspack_import_7 = __webpack_require__(\"../../framework/esm-translations/dist/index.js\");\n/* import */ var _icons_index_js__rspack_import_8 = __webpack_require__(\"../../framework/esm-styleguide/dist/icons/index.js\");\n/* import */ var _workspace2_js__rspack_import_9 = __webpack_require__(\"../../framework/esm-styleguide/dist/workspaces2/workspace2.js\");\n/* import */ var _workspace2_module_scss__rspack_import_10 = __webpack_require__(\"../../framework/esm-styleguide/dist/workspaces2/workspace2.module.scss\");\n\n\n\n\n\n\n\n\n\n\n\n\n\n// module-level so the store subscription's snapshot getter stays stable across renders\nconst selectRegisteredWorkspacesByName = (state)=>state.registeredWorkspacesByName;\n/**\n * Renders an opened workspace window. `actions` determines which store the window's workspaces\n * navigate within: the global workspace window system, or an `<ExportedWorkspace>`'s local store.\n */ const ActiveWorkspaceWindow = ({ openedWindow, groupProps, actions, renderChrome, showActionMenu })=>{\n const { openedWorkspaces } = openedWindow;\n // Keyed by opened workspace uuid rather than stack index. The lifecycles load\n // asynchronously, so when the stack changes (a workspace at some position is\n // replaced by another, for example closing a child workspace and immediately\n // opening a different one), an index-based lookup can hand the new workspace\n // the previous workspace's component until the reload resolves. The parcel\n // mounts whatever config it first receives, so the wrong component would then\n // render with the new workspace's props.\n const [lifeCyclesByUuid, setLifeCyclesByUuid] = (0,react__rspack_import_1.useState)({});\n // Reactive so the effect retries when a workspace registers after mount.\n const registeredWorkspacesByName = (0,_openmrs_esm_react_utils__rspack_import_6.useStore)(_openmrs_esm_extensions__rspack_import_5.workspace2Store, selectRegisteredWorkspacesByName);\n (0,react__rspack_import_1.useEffect)(()=>{\n let cancelled = false;\n Promise.all(openedWorkspaces.map(async (openedWorkspace)=>{\n const workspaceDef = registeredWorkspacesByName[openedWorkspace.workspaceName];\n if (!workspaceDef) {\n return null;\n }\n const { moduleName, component } = workspaceDef;\n return [\n openedWorkspace.uuid,\n await (0,_openmrs_esm_routes__rspack_import_11.loadLifeCycles)(moduleName, component)\n ];\n })).then((entries)=>{\n if (!cancelled) {\n setLifeCyclesByUuid(Object.fromEntries(entries.filter((entry)=>entry != null)));\n }\n });\n return ()=>{\n cancelled = true;\n };\n }, [\n openedWorkspaces,\n registeredWorkspacesByName\n ]);\n return /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(react_jsx_runtime__rspack_import_0.Fragment, {\n children: openedWorkspaces.map((openedWorkspace, i)=>/*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(ActiveWorkspace, {\n openedWorkspace: openedWorkspace,\n openedWindow: openedWindow,\n groupProps: groupProps,\n actions: actions,\n renderChrome: renderChrome,\n lifeCycle: lifeCyclesByUuid[openedWorkspace.uuid],\n isRootWorkspace: i === 0,\n isLeafWorkspace: i === openedWorkspaces.length - 1,\n showActionMenu: showActionMenu\n }, openedWorkspace.uuid))\n });\n};\nconst mountParcel = (0,_openmrs_esm_extensions__rspack_import_5.createParcelMounter)();\nconst ActiveWorkspace = ({ lifeCycle, openedWorkspace, openedWindow, groupProps, actions, renderChrome, isRootWorkspace, isLeafWorkspace, showActionMenu })=>{\n const props = (0,react__rspack_import_1.useMemo)(()=>openedWorkspace && {\n closeWorkspace: async (options = {})=>{\n const { closeWindow = false, discardUnsavedChanges = false } = options;\n if (closeWindow) {\n const okToCloseWorkspaces = discardUnsavedChanges || await actions.promptForClosingWorkspaces();\n if (okToCloseWorkspaces) {\n actions.closeWorkspace(openedWindow.openedWorkspaces[0].workspaceName);\n return true;\n }\n return false;\n } else {\n const okToCloseWorkspaces = discardUnsavedChanges || await actions.promptForClosingWorkspaces(openedWorkspace.workspaceName);\n if (okToCloseWorkspaces) {\n actions.closeWorkspace(openedWorkspace.workspaceName);\n return true;\n }\n return false;\n }\n },\n launchChildWorkspace: async (childWorkspaceName, childWorkspaceProps)=>{\n const parentWorkspaceName = openedWorkspace.workspaceName;\n const { openedWorkspaces } = openedWindow;\n const parentIndex = openedWorkspaces.findIndex((w)=>w.workspaceName === parentWorkspaceName);\n if (parentIndex === -1) {\n return;\n }\n const isLeaf = parentIndex === openedWorkspaces.length - 1;\n if (!isLeaf) {\n // There are workspaces above the parent that will be closed.\n // Prompt if any of them have unsaved changes.\n const workspacesAboveParent = openedWorkspaces.slice(parentIndex + 1);\n if (workspacesAboveParent.some((w)=>w.hasUnsavedChanges)) {\n const okToClose = await actions.promptForClosingWorkspaces(openedWorkspaces[parentIndex + 1].workspaceName);\n if (!okToClose) {\n return;\n }\n }\n }\n actions.openChildWorkspace(parentWorkspaceName, childWorkspaceName, childWorkspaceProps || {});\n },\n setWorkspaceTitle: (title)=>actions.setWorkspaceTitle(openedWorkspace.uuid, title),\n setHasUnsavedChanges: (hasUnsavedChanges)=>actions.setHasUnsavedChanges(openedWorkspace.uuid, hasUnsavedChanges),\n workspaceName: openedWorkspace.workspaceName,\n workspaceProps: openedWorkspace.props,\n windowProps: openedWindow.props,\n groupProps,\n workspaceMeta: _openmrs_esm_extensions__rspack_import_5.workspace2Store.getState().registeredWorkspacesByName[openedWorkspace.workspaceName]?.meta ?? {},\n isRootWorkspace,\n isLeafWorkspace,\n windowName: openedWindow.windowName,\n showActionMenu\n }, [\n openedWorkspace,\n openedWindow,\n groupProps,\n actions,\n isRootWorkspace,\n isLeafWorkspace,\n showActionMenu\n ]);\n // In bare mode (<ExportedWorkspace>) there is no chrome to stack workspaces, so every non-leaf\n // workspace is hidden (not unmounted, so it keeps its state) and the leaf covers them. In chrome\n // mode the absolute-positioned WorkspaceChrome containers handle stacking, so this class is not\n // applied there.\n const hideBehindLeaf = !renderChrome && !isLeafWorkspace;\n const content = (0,react__rspack_import_1.useMemo)(()=>lifeCycle ? /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(single_spa_react_parcel__rspack_import_3[\"default\"], {\n config: lifeCycle,\n mountParcel: mountParcel,\n wrapWith: \"div\",\n wrapClassName: classnames__rspack_import_2_default()(_workspace2_module_scss__rspack_import_10[\"default\"].workspaceContent, {\n [_workspace2_module_scss__rspack_import_10[\"default\"].hiddenExtraWorkspace]: hideBehindLeaf\n }),\n ...props\n }, openedWorkspace.workspaceName) : null, [\n lifeCycle,\n openedWorkspace.workspaceName,\n props,\n hideBehindLeaf\n ]);\n if (!renderChrome) {\n return content ?? /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_carbon_react__rspack_import_4.InlineLoading, {\n className: classnames__rspack_import_2_default()(_workspace2_module_scss__rspack_import_10[\"default\"].loader, {\n [_workspace2_module_scss__rspack_import_10[\"default\"].hiddenExtraWorkspace]: hideBehindLeaf\n }),\n description: `${(0,_openmrs_esm_translations__rspack_import_7.getCoreTranslation)('loading')}`\n });\n }\n // The node removed from the workspace grid on close must generate a box. WebKit before Safari 26.2\n // doesn't relayout the grid when the removed node is the `display: contents` outer container, so the\n // closed window keeps taking up space. https://bugs.webkit.org/show_bug.cgi?id=299258\n return /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(\"div\", {\n children: /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(WorkspaceChrome, {\n openedWorkspace: openedWorkspace,\n openedWindow: openedWindow,\n isRootWorkspace: isRootWorkspace,\n showActionMenu: showActionMenu,\n closeWindow: ()=>props.closeWorkspace({\n closeWindow: true\n }),\n children: content\n })\n });\n};\n/**\n * Renders the containers, title bar and window buttons around a workspace in the global workspace\n * window system.\n */ const WorkspaceChrome = ({ openedWorkspace, openedWindow, isRootWorkspace, showActionMenu, closeWindow, children })=>{\n const layout = (0,_openmrs_esm_react_utils__rspack_import_6.useLayoutType)();\n const { openedGroup, openedWindows, registeredWindowsByName, registeredWorkspacesByName, registeredGroupsByName, isMostRecentlyOpenedWindowHidden, setWindowMaximized, hideWindow } = (0,_workspace2_js__rspack_import_9.useWorkspace2Store)();\n const windowName = openedWindow.windowName;\n const { maximized } = openedWindow;\n const title = openedWorkspace.title ?? '';\n const windowDef = registeredWindowsByName[windowName];\n const width = (0,_workspace2_js__rspack_import_9.getOpenedWindowWidth)(openedWindow, registeredWorkspacesByName, registeredWindowsByName);\n const icon = windowDef?.icon;\n const canMaximize = windowDef?.canMaximize;\n const canCloseGroup = openedGroup ? registeredGroupsByName[openedGroup.groupName]?.persistence === 'closable' : false;\n const canHide = !!icon && !canCloseGroup;\n const openedWindowIndex = openedWindows.findIndex((w)=>w.windowName === windowName);\n const isWindowHidden = openedWindowIndex < openedWindows.length - 1 || isMostRecentlyOpenedWindowHidden;\n const isActionMenuOpened = Object.values(registeredWindowsByName).some((window)=>window.group === openedGroup?.groupName && window.icon !== undefined);\n return /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsxs)(\"div\", {\n className: classnames__rspack_import_2_default()(_workspace2_module_scss__rspack_import_10[\"default\"].workspaceOuterContainer, {\n [_workspace2_module_scss__rspack_import_10[\"default\"].narrowWorkspace]: width === 'narrow',\n [_workspace2_module_scss__rspack_import_10[\"default\"].widerWorkspace]: width === 'wider',\n [_workspace2_module_scss__rspack_import_10[\"default\"].extraWideWorkspace]: width === 'extra-wide',\n [_workspace2_module_scss__rspack_import_10[\"default\"].isActionMenuOpened]: isActionMenuOpened\n }),\n children: [\n /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(\"div\", {\n className: classnames__rspack_import_2_default()(_workspace2_module_scss__rspack_import_10[\"default\"].workspaceSpacer, {\n [_workspace2_module_scss__rspack_import_10[\"default\"].hidden]: isWindowHidden\n })\n }),\n /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(\"div\", {\n className: classnames__rspack_import_2_default()(_workspace2_module_scss__rspack_import_10[\"default\"].workspaceMiddleContainer, {\n [_workspace2_module_scss__rspack_import_10[\"default\"].maximized]: maximized,\n [_workspace2_module_scss__rspack_import_10[\"default\"].hidden]: isWindowHidden,\n [_workspace2_module_scss__rspack_import_10[\"default\"].isRootWorkspace]: isRootWorkspace,\n [_workspace2_module_scss__rspack_import_10[\"default\"].showActionMenu]: showActionMenu\n }),\n children: /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(\"div\", {\n className: classnames__rspack_import_2_default()(_workspace2_module_scss__rspack_import_10[\"default\"].workspaceInnerContainer, {\n [_workspace2_module_scss__rspack_import_10[\"default\"].maximized]: maximized,\n [_workspace2_module_scss__rspack_import_10[\"default\"].hidden]: isWindowHidden,\n [_workspace2_module_scss__rspack_import_10[\"default\"].isRootWorkspace]: isRootWorkspace\n }),\n children: children ? /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsxs)(react_jsx_runtime__rspack_import_0.Fragment, {\n children: [\n /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsxs)(_carbon_react__rspack_import_4.Header, {\n \"aria-label\": (0,_openmrs_esm_translations__rspack_import_7.getCoreTranslation)('workspaceHeader'),\n className: _workspace2_module_scss__rspack_import_10[\"default\"].header,\n children: [\n /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_carbon_react__rspack_import_4.HeaderName, {\n prefix: \"\",\n children: title\n }),\n /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(\"div\", {\n className: _workspace2_module_scss__rspack_import_10[\"default\"].overlayHeaderSpacer\n }),\n /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_carbon_react__rspack_import_4.HeaderGlobalBar, {\n className: _workspace2_module_scss__rspack_import_10[\"default\"].headerButtons,\n children: (0,_openmrs_esm_react_utils__rspack_import_6.isDesktop)(layout) ? /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsxs)(react_jsx_runtime__rspack_import_0.Fragment, {\n children: [\n (canMaximize || maximized) && /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_carbon_react__rspack_import_4.HeaderGlobalAction, {\n \"aria-label\": maximized ? (0,_openmrs_esm_translations__rspack_import_7.getCoreTranslation)('minimize') : (0,_openmrs_esm_translations__rspack_import_7.getCoreTranslation)('maximize'),\n onClick: ()=>setWindowMaximized(windowName, !maximized),\n children: maximized ? /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_carbon_react_icons__rspack_import_12.Minimize, {}) : /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_carbon_react_icons__rspack_import_12.Maximize, {})\n }),\n canHide && /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_carbon_react__rspack_import_4.HeaderGlobalAction, {\n \"aria-label\": (0,_openmrs_esm_translations__rspack_import_7.getCoreTranslation)('hide'),\n onClick: ()=>hideWindow(),\n children: /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_icons_index_js__rspack_import_8.ArrowRightIcon, {})\n }),\n !canCloseGroup && /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_carbon_react__rspack_import_4.HeaderGlobalAction, {\n \"aria-label\": (0,_openmrs_esm_translations__rspack_import_7.getCoreTranslation)('close'),\n onClick: closeWindow,\n children: /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_icons_index_js__rspack_import_8.CloseIcon, {})\n })\n ]\n }) : /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsxs)(react_jsx_runtime__rspack_import_0.Fragment, {\n children: [\n canHide && /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_carbon_react__rspack_import_4.HeaderGlobalAction, {\n \"aria-label\": (0,_openmrs_esm_translations__rspack_import_7.getCoreTranslation)('hide'),\n onClick: ()=>hideWindow(),\n children: /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_carbon_react_icons__rspack_import_13.DownToBottom, {})\n }),\n /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_carbon_react__rspack_import_4.HeaderGlobalAction, {\n \"aria-label\": (0,_openmrs_esm_translations__rspack_import_7.getCoreTranslation)('close'),\n onClick: ()=>{\n if (canCloseGroup) {\n void (0,_workspace2_js__rspack_import_9.closeWorkspaceGroup2)();\n } else {\n closeWindow();\n }\n },\n children: /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_icons_index_js__rspack_import_8.CloseIcon, {})\n })\n ]\n })\n })\n ]\n }),\n children\n ]\n }) : /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_carbon_react__rspack_import_4.InlineLoading, {\n className: _workspace2_module_scss__rspack_import_10[\"default\"].loader,\n description: `${(0,_openmrs_esm_translations__rspack_import_7.getCoreTranslation)('loading')} ...`\n })\n })\n })\n ]\n });\n};\n/* export default */ const __rspack_default_export = (ActiveWorkspaceWindow);\n\n//# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiYnVpbHRpbjpzd2MtbG9hZGVyPz9ydWxlU2V0WzFdLnJ1bGVzWzVdLnVzZVswXSEvaG9tZS9ydW5uZXIvd29yay9vcGVubXJzLWVzbS1jb3JlL29wZW5tcnMtZXNtLWNvcmUvcGFja2FnZXMvZnJhbWV3b3JrL2VzbS1zdHlsZWd1aWRlL2Rpc3Qvd29ya3NwYWNlczIvYWN0aXZlLXdvcmtzcGFjZS13aW5kb3cuY29tcG9uZW50LmpzIiwic291cmNlcyI6WyJ3ZWJwYWNrOi8vQG9wZW5tcnMvZXNtLWFwcC1zaGVsbC8uLi8uLi9mcmFtZXdvcmsvZXNtLXN0eWxlZ3VpZGUvZGlzdC93b3Jrc3BhY2VzMi9hY3RpdmUtd29ya3NwYWNlLXdpbmRvdy5jb21wb25lbnQuanM/ZGRmOCJdLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBqc3ggYXMgX2pzeCwganN4cyBhcyBfanN4cywgRnJhZ21lbnQgYXMgX0ZyYWdtZW50IH0gZnJvbSBcInJlYWN0L2pzeC1ydW50aW1lXCI7XG5pbXBvcnQgUmVhY3QsIHsgdXNlRWZmZWN0LCB1c2VNZW1vLCB1c2VTdGF0ZSB9IGZyb20gXCJyZWFjdFwiO1xuaW1wb3J0IGNsYXNzTmFtZXMgZnJvbSBcImNsYXNzbmFtZXNcIjtcbmltcG9ydCBQYXJjZWwgZnJvbSBcInNpbmdsZS1zcGEtcmVhY3QvcGFyY2VsXCI7XG5pbXBvcnQgeyBIZWFkZXIsIEhlYWRlckdsb2JhbEFjdGlvbiwgSGVhZGVyR2xvYmFsQmFyLCBIZWFkZXJOYW1lLCBJbmxpbmVMb2FkaW5nIH0gZnJvbSBcIkBjYXJib24vcmVhY3RcIjtcbmltcG9ydCB7IERvd25Ub0JvdHRvbSwgTWF4aW1pemUsIE1pbmltaXplIH0gZnJvbSBcIkBjYXJib24vcmVhY3QvaWNvbnNcIjtcbmltcG9ydCB7IGNyZWF0ZVBhcmNlbE1vdW50ZXIsIHdvcmtzcGFjZTJTdG9yZSB9IGZyb20gXCJAb3Blbm1ycy9lc20tZXh0ZW5zaW9uc1wiO1xuaW1wb3J0IHsgaXNEZXNrdG9wLCB1c2VMYXlvdXRUeXBlLCB1c2VTdG9yZSB9IGZyb20gXCJAb3Blbm1ycy9lc20tcmVhY3QtdXRpbHNcIjtcbmltcG9ydCB7IGxvYWRMaWZlQ3ljbGVzIH0gZnJvbSBcIkBvcGVubXJzL2VzbS1yb3V0ZXNcIjtcbmltcG9ydCB7IGdldENvcmVUcmFuc2xhdGlvbiB9IGZyb20gXCJAb3Blbm1ycy9lc20tdHJhbnNsYXRpb25zXCI7XG5pbXBvcnQgeyBBcnJvd1JpZ2h0SWNvbiwgQ2xvc2VJY29uIH0gZnJvbSBcIi4uL2ljb25zL2luZGV4LmpzXCI7XG5pbXBvcnQgeyBjbG9zZVdvcmtzcGFjZUdyb3VwMiwgZ2V0T3BlbmVkV2luZG93V2lkdGgsIHVzZVdvcmtzcGFjZTJTdG9yZSB9IGZyb20gXCIuL3dvcmtzcGFjZTIuanNcIjtcbmltcG9ydCBzdHlsZXMgZnJvbSBcIi4vd29ya3NwYWNlMi5tb2R1bGUuc2Nzc1wiO1xuLy8gbW9kdWxlLWxldmVsIHNvIHRoZSBzdG9yZSBzdWJzY3JpcHRpb24ncyBzbmFwc2hvdCBnZXR0ZXIgc3RheXMgc3RhYmxlIGFjcm9zcyByZW5kZXJzXG5jb25zdCBzZWxlY3RSZWdpc3RlcmVkV29ya3NwYWNlc0J5TmFtZSA9IChzdGF0ZSk9PnN0YXRlLnJlZ2lzdGVyZWRXb3Jrc3BhY2VzQnlOYW1lO1xuLyoqXG4gKiBSZW5kZXJzIGFuIG9wZW5lZCB3b3Jrc3BhY2Ugd2luZG93LiBgYWN0aW9uc2AgZGV0ZXJtaW5lcyB3aGljaCBzdG9yZSB0aGUgd2luZG93J3Mgd29ya3NwYWNlc1xuICogbmF2aWdhdGUgd2l0aGluOiB0aGUgZ2xvYmFsIHdvcmtzcGFjZSB3aW5kb3cgc3lzdGVtLCBvciBhbiBgPEV4cG9ydGVkV29ya3NwYWNlPmAncyBsb2NhbCBzdG9yZS5cbiAqLyBjb25zdCBBY3RpdmVXb3Jrc3BhY2VXaW5kb3cgPSAoeyBvcGVuZWRXaW5kb3csIGdyb3VwUHJvcHMsIGFjdGlvbnMsIHJlbmRlckNocm9tZSwgc2hvd0FjdGlvbk1lbnUgfSk9PntcbiAgICBjb25zdCB7IG9wZW5lZFdvcmtzcGFjZXMgfSA9IG9wZW5lZFdpbmRvdztcbiAgICAvLyBLZXllZCBieSBvcGVuZWQgd29ya3NwYWNlIHV1aWQgcmF0aGVyIHRoYW4gc3RhY2sgaW5kZXguIFRoZSBsaWZlY3ljbGVzIGxvYWRcbiAgICAvLyBhc3luY2hyb25vdXNseSwgc28gd2hlbiB0aGUgc3RhY2sgY2hhbmdlcyAoYSB3b3Jrc3BhY2UgYXQgc29tZSBwb3NpdGlvbiBpc1xuICAgIC8vIHJlcGxhY2VkIGJ5IGFub3RoZXIsIGZvciBleGFtcGxlIGNsb3NpbmcgYSBjaGlsZCB3b3Jrc3BhY2UgYW5kIGltbWVkaWF0ZWx5XG4gICAgLy8gb3BlbmluZyBhIGRpZmZlcmVudCBvbmUpLCBhbiBpbmRleC1iYXNlZCBsb29rdXAgY2FuIGhhbmQgdGhlIG5ldyB3b3Jrc3BhY2VcbiAgICAvLyB0aGUgcHJldmlvdXMgd29ya3NwYWNlJ3MgY29tcG9uZW50IHVudGlsIHRoZSByZWxvYWQgcmVzb2x2ZXMuIFRoZSBwYXJjZWxcbiAgICAvLyBtb3VudHMgd2hhdGV2ZXIgY29uZmlnIGl0IGZpcnN0IHJlY2VpdmVzLCBzbyB0aGUgd3JvbmcgY29tcG9uZW50IHdvdWxkIHRoZW5cbiAgICAvLyByZW5kZXIgd2l0aCB0aGUgbmV3IHdvcmtzcGFjZSdzIHByb3BzLlxuICAgIGNvbnN0IFtsaWZlQ3ljbGVzQnlVdWlkLCBzZXRMaWZlQ3ljbGVzQnlVdWlkXSA9IHVzZVN0YXRlKHt9KTtcbiAgICAvLyBSZWFjdGl2ZSBzbyB0aGUgZWZmZWN0IHJldHJpZXMgd2hlbiBhIHdvcmtzcGFjZSByZWdpc3RlcnMgYWZ0ZXIgbW91bnQuXG4gICAgY29uc3QgcmVnaXN0ZXJlZFdvcmtzcGFjZXNCeU5hbWUgPSB1c2VTdG9yZSh3b3Jrc3BhY2UyU3RvcmUsIHNlbGVjdFJlZ2lzdGVyZWRXb3Jrc3BhY2VzQnlOYW1lKTtcbiAgICB1c2VFZmZlY3QoKCk9PntcbiAgICAgICAgbGV0IGNhbmNlbGxlZCA9IGZhbHNlO1xuICAgICAgICBQcm9taXNlLmFsbChvcGVuZWRXb3Jrc3BhY2VzLm1hcChhc3luYyAob3BlbmVkV29ya3NwYWNlKT0+e1xuICAgICAgICAgICAgY29uc3Qgd29ya3NwYWNlRGVmID0gcmVnaXN0ZXJlZFdvcmtzcGFjZXNCeU5hbWVbb3BlbmVkV29ya3NwYWNlLndvcmtzcGFjZU5hbWVdO1xuICAgICAgICAgICAgaWYgKCF3b3Jrc3BhY2VEZWYpIHtcbiAgICAgICAgICAgICAgICByZXR1cm4gbnVsbDtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICAgIGNvbnN0IHsgbW9kdWxlTmFtZSwgY29tcG9uZW50IH0gPSB3b3Jrc3BhY2VEZWY7XG4gICAgICAgICAgICByZXR1cm4gW1xuICAgICAgICAgICAgICAgIG9wZW5lZFdvcmtzcGFjZS51dWlkLFxuICAgICAgICAgICAgICAgIGF3YWl0IGxvYWRMaWZlQ3ljbGVzKG1vZHVsZU5hbWUsIGNvbXBvbmVudClcbiAgICAgICAgICAgIF07XG4gICAgICAgIH0pKS50aGVuKChlbnRyaWVzKT0+e1xuICAgICAgICAgICAgaWYgKCFjYW5jZWxsZWQpIHtcbiAgICAgICAgICAgICAgICBzZXRMaWZlQ3ljbGVzQnlVdWlkKE9iamVjdC5mcm9tRW50cmllcyhlbnRyaWVzLmZpbHRlcigoZW50cnkpPT5lbnRyeSAhPSBudWxsKSkpO1xuICAgICAgICAgICAgfVxuICAgICAgICB9KTtcbiAgICAgICAgcmV0dXJuICgpPT57XG4gICAgICAgICAgICBjYW5jZWxsZWQgPSB0cnVlO1xuICAgICAgICB9O1xuICAgIH0sIFtcbiAgICAgICAgb3BlbmVkV29ya3NwYWNlcyxcbiAgICAgICAgcmVnaXN0ZXJlZFdvcmtzcGFjZXNCeU5hbWVcbiAgICBdKTtcbiAgICByZXR1cm4gLyojX19QVVJFX18qLyBfanN4KF9GcmFnbWVudCwge1xuICAgICAgICBjaGlsZHJlbjogb3BlbmVkV29ya3NwYWNlcy5tYXAoKG9wZW5lZFdvcmtzcGFjZSwgaSk9Pi8qI19fUFVSRV9fKi8gX2pzeChBY3RpdmVXb3Jrc3BhY2UsIHtcbiAgICAgICAgICAgICAgICBvcGVuZWRXb3Jrc3BhY2U6IG9wZW5lZFdvcmtzcGFjZSxcbiAgICAgICAgICAgICAgICBvcGVuZWRXaW5kb3c6IG9wZW5lZFdpbmRvdyxcbiAgICAgICAgICAgICAgICBncm91cFByb3BzOiBncm91cFByb3BzLFxuICAgICAgICAgICAgICAgIGFjdGlvbnM6IGFjdGlvbnMsXG4gICAgICAgICAgICAgICAgcmVuZGVyQ2hyb21lOiByZW5kZXJDaHJvbWUsXG4gICAgICAgICAgICAgICAgbGlmZUN5Y2xlOiBsaWZlQ3ljbGVzQnlVdWlkW29wZW5lZFdvcmtzcGFjZS51dWlkXSxcbiAgICAgICAgICAgICAgICBpc1Jvb3RXb3Jrc3BhY2U6IGkgPT09IDAsXG4gICAgICAgICAgICAgICAgaXNMZWFmV29ya3NwYWNlOiBpID09PSBvcGVuZWRXb3Jrc3BhY2VzLmxlbmd0aCAtIDEsXG4gICAgICAgICAgICAgICAgc2hvd0FjdGlvbk1lbnU6IHNob3dBY3Rpb25NZW51XG4gICAgICAgICAgICB9LCBvcGVuZWRXb3Jrc3BhY2UudXVpZCkpXG4gICAgfSk7XG59O1xuY29uc3QgbW91bnRQYXJjZWwgPSBjcmVhdGVQYXJjZWxNb3VudGVyKCk7XG5jb25zdCBBY3RpdmVXb3Jrc3BhY2UgPSAoeyBsaWZlQ3ljbGUsIG9wZW5lZFdvcmtzcGFjZSwgb3BlbmVkV2luZG93LCBncm91cFByb3BzLCBhY3Rpb25zLCByZW5kZXJDaHJvbWUsIGlzUm9vdFdvcmtzcGFjZSwgaXNMZWFmV29ya3NwYWNlLCBzaG93QWN0aW9uTWVudSB9KT0+e1xuICAgIGNvbnN0IHByb3BzID0gdXNlTWVtbygoKT0+b3BlbmVkV29ya3NwYWNlICYmIHtcbiAgICAgICAgICAgIGNsb3NlV29ya3NwYWNlOiBhc3luYyAob3B0aW9ucyA9IHt9KT0+e1xuICAgICAgICAgICAgICAgIGNvbnN0IHsgY2xvc2VXaW5kb3cgPSBmYWxzZSwgZGlzY2FyZFVuc2F2ZWRDaGFuZ2VzID0gZmFsc2UgfSA9IG9wdGlvbnM7XG4gICAgICAgICAgICAgICAgaWYgKGNsb3NlV2luZG93KSB7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IG9rVG9DbG9zZVdvcmtzcGFjZXMgPSBkaXNjYXJkVW5zYXZlZENoYW5nZXMgfHwgYXdhaXQgYWN0aW9ucy5wcm9tcHRGb3JDbG9zaW5nV29ya3NwYWNlcygpO1xuICAgICAgICAgICAgICAgICAgICBpZiAob2tUb0Nsb3NlV29ya3NwYWNlcykge1xuICAgICAgICAgICAgICAgICAgICAgICAgYWN0aW9ucy5jbG9zZVdvcmtzcGFjZShvcGVuZWRXaW5kb3cub3BlbmVkV29ya3NwYWNlc1swXS53b3Jrc3BhY2VOYW1lKTtcbiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiB0cnVlO1xuICAgICAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgICAgIHJldHVybiBmYWxzZTtcbiAgICAgICAgICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgICAgICAgICBjb25zdCBva1RvQ2xvc2VXb3Jrc3BhY2VzID0gZGlzY2FyZFVuc2F2ZWRDaGFuZ2VzIHx8IGF3YWl0IGFjdGlvbnMucHJvbXB0Rm9yQ2xvc2luZ1dvcmtzcGFjZXMob3BlbmVkV29ya3NwYWNlLndvcmtzcGFjZU5hbWUpO1xuICAgICAgICAgICAgICAgICAgICBpZiAob2tUb0Nsb3NlV29ya3NwYWNlcykge1xuICAgICAgICAgICAgICAgICAgICAgICAgYWN0aW9ucy5jbG9zZVdvcmtzcGFjZShvcGVuZWRXb3Jrc3BhY2Uud29ya3NwYWNlTmFtZSk7XG4gICAgICAgICAgICAgICAgICAgICAgICByZXR1cm4gdHJ1ZTtcbiAgICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgICAgICByZXR1cm4gZmFsc2U7XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgfSxcbiAgICAgICAgICAgIGxhdW5jaENoaWxkV29ya3NwYWNlOiBhc3luYyAoY2hpbGRXb3Jrc3BhY2VOYW1lLCBjaGlsZFdvcmtzcGFjZVByb3BzKT0+e1xuICAgICAgICAgICAgICAgIGNvbnN0IHBhcmVudFdvcmtzcGFjZU5hbWUgPSBvcGVuZWRXb3Jrc3BhY2Uud29ya3NwYWNlTmFtZTtcbiAgICAgICAgICAgICAgICBjb25zdCB7IG9wZW5lZFdvcmtzcGFjZXMgfSA9IG9wZW5lZFdpbmRvdztcbiAgICAgICAgICAgICAgICBjb25zdCBwYXJlbnRJbmRleCA9IG9wZW5lZFdvcmtzcGFjZXMuZmluZEluZGV4KCh3KT0+dy53b3Jrc3BhY2VOYW1lID09PSBwYXJlbnRXb3Jrc3BhY2VOYW1lKTtcbiAgICAgICAgICAgICAgICBpZiAocGFyZW50SW5kZXggPT09IC0xKSB7XG4gICAgICAgICAgICAgICAgICAgIHJldHVybjtcbiAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgY29uc3QgaXNMZWFmID0gcGFyZW50SW5kZXggPT09IG9wZW5lZFdvcmtzcGFjZXMubGVuZ3RoIC0gMTtcbiAgICAgICAgICAgICAgICBpZiAoIWlzTGVhZikge1xuICAgICAgICAgICAgICAgICAgICAvLyBUaGVyZSBhcmUgd29ya3NwYWNlcyBhYm92ZSB0aGUgcGFyZW50IHRoYXQgd2lsbCBiZSBjbG9zZWQuXG4gICAgICAgICAgICAgICAgICAgIC8vIFByb21wdCBpZiBhbnkgb2YgdGhlbSBoYXZlIHVuc2F2ZWQgY2hhbmdlcy5cbiAgICAgICAgICAgICAgICAgICAgY29uc3Qgd29ya3NwYWNlc0Fib3ZlUGFyZW50ID0gb3BlbmVkV29ya3NwYWNlcy5zbGljZShwYXJlbnRJbmRleCArIDEpO1xuICAgICAgICAgICAgICAgICAgICBpZiAod29ya3NwYWNlc0Fib3ZlUGFyZW50LnNvbWUoKHcpPT53Lmhhc1Vuc2F2ZWRDaGFuZ2VzKSkge1xuICAgICAgICAgICAgICAgICAgICAgICAgY29uc3Qgb2tUb0Nsb3NlID0gYXdhaXQgYWN0aW9ucy5wcm9tcHRGb3JDbG9zaW5nV29ya3NwYWNlcyhvcGVuZWRXb3Jrc3BhY2VzW3BhcmVudEluZGV4ICsgMV0ud29ya3NwYWNlTmFtZSk7XG4gICAgICAgICAgICAgICAgICAgICAgICBpZiAoIW9rVG9DbG9zZSkge1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybjtcbiAgICAgICAgICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICBhY3Rpb25zLm9wZW5DaGlsZFdvcmtzcGFjZShwYXJlbnRXb3Jrc3BhY2VOYW1lLCBjaGlsZFdvcmtzcGFjZU5hbWUsIGNoaWxkV29ya3NwYWNlUHJvcHMgfHwge30pO1xuICAgICAgICAgICAgfSxcbiAgICAgICAgICAgIHNldFdvcmtzcGFjZVRpdGxlOiAodGl0bGUpPT5hY3Rpb25zLnNldFdvcmtzcGFjZVRpdGxlKG9wZW5lZFdvcmtzcGFjZS51dWlkLCB0aXRsZSksXG4gICAgICAgICAgICBzZXRIYXNVbnNhdmVkQ2hhbmdlczogKGhhc1Vuc2F2ZWRDaGFuZ2VzKT0+YWN0aW9ucy5zZXRIYXNVbnNhdmVkQ2hhbmdlcyhvcGVuZWRXb3Jrc3BhY2UudXVpZCwgaGFzVW5zYXZlZENoYW5nZXMpLFxuICAgICAgICAgICAgd29ya3NwYWNlTmFtZTogb3BlbmVkV29ya3NwYWNlLndvcmtzcGFjZU5hbWUsXG4gICAgICAgICAgICB3b3Jrc3BhY2VQcm9wczogb3BlbmVkV29ya3NwYWNlLnByb3BzLFxuICAgICAgICAgICAgd2luZG93UHJvcHM6IG9wZW5lZFdpbmRvdy5wcm9wcyxcbiAgICAgICAgICAgIGdyb3VwUHJvcHMsXG4gICAgICAgICAgICB3b3Jrc3BhY2VNZXRhOiB3b3Jrc3BhY2UyU3RvcmUuZ2V0U3RhdGUoKS5yZWdpc3RlcmVkV29ya3NwYWNlc0J5TmFtZVtvcGVuZWRXb3Jrc3BhY2Uud29ya3NwYWNlTmFtZV0/Lm1ldGEgPz8ge30sXG4gICAgICAgICAgICBpc1Jvb3RXb3Jrc3BhY2UsXG4gICAgICAgICAgICBpc0xlYWZXb3Jrc3BhY2UsXG4gICAgICAgICAgICB3aW5kb3dOYW1lOiBvcGVuZWRXaW5kb3cud2luZG93TmFtZSxcbiAgICAgICAgICAgIHNob3dBY3Rpb25NZW51XG4gICAgICAgIH0sIFtcbiAgICAgICAgb3BlbmVkV29ya3NwYWNlLFxuICAgICAgICBvcGVuZWRXaW5kb3csXG4gICAgICAgIGdyb3VwUHJvcHMsXG4gICAgICAgIGFjdGlvbnMsXG4gICAgICAgIGlzUm9vdFdvcmtzcGFjZSxcbiAgICAgICAgaXNMZWFmV29ya3NwYWNlLFxuICAgICAgICBzaG93QWN0aW9uTWVudVxuICAgIF0pO1xuICAgIC8vIEluIGJhcmUgbW9kZSAoPEV4cG9ydGVkV29ya3NwYWNlPikgdGhlcmUgaXMgbm8gY2hyb21lIHRvIHN0YWNrIHdvcmtzcGFjZXMsIHNvIGV2ZXJ5IG5vbi1sZWFmXG4gICAgLy8gd29ya3NwYWNlIGlzIGhpZGRlbiAobm90IHVubW91bnRlZCwgc28gaXQga2VlcHMgaXRzIHN0YXRlKSBhbmQgdGhlIGxlYWYgY292ZXJzIHRoZW0uIEluIGNocm9tZVxuICAgIC8vIG1vZGUgdGhlIGFic29sdXRlLXBvc2l0aW9uZWQgV29ya3NwYWNlQ2hyb21lIGNvbnRhaW5lcnMgaGFuZGxlIHN0YWNraW5nLCBzbyB0aGlzIGNsYXNzIGlzIG5vdFxuICAgIC8vIGFwcGxpZWQgdGhlcmUuXG4gICAgY29uc3QgaGlkZUJlaGluZExlYWYgPSAhcmVuZGVyQ2hyb21lICYmICFpc0xlYWZXb3Jrc3BhY2U7XG4gICAgY29uc3QgY29udGVudCA9IHVzZU1lbW8oKCk9PmxpZmVDeWNsZSA/IC8qI19fUFVSRV9fKi8gX2pzeChQYXJjZWwsIHtcbiAgICAgICAgICAgIGNvbmZpZzogbGlmZUN5Y2xlLFxuICAgICAgICAgICAgbW91bnRQYXJjZWw6IG1vdW50UGFyY2VsLFxuICAgICAgICAgICAgd3JhcFdpdGg6IFwiZGl2XCIsXG4gICAgICAgICAgICB3cmFwQ2xhc3NOYW1lOiBjbGFzc05hbWVzKHN0eWxlcy53b3Jrc3BhY2VDb250ZW50LCB7XG4gICAgICAgICAgICAgICAgW3N0eWxlcy5oaWRkZW5FeHRyYVdvcmtzcGFjZV06IGhpZGVCZWhpbmRMZWFmXG4gICAgICAgICAgICB9KSxcbiAgICAgICAgICAgIC4uLnByb3BzXG4gICAgICAgIH0sIG9wZW5lZFdvcmtzcGFjZS53b3Jrc3BhY2VOYW1lKSA6IG51bGwsIFtcbiAgICAgICAgbGlmZUN5Y2xlLFxuICAgICAgICBvcGVuZWRXb3Jrc3BhY2Uud29ya3NwYWNlTmFtZSxcbiAgICAgICAgcHJvcHMsXG4gICAgICAgIGhpZGVCZWhpbmRMZWFmXG4gICAgXSk7XG4gICAgaWYgKCFyZW5kZXJDaHJvbWUpIHtcbiAgICAgICAgcmV0dXJuIGNvbnRlbnQgPz8gLyojX19QVVJFX18qLyBfanN4KElubGluZUxvYWRpbmcsIHtcbiAgICAgICAgICAgIGNsYXNzTmFtZTogY2xhc3NOYW1lcyhzdHlsZXMubG9hZGVyLCB7XG4gICAgICAgICAgICAgICAgW3N0eWxlcy5oaWRkZW5FeHRyYVdvcmtzcGFjZV06IGhpZGVCZWhpbmRMZWFmXG4gICAgICAgICAgICB9KSxcbiAgICAgICAgICAgIGRlc2NyaXB0aW9uOiBgJHtnZXRDb3JlVHJhbnNsYXRpb24oJ2xvYWRpbmcnKX1gXG4gICAgICAgIH0pO1xuICAgIH1cbiAgICAvLyBUaGUgbm9kZSByZW1vdmVkIGZyb20gdGhlIHdvcmtzcGFjZSBncmlkIG9uIGNsb3NlIG11c3QgZ2VuZXJhdGUgYSBib3guIFdlYktpdCBiZWZvcmUgU2FmYXJpIDI2LjJcbiAgICAvLyBkb2Vzbid0IHJlbGF5b3V0IHRoZSBncmlkIHdoZW4gdGhlIHJlbW92ZWQgbm9kZSBpcyB0aGUgYGRpc3BsYXk6IGNvbnRlbnRzYCBvdXRlciBjb250YWluZXIsIHNvIHRoZVxuICAgIC8vIGNsb3NlZCB3aW5kb3cga2VlcHMgdGFraW5nIHVwIHNwYWNlLiBodHRwczovL2J1Z3Mud2Via2l0Lm9yZy9zaG93X2J1Zy5jZ2k/aWQ9Mjk5MjU4XG4gICAgcmV0dXJuIC8qI19fUFVSRV9fKi8gX2pzeChcImRpdlwiLCB7XG4gICAgICAgIGNoaWxkcmVuOiAvKiNfX1BVUkVfXyovIF9qc3goV29ya3NwYWNlQ2hyb21lLCB7XG4gICAgICAgICAgICBvcGVuZWRXb3Jrc3BhY2U6IG9wZW5lZFdvcmtzcGFjZSxcbiAgICAgICAgICAgIG9wZW5lZFdpbmRvdzogb3BlbmVkV2luZG93LFxuICAgICAgICAgICAgaXNSb290V29ya3NwYWNlOiBpc1Jvb3RXb3Jrc3BhY2UsXG4gICAgICAgICAgICBzaG93QWN0aW9uTWVudTogc2hvd0FjdGlvbk1lbnUsXG4gICAgICAgICAgICBjbG9zZVdpbmRvdzogKCk9PnByb3BzLmNsb3NlV29ya3NwYWNlKHtcbiAgICAgICAgICAgICAgICAgICAgY2xvc2VXaW5kb3c6IHRydWVcbiAgICAgICAgICAgICAgICB9KSxcbiAgICAgICAgICAgIGNoaWxkcmVuOiBjb250ZW50XG4gICAgICAgIH0pXG4gICAgfSk7XG59O1xuLyoqXG4gKiBSZW5kZXJzIHRoZSBjb250YWluZXJzLCB0aXRsZSBiYXIgYW5kIHdpbmRvdyBidXR0b25zIGFyb3VuZCBhIHdvcmtzcGFjZSBpbiB0aGUgZ2xvYmFsIHdvcmtzcGFjZVxuICogd2luZG93IHN5c3RlbS5cbiAqLyBjb25zdCBXb3Jrc3BhY2VDaHJvbWUgPSAoeyBvcGVuZWRXb3Jrc3BhY2UsIG9wZW5lZFdpbmRvdywgaXNSb290V29ya3NwYWNlLCBzaG93QWN0aW9uTWVudSwgY2xvc2VXaW5kb3csIGNoaWxkcmVuIH0pPT57XG4gICAgY29uc3QgbGF5b3V0ID0gdXNlTGF5b3V0VHlwZSgpO1xuICAgIGNvbnN0IHsgb3BlbmVkR3JvdXAsIG9wZW5lZFdpbmRvd3MsIHJlZ2lzdGVyZWRXaW5kb3dzQnlOYW1lLCByZWdpc3RlcmVkV29ya3NwYWNlc0J5TmFtZSwgcmVnaXN0ZXJlZEdyb3Vwc0J5TmFtZSwgaXNNb3N0UmVjZW50bHlPcGVuZWRXaW5kb3dIaWRkZW4sIHNldFdpbmRvd01heGltaXplZCwgaGlkZVdpbmRvdyB9ID0gdXNlV29ya3NwYWNlMlN0b3JlKCk7XG4gICAgY29uc3Qgd2luZG93TmFtZSA9IG9wZW5lZFdpbmRvdy53aW5kb3dOYW1lO1xuICAgIGNvbnN0IHsgbWF4aW1pemVkIH0gPSBvcGVuZWRXaW5kb3c7XG4gICAgY29uc3QgdGl0bGUgPSBvcGVuZWRXb3Jrc3BhY2UudGl0bGUgPz8gJyc7XG4gICAgY29uc3Qgd2luZG93RGVmID0gcmVnaXN0ZXJlZFdpbmRvd3NCeU5hbWVbd2luZG93TmFtZV07XG4gICAgY29uc3Qgd2lkdGggPSBnZXRPcGVuZWRXaW5kb3dXaWR0aChvcGVuZWRXaW5kb3csIHJlZ2lzdGVyZWRXb3Jrc3BhY2VzQnlOYW1lLCByZWdpc3RlcmVkV2luZG93c0J5TmFtZSk7XG4gICAgY29uc3QgaWNvbiA9IHdpbmRvd0RlZj8uaWNvbjtcbiAgICBjb25zdCBjYW5NYXhpbWl6ZSA9IHdpbmRvd0RlZj8uY2FuTWF4aW1pemU7XG4gICAgY29uc3QgY2FuQ2xvc2VHcm91cCA9IG9wZW5lZEdyb3VwID8gcmVnaXN0ZXJlZEdyb3Vwc0J5TmFtZVtvcGVuZWRHcm91cC5ncm91cE5hbWVdPy5wZXJzaXN0ZW5jZSA9PT0gJ2Nsb3NhYmxlJyA6IGZhbHNlO1xuICAgIGNvbnN0IGNhbkhpZGUgPSAhIWljb24gJiYgIWNhbkNsb3NlR3JvdXA7XG4gICAgY29uc3Qgb3BlbmVkV2luZG93SW5kZXggPSBvcGVuZWRXaW5kb3dzLmZpbmRJbmRleCgodyk9Pncud2luZG93TmFtZSA9PT0gd2luZG93TmFtZSk7XG4gICAgY29uc3QgaXNXaW5kb3dIaWRkZW4gPSBvcGVuZWRXaW5kb3dJbmRleCA8IG9wZW5lZFdpbmRvd3MubGVuZ3RoIC0gMSB8fCBpc01vc3RSZWNlbnRseU9wZW5lZFdpbmRvd0hpZGRlbjtcbiAgICBjb25zdCBpc0FjdGlvbk1lbnVPcGVuZWQgPSBPYmplY3QudmFsdWVzKHJlZ2lzdGVyZWRXaW5kb3dzQnlOYW1lKS5zb21lKCh3aW5kb3cpPT53aW5kb3cuZ3JvdXAgPT09IG9wZW5lZEdyb3VwPy5ncm91cE5hbWUgJiYgd2luZG93Lmljb24gIT09IHVuZGVmaW5lZCk7XG4gICAgcmV0dXJuIC8qI19fUFVSRV9fKi8gX2pzeHMoXCJkaXZcIiwge1xuICAgICAgICBjbGFzc05hbWU6IGNsYXNzTmFtZXMoc3R5bGVzLndvcmtzcGFjZU91dGVyQ29udGFpbmVyLCB7XG4gICAgICAgICAgICBbc3R5bGVzLm5hcnJvd1dvcmtzcGFjZV06IHdpZHRoID09PSAnbmFycm93JyxcbiAgICAgICAgICAgIFtzdHlsZXMud2lkZXJXb3Jrc3BhY2VdOiB3aWR0aCA9PT0gJ3dpZGVyJyxcbiAgICAgICAgICAgIFtzdHlsZXMuZXh0cmFXaWRlV29ya3NwYWNlXTogd2lkdGggPT09ICdleHRyYS13aWRlJyxcbiAgICAgICAgICAgIFtzdHlsZXMuaXNBY3Rpb25NZW51T3BlbmVkXTogaXNBY3Rpb25NZW51T3BlbmVkXG4gICAgICAgIH0pLFxuICAgICAgICBjaGlsZHJlbjogW1xuICAgICAgICAgICAgLyojX19QVVJFX18qLyBfanN4KFwiZGl2XCIsIHtcbiAgICAgICAgICAgICAgICBjbGFzc05hbWU6IGNsYXNzTmFtZXMoc3R5bGVzLndvcmtzcGFjZVNwYWNlciwge1xuICAgICAgICAgICAgICAgICAgICBbc3R5bGVzLmhpZGRlbl06IGlzV2luZG93SGlkZGVuXG4gICAgICAgICAgICAgICAgfSlcbiAgICAgICAgICAgIH0pLFxuICAgICAgICAgICAgLyojX19QVVJFX18qLyBfanN4KFwiZGl2XCIsIHtcbiAgICAgICAgICAgICAgICBjbGFzc05hbWU6IGNsYXNzTmFtZXMoc3R5bGVzLndvcmtzcGFjZU1pZGRsZUNvbnRhaW5lciwge1xuICAgICAgICAgICAgICAgICAgICBbc3R5bGVzLm1heGltaXplZF06IG1heGltaXplZCxcbiAgICAgICAgICAgICAgICAgICAgW3N0eWxlcy5oaWRkZW5dOiBpc1dpbmRvd0hpZGRlbixcbiAgICAgICAgICAgICAgICAgICAgW3N0eWxlcy5pc1Jvb3RXb3Jrc3BhY2VdOiBpc1Jvb3RXb3Jrc3BhY2UsXG4gICAgICAgICAgICAgICAgICAgIFtzdHlsZXMuc2hvd0FjdGlvbk1lbnVdOiBzaG93QWN0aW9uTWVudVxuICAgICAgICAgICAgICAgIH0pLFxuICAgICAgICAgICAgICAgIGNoaWxkcmVuOiAvKiNfX1BVUkVfXyovIF9qc3goXCJkaXZcIiwge1xuICAgICAgICAgICAgICAgICAgICBjbGFzc05hbWU6IGNsYXNzTmFtZXMoc3R5bGVzLndvcmtzcGFjZUlubmVyQ29udGFpbmVyLCB7XG4gICAgICAgICAgICAgICAgICAgICAgICBbc3R5bGVzLm1heGltaXplZF06IG1heGltaXplZCxcbiAgICAgICAgICAgICAgICAgICAgICAgIFtzdHlsZXMuaGlkZGVuXTogaXNXaW5kb3dIaWRkZW4sXG4gICAgICAgICAgICAgICAgICAgICAgICBbc3R5bGVzLmlzUm9vdFdvcmtzcGFjZV06IGlzUm9vdFdvcmtzcGFjZVxuICAgICAgICAgICAgICAgICAgICB9KSxcbiAgICAgICAgICAgICAgICAgICAgY2hpbGRyZW46IGNoaWxkcmVuID8gLyojX19QVVJFX18qLyBfanN4cyhfRnJhZ21lbnQsIHtcbiAgICAgICAgICAgICAgICAgICAgICAgIGNoaWxkcmVuOiBbXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgLyojX19QVVJFX18qLyBfanN4cyhIZWFkZXIsIHtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgXCJhcmlhLWxhYmVsXCI6IGdldENvcmVUcmFuc2xhdGlvbignd29ya3NwYWNlSGVhZGVyJyksXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNsYXNzTmFtZTogc3R5bGVzLmhlYWRlcixcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY2hpbGRyZW46IFtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8qI19fUFVSRV9fKi8gX2pzeChIZWFkZXJOYW1lLCB7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcHJlZml4OiBcIlwiLFxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNoaWxkcmVuOiB0aXRsZVxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgfSksXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAvKiNfX1BVUkVfXyovIF9qc3goXCJkaXZcIiwge1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNsYXNzTmFtZTogc3R5bGVzLm92ZXJsYXlIZWFkZXJTcGFjZXJcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0pLFxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgLyojX19QVVJFX18qLyBfanN4KEhlYWRlckdsb2JhbEJhciwge1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNsYXNzTmFtZTogc3R5bGVzLmhlYWRlckJ1dHRvbnMsXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY2hpbGRyZW46IGlzRGVza3RvcChsYXlvdXQpID8gLyojX19QVVJFX18qLyBfanN4cyhfRnJhZ21lbnQsIHtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY2hpbGRyZW46IFtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIChjYW5NYXhpbWl6ZSB8fCBtYXhpbWl6ZWQpICYmIC8qI19fUFVSRV9fKi8gX2pzeChIZWFkZXJHbG9iYWxBY3Rpb24sIHtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBcImFyaWEtbGFiZWxcIjogbWF4aW1pemVkID8gZ2V0Q29yZVRyYW5zbGF0aW9uKCdtaW5pbWl6ZScpIDogZ2V0Q29yZVRyYW5zbGF0aW9uKCdtYXhpbWl6ZScpLFxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIG9uQ2xpY2s6ICgpPT5zZXRXaW5kb3dNYXhpbWl6ZWQod2luZG93TmFtZSwgIW1heGltaXplZCksXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY2hpbGRyZW46IG1heGltaXplZCA/IC8qI19fUFVSRV9fKi8gX2pzeChNaW5pbWl6ZSwge30pIDogLyojX19QVVJFX18qLyBfanN4KE1heGltaXplLCB7fSlcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0pLFxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY2FuSGlkZSAmJiAvKiNfX1BVUkVfXyovIF9qc3goSGVhZGVyR2xvYmFsQWN0aW9uLCB7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgXCJhcmlhLWxhYmVsXCI6IGdldENvcmVUcmFuc2xhdGlvbignaGlkZScpLFxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIG9uQ2xpY2s6ICgpPT5oaWRlV2luZG93KCksXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY2hpbGRyZW46IC8qI19fUFVSRV9fKi8gX2pzeChBcnJvd1JpZ2h0SWNvbiwge30pXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB9KSxcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICFjYW5DbG9zZUdyb3VwICYmIC8qI19fUFVSRV9fKi8gX2pzeChIZWFkZXJHbG9iYWxBY3Rpb24sIHtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBcImFyaWEtbGFiZWxcIjogZ2V0Q29yZVRyYW5zbGF0aW9uKCdjbG9zZScpLFxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIG9uQ2xpY2s6IGNsb3NlV2luZG93LFxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNoaWxkcmVuOiAvKiNfX1BVUkVfXyovIF9qc3goQ2xvc2VJY29uLCB7fSlcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0pXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIF1cbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB9KSA6IC8qI19fUFVSRV9fKi8gX2pzeHMoX0ZyYWdtZW50LCB7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNoaWxkcmVuOiBbXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBjYW5IaWRlICYmIC8qI19fUFVSRV9fKi8gX2pzeChIZWFkZXJHbG9iYWxBY3Rpb24sIHtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBcImFyaWEtbGFiZWxcIjogZ2V0Q29yZVRyYW5zbGF0aW9uKCdoaWRlJyksXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgb25DbGljazogKCk9PmhpZGVXaW5kb3coKSxcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBjaGlsZHJlbjogLyojX19QVVJFX18qLyBfanN4KERvd25Ub0JvdHRvbSwge30pXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB9KSxcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8qI19fUFVSRV9fKi8gX2pzeChIZWFkZXJHbG9iYWxBY3Rpb24sIHtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBcImFyaWEtbGFiZWxcIjogZ2V0Q29yZVRyYW5zbGF0aW9uKCdjbG9zZScpLFxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIG9uQ2xpY2s6ICgpPT57XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGlmIChjYW5DbG9zZUdyb3VwKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB2b2lkIGNsb3NlV29ya3NwYWNlR3JvdXAyKCk7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBjbG9zZVdpbmRvdygpO1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgfSxcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBjaGlsZHJlbjogLyojX19QVVJFX18qLyBfanN4KENsb3NlSWNvbiwge30pXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB9KVxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBdXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgfSlcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0pXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIF1cbiAgICAgICAgICAgICAgICAgICAgICAgICAgICB9KSxcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICBjaGlsZHJlblxuICAgICAgICAgICAgICAgICAgICAgICAgXVxuICAgICAgICAgICAgICAgICAgICB9KSA6IC8qI19fUFVSRV9fKi8gX2pzeChJbmxpbmVMb2FkaW5nLCB7XG4gICAgICAgICAgICAgICAgICAgICAgICBjbGFzc05hbWU6IHN0eWxlcy5sb2FkZXIsXG4gICAgICAgICAgICAgICAgICAgICAgICBkZXNjcmlwdGlvbjogYCR7Z2V0Q29yZVRyYW5zbGF0aW9uKCdsb2FkaW5nJyl9IC4uLmBcbiAgICAgICAgICAgICAgICAgICAgfSlcbiAgICAgICAgICAgICAgICB9KVxuICAgICAgICAgICAgfSlcbiAgICAgICAgXVxuICAgIH0pO1xufTtcbmV4cG9ydCBkZWZhdWx0IEFjdGl2ZVdvcmtzcGFjZVdpbmRvdztcbiJdLCJuYW1lcyI6WyJqc3giLCJfanN4IiwianN4cyIsIl9qc3hzIiwiRnJhZ21lbnQiLCJfRnJhZ21lbnQiLCJSZWFjdCIsInVzZUVmZmVjdCIsInVzZU1lbW8iLCJ1c2VTdGF0ZSIsImNsYXNzTmFtZXMiLCJQYXJjZWwiLCJIZWFkZXIiLCJIZWFkZXJHbG9iYWxBY3Rpb24iLCJIZWFkZXJHbG9iYWxCYXIiLCJIZWFkZXJOYW1lIiwiSW5saW5lTG9hZGluZyIsIkRvd25Ub0JvdHRvbSIsIk1heGltaXplIiwiTWluaW1pemUiLCJjcmVhdGVQYXJjZWxNb3VudGVyIiwid29ya3NwYWNlMlN0b3JlIiwiaXNEZXNrdG9wIiwidXNlTGF5b3V0VHlwZSIsInVzZVN0b3JlIiwibG9hZExpZmVDeWNsZXMiLCJnZXRDb3JlVHJhbnNsYXRpb24iLCJBcnJvd1JpZ2h0SWNvbiIsIkNsb3NlSWNvbiIsImNsb3NlV29ya3NwYWNlR3JvdXAyIiwiZ2V0T3BlbmVkV2luZG93V2lkdGgiLCJ1c2VXb3Jrc3BhY2UyU3RvcmUiLCJzdHlsZXMiLCJzZWxlY3RSZWdpc3RlcmVkV29ya3NwYWNlc0J5TmFtZSIsInN0YXRlIiwiQWN0aXZlV29ya3NwYWNlV2luZG93Iiwib3BlbmVkV2luZG93IiwiZ3JvdXBQcm9wcyIsImFjdGlvbnMiLCJyZW5kZXJDaHJvbWUiLCJzaG93QWN0aW9uTWVudSIsIm9wZW5lZFdvcmtzcGFjZXMiLCJsaWZlQ3ljbGVzQnlVdWlkIiwic2V0TGlmZUN5Y2xlc0J5VXVpZCIsInJlZ2lzdGVyZWRXb3Jrc3BhY2VzQnlOYW1lIiwiY2FuY2VsbGVkIiwiUHJvbWlzZSIsIm9wZW5lZFdvcmtzcGFjZSIsIndvcmtzcGFjZURlZiIsIm1vZHVsZU5hbWUiLCJjb21wb25lbnQiLCJlbnRyaWVzIiwiT2JqZWN0IiwiZW50cnkiLCJpIiwiQWN0aXZlV29ya3NwYWNlIiwibW91bnRQYXJjZWwiLCJsaWZlQ3ljbGUiLCJpc1Jvb3RXb3Jrc3BhY2UiLCJpc0xlYWZXb3Jrc3BhY2UiLCJwcm9wcyIsIm9wdGlvbnMiLCJjbG9zZVdpbmRvdyIsImRpc2NhcmRVbnNhdmVkQ2hhbmdlcyIsIm9rVG9DbG9zZVdvcmtzcGFjZXMiLCJjaGlsZFdvcmtzcGFjZU5hbWUiLCJjaGlsZFdvcmtzcGFjZVByb3BzIiwicGFyZW50V29ya3NwYWNlTmFtZSIsInBhcmVudEluZGV4IiwidyIsImlzTGVhZiIsIndvcmtzcGFjZXNBYm92ZVBhcmVudCIsIm9rVG9DbG9zZSIsInRpdGxlIiwiaGFzVW5zYXZlZENoYW5nZXMiLCJoaWRlQmVoaW5kTGVhZiIsImNvbnRlbnQiLCJXb3Jrc3BhY2VDaHJvbWUiLCJjaGlsZHJlbiIsImxheW91dCIsIm9wZW5lZEdyb3VwIiwib3BlbmVkV2luZG93cyIsInJlZ2lzdGVyZWRXaW5kb3dzQnlOYW1lIiwicmVnaXN0ZXJlZEdyb3Vwc0J5TmFtZSIsImlzTW9zdFJlY2VudGx5T3BlbmVkV2luZG93SGlkZGVuIiwic2V0V2luZG93TWF4aW1pemVkIiwiaGlkZVdpbmRvdyIsIndpbmRvd05hbWUiLCJtYXhpbWl6ZWQiLCJ3aW5kb3dEZWYiLCJ3aWR0aCIsImljb24iLCJjYW5NYXhpbWl6ZSIsImNhbkNsb3NlR3JvdXAiLCJjYW5IaWRlIiwib3BlbmVkV2luZG93SW5kZXgiLCJpc1dpbmRvd0hpZGRlbiIsImlzQWN0aW9uTWVudU9wZW5lZCIsIndpbmRvdyIsInVuZGVmaW5lZCJdLCJtYXBwaW5ncyI6Ijs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7O0FBQXNGO0FBQzFCO0FBQ3hCO0FBQ1M7QUFDMEQ7QUFDaEM7QUFDUTtBQUNEO0FBQ3pCO0FBQ1U7QUFDRDtBQUNtQztBQUNuRDtBQUM5Qyx1RkFBdUY7QUFDdkYsTUFBTWlDLG1DQUFtQyxDQUFDQyxRQUFRQSxNQUFNLDBCQUEwQjtBQUNsRjs7O0NBR0MsR0FBRyxNQUFNQyx3QkFBd0IsQ0FBQyxFQUFFQyxZQUFZLEVBQUVDLFVBQVUsRUFBRUMsT0FBTyxFQUFFQyxZQUFZLEVBQUVDLGNBQWMsRUFBRTtJQUNsRyxNQUFNLEVBQUVDLGdCQUFnQixFQUFFLEdBQUdMO0lBQzdCLDhFQUE4RTtJQUM5RSw2RUFBNkU7SUFDN0UsNkVBQTZFO0lBQzdFLDZFQUE2RTtJQUM3RSwyRUFBMkU7SUFDM0UsOEVBQThFO0lBQzlFLHlDQUF5QztJQUN6QyxNQUFNLENBQUNNLGtCQUFrQkMsb0JBQW9CLEdBQUdsQyxtQ0FBUUEsQ0FBQyxDQUFDO0lBQzFELHlFQUF5RTtJQUN6RSxNQUFNbUMsNkJBQTZCcEIsc0RBQVFBLENBQUNILHdEQUFlQSxFQUFFWTtJQUM3RDFCLG9DQUFTQSxDQUFDO1FBQ04sSUFBSXNDLFlBQVk7UUFDaEJDLFFBQVEsR0FBRyxDQUFDTCxpQkFBaUIsR0FBRyxDQUFDLE9BQU9NO1lBQ3BDLE1BQU1DLGVBQWVKLDBCQUEwQixDQUFDRyxnQkFBZ0IsYUFBYSxDQUFDO1lBQzlFLElBQUksQ0FBQ0MsY0FBYztnQkFDZixPQUFPO1lBQ1g7WUFDQSxNQUFNLEVBQUVDLFVBQVUsRUFBRUMsU0FBUyxFQUFFLEdBQUdGO1lBQ2xDLE9BQU87Z0JBQ0hELGdCQUFnQixJQUFJO2dCQUNwQixNQUFNdEIsd0RBQWNB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\n//# sourceURL=webpack-internal:///../../framework/esm-styleguide/dist/workspaces2/active-workspace-window.component.js\n\n}");
834
+ eval("{__webpack_require__.r(__webpack_exports__);\n__webpack_require__.d(__webpack_exports__, {\n \"default\": () => (__rspack_default_export)\n});\n/* import */ var react_jsx_runtime__rspack_import_0 = __webpack_require__(\"../../../node_modules/react/jsx-runtime.js\");\n/* import */ var react__rspack_import_1 = __webpack_require__(\"webpack/sharing/consume/default/react/react\");\n/* import */ var react__rspack_import_1_default = /*#__PURE__*/__webpack_require__.n(react__rspack_import_1);\n/* import */ var classnames__rspack_import_2 = __webpack_require__(\"../../../node_modules/classnames/index.js\");\n/* import */ var classnames__rspack_import_2_default = /*#__PURE__*/__webpack_require__.n(classnames__rspack_import_2);\n/* import */ var single_spa_react_parcel__rspack_import_3 = __webpack_require__(\"../../../node_modules/single-spa-react/lib/esm/parcel.js\");\n/* import */ var _carbon_react__rspack_import_4 = __webpack_require__(\"webpack/sharing/consume/default/@carbon/react/@carbon/react\");\n/* import */ var _carbon_react__rspack_import_4_default = /*#__PURE__*/__webpack_require__.n(_carbon_react__rspack_import_4);\n/* import */ var _carbon_react_icons__rspack_import_13 = __webpack_require__(\"../../../node_modules/@carbon/icons-react/es/generated/bucket-11.js\");\n/* import */ var _carbon_react_icons__rspack_import_14 = __webpack_require__(\"../../../node_modules/@carbon/icons-react/es/generated/bucket-6.js\");\n/* import */ var _openmrs_esm_extensions__rspack_import_5 = __webpack_require__(\"../../framework/esm-extensions/dist/index.js\");\n/* import */ var _openmrs_esm_react_utils__rspack_import_6 = __webpack_require__(\"../../framework/esm-react-utils/dist/index.js\");\n/* import */ var _openmrs_esm_error_handling__rspack_import_7 = __webpack_require__(\"../../framework/esm-error-handling/dist/index.js\");\n/* import */ var _openmrs_esm_routes__rspack_import_12 = __webpack_require__(\"../../framework/esm-routes/dist/loaders/load-lifecycles.js\");\n/* import */ var _openmrs_esm_translations__rspack_import_8 = __webpack_require__(\"../../framework/esm-translations/dist/index.js\");\n/* import */ var _icons_index_js__rspack_import_9 = __webpack_require__(\"../../framework/esm-styleguide/dist/icons/index.js\");\n/* import */ var _workspace2_js__rspack_import_10 = __webpack_require__(\"../../framework/esm-styleguide/dist/workspaces2/workspace2.js\");\n/* import */ var _workspace2_module_scss__rspack_import_11 = __webpack_require__(\"../../framework/esm-styleguide/dist/workspaces2/workspace2.module.scss\");\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n// module-level so the store subscription's snapshot getter stays stable across renders\nconst selectRegisteredWorkspacesByName = (state)=>state.registeredWorkspacesByName;\n/**\n * Renders an opened workspace window. `actions` determines which store the window's workspaces\n * navigate within: the global workspace window system, or an `<ExportedWorkspace>`'s local store.\n */ const ActiveWorkspaceWindow = ({ openedWindow, groupProps, actions, renderChrome, showActionMenu })=>{\n const { openedWorkspaces } = openedWindow;\n // Keyed by opened workspace uuid rather than stack index. The lifecycles load\n // asynchronously, so when the stack changes (a workspace at some position is\n // replaced by another, for example closing a child workspace and immediately\n // opening a different one), an index-based lookup can hand the new workspace\n // the previous workspace's component until the reload resolves. The parcel\n // mounts whatever config it first receives, so the wrong component would then\n // render with the new workspace's props.\n const [lifeCyclesByUuid, setLifeCyclesByUuid] = (0,react__rspack_import_1.useState)({});\n // Reactive so the effect retries when a workspace registers after mount.\n const registeredWorkspacesByName = (0,_openmrs_esm_react_utils__rspack_import_6.useStore)(_openmrs_esm_extensions__rspack_import_5.workspace2Store, selectRegisteredWorkspacesByName);\n // The effect reloads every workspace whenever any of them changes (for example, its title), so\n // track which workspaces have already reported a load failure to report each one only once.\n const reportedFailureUuids = (0,react__rspack_import_1.useRef)(new Set());\n (0,react__rspack_import_1.useEffect)(()=>{\n let cancelled = false;\n Promise.all(openedWorkspaces.map(async (openedWorkspace)=>{\n const workspaceDef = registeredWorkspacesByName[openedWorkspace.workspaceName];\n if (!workspaceDef) {\n return null;\n }\n const { moduleName, component } = workspaceDef;\n try {\n return [\n openedWorkspace.uuid,\n await (0,_openmrs_esm_routes__rspack_import_12.loadLifeCycles)(moduleName, component)\n ];\n } catch (error) {\n if (!cancelled && !reportedFailureUuids.current.has(openedWorkspace.uuid)) {\n reportedFailureUuids.current.add(openedWorkspace.uuid);\n (0,_openmrs_esm_error_handling__rspack_import_7.reportError)(error);\n }\n return [\n openedWorkspace.uuid,\n null\n ];\n }\n })).then((entries)=>{\n if (!cancelled) {\n setLifeCyclesByUuid(Object.fromEntries(entries.filter((entry)=>entry != null)));\n }\n }, _openmrs_esm_error_handling__rspack_import_7.reportError);\n return ()=>{\n cancelled = true;\n };\n }, [\n openedWorkspaces,\n registeredWorkspacesByName\n ]);\n return /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(react_jsx_runtime__rspack_import_0.Fragment, {\n children: openedWorkspaces.map((openedWorkspace, i)=>/*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(ActiveWorkspace, {\n openedWorkspace: openedWorkspace,\n openedWindow: openedWindow,\n groupProps: groupProps,\n actions: actions,\n renderChrome: renderChrome,\n lifeCycle: lifeCyclesByUuid[openedWorkspace.uuid],\n isRootWorkspace: i === 0,\n isLeafWorkspace: i === openedWorkspaces.length - 1,\n showActionMenu: showActionMenu\n }, openedWorkspace.uuid))\n });\n};\nconst mountParcel = (0,_openmrs_esm_extensions__rspack_import_5.createParcelMounter)();\nconst ActiveWorkspace = ({ lifeCycle, openedWorkspace, openedWindow, groupProps, actions, renderChrome, isRootWorkspace, isLeafWorkspace, showActionMenu })=>{\n const props = (0,react__rspack_import_1.useMemo)(()=>openedWorkspace && {\n closeWorkspace: async (options = {})=>{\n const { closeWindow = false, discardUnsavedChanges = false } = options;\n if (closeWindow) {\n const okToCloseWorkspaces = discardUnsavedChanges || await actions.promptForClosingWorkspaces();\n if (okToCloseWorkspaces) {\n actions.closeWorkspace(openedWindow.openedWorkspaces[0].workspaceName);\n return true;\n }\n return false;\n } else {\n const okToCloseWorkspaces = discardUnsavedChanges || await actions.promptForClosingWorkspaces(openedWorkspace.workspaceName);\n if (okToCloseWorkspaces) {\n actions.closeWorkspace(openedWorkspace.workspaceName);\n return true;\n }\n return false;\n }\n },\n launchChildWorkspace: async (childWorkspaceName, childWorkspaceProps)=>{\n const parentWorkspaceName = openedWorkspace.workspaceName;\n const { openedWorkspaces } = openedWindow;\n const parentIndex = openedWorkspaces.findIndex((w)=>w.workspaceName === parentWorkspaceName);\n if (parentIndex === -1) {\n return;\n }\n const isLeaf = parentIndex === openedWorkspaces.length - 1;\n if (!isLeaf) {\n // There are workspaces above the parent that will be closed.\n // Prompt if any of them have unsaved changes.\n const workspacesAboveParent = openedWorkspaces.slice(parentIndex + 1);\n if (workspacesAboveParent.some((w)=>w.hasUnsavedChanges)) {\n const okToClose = await actions.promptForClosingWorkspaces(openedWorkspaces[parentIndex + 1].workspaceName);\n if (!okToClose) {\n return;\n }\n }\n }\n actions.openChildWorkspace(parentWorkspaceName, childWorkspaceName, childWorkspaceProps || {});\n },\n setWorkspaceTitle: (title)=>actions.setWorkspaceTitle(openedWorkspace.uuid, title),\n setHasUnsavedChanges: (hasUnsavedChanges)=>actions.setHasUnsavedChanges(openedWorkspace.uuid, hasUnsavedChanges),\n workspaceName: openedWorkspace.workspaceName,\n workspaceProps: openedWorkspace.props,\n windowProps: openedWindow.props,\n groupProps,\n workspaceMeta: _openmrs_esm_extensions__rspack_import_5.workspace2Store.getState().registeredWorkspacesByName[openedWorkspace.workspaceName]?.meta ?? {},\n isRootWorkspace,\n isLeafWorkspace,\n windowName: openedWindow.windowName,\n showActionMenu\n }, [\n openedWorkspace,\n openedWindow,\n groupProps,\n actions,\n isRootWorkspace,\n isLeafWorkspace,\n showActionMenu\n ]);\n // In bare mode (<ExportedWorkspace>) there is no chrome to stack workspaces, so every non-leaf\n // workspace is hidden (not unmounted, so it keeps its state) and the leaf covers them. In chrome\n // mode the absolute-positioned WorkspaceChrome containers handle stacking, so this class is not\n // applied there.\n const hideBehindLeaf = !renderChrome && !isLeafWorkspace;\n const content = (0,react__rspack_import_1.useMemo)(()=>lifeCycle ? /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(single_spa_react_parcel__rspack_import_3[\"default\"], {\n config: lifeCycle,\n mountParcel: mountParcel,\n wrapWith: \"div\",\n wrapClassName: classnames__rspack_import_2_default()(_workspace2_module_scss__rspack_import_11[\"default\"].workspaceContent, {\n [_workspace2_module_scss__rspack_import_11[\"default\"].hiddenExtraWorkspace]: hideBehindLeaf\n }),\n ...props\n }, openedWorkspace.workspaceName) : lifeCycle === null ? /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(\"div\", {\n className: classnames__rspack_import_2_default()(_workspace2_module_scss__rspack_import_11[\"default\"].workspaceContent, {\n [_workspace2_module_scss__rspack_import_11[\"default\"].hiddenExtraWorkspace]: hideBehindLeaf\n }),\n children: /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_carbon_react__rspack_import_4.InlineNotification, {\n kind: \"error\",\n title: (0,_openmrs_esm_translations__rspack_import_8.getCoreTranslation)('error'),\n subtitle: (0,_openmrs_esm_translations__rspack_import_8.getCoreTranslation)('somethingWentWrongTryReloading'),\n hideCloseButton: true\n })\n }) : null, [\n lifeCycle,\n openedWorkspace.workspaceName,\n props,\n hideBehindLeaf\n ]);\n if (!renderChrome) {\n return content ?? /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_carbon_react__rspack_import_4.InlineLoading, {\n className: classnames__rspack_import_2_default()(_workspace2_module_scss__rspack_import_11[\"default\"].loader, {\n [_workspace2_module_scss__rspack_import_11[\"default\"].hiddenExtraWorkspace]: hideBehindLeaf\n }),\n description: `${(0,_openmrs_esm_translations__rspack_import_8.getCoreTranslation)('loading')}`\n });\n }\n // The node removed from the workspace grid on close must generate a box. WebKit before Safari 26.2\n // doesn't relayout the grid when the removed node is the `display: contents` outer container, so the\n // closed window keeps taking up space. https://bugs.webkit.org/show_bug.cgi?id=299258\n return /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(\"div\", {\n children: /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(WorkspaceChrome, {\n openedWorkspace: openedWorkspace,\n openedWindow: openedWindow,\n isRootWorkspace: isRootWorkspace,\n showActionMenu: showActionMenu,\n closeWindow: ()=>props.closeWorkspace({\n closeWindow: true\n }),\n children: content\n })\n });\n};\n/**\n * Renders the containers, title bar and window buttons around a workspace in the global workspace\n * window system.\n */ const WorkspaceChrome = ({ openedWorkspace, openedWindow, isRootWorkspace, showActionMenu, closeWindow, children })=>{\n const layout = (0,_openmrs_esm_react_utils__rspack_import_6.useLayoutType)();\n const { openedGroup, openedWindows, registeredWindowsByName, registeredWorkspacesByName, registeredGroupsByName, isMostRecentlyOpenedWindowHidden, setWindowMaximized, hideWindow } = (0,_workspace2_js__rspack_import_10.useWorkspace2Store)();\n const windowName = openedWindow.windowName;\n const { maximized } = openedWindow;\n const title = openedWorkspace.title ?? '';\n const windowDef = registeredWindowsByName[windowName];\n const width = (0,_workspace2_js__rspack_import_10.getOpenedWindowWidth)(openedWindow, registeredWorkspacesByName, registeredWindowsByName);\n const icon = windowDef?.icon;\n const canMaximize = windowDef?.canMaximize;\n const canCloseGroup = openedGroup ? registeredGroupsByName[openedGroup.groupName]?.persistence === 'closable' : false;\n const canHide = !!icon && !canCloseGroup;\n const openedWindowIndex = openedWindows.findIndex((w)=>w.windowName === windowName);\n const isWindowHidden = openedWindowIndex < openedWindows.length - 1 || isMostRecentlyOpenedWindowHidden;\n const isActionMenuOpened = Object.values(registeredWindowsByName).some((window)=>window.group === openedGroup?.groupName && window.icon !== undefined);\n return /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsxs)(\"div\", {\n className: classnames__rspack_import_2_default()(_workspace2_module_scss__rspack_import_11[\"default\"].workspaceOuterContainer, {\n [_workspace2_module_scss__rspack_import_11[\"default\"].narrowWorkspace]: width === 'narrow',\n [_workspace2_module_scss__rspack_import_11[\"default\"].widerWorkspace]: width === 'wider',\n [_workspace2_module_scss__rspack_import_11[\"default\"].extraWideWorkspace]: width === 'extra-wide',\n [_workspace2_module_scss__rspack_import_11[\"default\"].isActionMenuOpened]: isActionMenuOpened\n }),\n children: [\n /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(\"div\", {\n className: classnames__rspack_import_2_default()(_workspace2_module_scss__rspack_import_11[\"default\"].workspaceSpacer, {\n [_workspace2_module_scss__rspack_import_11[\"default\"].hidden]: isWindowHidden\n })\n }),\n /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(\"div\", {\n className: classnames__rspack_import_2_default()(_workspace2_module_scss__rspack_import_11[\"default\"].workspaceMiddleContainer, {\n [_workspace2_module_scss__rspack_import_11[\"default\"].maximized]: maximized,\n [_workspace2_module_scss__rspack_import_11[\"default\"].hidden]: isWindowHidden,\n [_workspace2_module_scss__rspack_import_11[\"default\"].isRootWorkspace]: isRootWorkspace,\n [_workspace2_module_scss__rspack_import_11[\"default\"].showActionMenu]: showActionMenu\n }),\n children: /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(\"div\", {\n className: classnames__rspack_import_2_default()(_workspace2_module_scss__rspack_import_11[\"default\"].workspaceInnerContainer, {\n [_workspace2_module_scss__rspack_import_11[\"default\"].maximized]: maximized,\n [_workspace2_module_scss__rspack_import_11[\"default\"].hidden]: isWindowHidden,\n [_workspace2_module_scss__rspack_import_11[\"default\"].isRootWorkspace]: isRootWorkspace\n }),\n children: children ? /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsxs)(react_jsx_runtime__rspack_import_0.Fragment, {\n children: [\n /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsxs)(_carbon_react__rspack_import_4.Header, {\n \"aria-label\": (0,_openmrs_esm_translations__rspack_import_8.getCoreTranslation)('workspaceHeader'),\n className: _workspace2_module_scss__rspack_import_11[\"default\"].header,\n children: [\n /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_carbon_react__rspack_import_4.HeaderName, {\n prefix: \"\",\n children: title\n }),\n /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(\"div\", {\n className: _workspace2_module_scss__rspack_import_11[\"default\"].overlayHeaderSpacer\n }),\n /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_carbon_react__rspack_import_4.HeaderGlobalBar, {\n className: _workspace2_module_scss__rspack_import_11[\"default\"].headerButtons,\n children: (0,_openmrs_esm_react_utils__rspack_import_6.isDesktop)(layout) ? /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsxs)(react_jsx_runtime__rspack_import_0.Fragment, {\n children: [\n (canMaximize || maximized) && /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_carbon_react__rspack_import_4.HeaderGlobalAction, {\n \"aria-label\": maximized ? (0,_openmrs_esm_translations__rspack_import_8.getCoreTranslation)('minimize') : (0,_openmrs_esm_translations__rspack_import_8.getCoreTranslation)('maximize'),\n onClick: ()=>setWindowMaximized(windowName, !maximized),\n children: maximized ? /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_carbon_react_icons__rspack_import_13.Minimize, {}) : /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_carbon_react_icons__rspack_import_13.Maximize, {})\n }),\n canHide && /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_carbon_react__rspack_import_4.HeaderGlobalAction, {\n \"aria-label\": (0,_openmrs_esm_translations__rspack_import_8.getCoreTranslation)('hide'),\n onClick: ()=>hideWindow(),\n children: /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_icons_index_js__rspack_import_9.ArrowRightIcon, {})\n }),\n !canCloseGroup && /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_carbon_react__rspack_import_4.HeaderGlobalAction, {\n \"aria-label\": (0,_openmrs_esm_translations__rspack_import_8.getCoreTranslation)('close'),\n onClick: closeWindow,\n children: /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_icons_index_js__rspack_import_9.CloseIcon, {})\n })\n ]\n }) : /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsxs)(react_jsx_runtime__rspack_import_0.Fragment, {\n children: [\n canHide && /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_carbon_react__rspack_import_4.HeaderGlobalAction, {\n \"aria-label\": (0,_openmrs_esm_translations__rspack_import_8.getCoreTranslation)('hide'),\n onClick: ()=>hideWindow(),\n children: /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_carbon_react_icons__rspack_import_14.DownToBottom, {})\n }),\n /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_carbon_react__rspack_import_4.HeaderGlobalAction, {\n \"aria-label\": (0,_openmrs_esm_translations__rspack_import_8.getCoreTranslation)('close'),\n onClick: ()=>{\n if (canCloseGroup) {\n void (0,_workspace2_js__rspack_import_10.closeWorkspaceGroup2)();\n } else {\n closeWindow();\n }\n },\n children: /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_icons_index_js__rspack_import_9.CloseIcon, {})\n })\n ]\n })\n })\n ]\n }),\n children\n ]\n }) : /*#__PURE__*/ (0,react_jsx_runtime__rspack_import_0.jsx)(_carbon_react__rspack_import_4.InlineLoading, {\n className: _workspace2_module_scss__rspack_import_11[\"default\"].loader,\n description: `${(0,_openmrs_esm_translations__rspack_import_8.getCoreTranslation)('loading')} ...`\n })\n })\n })\n ]\n });\n};\n/* export default */ const __rspack_default_export = (ActiveWorkspaceWindow);\n\n//# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiYnVpbHRpbjpzd2MtbG9hZGVyPz9ydWxlU2V0WzFdLnJ1bGVzWzVdLnVzZVswXSEvaG9tZS9ydW5uZXIvd29yay9vcGVubXJzLWVzbS1jb3JlL29wZW5tcnMtZXNtLWNvcmUvcGFja2FnZXMvZnJhbWV3b3JrL2VzbS1zdHlsZWd1aWRlL2Rpc3Qvd29ya3NwYWNlczIvYWN0aXZlLXdvcmtzcGFjZS13aW5kb3cuY29tcG9uZW50LmpzIiwic291cmNlcyI6WyJ3ZWJwYWNrOi8vQG9wZW5tcnMvZXNtLWFwcC1zaGVsbC8uLi8uLi9mcmFtZXdvcmsvZXNtLXN0eWxlZ3VpZGUvZGlzdC93b3Jrc3BhY2VzMi9hY3RpdmUtd29ya3NwYWNlLXdpbmRvdy5jb21wb25lbnQuanM/ZGRmOCJdLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBqc3ggYXMgX2pzeCwganN4cyBhcyBfanN4cywgRnJhZ21lbnQgYXMgX0ZyYWdtZW50IH0gZnJvbSBcInJlYWN0L2pzeC1ydW50aW1lXCI7XG5pbXBvcnQgUmVhY3QsIHsgdXNlRWZmZWN0LCB1c2VNZW1vLCB1c2VSZWYsIHVzZVN0YXRlIH0gZnJvbSBcInJlYWN0XCI7XG5pbXBvcnQgY2xhc3NOYW1lcyBmcm9tIFwiY2xhc3NuYW1lc1wiO1xuaW1wb3J0IFBhcmNlbCBmcm9tIFwic2luZ2xlLXNwYS1yZWFjdC9wYXJjZWxcIjtcbmltcG9ydCB7IEhlYWRlciwgSGVhZGVyR2xvYmFsQWN0aW9uLCBIZWFkZXJHbG9iYWxCYXIsIEhlYWRlck5hbWUsIElubGluZUxvYWRpbmcsIElubGluZU5vdGlmaWNhdGlvbiB9IGZyb20gXCJAY2FyYm9uL3JlYWN0XCI7XG5pbXBvcnQgeyBEb3duVG9Cb3R0b20sIE1heGltaXplLCBNaW5pbWl6ZSB9IGZyb20gXCJAY2FyYm9uL3JlYWN0L2ljb25zXCI7XG5pbXBvcnQgeyBjcmVhdGVQYXJjZWxNb3VudGVyLCB3b3Jrc3BhY2UyU3RvcmUgfSBmcm9tIFwiQG9wZW5tcnMvZXNtLWV4dGVuc2lvbnNcIjtcbmltcG9ydCB7IGlzRGVza3RvcCwgdXNlTGF5b3V0VHlwZSwgdXNlU3RvcmUgfSBmcm9tIFwiQG9wZW5tcnMvZXNtLXJlYWN0LXV0aWxzXCI7XG5pbXBvcnQgeyByZXBvcnRFcnJvciB9IGZyb20gXCJAb3Blbm1ycy9lc20tZXJyb3ItaGFuZGxpbmdcIjtcbmltcG9ydCB7IGxvYWRMaWZlQ3ljbGVzIH0gZnJvbSBcIkBvcGVubXJzL2VzbS1yb3V0ZXNcIjtcbmltcG9ydCB7IGdldENvcmVUcmFuc2xhdGlvbiB9IGZyb20gXCJAb3Blbm1ycy9lc20tdHJhbnNsYXRpb25zXCI7XG5pbXBvcnQgeyBBcnJvd1JpZ2h0SWNvbiwgQ2xvc2VJY29uIH0gZnJvbSBcIi4uL2ljb25zL2luZGV4LmpzXCI7XG5pbXBvcnQgeyBjbG9zZVdvcmtzcGFjZUdyb3VwMiwgZ2V0T3BlbmVkV2luZG93V2lkdGgsIHVzZVdvcmtzcGFjZTJTdG9yZSB9IGZyb20gXCIuL3dvcmtzcGFjZTIuanNcIjtcbmltcG9ydCBzdHlsZXMgZnJvbSBcIi4vd29ya3NwYWNlMi5tb2R1bGUuc2Nzc1wiO1xuLy8gbW9kdWxlLWxldmVsIHNvIHRoZSBzdG9yZSBzdWJzY3JpcHRpb24ncyBzbmFwc2hvdCBnZXR0ZXIgc3RheXMgc3RhYmxlIGFjcm9zcyByZW5kZXJzXG5jb25zdCBzZWxlY3RSZWdpc3RlcmVkV29ya3NwYWNlc0J5TmFtZSA9IChzdGF0ZSk9PnN0YXRlLnJlZ2lzdGVyZWRXb3Jrc3BhY2VzQnlOYW1lO1xuLyoqXG4gKiBSZW5kZXJzIGFuIG9wZW5lZCB3b3Jrc3BhY2Ugd2luZG93LiBgYWN0aW9uc2AgZGV0ZXJtaW5lcyB3aGljaCBzdG9yZSB0aGUgd2luZG93J3Mgd29ya3NwYWNlc1xuICogbmF2aWdhdGUgd2l0aGluOiB0aGUgZ2xvYmFsIHdvcmtzcGFjZSB3aW5kb3cgc3lzdGVtLCBvciBhbiBgPEV4cG9ydGVkV29ya3NwYWNlPmAncyBsb2NhbCBzdG9yZS5cbiAqLyBjb25zdCBBY3RpdmVXb3Jrc3BhY2VXaW5kb3cgPSAoeyBvcGVuZWRXaW5kb3csIGdyb3VwUHJvcHMsIGFjdGlvbnMsIHJlbmRlckNocm9tZSwgc2hvd0FjdGlvbk1lbnUgfSk9PntcbiAgICBjb25zdCB7IG9wZW5lZFdvcmtzcGFjZXMgfSA9IG9wZW5lZFdpbmRvdztcbiAgICAvLyBLZXllZCBieSBvcGVuZWQgd29ya3NwYWNlIHV1aWQgcmF0aGVyIHRoYW4gc3RhY2sgaW5kZXguIFRoZSBsaWZlY3ljbGVzIGxvYWRcbiAgICAvLyBhc3luY2hyb25vdXNseSwgc28gd2hlbiB0aGUgc3RhY2sgY2hhbmdlcyAoYSB3b3Jrc3BhY2UgYXQgc29tZSBwb3NpdGlvbiBpc1xuICAgIC8vIHJlcGxhY2VkIGJ5IGFub3RoZXIsIGZvciBleGFtcGxlIGNsb3NpbmcgYSBjaGlsZCB3b3Jrc3BhY2UgYW5kIGltbWVkaWF0ZWx5XG4gICAgLy8gb3BlbmluZyBhIGRpZmZlcmVudCBvbmUpLCBhbiBpbmRleC1iYXNlZCBsb29rdXAgY2FuIGhhbmQgdGhlIG5ldyB3b3Jrc3BhY2VcbiAgICAvLyB0aGUgcHJldmlvdXMgd29ya3NwYWNlJ3MgY29tcG9uZW50IHVudGlsIHRoZSByZWxvYWQgcmVzb2x2ZXMuIFRoZSBwYXJjZWxcbiAgICAvLyBtb3VudHMgd2hhdGV2ZXIgY29uZmlnIGl0IGZpcnN0IHJlY2VpdmVzLCBzbyB0aGUgd3JvbmcgY29tcG9uZW50IHdvdWxkIHRoZW5cbiAgICAvLyByZW5kZXIgd2l0aCB0aGUgbmV3IHdvcmtzcGFjZSdzIHByb3BzLlxuICAgIGNvbnN0IFtsaWZlQ3ljbGVzQnlVdWlkLCBzZXRMaWZlQ3ljbGVzQnlVdWlkXSA9IHVzZVN0YXRlKHt9KTtcbiAgICAvLyBSZWFjdGl2ZSBzbyB0aGUgZWZmZWN0IHJldHJpZXMgd2hlbiBhIHdvcmtzcGFjZSByZWdpc3RlcnMgYWZ0ZXIgbW91bnQuXG4gICAgY29uc3QgcmVnaXN0ZXJlZFdvcmtzcGFjZXNCeU5hbWUgPSB1c2VTdG9yZSh3b3Jrc3BhY2UyU3RvcmUsIHNlbGVjdFJlZ2lzdGVyZWRXb3Jrc3BhY2VzQnlOYW1lKTtcbiAgICAvLyBUaGUgZWZmZWN0IHJlbG9hZHMgZXZlcnkgd29ya3NwYWNlIHdoZW5ldmVyIGFueSBvZiB0aGVtIGNoYW5nZXMgKGZvciBleGFtcGxlLCBpdHMgdGl0bGUpLCBzb1xuICAgIC8vIHRyYWNrIHdoaWNoIHdvcmtzcGFjZXMgaGF2ZSBhbHJlYWR5IHJlcG9ydGVkIGEgbG9hZCBmYWlsdXJlIHRvIHJlcG9ydCBlYWNoIG9uZSBvbmx5IG9uY2UuXG4gICAgY29uc3QgcmVwb3J0ZWRGYWlsdXJlVXVpZHMgPSB1c2VSZWYobmV3IFNldCgpKTtcbiAgICB1c2VFZmZlY3QoKCk9PntcbiAgICAgICAgbGV0IGNhbmNlbGxlZCA9IGZhbHNlO1xuICAgICAgICBQcm9taXNlLmFsbChvcGVuZWRXb3Jrc3BhY2VzLm1hcChhc3luYyAob3BlbmVkV29ya3NwYWNlKT0+e1xuICAgICAgICAgICAgY29uc3Qgd29ya3NwYWNlRGVmID0gcmVnaXN0ZXJlZFdvcmtzcGFjZXNCeU5hbWVbb3BlbmVkV29ya3NwYWNlLndvcmtzcGFjZU5hbWVdO1xuICAgICAgICAgICAgaWYgKCF3b3Jrc3BhY2VEZWYpIHtcbiAgICAgICAgICAgICAgICByZXR1cm4gbnVsbDtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICAgIGNvbnN0IHsgbW9kdWxlTmFtZSwgY29tcG9uZW50IH0gPSB3b3Jrc3BhY2VEZWY7XG4gICAgICAgICAgICB0cnkge1xuICAgICAgICAgICAgICAgIHJldHVybiBbXG4gICAgICAgICAgICAgICAgICAgIG9wZW5lZFdvcmtzcGFjZS51dWlkLFxuICAgICAgICAgICAgICAgICAgICBhd2FpdCBsb2FkTGlmZUN5Y2xlcyhtb2R1bGVOYW1lLCBjb21wb25lbnQpXG4gICAgICAgICAgICAgICAgXTtcbiAgICAgICAgICAgIH0gY2F0Y2ggKGVycm9yKSB7XG4gICAgICAgICAgICAgICAgaWYgKCFjYW5jZWxsZWQgJiYgIXJlcG9ydGVkRmFpbHVyZVV1aWRzLmN1cnJlbnQuaGFzKG9wZW5lZFdvcmtzcGFjZS51dWlkKSkge1xuICAgICAgICAgICAgICAgICAgICByZXBvcnRlZEZhaWx1cmVVdWlkcy5jdXJyZW50LmFkZChvcGVuZWRXb3Jrc3BhY2UudXVpZCk7XG4gICAgICAgICAgICAgICAgICAgIHJlcG9ydEVycm9yKGVycm9yKTtcbiAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgcmV0dXJuIFtcbiAgICAgICAgICAgICAgICAgICAgb3BlbmVkV29ya3NwYWNlLnV1aWQsXG4gICAgICAgICAgICAgICAgICAgIG51bGxcbiAgICAgICAgICAgICAgICBdO1xuICAgICAgICAgICAgfVxuICAgICAgICB9KSkudGhlbigoZW50cmllcyk9PntcbiAgICAgICAgICAgIGlmICghY2FuY2VsbGVkKSB7XG4gICAgICAgICAgICAgICAgc2V0TGlmZUN5Y2xlc0J5VXVpZChPYmplY3QuZnJvbUVudHJpZXMoZW50cmllcy5maWx0ZXIoKGVudHJ5KT0+ZW50cnkgIT0gbnVsbCkpKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgfSwgcmVwb3J0RXJyb3IpO1xuICAgICAgICByZXR1cm4gKCk9PntcbiAgICAgICAgICAgIGNhbmNlbGxlZCA9IHRydWU7XG4gICAgICAgIH07XG4gICAgfSwgW1xuICAgICAgICBvcGVuZWRXb3Jrc3BhY2VzLFxuICAgICAgICByZWdpc3RlcmVkV29ya3NwYWNlc0J5TmFtZVxuICAgIF0pO1xuICAgIHJldHVybiAvKiNfX1BVUkVfXyovIF9qc3goX0ZyYWdtZW50LCB7XG4gICAgICAgIGNoaWxkcmVuOiBvcGVuZWRXb3Jrc3BhY2VzLm1hcCgob3BlbmVkV29ya3NwYWNlLCBpKT0+LyojX19QVVJFX18qLyBfanN4KEFjdGl2ZVdvcmtzcGFjZSwge1xuICAgICAgICAgICAgICAgIG9wZW5lZFdvcmtzcGFjZTogb3BlbmVkV29ya3NwYWNlLFxuICAgICAgICAgICAgICAgIG9wZW5lZFdpbmRvdzogb3BlbmVkV2luZG93LFxuICAgICAgICAgICAgICAgIGdyb3VwUHJvcHM6IGdyb3VwUHJvcHMsXG4gICAgICAgICAgICAgICAgYWN0aW9uczogYWN0aW9ucyxcbiAgICAgICAgICAgICAgICByZW5kZXJDaHJvbWU6IHJlbmRlckNocm9tZSxcbiAgICAgICAgICAgICAgICBsaWZlQ3ljbGU6IGxpZmVDeWNsZXNCeVV1aWRbb3BlbmVkV29ya3NwYWNlLnV1aWRdLFxuICAgICAgICAgICAgICAgIGlzUm9vdFdvcmtzcGFjZTogaSA9PT0gMCxcbiAgICAgICAgICAgICAgICBpc0xlYWZXb3Jrc3BhY2U6IGkgPT09IG9wZW5lZFdvcmtzcGFjZXMubGVuZ3RoIC0gMSxcbiAgICAgICAgICAgICAgICBzaG93QWN0aW9uTWVudTogc2hvd0FjdGlvbk1lbnVcbiAgICAgICAgICAgIH0sIG9wZW5lZFdvcmtzcGFjZS51dWlkKSlcbiAgICB9KTtcbn07XG5jb25zdCBtb3VudFBhcmNlbCA9IGNyZWF0ZVBhcmNlbE1vdW50ZXIoKTtcbmNvbnN0IEFjdGl2ZVdvcmtzcGFjZSA9ICh7IGxpZmVDeWNsZSwgb3BlbmVkV29ya3NwYWNlLCBvcGVuZWRXaW5kb3csIGdyb3VwUHJvcHMsIGFjdGlvbnMsIHJlbmRlckNocm9tZSwgaXNSb290V29ya3NwYWNlLCBpc0xlYWZXb3Jrc3BhY2UsIHNob3dBY3Rpb25NZW51IH0pPT57XG4gICAgY29uc3QgcHJvcHMgPSB1c2VNZW1vKCgpPT5vcGVuZWRXb3Jrc3BhY2UgJiYge1xuICAgICAgICAgICAgY2xvc2VXb3Jrc3BhY2U6IGFzeW5jIChvcHRpb25zID0ge30pPT57XG4gICAgICAgICAgICAgICAgY29uc3QgeyBjbG9zZVdpbmRvdyA9IGZhbHNlLCBkaXNjYXJkVW5zYXZlZENoYW5nZXMgPSBmYWxzZSB9ID0gb3B0aW9ucztcbiAgICAgICAgICAgICAgICBpZiAoY2xvc2VXaW5kb3cpIHtcbiAgICAgICAgICAgICAgICAgICAgY29uc3Qgb2tUb0Nsb3NlV29ya3NwYWNlcyA9IGRpc2NhcmRVbnNhdmVkQ2hhbmdlcyB8fCBhd2FpdCBhY3Rpb25zLnByb21wdEZvckNsb3NpbmdXb3Jrc3BhY2VzKCk7XG4gICAgICAgICAgICAgICAgICAgIGlmIChva1RvQ2xvc2VXb3Jrc3BhY2VzKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICBhY3Rpb25zLmNsb3NlV29ya3NwYWNlKG9wZW5lZFdpbmRvdy5vcGVuZWRXb3Jrc3BhY2VzWzBdLndvcmtzcGFjZU5hbWUpO1xuICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHRydWU7XG4gICAgICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGZhbHNlO1xuICAgICAgICAgICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IG9rVG9DbG9zZVdvcmtzcGFjZXMgPSBkaXNjYXJkVW5zYXZlZENoYW5nZXMgfHwgYXdhaXQgYWN0aW9ucy5wcm9tcHRGb3JDbG9zaW5nV29ya3NwYWNlcyhvcGVuZWRXb3Jrc3BhY2Uud29ya3NwYWNlTmFtZSk7XG4gICAgICAgICAgICAgICAgICAgIGlmIChva1RvQ2xvc2VXb3Jrc3BhY2VzKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICBhY3Rpb25zLmNsb3NlV29ya3NwYWNlKG9wZW5lZFdvcmtzcGFjZS53b3Jrc3BhY2VOYW1lKTtcbiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiB0cnVlO1xuICAgICAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgICAgIHJldHVybiBmYWxzZTtcbiAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICB9LFxuICAgICAgICAgICAgbGF1bmNoQ2hpbGRXb3Jrc3BhY2U6IGFzeW5jIChjaGlsZFdvcmtzcGFjZU5hbWUsIGNoaWxkV29ya3NwYWNlUHJvcHMpPT57XG4gICAgICAgICAgICAgICAgY29uc3QgcGFyZW50V29ya3NwYWNlTmFtZSA9IG9wZW5lZFdvcmtzcGFjZS53b3Jrc3BhY2VOYW1lO1xuICAgICAgICAgICAgICAgIGNvbnN0IHsgb3BlbmVkV29ya3NwYWNlcyB9ID0gb3BlbmVkV2luZG93O1xuICAgICAgICAgICAgICAgIGNvbnN0IHBhcmVudEluZGV4ID0gb3BlbmVkV29ya3NwYWNlcy5maW5kSW5kZXgoKHcpPT53LndvcmtzcGFjZU5hbWUgPT09IHBhcmVudFdvcmtzcGFjZU5hbWUpO1xuICAgICAgICAgICAgICAgIGlmIChwYXJlbnRJbmRleCA9PT0gLTEpIHtcbiAgICAgICAgICAgICAgICAgICAgcmV0dXJuO1xuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICBjb25zdCBpc0xlYWYgPSBwYXJlbnRJbmRleCA9PT0gb3BlbmVkV29ya3NwYWNlcy5sZW5ndGggLSAxO1xuICAgICAgICAgICAgICAgIGlmICghaXNMZWFmKSB7XG4gICAgICAgICAgICAgICAgICAgIC8vIFRoZXJlIGFyZSB3b3Jrc3BhY2VzIGFib3ZlIHRoZSBwYXJlbnQgdGhhdCB3aWxsIGJlIGNsb3NlZC5cbiAgICAgICAgICAgICAgICAgICAgLy8gUHJvbXB0IGlmIGFueSBvZiB0aGVtIGhhdmUgdW5zYXZlZCBjaGFuZ2VzLlxuICAgICAgICAgICAgICAgICAgICBjb25zdCB3b3Jrc3BhY2VzQWJvdmVQYXJlbnQgPSBvcGVuZWRXb3Jrc3BhY2VzLnNsaWNlKHBhcmVudEluZGV4ICsgMSk7XG4gICAgICAgICAgICAgICAgICAgIGlmICh3b3Jrc3BhY2VzQWJvdmVQYXJlbnQuc29tZSgodyk9PncuaGFzVW5zYXZlZENoYW5nZXMpKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICBjb25zdCBva1RvQ2xvc2UgPSBhd2FpdCBhY3Rpb25zLnByb21wdEZvckNsb3NpbmdXb3Jrc3BhY2VzKG9wZW5lZFdvcmtzcGFjZXNbcGFyZW50SW5kZXggKyAxXS53b3Jrc3BhY2VOYW1lKTtcbiAgICAgICAgICAgICAgICAgICAgICAgIGlmICghb2tUb0Nsb3NlKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuO1xuICAgICAgICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgIGFjdGlvbnMub3BlbkNoaWxkV29ya3NwYWNlKHBhcmVudFdvcmtzcGFjZU5hbWUsIGNoaWxkV29ya3NwYWNlTmFtZSwgY2hpbGRXb3Jrc3BhY2VQcm9wcyB8fCB7fSk7XG4gICAgICAgICAgICB9LFxuICAgICAgICAgICAgc2V0V29ya3NwYWNlVGl0bGU6ICh0aXRsZSk9PmFjdGlvbnMuc2V0V29ya3NwYWNlVGl0bGUob3BlbmVkV29ya3NwYWNlLnV1aWQsIHRpdGxlKSxcbiAgICAgICAgICAgIHNldEhhc1Vuc2F2ZWRDaGFuZ2VzOiAoaGFzVW5zYXZlZENoYW5nZXMpPT5hY3Rpb25zLnNldEhhc1Vuc2F2ZWRDaGFuZ2VzKG9wZW5lZFdvcmtzcGFjZS51dWlkLCBoYXNVbnNhdmVkQ2hhbmdlcyksXG4gICAgICAgICAgICB3b3Jrc3BhY2VOYW1lOiBvcGVuZWRXb3Jrc3BhY2Uud29ya3NwYWNlTmFtZSxcbiAgICAgICAgICAgIHdvcmtzcGFjZVByb3BzOiBvcGVuZWRXb3Jrc3BhY2UucHJvcHMsXG4gICAgICAgICAgICB3aW5kb3dQcm9wczogb3BlbmVkV2luZG93LnByb3BzLFxuICAgICAgICAgICAgZ3JvdXBQcm9wcyxcbiAgICAgICAgICAgIHdvcmtzcGFjZU1ldGE6IHdvcmtzcGFjZTJTdG9yZS5nZXRTdGF0ZSgpLnJlZ2lzdGVyZWRXb3Jrc3BhY2VzQnlOYW1lW29wZW5lZFdvcmtzcGFjZS53b3Jrc3BhY2VOYW1lXT8ubWV0YSA/PyB7fSxcbiAgICAgICAgICAgIGlzUm9vdFdvcmtzcGFjZSxcbiAgICAgICAgICAgIGlzTGVhZldvcmtzcGFjZSxcbiAgICAgICAgICAgIHdpbmRvd05hbWU6IG9wZW5lZFdpbmRvdy53aW5kb3dOYW1lLFxuICAgICAgICAgICAgc2hvd0FjdGlvbk1lbnVcbiAgICAgICAgfSwgW1xuICAgICAgICBvcGVuZWRXb3Jrc3BhY2UsXG4gICAgICAgIG9wZW5lZFdpbmRvdyxcbiAgICAgICAgZ3JvdXBQcm9wcyxcbiAgICAgICAgYWN0aW9ucyxcbiAgICAgICAgaXNSb290V29ya3NwYWNlLFxuICAgICAgICBpc0xlYWZXb3Jrc3BhY2UsXG4gICAgICAgIHNob3dBY3Rpb25NZW51XG4gICAgXSk7XG4gICAgLy8gSW4gYmFyZSBtb2RlICg8RXhwb3J0ZWRXb3Jrc3BhY2U+KSB0aGVyZSBpcyBubyBjaHJvbWUgdG8gc3RhY2sgd29ya3NwYWNlcywgc28gZXZlcnkgbm9uLWxlYWZcbiAgICAvLyB3b3Jrc3BhY2UgaXMgaGlkZGVuIChub3QgdW5tb3VudGVkLCBzbyBpdCBrZWVwcyBpdHMgc3RhdGUpIGFuZCB0aGUgbGVhZiBjb3ZlcnMgdGhlbS4gSW4gY2hyb21lXG4gICAgLy8gbW9kZSB0aGUgYWJzb2x1dGUtcG9zaXRpb25lZCBXb3Jrc3BhY2VDaHJvbWUgY29udGFpbmVycyBoYW5kbGUgc3RhY2tpbmcsIHNvIHRoaXMgY2xhc3MgaXMgbm90XG4gICAgLy8gYXBwbGllZCB0aGVyZS5cbiAgICBjb25zdCBoaWRlQmVoaW5kTGVhZiA9ICFyZW5kZXJDaHJvbWUgJiYgIWlzTGVhZldvcmtzcGFjZTtcbiAgICBjb25zdCBjb250ZW50ID0gdXNlTWVtbygoKT0+bGlmZUN5Y2xlID8gLyojX19QVVJFX18qLyBfanN4KFBhcmNlbCwge1xuICAgICAgICAgICAgY29uZmlnOiBsaWZlQ3ljbGUsXG4gICAgICAgICAgICBtb3VudFBhcmNlbDogbW91bnRQYXJjZWwsXG4gICAgICAgICAgICB3cmFwV2l0aDogXCJkaXZcIixcbiAgICAgICAgICAgIHdyYXBDbGFzc05hbWU6IGNsYXNzTmFtZXMoc3R5bGVzLndvcmtzcGFjZUNvbnRlbnQsIHtcbiAgICAgICAgICAgICAgICBbc3R5bGVzLmhpZGRlbkV4dHJhV29ya3NwYWNlXTogaGlkZUJlaGluZExlYWZcbiAgICAgICAgICAgIH0pLFxuICAgICAgICAgICAgLi4ucHJvcHNcbiAgICAgICAgfSwgb3BlbmVkV29ya3NwYWNlLndvcmtzcGFjZU5hbWUpIDogbGlmZUN5Y2xlID09PSBudWxsID8gLyojX19QVVJFX18qLyBfanN4KFwiZGl2XCIsIHtcbiAgICAgICAgICAgIGNsYXNzTmFtZTogY2xhc3NOYW1lcyhzdHlsZXMud29ya3NwYWNlQ29udGVudCwge1xuICAgICAgICAgICAgICAgIFtzdHlsZXMuaGlkZGVuRXh0cmFXb3Jrc3BhY2VdOiBoaWRlQmVoaW5kTGVhZlxuICAgICAgICAgICAgfSksXG4gICAgICAgICAgICBjaGlsZHJlbjogLyojX19QVVJFX18qLyBfanN4KElubGluZU5vdGlmaWNhdGlvbiwge1xuICAgICAgICAgICAgICAgIGtpbmQ6IFwiZXJyb3JcIixcbiAgICAgICAgICAgICAgICB0aXRsZTogZ2V0Q29yZVRyYW5zbGF0aW9uKCdlcnJvcicpLFxuICAgICAgICAgICAgICAgIHN1YnRpdGxlOiBnZXRDb3JlVHJhbnNsYXRpb24oJ3NvbWV0aGluZ1dlbnRXcm9uZ1RyeVJlbG9hZGluZycpLFxuICAgICAgICAgICAgICAgIGhpZGVDbG9zZUJ1dHRvbjogdHJ1ZVxuICAgICAgICAgICAgfSlcbiAgICAgICAgfSkgOiBudWxsLCBbXG4gICAgICAgIGxpZmVDeWNsZSxcbiAgICAgICAgb3BlbmVkV29ya3NwYWNlLndvcmtzcGFjZU5hbWUsXG4gICAgICAgIHByb3BzLFxuICAgICAgICBoaWRlQmVoaW5kTGVhZlxuICAgIF0pO1xuICAgIGlmICghcmVuZGVyQ2hyb21lKSB7XG4gICAgICAgIHJldHVybiBjb250ZW50ID8/IC8qI19fUFVSRV9fKi8gX2pzeChJbmxpbmVMb2FkaW5nLCB7XG4gICAgICAgICAgICBjbGFzc05hbWU6IGNsYXNzTmFtZXMoc3R5bGVzLmxvYWRlciwge1xuICAgICAgICAgICAgICAgIFtzdHlsZXMuaGlkZGVuRXh0cmFXb3Jrc3BhY2VdOiBoaWRlQmVoaW5kTGVhZlxuICAgICAgICAgICAgfSksXG4gICAgICAgICAgICBkZXNjcmlwdGlvbjogYCR7Z2V0Q29yZVRyYW5zbGF0aW9uKCdsb2FkaW5nJyl9YFxuICAgICAgICB9KTtcbiAgICB9XG4gICAgLy8gVGhlIG5vZGUgcmVtb3ZlZCBmcm9tIHRoZSB3b3Jrc3BhY2UgZ3JpZCBvbiBjbG9zZSBtdXN0IGdlbmVyYXRlIGEgYm94LiBXZWJLaXQgYmVmb3JlIFNhZmFyaSAyNi4yXG4gICAgLy8gZG9lc24ndCByZWxheW91dCB0aGUgZ3JpZCB3aGVuIHRoZSByZW1vdmVkIG5vZGUgaXMgdGhlIGBkaXNwbGF5OiBjb250ZW50c2Agb3V0ZXIgY29udGFpbmVyLCBzbyB0aGVcbiAgICAvLyBjbG9zZWQgd2luZG93IGtlZXBzIHRha2luZyB1cCBzcGFjZS4gaHR0cHM6Ly9idWdzLndlYmtpdC5vcmcvc2hvd19idWcuY2dpP2lkPTI5OTI1OFxuICAgIHJldHVybiAvKiNfX1BVUkVfXyovIF9qc3goXCJkaXZcIiwge1xuICAgICAgICBjaGlsZHJlbjogLyojX19QVVJFX18qLyBfanN4KFdvcmtzcGFjZUNocm9tZSwge1xuICAgICAgICAgICAgb3BlbmVkV29ya3NwYWNlOiBvcGVuZWRXb3Jrc3BhY2UsXG4gICAgICAgICAgICBvcGVuZWRXaW5kb3c6IG9wZW5lZFdpbmRvdyxcbiAgICAgICAgICAgIGlzUm9vdFdvcmtzcGFjZTogaXNSb290V29ya3NwYWNlLFxuICAgICAgICAgICAgc2hvd0FjdGlvbk1lbnU6IHNob3dBY3Rpb25NZW51LFxuICAgICAgICAgICAgY2xvc2VXaW5kb3c6ICgpPT5wcm9wcy5jbG9zZVdvcmtzcGFjZSh7XG4gICAgICAgICAgICAgICAgICAgIGNsb3NlV2luZG93OiB0cnVlXG4gICAgICAgICAgICAgICAgfSksXG4gICAgICAgICAgICBjaGlsZHJlbjogY29udGVudFxuICAgICAgICB9KVxuICAgIH0pO1xufTtcbi8qKlxuICogUmVuZGVycyB0aGUgY29udGFpbmVycywgdGl0bGUgYmFyIGFuZCB3aW5kb3cgYnV0dG9ucyBhcm91bmQgYSB3b3Jrc3BhY2UgaW4gdGhlIGdsb2JhbCB3b3Jrc3BhY2VcbiAqIHdpbmRvdyBzeXN0ZW0uXG4gKi8gY29uc3QgV29ya3NwYWNlQ2hyb21lID0gKHsgb3BlbmVkV29ya3NwYWNlLCBvcGVuZWRXaW5kb3csIGlzUm9vdFdvcmtzcGFjZSwgc2hvd0FjdGlvbk1lbnUsIGNsb3NlV2luZG93LCBjaGlsZHJlbiB9KT0+e1xuICAgIGNvbnN0IGxheW91dCA9IHVzZUxheW91dFR5cGUoKTtcbiAgICBjb25zdCB7IG9wZW5lZEdyb3VwLCBvcGVuZWRXaW5kb3dzLCByZWdpc3RlcmVkV2luZG93c0J5TmFtZSwgcmVnaXN0ZXJlZFdvcmtzcGFjZXNCeU5hbWUsIHJlZ2lzdGVyZWRHcm91cHNCeU5hbWUsIGlzTW9zdFJlY2VudGx5T3BlbmVkV2luZG93SGlkZGVuLCBzZXRXaW5kb3dNYXhpbWl6ZWQsIGhpZGVXaW5kb3cgfSA9IHVzZVdvcmtzcGFjZTJTdG9yZSgpO1xuICAgIGNvbnN0IHdpbmRvd05hbWUgPSBvcGVuZWRXaW5kb3cud2luZG93TmFtZTtcbiAgICBjb25zdCB7IG1heGltaXplZCB9ID0gb3BlbmVkV2luZG93O1xuICAgIGNvbnN0IHRpdGxlID0gb3BlbmVkV29ya3NwYWNlLnRpdGxlID8/ICcnO1xuICAgIGNvbnN0IHdpbmRvd0RlZiA9IHJlZ2lzdGVyZWRXaW5kb3dzQnlOYW1lW3dpbmRvd05hbWVdO1xuICAgIGNvbnN0IHdpZHRoID0gZ2V0T3BlbmVkV2luZG93V2lkdGgob3BlbmVkV2luZG93LCByZWdpc3RlcmVkV29ya3NwYWNlc0J5TmFtZSwgcmVnaXN0ZXJlZFdpbmRvd3NCeU5hbWUpO1xuICAgIGNvbnN0IGljb24gPSB3aW5kb3dEZWY/Lmljb247XG4gICAgY29uc3QgY2FuTWF4aW1pemUgPSB3aW5kb3dEZWY/LmNhbk1heGltaXplO1xuICAgIGNvbnN0IGNhbkNsb3NlR3JvdXAgPSBvcGVuZWRHcm91cCA/IHJlZ2lzdGVyZWRHcm91cHNCeU5hbWVbb3BlbmVkR3JvdXAuZ3JvdXBOYW1lXT8ucGVyc2lzdGVuY2UgPT09ICdjbG9zYWJsZScgOiBmYWxzZTtcbiAgICBjb25zdCBjYW5IaWRlID0gISFpY29uICYmICFjYW5DbG9zZUdyb3VwO1xuICAgIGNvbnN0IG9wZW5lZFdpbmRvd0luZGV4ID0gb3BlbmVkV2luZG93cy5maW5kSW5kZXgoKHcpPT53LndpbmRvd05hbWUgPT09IHdpbmRvd05hbWUpO1xuICAgIGNvbnN0IGlzV2luZG93SGlkZGVuID0gb3BlbmVkV2luZG93SW5kZXggPCBvcGVuZWRXaW5kb3dzLmxlbmd0aCAtIDEgfHwgaXNNb3N0UmVjZW50bHlPcGVuZWRXaW5kb3dIaWRkZW47XG4gICAgY29uc3QgaXNBY3Rpb25NZW51T3BlbmVkID0gT2JqZWN0LnZhbHVlcyhyZWdpc3RlcmVkV2luZG93c0J5TmFtZSkuc29tZSgod2luZG93KT0+d2luZG93Lmdyb3VwID09PSBvcGVuZWRHcm91cD8uZ3JvdXBOYW1lICYmIHdpbmRvdy5pY29uICE9PSB1bmRlZmluZWQpO1xuICAgIHJldHVybiAvKiNfX1BVUkVfXyovIF9qc3hzKFwiZGl2XCIsIHtcbiAgICAgICAgY2xhc3NOYW1lOiBjbGFzc05hbWVzKHN0eWxlcy53b3Jrc3BhY2VPdXRlckNvbnRhaW5lciwge1xuICAgICAgICAgICAgW3N0eWxlcy5uYXJyb3dXb3Jrc3BhY2VdOiB3aWR0aCA9PT0gJ25hcnJvdycsXG4gICAgICAgICAgICBbc3R5bGVzLndpZGVyV29ya3NwYWNlXTogd2lkdGggPT09ICd3aWRlcicsXG4gICAgICAgICAgICBbc3R5bGVzLmV4dHJhV2lkZVdvcmtzcGFjZV06IHdpZHRoID09PSAnZXh0cmEtd2lkZScsXG4gICAgICAgICAgICBbc3R5bGVzLmlzQWN0aW9uTWVudU9wZW5lZF06IGlzQWN0aW9uTWVudU9wZW5lZFxuICAgICAgICB9KSxcbiAgICAgICAgY2hpbGRyZW46IFtcbiAgICAgICAgICAgIC8qI19fUFVSRV9fKi8gX2pzeChcImRpdlwiLCB7XG4gICAgICAgICAgICAgICAgY2xhc3NOYW1lOiBjbGFzc05hbWVzKHN0eWxlcy53b3Jrc3BhY2VTcGFjZXIsIHtcbiAgICAgICAgICAgICAgICAgICAgW3N0eWxlcy5oaWRkZW5dOiBpc1dpbmRvd0hpZGRlblxuICAgICAgICAgICAgICAgIH0pXG4gICAgICAgICAgICB9KSxcbiAgICAgICAgICAgIC8qI19fUFVSRV9fKi8gX2pzeChcImRpdlwiLCB7XG4gICAgICAgICAgICAgICAgY2xhc3NOYW1lOiBjbGFzc05hbWVzKHN0eWxlcy53b3Jrc3BhY2VNaWRkbGVDb250YWluZXIsIHtcbiAgICAgICAgICAgICAgICAgICAgW3N0eWxlcy5tYXhpbWl6ZWRdOiBtYXhpbWl6ZWQsXG4gICAgICAgICAgICAgICAgICAgIFtzdHlsZXMuaGlkZGVuXTogaXNXaW5kb3dIaWRkZW4sXG4gICAgICAgICAgICAgICAgICAgIFtzdHlsZXMuaXNSb290V29ya3NwYWNlXTogaXNSb290V29ya3NwYWNlLFxuICAgICAgICAgICAgICAgICAgICBbc3R5bGVzLnNob3dBY3Rpb25NZW51XTogc2hvd0FjdGlvbk1lbnVcbiAgICAgICAgICAgICAgICB9KSxcbiAgICAgICAgICAgICAgICBjaGlsZHJlbjogLyojX19QVVJFX18qLyBfanN4KFwiZGl2XCIsIHtcbiAgICAgICAgICAgICAgICAgICAgY2xhc3NOYW1lOiBjbGFzc05hbWVzKHN0eWxlcy53b3Jrc3BhY2VJbm5lckNvbnRhaW5lciwge1xuICAgICAgICAgICAgICAgICAgICAgICAgW3N0eWxlcy5tYXhpbWl6ZWRdOiBtYXhpbWl6ZWQsXG4gICAgICAgICAgICAgICAgICAgICAgICBbc3R5bGVzLmhpZGRlbl06IGlzV2luZG93SGlkZGVuLFxuICAgICAgICAgICAgICAgICAgICAgICAgW3N0eWxlcy5pc1Jvb3RXb3Jrc3BhY2VdOiBpc1Jvb3RXb3Jrc3BhY2VcbiAgICAgICAgICAgICAgICAgICAgfSksXG4gICAgICAgICAgICAgICAgICAgIGNoaWxkcmVuOiBjaGlsZHJlbiA/IC8qI19fUFVSRV9fKi8gX2pzeHMoX0ZyYWdtZW50LCB7XG4gICAgICAgICAgICAgICAgICAgICAgICBjaGlsZHJlbjogW1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8qI19fUFVSRV9fKi8gX2pzeHMoSGVhZGVyLCB7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFwiYXJpYS1sYWJlbFwiOiBnZXRDb3JlVHJhbnNsYXRpb24oJ3dvcmtzcGFjZUhlYWRlcicpLFxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBjbGFzc05hbWU6IHN0eWxlcy5oZWFkZXIsXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNoaWxkcmVuOiBbXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAvKiNfX1BVUkVfXyovIF9qc3goSGVhZGVyTmFtZSwge1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHByZWZpeDogXCJcIixcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBjaGlsZHJlbjogdGl0bGVcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0pLFxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgLyojX19QVVJFX18qLyBfanN4KFwiZGl2XCIsIHtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBjbGFzc05hbWU6IHN0eWxlcy5vdmVybGF5SGVhZGVyU3BhY2VyXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB9KSxcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8qI19fUFVSRV9fKi8gX2pzeChIZWFkZXJHbG9iYWxCYXIsIHtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBjbGFzc05hbWU6IHN0eWxlcy5oZWFkZXJCdXR0b25zLFxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNoaWxkcmVuOiBpc0Rlc2t0b3AobGF5b3V0KSA/IC8qI19fUFVSRV9fKi8gX2pzeHMoX0ZyYWdtZW50LCB7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNoaWxkcmVuOiBbXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAoY2FuTWF4aW1pemUgfHwgbWF4aW1pemVkKSAmJiAvKiNfX1BVUkVfXyovIF9qc3goSGVhZGVyR2xvYmFsQWN0aW9uLCB7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgXCJhcmlhLWxhYmVsXCI6IG1heGltaXplZCA/IGdldENvcmVUcmFuc2xhdGlvbignbWluaW1pemUnKSA6IGdldENvcmVUcmFuc2xhdGlvbignbWF4aW1pemUnKSxcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBvbkNsaWNrOiAoKT0+c2V0V2luZG93TWF4aW1pemVkKHdpbmRvd05hbWUsICFtYXhpbWl6ZWQpLFxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNoaWxkcmVuOiBtYXhpbWl6ZWQgPyAvKiNfX1BVUkVfXyovIF9qc3goTWluaW1pemUsIHt9KSA6IC8qI19fUFVSRV9fKi8gX2pzeChNYXhpbWl6ZSwge30pXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB9KSxcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNhbkhpZGUgJiYgLyojX19QVVJFX18qLyBfanN4KEhlYWRlckdsb2JhbEFjdGlvbiwge1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFwiYXJpYS1sYWJlbFwiOiBnZXRDb3JlVHJhbnNsYXRpb24oJ2hpZGUnKSxcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBvbkNsaWNrOiAoKT0+aGlkZVdpbmRvdygpLFxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNoaWxkcmVuOiAvKiNfX1BVUkVfXyovIF9qc3goQXJyb3dSaWdodEljb24sIHt9KVxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgfSksXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAhY2FuQ2xvc2VHcm91cCAmJiAvKiNfX1BVUkVfXyovIF9qc3goSGVhZGVyR2xvYmFsQWN0aW9uLCB7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgXCJhcmlhLWxhYmVsXCI6IGdldENvcmVUcmFuc2xhdGlvbignY2xvc2UnKSxcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBvbkNsaWNrOiBjbG9zZVdpbmRvdyxcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBjaGlsZHJlbjogLyojX19QVVJFX18qLyBfanN4KENsb3NlSWNvbiwge30pXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB9KVxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBdXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgfSkgOiAvKiNfX1BVUkVfXyovIF9qc3hzKF9GcmFnbWVudCwge1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBjaGlsZHJlbjogW1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY2FuSGlkZSAmJiAvKiNfX1BVUkVfXyovIF9qc3goSGVhZGVyR2xvYmFsQWN0aW9uLCB7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgXCJhcmlhLWxhYmVsXCI6IGdldENvcmVUcmFuc2xhdGlvbignaGlkZScpLFxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIG9uQ2xpY2s6ICgpPT5oaWRlV2luZG93KCksXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY2hpbGRyZW46IC8qI19fUFVSRV9fKi8gX2pzeChEb3duVG9Cb3R0b20sIHt9KVxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgfSksXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAvKiNfX1BVUkVfXyovIF9qc3goSGVhZGVyR2xvYmFsQWN0aW9uLCB7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgXCJhcmlhLWxhYmVsXCI6IGdldENvcmVUcmFuc2xhdGlvbignY2xvc2UnKSxcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBvbkNsaWNrOiAoKT0+e1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBpZiAoY2FuQ2xvc2VHcm91cCkge1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdm9pZCBjbG9zZVdvcmtzcGFjZUdyb3VwMigpO1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY2xvc2VXaW5kb3coKTtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0sXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY2hpbGRyZW46IC8qI19fUFVSRV9fKi8gX2pzeChDbG9zZUljb24sIHt9KVxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgfSlcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgXVxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0pXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB9KVxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBdXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgfSksXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgY2hpbGRyZW5cbiAgICAgICAgICAgICAgICAgICAgICAgIF1cbiAgICAgICAgICAgICAgICAgICAgfSkgOiAvKiNfX1BVUkVfXyovIF9qc3goSW5saW5lTG9hZGluZywge1xuICAgICAgICAgICAgICAgICAgICAgICAgY2xhc3NOYW1lOiBzdHlsZXMubG9hZGVyLFxuICAgICAgICAgICAgICAgICAgICAgICAgZGVzY3JpcHRpb246IGAke2dldENvcmVUcmFuc2xhdGlvbignbG9hZGluZycpfSAuLi5gXG4gICAgICAgICAgICAgICAgICAgIH0pXG4gICAgICAgICAgICAgICAgfSlcbiAgICAgICAgICAgIH0pXG4gICAgICAgIF1cbiAgICB9KTtcbn07XG5leHBvcnQgZGVmYXVsdCBBY3RpdmVXb3Jrc3BhY2VXaW5kb3c7XG4iXSwibmFtZXMiOlsianN4IiwiX2pzeCIsImpzeHMiLCJfanN4cyIsIkZyYWdtZW50IiwiX0ZyYWdtZW50IiwiUmVhY3QiLCJ1c2VFZmZlY3QiLCJ1c2VNZW1vIiwidXNlUmVmIiwidXNlU3RhdGUiLCJjbGFzc05hbWVzIiwiUGFyY2VsIiwiSGVhZGVyIiwiSGVhZGVyR2xvYmFsQWN0aW9uIiwiSGVhZGVyR2xvYmFsQmFyIiwiSGVhZGVyTmFtZSIsIklubGluZUxvYWRpbmciLCJJbmxpbmVOb3RpZmljYXRpb24iLCJEb3duVG9Cb3R0b20iLCJNYXhpbWl6ZSIsIk1pbmltaXplIiwiY3JlYXRlUGFyY2VsTW91bnRlciIsIndvcmtzcGFjZTJTdG9yZSIsImlzRGVza3RvcCIsInVzZUxheW91dFR5cGUiLCJ1c2VTdG9yZSIsInJlcG9ydEVycm9yIiwibG9hZExpZmVDeWNsZXMiLCJnZXRDb3JlVHJhbnNsYXRpb24iLCJBcnJvd1JpZ2h0SWNvbiIsIkNsb3NlSWNvbiIsImNsb3NlV29ya3NwYWNlR3JvdXAyIiwiZ2V0T3BlbmVkV2luZG93V2lkdGgiLCJ1c2VXb3Jrc3BhY2UyU3RvcmUiLCJzdHlsZXMiLCJzZWxlY3RSZWdpc3RlcmVkV29ya3NwYWNlc0J5TmFtZSIsInN0YXRlIiwiQWN0aXZlV29ya3NwYWNlV2luZG93Iiwib3BlbmVkV2luZG93IiwiZ3JvdXBQcm9wcyIsImFjdGlvbnMiLCJyZW5kZXJDaHJvbWUiLCJzaG93QWN0aW9uTWVudSIsIm9wZW5lZFdvcmtzcGFjZXMiLCJsaWZlQ3ljbGVzQnlVdWlkIiwic2V0TGlmZUN5Y2xlc0J5VXVpZCIsInJlZ2lzdGVyZWRXb3Jrc3BhY2VzQnlOYW1lIiwicmVwb3J0ZWRGYWlsdXJlVXVpZHMiLCJTZXQiLCJjYW5jZWxsZWQiLCJQcm9taXNlIiwib3BlbmVkV29ya3NwYWNlIiwid29ya3NwYWNlRGVmIiwibW9kdWxlTmFtZSIsImNvbXBvbmVudCIsImVycm9yIiwiZW50cmllcyIsIk9iamVjdCIsImVudHJ5IiwiaSIsIkFjdGl2ZVdvcmtzcGFjZSIsIm1vdW50UGFyY2VsIiwibGlmZUN5Y2xlIiwiaXNSb290V29ya3NwYWNlIiwiaXNMZWFmV29ya3NwYWNlIiwicHJvcHMiLCJvcHRpb25zIiwiY2xvc2VXaW5kb3ciLCJkaXNjYXJkVW5zYXZlZENoYW5nZXMiLCJva1RvQ2xvc2VXb3Jrc3BhY2VzIiwiY2hpbGRXb3Jrc3BhY2VOYW1lIiwiY2hpbGRXb3Jrc3BhY2VQcm9wcyIsInBhcmVudFdvcmtzcGFjZU5hbWUiLCJwYXJlbnRJbmRleCIsInciLCJpc0xlYWYiLCJ3b3Jrc3BhY2VzQWJvdmVQYXJlbnQiLCJva1RvQ2xvc2UiLCJ0aXRsZSIsImhhc1Vuc2F2ZWRDaGFuZ2VzIiwiaGlkZUJlaGluZExlYWYiLCJjb250ZW50IiwiV29ya3NwYWNlQ2hyb21lIiwiY2hpbGRyZW4iLCJsYXlvdXQiLCJvcGVuZWRHcm91cCIsIm9wZW5lZFdpbmRvd3MiLCJyZWdpc3RlcmVkV2luZG93c0J5TmFtZSIsInJlZ2lzdGVyZWRHcm91cHNCeU5hbWUiLCJpc01vc3RSZWNlbnRseU9wZW5lZFdpbmRvd0hpZGRlbiIsInNldFdpbmRvd01heGltaXplZCIsImhpZGVXaW5kb3ciLCJ3aW5kb3dOYW1lIiwibWF4aW1pemVkIiwid2luZG93RGVmIiwid2lkdGgiLCJpY29uIiwiY2FuTWF4aW1pemUiLCJjYW5DbG9zZUdyb3VwIiwiY2FuSGlkZSIsIm9wZW5lZFdpbmRvd0luZGV4IiwiaXNXaW5kb3dIaWRkZW4iLCJpc0FjdGlvbk1lbnVPcGVuZWQiLCJ3aW5kb3ciLCJ1bmRlZmluZWQiXSwibWFwcGluZ3MiOiI7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7QUFBc0Y7QUFDbEI7QUFDaEM7QUFDUztBQUM4RTtBQUNwRDtBQUNRO0FBQ0Q7QUFDcEI7QUFDTDtBQUNVO0FBQ0Q7QUFDbUM7QUFDbkQ7QUFDOUMsdUZBQXVGO0FBQ3ZGLE1BQU1vQyxtQ0FBbUMsQ0FBQ0MsUUFBUUEsTUFBTSwwQkFBMEI7QUFDbEY7OztDQUdDLEdBQUcsTUFBTUMsd0JBQXdCLENBQUMsRUFBRUMsWUFBWSxFQUFFQyxVQUFVLEVBQUVDLE9BQU8sRUFBRUMsWUFBWSxFQUFFQyxjQUFjLEVBQUU7SUFDbEcsTUFBTSxFQUFFQyxnQkFBZ0IsRUFBRSxHQUFHTDtJQUM3Qiw4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\n//# sourceURL=webpack-internal:///../../framework/esm-styleguide/dist/workspaces2/active-workspace-window.component.js\n\n}");
835
835
 
836
836
  },
837
837
  "../../framework/esm-styleguide/dist/workspaces2/exported-workspace.component.js"(__unused_rspack_module, __webpack_exports__, __webpack_require__) {
@@ -4411,7 +4411,7 @@ eval("{__webpack_require__.r(__webpack_exports__);\n__webpack_require__.d(__webp
4411
4411
  },
4412
4412
  "../../framework/esm-api/dist/current-user.js"(__unused_rspack___webpack_module__, __webpack_exports__, __webpack_require__) {
4413
4413
  "use strict";
4414
- eval("{__webpack_require__.r(__webpack_exports__);\n__webpack_require__.d(__webpack_exports__, {\n clearCurrentUser: () => (clearCurrentUser),\n getCurrentUser: () => (getCurrentUser),\n getLoggedInUser: () => (getLoggedInUser),\n getSessionLocation: () => (getSessionLocation),\n getSessionStore: () => (getSessionStore),\n logout: () => (logout),\n refetchCurrentUser: () => (refetchCurrentUser),\n sessionStore: () => (sessionStore),\n setSessionLocale: () => (setSessionLocale),\n setSessionLocation: () => (setSessionLocation),\n setUserLanguage: () => (setUserLanguage),\n setUserProperties: () => (setUserProperties),\n userHasAccess: () => (userHasAccess),\n verifyTotpCode: () => (verifyTotpCode)\n});\n/* import */ var _openmrs_esm_error_handling__rspack_import_0 = __webpack_require__(\"../../framework/esm-error-handling/dist/index.js\");\n/* import */ var _openmrs_esm_state__rspack_import_1 = __webpack_require__(\"../../framework/esm-state/dist/index.js\");\n/* import */ var lodash_es__rspack_import_3 = __webpack_require__(\"../../../node_modules/lodash-es/isUndefined.js\");\n/* import */ var _openmrs_fetch_js__rspack_import_2 = __webpack_require__(\"../../framework/esm-api/dist/openmrs-fetch.js\");\n/** @module @category API */ \n\n\n\n/** @internal */ const sessionStore = (0,_openmrs_esm_state__rspack_import_1.createGlobalStore)('session', {\n loaded: false,\n session: null\n});\n/**\n * The upper bound on how old the session handed to a reader may be. It is measured from the moment a\n * fetch is *started*, not from the moment its response lands, so the session a reader sees is always\n * strictly newer than this.\n */ const sessionMaxAgeMillis = 60 * 1000;\nlet lastFetchTimeMillis = 0;\n/**\n * How long after the first session fetch a 502 is taken to mean that the backend is still starting up. A\n * gateway answers with a 502 until the backend has deployed, which can take a few minutes after a restart.\n */ const startupGracePeriodMillis = 3 * 60 * 1000;\nlet firstFetchTimeMillis;\nlet inFlightRefresh = null;\n/**\n * Fetches the session if the store is unloaded or its session is older than `sessionMaxAgeMillis`.\n * Returns `null` only when the store already holds a session fresh enough to be read as-is, so a\n * caller that gets a promise back must wait for it rather than read the store.\n *\n * A fetch already in flight is joined rather than duplicated. This is what keeps `sessionMaxAgeMillis`\n * an upper bound: while a fetch is running, the store still holds the previous session, and returning\n * that would hand back data older than the bound allows.\n *\n * The returned promise rejects if the fetch fails, but the rejection is already handled and reported,\n * so a caller that only needs the fetch started can ignore it.\n */ function refreshSessionIfStale() {\n if (inFlightRefresh) {\n return inFlightRefresh;\n }\n if (sessionStore.getState().loaded && lastFetchTimeMillis >= Date.now() - sessionMaxAgeMillis) {\n return null;\n }\n return refetchCurrentUser();\n}\nfunction getCurrentUser(opts) {\n const includeAuthStatus = opts?.includeAuthStatus ?? true;\n const select = (session)=>includeAuthStatus ? session : session.user;\n const refresh = refreshSessionIfStale();\n if (!refresh) {\n return Promise.resolve(select(sessionStore.getState().session));\n }\n return new Promise((resolve)=>{\n const resolveIfLoaded = ()=>{\n const state = sessionStore.getState();\n if (state.loaded) {\n unsubscribe();\n resolve(select(state.session));\n }\n };\n const unsubscribe = sessionStore.subscribe(resolveIfLoaded);\n // A failed refresh keeps an already-loaded session without updating the store, so the\n // subscription alone would never fire.\n refresh.then(resolveIfLoaded, resolveIfLoaded);\n });\n}\n\n/**\n * Returns the global session store containing the current user's session information.\n * If the session data is stale (older than 1 minute) or not yet loaded, this function\n * will trigger a refetch of the current user's session.\n *\n * @returns The global session store that can be subscribed to for session updates.\n *\n * @example\n * ```ts\n * import { getSessionStore } from '@openmrs/esm-api';\n * const store = getSessionStore();\n * const unsubscribe = store.subscribe((state) => {\n * if (state.loaded) {\n * console.log('Session:', state.session);\n * }\n * });\n * ```\n */ function getSessionStore() {\n refreshSessionIfStale();\n return sessionStore;\n}\n// NB locale is string only if this returns true\nfunction isValidLocale(locale) {\n if (locale === undefined || typeof locale !== 'string') {\n return false;\n }\n try {\n new Intl.Locale(locale);\n } catch (e) {\n return false;\n }\n return true;\n}\n/**\n * Sets the document's language attribute based on the user's locale preference\n * from the session data. This affects the HTML `lang` attribute which is used\n * for accessibility and internationalization.\n *\n * The locale is determined from either the session's locale or the user's\n * default locale property. Underscores in the locale are converted to hyphens\n * to match BCP 47 language tag format.\n *\n * @param data The session object containing locale information.\n */ function setUserLanguage(data) {\n let locale = data.locale ?? data.user?.userProperties?.defaultLocale;\n // Only underscores are converted here, deliberately, rather than reusing `toLanguageTag`. i18next\n // reads this value back off `document.lang` and uses it as the translation bundle key, and those\n // bundles are named with the POSIX form (`uz@Latn.json`), so converting `@` would send the loader\n // after a bundle that does not exist.\n if (locale && locale.includes('_')) {\n locale = locale.replaceAll('_', '-');\n }\n if (isValidLocale(locale) && locale !== document.documentElement.getAttribute('lang')) {\n document.documentElement.setAttribute('lang', locale);\n }\n}\nsessionStore.subscribe((state)=>{\n if (state.loaded && state.session) {\n setUserLanguage(state.session);\n }\n});\nfunction userHasPrivilege(requiredPrivilege, user) {\n if (typeof requiredPrivilege === 'string') {\n return !(0,lodash_es__rspack_import_3[\"default\"])(user.privileges.find((p)=>requiredPrivilege === p.display));\n } else if (Array.isArray(requiredPrivilege)) {\n return requiredPrivilege.every((rp)=>!(0,lodash_es__rspack_import_3[\"default\"])(user.privileges.find((p)=>rp === p.display)));\n } else if (!(0,lodash_es__rspack_import_3[\"default\"])(requiredPrivilege)) {\n console.error(`Could not understand privileges \"${requiredPrivilege}\"`);\n }\n return true;\n}\nfunction isSuperUser(user) {\n return !(0,lodash_es__rspack_import_3[\"default\"])(user.roles.find((role)=>role.display === 'System Developer'));\n}\n/**\n * The `refetchCurrentUser` function causes a network request to redownload\n * the user. All subscribers to the session store will be notified of the\n * new user once the new version of the user object is downloaded.\n *\n * If the server rejects the request as unauthenticated (401 or 403), the store records a\n * logged-out session. If the request fails for any other reason, a session that has already\n * loaded is kept; otherwise the store records the error.\n *\n * @returns A Promise resolving to the updated session store state. It rejects with the\n * store state if the request fails for a reason other than authentication.\n *\n * @example\n * ```js\n * import { refetchCurrentUser } from '@openmrs/esm-api'\n * refetchCurrentUser()\n * ```\n */ function refetchCurrentUser(username, password) {\n lastFetchTimeMillis = Date.now();\n firstFetchTimeMillis ?? (firstFetchTimeMillis = lastFetchTimeMillis);\n let headers = {};\n if (username && password) {\n headers['Authorization'] = `Basic ${window.btoa(`${username}:${password}`)}`;\n }\n const refresh = handleSessionResponse((0,_openmrs_fetch_js__rspack_import_2.openmrsFetch)(_openmrs_fetch_js__rspack_import_2.sessionEndpoint, {\n headers,\n rejectAuthFailure: true\n }));\n // Publish the request so that readers can wait on it instead of reading the session it is about to\n // replace. Each call still issues its own request; this only tracks the most recent one.\n const clear = ()=>{\n if (inFlightRefresh === refresh) {\n inFlightRefresh = null;\n }\n };\n refresh.then(clear, clear);\n inFlightRefresh = refresh;\n return refresh;\n}\n/**\n * Clears the current user session from the session store, setting the session\n * to an unauthenticated state. This is typically called during logout to reset\n * the application's authentication state.\n *\n * @example\n * ```ts\n * import { clearCurrentUser } from '@openmrs/esm-api';\n * // During logout\n * clearCurrentUser();\n * ```\n */ function clearCurrentUser() {\n sessionStore.setState({\n loaded: true,\n session: {\n authenticated: false,\n sessionId: ''\n }\n }, true);\n}\n/**\n * Checks whether the given user has access based on the required privilege(s).\n * A user has access if they have the required privilege(s) or if they are a\n * \"System Developer\" (super user). If no privilege is required, access is granted.\n *\n * @param requiredPrivilege A single privilege string or an array of privilege strings\n * that the user must have. If an array is provided, the user must have ALL privileges.\n * @param user The user object containing their privileges and roles.\n * @returns `true` if the user has access, `false` otherwise. Returns `true` if no\n * privilege is required, and `false` if the user is undefined but a privilege is required.\n *\n * @example\n * ```ts\n * import { userHasAccess } from '@openmrs/esm-api';\n * const hasAccess = userHasAccess('View Patients', currentUser);\n * const hasMultipleAccess = userHasAccess(['View Patients', 'Edit Patients'], currentUser);\n * ```\n */ function userHasAccess(requiredPrivilege, user) {\n if (user === undefined) {\n // if the user hasn't been loaded, then return false iff there is a required privilege\n return !Boolean(requiredPrivilege);\n }\n if (!Boolean(requiredPrivilege)) {\n // if user exists but no requiredPrivilege is defined\n return true;\n }\n return userHasPrivilege(requiredPrivilege, user) || isSuperUser(user);\n}\n/**\n * Returns a Promise that resolves with the currently logged-in user object.\n * If the user is already loaded in the session store, the Promise resolves immediately.\n * Otherwise, it subscribes to the session store and resolves when a logged-in user\n * becomes available.\n *\n * @returns A Promise that resolves with the LoggedInUser object once available.\n *\n * @example\n * ```ts\n * import { getLoggedInUser } from '@openmrs/esm-api';\n * const user = await getLoggedInUser();\n * console.log('Logged in as:', user.display);\n * ```\n */ function getLoggedInUser() {\n let user;\n let unsubscribe;\n return new Promise((res)=>{\n const handler = (state)=>{\n if (state.loaded && state.session.user) {\n user = state.session.user;\n res(state.session.user);\n if (unsubscribe) {\n unsubscribe();\n }\n }\n };\n handler(sessionStore.getState());\n if (!user) {\n unsubscribe = sessionStore.subscribe(handler);\n }\n });\n}\n/**\n * Returns a Promise that resolves with the current session location, if one is set.\n * The session location represents the physical location where the user is currently\n * working (e.g., a clinic or ward).\n *\n * @returns A Promise that resolves with the SessionLocation object, or `undefined`\n * if no session location is set.\n *\n * @example\n * ```ts\n * import { getSessionLocation } from '@openmrs/esm-api';\n * const location = await getSessionLocation();\n * if (location) {\n * console.log('Current location:', location.display);\n * }\n * ```\n */ async function getSessionLocation() {\n const session = await getCurrentUser();\n return session.sessionLocation;\n}\n/**\n * Sets the session location for the current user. The session location represents\n * the physical location where the user is working (e.g., a clinic or ward).\n * This triggers a server request to update the session and refreshes the local\n * session store.\n *\n * @param locationUuid The UUID of the location to set as the session location.\n * @param abortController An AbortController to allow cancellation of the request.\n * @returns A Promise that resolves with the updated SessionStore.\n *\n * @example\n * ```ts\n * import { setSessionLocation } from '@openmrs/esm-api';\n * const abortController = new AbortController();\n * await setSessionLocation('location-uuid-here', abortController);\n * ```\n */ async function setSessionLocation(locationUuid, abortController) {\n return handleSessionResponse((0,_openmrs_fetch_js__rspack_import_2.openmrsFetch)(_openmrs_fetch_js__rspack_import_2.sessionEndpoint, {\n method: 'POST',\n body: {\n sessionLocation: locationUuid\n },\n headers: {\n 'Content-Type': 'application/json'\n },\n rejectAuthFailure: true,\n signal: abortController?.signal\n }));\n}\n/**\n * Sets the locale for the current session only, leaving the user's default locale unchanged.\n * Use {@link setUserProperties} with a `defaultLocale` property to change the default instead.\n *\n * @param locale The locale in Java's `Locale#toString()` form, e.g. `en_GB`.\n * @param abortController Optional AbortController to allow cancellation of the request.\n * @returns A Promise that resolves with the updated SessionStore after refetching the current user.\n * It rejects with an {@link OpenmrsFetchError} if the server does not accept the locale.\n *\n * @example\n * ```ts\n * import { setSessionLocale } from '@openmrs/esm-api';\n * await setSessionLocale('fr');\n * ```\n *\n * @internal\n */ async function setSessionLocale(locale, abortController) {\n await (0,_openmrs_fetch_js__rspack_import_2.openmrsFetch)(_openmrs_fetch_js__rspack_import_2.sessionEndpoint, {\n method: 'POST',\n body: {\n locale\n },\n headers: {\n 'Content-Type': 'application/json'\n },\n signal: abortController?.signal\n });\n return refetchCurrentUser();\n}\n/**\n * Updates the user properties for a specific user. User properties are key-value\n * pairs that store user-specific settings and preferences. After updating the\n * properties on the server, the current user session is refetched to reflect\n * the changes.\n *\n * @param userUuid The UUID of the user whose properties should be updated.\n * @param userProperties An object containing the properties to set or update.\n * @param abortController Optional AbortController to allow cancellation of the request.\n * If not provided, a new AbortController is created.\n * @returns A Promise that resolves with the updated SessionStore after refetching\n * the current user.\n *\n * @example\n * ```ts\n * import { getLoggedInUser, setUserProperties } from '@openmrs/esm-api';\n * const user = await getLoggedInUser();\n * await setUserProperties(user.uuid, {\n * defaultLocale: 'en_GB',\n * customSetting: 'value'\n * });\n * ```\n */ async function setUserProperties(userUuid, userProperties, abortController) {\n if (!abortController) {\n abortController = new AbortController();\n }\n await (0,_openmrs_fetch_js__rspack_import_2.openmrsFetch)(`${_openmrs_fetch_js__rspack_import_2.restBaseUrl}/user/${userUuid}`, {\n method: 'POST',\n body: {\n userProperties\n },\n headers: {\n 'Content-Type': 'application/json'\n },\n signal: abortController.signal\n });\n return refetchCurrentUser();\n}\n/**\n * Submits a TOTP code to complete a two-factor login challenge. When the code is accepted, the\n * session store is refreshed with the now-authenticated session.\n *\n * @param code The code from the user's authenticator app.\n * @param rememberDevice Whether the server should skip the challenge on this device in future.\n * @returns A Promise resolving to the session. Its `authenticated` property is `false` if the\n * code was not accepted. It rejects with an {@link OpenmrsFetchError} if the server rejects the\n * request, in which case `responseBody` may explain why.\n *\n * @example\n * ```ts\n * import { verifyTotpCode } from '@openmrs/esm-api';\n * const session = await verifyTotpCode('123456', true);\n * ```\n *\n * @internal\n */ async function verifyTotpCode(code, rememberDevice = false) {\n const response = await (0,_openmrs_fetch_js__rspack_import_2.openmrsFetch)(rememberDevice ? `${_openmrs_fetch_js__rspack_import_2.sessionEndpoint}?rememberMe=true` : _openmrs_fetch_js__rspack_import_2.sessionEndpoint, {\n headers: {\n 'X-Totp-Code': code\n }\n });\n if (response.data?.authenticated) {\n // `refetchCurrentUser` only resolves once the store holds a session.\n const store = await refetchCurrentUser();\n return store.session;\n }\n return response.data;\n}\n/**\n * Ends the current session on the server and records a logged-out session in the session store.\n * A server that has already ended the session (401 or 403) counts as a successful logout.\n *\n * Other data cached for the logged-in user, such as SWR caches, is the caller's to clear.\n *\n * @returns A Promise that resolves once the session store holds a logged-out session.\n *\n * @example\n * ```ts\n * import { logout } from '@openmrs/esm-api';\n * await logout();\n * ```\n *\n * @internal\n */ async function logout() {\n try {\n await (0,_openmrs_fetch_js__rspack_import_2.openmrsFetch)(_openmrs_fetch_js__rspack_import_2.sessionEndpoint, {\n method: 'DELETE',\n rejectAuthFailure: true\n });\n } catch (err) {\n if (!isAuthFailure(err)) {\n throw err;\n }\n }\n clearCurrentUser();\n // The session just cleared is already correct, so a failed refresh loses nothing.\n await refetchCurrentUser().catch(()=>{});\n}\nfunction handleSessionResponse(result) {\n return new Promise((resolve, reject)=>{\n result.then((res)=>{\n if (typeof res?.data === 'object') {\n const nextState = {\n loaded: true,\n session: res.data\n };\n sessionStore.setState(nextState, true);\n resolve(nextState);\n } else if (isInitialSetupRedirect(res)) {\n reject(recordSessionFailure(Error('The server is still starting up'), true));\n } else {\n reject(recordSessionFailure(Error('The session endpoint did not respond with a session')));\n }\n }).catch((err)=>{\n // An auth failure is the session endpoint's answer for \"not logged in\", not a failed lookup.\n if (isAuthFailure(err)) {\n if (isUnauthenticatedSession(err.responseBody)) {\n sessionStore.setState({\n loaded: true,\n session: err.responseBody\n }, true);\n } else {\n clearCurrentUser();\n }\n resolve(sessionStore.getState());\n return;\n }\n if (isGatewayErrorDuringStartup(err)) {\n reject(recordSessionFailure(err, true));\n return;\n }\n (0,_openmrs_esm_error_handling__rspack_import_0.reportError)(`Failed to fetch new session information: ${err}`);\n reject(recordSessionFailure(err));\n });\n });\n}\nfunction isAuthFailure(err) {\n return err instanceof _openmrs_fetch_js__rspack_import_2.OpenmrsFetchError && (err.response.status === 401 || err.response.status === 403);\n}\n/**\n * Until the backend has finished its initial setup, it answers every request with a redirect to its\n * setup page, which `fetch()` follows, so the session request resolves with that page's HTML.\n */ function isInitialSetupRedirect(res) {\n if (!res?.redirected || !res.url) {\n return false;\n }\n try {\n return new URL(res.url, window.location.href).pathname.replace(/\\/+$/, '').endsWith('/initialsetup');\n } catch {\n return false;\n }\n}\nfunction isGatewayErrorDuringStartup(err) {\n return err instanceof _openmrs_fetch_js__rspack_import_2.OpenmrsFetchError && err.response.status === 502 && !sessionStore.getState().loaded && firstFetchTimeMillis !== undefined && Date.now() - firstFetchTimeMillis < startupGracePeriodMillis;\n}\nfunction isUnauthenticatedSession(body) {\n return typeof body === 'object' && body !== null && body.authenticated === false;\n}\n/**\n * A session that has already loaded is kept when a later fetch fails, since it is still the best answer\n * available. With nothing to fall back on, the error is recorded so the app shell can show an error page.\n */ function recordSessionFailure(err, initializing = false) {\n if (!sessionStore.getState().loaded) {\n sessionStore.setState({\n loaded: false,\n session: null,\n error: err instanceof Error ? err : Error(String(err)),\n initializing\n }, true);\n }\n return sessionStore.getState();\n}\n\n//# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiamF2YXNjcmlwdC9lc218YnVpbHRpbjpzd2MtbG9hZGVyPz9ydWxlU2V0WzFdLnJ1bGVzWzVdLnVzZVswXSEvaG9tZS9ydW5uZXIvd29yay9vcGVubXJzLWVzbS1jb3JlL29wZW5tcnMtZXNtLWNvcmUvcGFja2FnZXMvZnJhbWV3b3JrL2VzbS1hcGkvZGlzdC9jdXJyZW50LXVzZXIuanMiLCJzb3VyY2VzIjpbIndlYnBhY2s6Ly9Ab3Blbm1ycy9lc20tYXBwLXNoZWxsLy4uLy4uL2ZyYW1ld29yay9lc20tYXBpL2Rpc3QvY3VycmVudC11c2VyLmpzPzcxMjkiXSwic291cmNlc0NvbnRlbnQiOlsiLyoqIEBtb2R1bGUgQGNhdGVnb3J5IEFQSSAqLyBpbXBvcnQgeyByZXBvcnRFcnJvciB9IGZyb20gXCJAb3Blbm1ycy9lc20tZXJyb3ItaGFuZGxpbmdcIjtcbmltcG9ydCB7IGNyZWF0ZUdsb2JhbFN0b3JlIH0gZnJvbSBcIkBvcGVubXJzL2VzbS1zdGF0ZVwiO1xuaW1wb3J0IHsgaXNVbmRlZmluZWQgfSBmcm9tIFwibG9kYXNoLWVzXCI7XG5pbXBvcnQgeyBPcGVubXJzRmV0Y2hFcnJvciwgb3Blbm1yc0ZldGNoLCByZXN0QmFzZVVybCwgc2Vzc2lvbkVuZHBvaW50IH0gZnJvbSBcIi4vb3Blbm1ycy1mZXRjaC5qc1wiO1xuLyoqIEBpbnRlcm5hbCAqLyBleHBvcnQgY29uc3Qgc2Vzc2lvblN0b3JlID0gY3JlYXRlR2xvYmFsU3RvcmUoJ3Nlc3Npb24nLCB7XG4gICAgbG9hZGVkOiBmYWxzZSxcbiAgICBzZXNzaW9uOiBudWxsXG59KTtcbi8qKlxuICogVGhlIHVwcGVyIGJvdW5kIG9uIGhvdyBvbGQgdGhlIHNlc3Npb24gaGFuZGVkIHRvIGEgcmVhZGVyIG1heSBiZS4gSXQgaXMgbWVhc3VyZWQgZnJvbSB0aGUgbW9tZW50IGFcbiAqIGZldGNoIGlzICpzdGFydGVkKiwgbm90IGZyb20gdGhlIG1vbWVudCBpdHMgcmVzcG9uc2UgbGFuZHMsIHNvIHRoZSBzZXNzaW9uIGEgcmVhZGVyIHNlZXMgaXMgYWx3YXlzXG4gKiBzdHJpY3RseSBuZXdlciB0aGFuIHRoaXMuXG4gKi8gY29uc3Qgc2Vzc2lvbk1heEFnZU1pbGxpcyA9IDYwICogMTAwMDtcbmxldCBsYXN0RmV0Y2hUaW1lTWlsbGlzID0gMDtcbi8qKlxuICogSG93IGxvbmcgYWZ0ZXIgdGhlIGZpcnN0IHNlc3Npb24gZmV0Y2ggYSA1MDIgaXMgdGFrZW4gdG8gbWVhbiB0aGF0IHRoZSBiYWNrZW5kIGlzIHN0aWxsIHN0YXJ0aW5nIHVwLiBBXG4gKiBnYXRld2F5IGFuc3dlcnMgd2l0aCBhIDUwMiB1bnRpbCB0aGUgYmFja2VuZCBoYXMgZGVwbG95ZWQsIHdoaWNoIGNhbiB0YWtlIGEgZmV3IG1pbnV0ZXMgYWZ0ZXIgYSByZXN0YXJ0LlxuICovIGNvbnN0IHN0YXJ0dXBHcmFjZVBlcmlvZE1pbGxpcyA9IDMgKiA2MCAqIDEwMDA7XG5sZXQgZmlyc3RGZXRjaFRpbWVNaWxsaXM7XG5sZXQgaW5GbGlnaHRSZWZyZXNoID0gbnVsbDtcbi8qKlxuICogRmV0Y2hlcyB0aGUgc2Vzc2lvbiBpZiB0aGUgc3RvcmUgaXMgdW5sb2FkZWQgb3IgaXRzIHNlc3Npb24gaXMgb2xkZXIgdGhhbiBgc2Vzc2lvbk1heEFnZU1pbGxpc2AuXG4gKiBSZXR1cm5zIGBudWxsYCBvbmx5IHdoZW4gdGhlIHN0b3JlIGFscmVhZHkgaG9sZHMgYSBzZXNzaW9uIGZyZXNoIGVub3VnaCB0byBiZSByZWFkIGFzLWlzLCBzbyBhXG4gKiBjYWxsZXIgdGhhdCBnZXRzIGEgcHJvbWlzZSBiYWNrIG11c3Qgd2FpdCBmb3IgaXQgcmF0aGVyIHRoYW4gcmVhZCB0aGUgc3RvcmUuXG4gKlxuICogQSBmZXRjaCBhbHJlYWR5IGluIGZsaWdodCBpcyBqb2luZWQgcmF0aGVyIHRoYW4gZHVwbGljYXRlZC4gVGhpcyBpcyB3aGF0IGtlZXBzIGBzZXNzaW9uTWF4QWdlTWlsbGlzYFxuICogYW4gdXBwZXIgYm91bmQ6IHdoaWxlIGEgZmV0Y2ggaXMgcnVubmluZywgdGhlIHN0b3JlIHN0aWxsIGhvbGRzIHRoZSBwcmV2aW91cyBzZXNzaW9uLCBhbmQgcmV0dXJuaW5nXG4gKiB0aGF0IHdvdWxkIGhhbmQgYmFjayBkYXRhIG9sZGVyIHRoYW4gdGhlIGJvdW5kIGFsbG93cy5cbiAqXG4gKiBUaGUgcmV0dXJuZWQgcHJvbWlzZSByZWplY3RzIGlmIHRoZSBmZXRjaCBmYWlscywgYnV0IHRoZSByZWplY3Rpb24gaXMgYWxyZWFkeSBoYW5kbGVkIGFuZCByZXBvcnRlZCxcbiAqIHNvIGEgY2FsbGVyIHRoYXQgb25seSBuZWVkcyB0aGUgZmV0Y2ggc3RhcnRlZCBjYW4gaWdub3JlIGl0LlxuICovIGZ1bmN0aW9uIHJlZnJlc2hTZXNzaW9uSWZTdGFsZSgpIHtcbiAgICBpZiAoaW5GbGlnaHRSZWZyZXNoKSB7XG4gICAgICAgIHJldHVybiBpbkZsaWdodFJlZnJlc2g7XG4gICAgfVxuICAgIGlmIChzZXNzaW9uU3RvcmUuZ2V0U3RhdGUoKS5sb2FkZWQgJiYgbGFzdEZldGNoVGltZU1pbGxpcyA+PSBEYXRlLm5vdygpIC0gc2Vzc2lvbk1heEFnZU1pbGxpcykge1xuICAgICAgICByZXR1cm4gbnVsbDtcbiAgICB9XG4gICAgcmV0dXJuIHJlZmV0Y2hDdXJyZW50VXNlcigpO1xufVxuZnVuY3Rpb24gZ2V0Q3VycmVudFVzZXIob3B0cykge1xuICAgIGNvbnN0IGluY2x1ZGVBdXRoU3RhdHVzID0gb3B0cz8uaW5jbHVkZUF1dGhTdGF0dXMgPz8gdHJ1ZTtcbiAgICBjb25zdCBzZWxlY3QgPSAoc2Vzc2lvbik9PmluY2x1ZGVBdXRoU3RhdHVzID8gc2Vzc2lvbiA6IHNlc3Npb24udXNlcjtcbiAgICBjb25zdCByZWZyZXNoID0gcmVmcmVzaFNlc3Npb25JZlN0YWxlKCk7XG4gICAgaWYgKCFyZWZyZXNoKSB7XG4gICAgICAgIHJldHVybiBQcm9taXNlLnJlc29sdmUoc2VsZWN0KHNlc3Npb25TdG9yZS5nZXRTdGF0ZSgpLnNlc3Npb24pKTtcbiAgICB9XG4gICAgcmV0dXJuIG5ldyBQcm9taXNlKChyZXNvbHZlKT0+e1xuICAgICAgICBjb25zdCByZXNvbHZlSWZMb2FkZWQgPSAoKT0+e1xuICAgICAgICAgICAgY29uc3Qgc3RhdGUgPSBzZXNzaW9uU3RvcmUuZ2V0U3RhdGUoKTtcbiAgICAgICAgICAgIGlmIChzdGF0ZS5sb2FkZWQpIHtcbiAgICAgICAgICAgICAgICB1bnN1YnNjcmliZSgpO1xuICAgICAgICAgICAgICAgIHJlc29sdmUoc2VsZWN0KHN0YXRlLnNlc3Npb24pKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgfTtcbiAgICAgICAgY29uc3QgdW5zdWJzY3JpYmUgPSBzZXNzaW9uU3RvcmUuc3Vic2NyaWJlKHJlc29sdmVJZkxvYWRlZCk7XG4gICAgICAgIC8vIEEgZmFpbGVkIHJlZnJlc2gga2VlcHMgYW4gYWxyZWFkeS1sb2FkZWQgc2Vzc2lvbiB3aXRob3V0IHVwZGF0aW5nIHRoZSBzdG9yZSwgc28gdGhlXG4gICAgICAgIC8vIHN1YnNjcmlwdGlvbiBhbG9uZSB3b3VsZCBuZXZlciBmaXJlLlxuICAgICAgICByZWZyZXNoLnRoZW4ocmVzb2x2ZUlmTG9hZGVkLCByZXNvbHZlSWZMb2FkZWQpO1xuICAgIH0pO1xufVxuZXhwb3J0IHsgZ2V0Q3VycmVudFVzZXIgfTtcbi8qKlxuICogUmV0dXJucyB0aGUgZ2xvYmFsIHNlc3Npb24gc3RvcmUgY29udGFpbmluZyB0aGUgY3VycmVudCB1c2VyJ3Mgc2Vzc2lvbiBpbmZvcm1hdGlvbi5cbiAqIElmIHRoZSBzZXNzaW9uIGRhdGEgaXMgc3RhbGUgKG9sZGVyIHRoYW4gMSBtaW51dGUpIG9yIG5vdCB5ZXQgbG9hZGVkLCB0aGlzIGZ1bmN0aW9uXG4gKiB3aWxsIHRyaWdnZXIgYSByZWZldGNoIG9mIHRoZSBjdXJyZW50IHVzZXIncyBzZXNzaW9uLlxuICpcbiAqIEByZXR1cm5zIFRoZSBnbG9iYWwgc2Vzc2lvbiBzdG9yZSB0aGF0IGNhbiBiZSBzdWJzY3JpYmVkIHRvIGZvciBzZXNzaW9uIHVwZGF0ZXMuXG4gKlxuICogQGV4YW1wbGVcbiAqIGBgYHRzXG4gKiBpbXBvcnQgeyBnZXRTZXNzaW9uU3RvcmUgfSBmcm9tICdAb3Blbm1ycy9lc20tYXBpJztcbiAqIGNvbnN0IHN0b3JlID0gZ2V0U2Vzc2lvblN0b3JlKCk7XG4gKiBjb25zdCB1bnN1YnNjcmliZSA9IHN0b3JlLnN1YnNjcmliZSgoc3RhdGUpID0+IHtcbiAqICAgaWYgKHN0YXRlLmxvYWRlZCkge1xuICogICAgIGNvbnNvbGUubG9nKCdTZXNzaW9uOicsIHN0YXRlLnNlc3Npb24pO1xuICogICB9XG4gKiB9KTtcbiAqIGBgYFxuICovIGV4cG9ydCBmdW5jdGlvbiBnZXRTZXNzaW9uU3RvcmUoKSB7XG4gICAgcmVmcmVzaFNlc3Npb25JZlN0YWxlKCk7XG4gICAgcmV0dXJuIHNlc3Npb25TdG9yZTtcbn1cbi8vIE5CIGxvY2FsZSBpcyBzdHJpbmcgb25seSBpZiB0aGlzIHJldHVybnMgdHJ1ZVxuZnVuY3Rpb24gaXNWYWxpZExvY2FsZShsb2NhbGUpIHtcbiAgICBpZiAobG9jYWxlID09PSB1bmRlZmluZWQgfHwgdHlwZW9mIGxvY2FsZSAhPT0gJ3N0cmluZycpIHtcbiAgICAgICAgcmV0dXJuIGZhbHNlO1xuICAgIH1cbiAgICB0cnkge1xuICAgICAgICBuZXcgSW50bC5Mb2NhbGUobG9jYWxlKTtcbiAgICB9IGNhdGNoIChlKSB7XG4gICAgICAgIHJldHVybiBmYWxzZTtcbiAgICB9XG4gICAgcmV0dXJuIHRydWU7XG59XG4vKipcbiAqIFNldHMgdGhlIGRvY3VtZW50J3MgbGFuZ3VhZ2UgYXR0cmlidXRlIGJhc2VkIG9uIHRoZSB1c2VyJ3MgbG9jYWxlIHByZWZlcmVuY2VcbiAqIGZyb20gdGhlIHNlc3Npb24gZGF0YS4gVGhpcyBhZmZlY3RzIHRoZSBIVE1MIGBsYW5nYCBhdHRyaWJ1dGUgd2hpY2ggaXMgdXNlZFxuICogZm9yIGFjY2Vzc2liaWxpdHkgYW5kIGludGVybmF0aW9uYWxpemF0aW9uLlxuICpcbiAqIFRoZSBsb2NhbGUgaXMgZGV0ZXJtaW5lZCBmcm9tIGVpdGhlciB0aGUgc2Vzc2lvbidzIGxvY2FsZSBvciB0aGUgdXNlcidzXG4gKiBkZWZhdWx0IGxvY2FsZSBwcm9wZXJ0eS4gVW5kZXJzY29yZXMgaW4gdGhlIGxvY2FsZSBhcmUgY29udmVydGVkIHRvIGh5cGhlbnNcbiAqIHRvIG1hdGNoIEJDUCA0NyBsYW5ndWFnZSB0YWcgZm9ybWF0LlxuICpcbiAqIEBwYXJhbSBkYXRhIFRoZSBzZXNzaW9uIG9iamVjdCBjb250YWluaW5nIGxvY2FsZSBpbmZvcm1hdGlvbi5cbiAqLyBleHBvcnQgZnVuY3Rpb24gc2V0VXNlckxhbmd1YWdlKGRhdGEpIHtcbiAgICBsZXQgbG9jYWxlID0gZGF0YS5sb2NhbGUgPz8gZGF0YS51c2VyPy51c2VyUHJvcGVydGllcz8uZGVmYXVsdExvY2FsZTtcbiAgICAvLyBPbmx5IHVuZGVyc2NvcmVzIGFyZSBjb252ZXJ0ZWQgaGVyZSwgZGVsaWJlcmF0ZWx5LCByYXRoZXIgdGhhbiByZXVzaW5nIGB0b0xhbmd1YWdlVGFnYC4gaTE4bmV4dFxuICAgIC8vIHJlYWRzIHRoaXMgdmFsdWUgYmFjayBvZmYgYGRvY3VtZW50LmxhbmdgIGFuZCB1c2VzIGl0IGFzIHRoZSB0cmFuc2xhdGlvbiBidW5kbGUga2V5LCBhbmQgdGhvc2VcbiAgICAvLyBidW5kbGVzIGFyZSBuYW1lZCB3aXRoIHRoZSBQT1NJWCBmb3JtIChgdXpATGF0bi5qc29uYCksIHNvIGNvbnZlcnRpbmcgYEBgIHdvdWxkIHNlbmQgdGhlIGxvYWRlclxuICAgIC8vIGFmdGVyIGEgYnVuZGxlIHRoYXQgZG9lcyBub3QgZXhpc3QuXG4gICAgaWYgKGxvY2FsZSAmJiBsb2NhbGUuaW5jbHVkZXMoJ18nKSkge1xuICAgICAgICBsb2NhbGUgPSBsb2NhbGUucmVwbGFjZUFsbCgnXycsICctJyk7XG4gICAgfVxuICAgIGlmIChpc1ZhbGlkTG9jYWxlKGxvY2FsZSkgJiYgbG9jYWxlICE9PSBkb2N1bWVudC5kb2N1bWVudEVsZW1lbnQuZ2V0QXR0cmlidXRlKCdsYW5nJykpIHtcbiAgICAgICAgZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50LnNldEF0dHJpYnV0ZSgnbGFuZycsIGxvY2FsZSk7XG4gICAgfVxufVxuc2Vzc2lvblN0b3JlLnN1YnNjcmliZSgoc3RhdGUpPT57XG4gICAgaWYgKHN0YXRlLmxvYWRlZCAmJiBzdGF0ZS5zZXNzaW9uKSB7XG4gICAgICAgIHNldFVzZXJMYW5ndWFnZShzdGF0ZS5zZXNzaW9uKTtcbiAgICB9XG59KTtcbmZ1bmN0aW9uIHVzZXJIYXNQcml2aWxlZ2UocmVxdWlyZWRQcml2aWxlZ2UsIHVzZXIpIHtcbiAgICBpZiAodHlwZW9mIHJlcXVpcmVkUHJpdmlsZWdlID09PSAnc3RyaW5nJykge1xuICAgICAgICByZXR1cm4gIWlzVW5kZWZpbmVkKHVzZXIucHJpdmlsZWdlcy5maW5kKChwKT0+cmVxdWlyZWRQcml2aWxlZ2UgPT09IHAuZGlzcGxheSkpO1xuICAgIH0gZWxzZSBpZiAoQXJyYXkuaXNBcnJheShyZXF1aXJlZFByaXZpbGVnZSkpIHtcbiAgICAgICAgcmV0dXJuIHJlcXVpcmVkUHJpdmlsZWdlLmV2ZXJ5KChycCk9PiFpc1VuZGVmaW5lZCh1c2VyLnByaXZpbGVnZXMuZmluZCgocCk9PnJwID09PSBwLmRpc3BsYXkpKSk7XG4gICAgfSBlbHNlIGlmICghaXNVbmRlZmluZWQocmVxdWlyZWRQcml2aWxlZ2UpKSB7XG4gICAgICAgIGNvbnNvbGUuZXJyb3IoYENvdWxkIG5vdCB1bmRlcnN0YW5kIHByaXZpbGVnZXMgXCIke3JlcXVpcmVkUHJpdmlsZWdlfVwiYCk7XG4gICAgfVxuICAgIHJldHVybiB0cnVlO1xufVxuZnVuY3Rpb24gaXNTdXBlclVzZXIodXNlcikge1xuICAgIHJldHVybiAhaXNVbmRlZmluZWQodXNlci5yb2xlcy5maW5kKChyb2xlKT0+cm9sZS5kaXNwbGF5ID09PSAnU3lzdGVtIERldmVsb3BlcicpKTtcbn1cbi8qKlxuICogVGhlIGByZWZldGNoQ3VycmVudFVzZXJgIGZ1bmN0aW9uIGNhdXNlcyBhIG5ldHdvcmsgcmVxdWVzdCB0byByZWRvd25sb2FkXG4gKiB0aGUgdXNlci4gQWxsIHN1YnNjcmliZXJzIHRvIHRoZSBzZXNzaW9uIHN0b3JlIHdpbGwgYmUgbm90aWZpZWQgb2YgdGhlXG4gKiBuZXcgdXNlciBvbmNlIHRoZSBuZXcgdmVyc2lvbiBvZiB0aGUgdXNlciBvYmplY3QgaXMgZG93bmxvYWRlZC5cbiAqXG4gKiBJZiB0aGUgc2VydmVyIHJlamVjdHMgdGhlIHJlcXVlc3QgYXMgdW5hdXRoZW50aWNhdGVkICg0MDEgb3IgNDAzKSwgdGhlIHN0b3JlIHJlY29yZHMgYVxuICogbG9nZ2VkLW91dCBzZXNzaW9uLiBJZiB0aGUgcmVxdWVzdCBmYWlscyBmb3IgYW55IG90aGVyIHJlYXNvbiwgYSBzZXNzaW9uIHRoYXQgaGFzIGFscmVhZHlcbiAqIGxvYWRlZCBpcyBrZXB0OyBvdGhlcndpc2UgdGhlIHN0b3JlIHJlY29yZHMgdGhlIGVycm9yLlxuICpcbiAqIEByZXR1cm5zIEEgUHJvbWlzZSByZXNvbHZpbmcgdG8gdGhlIHVwZGF0ZWQgc2Vzc2lvbiBzdG9yZSBzdGF0ZS4gSXQgcmVqZWN0cyB3aXRoIHRoZVxuICogICBzdG9yZSBzdGF0ZSBpZiB0aGUgcmVxdWVzdCBmYWlscyBmb3IgYSByZWFzb24gb3RoZXIgdGhhbiBhdXRoZW50aWNhdGlvbi5cbiAqXG4gKiBAZXhhbXBsZVxuICogYGBganNcbiAqIGltcG9ydCB7IHJlZmV0Y2hDdXJyZW50VXNlciB9IGZyb20gJ0BvcGVubXJzL2VzbS1hcGknXG4gKiByZWZldGNoQ3VycmVudFVzZXIoKVxuICogYGBgXG4gKi8gZXhwb3J0IGZ1bmN0aW9uIHJlZmV0Y2hDdXJyZW50VXNlcih1c2VybmFtZSwgcGFzc3dvcmQpIHtcbiAgICBsYXN0RmV0Y2hUaW1lTWlsbGlzID0gRGF0ZS5ub3coKTtcbiAgICBmaXJzdEZldGNoVGltZU1pbGxpcyA/PyAoZmlyc3RGZXRjaFRpbWVNaWxsaXMgPSBsYXN0RmV0Y2hUaW1lTWlsbGlzKTtcbiAgICBsZXQgaGVhZGVycyA9IHt9O1xuICAgIGlmICh1c2VybmFtZSAmJiBwYXNzd29yZCkge1xuICAgICAgICBoZWFkZXJzWydBdXRob3JpemF0aW9uJ10gPSBgQmFzaWMgJHt3aW5kb3cuYnRvYShgJHt1c2VybmFtZX06JHtwYXNzd29yZH1gKX1gO1xuICAgIH1cbiAgICBjb25zdCByZWZyZXNoID0gaGFuZGxlU2Vzc2lvblJlc3BvbnNlKG9wZW5tcnNGZXRjaChzZXNzaW9uRW5kcG9pbnQsIHtcbiAgICAgICAgaGVhZGVycyxcbiAgICAgICAgcmVqZWN0QXV0aEZhaWx1cmU6IHRydWVcbiAgICB9KSk7XG4gICAgLy8gUHVibGlzaCB0aGUgcmVxdWVzdCBzbyB0aGF0IHJlYWRlcnMgY2FuIHdhaXQgb24gaXQgaW5zdGVhZCBvZiByZWFkaW5nIHRoZSBzZXNzaW9uIGl0IGlzIGFib3V0IHRvXG4gICAgLy8gcmVwbGFjZS4gRWFjaCBjYWxsIHN0aWxsIGlzc3VlcyBpdHMgb3duIHJlcXVlc3Q7IHRoaXMgb25seSB0cmFja3MgdGhlIG1vc3QgcmVjZW50IG9uZS5cbiAgICBjb25zdCBjbGVhciA9ICgpPT57XG4gICAgICAgIGlmIChpbkZsaWdodFJlZnJlc2ggPT09IHJlZnJlc2gpIHtcbiAgICAgICAgICAgIGluRmxpZ2h0UmVmcmVzaCA9IG51bGw7XG4gICAgICAgIH1cbiAgICB9O1xuICAgIHJlZnJlc2gudGhlbihjbGVhciwgY2xlYXIpO1xuICAgIGluRmxpZ2h0UmVmcmVzaCA9IHJlZnJlc2g7XG4gICAgcmV0dXJuIHJlZnJlc2g7XG59XG4vKipcbiAqIENsZWFycyB0aGUgY3VycmVudCB1c2VyIHNlc3Npb24gZnJvbSB0aGUgc2Vzc2lvbiBzdG9yZSwgc2V0dGluZyB0aGUgc2Vzc2lvblxuICogdG8gYW4gdW5hdXRoZW50aWNhdGVkIHN0YXRlLiBUaGlzIGlzIHR5cGljYWxseSBjYWxsZWQgZHVyaW5nIGxvZ291dCB0byByZXNldFxuICogdGhlIGFwcGxpY2F0aW9uJ3MgYXV0aGVudGljYXRpb24gc3RhdGUuXG4gKlxuICogQGV4YW1wbGVcbiAqIGBgYHRzXG4gKiBpbXBvcnQgeyBjbGVhckN1cnJlbnRVc2VyIH0gZnJvbSAnQG9wZW5tcnMvZXNtLWFwaSc7XG4gKiAvLyBEdXJpbmcgbG9nb3V0XG4gKiBjbGVhckN1cnJlbnRVc2VyKCk7XG4gKiBgYGBcbiAqLyBleHBvcnQgZnVuY3Rpb24gY2xlYXJDdXJyZW50VXNlcigpIHtcbiAgICBzZXNzaW9uU3RvcmUuc2V0U3RhdGUoe1xuICAgICAgICBsb2FkZWQ6IHRydWUsXG4gICAgICAgIHNlc3Npb246IHtcbiAgICAgICAgICAgIGF1dGhlbnRpY2F0ZWQ6IGZhbHNlLFxuICAgICAgICAgICAgc2Vzc2lvbklkOiAnJ1xuICAgICAgICB9XG4gICAgfSwgdHJ1ZSk7XG59XG4vKipcbiAqIENoZWNrcyB3aGV0aGVyIHRoZSBnaXZlbiB1c2VyIGhhcyBhY2Nlc3MgYmFzZWQgb24gdGhlIHJlcXVpcmVkIHByaXZpbGVnZShzKS5cbiAqIEEgdXNlciBoYXMgYWNjZXNzIGlmIHRoZXkgaGF2ZSB0aGUgcmVxdWlyZWQgcHJpdmlsZWdlKHMpIG9yIGlmIHRoZXkgYXJlIGFcbiAqIFwiU3lzdGVtIERldmVsb3BlclwiIChzdXBlciB1c2VyKS4gSWYgbm8gcHJpdmlsZWdlIGlzIHJlcXVpcmVkLCBhY2Nlc3MgaXMgZ3JhbnRlZC5cbiAqXG4gKiBAcGFyYW0gcmVxdWlyZWRQcml2aWxlZ2UgQSBzaW5nbGUgcHJpdmlsZWdlIHN0cmluZyBvciBhbiBhcnJheSBvZiBwcml2aWxlZ2Ugc3RyaW5nc1xuICogICB0aGF0IHRoZSB1c2VyIG11c3QgaGF2ZS4gSWYgYW4gYXJyYXkgaXMgcHJvdmlkZWQsIHRoZSB1c2VyIG11c3QgaGF2ZSBBTEwgcHJpdmlsZWdlcy5cbiAqIEBwYXJhbSB1c2VyIFRoZSB1c2VyIG9iamVjdCBjb250YWluaW5nIHRoZWlyIHByaXZpbGVnZXMgYW5kIHJvbGVzLlxuICogQHJldHVybnMgYHRydWVgIGlmIHRoZSB1c2VyIGhhcyBhY2Nlc3MsIGBmYWxzZWAgb3RoZXJ3aXNlLiBSZXR1cm5zIGB0cnVlYCBpZiBub1xuICogICBwcml2aWxlZ2UgaXMgcmVxdWlyZWQsIGFuZCBgZmFsc2VgIGlmIHRoZSB1c2VyIGlzIHVuZGVmaW5lZCBidXQgYSBwcml2aWxlZ2UgaXMgcmVxdWlyZWQuXG4gKlxuICogQGV4YW1wbGVcbiAqIGBgYHRzXG4gKiBpbXBvcnQgeyB1c2VySGFzQWNjZXNzIH0gZnJvbSAnQG9wZW5tcnMvZXNtLWFwaSc7XG4gKiBjb25zdCBoYXNBY2Nlc3MgPSB1c2VySGFzQWNjZXNzKCdWaWV3IFBhdGllbnRzJywgY3VycmVudFVzZXIpO1xuICogY29uc3QgaGFzTXVsdGlwbGVBY2Nlc3MgPSB1c2VySGFzQWNjZXNzKFsnVmlldyBQYXRpZW50cycsICdFZGl0IFBhdGllbnRzJ10sIGN1cnJlbnRVc2VyKTtcbiAqIGBgYFxuICovIGV4cG9ydCBmdW5jdGlvbiB1c2VySGFzQWNjZXNzKHJlcXVpcmVkUHJpdmlsZWdlLCB1c2VyKSB7XG4gICAgaWYgKHVzZXIgPT09IHVuZGVmaW5lZCkge1xuICAgICAgICAvLyBpZiB0aGUgdXNlciBoYXNuJ3QgYmVlbiBsb2FkZWQsIHRoZW4gcmV0dXJuIGZhbHNlIGlmZiB0aGVyZSBpcyBhIHJlcXVpcmVkIHByaXZpbGVnZVxuICAgICAgICByZXR1cm4gIUJvb2xlYW4ocmVxdWlyZWRQcml2aWxlZ2UpO1xuICAgIH1cbiAgICBpZiAoIUJvb2xlYW4ocmVxdWlyZWRQcml2aWxlZ2UpKSB7XG4gICAgICAgIC8vIGlmIHVzZXIgZXhpc3RzIGJ1dCBubyByZXF1aXJlZFByaXZpbGVnZSBpcyBkZWZpbmVkXG4gICAgICAgIHJldHVybiB0cnVlO1xuICAgIH1cbiAgICByZXR1cm4gdXNlckhhc1ByaXZpbGVnZShyZXF1aXJlZFByaXZpbGVnZSwgdXNlcikgfHwgaXNTdXBlclVzZXIodXNlcik7XG59XG4vKipcbiAqIFJldHVybnMgYSBQcm9taXNlIHRoYXQgcmVzb2x2ZXMgd2l0aCB0aGUgY3VycmVudGx5IGxvZ2dlZC1pbiB1c2VyIG9iamVjdC5cbiAqIElmIHRoZSB1c2VyIGlzIGFscmVhZHkgbG9hZGVkIGluIHRoZSBzZXNzaW9uIHN0b3JlLCB0aGUgUHJvbWlzZSByZXNvbHZlcyBpbW1lZGlhdGVseS5cbiAqIE90aGVyd2lzZSwgaXQgc3Vic2NyaWJlcyB0byB0aGUgc2Vzc2lvbiBzdG9yZSBhbmQgcmVzb2x2ZXMgd2hlbiBhIGxvZ2dlZC1pbiB1c2VyXG4gKiBiZWNvbWVzIGF2YWlsYWJsZS5cbiAqXG4gKiBAcmV0dXJucyBBIFByb21pc2UgdGhhdCByZXNvbHZlcyB3aXRoIHRoZSBMb2dnZWRJblVzZXIgb2JqZWN0IG9uY2UgYXZhaWxhYmxlLlxuICpcbiAqIEBleGFtcGxlXG4gKiBgYGB0c1xuICogaW1wb3J0IHsgZ2V0TG9nZ2VkSW5Vc2VyIH0gZnJvbSAnQG9wZW5tcnMvZXNtLWFwaSc7XG4gKiBjb25zdCB1c2VyID0gYXdhaXQgZ2V0TG9nZ2VkSW5Vc2VyKCk7XG4gKiBjb25zb2xlLmxvZygnTG9nZ2VkIGluIGFzOicsIHVzZXIuZGlzcGxheSk7XG4gKiBgYGBcbiAqLyBleHBvcnQgZnVuY3Rpb24gZ2V0TG9nZ2VkSW5Vc2VyKCkge1xuICAgIGxldCB1c2VyO1xuICAgIGxldCB1bnN1YnNjcmliZTtcbiAgICByZXR1cm4gbmV3IFByb21pc2UoKHJlcyk9PntcbiAgICAgICAgY29uc3QgaGFuZGxlciA9IChzdGF0ZSk9PntcbiAgICAgICAgICAgIGlmIChzdGF0ZS5sb2FkZWQgJiYgc3RhdGUuc2Vzc2lvbi51c2VyKSB7XG4gICAgICAgICAgICAgICAgdXNlciA9IHN0YXRlLnNlc3Npb24udXNlcjtcbiAgICAgICAgICAgICAgICByZXMoc3RhdGUuc2Vzc2lvbi51c2VyKTtcbiAgICAgICAgICAgICAgICBpZiAodW5zdWJzY3JpYmUpIHtcbiAgICAgICAgICAgICAgICAgICAgdW5zdWJzY3JpYmUoKTtcbiAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICB9XG4gICAgICAgIH07XG4gICAgICAgIGhhbmRsZXIoc2Vzc2lvblN0b3JlLmdldFN0YXRlKCkpO1xuICAgICAgICBpZiAoIXVzZXIpIHtcbiAgICAgICAgICAgIHVuc3Vic2NyaWJlID0gc2Vzc2lvblN0b3JlLnN1YnNjcmliZShoYW5kbGVyKTtcbiAgICAgICAgfVxuICAgIH0pO1xufVxuLyoqXG4gKiBSZXR1cm5zIGEgUHJvbWlzZSB0aGF0IHJlc29sdmVzIHdpdGggdGhlIGN1cnJlbnQgc2Vzc2lvbiBsb2NhdGlvbiwgaWYgb25lIGlzIHNldC5cbiAqIFRoZSBzZXNzaW9uIGxvY2F0aW9uIHJlcHJlc2VudHMgdGhlIHBoeXNpY2FsIGxvY2F0aW9uIHdoZXJlIHRoZSB1c2VyIGlzIGN1cnJlbnRseVxuICogd29ya2luZyAoZS5nLiwgYSBjbGluaWMgb3Igd2FyZCkuXG4gKlxuICogQHJldHVybnMgQSBQcm9taXNlIHRoYXQgcmVzb2x2ZXMgd2l0aCB0aGUgU2Vzc2lvbkxvY2F0aW9uIG9iamVjdCwgb3IgYHVuZGVmaW5lZGBcbiAqICAgaWYgbm8gc2Vzc2lvbiBsb2NhdGlvbiBpcyBzZXQuXG4gKlxuICogQGV4YW1wbGVcbiAqIGBgYHRzXG4gKiBpbXBvcnQgeyBnZXRTZXNzaW9uTG9jYXRpb24gfSBmcm9tICdAb3Blbm1ycy9lc20tYXBpJztcbiAqIGNvbnN0IGxvY2F0aW9uID0gYXdhaXQgZ2V0U2Vzc2lvbkxvY2F0aW9uKCk7XG4gKiBpZiAobG9jYXRpb24pIHtcbiAqICAgY29uc29sZS5sb2coJ0N1cnJlbnQgbG9jYXRpb246JywgbG9jYXRpb24uZGlzcGxheSk7XG4gKiB9XG4gKiBgYGBcbiAqLyBleHBvcnQgYXN5bmMgZnVuY3Rpb24gZ2V0U2Vzc2lvbkxvY2F0aW9uKCkge1xuICAgIGNvbnN0IHNlc3Npb24gPSBhd2FpdCBnZXRDdXJyZW50VXNlcigpO1xuICAgIHJldHVybiBzZXNzaW9uLnNlc3Npb25Mb2NhdGlvbjtcbn1cbi8qKlxuICogU2V0cyB0aGUgc2Vzc2lvbiBsb2NhdGlvbiBmb3IgdGhlIGN1cnJlbnQgdXNlci4gVGhlIHNlc3Npb24gbG9jYXRpb24gcmVwcmVzZW50c1xuICogdGhlIHBoeXNpY2FsIGxvY2F0aW9uIHdoZXJlIHRoZSB1c2VyIGlzIHdvcmtpbmcgKGUuZy4sIGEgY2xpbmljIG9yIHdhcmQpLlxuICogVGhpcyB0cmlnZ2VycyBhIHNlcnZlciByZXF1ZXN0IHRvIHVwZGF0ZSB0aGUgc2Vzc2lvbiBhbmQgcmVmcmVzaGVzIHRoZSBsb2NhbFxuICogc2Vzc2lvbiBzdG9yZS5cbiAqXG4gKiBAcGFyYW0gbG9jYXRpb25VdWlkIFRoZSBVVUlEIG9mIHRoZSBsb2NhdGlvbiB0byBzZXQgYXMgdGhlIHNlc3Npb24gbG9jYXRpb24uXG4gKiBAcGFyYW0gYWJvcnRDb250cm9sbGVyIEFuIEFib3J0Q29udHJvbGxlciB0byBhbGxvdyBjYW5jZWxsYXRpb24gb2YgdGhlIHJlcXVlc3QuXG4gKiBAcmV0dXJucyBBIFByb21pc2UgdGhhdCByZXNvbHZlcyB3aXRoIHRoZSB1cGRhdGVkIFNlc3Npb25TdG9yZS5cbiAqXG4gKiBAZXhhbXBsZVxuICogYGBgdHNcbiAqIGltcG9ydCB7IHNldFNlc3Npb25Mb2NhdGlvbiB9IGZyb20gJ0BvcGVubXJzL2VzbS1hcGknO1xuICogY29uc3QgYWJvcnRDb250cm9sbGVyID0gbmV3IEFib3J0Q29udHJvbGxlcigpO1xuICogYXdhaXQgc2V0U2Vzc2lvbkxvY2F0aW9uKCdsb2NhdGlvbi11dWlkLWhlcmUnLCBhYm9ydENvbnRyb2xsZXIpO1xuICogYGBgXG4gKi8gZXhwb3J0IGFzeW5jIGZ1bmN0aW9uIHNldFNlc3Npb25Mb2NhdGlvbihsb2NhdGlvblV1aWQsIGFib3J0Q29udHJvbGxlcikge1xuICAgIHJldHVybiBoYW5kbGVTZXNzaW9uUmVzcG9uc2Uob3Blbm1yc0ZldGNoKHNlc3Npb25FbmRwb2ludCwge1xuICAgICAgICBtZXRob2Q6ICdQT1NUJyxcbiAgICAgICAgYm9keToge1xuICAgICAgICAgICAgc2Vzc2lvbkxvY2F0aW9uOiBsb2NhdGlvblV1aWRcbiAgICAgICAgfSxcbiAgICAgICAgaGVhZGVyczoge1xuICAgICAgICAgICAgJ0NvbnRlbnQtVHlwZSc6ICdhcHBsaWNhdGlvbi9qc29uJ1xuICAgICAgICB9LFxuICAgICAgICByZWplY3RBdXRoRmFpbHVyZTogdHJ1ZSxcbiAgICAgICAgc2lnbmFsOiBhYm9ydENvbnRyb2xsZXI/LnNpZ25hbFxuICAgIH0pKTtcbn1cbi8qKlxuICogU2V0cyB0aGUgbG9jYWxlIGZvciB0aGUgY3VycmVudCBzZXNzaW9uIG9ubHksIGxlYXZpbmcgdGhlIHVzZXIncyBkZWZhdWx0IGxvY2FsZSB1bmNoYW5nZWQuXG4gKiBVc2Uge0BsaW5rIHNldFVzZXJQcm9wZXJ0aWVzfSB3aXRoIGEgYGRlZmF1bHRMb2NhbGVgIHByb3BlcnR5IHRvIGNoYW5nZSB0aGUgZGVmYXVsdCBpbnN0ZWFkLlxuICpcbiAqIEBwYXJhbSBsb2NhbGUgVGhlIGxvY2FsZSBpbiBKYXZhJ3MgYExvY2FsZSN0b1N0cmluZygpYCBmb3JtLCBlLmcuIGBlbl9HQmAuXG4gKiBAcGFyYW0gYWJvcnRDb250cm9sbGVyIE9wdGlvbmFsIEFib3J0Q29udHJvbGxlciB0byBhbGxvdyBjYW5jZWxsYXRpb24gb2YgdGhlIHJlcXVlc3QuXG4gKiBAcmV0dXJucyBBIFByb21pc2UgdGhhdCByZXNvbHZlcyB3aXRoIHRoZSB1cGRhdGVkIFNlc3Npb25TdG9yZSBhZnRlciByZWZldGNoaW5nIHRoZSBjdXJyZW50IHVzZXIuXG4gKiAgIEl0IHJlamVjdHMgd2l0aCBhbiB7QGxpbmsgT3Blbm1yc0ZldGNoRXJyb3J9IGlmIHRoZSBzZXJ2ZXIgZG9lcyBub3QgYWNjZXB0IHRoZSBsb2NhbGUuXG4gKlxuICogQGV4YW1wbGVcbiAqIGBgYHRzXG4gKiBpbXBvcnQgeyBzZXRTZXNzaW9uTG9jYWxlIH0gZnJvbSAnQG9wZW5tcnMvZXNtLWFwaSc7XG4gKiBhd2FpdCBzZXRTZXNzaW9uTG9jYWxlKCdmcicpO1xuICogYGBgXG4gKlxuICogQGludGVybmFsXG4gKi8gZXhwb3J0IGFzeW5jIGZ1bmN0aW9uIHNldFNlc3Npb25Mb2NhbGUobG9jYWxlLCBhYm9ydENvbnRyb2xsZXIpIHtcbiAgICBhd2FpdCBvcGVubXJzRmV0Y2goc2Vzc2lvbkVuZHBvaW50LCB7XG4gICAgICAgIG1ldGhvZDogJ1BPU1QnLFxuICAgICAgICBib2R5OiB7XG4gICAgICAgICAgICBsb2NhbGVcbiAgICAgICAgfSxcbiAgICAgICAgaGVhZGVyczoge1xuICAgICAgICAgICAgJ0NvbnRlbnQtVHlwZSc6ICdhcHBsaWNhdGlvbi9qc29uJ1xuICAgICAgICB9LFxuICAgICAgICBzaWduYWw6IGFib3J0Q29udHJvbGxlcj8uc2lnbmFsXG4gICAgfSk7XG4gICAgcmV0dXJuIHJlZmV0Y2hDdXJyZW50VXNlcigpO1xufVxuLyoqXG4gKiBVcGRhdGVzIHRoZSB1c2VyIHByb3BlcnRpZXMgZm9yIGEgc3BlY2lmaWMgdXNlci4gVXNlciBwcm9wZXJ0aWVzIGFyZSBrZXktdmFsdWVcbiAqIHBhaXJzIHRoYXQgc3RvcmUgdXNlci1zcGVjaWZpYyBzZXR0aW5ncyBhbmQgcHJlZmVyZW5jZXMuIEFmdGVyIHVwZGF0aW5nIHRoZVxuICogcHJvcGVydGllcyBvbiB0aGUgc2VydmVyLCB0aGUgY3VycmVudCB1c2VyIHNlc3Npb24gaXMgcmVmZXRjaGVkIHRvIHJlZmxlY3RcbiAqIHRoZSBjaGFuZ2VzLlxuICpcbiAqIEBwYXJhbSB1c2VyVXVpZCBUaGUgVVVJRCBvZiB0aGUgdXNlciB3aG9zZSBwcm9wZXJ0aWVzIHNob3VsZCBiZSB1cGRhdGVkLlxuICogQHBhcmFtIHVzZXJQcm9wZXJ0aWVzIEFuIG9iamVjdCBjb250YWluaW5nIHRoZSBwcm9wZXJ0aWVzIHRvIHNldCBvciB1cGRhdGUuXG4gKiBAcGFyYW0gYWJvcnRDb250cm9sbGVyIE9wdGlvbmFsIEFib3J0Q29udHJvbGxlciB0byBhbGxvdyBjYW5jZWxsYXRpb24gb2YgdGhlIHJlcXVlc3QuXG4gKiAgIElmIG5vdCBwcm92aWRlZCwgYSBuZXcgQWJvcnRDb250cm9sbGVyIGlzIGNyZWF0ZWQuXG4gKiBAcmV0dXJucyBBIFByb21pc2UgdGhhdCByZXNvbHZlcyB3aXRoIHRoZSB1cGRhdGVkIFNlc3Npb25TdG9yZSBhZnRlciByZWZldGNoaW5nXG4gKiAgIHRoZSBjdXJyZW50IHVzZXIuXG4gKlxuICogQGV4YW1wbGVcbiAqIGBgYHRzXG4gKiBpbXBvcnQgeyBnZXRMb2dnZWRJblVzZXIsIHNldFVzZXJQcm9wZXJ0aWVzIH0gZnJvbSAnQG9wZW5tcnMvZXNtLWFwaSc7XG4gKiBjb25zdCB1c2VyID0gYXdhaXQgZ2V0TG9nZ2VkSW5Vc2VyKCk7XG4gKiBhd2FpdCBzZXRVc2VyUHJvcGVydGllcyh1c2VyLnV1aWQsIHtcbiAqICAgZGVmYXVsdExvY2FsZTogJ2VuX0dCJyxcbiAqICAgY3VzdG9tU2V0dGluZzogJ3ZhbHVlJ1xuICogfSk7XG4gKiBgYGBcbiAqLyBleHBvcnQgYXN5bmMgZnVuY3Rpb24gc2V0VXNlclByb3BlcnRpZXModXNlclV1aWQsIHVzZXJQcm9wZXJ0aWVzLCBhYm9ydENvbnRyb2xsZXIpIHtcbiAgICBpZiAoIWFib3J0Q29udHJvbGxlcikge1xuICAgICAgICBhYm9ydENvbnRyb2xsZXIgPSBuZXcgQWJvcnRDb250cm9sbGVyKCk7XG4gICAgfVxuICAgIGF3YWl0IG9wZW5tcnNGZXRjaChgJHtyZXN0QmFzZVVybH0vdXNlci8ke3VzZXJVdWlkfWAsIHtcbiAgICAgICAgbWV0aG9kOiAnUE9TVCcsXG4gICAgICAgIGJvZHk6IHtcbiAgICAgICAgICAgIHVzZXJQcm9wZXJ0aWVzXG4gICAgICAgIH0sXG4gICAgICAgIGhlYWRlcnM6IHtcbiAgICAgICAgICAgICdDb250ZW50LVR5cGUnOiAnYXBwbGljYXRpb24vanNvbidcbiAgICAgICAgfSxcbiAgICAgICAgc2lnbmFsOiBhYm9ydENvbnRyb2xsZXIuc2lnbmFsXG4gICAgfSk7XG4gICAgcmV0dXJuIHJlZmV0Y2hDdXJyZW50VXNlcigpO1xufVxuLyoqXG4gKiBTdWJtaXRzIGEgVE9UUCBjb2RlIHRvIGNvbXBsZXRlIGEgdHdvLWZhY3RvciBsb2dpbiBjaGFsbGVuZ2UuIFdoZW4gdGhlIGNvZGUgaXMgYWNjZXB0ZWQsIHRoZVxuICogc2Vzc2lvbiBzdG9yZSBpcyByZWZyZXNoZWQgd2l0aCB0aGUgbm93LWF1dGhlbnRpY2F0ZWQgc2Vzc2lvbi5cbiAqXG4gKiBAcGFyYW0gY29kZSBUaGUgY29kZSBmcm9tIHRoZSB1c2VyJ3MgYXV0aGVudGljYXRvciBhcHAuXG4gKiBAcGFyYW0gcmVtZW1iZXJEZXZpY2UgV2hldGhlciB0aGUgc2VydmVyIHNob3VsZCBza2lwIHRoZSBjaGFsbGVuZ2Ugb24gdGhpcyBkZXZpY2UgaW4gZnV0dXJlLlxuICogQHJldHVybnMgQSBQcm9taXNlIHJlc29sdmluZyB0byB0aGUgc2Vzc2lvbi4gSXRzIGBhdXRoZW50aWNhdGVkYCBwcm9wZXJ0eSBpcyBgZmFsc2VgIGlmIHRoZVxuICogICBjb2RlIHdhcyBub3QgYWNjZXB0ZWQuIEl0IHJlamVjdHMgd2l0aCBhbiB7QGxpbmsgT3Blbm1yc0ZldGNoRXJyb3J9IGlmIHRoZSBzZXJ2ZXIgcmVqZWN0cyB0aGVcbiAqICAgcmVxdWVzdCwgaW4gd2hpY2ggY2FzZSBgcmVzcG9uc2VCb2R5YCBtYXkgZXhwbGFpbiB3aHkuXG4gKlxuICogQGV4YW1wbGVcbiAqIGBgYHRzXG4gKiBpbXBvcnQgeyB2ZXJpZnlUb3RwQ29kZSB9IGZyb20gJ0BvcGVubXJzL2VzbS1hcGknO1xuICogY29uc3Qgc2Vzc2lvbiA9IGF3YWl0IHZlcmlmeVRvdHBDb2RlKCcxMjM0NTYnLCB0cnVlKTtcbiAqIGBgYFxuICpcbiAqIEBpbnRlcm5hbFxuICovIGV4cG9ydCBhc3luYyBmdW5jdGlvbiB2ZXJpZnlUb3RwQ29kZShjb2RlLCByZW1lbWJlckRldmljZSA9IGZhbHNlKSB7XG4gICAgY29uc3QgcmVzcG9uc2UgPSBhd2FpdCBvcGVubXJzRmV0Y2gocmVtZW1iZXJEZXZpY2UgPyBgJHtzZXNzaW9uRW5kcG9pbnR9P3JlbWVtYmVyTWU9dHJ1ZWAgOiBzZXNzaW9uRW5kcG9pbnQsIHtcbiAgICAgICAgaGVhZGVyczoge1xuICAgICAgICAgICAgJ1gtVG90cC1Db2RlJzogY29kZVxuICAgICAgICB9XG4gICAgfSk7XG4gICAgaWYgKHJlc3BvbnNlLmRhdGE/LmF1dGhlbnRpY2F0ZWQpIHtcbiAgICAgICAgLy8gYHJlZmV0Y2hDdXJyZW50VXNlcmAgb25seSByZXNvbHZlcyBvbmNlIHRoZSBzdG9yZSBob2xkcyBhIHNlc3Npb24uXG4gICAgICAgIGNvbnN0IHN0b3JlID0gYXdhaXQgcmVmZXRjaEN1cnJlbnRVc2VyKCk7XG4gICAgICAgIHJldHVybiBzdG9yZS5zZXNzaW9uO1xuICAgIH1cbiAgICByZXR1cm4gcmVzcG9uc2UuZGF0YTtcbn1cbi8qKlxuICogRW5kcyB0aGUgY3VycmVudCBzZXNzaW9uIG9uIHRoZSBzZXJ2ZXIgYW5kIHJlY29yZHMgYSBsb2dnZWQtb3V0IHNlc3Npb24gaW4gdGhlIHNlc3Npb24gc3RvcmUuXG4gKiBBIHNlcnZlciB0aGF0IGhhcyBhbHJlYWR5IGVuZGVkIHRoZSBzZXNzaW9uICg0MDEgb3IgNDAzKSBjb3VudHMgYXMgYSBzdWNjZXNzZnVsIGxvZ291dC5cbiAqXG4gKiBPdGhlciBkYXRhIGNhY2hlZCBmb3IgdGhlIGxvZ2dlZC1pbiB1c2VyLCBzdWNoIGFzIFNXUiBjYWNoZXMsIGlzIHRoZSBjYWxsZXIncyB0byBjbGVhci5cbiAqXG4gKiBAcmV0dXJucyBBIFByb21pc2UgdGhhdCByZXNvbHZlcyBvbmNlIHRoZSBzZXNzaW9uIHN0b3JlIGhvbGRzIGEgbG9nZ2VkLW91dCBzZXNzaW9uLlxuICpcbiAqIEBleGFtcGxlXG4gKiBgYGB0c1xuICogaW1wb3J0IHsgbG9nb3V0IH0gZnJvbSAnQG9wZW5tcnMvZXNtLWFwaSc7XG4gKiBhd2FpdCBsb2dvdXQoKTtcbiAqIGBgYFxuICpcbiAqIEBpbnRlcm5hbFxuICovIGV4cG9ydCBhc3luYyBmdW5jdGlvbiBsb2dvdXQoKSB7XG4gICAgdHJ5IHtcbiAgICAgICAgYXdhaXQgb3Blbm1yc0ZldGNoKHNlc3Npb25FbmRwb2ludCwge1xuICAgICAgICAgICAgbWV0aG9kOiAnREVMRVRFJyxcbiAgICAgICAgICAgIHJlamVjdEF1dGhGYWlsdXJlOiB0cnVlXG4gICAgICAgIH0pO1xuICAgIH0gY2F0Y2ggKGVycikge1xuICAgICAgICBpZiAoIWlzQXV0aEZhaWx1cmUoZXJyKSkge1xuICAgICAgICAgICAgdGhyb3cgZXJyO1xuICAgICAgICB9XG4gICAgfVxuICAgIGNsZWFyQ3VycmVudFVzZXIoKTtcbiAgICAvLyBUaGUgc2Vzc2lvbiBqdXN0IGNsZWFyZWQgaXMgYWxyZWFkeSBjb3JyZWN0LCBzbyBhIGZhaWxlZCByZWZyZXNoIGxvc2VzIG5vdGhpbmcuXG4gICAgYXdhaXQgcmVmZXRjaEN1cnJlbnRVc2VyKCkuY2F0Y2goKCk9Pnt9KTtcbn1cbmZ1bmN0aW9uIGhhbmRsZVNlc3Npb25SZXNwb25zZShyZXN1bHQpIHtcbiAgICByZXR1cm4gbmV3IFByb21pc2UoKHJlc29sdmUsIHJlamVjdCk9PntcbiAgICAgICAgcmVzdWx0LnRoZW4oKHJlcyk9PntcbiAgICAgICAgICAgIGlmICh0eXBlb2YgcmVzPy5kYXRhID09PSAnb2JqZWN0Jykge1xuICAgICAgICAgICAgICAgIGNvbnN0IG5leHRTdGF0ZSA9IHtcbiAgICAgICAgICAgICAgICAgICAgbG9hZGVkOiB0cnVlLFxuICAgICAgICAgICAgICAgICAgICBzZXNzaW9uOiByZXMuZGF0YVxuICAgICAgICAgICAgICAgIH07XG4gICAgICAgICAgICAgICAgc2Vzc2lvblN0b3JlLnNldFN0YXRlKG5leHRTdGF0ZSwgdHJ1ZSk7XG4gICAgICAgICAgICAgICAgcmVzb2x2ZShuZXh0U3RhdGUpO1xuICAgICAgICAgICAgfSBlbHNlIGlmIChpc0luaXRpYWxTZXR1cFJlZGlyZWN0KHJlcykpIHtcbiAgICAgICAgICAgICAgICByZWplY3QocmVjb3JkU2Vzc2lvbkZhaWx1cmUoRXJyb3IoJ1RoZSBzZXJ2ZXIgaXMgc3RpbGwgc3RhcnRpbmcgdXAnKSwgdHJ1ZSkpO1xuICAgICAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICAgICAgICByZWplY3QocmVjb3JkU2Vzc2lvbkZhaWx1cmUoRXJyb3IoJ1RoZSBzZXNzaW9uIGVuZHBvaW50IGRpZCBub3QgcmVzcG9uZCB3aXRoIGEgc2Vzc2lvbicpKSk7XG4gICAgICAgICAgICB9XG4gICAgICAgIH0pLmNhdGNoKChlcnIpPT57XG4gICAgICAgICAgICAvLyBBbiBhdXRoIGZhaWx1cmUgaXMgdGhlIHNlc3Npb24gZW5kcG9pbnQncyBhbnN3ZXIgZm9yIFwibm90IGxvZ2dlZCBpblwiLCBub3QgYSBmYWlsZWQgbG9va3VwLlxuICAgICAgICAgICAgaWYgKGlzQXV0aEZhaWx1cmUoZXJyKSkge1xuICAgICAgICAgICAgICAgIGlmIChpc1VuYXV0aGVudGljYXRlZFNlc3Npb24oZXJyLnJlc3BvbnNlQm9keSkpIHtcbiAgICAgICAgICAgICAgICAgICAgc2Vzc2lvblN0b3JlLnNldFN0YXRlKHtcbiAgICAgICAgICAgICAgICAgICAgICAgIGxvYWRlZDogdHJ1ZSxcbiAgICAgICAgICAgICAgICAgICAgICAgIHNlc3Npb246IGVyci5yZXNwb25zZUJvZHlcbiAgICAgICAgICAgICAgICAgICAgfSwgdHJ1ZSk7XG4gICAgICAgICAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICAgICAgICAgICAgY2xlYXJDdXJyZW50VXNlcigpO1xuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICByZXNvbHZlKHNlc3Npb25TdG9yZS5nZXRTdGF0ZSgpKTtcbiAgICAgICAgICAgICAgICByZXR1cm47XG4gICAgICAgICAgICB9XG4gICAgICAgICAgICBpZiAoaXNHYXRld2F5RXJyb3JEdXJpbmdTdGFydHVwKGVycikpIHtcbiAgICAgICAgICAgICAgICByZWplY3QocmVjb3JkU2Vzc2lvbkZhaWx1cmUoZXJyLCB0cnVlKSk7XG4gICAgICAgICAgICAgICAgcmV0dXJuO1xuICAgICAgICAgICAgfVxuICAgICAgICAgICAgcmVwb3J0RXJyb3IoYEZhaWxlZCB0byBmZXRjaCBuZXcgc2Vzc2lvbiBpbmZvcm1hdGlvbjogJHtlcnJ9YCk7XG4gICAgICAgICAgICByZWplY3QocmVjb3JkU2Vzc2lvbkZhaWx1cmUoZXJyKSk7XG4gICAgICAgIH0pO1xuICAgIH0pO1xufVxuZnVuY3Rpb24gaXNBdXRoRmFpbHVyZShlcnIpIHtcbiAgICByZXR1cm4gZXJyIGluc3RhbmNlb2YgT3Blbm1yc0ZldGNoRXJyb3IgJiYgKGVyci5yZXNwb25zZS5zdGF0dXMgPT09IDQwMSB8fCBlcnIucmVzcG9uc2Uuc3RhdHVzID09PSA0MDMpO1xufVxuLyoqXG4gKiBVbnRpbCB0aGUgYmFja2VuZCBoYXMgZmluaXNoZWQgaXRzIGluaXRpYWwgc2V0dXAsIGl0IGFuc3dlcnMgZXZlcnkgcmVxdWVzdCB3aXRoIGEgcmVkaXJlY3QgdG8gaXRzXG4gKiBzZXR1cCBwYWdlLCB3aGljaCBgZmV0Y2goKWAgZm9sbG93cywgc28gdGhlIHNlc3Npb24gcmVxdWVzdCByZXNvbHZlcyB3aXRoIHRoYXQgcGFnZSdzIEhUTUwuXG4gKi8gZnVuY3Rpb24gaXNJbml0aWFsU2V0dXBSZWRpcmVjdChyZXMpIHtcbiAgICBpZiAoIXJlcz8ucmVkaXJlY3RlZCB8fCAhcmVzLnVybCkge1xuICAgICAgICByZXR1cm4gZmFsc2U7XG4gICAgfVxuICAgIHRyeSB7XG4gICAgICAgIHJldHVybiBuZXcgVVJMKHJlcy51cmwsIHdpbmRvdy5sb2NhdGlvbi5ocmVmKS5wYXRobmFtZS5yZXBsYWNlKC9cXC8rJC8sICcnKS5lbmRzV2l0aCgnL2luaXRpYWxzZXR1cCcpO1xuICAgIH0gY2F0Y2ggIHtcbiAgICAgICAgcmV0dXJuIGZhbHNlO1xuICAgIH1cbn1cbmZ1bmN0aW9uIGlzR2F0ZXdheUVycm9yRHVyaW5nU3RhcnR1cChlcnIpIHtcbiAgICByZXR1cm4gZXJyIGluc3RhbmNlb2YgT3Blbm1yc0ZldGNoRXJyb3IgJiYgZXJyLnJlc3BvbnNlLnN0YXR1cyA9PT0gNTAyICYmICFzZXNzaW9uU3RvcmUuZ2V0U3RhdGUoKS5sb2FkZWQgJiYgZmlyc3RGZXRjaFRpbWVNaWxsaXMgIT09IHVuZGVmaW5lZCAmJiBEYXRlLm5vdygpIC0gZmlyc3RGZXRjaFRpbWVNaWxsaXMgPCBzdGFydHVwR3JhY2VQZXJpb2RNaWxsaXM7XG59XG5mdW5jdGlvbiBpc1VuYXV0aGVudGljYXRlZFNlc3Npb24oYm9keSkge1xuICAgIHJldHVybiB0eXBlb2YgYm9keSA9PT0gJ29iamVjdCcgJiYgYm9keSAhPT0gbnVsbCAmJiBib2R5LmF1dGhlbnRpY2F0ZWQgPT09IGZhbHNlO1xufVxuLyoqXG4gKiBBIHNlc3Npb24gdGhhdCBoYXMgYWxyZWFkeSBsb2FkZWQgaXMga2VwdCB3aGVuIGEgbGF0ZXIgZmV0Y2ggZmFpbHMsIHNpbmNlIGl0IGlzIHN0aWxsIHRoZSBiZXN0IGFuc3dlclxuICogYXZhaWxhYmxlLiBXaXRoIG5vdGhpbmcgdG8gZmFsbCBiYWNrIG9uLCB0aGUgZXJyb3IgaXMgcmVjb3JkZWQgc28gdGhlIGFwcCBzaGVsbCBjYW4gc2hvdyBhbiBlcnJvciBwYWdlLlxuICovIGZ1bmN0aW9uIHJlY29yZFNlc3Npb25GYWlsdXJlKGVyciwgaW5pdGlhbGl6aW5nID0gZmFsc2UpIHtcbiAgICBpZiAoIXNlc3Npb25TdG9yZS5nZXRTdGF0ZSgpLmxvYWRlZCkge1xuICAgICAgICBzZXNzaW9uU3RvcmUuc2V0U3RhdGUoe1xuICAgICAgICAgICAgbG9hZGVkOiBmYWxzZSxcbiAgICAgICAgICAgIHNlc3Npb246IG51bGwsXG4gICAgICAgICAgICBlcnJvcjogZXJyIGluc3RhbmNlb2YgRXJyb3IgPyBlcnIgOiBFcnJvcihTdHJpbmcoZXJyKSksXG4gICAgICAgICAgICBpbml0aWFsaXppbmdcbiAgICAgICAgfSwgdHJ1ZSk7XG4gICAgfVxuICAgIHJldHVybiBzZXNzaW9uU3RvcmUuZ2V0U3RhdGUoKTtcbn1cbiJdLCJuYW1lcyI6WyJyZXBvcnRFcnJvciIsImNyZWF0ZUdsb2JhbFN0b3JlIiwiaXNVbmRlZmluZWQiLCJPcGVubXJzRmV0Y2hFcnJvciIsIm9wZW5tcnNGZXRjaCIsInJlc3RCYXNlVXJsIiwic2Vzc2lvbkVuZHBvaW50Iiwic2Vzc2lvblN0b3JlIiwic2Vzc2lvbk1heEFnZU1pbGxpcyIsImxhc3RGZXRjaFRpbWVNaWxsaXMiLCJzdGFydHVwR3JhY2VQZXJpb2RNaWxsaXMiLCJmaXJzdEZldGNoVGltZU1pbGxpcyIsImluRmxpZ2h0UmVmcmVzaCIsInJlZnJlc2hTZXNzaW9uSWZTdGFsZSIsIkRhdGUiLCJyZWZldGNoQ3VycmVudFVzZXIiLCJnZXRDdXJyZW50VXNlciIsIm9wdHMiLCJpbmNsdWRlQXV0aFN0YXR1cyIsInNlbGVjdCIsInNlc3Npb24iLCJyZWZyZXNoIiwiUHJvbWlzZSIsInJlc29sdmUiLCJyZXNvbHZlSWZMb2FkZWQiLCJzdGF0ZSIsInVuc3Vic2NyaWJlIiwiZ2V0U2Vzc2lvblN0b3JlIiwiaXNWYWxpZExvY2FsZSIsImxvY2FsZSIsInVuZGVmaW5lZCIsIkludGwiLCJlIiwic2V0VXNlckxhbmd1YWdlIiwiZGF0YSIsImRvY3VtZW50IiwidXNlckhhc1ByaXZpbGVnZSIsInJlcXVpcmVkUHJpdmlsZWdlIiwidXNlciIsInAiLCJBcnJheSIsInJwIiwiY29uc29sZSIsImlzU3VwZXJVc2VyIiwicm9sZSIsInVzZXJuYW1lIiwicGFzc3dvcmQiLCJoZWFkZXJzIiwid2luZG93IiwiaGFuZGxlU2Vzc2lvblJlc3BvbnNlIiwiY2xlYXIiLCJjbGVhckN1cnJlbnRVc2VyIiwidXNlckhhc0FjY2VzcyIsIkJvb2xlYW4iLCJnZXRMb2dnZWRJblVzZXIiLCJyZXMiLCJoYW5kbGVyIiwiZ2V0U2Vzc2lvbkxvY2F0aW9uIiwic2V0U2Vzc2lvbkxvY2F0aW9uIiwibG9jYXRpb25VdWlkIiwiYWJvcnRDb250cm9sbGVyIiwic2V0U2Vzc2lvbkxvY2FsZSIsInNldFVzZXJQcm9wZXJ0aWVzIiwidXNlclV1aWQiLCJ1c2VyUHJvcGVydGllcyIsIkFib3J0Q29udHJvbGxlciIsInZlcmlmeVRvdHBDb2RlIiwiY29kZSIsInJlbWVtYmVyRGV2aWNlIiwicmVzcG9uc2UiLCJzdG9yZSIsImxvZ291dCIsImVyciIsImlzQXV0aEZhaWx1cmUiLCJyZXN1bHQiLCJyZWplY3QiLCJuZXh0U3RhdGUiLCJpc0luaXRpYWxTZXR1cFJlZGlyZWN0IiwicmVjb3JkU2Vzc2lvbkZhaWx1cmUiLCJFcnJvciIsImlzVW5hdXRoZW50aWNhdGVkU2Vzc2lvbiIsImlzR2F0ZXdheUVycm9yRHVyaW5nU3RhcnR1cCIsIlVSTCIsImJvZHkiLCJpbml0aWFsaXppbmciLCJTdHJpbmciXSwibWFwcGluZ3MiOiI7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7OztBQUFBLDBCQUEwQixHQUE2RDtBQUNoQztBQUNmO0FBQzJEO0FBQ25HLGNBQWMsR0FBVSxNQUFNTyxlQUFlTix5REFBaUJBLENBQUMsV0FBVztJQUN0RSxRQUFRO0lBQ1IsU0FBUztBQUNiLEdBQUc7QUFDSDs7OztDQUlDLEdBQUcsTUFBTU8sc0JBQXNCLEtBQUs7QUFDckMsSUFBSUMsc0JBQXNCO0FBQzFCOzs7Q0FHQyxHQUFHLE1BQU1DLDJCQUEyQixJQUFJLEtBQUs7QUFDOUMsSUFBSUM7QUFDSixJQUFJQyxrQkFBa0I7QUFDdEI7Ozs7Ozs7Ozs7O0NBV0MsR0FBRyxTQUFTQztJQUNULElBQUlELGlCQUFpQjtRQUNqQixPQUFPQTtJQUNYO0lBQ0EsSUFBSUwsYUFBYSxRQUFRLEdBQUcsTUFBTSxJQUFJRSx1QkFBdUJLLEtBQUssR0FBRyxLQUFLTixxQkFBcUI7UUFDM0YsT0FBTztJQUNYO0lBQ0EsT0FBT087QUFDWDtBQUNBLFNBQVNDLGVBQWVDLElBQUk7SUFDeEIsTUFBTUMsb0JBQW9CRCxNQUFNLHFCQUFxQjtJQUNyRCxNQUFNRSxTQUFTLENBQUNDLFVBQVVGLG9CQUFvQkUsVUFBVUEsUUFBUSxJQUFJO0lBQ3BFLE1BQU1DLFVBQVVSO0lBQ2hCLElBQUksQ0FBQ1EsU0FBUztRQUNWLE9BQU9DLFFBQVEsT0FBTyxDQUFDSCxPQUFPWixhQUFhLFFBQVEsR0FBRyxPQUFPO0lBQ2pFO0lBQ0EsT0FB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\n//# sourceURL=webpack-internal:///../../framework/esm-api/dist/current-user.js\n\n}");
4414
+ eval("{__webpack_require__.r(__webpack_exports__);\n__webpack_require__.d(__webpack_exports__, {\n clearCurrentUser: () => (clearCurrentUser),\n getCurrentUser: () => (getCurrentUser),\n getLoggedInUser: () => (getLoggedInUser),\n getSessionLocation: () => (getSessionLocation),\n getSessionStore: () => (getSessionStore),\n logout: () => (logout),\n refetchCurrentUser: () => (refetchCurrentUser),\n sessionStore: () => (sessionStore),\n setSessionLocale: () => (setSessionLocale),\n setSessionLocation: () => (setSessionLocation),\n setUserLanguage: () => (setUserLanguage),\n setUserProperties: () => (setUserProperties),\n userHasAccess: () => (userHasAccess),\n verifyTotpCode: () => (verifyTotpCode)\n});\n/* import */ var _openmrs_esm_error_handling__rspack_import_0 = __webpack_require__(\"../../framework/esm-error-handling/dist/index.js\");\n/* import */ var _openmrs_esm_state__rspack_import_1 = __webpack_require__(\"../../framework/esm-state/dist/index.js\");\n/* import */ var lodash_es__rspack_import_3 = __webpack_require__(\"../../../node_modules/lodash-es/isUndefined.js\");\n/* import */ var _openmrs_fetch_js__rspack_import_2 = __webpack_require__(\"../../framework/esm-api/dist/openmrs-fetch.js\");\n/** @module @category API */ \n\n\n\n/** @internal */ const sessionStore = (0,_openmrs_esm_state__rspack_import_1.createGlobalStore)('session', {\n loaded: false,\n session: null\n});\n/**\n * The upper bound on how old the session handed to a reader may be. It is measured from the moment a\n * fetch is *started*, not from the moment its response lands, so the session a reader sees is always\n * strictly newer than this.\n */ const sessionMaxAgeMillis = 60 * 1000;\nlet lastFetchTimeMillis = 0;\n/**\n * How long after the first session fetch a 502 is taken to mean that the backend is still starting up. A\n * gateway answers with a 502 until the backend has deployed, which can take a few minutes after a restart.\n */ const startupGracePeriodMillis = 3 * 60 * 1000;\nlet firstFetchTimeMillis;\nlet inFlightRefresh = null;\n/**\n * Fetches the session if the store is unloaded or its session is older than `sessionMaxAgeMillis`.\n * Returns `null` only when the store already holds a session fresh enough to be read as-is, so a\n * caller that gets a promise back must wait for it rather than read the store.\n *\n * A fetch already in flight is joined rather than duplicated. This is what keeps `sessionMaxAgeMillis`\n * an upper bound: while a fetch is running, the store still holds the previous session, and returning\n * that would hand back data older than the bound allows.\n *\n * The returned promise rejects if the fetch fails, but the rejection is already handled and reported,\n * so a caller that only needs the fetch started can ignore it.\n */ function refreshSessionIfStale() {\n if (inFlightRefresh) {\n return inFlightRefresh;\n }\n if (sessionStore.getState().loaded && lastFetchTimeMillis >= Date.now() - sessionMaxAgeMillis) {\n return null;\n }\n return refetchCurrentUser();\n}\nfunction getCurrentUser(opts) {\n const includeAuthStatus = opts?.includeAuthStatus ?? true;\n const select = (session)=>includeAuthStatus ? session : session.user;\n const refresh = refreshSessionIfStale();\n if (!refresh) {\n return Promise.resolve(select(sessionStore.getState().session));\n }\n return new Promise((resolve)=>{\n const resolveIfLoaded = ()=>{\n const state = sessionStore.getState();\n if (state.loaded) {\n unsubscribe();\n resolve(select(state.session));\n }\n };\n const unsubscribe = sessionStore.subscribe(resolveIfLoaded);\n // A failed refresh keeps an already-loaded session without updating the store, so the\n // subscription alone would never fire.\n refresh.then(resolveIfLoaded, resolveIfLoaded);\n });\n}\n\n/**\n * Returns the global session store containing the current user's session information.\n * If the session data is stale (older than 1 minute) or not yet loaded, this function\n * will trigger a refetch of the current user's session.\n *\n * @returns The global session store that can be subscribed to for session updates.\n *\n * @example\n * ```ts\n * import { getSessionStore } from '@openmrs/esm-api';\n * const store = getSessionStore();\n * const unsubscribe = store.subscribe((state) => {\n * if (state.loaded) {\n * console.log('Session:', state.session);\n * }\n * });\n * ```\n */ function getSessionStore() {\n void refreshSessionIfStale();\n return sessionStore;\n}\n// NB locale is string only if this returns true\nfunction isValidLocale(locale) {\n if (locale === undefined || typeof locale !== 'string') {\n return false;\n }\n try {\n new Intl.Locale(locale);\n } catch (e) {\n return false;\n }\n return true;\n}\n/**\n * Sets the document's language attribute based on the user's locale preference\n * from the session data. This affects the HTML `lang` attribute which is used\n * for accessibility and internationalization.\n *\n * The locale is determined from either the session's locale or the user's\n * default locale property. Underscores in the locale are converted to hyphens\n * to match BCP 47 language tag format.\n *\n * @param data The session object containing locale information.\n */ function setUserLanguage(data) {\n let locale = data.locale ?? data.user?.userProperties?.defaultLocale;\n // Only underscores are converted here, deliberately, rather than reusing `toLanguageTag`. i18next\n // reads this value back off `document.lang` and uses it as the translation bundle key, and those\n // bundles are named with the POSIX form (`uz@Latn.json`), so converting `@` would send the loader\n // after a bundle that does not exist.\n if (locale && locale.includes('_')) {\n locale = locale.replaceAll('_', '-');\n }\n if (isValidLocale(locale) && locale !== document.documentElement.getAttribute('lang')) {\n document.documentElement.setAttribute('lang', locale);\n }\n}\nsessionStore.subscribe((state)=>{\n if (state.loaded && state.session) {\n setUserLanguage(state.session);\n }\n});\nfunction userHasPrivilege(requiredPrivilege, user) {\n if (typeof requiredPrivilege === 'string') {\n return !(0,lodash_es__rspack_import_3[\"default\"])(user.privileges.find((p)=>requiredPrivilege === p.display));\n } else if (Array.isArray(requiredPrivilege)) {\n return requiredPrivilege.every((rp)=>!(0,lodash_es__rspack_import_3[\"default\"])(user.privileges.find((p)=>rp === p.display)));\n } else if (!(0,lodash_es__rspack_import_3[\"default\"])(requiredPrivilege)) {\n console.error(`Could not understand privileges \"${requiredPrivilege}\"`);\n }\n return true;\n}\nfunction isSuperUser(user) {\n return !(0,lodash_es__rspack_import_3[\"default\"])(user.roles.find((role)=>role.display === 'System Developer'));\n}\n/**\n * The `refetchCurrentUser` function causes a network request to redownload\n * the user. All subscribers to the session store will be notified of the\n * new user once the new version of the user object is downloaded.\n *\n * If the server rejects the request as unauthenticated (401 or 403), the store records a\n * logged-out session. If the request fails for any other reason, a session that has already\n * loaded is kept; otherwise the store records the error.\n *\n * @returns A Promise resolving to the updated session store state. It rejects with the\n * store state if the request fails for a reason other than authentication.\n *\n * @example\n * ```js\n * import { refetchCurrentUser } from '@openmrs/esm-api'\n * refetchCurrentUser()\n * ```\n */ function refetchCurrentUser(username, password) {\n lastFetchTimeMillis = Date.now();\n firstFetchTimeMillis ?? (firstFetchTimeMillis = lastFetchTimeMillis);\n let headers = {};\n if (username && password) {\n headers['Authorization'] = `Basic ${window.btoa(`${username}:${password}`)}`;\n }\n const refresh = handleSessionResponse((0,_openmrs_fetch_js__rspack_import_2.openmrsFetch)(_openmrs_fetch_js__rspack_import_2.sessionEndpoint, {\n headers,\n rejectAuthFailure: true\n }));\n // Publish the request so that readers can wait on it instead of reading the session it is about to\n // replace. Each call still issues its own request; this only tracks the most recent one.\n const clear = ()=>{\n if (inFlightRefresh === refresh) {\n inFlightRefresh = null;\n }\n };\n refresh.then(clear, clear);\n inFlightRefresh = refresh;\n return refresh;\n}\n/**\n * Clears the current user session from the session store, setting the session\n * to an unauthenticated state. This is typically called during logout to reset\n * the application's authentication state.\n *\n * @example\n * ```ts\n * import { clearCurrentUser } from '@openmrs/esm-api';\n * // During logout\n * clearCurrentUser();\n * ```\n */ function clearCurrentUser() {\n sessionStore.setState({\n loaded: true,\n session: {\n authenticated: false,\n sessionId: ''\n }\n }, true);\n}\n/**\n * Checks whether the given user has access based on the required privilege(s).\n * A user has access if they have the required privilege(s) or if they are a\n * \"System Developer\" (super user). If no privilege is required, access is granted.\n *\n * @param requiredPrivilege A single privilege string or an array of privilege strings\n * that the user must have. If an array is provided, the user must have ALL privileges.\n * @param user The user object containing their privileges and roles.\n * @returns `true` if the user has access, `false` otherwise. Returns `true` if no\n * privilege is required, and `false` if the user is undefined but a privilege is required.\n *\n * @example\n * ```ts\n * import { userHasAccess } from '@openmrs/esm-api';\n * const hasAccess = userHasAccess('View Patients', currentUser);\n * const hasMultipleAccess = userHasAccess(['View Patients', 'Edit Patients'], currentUser);\n * ```\n */ function userHasAccess(requiredPrivilege, user) {\n if (user === undefined) {\n // if the user hasn't been loaded, then return false iff there is a required privilege\n return !Boolean(requiredPrivilege);\n }\n if (!Boolean(requiredPrivilege)) {\n // if user exists but no requiredPrivilege is defined\n return true;\n }\n return userHasPrivilege(requiredPrivilege, user) || isSuperUser(user);\n}\n/**\n * Returns a Promise that resolves with the currently logged-in user object.\n * If the user is already loaded in the session store, the Promise resolves immediately.\n * Otherwise, it subscribes to the session store and resolves when a logged-in user\n * becomes available.\n *\n * @returns A Promise that resolves with the LoggedInUser object once available.\n *\n * @example\n * ```ts\n * import { getLoggedInUser } from '@openmrs/esm-api';\n * const user = await getLoggedInUser();\n * console.log('Logged in as:', user.display);\n * ```\n */ function getLoggedInUser() {\n let user;\n let unsubscribe;\n return new Promise((res)=>{\n const handler = (state)=>{\n if (state.loaded && state.session.user) {\n user = state.session.user;\n res(state.session.user);\n if (unsubscribe) {\n unsubscribe();\n }\n }\n };\n handler(sessionStore.getState());\n if (!user) {\n unsubscribe = sessionStore.subscribe(handler);\n }\n });\n}\n/**\n * Returns a Promise that resolves with the current session location, if one is set.\n * The session location represents the physical location where the user is currently\n * working (e.g., a clinic or ward).\n *\n * @returns A Promise that resolves with the SessionLocation object, or `undefined`\n * if no session location is set.\n *\n * @example\n * ```ts\n * import { getSessionLocation } from '@openmrs/esm-api';\n * const location = await getSessionLocation();\n * if (location) {\n * console.log('Current location:', location.display);\n * }\n * ```\n */ async function getSessionLocation() {\n const session = await getCurrentUser();\n return session.sessionLocation;\n}\n/**\n * Sets the session location for the current user. The session location represents\n * the physical location where the user is working (e.g., a clinic or ward).\n * This triggers a server request to update the session and refreshes the local\n * session store.\n *\n * @param locationUuid The UUID of the location to set as the session location.\n * @param abortController An AbortController to allow cancellation of the request.\n * @returns A Promise that resolves with the updated SessionStore.\n *\n * @example\n * ```ts\n * import { setSessionLocation } from '@openmrs/esm-api';\n * const abortController = new AbortController();\n * await setSessionLocation('location-uuid-here', abortController);\n * ```\n */ async function setSessionLocation(locationUuid, abortController) {\n return handleSessionResponse((0,_openmrs_fetch_js__rspack_import_2.openmrsFetch)(_openmrs_fetch_js__rspack_import_2.sessionEndpoint, {\n method: 'POST',\n body: {\n sessionLocation: locationUuid\n },\n headers: {\n 'Content-Type': 'application/json'\n },\n rejectAuthFailure: true,\n signal: abortController?.signal\n }));\n}\n/**\n * Sets the locale for the current session only, leaving the user's default locale unchanged.\n * Use {@link setUserProperties} with a `defaultLocale` property to change the default instead.\n *\n * @param locale The locale in Java's `Locale#toString()` form, e.g. `en_GB`.\n * @param abortController Optional AbortController to allow cancellation of the request.\n * @returns A Promise that resolves with the updated SessionStore after refetching the current user.\n * It rejects with an {@link OpenmrsFetchError} if the server does not accept the locale.\n *\n * @example\n * ```ts\n * import { setSessionLocale } from '@openmrs/esm-api';\n * await setSessionLocale('fr');\n * ```\n *\n * @internal\n */ async function setSessionLocale(locale, abortController) {\n await (0,_openmrs_fetch_js__rspack_import_2.openmrsFetch)(_openmrs_fetch_js__rspack_import_2.sessionEndpoint, {\n method: 'POST',\n body: {\n locale\n },\n headers: {\n 'Content-Type': 'application/json'\n },\n signal: abortController?.signal\n });\n return refetchCurrentUser();\n}\n/**\n * Updates the user properties for a specific user. User properties are key-value\n * pairs that store user-specific settings and preferences. After updating the\n * properties on the server, the current user session is refetched to reflect\n * the changes.\n *\n * @param userUuid The UUID of the user whose properties should be updated.\n * @param userProperties An object containing the properties to set or update.\n * @param abortController Optional AbortController to allow cancellation of the request.\n * If not provided, a new AbortController is created.\n * @returns A Promise that resolves with the updated SessionStore after refetching\n * the current user.\n *\n * @example\n * ```ts\n * import { getLoggedInUser, setUserProperties } from '@openmrs/esm-api';\n * const user = await getLoggedInUser();\n * await setUserProperties(user.uuid, {\n * defaultLocale: 'en_GB',\n * customSetting: 'value'\n * });\n * ```\n */ async function setUserProperties(userUuid, userProperties, abortController) {\n if (!abortController) {\n abortController = new AbortController();\n }\n await (0,_openmrs_fetch_js__rspack_import_2.openmrsFetch)(`${_openmrs_fetch_js__rspack_import_2.restBaseUrl}/user/${userUuid}`, {\n method: 'POST',\n body: {\n userProperties\n },\n headers: {\n 'Content-Type': 'application/json'\n },\n signal: abortController.signal\n });\n return refetchCurrentUser();\n}\n/**\n * Submits a TOTP code to complete a two-factor login challenge. When the code is accepted, the\n * session store is refreshed with the now-authenticated session.\n *\n * @param code The code from the user's authenticator app.\n * @param rememberDevice Whether the server should skip the challenge on this device in future.\n * @returns A Promise resolving to the session. Its `authenticated` property is `false` if the\n * code was not accepted. It rejects with an {@link OpenmrsFetchError} if the server rejects the\n * request, in which case `responseBody` may explain why.\n *\n * @example\n * ```ts\n * import { verifyTotpCode } from '@openmrs/esm-api';\n * const session = await verifyTotpCode('123456', true);\n * ```\n *\n * @internal\n */ async function verifyTotpCode(code, rememberDevice = false) {\n const response = await (0,_openmrs_fetch_js__rspack_import_2.openmrsFetch)(rememberDevice ? `${_openmrs_fetch_js__rspack_import_2.sessionEndpoint}?rememberMe=true` : _openmrs_fetch_js__rspack_import_2.sessionEndpoint, {\n headers: {\n 'X-Totp-Code': code\n }\n });\n if (response.data?.authenticated) {\n // `refetchCurrentUser` only resolves once the store holds a session.\n const store = await refetchCurrentUser();\n return store.session;\n }\n return response.data;\n}\n/**\n * Ends the current session on the server and records a logged-out session in the session store.\n * A server that has already ended the session (401 or 403) counts as a successful logout.\n *\n * Other data cached for the logged-in user, such as SWR caches, is the caller's to clear.\n *\n * @returns A Promise that resolves once the session store holds a logged-out session.\n *\n * @example\n * ```ts\n * import { logout } from '@openmrs/esm-api';\n * await logout();\n * ```\n *\n * @internal\n */ async function logout() {\n try {\n await (0,_openmrs_fetch_js__rspack_import_2.openmrsFetch)(_openmrs_fetch_js__rspack_import_2.sessionEndpoint, {\n method: 'DELETE',\n rejectAuthFailure: true\n });\n } catch (err) {\n if (!isAuthFailure(err)) {\n throw err;\n }\n }\n clearCurrentUser();\n // The session just cleared is already correct, so a failed refresh loses nothing.\n await refetchCurrentUser().catch(()=>{});\n}\nfunction handleSessionResponse(result) {\n return new Promise((resolve, reject)=>{\n result.then((res)=>{\n if (typeof res?.data === 'object') {\n const nextState = {\n loaded: true,\n session: res.data\n };\n sessionStore.setState(nextState, true);\n resolve(nextState);\n } else if (isInitialSetupRedirect(res)) {\n reject(recordSessionFailure(Error('The server is still starting up'), true));\n } else {\n reject(recordSessionFailure(Error('The session endpoint did not respond with a session')));\n }\n }).catch((err)=>{\n // An auth failure is the session endpoint's answer for \"not logged in\", not a failed lookup.\n if (isAuthFailure(err)) {\n if (isUnauthenticatedSession(err.responseBody)) {\n sessionStore.setState({\n loaded: true,\n session: err.responseBody\n }, true);\n } else {\n clearCurrentUser();\n }\n resolve(sessionStore.getState());\n return;\n }\n if (isGatewayErrorDuringStartup(err)) {\n reject(recordSessionFailure(err, true));\n return;\n }\n (0,_openmrs_esm_error_handling__rspack_import_0.reportError)(`Failed to fetch new session information: ${err}`);\n reject(recordSessionFailure(err));\n });\n });\n}\nfunction isAuthFailure(err) {\n return err instanceof _openmrs_fetch_js__rspack_import_2.OpenmrsFetchError && (err.response.status === 401 || err.response.status === 403);\n}\n/**\n * Until the backend has finished its initial setup, it answers every request with a redirect to its\n * setup page, which `fetch()` follows, so the session request resolves with that page's HTML.\n */ function isInitialSetupRedirect(res) {\n if (!res?.redirected || !res.url) {\n return false;\n }\n try {\n return new URL(res.url, window.location.href).pathname.replace(/\\/+$/, '').endsWith('/initialsetup');\n } catch {\n return false;\n }\n}\nfunction isGatewayErrorDuringStartup(err) {\n return err instanceof _openmrs_fetch_js__rspack_import_2.OpenmrsFetchError && err.response.status === 502 && !sessionStore.getState().loaded && firstFetchTimeMillis !== undefined && Date.now() - firstFetchTimeMillis < startupGracePeriodMillis;\n}\nfunction isUnauthenticatedSession(body) {\n return typeof body === 'object' && body !== null && body.authenticated === false;\n}\n/**\n * A session that has already loaded is kept when a later fetch fails, since it is still the best answer\n * available. With nothing to fall back on, the error is recorded so the app shell can show an error page.\n */ function recordSessionFailure(err, initializing = false) {\n if (!sessionStore.getState().loaded) {\n sessionStore.setState({\n loaded: false,\n session: null,\n error: err instanceof Error ? err : Error(String(err)),\n initializing\n }, true);\n }\n return sessionStore.getState();\n}\n\n//# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiamF2YXNjcmlwdC9lc218YnVpbHRpbjpzd2MtbG9hZGVyPz9ydWxlU2V0WzFdLnJ1bGVzWzVdLnVzZVswXSEvaG9tZS9ydW5uZXIvd29yay9vcGVubXJzLWVzbS1jb3JlL29wZW5tcnMtZXNtLWNvcmUvcGFja2FnZXMvZnJhbWV3b3JrL2VzbS1hcGkvZGlzdC9jdXJyZW50LXVzZXIuanMiLCJzb3VyY2VzIjpbIndlYnBhY2s6Ly9Ab3Blbm1ycy9lc20tYXBwLXNoZWxsLy4uLy4uL2ZyYW1ld29yay9lc20tYXBpL2Rpc3QvY3VycmVudC11c2VyLmpzPzcxMjkiXSwic291cmNlc0NvbnRlbnQiOlsiLyoqIEBtb2R1bGUgQGNhdGVnb3J5IEFQSSAqLyBpbXBvcnQgeyByZXBvcnRFcnJvciB9IGZyb20gXCJAb3Blbm1ycy9lc20tZXJyb3ItaGFuZGxpbmdcIjtcbmltcG9ydCB7IGNyZWF0ZUdsb2JhbFN0b3JlIH0gZnJvbSBcIkBvcGVubXJzL2VzbS1zdGF0ZVwiO1xuaW1wb3J0IHsgaXNVbmRlZmluZWQgfSBmcm9tIFwibG9kYXNoLWVzXCI7XG5pbXBvcnQgeyBPcGVubXJzRmV0Y2hFcnJvciwgb3Blbm1yc0ZldGNoLCByZXN0QmFzZVVybCwgc2Vzc2lvbkVuZHBvaW50IH0gZnJvbSBcIi4vb3Blbm1ycy1mZXRjaC5qc1wiO1xuLyoqIEBpbnRlcm5hbCAqLyBleHBvcnQgY29uc3Qgc2Vzc2lvblN0b3JlID0gY3JlYXRlR2xvYmFsU3RvcmUoJ3Nlc3Npb24nLCB7XG4gICAgbG9hZGVkOiBmYWxzZSxcbiAgICBzZXNzaW9uOiBudWxsXG59KTtcbi8qKlxuICogVGhlIHVwcGVyIGJvdW5kIG9uIGhvdyBvbGQgdGhlIHNlc3Npb24gaGFuZGVkIHRvIGEgcmVhZGVyIG1heSBiZS4gSXQgaXMgbWVhc3VyZWQgZnJvbSB0aGUgbW9tZW50IGFcbiAqIGZldGNoIGlzICpzdGFydGVkKiwgbm90IGZyb20gdGhlIG1vbWVudCBpdHMgcmVzcG9uc2UgbGFuZHMsIHNvIHRoZSBzZXNzaW9uIGEgcmVhZGVyIHNlZXMgaXMgYWx3YXlzXG4gKiBzdHJpY3RseSBuZXdlciB0aGFuIHRoaXMuXG4gKi8gY29uc3Qgc2Vzc2lvbk1heEFnZU1pbGxpcyA9IDYwICogMTAwMDtcbmxldCBsYXN0RmV0Y2hUaW1lTWlsbGlzID0gMDtcbi8qKlxuICogSG93IGxvbmcgYWZ0ZXIgdGhlIGZpcnN0IHNlc3Npb24gZmV0Y2ggYSA1MDIgaXMgdGFrZW4gdG8gbWVhbiB0aGF0IHRoZSBiYWNrZW5kIGlzIHN0aWxsIHN0YXJ0aW5nIHVwLiBBXG4gKiBnYXRld2F5IGFuc3dlcnMgd2l0aCBhIDUwMiB1bnRpbCB0aGUgYmFja2VuZCBoYXMgZGVwbG95ZWQsIHdoaWNoIGNhbiB0YWtlIGEgZmV3IG1pbnV0ZXMgYWZ0ZXIgYSByZXN0YXJ0LlxuICovIGNvbnN0IHN0YXJ0dXBHcmFjZVBlcmlvZE1pbGxpcyA9IDMgKiA2MCAqIDEwMDA7XG5sZXQgZmlyc3RGZXRjaFRpbWVNaWxsaXM7XG5sZXQgaW5GbGlnaHRSZWZyZXNoID0gbnVsbDtcbi8qKlxuICogRmV0Y2hlcyB0aGUgc2Vzc2lvbiBpZiB0aGUgc3RvcmUgaXMgdW5sb2FkZWQgb3IgaXRzIHNlc3Npb24gaXMgb2xkZXIgdGhhbiBgc2Vzc2lvbk1heEFnZU1pbGxpc2AuXG4gKiBSZXR1cm5zIGBudWxsYCBvbmx5IHdoZW4gdGhlIHN0b3JlIGFscmVhZHkgaG9sZHMgYSBzZXNzaW9uIGZyZXNoIGVub3VnaCB0byBiZSByZWFkIGFzLWlzLCBzbyBhXG4gKiBjYWxsZXIgdGhhdCBnZXRzIGEgcHJvbWlzZSBiYWNrIG11c3Qgd2FpdCBmb3IgaXQgcmF0aGVyIHRoYW4gcmVhZCB0aGUgc3RvcmUuXG4gKlxuICogQSBmZXRjaCBhbHJlYWR5IGluIGZsaWdodCBpcyBqb2luZWQgcmF0aGVyIHRoYW4gZHVwbGljYXRlZC4gVGhpcyBpcyB3aGF0IGtlZXBzIGBzZXNzaW9uTWF4QWdlTWlsbGlzYFxuICogYW4gdXBwZXIgYm91bmQ6IHdoaWxlIGEgZmV0Y2ggaXMgcnVubmluZywgdGhlIHN0b3JlIHN0aWxsIGhvbGRzIHRoZSBwcmV2aW91cyBzZXNzaW9uLCBhbmQgcmV0dXJuaW5nXG4gKiB0aGF0IHdvdWxkIGhhbmQgYmFjayBkYXRhIG9sZGVyIHRoYW4gdGhlIGJvdW5kIGFsbG93cy5cbiAqXG4gKiBUaGUgcmV0dXJuZWQgcHJvbWlzZSByZWplY3RzIGlmIHRoZSBmZXRjaCBmYWlscywgYnV0IHRoZSByZWplY3Rpb24gaXMgYWxyZWFkeSBoYW5kbGVkIGFuZCByZXBvcnRlZCxcbiAqIHNvIGEgY2FsbGVyIHRoYXQgb25seSBuZWVkcyB0aGUgZmV0Y2ggc3RhcnRlZCBjYW4gaWdub3JlIGl0LlxuICovIGZ1bmN0aW9uIHJlZnJlc2hTZXNzaW9uSWZTdGFsZSgpIHtcbiAgICBpZiAoaW5GbGlnaHRSZWZyZXNoKSB7XG4gICAgICAgIHJldHVybiBpbkZsaWdodFJlZnJlc2g7XG4gICAgfVxuICAgIGlmIChzZXNzaW9uU3RvcmUuZ2V0U3RhdGUoKS5sb2FkZWQgJiYgbGFzdEZldGNoVGltZU1pbGxpcyA+PSBEYXRlLm5vdygpIC0gc2Vzc2lvbk1heEFnZU1pbGxpcykge1xuICAgICAgICByZXR1cm4gbnVsbDtcbiAgICB9XG4gICAgcmV0dXJuIHJlZmV0Y2hDdXJyZW50VXNlcigpO1xufVxuZnVuY3Rpb24gZ2V0Q3VycmVudFVzZXIob3B0cykge1xuICAgIGNvbnN0IGluY2x1ZGVBdXRoU3RhdHVzID0gb3B0cz8uaW5jbHVkZUF1dGhTdGF0dXMgPz8gdHJ1ZTtcbiAgICBjb25zdCBzZWxlY3QgPSAoc2Vzc2lvbik9PmluY2x1ZGVBdXRoU3RhdHVzID8gc2Vzc2lvbiA6IHNlc3Npb24udXNlcjtcbiAgICBjb25zdCByZWZyZXNoID0gcmVmcmVzaFNlc3Npb25JZlN0YWxlKCk7XG4gICAgaWYgKCFyZWZyZXNoKSB7XG4gICAgICAgIHJldHVybiBQcm9taXNlLnJlc29sdmUoc2VsZWN0KHNlc3Npb25TdG9yZS5nZXRTdGF0ZSgpLnNlc3Npb24pKTtcbiAgICB9XG4gICAgcmV0dXJuIG5ldyBQcm9taXNlKChyZXNvbHZlKT0+e1xuICAgICAgICBjb25zdCByZXNvbHZlSWZMb2FkZWQgPSAoKT0+e1xuICAgICAgICAgICAgY29uc3Qgc3RhdGUgPSBzZXNzaW9uU3RvcmUuZ2V0U3RhdGUoKTtcbiAgICAgICAgICAgIGlmIChzdGF0ZS5sb2FkZWQpIHtcbiAgICAgICAgICAgICAgICB1bnN1YnNjcmliZSgpO1xuICAgICAgICAgICAgICAgIHJlc29sdmUoc2VsZWN0KHN0YXRlLnNlc3Npb24pKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgfTtcbiAgICAgICAgY29uc3QgdW5zdWJzY3JpYmUgPSBzZXNzaW9uU3RvcmUuc3Vic2NyaWJlKHJlc29sdmVJZkxvYWRlZCk7XG4gICAgICAgIC8vIEEgZmFpbGVkIHJlZnJlc2gga2VlcHMgYW4gYWxyZWFkeS1sb2FkZWQgc2Vzc2lvbiB3aXRob3V0IHVwZGF0aW5nIHRoZSBzdG9yZSwgc28gdGhlXG4gICAgICAgIC8vIHN1YnNjcmlwdGlvbiBhbG9uZSB3b3VsZCBuZXZlciBmaXJlLlxuICAgICAgICByZWZyZXNoLnRoZW4ocmVzb2x2ZUlmTG9hZGVkLCByZXNvbHZlSWZMb2FkZWQpO1xuICAgIH0pO1xufVxuZXhwb3J0IHsgZ2V0Q3VycmVudFVzZXIgfTtcbi8qKlxuICogUmV0dXJucyB0aGUgZ2xvYmFsIHNlc3Npb24gc3RvcmUgY29udGFpbmluZyB0aGUgY3VycmVudCB1c2VyJ3Mgc2Vzc2lvbiBpbmZvcm1hdGlvbi5cbiAqIElmIHRoZSBzZXNzaW9uIGRhdGEgaXMgc3RhbGUgKG9sZGVyIHRoYW4gMSBtaW51dGUpIG9yIG5vdCB5ZXQgbG9hZGVkLCB0aGlzIGZ1bmN0aW9uXG4gKiB3aWxsIHRyaWdnZXIgYSByZWZldGNoIG9mIHRoZSBjdXJyZW50IHVzZXIncyBzZXNzaW9uLlxuICpcbiAqIEByZXR1cm5zIFRoZSBnbG9iYWwgc2Vzc2lvbiBzdG9yZSB0aGF0IGNhbiBiZSBzdWJzY3JpYmVkIHRvIGZvciBzZXNzaW9uIHVwZGF0ZXMuXG4gKlxuICogQGV4YW1wbGVcbiAqIGBgYHRzXG4gKiBpbXBvcnQgeyBnZXRTZXNzaW9uU3RvcmUgfSBmcm9tICdAb3Blbm1ycy9lc20tYXBpJztcbiAqIGNvbnN0IHN0b3JlID0gZ2V0U2Vzc2lvblN0b3JlKCk7XG4gKiBjb25zdCB1bnN1YnNjcmliZSA9IHN0b3JlLnN1YnNjcmliZSgoc3RhdGUpID0+IHtcbiAqICAgaWYgKHN0YXRlLmxvYWRlZCkge1xuICogICAgIGNvbnNvbGUubG9nKCdTZXNzaW9uOicsIHN0YXRlLnNlc3Npb24pO1xuICogICB9XG4gKiB9KTtcbiAqIGBgYFxuICovIGV4cG9ydCBmdW5jdGlvbiBnZXRTZXNzaW9uU3RvcmUoKSB7XG4gICAgdm9pZCByZWZyZXNoU2Vzc2lvbklmU3RhbGUoKTtcbiAgICByZXR1cm4gc2Vzc2lvblN0b3JlO1xufVxuLy8gTkIgbG9jYWxlIGlzIHN0cmluZyBvbmx5IGlmIHRoaXMgcmV0dXJucyB0cnVlXG5mdW5jdGlvbiBpc1ZhbGlkTG9jYWxlKGxvY2FsZSkge1xuICAgIGlmIChsb2NhbGUgPT09IHVuZGVmaW5lZCB8fCB0eXBlb2YgbG9jYWxlICE9PSAnc3RyaW5nJykge1xuICAgICAgICByZXR1cm4gZmFsc2U7XG4gICAgfVxuICAgIHRyeSB7XG4gICAgICAgIG5ldyBJbnRsLkxvY2FsZShsb2NhbGUpO1xuICAgIH0gY2F0Y2ggKGUpIHtcbiAgICAgICAgcmV0dXJuIGZhbHNlO1xuICAgIH1cbiAgICByZXR1cm4gdHJ1ZTtcbn1cbi8qKlxuICogU2V0cyB0aGUgZG9jdW1lbnQncyBsYW5ndWFnZSBhdHRyaWJ1dGUgYmFzZWQgb24gdGhlIHVzZXIncyBsb2NhbGUgcHJlZmVyZW5jZVxuICogZnJvbSB0aGUgc2Vzc2lvbiBkYXRhLiBUaGlzIGFmZmVjdHMgdGhlIEhUTUwgYGxhbmdgIGF0dHJpYnV0ZSB3aGljaCBpcyB1c2VkXG4gKiBmb3IgYWNjZXNzaWJpbGl0eSBhbmQgaW50ZXJuYXRpb25hbGl6YXRpb24uXG4gKlxuICogVGhlIGxvY2FsZSBpcyBkZXRlcm1pbmVkIGZyb20gZWl0aGVyIHRoZSBzZXNzaW9uJ3MgbG9jYWxlIG9yIHRoZSB1c2VyJ3NcbiAqIGRlZmF1bHQgbG9jYWxlIHByb3BlcnR5LiBVbmRlcnNjb3JlcyBpbiB0aGUgbG9jYWxlIGFyZSBjb252ZXJ0ZWQgdG8gaHlwaGVuc1xuICogdG8gbWF0Y2ggQkNQIDQ3IGxhbmd1YWdlIHRhZyBmb3JtYXQuXG4gKlxuICogQHBhcmFtIGRhdGEgVGhlIHNlc3Npb24gb2JqZWN0IGNvbnRhaW5pbmcgbG9jYWxlIGluZm9ybWF0aW9uLlxuICovIGV4cG9ydCBmdW5jdGlvbiBzZXRVc2VyTGFuZ3VhZ2UoZGF0YSkge1xuICAgIGxldCBsb2NhbGUgPSBkYXRhLmxvY2FsZSA/PyBkYXRhLnVzZXI/LnVzZXJQcm9wZXJ0aWVzPy5kZWZhdWx0TG9jYWxlO1xuICAgIC8vIE9ubHkgdW5kZXJzY29yZXMgYXJlIGNvbnZlcnRlZCBoZXJlLCBkZWxpYmVyYXRlbHksIHJhdGhlciB0aGFuIHJldXNpbmcgYHRvTGFuZ3VhZ2VUYWdgLiBpMThuZXh0XG4gICAgLy8gcmVhZHMgdGhpcyB2YWx1ZSBiYWNrIG9mZiBgZG9jdW1lbnQubGFuZ2AgYW5kIHVzZXMgaXQgYXMgdGhlIHRyYW5zbGF0aW9uIGJ1bmRsZSBrZXksIGFuZCB0aG9zZVxuICAgIC8vIGJ1bmRsZXMgYXJlIG5hbWVkIHdpdGggdGhlIFBPU0lYIGZvcm0gKGB1ekBMYXRuLmpzb25gKSwgc28gY29udmVydGluZyBgQGAgd291bGQgc2VuZCB0aGUgbG9hZGVyXG4gICAgLy8gYWZ0ZXIgYSBidW5kbGUgdGhhdCBkb2VzIG5vdCBleGlzdC5cbiAgICBpZiAobG9jYWxlICYmIGxvY2FsZS5pbmNsdWRlcygnXycpKSB7XG4gICAgICAgIGxvY2FsZSA9IGxvY2FsZS5yZXBsYWNlQWxsKCdfJywgJy0nKTtcbiAgICB9XG4gICAgaWYgKGlzVmFsaWRMb2NhbGUobG9jYWxlKSAmJiBsb2NhbGUgIT09IGRvY3VtZW50LmRvY3VtZW50RWxlbWVudC5nZXRBdHRyaWJ1dGUoJ2xhbmcnKSkge1xuICAgICAgICBkb2N1bWVudC5kb2N1bWVudEVsZW1lbnQuc2V0QXR0cmlidXRlKCdsYW5nJywgbG9jYWxlKTtcbiAgICB9XG59XG5zZXNzaW9uU3RvcmUuc3Vic2NyaWJlKChzdGF0ZSk9PntcbiAgICBpZiAoc3RhdGUubG9hZGVkICYmIHN0YXRlLnNlc3Npb24pIHtcbiAgICAgICAgc2V0VXNlckxhbmd1YWdlKHN0YXRlLnNlc3Npb24pO1xuICAgIH1cbn0pO1xuZnVuY3Rpb24gdXNlckhhc1ByaXZpbGVnZShyZXF1aXJlZFByaXZpbGVnZSwgdXNlcikge1xuICAgIGlmICh0eXBlb2YgcmVxdWlyZWRQcml2aWxlZ2UgPT09ICdzdHJpbmcnKSB7XG4gICAgICAgIHJldHVybiAhaXNVbmRlZmluZWQodXNlci5wcml2aWxlZ2VzLmZpbmQoKHApPT5yZXF1aXJlZFByaXZpbGVnZSA9PT0gcC5kaXNwbGF5KSk7XG4gICAgfSBlbHNlIGlmIChBcnJheS5pc0FycmF5KHJlcXVpcmVkUHJpdmlsZWdlKSkge1xuICAgICAgICByZXR1cm4gcmVxdWlyZWRQcml2aWxlZ2UuZXZlcnkoKHJwKT0+IWlzVW5kZWZpbmVkKHVzZXIucHJpdmlsZWdlcy5maW5kKChwKT0+cnAgPT09IHAuZGlzcGxheSkpKTtcbiAgICB9IGVsc2UgaWYgKCFpc1VuZGVmaW5lZChyZXF1aXJlZFByaXZpbGVnZSkpIHtcbiAgICAgICAgY29uc29sZS5lcnJvcihgQ291bGQgbm90IHVuZGVyc3RhbmQgcHJpdmlsZWdlcyBcIiR7cmVxdWlyZWRQcml2aWxlZ2V9XCJgKTtcbiAgICB9XG4gICAgcmV0dXJuIHRydWU7XG59XG5mdW5jdGlvbiBpc1N1cGVyVXNlcih1c2VyKSB7XG4gICAgcmV0dXJuICFpc1VuZGVmaW5lZCh1c2VyLnJvbGVzLmZpbmQoKHJvbGUpPT5yb2xlLmRpc3BsYXkgPT09ICdTeXN0ZW0gRGV2ZWxvcGVyJykpO1xufVxuLyoqXG4gKiBUaGUgYHJlZmV0Y2hDdXJyZW50VXNlcmAgZnVuY3Rpb24gY2F1c2VzIGEgbmV0d29yayByZXF1ZXN0IHRvIHJlZG93bmxvYWRcbiAqIHRoZSB1c2VyLiBBbGwgc3Vic2NyaWJlcnMgdG8gdGhlIHNlc3Npb24gc3RvcmUgd2lsbCBiZSBub3RpZmllZCBvZiB0aGVcbiAqIG5ldyB1c2VyIG9uY2UgdGhlIG5ldyB2ZXJzaW9uIG9mIHRoZSB1c2VyIG9iamVjdCBpcyBkb3dubG9hZGVkLlxuICpcbiAqIElmIHRoZSBzZXJ2ZXIgcmVqZWN0cyB0aGUgcmVxdWVzdCBhcyB1bmF1dGhlbnRpY2F0ZWQgKDQwMSBvciA0MDMpLCB0aGUgc3RvcmUgcmVjb3JkcyBhXG4gKiBsb2dnZWQtb3V0IHNlc3Npb24uIElmIHRoZSByZXF1ZXN0IGZhaWxzIGZvciBhbnkgb3RoZXIgcmVhc29uLCBhIHNlc3Npb24gdGhhdCBoYXMgYWxyZWFkeVxuICogbG9hZGVkIGlzIGtlcHQ7IG90aGVyd2lzZSB0aGUgc3RvcmUgcmVjb3JkcyB0aGUgZXJyb3IuXG4gKlxuICogQHJldHVybnMgQSBQcm9taXNlIHJlc29sdmluZyB0byB0aGUgdXBkYXRlZCBzZXNzaW9uIHN0b3JlIHN0YXRlLiBJdCByZWplY3RzIHdpdGggdGhlXG4gKiAgIHN0b3JlIHN0YXRlIGlmIHRoZSByZXF1ZXN0IGZhaWxzIGZvciBhIHJlYXNvbiBvdGhlciB0aGFuIGF1dGhlbnRpY2F0aW9uLlxuICpcbiAqIEBleGFtcGxlXG4gKiBgYGBqc1xuICogaW1wb3J0IHsgcmVmZXRjaEN1cnJlbnRVc2VyIH0gZnJvbSAnQG9wZW5tcnMvZXNtLWFwaSdcbiAqIHJlZmV0Y2hDdXJyZW50VXNlcigpXG4gKiBgYGBcbiAqLyBleHBvcnQgZnVuY3Rpb24gcmVmZXRjaEN1cnJlbnRVc2VyKHVzZXJuYW1lLCBwYXNzd29yZCkge1xuICAgIGxhc3RGZXRjaFRpbWVNaWxsaXMgPSBEYXRlLm5vdygpO1xuICAgIGZpcnN0RmV0Y2hUaW1lTWlsbGlzID8/IChmaXJzdEZldGNoVGltZU1pbGxpcyA9IGxhc3RGZXRjaFRpbWVNaWxsaXMpO1xuICAgIGxldCBoZWFkZXJzID0ge307XG4gICAgaWYgKHVzZXJuYW1lICYmIHBhc3N3b3JkKSB7XG4gICAgICAgIGhlYWRlcnNbJ0F1dGhvcml6YXRpb24nXSA9IGBCYXNpYyAke3dpbmRvdy5idG9hKGAke3VzZXJuYW1lfToke3Bhc3N3b3JkfWApfWA7XG4gICAgfVxuICAgIGNvbnN0IHJlZnJlc2ggPSBoYW5kbGVTZXNzaW9uUmVzcG9uc2Uob3Blbm1yc0ZldGNoKHNlc3Npb25FbmRwb2ludCwge1xuICAgICAgICBoZWFkZXJzLFxuICAgICAgICByZWplY3RBdXRoRmFpbHVyZTogdHJ1ZVxuICAgIH0pKTtcbiAgICAvLyBQdWJsaXNoIHRoZSByZXF1ZXN0IHNvIHRoYXQgcmVhZGVycyBjYW4gd2FpdCBvbiBpdCBpbnN0ZWFkIG9mIHJlYWRpbmcgdGhlIHNlc3Npb24gaXQgaXMgYWJvdXQgdG9cbiAgICAvLyByZXBsYWNlLiBFYWNoIGNhbGwgc3RpbGwgaXNzdWVzIGl0cyBvd24gcmVxdWVzdDsgdGhpcyBvbmx5IHRyYWNrcyB0aGUgbW9zdCByZWNlbnQgb25lLlxuICAgIGNvbnN0IGNsZWFyID0gKCk9PntcbiAgICAgICAgaWYgKGluRmxpZ2h0UmVmcmVzaCA9PT0gcmVmcmVzaCkge1xuICAgICAgICAgICAgaW5GbGlnaHRSZWZyZXNoID0gbnVsbDtcbiAgICAgICAgfVxuICAgIH07XG4gICAgcmVmcmVzaC50aGVuKGNsZWFyLCBjbGVhcik7XG4gICAgaW5GbGlnaHRSZWZyZXNoID0gcmVmcmVzaDtcbiAgICByZXR1cm4gcmVmcmVzaDtcbn1cbi8qKlxuICogQ2xlYXJzIHRoZSBjdXJyZW50IHVzZXIgc2Vzc2lvbiBmcm9tIHRoZSBzZXNzaW9uIHN0b3JlLCBzZXR0aW5nIHRoZSBzZXNzaW9uXG4gKiB0byBhbiB1bmF1dGhlbnRpY2F0ZWQgc3RhdGUuIFRoaXMgaXMgdHlwaWNhbGx5IGNhbGxlZCBkdXJpbmcgbG9nb3V0IHRvIHJlc2V0XG4gKiB0aGUgYXBwbGljYXRpb24ncyBhdXRoZW50aWNhdGlvbiBzdGF0ZS5cbiAqXG4gKiBAZXhhbXBsZVxuICogYGBgdHNcbiAqIGltcG9ydCB7IGNsZWFyQ3VycmVudFVzZXIgfSBmcm9tICdAb3Blbm1ycy9lc20tYXBpJztcbiAqIC8vIER1cmluZyBsb2dvdXRcbiAqIGNsZWFyQ3VycmVudFVzZXIoKTtcbiAqIGBgYFxuICovIGV4cG9ydCBmdW5jdGlvbiBjbGVhckN1cnJlbnRVc2VyKCkge1xuICAgIHNlc3Npb25TdG9yZS5zZXRTdGF0ZSh7XG4gICAgICAgIGxvYWRlZDogdHJ1ZSxcbiAgICAgICAgc2Vzc2lvbjoge1xuICAgICAgICAgICAgYXV0aGVudGljYXRlZDogZmFsc2UsXG4gICAgICAgICAgICBzZXNzaW9uSWQ6ICcnXG4gICAgICAgIH1cbiAgICB9LCB0cnVlKTtcbn1cbi8qKlxuICogQ2hlY2tzIHdoZXRoZXIgdGhlIGdpdmVuIHVzZXIgaGFzIGFjY2VzcyBiYXNlZCBvbiB0aGUgcmVxdWlyZWQgcHJpdmlsZWdlKHMpLlxuICogQSB1c2VyIGhhcyBhY2Nlc3MgaWYgdGhleSBoYXZlIHRoZSByZXF1aXJlZCBwcml2aWxlZ2Uocykgb3IgaWYgdGhleSBhcmUgYVxuICogXCJTeXN0ZW0gRGV2ZWxvcGVyXCIgKHN1cGVyIHVzZXIpLiBJZiBubyBwcml2aWxlZ2UgaXMgcmVxdWlyZWQsIGFjY2VzcyBpcyBncmFudGVkLlxuICpcbiAqIEBwYXJhbSByZXF1aXJlZFByaXZpbGVnZSBBIHNpbmdsZSBwcml2aWxlZ2Ugc3RyaW5nIG9yIGFuIGFycmF5IG9mIHByaXZpbGVnZSBzdHJpbmdzXG4gKiAgIHRoYXQgdGhlIHVzZXIgbXVzdCBoYXZlLiBJZiBhbiBhcnJheSBpcyBwcm92aWRlZCwgdGhlIHVzZXIgbXVzdCBoYXZlIEFMTCBwcml2aWxlZ2VzLlxuICogQHBhcmFtIHVzZXIgVGhlIHVzZXIgb2JqZWN0IGNvbnRhaW5pbmcgdGhlaXIgcHJpdmlsZWdlcyBhbmQgcm9sZXMuXG4gKiBAcmV0dXJucyBgdHJ1ZWAgaWYgdGhlIHVzZXIgaGFzIGFjY2VzcywgYGZhbHNlYCBvdGhlcndpc2UuIFJldHVybnMgYHRydWVgIGlmIG5vXG4gKiAgIHByaXZpbGVnZSBpcyByZXF1aXJlZCwgYW5kIGBmYWxzZWAgaWYgdGhlIHVzZXIgaXMgdW5kZWZpbmVkIGJ1dCBhIHByaXZpbGVnZSBpcyByZXF1aXJlZC5cbiAqXG4gKiBAZXhhbXBsZVxuICogYGBgdHNcbiAqIGltcG9ydCB7IHVzZXJIYXNBY2Nlc3MgfSBmcm9tICdAb3Blbm1ycy9lc20tYXBpJztcbiAqIGNvbnN0IGhhc0FjY2VzcyA9IHVzZXJIYXNBY2Nlc3MoJ1ZpZXcgUGF0aWVudHMnLCBjdXJyZW50VXNlcik7XG4gKiBjb25zdCBoYXNNdWx0aXBsZUFjY2VzcyA9IHVzZXJIYXNBY2Nlc3MoWydWaWV3IFBhdGllbnRzJywgJ0VkaXQgUGF0aWVudHMnXSwgY3VycmVudFVzZXIpO1xuICogYGBgXG4gKi8gZXhwb3J0IGZ1bmN0aW9uIHVzZXJIYXNBY2Nlc3MocmVxdWlyZWRQcml2aWxlZ2UsIHVzZXIpIHtcbiAgICBpZiAodXNlciA9PT0gdW5kZWZpbmVkKSB7XG4gICAgICAgIC8vIGlmIHRoZSB1c2VyIGhhc24ndCBiZWVuIGxvYWRlZCwgdGhlbiByZXR1cm4gZmFsc2UgaWZmIHRoZXJlIGlzIGEgcmVxdWlyZWQgcHJpdmlsZWdlXG4gICAgICAgIHJldHVybiAhQm9vbGVhbihyZXF1aXJlZFByaXZpbGVnZSk7XG4gICAgfVxuICAgIGlmICghQm9vbGVhbihyZXF1aXJlZFByaXZpbGVnZSkpIHtcbiAgICAgICAgLy8gaWYgdXNlciBleGlzdHMgYnV0IG5vIHJlcXVpcmVkUHJpdmlsZWdlIGlzIGRlZmluZWRcbiAgICAgICAgcmV0dXJuIHRydWU7XG4gICAgfVxuICAgIHJldHVybiB1c2VySGFzUHJpdmlsZWdlKHJlcXVpcmVkUHJpdmlsZWdlLCB1c2VyKSB8fCBpc1N1cGVyVXNlcih1c2VyKTtcbn1cbi8qKlxuICogUmV0dXJucyBhIFByb21pc2UgdGhhdCByZXNvbHZlcyB3aXRoIHRoZSBjdXJyZW50bHkgbG9nZ2VkLWluIHVzZXIgb2JqZWN0LlxuICogSWYgdGhlIHVzZXIgaXMgYWxyZWFkeSBsb2FkZWQgaW4gdGhlIHNlc3Npb24gc3RvcmUsIHRoZSBQcm9taXNlIHJlc29sdmVzIGltbWVkaWF0ZWx5LlxuICogT3RoZXJ3aXNlLCBpdCBzdWJzY3JpYmVzIHRvIHRoZSBzZXNzaW9uIHN0b3JlIGFuZCByZXNvbHZlcyB3aGVuIGEgbG9nZ2VkLWluIHVzZXJcbiAqIGJlY29tZXMgYXZhaWxhYmxlLlxuICpcbiAqIEByZXR1cm5zIEEgUHJvbWlzZSB0aGF0IHJlc29sdmVzIHdpdGggdGhlIExvZ2dlZEluVXNlciBvYmplY3Qgb25jZSBhdmFpbGFibGUuXG4gKlxuICogQGV4YW1wbGVcbiAqIGBgYHRzXG4gKiBpbXBvcnQgeyBnZXRMb2dnZWRJblVzZXIgfSBmcm9tICdAb3Blbm1ycy9lc20tYXBpJztcbiAqIGNvbnN0IHVzZXIgPSBhd2FpdCBnZXRMb2dnZWRJblVzZXIoKTtcbiAqIGNvbnNvbGUubG9nKCdMb2dnZWQgaW4gYXM6JywgdXNlci5kaXNwbGF5KTtcbiAqIGBgYFxuICovIGV4cG9ydCBmdW5jdGlvbiBnZXRMb2dnZWRJblVzZXIoKSB7XG4gICAgbGV0IHVzZXI7XG4gICAgbGV0IHVuc3Vic2NyaWJlO1xuICAgIHJldHVybiBuZXcgUHJvbWlzZSgocmVzKT0+e1xuICAgICAgICBjb25zdCBoYW5kbGVyID0gKHN0YXRlKT0+e1xuICAgICAgICAgICAgaWYgKHN0YXRlLmxvYWRlZCAmJiBzdGF0ZS5zZXNzaW9uLnVzZXIpIHtcbiAgICAgICAgICAgICAgICB1c2VyID0gc3RhdGUuc2Vzc2lvbi51c2VyO1xuICAgICAgICAgICAgICAgIHJlcyhzdGF0ZS5zZXNzaW9uLnVzZXIpO1xuICAgICAgICAgICAgICAgIGlmICh1bnN1YnNjcmliZSkge1xuICAgICAgICAgICAgICAgICAgICB1bnN1YnNjcmliZSgpO1xuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgIH1cbiAgICAgICAgfTtcbiAgICAgICAgaGFuZGxlcihzZXNzaW9uU3RvcmUuZ2V0U3RhdGUoKSk7XG4gICAgICAgIGlmICghdXNlcikge1xuICAgICAgICAgICAgdW5zdWJzY3JpYmUgPSBzZXNzaW9uU3RvcmUuc3Vic2NyaWJlKGhhbmRsZXIpO1xuICAgICAgICB9XG4gICAgfSk7XG59XG4vKipcbiAqIFJldHVybnMgYSBQcm9taXNlIHRoYXQgcmVzb2x2ZXMgd2l0aCB0aGUgY3VycmVudCBzZXNzaW9uIGxvY2F0aW9uLCBpZiBvbmUgaXMgc2V0LlxuICogVGhlIHNlc3Npb24gbG9jYXRpb24gcmVwcmVzZW50cyB0aGUgcGh5c2ljYWwgbG9jYXRpb24gd2hlcmUgdGhlIHVzZXIgaXMgY3VycmVudGx5XG4gKiB3b3JraW5nIChlLmcuLCBhIGNsaW5pYyBvciB3YXJkKS5cbiAqXG4gKiBAcmV0dXJucyBBIFByb21pc2UgdGhhdCByZXNvbHZlcyB3aXRoIHRoZSBTZXNzaW9uTG9jYXRpb24gb2JqZWN0LCBvciBgdW5kZWZpbmVkYFxuICogICBpZiBubyBzZXNzaW9uIGxvY2F0aW9uIGlzIHNldC5cbiAqXG4gKiBAZXhhbXBsZVxuICogYGBgdHNcbiAqIGltcG9ydCB7IGdldFNlc3Npb25Mb2NhdGlvbiB9IGZyb20gJ0BvcGVubXJzL2VzbS1hcGknO1xuICogY29uc3QgbG9jYXRpb24gPSBhd2FpdCBnZXRTZXNzaW9uTG9jYXRpb24oKTtcbiAqIGlmIChsb2NhdGlvbikge1xuICogICBjb25zb2xlLmxvZygnQ3VycmVudCBsb2NhdGlvbjonLCBsb2NhdGlvbi5kaXNwbGF5KTtcbiAqIH1cbiAqIGBgYFxuICovIGV4cG9ydCBhc3luYyBmdW5jdGlvbiBnZXRTZXNzaW9uTG9jYXRpb24oKSB7XG4gICAgY29uc3Qgc2Vzc2lvbiA9IGF3YWl0IGdldEN1cnJlbnRVc2VyKCk7XG4gICAgcmV0dXJuIHNlc3Npb24uc2Vzc2lvbkxvY2F0aW9uO1xufVxuLyoqXG4gKiBTZXRzIHRoZSBzZXNzaW9uIGxvY2F0aW9uIGZvciB0aGUgY3VycmVudCB1c2VyLiBUaGUgc2Vzc2lvbiBsb2NhdGlvbiByZXByZXNlbnRzXG4gKiB0aGUgcGh5c2ljYWwgbG9jYXRpb24gd2hlcmUgdGhlIHVzZXIgaXMgd29ya2luZyAoZS5nLiwgYSBjbGluaWMgb3Igd2FyZCkuXG4gKiBUaGlzIHRyaWdnZXJzIGEgc2VydmVyIHJlcXVlc3QgdG8gdXBkYXRlIHRoZSBzZXNzaW9uIGFuZCByZWZyZXNoZXMgdGhlIGxvY2FsXG4gKiBzZXNzaW9uIHN0b3JlLlxuICpcbiAqIEBwYXJhbSBsb2NhdGlvblV1aWQgVGhlIFVVSUQgb2YgdGhlIGxvY2F0aW9uIHRvIHNldCBhcyB0aGUgc2Vzc2lvbiBsb2NhdGlvbi5cbiAqIEBwYXJhbSBhYm9ydENvbnRyb2xsZXIgQW4gQWJvcnRDb250cm9sbGVyIHRvIGFsbG93IGNhbmNlbGxhdGlvbiBvZiB0aGUgcmVxdWVzdC5cbiAqIEByZXR1cm5zIEEgUHJvbWlzZSB0aGF0IHJlc29sdmVzIHdpdGggdGhlIHVwZGF0ZWQgU2Vzc2lvblN0b3JlLlxuICpcbiAqIEBleGFtcGxlXG4gKiBgYGB0c1xuICogaW1wb3J0IHsgc2V0U2Vzc2lvbkxvY2F0aW9uIH0gZnJvbSAnQG9wZW5tcnMvZXNtLWFwaSc7XG4gKiBjb25zdCBhYm9ydENvbnRyb2xsZXIgPSBuZXcgQWJvcnRDb250cm9sbGVyKCk7XG4gKiBhd2FpdCBzZXRTZXNzaW9uTG9jYXRpb24oJ2xvY2F0aW9uLXV1aWQtaGVyZScsIGFib3J0Q29udHJvbGxlcik7XG4gKiBgYGBcbiAqLyBleHBvcnQgYXN5bmMgZnVuY3Rpb24gc2V0U2Vzc2lvbkxvY2F0aW9uKGxvY2F0aW9uVXVpZCwgYWJvcnRDb250cm9sbGVyKSB7XG4gICAgcmV0dXJuIGhhbmRsZVNlc3Npb25SZXNwb25zZShvcGVubXJzRmV0Y2goc2Vzc2lvbkVuZHBvaW50LCB7XG4gICAgICAgIG1ldGhvZDogJ1BPU1QnLFxuICAgICAgICBib2R5OiB7XG4gICAgICAgICAgICBzZXNzaW9uTG9jYXRpb246IGxvY2F0aW9uVXVpZFxuICAgICAgICB9LFxuICAgICAgICBoZWFkZXJzOiB7XG4gICAgICAgICAgICAnQ29udGVudC1UeXBlJzogJ2FwcGxpY2F0aW9uL2pzb24nXG4gICAgICAgIH0sXG4gICAgICAgIHJlamVjdEF1dGhGYWlsdXJlOiB0cnVlLFxuICAgICAgICBzaWduYWw6IGFib3J0Q29udHJvbGxlcj8uc2lnbmFsXG4gICAgfSkpO1xufVxuLyoqXG4gKiBTZXRzIHRoZSBsb2NhbGUgZm9yIHRoZSBjdXJyZW50IHNlc3Npb24gb25seSwgbGVhdmluZyB0aGUgdXNlcidzIGRlZmF1bHQgbG9jYWxlIHVuY2hhbmdlZC5cbiAqIFVzZSB7QGxpbmsgc2V0VXNlclByb3BlcnRpZXN9IHdpdGggYSBgZGVmYXVsdExvY2FsZWAgcHJvcGVydHkgdG8gY2hhbmdlIHRoZSBkZWZhdWx0IGluc3RlYWQuXG4gKlxuICogQHBhcmFtIGxvY2FsZSBUaGUgbG9jYWxlIGluIEphdmEncyBgTG9jYWxlI3RvU3RyaW5nKClgIGZvcm0sIGUuZy4gYGVuX0dCYC5cbiAqIEBwYXJhbSBhYm9ydENvbnRyb2xsZXIgT3B0aW9uYWwgQWJvcnRDb250cm9sbGVyIHRvIGFsbG93IGNhbmNlbGxhdGlvbiBvZiB0aGUgcmVxdWVzdC5cbiAqIEByZXR1cm5zIEEgUHJvbWlzZSB0aGF0IHJlc29sdmVzIHdpdGggdGhlIHVwZGF0ZWQgU2Vzc2lvblN0b3JlIGFmdGVyIHJlZmV0Y2hpbmcgdGhlIGN1cnJlbnQgdXNlci5cbiAqICAgSXQgcmVqZWN0cyB3aXRoIGFuIHtAbGluayBPcGVubXJzRmV0Y2hFcnJvcn0gaWYgdGhlIHNlcnZlciBkb2VzIG5vdCBhY2NlcHQgdGhlIGxvY2FsZS5cbiAqXG4gKiBAZXhhbXBsZVxuICogYGBgdHNcbiAqIGltcG9ydCB7IHNldFNlc3Npb25Mb2NhbGUgfSBmcm9tICdAb3Blbm1ycy9lc20tYXBpJztcbiAqIGF3YWl0IHNldFNlc3Npb25Mb2NhbGUoJ2ZyJyk7XG4gKiBgYGBcbiAqXG4gKiBAaW50ZXJuYWxcbiAqLyBleHBvcnQgYXN5bmMgZnVuY3Rpb24gc2V0U2Vzc2lvbkxvY2FsZShsb2NhbGUsIGFib3J0Q29udHJvbGxlcikge1xuICAgIGF3YWl0IG9wZW5tcnNGZXRjaChzZXNzaW9uRW5kcG9pbnQsIHtcbiAgICAgICAgbWV0aG9kOiAnUE9TVCcsXG4gICAgICAgIGJvZHk6IHtcbiAgICAgICAgICAgIGxvY2FsZVxuICAgICAgICB9LFxuICAgICAgICBoZWFkZXJzOiB7XG4gICAgICAgICAgICAnQ29udGVudC1UeXBlJzogJ2FwcGxpY2F0aW9uL2pzb24nXG4gICAgICAgIH0sXG4gICAgICAgIHNpZ25hbDogYWJvcnRDb250cm9sbGVyPy5zaWduYWxcbiAgICB9KTtcbiAgICByZXR1cm4gcmVmZXRjaEN1cnJlbnRVc2VyKCk7XG59XG4vKipcbiAqIFVwZGF0ZXMgdGhlIHVzZXIgcHJvcGVydGllcyBmb3IgYSBzcGVjaWZpYyB1c2VyLiBVc2VyIHByb3BlcnRpZXMgYXJlIGtleS12YWx1ZVxuICogcGFpcnMgdGhhdCBzdG9yZSB1c2VyLXNwZWNpZmljIHNldHRpbmdzIGFuZCBwcmVmZXJlbmNlcy4gQWZ0ZXIgdXBkYXRpbmcgdGhlXG4gKiBwcm9wZXJ0aWVzIG9uIHRoZSBzZXJ2ZXIsIHRoZSBjdXJyZW50IHVzZXIgc2Vzc2lvbiBpcyByZWZldGNoZWQgdG8gcmVmbGVjdFxuICogdGhlIGNoYW5nZXMuXG4gKlxuICogQHBhcmFtIHVzZXJVdWlkIFRoZSBVVUlEIG9mIHRoZSB1c2VyIHdob3NlIHByb3BlcnRpZXMgc2hvdWxkIGJlIHVwZGF0ZWQuXG4gKiBAcGFyYW0gdXNlclByb3BlcnRpZXMgQW4gb2JqZWN0IGNvbnRhaW5pbmcgdGhlIHByb3BlcnRpZXMgdG8gc2V0IG9yIHVwZGF0ZS5cbiAqIEBwYXJhbSBhYm9ydENvbnRyb2xsZXIgT3B0aW9uYWwgQWJvcnRDb250cm9sbGVyIHRvIGFsbG93IGNhbmNlbGxhdGlvbiBvZiB0aGUgcmVxdWVzdC5cbiAqICAgSWYgbm90IHByb3ZpZGVkLCBhIG5ldyBBYm9ydENvbnRyb2xsZXIgaXMgY3JlYXRlZC5cbiAqIEByZXR1cm5zIEEgUHJvbWlzZSB0aGF0IHJlc29sdmVzIHdpdGggdGhlIHVwZGF0ZWQgU2Vzc2lvblN0b3JlIGFmdGVyIHJlZmV0Y2hpbmdcbiAqICAgdGhlIGN1cnJlbnQgdXNlci5cbiAqXG4gKiBAZXhhbXBsZVxuICogYGBgdHNcbiAqIGltcG9ydCB7IGdldExvZ2dlZEluVXNlciwgc2V0VXNlclByb3BlcnRpZXMgfSBmcm9tICdAb3Blbm1ycy9lc20tYXBpJztcbiAqIGNvbnN0IHVzZXIgPSBhd2FpdCBnZXRMb2dnZWRJblVzZXIoKTtcbiAqIGF3YWl0IHNldFVzZXJQcm9wZXJ0aWVzKHVzZXIudXVpZCwge1xuICogICBkZWZhdWx0TG9jYWxlOiAnZW5fR0InLFxuICogICBjdXN0b21TZXR0aW5nOiAndmFsdWUnXG4gKiB9KTtcbiAqIGBgYFxuICovIGV4cG9ydCBhc3luYyBmdW5jdGlvbiBzZXRVc2VyUHJvcGVydGllcyh1c2VyVXVpZCwgdXNlclByb3BlcnRpZXMsIGFib3J0Q29udHJvbGxlcikge1xuICAgIGlmICghYWJvcnRDb250cm9sbGVyKSB7XG4gICAgICAgIGFib3J0Q29udHJvbGxlciA9IG5ldyBBYm9ydENvbnRyb2xsZXIoKTtcbiAgICB9XG4gICAgYXdhaXQgb3Blbm1yc0ZldGNoKGAke3Jlc3RCYXNlVXJsfS91c2VyLyR7dXNlclV1aWR9YCwge1xuICAgICAgICBtZXRob2Q6ICdQT1NUJyxcbiAgICAgICAgYm9keToge1xuICAgICAgICAgICAgdXNlclByb3BlcnRpZXNcbiAgICAgICAgfSxcbiAgICAgICAgaGVhZGVyczoge1xuICAgICAgICAgICAgJ0NvbnRlbnQtVHlwZSc6ICdhcHBsaWNhdGlvbi9qc29uJ1xuICAgICAgICB9LFxuICAgICAgICBzaWduYWw6IGFib3J0Q29udHJvbGxlci5zaWduYWxcbiAgICB9KTtcbiAgICByZXR1cm4gcmVmZXRjaEN1cnJlbnRVc2VyKCk7XG59XG4vKipcbiAqIFN1Ym1pdHMgYSBUT1RQIGNvZGUgdG8gY29tcGxldGUgYSB0d28tZmFjdG9yIGxvZ2luIGNoYWxsZW5nZS4gV2hlbiB0aGUgY29kZSBpcyBhY2NlcHRlZCwgdGhlXG4gKiBzZXNzaW9uIHN0b3JlIGlzIHJlZnJlc2hlZCB3aXRoIHRoZSBub3ctYXV0aGVudGljYXRlZCBzZXNzaW9uLlxuICpcbiAqIEBwYXJhbSBjb2RlIFRoZSBjb2RlIGZyb20gdGhlIHVzZXIncyBhdXRoZW50aWNhdG9yIGFwcC5cbiAqIEBwYXJhbSByZW1lbWJlckRldmljZSBXaGV0aGVyIHRoZSBzZXJ2ZXIgc2hvdWxkIHNraXAgdGhlIGNoYWxsZW5nZSBvbiB0aGlzIGRldmljZSBpbiBmdXR1cmUuXG4gKiBAcmV0dXJucyBBIFByb21pc2UgcmVzb2x2aW5nIHRvIHRoZSBzZXNzaW9uLiBJdHMgYGF1dGhlbnRpY2F0ZWRgIHByb3BlcnR5IGlzIGBmYWxzZWAgaWYgdGhlXG4gKiAgIGNvZGUgd2FzIG5vdCBhY2NlcHRlZC4gSXQgcmVqZWN0cyB3aXRoIGFuIHtAbGluayBPcGVubXJzRmV0Y2hFcnJvcn0gaWYgdGhlIHNlcnZlciByZWplY3RzIHRoZVxuICogICByZXF1ZXN0LCBpbiB3aGljaCBjYXNlIGByZXNwb25zZUJvZHlgIG1heSBleHBsYWluIHdoeS5cbiAqXG4gKiBAZXhhbXBsZVxuICogYGBgdHNcbiAqIGltcG9ydCB7IHZlcmlmeVRvdHBDb2RlIH0gZnJvbSAnQG9wZW5tcnMvZXNtLWFwaSc7XG4gKiBjb25zdCBzZXNzaW9uID0gYXdhaXQgdmVyaWZ5VG90cENvZGUoJzEyMzQ1NicsIHRydWUpO1xuICogYGBgXG4gKlxuICogQGludGVybmFsXG4gKi8gZXhwb3J0IGFzeW5jIGZ1bmN0aW9uIHZlcmlmeVRvdHBDb2RlKGNvZGUsIHJlbWVtYmVyRGV2aWNlID0gZmFsc2UpIHtcbiAgICBjb25zdCByZXNwb25zZSA9IGF3YWl0IG9wZW5tcnNGZXRjaChyZW1lbWJlckRldmljZSA/IGAke3Nlc3Npb25FbmRwb2ludH0/cmVtZW1iZXJNZT10cnVlYCA6IHNlc3Npb25FbmRwb2ludCwge1xuICAgICAgICBoZWFkZXJzOiB7XG4gICAgICAgICAgICAnWC1Ub3RwLUNvZGUnOiBjb2RlXG4gICAgICAgIH1cbiAgICB9KTtcbiAgICBpZiAocmVzcG9uc2UuZGF0YT8uYXV0aGVudGljYXRlZCkge1xuICAgICAgICAvLyBgcmVmZXRjaEN1cnJlbnRVc2VyYCBvbmx5IHJlc29sdmVzIG9uY2UgdGhlIHN0b3JlIGhvbGRzIGEgc2Vzc2lvbi5cbiAgICAgICAgY29uc3Qgc3RvcmUgPSBhd2FpdCByZWZldGNoQ3VycmVudFVzZXIoKTtcbiAgICAgICAgcmV0dXJuIHN0b3JlLnNlc3Npb247XG4gICAgfVxuICAgIHJldHVybiByZXNwb25zZS5kYXRhO1xufVxuLyoqXG4gKiBFbmRzIHRoZSBjdXJyZW50IHNlc3Npb24gb24gdGhlIHNlcnZlciBhbmQgcmVjb3JkcyBhIGxvZ2dlZC1vdXQgc2Vzc2lvbiBpbiB0aGUgc2Vzc2lvbiBzdG9yZS5cbiAqIEEgc2VydmVyIHRoYXQgaGFzIGFscmVhZHkgZW5kZWQgdGhlIHNlc3Npb24gKDQwMSBvciA0MDMpIGNvdW50cyBhcyBhIHN1Y2Nlc3NmdWwgbG9nb3V0LlxuICpcbiAqIE90aGVyIGRhdGEgY2FjaGVkIGZvciB0aGUgbG9nZ2VkLWluIHVzZXIsIHN1Y2ggYXMgU1dSIGNhY2hlcywgaXMgdGhlIGNhbGxlcidzIHRvIGNsZWFyLlxuICpcbiAqIEByZXR1cm5zIEEgUHJvbWlzZSB0aGF0IHJlc29sdmVzIG9uY2UgdGhlIHNlc3Npb24gc3RvcmUgaG9sZHMgYSBsb2dnZWQtb3V0IHNlc3Npb24uXG4gKlxuICogQGV4YW1wbGVcbiAqIGBgYHRzXG4gKiBpbXBvcnQgeyBsb2dvdXQgfSBmcm9tICdAb3Blbm1ycy9lc20tYXBpJztcbiAqIGF3YWl0IGxvZ291dCgpO1xuICogYGBgXG4gKlxuICogQGludGVybmFsXG4gKi8gZXhwb3J0IGFzeW5jIGZ1bmN0aW9uIGxvZ291dCgpIHtcbiAgICB0cnkge1xuICAgICAgICBhd2FpdCBvcGVubXJzRmV0Y2goc2Vzc2lvbkVuZHBvaW50LCB7XG4gICAgICAgICAgICBtZXRob2Q6ICdERUxFVEUnLFxuICAgICAgICAgICAgcmVqZWN0QXV0aEZhaWx1cmU6IHRydWVcbiAgICAgICAgfSk7XG4gICAgfSBjYXRjaCAoZXJyKSB7XG4gICAgICAgIGlmICghaXNBdXRoRmFpbHVyZShlcnIpKSB7XG4gICAgICAgICAgICB0aHJvdyBlcnI7XG4gICAgICAgIH1cbiAgICB9XG4gICAgY2xlYXJDdXJyZW50VXNlcigpO1xuICAgIC8vIFRoZSBzZXNzaW9uIGp1c3QgY2xlYXJlZCBpcyBhbHJlYWR5IGNvcnJlY3QsIHNvIGEgZmFpbGVkIHJlZnJlc2ggbG9zZXMgbm90aGluZy5cbiAgICBhd2FpdCByZWZldGNoQ3VycmVudFVzZXIoKS5jYXRjaCgoKT0+e30pO1xufVxuZnVuY3Rpb24gaGFuZGxlU2Vzc2lvblJlc3BvbnNlKHJlc3VsdCkge1xuICAgIHJldHVybiBuZXcgUHJvbWlzZSgocmVzb2x2ZSwgcmVqZWN0KT0+e1xuICAgICAgICByZXN1bHQudGhlbigocmVzKT0+e1xuICAgICAgICAgICAgaWYgKHR5cGVvZiByZXM/LmRhdGEgPT09ICdvYmplY3QnKSB7XG4gICAgICAgICAgICAgICAgY29uc3QgbmV4dFN0YXRlID0ge1xuICAgICAgICAgICAgICAgICAgICBsb2FkZWQ6IHRydWUsXG4gICAgICAgICAgICAgICAgICAgIHNlc3Npb246IHJlcy5kYXRhXG4gICAgICAgICAgICAgICAgfTtcbiAgICAgICAgICAgICAgICBzZXNzaW9uU3RvcmUuc2V0U3RhdGUobmV4dFN0YXRlLCB0cnVlKTtcbiAgICAgICAgICAgICAgICByZXNvbHZlKG5leHRTdGF0ZSk7XG4gICAgICAgICAgICB9IGVsc2UgaWYgKGlzSW5pdGlhbFNldHVwUmVkaXJlY3QocmVzKSkge1xuICAgICAgICAgICAgICAgIHJlamVjdChyZWNvcmRTZXNzaW9uRmFpbHVyZShFcnJvcignVGhlIHNlcnZlciBpcyBzdGlsbCBzdGFydGluZyB1cCcpLCB0cnVlKSk7XG4gICAgICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgICAgIHJlamVjdChyZWNvcmRTZXNzaW9uRmFpbHVyZShFcnJvcignVGhlIHNlc3Npb24gZW5kcG9pbnQgZGlkIG5vdCByZXNwb25kIHdpdGggYSBzZXNzaW9uJykpKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgfSkuY2F0Y2goKGVycik9PntcbiAgICAgICAgICAgIC8vIEFuIGF1dGggZmFpbHVyZSBpcyB0aGUgc2Vzc2lvbiBlbmRwb2ludCdzIGFuc3dlciBmb3IgXCJub3QgbG9nZ2VkIGluXCIsIG5vdCBhIGZhaWxlZCBsb29rdXAuXG4gICAgICAgICAgICBpZiAoaXNBdXRoRmFpbHVyZShlcnIpKSB7XG4gICAgICAgICAgICAgICAgaWYgKGlzVW5hdXRoZW50aWNhdGVkU2Vzc2lvbihlcnIucmVzcG9uc2VCb2R5KSkge1xuICAgICAgICAgICAgICAgICAgICBzZXNzaW9uU3RvcmUuc2V0U3RhdGUoe1xuICAgICAgICAgICAgICAgICAgICAgICAgbG9hZGVkOiB0cnVlLFxuICAgICAgICAgICAgICAgICAgICAgICAgc2Vzc2lvbjogZXJyLnJlc3BvbnNlQm9keVxuICAgICAgICAgICAgICAgICAgICB9LCB0cnVlKTtcbiAgICAgICAgICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgICAgICAgICBjbGVhckN1cnJlbnRVc2VyKCk7XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgIHJlc29sdmUoc2Vzc2lvblN0b3JlLmdldFN0YXRlKCkpO1xuICAgICAgICAgICAgICAgIHJldHVybjtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICAgIGlmIChpc0dhdGV3YXlFcnJvckR1cmluZ1N0YXJ0dXAoZXJyKSkge1xuICAgICAgICAgICAgICAgIHJlamVjdChyZWNvcmRTZXNzaW9uRmFpbHVyZShlcnIsIHRydWUpKTtcbiAgICAgICAgICAgICAgICByZXR1cm47XG4gICAgICAgICAgICB9XG4gICAgICAgICAgICByZXBvcnRFcnJvcihgRmFpbGVkIHRvIGZldGNoIG5ldyBzZXNzaW9uIGluZm9ybWF0aW9uOiAke2Vycn1gKTtcbiAgICAgICAgICAgIHJlamVjdChyZWNvcmRTZXNzaW9uRmFpbHVyZShlcnIpKTtcbiAgICAgICAgfSk7XG4gICAgfSk7XG59XG5mdW5jdGlvbiBpc0F1dGhGYWlsdXJlKGVycikge1xuICAgIHJldHVybiBlcnIgaW5zdGFuY2VvZiBPcGVubXJzRmV0Y2hFcnJvciAmJiAoZXJyLnJlc3BvbnNlLnN0YXR1cyA9PT0gNDAxIHx8IGVyci5yZXNwb25zZS5zdGF0dXMgPT09IDQwMyk7XG59XG4vKipcbiAqIFVudGlsIHRoZSBiYWNrZW5kIGhhcyBmaW5pc2hlZCBpdHMgaW5pdGlhbCBzZXR1cCwgaXQgYW5zd2VycyBldmVyeSByZXF1ZXN0IHdpdGggYSByZWRpcmVjdCB0byBpdHNcbiAqIHNldHVwIHBhZ2UsIHdoaWNoIGBmZXRjaCgpYCBmb2xsb3dzLCBzbyB0aGUgc2Vzc2lvbiByZXF1ZXN0IHJlc29sdmVzIHdpdGggdGhhdCBwYWdlJ3MgSFRNTC5cbiAqLyBmdW5jdGlvbiBpc0luaXRpYWxTZXR1cFJlZGlyZWN0KHJlcykge1xuICAgIGlmICghcmVzPy5yZWRpcmVjdGVkIHx8ICFyZXMudXJsKSB7XG4gICAgICAgIHJldHVybiBmYWxzZTtcbiAgICB9XG4gICAgdHJ5IHtcbiAgICAgICAgcmV0dXJuIG5ldyBVUkwocmVzLnVybCwgd2luZG93LmxvY2F0aW9uLmhyZWYpLnBhdGhuYW1lLnJlcGxhY2UoL1xcLyskLywgJycpLmVuZHNXaXRoKCcvaW5pdGlhbHNldHVwJyk7XG4gICAgfSBjYXRjaCAge1xuICAgICAgICByZXR1cm4gZmFsc2U7XG4gICAgfVxufVxuZnVuY3Rpb24gaXNHYXRld2F5RXJyb3JEdXJpbmdTdGFydHVwKGVycikge1xuICAgIHJldHVybiBlcnIgaW5zdGFuY2VvZiBPcGVubXJzRmV0Y2hFcnJvciAmJiBlcnIucmVzcG9uc2Uuc3RhdHVzID09PSA1MDIgJiYgIXNlc3Npb25TdG9yZS5nZXRTdGF0ZSgpLmxvYWRlZCAmJiBmaXJzdEZldGNoVGltZU1pbGxpcyAhPT0gdW5kZWZpbmVkICYmIERhdGUubm93KCkgLSBmaXJzdEZldGNoVGltZU1pbGxpcyA8IHN0YXJ0dXBHcmFjZVBlcmlvZE1pbGxpcztcbn1cbmZ1bmN0aW9uIGlzVW5hdXRoZW50aWNhdGVkU2Vzc2lvbihib2R5KSB7XG4gICAgcmV0dXJuIHR5cGVvZiBib2R5ID09PSAnb2JqZWN0JyAmJiBib2R5ICE9PSBudWxsICYmIGJvZHkuYXV0aGVudGljYXRlZCA9PT0gZmFsc2U7XG59XG4vKipcbiAqIEEgc2Vzc2lvbiB0aGF0IGhhcyBhbHJlYWR5IGxvYWRlZCBpcyBrZXB0IHdoZW4gYSBsYXRlciBmZXRjaCBmYWlscywgc2luY2UgaXQgaXMgc3RpbGwgdGhlIGJlc3QgYW5zd2VyXG4gKiBhdmFpbGFibGUuIFdpdGggbm90aGluZyB0byBmYWxsIGJhY2sgb24sIHRoZSBlcnJvciBpcyByZWNvcmRlZCBzbyB0aGUgYXBwIHNoZWxsIGNhbiBzaG93IGFuIGVycm9yIHBhZ2UuXG4gKi8gZnVuY3Rpb24gcmVjb3JkU2Vzc2lvbkZhaWx1cmUoZXJyLCBpbml0aWFsaXppbmcgPSBmYWxzZSkge1xuICAgIGlmICghc2Vzc2lvblN0b3JlLmdldFN0YXRlKCkubG9hZGVkKSB7XG4gICAgICAgIHNlc3Npb25TdG9yZS5zZXRTdGF0ZSh7XG4gICAgICAgICAgICBsb2FkZWQ6IGZhbHNlLFxuICAgICAgICAgICAgc2Vzc2lvbjogbnVsbCxcbiAgICAgICAgICAgIGVycm9yOiBlcnIgaW5zdGFuY2VvZiBFcnJvciA/IGVyciA6IEVycm9yKFN0cmluZyhlcnIpKSxcbiAgICAgICAgICAgIGluaXRpYWxpemluZ1xuICAgICAgICB9LCB0cnVlKTtcbiAgICB9XG4gICAgcmV0dXJuIHNlc3Npb25TdG9yZS5nZXRTdGF0ZSgpO1xufVxuIl0sIm5hbWVzIjpbInJlcG9ydEVycm9yIiwiY3JlYXRlR2xvYmFsU3RvcmUiLCJpc1VuZGVmaW5lZCIsIk9wZW5tcnNGZXRjaEVycm9yIiwib3Blbm1yc0ZldGNoIiwicmVzdEJhc2VVcmwiLCJzZXNzaW9uRW5kcG9pbnQiLCJzZXNzaW9uU3RvcmUiLCJzZXNzaW9uTWF4QWdlTWlsbGlzIiwibGFzdEZldGNoVGltZU1pbGxpcyIsInN0YXJ0dXBHcmFjZVBlcmlvZE1pbGxpcyIsImZpcnN0RmV0Y2hUaW1lTWlsbGlzIiwiaW5GbGlnaHRSZWZyZXNoIiwicmVmcmVzaFNlc3Npb25JZlN0YWxlIiwiRGF0ZSIsInJlZmV0Y2hDdXJyZW50VXNlciIsImdldEN1cnJlbnRVc2VyIiwib3B0cyIsImluY2x1ZGVBdXRoU3RhdHVzIiwic2VsZWN0Iiwic2Vzc2lvbiIsInJlZnJlc2giLCJQcm9taXNlIiwicmVzb2x2ZSIsInJlc29sdmVJZkxvYWRlZCIsInN0YXRlIiwidW5zdWJzY3JpYmUiLCJnZXRTZXNzaW9uU3RvcmUiLCJpc1ZhbGlkTG9jYWxlIiwibG9jYWxlIiwidW5kZWZpbmVkIiwiSW50bCIsImUiLCJzZXRVc2VyTGFuZ3VhZ2UiLCJkYXRhIiwiZG9jdW1lbnQiLCJ1c2VySGFzUHJpdmlsZWdlIiwicmVxdWlyZWRQcml2aWxlZ2UiLCJ1c2VyIiwicCIsIkFycmF5IiwicnAiLCJjb25zb2xlIiwiaXNTdXBlclVzZXIiLCJyb2xlIiwidXNlcm5hbWUiLCJwYXNzd29yZCIsImhlYWRlcnMiLCJ3aW5kb3ciLCJoYW5kbGVTZXNzaW9uUmVzcG9uc2UiLCJjbGVhciIsImNsZWFyQ3VycmVudFVzZXIiLCJ1c2VySGFzQWNjZXNzIiwiQm9vbGVhbiIsImdldExvZ2dlZEluVXNlciIsInJlcyIsImhhbmRsZXIiLCJnZXRTZXNzaW9uTG9jYXRpb24iLCJzZXRTZXNzaW9uTG9jYXRpb24iLCJsb2NhdGlvblV1aWQiLCJhYm9ydENvbnRyb2xsZXIiLCJzZXRTZXNzaW9uTG9jYWxlIiwic2V0VXNlclByb3BlcnRpZXMiLCJ1c2VyVXVpZCIsInVzZXJQcm9wZXJ0aWVzIiwiQWJvcnRDb250cm9sbGVyIiwidmVyaWZ5VG90cENvZGUiLCJjb2RlIiwicmVtZW1iZXJEZXZpY2UiLCJyZXNwb25zZSIsInN0b3JlIiwibG9nb3V0IiwiZXJyIiwiaXNBdXRoRmFpbHVyZSIsInJlc3VsdCIsInJlamVjdCIsIm5leHRTdGF0ZSIsImlzSW5pdGlhbFNldHVwUmVkaXJlY3QiLCJyZWNvcmRTZXNzaW9uRmFpbHVyZSIsIkVycm9yIiwiaXNVbmF1dGhlbnRpY2F0ZWRTZXNzaW9uIiwiaXNHYXRld2F5RXJyb3JEdXJpbmdTdGFydHVwIiwiVVJMIiwiYm9keSIsImluaXRpYWxpemluZyIsIlN0cmluZyJdLCJtYXBwaW5ncyI6Ijs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7O0FBQUEsMEJBQTBCLEdBQTZEO0FBQ2hDO0FBQ2Y7QUFDMkQ7QUFDbkcsY0FBYyxHQUFVLE1BQU1PLGVBQWVOLHlEQUFpQkEsQ0FBQyxXQUFXO0lBQ3RFLFFBQVE7SUFDUixTQUFTO0FBQ2IsR0FBRztBQUNIOzs7O0NBSUMsR0FBRyxNQUFNTyxzQkFBc0IsS0FBSztBQUNyQyxJQUFJQyxzQkFBc0I7QUFDMUI7OztDQUdDLEdBQUcsTUFBTUMsMkJBQTJCLElBQUksS0FBSztBQUM5QyxJQUFJQztBQUNKLElBQUlDLGtCQUFrQjtBQUN0Qjs7Ozs7Ozs7Ozs7Q0FXQyxHQUFHLFNBQVNDO0lBQ1QsSUFBSUQsaUJBQWlCO1FBQ2pCLE9BQU9BO0lBQ1g7SUFDQSxJQUFJTCxhQUFhLFFBQVEsR0FBRyxNQUFNLElBQUlFLHVCQUF1QkssS0FBSyxHQUFHLEtBQUtOLHFCQUFxQjtRQUMzRixPQUFPO0lBQ1g7SUFDQSxPQUFPTztBQUNYO0FBQ0EsU0FBU0MsZUFBZUMsSUFBSTtJQUN4QixNQUFNQyxvQkFBb0JELE1BQU0scUJBQXFCO0lBQ3JELE1BQU1FLFNBQVMsQ0FBQ0MsVUFBVUYsb0JBQW9CRSxVQUFVQSxRQUFRLElBQUk7SUFDcEUsTUFBTUMsVUFBVVI7SUFDaEIsSUFBSSxDQUFDUSxTQUFTO1FBQ1YsT0FBT0MsUUFBUSxPQUFPLENBQUNILE9BQU9aLGFBQWEsUUFBUSxHQUFHLE9BQU87SUFDakU7SUFD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\n//# sourceURL=webpack-internal:///../../framework/esm-api/dist/current-user.js\n\n}");
4415
4415
 
4416
4416
  },
4417
4417
  "../../framework/esm-api/dist/environment.js"(__unused_rspack___webpack_module__, __webpack_exports__, __webpack_require__) {
package/lib/index.html CHANGED
@@ -33,7 +33,7 @@
33
33
  <script type="openmrs-routes" src="/openmrs/spa/routes.registry.json"></script>
34
34
 
35
35
 
36
- <link rel="preload" href="/openmrs/spa/6fa8075110bb9581.js" as="script"><link rel="preload" href="/openmrs/spa/95d37770ece215c2.js" as="script"><link rel="preload" href="/openmrs/spa/4afcde165187cf34.js" as="script"><link rel="preload" href="/openmrs/spa/a8eb6366799b605a.js" as="script"><link rel="preload" href="/openmrs/spa/6a07d9edae91d64a.js" as="script"><link rel="preload" href="/openmrs/spa/29eb002ac8b08df5.js" as="script"><link rel="preload" href="/openmrs/spa/2b18050c552ba37b.js" as="script"><link rel="preload" href="/openmrs/spa/41733b40a9c3c3a5.js" as="script"><link rel="preload" href="/openmrs/spa/dba37f937b9fef08.js" as="script"><link rel="preload" href="/openmrs/spa/9728df55a98ebbd2.js" as="script"><link rel="preload" href="/openmrs/spa/dcee9941dbf0fcae.js" as="script"><link rel="preload" href="/openmrs/spa/e0650e8f5bc5a5f0.js" as="script"><link rel="preload" href="/openmrs/spa/965c2ea7ad36f9b9.js" as="script"><link rel="preload" href="/openmrs/spa/18ec06b4e1782343.js" as="script"><link rel="preload" href="/openmrs/spa/c912d57aa96a2320.js" as="script"><link rel="preload" href="/openmrs/spa/ab4148a466ebd6ef.js" as="script"><link rel="preload" href="/openmrs/spa/a2ed0a758d2afe95.js" as="script"><link rel="preload" href="/openmrs/spa/4907fc954ee36d02.js" as="script"><link rel="preload" href="/openmrs/spa/6c72dcc37b6da71c.js" as="script"><link rel="preload" href="/openmrs/spa/258c11567d1269c4.js" as="script"><link rel="preload" href="/openmrs/spa/41084f226b2f0007.js" as="script">
36
+ <link rel="preload" href="/openmrs/spa/6fa8075110bb9581.js" as="script"><link rel="preload" href="/openmrs/spa/be46574bb74a2879.js" as="script"><link rel="preload" href="/openmrs/spa/4afcde165187cf34.js" as="script"><link rel="preload" href="/openmrs/spa/a8eb6366799b605a.js" as="script"><link rel="preload" href="/openmrs/spa/6a07d9edae91d64a.js" as="script"><link rel="preload" href="/openmrs/spa/29eb002ac8b08df5.js" as="script"><link rel="preload" href="/openmrs/spa/2b18050c552ba37b.js" as="script"><link rel="preload" href="/openmrs/spa/41733b40a9c3c3a5.js" as="script"><link rel="preload" href="/openmrs/spa/dba37f937b9fef08.js" as="script"><link rel="preload" href="/openmrs/spa/9728df55a98ebbd2.js" as="script"><link rel="preload" href="/openmrs/spa/dcee9941dbf0fcae.js" as="script"><link rel="preload" href="/openmrs/spa/e0650e8f5bc5a5f0.js" as="script"><link rel="preload" href="/openmrs/spa/965c2ea7ad36f9b9.js" as="script"><link rel="preload" href="/openmrs/spa/18ec06b4e1782343.js" as="script"><link rel="preload" href="/openmrs/spa/c912d57aa96a2320.js" as="script"><link rel="preload" href="/openmrs/spa/ab4148a466ebd6ef.js" as="script"><link rel="preload" href="/openmrs/spa/a2ed0a758d2afe95.js" as="script"><link rel="preload" href="/openmrs/spa/4907fc954ee36d02.js" as="script"><link rel="preload" href="/openmrs/spa/6c72dcc37b6da71c.js" as="script"><link rel="preload" href="/openmrs/spa/258c11567d1269c4.js" as="script"><link rel="preload" href="/openmrs/spa/41084f226b2f0007.js" as="script">
37
37
  <meta name="theme-color" content="#005d5d" /><link rel="manifest" href="/openmrs/spa/manifest.8bf1757a96431f7a7b87baad8f950c48.json" /></head>
38
38
  <body>
39
39
  <script src="/openmrs/spa/openmrs.js"></script>