@mnaoumov/obsidian-lib 10.12.0 → 11.0.0

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.
Files changed (399) hide show
  1. package/components/worker-component/package.json +6 -0
  2. package/components/worker-pool-component/package.json +6 -0
  3. package/dist/lib/cjs/__merged.cjs +409 -292
  4. package/dist/lib/cjs/__merged.d.cts +17 -8
  5. package/dist/lib/cjs/anchored-suggest.cjs +1 -1
  6. package/dist/lib/cjs/app.cjs +2 -2
  7. package/dist/lib/cjs/async-with-notice.cjs +4 -4
  8. package/dist/lib/cjs/attachment-path.cjs +9 -9
  9. package/dist/lib/cjs/attachment-path.d.cts +3 -3
  10. package/dist/lib/cjs/attachment-unit-folder.cjs +2 -2
  11. package/dist/lib/cjs/backlink-index.cjs +5 -5
  12. package/dist/lib/cjs/backlink.cjs +7 -7
  13. package/dist/lib/cjs/bases-view-registrar.cjs +1 -1
  14. package/dist/lib/cjs/broken-link-candidates.cjs +1 -1
  15. package/dist/lib/cjs/bug-report.cjs +3 -3
  16. package/dist/lib/cjs/bulk-operation-progress.cjs +1 -1
  17. package/dist/lib/cjs/bulk-operation.cjs +2 -2
  18. package/dist/lib/cjs/callout.cjs +6 -6
  19. package/dist/lib/cjs/canvas.cjs +11 -9
  20. package/dist/lib/cjs/canvas.d.cts +13 -0
  21. package/dist/lib/cjs/case-insensitive-file-index.cjs +3 -3
  22. package/dist/lib/cjs/code-block-render-handoff.cjs +5 -5
  23. package/dist/lib/cjs/codemirror/editor-mode-extension.cjs +4 -4
  24. package/dist/lib/cjs/codemirror/incremental-parse-state-field.cjs +2 -2
  25. package/dist/lib/cjs/codemirror/index.cjs +7 -7
  26. package/dist/lib/cjs/codemirror/inline-token-widgets.cjs +5 -5
  27. package/dist/lib/cjs/codemirror/markdown-editor-views.cjs +2 -2
  28. package/dist/lib/cjs/codemirror/settings-facet.cjs +1 -1
  29. package/dist/lib/cjs/command-handlers/abstract-file-command-handler.cjs +17 -17
  30. package/dist/lib/cjs/command-handlers/abstract-file-command-handler.d.cts +13 -13
  31. package/dist/lib/cjs/command-handlers/command-handler-component.cjs +2 -2
  32. package/dist/lib/cjs/command-handlers/command-handler.cjs +2 -2
  33. package/dist/lib/cjs/command-handlers/editor-command-handler.cjs +10 -10
  34. package/dist/lib/cjs/command-handlers/editor-command-handler.d.cts +7 -7
  35. package/dist/lib/cjs/command-handlers/file-command-handler.cjs +3 -3
  36. package/dist/lib/cjs/command-handlers/folder-command-handler.cjs +3 -3
  37. package/dist/lib/cjs/command-handlers/global-command-handler.cjs +2 -2
  38. package/dist/lib/cjs/command-handlers/index.cjs +15 -15
  39. package/dist/lib/cjs/command-handlers/open-bug-report-command-handler.cjs +6 -6
  40. package/dist/lib/cjs/command-handlers/open-demo-vault-command-handler.cjs +2 -2
  41. package/dist/lib/cjs/command-handlers/open-discussion-command-handler.cjs +2 -2
  42. package/dist/lib/cjs/command-handlers/open-feature-request-command-handler.cjs +2 -2
  43. package/dist/lib/cjs/command-handlers/open-git-hub-command-handler.cjs +1 -1
  44. package/dist/lib/cjs/command-handlers/open-settings-command-handler.cjs +2 -2
  45. package/dist/lib/cjs/command-handlers/undo-bulk-operation-command-handler.cjs +2 -2
  46. package/dist/lib/cjs/command-handlers/unlock-active-note-command-handler.cjs +1 -1
  47. package/dist/lib/cjs/community-plugins.cjs +3 -3
  48. package/dist/lib/cjs/components/abort-signal-component.cjs +2 -2
  49. package/dist/lib/cjs/components/all-windows-event-component.cjs +5 -5
  50. package/dist/lib/cjs/components/all-windows-status-bar-item-component.cjs +3 -3
  51. package/dist/lib/cjs/components/async-error-handler-component.cjs +5 -5
  52. package/dist/lib/cjs/components/async-events-component.cjs +1 -1
  53. package/dist/lib/cjs/components/bulk-operation-commit-component.cjs +12 -12
  54. package/dist/lib/cjs/components/case-insensitive-file-index-component.cjs +2 -2
  55. package/dist/lib/cjs/components/component-ex.cjs +21 -11
  56. package/dist/lib/cjs/components/component-ex.d.cts +11 -0
  57. package/dist/lib/cjs/components/console-debug-component.cjs +2 -2
  58. package/dist/lib/cjs/components/core-plugin-toggle-component.cjs +2 -2
  59. package/dist/lib/cjs/components/disposable-component.cjs +2 -2
  60. package/dist/lib/cjs/components/embed-extensions-component.cjs +1 -1
  61. package/dist/lib/cjs/components/embeddable-markdown-editor-component.cjs +8 -8
  62. package/dist/lib/cjs/components/file-explorer-root-menu-component.cjs +7 -7
  63. package/dist/lib/cjs/components/generate-markdown-link-default-params-component.cjs +2 -2
  64. package/dist/lib/cjs/components/incremental-file-index-component.cjs +4 -4
  65. package/dist/lib/cjs/components/index.cjs +46 -40
  66. package/dist/lib/cjs/components/index.d.cts +2 -0
  67. package/dist/lib/cjs/components/layout-ready-component.cjs +3 -3
  68. package/dist/lib/cjs/components/menu-event-registrar-component.cjs +2 -2
  69. package/dist/lib/cjs/components/monkey-around-component.cjs +3 -3
  70. package/dist/lib/cjs/components/notebook-navigator-menu-event-registrar-component.cjs +5 -5
  71. package/dist/lib/cjs/components/plugin-context-component.cjs +5 -5
  72. package/dist/lib/cjs/components/plugin-gate-component.cjs +68 -28
  73. package/dist/lib/cjs/components/plugin-gate-component.d.cts +36 -13
  74. package/dist/lib/cjs/components/plugin-notice-component.cjs +39 -33
  75. package/dist/lib/cjs/components/plugin-notice-component.d.cts +4 -3
  76. package/dist/lib/cjs/components/plugin-settings-component.cjs +113 -17
  77. package/dist/lib/cjs/components/plugin-settings-component.d.cts +35 -5
  78. package/dist/lib/cjs/components/plugin-settings-tab-component.cjs +2 -2
  79. package/dist/lib/cjs/components/plugin-suggestion-component.cjs +8 -8
  80. package/dist/lib/cjs/components/pointer-position-component.cjs +2 -2
  81. package/dist/lib/cjs/components/reconfigurable-editor-extension-component.cjs +3 -3
  82. package/dist/lib/cjs/components/registry-component.cjs +2 -2
  83. package/dist/lib/cjs/components/release-notes-component.cjs +6 -6
  84. package/dist/lib/cjs/components/rename-delete-handler-component.cjs +25 -25
  85. package/dist/lib/cjs/components/rmdir-guard-component.cjs +2 -2
  86. package/dist/lib/cjs/components/settings-facet-component.cjs +1 -1
  87. package/dist/lib/cjs/components/settings-migration-component.cjs +5 -5
  88. package/dist/lib/cjs/components/shared-component-pool-component.cjs +6 -6
  89. package/dist/lib/cjs/components/style-sheet-component.cjs +3 -3
  90. package/dist/lib/cjs/components/syntax-highlighting-component.cjs +3 -3
  91. package/dist/lib/cjs/components/templates-language-component.cjs +1 -1
  92. package/dist/lib/cjs/components/worker-component.cjs +363 -0
  93. package/dist/lib/cjs/components/worker-component.d.cts +156 -0
  94. package/dist/lib/cjs/components/worker-pool-component.cjs +185 -0
  95. package/dist/lib/cjs/components/worker-pool-component.d.cts +102 -0
  96. package/dist/lib/cjs/components/workspace-layout-state-component.cjs +7 -7
  97. package/dist/lib/cjs/constructors/get-dom-events-handlers-constructor.cjs +5 -5
  98. package/dist/lib/cjs/constructors/index.cjs +1 -1
  99. package/dist/lib/cjs/data-handler.cjs +111 -4
  100. package/dist/lib/cjs/data-handler.d.cts +92 -1
  101. package/dist/lib/cjs/data-stores/data-store-locations.cjs +82 -24
  102. package/dist/lib/cjs/data-stores/data-store-locations.d.cts +15 -0
  103. package/dist/lib/cjs/data-stores/data-store-replica.cjs +33 -5
  104. package/dist/lib/cjs/data-stores/data-store-seeds.cjs +6 -6
  105. package/dist/lib/cjs/data-stores/data-store-seeds.d.cts +2 -2
  106. package/dist/lib/cjs/data-stores/data-store-transport.cjs +81 -8
  107. package/dist/lib/cjs/data-stores/data-store-transport.d.cts +30 -1
  108. package/dist/lib/cjs/data-stores/index.cjs +6 -6
  109. package/dist/lib/cjs/data-stores/local-data-store.cjs +74 -10
  110. package/dist/lib/cjs/data-stores/local-data-store.d.cts +58 -1
  111. package/dist/lib/cjs/data-stores/shared-data-store.cjs +76 -19
  112. package/dist/lib/cjs/data-stores/shared-data-store.d.cts +18 -1
  113. package/dist/lib/cjs/dataview-link.cjs +2 -2
  114. package/dist/lib/cjs/dataview.cjs +27 -7
  115. package/dist/lib/cjs/dataview.d.cts +14 -0
  116. package/dist/lib/cjs/debug.cjs +3 -3
  117. package/dist/lib/cjs/demo-vault-helper.cjs +34 -6
  118. package/dist/lib/cjs/demo-vault-helper.d.cts +6 -2
  119. package/dist/lib/cjs/desktop-bulk-operation-git.cjs +10 -10
  120. package/dist/lib/cjs/desktop-demo-vault-opener.cjs +13 -13
  121. package/dist/lib/cjs/desktop-git-runner.cjs +2 -2
  122. package/dist/lib/cjs/desktop-operating-system.cjs +1 -1
  123. package/dist/lib/cjs/desktop-request-url-stream.cjs +8 -14
  124. package/dist/lib/cjs/desktop-trusted-input.cjs +2 -2
  125. package/dist/lib/cjs/disposable.cjs +150 -0
  126. package/dist/lib/cjs/disposable.d.cts +39 -0
  127. package/dist/lib/cjs/editor-extension-registrar.cjs +1 -1
  128. package/dist/lib/cjs/editor-suggest-registrar.cjs +2 -2
  129. package/dist/lib/cjs/editor-suggest.cjs +1 -1
  130. package/dist/lib/cjs/editor.cjs +6 -6
  131. package/dist/lib/cjs/events.cjs +2 -2
  132. package/dist/lib/cjs/extensions-registrar.cjs +1 -1
  133. package/dist/lib/cjs/feature-request.cjs +1 -1
  134. package/dist/lib/cjs/file-change.cjs +10 -10
  135. package/dist/lib/cjs/file-explorer.cjs +2 -2
  136. package/dist/lib/cjs/file-manager.cjs +5 -5
  137. package/dist/lib/cjs/file-system.cjs +10 -10
  138. package/dist/lib/cjs/folder-note.cjs +4 -4
  139. package/dist/lib/cjs/frontmatter-formatting.cjs +7 -6
  140. package/dist/lib/cjs/frontmatter-link-cache-with-offsets.cjs +1 -1
  141. package/dist/lib/cjs/frontmatter.cjs +5 -5
  142. package/dist/lib/cjs/generated-during-build.cjs +1 -1
  143. package/dist/lib/cjs/hotkey.cjs +1 -1
  144. package/dist/lib/cjs/hover-link-source-registrar.cjs +1 -1
  145. package/dist/lib/cjs/html-element.cjs +2 -2
  146. package/dist/lib/cjs/i18n/custom-type-options.cjs +1 -1
  147. package/dist/lib/cjs/i18n/default-translations.cjs +1 -1
  148. package/dist/lib/cjs/i18n/i18n.cjs +7 -7
  149. package/dist/lib/cjs/i18n/index.cjs +4 -4
  150. package/dist/lib/cjs/i18n/locales/en.cjs +5 -1
  151. package/dist/lib/cjs/i18n/locales/en.d.cts +4 -0
  152. package/dist/lib/cjs/i18n/locales/index.cjs +2 -2
  153. package/dist/lib/cjs/i18n/locales/translations-map.cjs +1 -1
  154. package/dist/lib/cjs/i18n/locales/translations-map.d.cts +4 -0
  155. package/dist/lib/cjs/index.cjs +145 -127
  156. package/dist/lib/cjs/index.d.cts +6 -0
  157. package/dist/lib/cjs/inline-token-renderer.cjs +2 -2
  158. package/dist/lib/cjs/is-in-obsidian.cjs +1 -1
  159. package/dist/lib/cjs/library-styles.cjs +3 -3
  160. package/dist/lib/cjs/link-and-tag-input-suggest.cjs +2 -2
  161. package/dist/lib/cjs/link.cjs +76 -56
  162. package/dist/lib/cjs/link.d.cts +20 -14
  163. package/dist/lib/cjs/logger.cjs +4 -4
  164. package/dist/lib/cjs/loop.cjs +10 -16
  165. package/dist/lib/cjs/markdown-code-block-processor-registrar.cjs +17 -2
  166. package/dist/lib/cjs/markdown-code-block-processor-registrar.d.cts +7 -0
  167. package/dist/lib/cjs/markdown-code-block-processor.cjs +13 -13
  168. package/dist/lib/cjs/markdown-post-processor-registrar.cjs +2 -2
  169. package/dist/lib/cjs/markdown-view.cjs +3 -3
  170. package/dist/lib/cjs/markdown.cjs +12 -12
  171. package/dist/lib/cjs/metadata-cache.cjs +23 -23
  172. package/dist/lib/cjs/metadata-cache.d.cts +5 -4
  173. package/dist/lib/cjs/misplaced-attachment.cjs +297 -0
  174. package/dist/lib/cjs/misplaced-attachment.d.cts +228 -0
  175. package/dist/lib/cjs/mobile-app-info.cjs +1 -1
  176. package/dist/lib/cjs/modals/alert.cjs +4 -4
  177. package/dist/lib/cjs/modals/code-block-builder.cjs +7 -7
  178. package/dist/lib/cjs/modals/confirm.cjs +4 -4
  179. package/dist/lib/cjs/modals/copy-text-manually.cjs +4 -4
  180. package/dist/lib/cjs/modals/index.cjs +12 -12
  181. package/dist/lib/cjs/modals/minimizable-modal.cjs +6 -6
  182. package/dist/lib/cjs/modals/modal-command-builder.cjs +3 -3
  183. package/dist/lib/cjs/modals/modal.cjs +3 -3
  184. package/dist/lib/cjs/modals/prompt.cjs +10 -10
  185. package/dist/lib/cjs/modals/prompt.d.cts +1 -1
  186. package/dist/lib/cjs/modals/review-bug-report-diagnostics.cjs +5 -5
  187. package/dist/lib/cjs/modals/select-item.cjs +6 -6
  188. package/dist/lib/cjs/modals/select-option.cjs +3 -3
  189. package/dist/lib/cjs/modals/suggest-modal-command-builder.cjs +1 -1
  190. package/dist/lib/cjs/note-priority.cjs +2 -2
  191. package/dist/lib/cjs/notebook-navigator.cjs +12 -2
  192. package/dist/lib/cjs/notebook-navigator.d.cts +6 -0
  193. package/dist/lib/cjs/obsidian-lib-state.cjs +1 -1
  194. package/dist/lib/cjs/obsidian-protocol-handler-registrar.cjs +1 -1
  195. package/dist/lib/cjs/obsidian-settings.cjs +1 -1
  196. package/dist/lib/cjs/obsidian-word-characters.cjs +1 -1
  197. package/dist/lib/cjs/parse-link.cjs +14 -14
  198. package/dist/lib/cjs/path-compatibility.cjs +368 -0
  199. package/dist/lib/cjs/path-compatibility.d.cts +263 -0
  200. package/dist/lib/cjs/path-settings.cjs +3 -3
  201. package/dist/lib/cjs/pdf.cjs +2 -2
  202. package/dist/lib/cjs/plugin/index.cjs +16 -13
  203. package/dist/lib/cjs/plugin/index.d.cts +1 -0
  204. package/dist/lib/cjs/plugin/plugin-api.cjs +8 -8
  205. package/dist/lib/cjs/plugin/plugin-async-cleanup.cjs +6 -3
  206. package/dist/lib/cjs/plugin/plugin-async-cleanup.d.cts +5 -0
  207. package/dist/lib/cjs/plugin/plugin-context.cjs +10 -9
  208. package/dist/lib/cjs/plugin/plugin-event-source.cjs +1 -1
  209. package/dist/lib/cjs/plugin/plugin-event-source.d.cts +4 -4
  210. package/dist/lib/cjs/plugin/plugin-install-state.cjs +4 -4
  211. package/dist/lib/cjs/plugin/plugin-instance.cjs +14 -12
  212. package/dist/lib/cjs/plugin/plugin-instance.d.cts +7 -0
  213. package/dist/lib/cjs/plugin/plugin-lifecycle-events.cjs +1 -1
  214. package/dist/lib/cjs/plugin/plugin-lifecycle-events.d.cts +6 -4
  215. package/dist/lib/cjs/plugin/plugin-settings-tab.cjs +15 -15
  216. package/dist/lib/cjs/plugin/plugin.cjs +118 -34
  217. package/dist/lib/cjs/plugin/plugin.d.cts +28 -5
  218. package/dist/lib/cjs/plugin/settings-migration-api.cjs +1 -1
  219. package/dist/lib/cjs/plugin/third-party-plugin.cjs +231 -0
  220. package/dist/lib/cjs/plugin/third-party-plugin.d.cts +244 -0
  221. package/dist/lib/cjs/plugin-cli-handler-registrar.cjs +2 -2
  222. package/dist/lib/cjs/popovers/field-popover.cjs +4 -4
  223. package/dist/lib/cjs/popovers/index.cjs +3 -3
  224. package/dist/lib/cjs/popovers/popover-anchor.cjs +1 -1
  225. package/dist/lib/cjs/popovers/popover.cjs +5 -5
  226. package/dist/lib/cjs/queue.cjs +8 -8
  227. package/dist/lib/cjs/react/app-context.cjs +3 -3
  228. package/dist/lib/cjs/react/index.cjs +1 -1
  229. package/dist/lib/cjs/reference-definition.cjs +1 -1
  230. package/dist/lib/cjs/reference.cjs +3 -3
  231. package/dist/lib/cjs/release-asset.cjs +5 -5
  232. package/dist/lib/cjs/rendered-markdown.cjs +4 -4
  233. package/dist/lib/cjs/request-url.cjs +4 -4
  234. package/dist/lib/cjs/resource-lock.cjs +46 -42
  235. package/dist/lib/cjs/resource-lock.d.cts +8 -7
  236. package/dist/lib/cjs/resource-url.cjs +3 -3
  237. package/dist/lib/cjs/ribbon-icon-registrar.cjs +1 -1
  238. package/dist/lib/cjs/setting-components/checkbox-component.cjs +3 -3
  239. package/dist/lib/cjs/setting-components/code-highlighter-component.cjs +7 -7
  240. package/dist/lib/cjs/setting-components/date-component.cjs +4 -4
  241. package/dist/lib/cjs/setting-components/date-time-component.cjs +4 -4
  242. package/dist/lib/cjs/setting-components/email-component.cjs +2 -2
  243. package/dist/lib/cjs/setting-components/file-component.cjs +2 -2
  244. package/dist/lib/cjs/setting-components/folder-list-component.cjs +3 -3
  245. package/dist/lib/cjs/setting-components/hotkey-component.cjs +5 -5
  246. package/dist/lib/cjs/setting-components/index.cjs +30 -30
  247. package/dist/lib/cjs/setting-components/list-component.cjs +5 -5
  248. package/dist/lib/cjs/setting-components/month-component.cjs +4 -4
  249. package/dist/lib/cjs/setting-components/multiple-dropdown-component.cjs +3 -3
  250. package/dist/lib/cjs/setting-components/multiple-email-component.cjs +2 -2
  251. package/dist/lib/cjs/setting-components/multiple-file-component.cjs +3 -3
  252. package/dist/lib/cjs/setting-components/multiple-text-component.cjs +9 -6
  253. package/dist/lib/cjs/setting-components/multiple-text-component.d.cts +4 -1
  254. package/dist/lib/cjs/setting-components/number-component.cjs +2 -2
  255. package/dist/lib/cjs/setting-components/password-component.cjs +2 -2
  256. package/dist/lib/cjs/setting-components/setting-component-wrapper.cjs +3 -3
  257. package/dist/lib/cjs/setting-components/tag-list-component.cjs +4 -4
  258. package/dist/lib/cjs/setting-components/telephone-component.cjs +2 -2
  259. package/dist/lib/cjs/setting-components/text-based-component.cjs +1 -1
  260. package/dist/lib/cjs/setting-components/time-component.cjs +3 -3
  261. package/dist/lib/cjs/setting-components/tri-state-checkbox-component.cjs +3 -3
  262. package/dist/lib/cjs/setting-components/typed-dropdown-component.cjs +3 -3
  263. package/dist/lib/cjs/setting-components/typed-multiple-dropdown-component.cjs +4 -4
  264. package/dist/lib/cjs/setting-components/typed-range-text-component.cjs +1 -1
  265. package/dist/lib/cjs/setting-components/typed-text-component.cjs +3 -3
  266. package/dist/lib/cjs/setting-components/url-component.cjs +2 -2
  267. package/dist/lib/cjs/setting-components/validator-component.cjs +4 -4
  268. package/dist/lib/cjs/setting-components/week-component.cjs +4 -4
  269. package/dist/lib/cjs/setting-ex.cjs +26 -26
  270. package/dist/lib/cjs/setting-group-ex.cjs +2 -2
  271. package/dist/lib/cjs/settings-recovery.cjs +217 -0
  272. package/dist/lib/cjs/settings-recovery.d.cts +178 -0
  273. package/dist/lib/cjs/settings-tabs.cjs +5 -5
  274. package/dist/lib/cjs/status-bar-item-registrar.cjs +1 -1
  275. package/dist/lib/cjs/templater.cjs +14 -4
  276. package/dist/lib/cjs/templater.d.cts +6 -0
  277. package/dist/lib/cjs/transformers/duration-transformer.cjs +2 -2
  278. package/dist/lib/cjs/transformers/index.cjs +1 -1
  279. package/dist/lib/cjs/trusted-input.cjs +1 -1
  280. package/dist/lib/cjs/validation.cjs +4 -4
  281. package/dist/lib/cjs/vault-delete.cjs +6 -6
  282. package/dist/lib/cjs/vault-transaction.cjs +5 -5
  283. package/dist/lib/cjs/vault.cjs +12 -12
  284. package/dist/lib/cjs/view-registrar.cjs +1 -1
  285. package/dist/lib/cjs/virtual-file.cjs +16 -14
  286. package/dist/lib/cjs/virtual-file.d.cts +2 -1
  287. package/dist/lib/cjs/wasm.cjs +119 -0
  288. package/dist/lib/cjs/wasm.d.cts +54 -0
  289. package/dist/lib/cjs/worker-protocol.cjs +209 -0
  290. package/dist/lib/cjs/worker-protocol.d.cts +282 -0
  291. package/dist/lib/cjs/workspace.cjs +1 -1
  292. package/dist/lib/esm/__merged.d.mts +17 -8
  293. package/dist/lib/esm/__merged.mjs +133 -3
  294. package/dist/lib/esm/app.mjs +2 -2
  295. package/dist/lib/esm/attachment-path.d.mts +3 -3
  296. package/dist/lib/esm/attachment-path.mjs +2 -2
  297. package/dist/lib/esm/backlink-index.mjs +2 -2
  298. package/dist/lib/esm/canvas.d.mts +13 -0
  299. package/dist/lib/esm/canvas.mjs +6 -5
  300. package/dist/lib/esm/command-handlers/abstract-file-command-handler.d.mts +13 -13
  301. package/dist/lib/esm/command-handlers/abstract-file-command-handler.mjs +14 -14
  302. package/dist/lib/esm/command-handlers/editor-command-handler.d.mts +7 -7
  303. package/dist/lib/esm/command-handlers/editor-command-handler.mjs +8 -8
  304. package/dist/lib/esm/components/component-ex.d.mts +11 -0
  305. package/dist/lib/esm/components/component-ex.mjs +19 -6
  306. package/dist/lib/esm/components/disposable-component.mjs +1 -1
  307. package/dist/lib/esm/components/index.d.mts +2 -0
  308. package/dist/lib/esm/components/index.mjs +5 -1
  309. package/dist/lib/esm/components/plugin-gate-component.d.mts +36 -13
  310. package/dist/lib/esm/components/plugin-gate-component.mjs +57 -14
  311. package/dist/lib/esm/components/plugin-notice-component.d.mts +4 -3
  312. package/dist/lib/esm/components/plugin-notice-component.mjs +30 -21
  313. package/dist/lib/esm/components/plugin-settings-component.d.mts +35 -5
  314. package/dist/lib/esm/components/plugin-settings-component.mjs +99 -3
  315. package/dist/lib/esm/components/rename-delete-handler-component.mjs +2 -2
  316. package/dist/lib/esm/components/worker-component.d.mts +156 -0
  317. package/dist/lib/esm/components/worker-component.mjs +279 -0
  318. package/dist/lib/esm/components/worker-pool-component.d.mts +102 -0
  319. package/dist/lib/esm/components/worker-pool-component.mjs +95 -0
  320. package/dist/lib/esm/components/workspace-layout-state-component.mjs +1 -1
  321. package/dist/lib/esm/data-handler.d.mts +92 -1
  322. package/dist/lib/esm/data-handler.mjs +112 -3
  323. package/dist/lib/esm/data-stores/data-store-locations.d.mts +15 -0
  324. package/dist/lib/esm/data-stores/data-store-locations.mjs +80 -22
  325. package/dist/lib/esm/data-stores/data-store-replica.mjs +33 -5
  326. package/dist/lib/esm/data-stores/data-store-seeds.d.mts +2 -2
  327. package/dist/lib/esm/data-stores/data-store-seeds.mjs +4 -4
  328. package/dist/lib/esm/data-stores/data-store-transport.d.mts +30 -1
  329. package/dist/lib/esm/data-stores/data-store-transport.mjs +78 -5
  330. package/dist/lib/esm/data-stores/local-data-store.d.mts +58 -1
  331. package/dist/lib/esm/data-stores/local-data-store.mjs +71 -9
  332. package/dist/lib/esm/data-stores/shared-data-store.d.mts +18 -1
  333. package/dist/lib/esm/data-stores/shared-data-store.mjs +72 -15
  334. package/dist/lib/esm/dataview.d.mts +14 -0
  335. package/dist/lib/esm/dataview.mjs +19 -1
  336. package/dist/lib/esm/demo-vault-helper.d.mts +6 -2
  337. package/dist/lib/esm/demo-vault-helper.mjs +29 -1
  338. package/dist/lib/esm/desktop-demo-vault-opener.mjs +1 -1
  339. package/dist/lib/esm/desktop-request-url-stream.mjs +4 -10
  340. package/dist/lib/esm/disposable.d.mts +39 -0
  341. package/dist/lib/esm/disposable.mjs +64 -0
  342. package/dist/lib/esm/file-system.mjs +2 -2
  343. package/dist/lib/esm/frontmatter-formatting.mjs +2 -1
  344. package/dist/lib/esm/generated-during-build.mjs +1 -1
  345. package/dist/lib/esm/i18n/locales/en.d.mts +4 -0
  346. package/dist/lib/esm/i18n/locales/en.mjs +5 -1
  347. package/dist/lib/esm/i18n/locales/translations-map.d.mts +4 -0
  348. package/dist/lib/esm/index.d.mts +6 -0
  349. package/dist/lib/esm/index.mjs +13 -1
  350. package/dist/lib/esm/link.d.mts +20 -14
  351. package/dist/lib/esm/link.mjs +57 -38
  352. package/dist/lib/esm/loop.mjs +2 -8
  353. package/dist/lib/esm/markdown-code-block-processor-registrar.d.mts +7 -0
  354. package/dist/lib/esm/markdown-code-block-processor-registrar.mjs +16 -1
  355. package/dist/lib/esm/metadata-cache.d.mts +5 -4
  356. package/dist/lib/esm/metadata-cache.mjs +6 -6
  357. package/dist/lib/esm/misplaced-attachment.d.mts +228 -0
  358. package/dist/lib/esm/misplaced-attachment.mjs +212 -0
  359. package/dist/lib/esm/modals/prompt.d.mts +1 -1
  360. package/dist/lib/esm/modals/prompt.mjs +1 -1
  361. package/dist/lib/esm/notebook-navigator.d.mts +6 -0
  362. package/dist/lib/esm/notebook-navigator.mjs +11 -2
  363. package/dist/lib/esm/parse-link.mjs +4 -4
  364. package/dist/lib/esm/path-compatibility.d.mts +263 -0
  365. package/dist/lib/esm/path-compatibility.mjs +277 -0
  366. package/dist/lib/esm/plugin/index.d.mts +1 -0
  367. package/dist/lib/esm/plugin/index.mjs +4 -2
  368. package/dist/lib/esm/plugin/plugin-async-cleanup.d.mts +5 -0
  369. package/dist/lib/esm/plugin/plugin-async-cleanup.mjs +3 -1
  370. package/dist/lib/esm/plugin/plugin-context.mjs +2 -1
  371. package/dist/lib/esm/plugin/plugin-event-source.d.mts +4 -4
  372. package/dist/lib/esm/plugin/plugin-event-source.mjs +1 -1
  373. package/dist/lib/esm/plugin/plugin-instance.d.mts +7 -0
  374. package/dist/lib/esm/plugin/plugin-instance.mjs +2 -1
  375. package/dist/lib/esm/plugin/plugin-lifecycle-events.d.mts +6 -4
  376. package/dist/lib/esm/plugin/plugin-lifecycle-events.mjs +1 -1
  377. package/dist/lib/esm/plugin/plugin.d.mts +28 -5
  378. package/dist/lib/esm/plugin/plugin.mjs +103 -9
  379. package/dist/lib/esm/plugin/third-party-plugin.d.mts +244 -0
  380. package/dist/lib/esm/plugin/third-party-plugin.mjs +147 -0
  381. package/dist/lib/esm/release-asset.mjs +1 -1
  382. package/dist/lib/esm/resource-lock.d.mts +8 -7
  383. package/dist/lib/esm/resource-lock.mjs +31 -26
  384. package/dist/lib/esm/setting-components/multiple-text-component.d.mts +4 -1
  385. package/dist/lib/esm/setting-components/multiple-text-component.mjs +6 -3
  386. package/dist/lib/esm/settings-recovery.d.mts +178 -0
  387. package/dist/lib/esm/settings-recovery.mjs +125 -0
  388. package/dist/lib/esm/settings-tabs.mjs +2 -2
  389. package/dist/lib/esm/templater.d.mts +6 -0
  390. package/dist/lib/esm/templater.mjs +11 -2
  391. package/dist/lib/esm/vault.mjs +1 -1
  392. package/dist/lib/esm/virtual-file.d.mts +2 -1
  393. package/dist/lib/esm/virtual-file.mjs +7 -5
  394. package/dist/lib/esm/wasm.d.mts +54 -0
  395. package/dist/lib/esm/wasm.mjs +30 -0
  396. package/dist/lib/esm/worker-protocol.d.mts +282 -0
  397. package/dist/lib/esm/worker-protocol.mjs +113 -0
  398. package/package.json +9 -8
  399. package/plugin/third-party-plugin/package.json +6 -0
@@ -47,10 +47,13 @@ import { SetTransformer } from "@mnaoumov/typescript-lib/transformers/set-transf
47
47
  import { SkipPrivatePropertyTransformer } from "@mnaoumov/typescript-lib/transformers/skip-private-property-transformer";
48
48
  import { TwoWayMapTransformer } from "@mnaoumov/typescript-lib/transformers/two-way-map-transformer";
49
49
  import { ValueWrapper } from "@mnaoumov/typescript-lib/value-wrapper";
50
+ import { PluginDataParseError } from "../data-handler.mjs";
50
51
  import { getObsidianLibDebugger } from "../debug.mjs";
52
+ import { SettingsRecoveryReason } from "../settings-recovery.mjs";
51
53
  import { DurationTransformer } from "../transformers/duration-transformer.mjs";
52
54
  import { registerAsyncEvent } from "./async-events-component.mjs";
53
55
  import { ComponentEx } from "./component-ex.mjs";
56
+ const JSON_INDENT = 2;
54
57
  const defaultTransformer = new GroupTransformer([
55
58
  new SkipPrivatePropertyTransformer(),
56
59
  new DateTransformer(),
@@ -148,6 +151,15 @@ class PluginSettingsComponentBase extends ComponentEx {
148
151
  }
149
152
  }
150
153
  }
154
+ /**
155
+ * Lists the recovery copies of `data.json` kept on this device: copies of a file that did not parse, and of a file
156
+ * whose stored values a first save would have dropped or changed.
157
+ *
158
+ * @returns The copies, newest first; none when the data handler keeps no recovery copies.
159
+ */
160
+ async getRecoveryCopies() {
161
+ return await this.dataHandler.recoveryStore?.list() ?? [];
162
+ }
151
163
  /**
152
164
  * Gets a safe copy of the settings.
153
165
  *
@@ -168,7 +180,24 @@ class PluginSettingsComponentBase extends ComponentEx {
168
180
  */
169
181
  async loadFromFile(isInitialLoad) {
170
182
  this.ensureLoaded();
171
- const data = await this.dataHandler.loadData();
183
+ let data;
184
+ try {
185
+ data = await this.dataHandler.loadData();
186
+ } catch (error) {
187
+ if (!(error instanceof PluginDataParseError) || error.recoveryCopy === null) {
188
+ throw error;
189
+ }
190
+ if (isInitialLoad) {
191
+ this.lastSavedState = this.createDefaultState();
192
+ this.currentState = this.createDefaultState();
193
+ }
194
+ this.markLoadedFromFile();
195
+ if (isInitialLoad) {
196
+ await this.asyncEvents.triggerAsync("loadSettings", this.currentState, isInitialLoad);
197
+ }
198
+ return;
199
+ }
200
+ const originalJson = JSON.stringify(data, void 0, JSON_INDENT);
172
201
  this.lastSavedState = this.createDefaultState();
173
202
  this.currentState = this.createDefaultState();
174
203
  try {
@@ -191,7 +220,7 @@ class PluginSettingsComponentBase extends ComponentEx {
191
220
  return;
192
221
  }
193
222
  const newRecord = await this.settingsToRawRecord(this.currentState.inputValues);
194
- if (!isDeepEqual(newRecord, data)) {
223
+ if (!isDeepEqual(newRecord, data) && await this.keepCopyBeforeLossyRewrite(originalJson, newRecord)) {
195
224
  await this.saveToFileImpl();
196
225
  }
197
226
  } finally {
@@ -301,6 +330,43 @@ class PluginSettingsComponentBase extends ComponentEx {
301
330
  registerValidator(propertyName, validator) {
302
331
  this.validators.set(propertyName, validator);
303
332
  }
333
+ /**
334
+ * Restores a recovery copy of `data.json` kept on this device: writes its record back to the file and reloads the
335
+ * settings from it.
336
+ *
337
+ * The settings in use are kept as a recovery copy of their own first, so a restore loses nothing either.
338
+ *
339
+ * @param id - The id of the copy, from {@link getRecoveryCopies}.
340
+ * @returns A {@link Promise} that resolves when the restored settings are loaded.
341
+ * @throws If the data handler keeps no recovery copies, no copy has that id, or the copy is not valid JSON (a copy
342
+ * of an unparseable file has to be repaired by hand first).
343
+ */
344
+ async restoreRecoveryCopy(id) {
345
+ this.ensureLoaded();
346
+ const recoveryStore = this.dataHandler.recoveryStore;
347
+ if (!recoveryStore) {
348
+ throw new Error("The data handler keeps no recovery copies.");
349
+ }
350
+ const copies = await recoveryStore.list();
351
+ const copy = copies.find((candidate) => candidate.id === id);
352
+ if (!copy) {
353
+ throw new Error(`No recovery copy "${id}" is kept on this device.`);
354
+ }
355
+ let data;
356
+ try {
357
+ data = JSON.parse(copy.rawText);
358
+ } catch (error) {
359
+ throw new Error(`Recovery copy "${id}" is not valid JSON, so it cannot be restored as it is.`, { cause: error });
360
+ }
361
+ const currentRecord = await this.settingsToRawRecord(this.currentState.inputValues);
362
+ await recoveryStore.keep({
363
+ path: copy.path,
364
+ rawText: JSON.stringify(currentRecord, void 0, JSON_INDENT),
365
+ reason: SettingsRecoveryReason.LossyRewrite
366
+ });
367
+ await this.dataHandler.saveData(data);
368
+ await this.loadFromFile(false);
369
+ }
304
370
  /**
305
371
  * Revalidates the settings.
306
372
  *
@@ -488,6 +554,36 @@ class PluginSettingsComponentBase extends ComponentEx {
488
554
  isValidPropertyName(property) {
489
555
  return typeof property === "string" && this.propertyNames.includes(property);
490
556
  }
557
+ /**
558
+ * Keeps a recovery copy before the initial load's normalizing save, when that save would drop or change a stored
559
+ * value: an unknown key (a newer plugin version's setting), a legacy migration, a value the transformer rewrites.
560
+ * Adding defaults for keys the file lacks loses nothing and keeps no copy.
561
+ *
562
+ * @param originalJson - The record as the file held it, serialized before anything could mutate it.
563
+ * @param newRecord - The record about to be saved.
564
+ * @returns Whether the save may go ahead: nothing would be lost, a copy was kept, or the handler keeps no copies.
565
+ */
566
+ async keepCopyBeforeLossyRewrite(originalJson, newRecord) {
567
+ const recoveryStore = this.dataHandler.recoveryStore;
568
+ if (!recoveryStore || originalJson === void 0) {
569
+ return true;
570
+ }
571
+ const originalRecord = JSON.parse(originalJson);
572
+ if (originalRecord === null) {
573
+ return true;
574
+ }
575
+ const isLossy = Object.keys(originalRecord).some((key) => !Object.hasOwn(newRecord, key) || !isDeepEqual(newRecord[key], originalRecord[key]));
576
+ if (!isLossy) {
577
+ return true;
578
+ }
579
+ try {
580
+ await recoveryStore.keep({ path: "data.json", rawText: originalJson, reason: SettingsRecoveryReason.LossyRewrite });
581
+ return true;
582
+ } catch (error) {
583
+ console.error(new Error("Could not keep a recovery copy of data.json, so the normalized settings were not saved over it.", { cause: error }));
584
+ return false;
585
+ }
586
+ }
491
587
  markLoadedFromFile() {
492
588
  this.isLoadedFromFile = true;
493
589
  const resolvers = this.loadedFromFileResolvers.splice(0);
@@ -548,4 +644,4 @@ class PluginSettingsComponentBase extends ComponentEx {
548
644
  export {
549
645
  PluginSettingsComponentBase
550
646
  };
551
- //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi4uLy4uLy4uLy4uL3NyYy9jb21wb25lbnRzL3BsdWdpbi1zZXR0aW5ncy1jb21wb25lbnQudHMiXSwic291cmNlc0NvbnRlbnQiOlsiLyoqXG4gKiBAZmlsZVxuICpcbiAqIENvbXBvbmVudCB0aGF0IG1hbmFnZXMgcGx1Z2luIHNldHRpbmdzOiBkYXRhLCBwZXJzaXN0ZW5jZSwgdmFsaWRhdGlvbiwgYW5kIGV2ZW50cy5cbiAqXG4gKiBUaGlzIGlzIHRoZSBzaW5nbGUgcHVibGljLWZhY2luZyBzZXR0aW5ncyBBUEkgZm9yIHBsdWdpbiBhdXRob3JzLlxuICogQWxsIHNldHRpbmdzIGxvZ2ljIChsb2FkLCBzYXZlLCB2YWxpZGF0ZSwgdHJhbnNmb3JtLCBjbG9uZSkgaXMgaGFuZGxlZCBkaXJlY3RseVxuICogYnkgdGhpcyBjb21wb25lbnQg4oCUIG5vIHNlcGFyYXRlIG1hbmFnZXIgY2xhc3MgaXMgbmVlZGVkLlxuICovXG5cbmltcG9ydCB0eXBlIHtcbiAgQXN5bmNFdmVudFJlZixcbiAgQXN5bmNFdmVudFNvdXJjZVxufSBmcm9tICdAbW5hb3Vtb3YvdHlwZXNjcmlwdC1saWIvYXN5bmMtZXZlbnRzJztcbmltcG9ydCB0eXBlIHsgVHJhbnNmb3JtZXIgfSBmcm9tICdAbW5hb3Vtb3YvdHlwZXNjcmlwdC1saWIvdHJhbnNmb3JtZXJzL3RyYW5zZm9ybWVyJztcbmltcG9ydCB0eXBlIHtcbiAgTWF5YmVSZXR1cm4sXG4gIFN0cmluZ0tleXNcbn0gZnJvbSAnQG1uYW91bW92L3R5cGVzY3JpcHQtbGliL3R5cGUnO1xuaW1wb3J0IHR5cGUgeyBHZW5lcmljT2JqZWN0IH0gZnJvbSAnQG1uYW91bW92L3R5cGVzY3JpcHQtbGliL3R5cGUtZ3VhcmRzJztcbmltcG9ydCB0eXBlIHtcbiAgQ29uc3RydWN0b3IsXG4gIFByb21pc2FibGUsXG4gIFJlYWRvbmx5RGVlcFxufSBmcm9tICd0eXBlLWZlc3QnO1xuXG5pbXBvcnQgeyBBc3luY0V2ZW50cyB9IGZyb20gJ0BtbmFvdW1vdi90eXBlc2NyaXB0LWxpYi9hc3luYy1ldmVudHMnO1xuaW1wb3J0IHtcbiAgbm9vcCxcbiAgbm9vcEFzeW5jXG59IGZyb20gJ0BtbmFvdW1vdi90eXBlc2NyaXB0LWxpYi9mdW5jdGlvbic7XG5pbXBvcnQge1xuICBjYXN0VG8sXG4gIGdldEFsbEtleXMsXG4gIGlzRGVlcEVxdWFsXG59IGZyb20gJ0BtbmFvdW1vdi90eXBlc2NyaXB0LWxpYi9vYmplY3QtdXRpbHMnO1xuaW1wb3J0IHsgRGF0ZVRyYW5zZm9ybWVyIH0gZnJvbSAnQG1uYW91bW92L3R5cGVzY3JpcHQtbGliL3RyYW5zZm9ybWVycy9kYXRlLXRyYW5zZm9ybWVyJztcbmltcG9ydCB7IEdyb3VwVHJhbnNmb3JtZXIgfSBmcm9tICdAbW5hb3Vtb3YvdHlwZXNjcmlwdC1saWIvdHJhbnNmb3JtZXJzL2dyb3VwLXRyYW5zZm9ybWVyJztcbmltcG9ydCB7IE1hcFRyYW5zZm9ybWVyIH0gZnJvbSAnQG1uYW91bW92L3R5cGVzY3JpcHQtbGliL3RyYW5zZm9ybWVycy9tYXAtdHJhbnNmb3JtZXInO1xuaW1wb3J0IHsgU2V0VHJhbnNmb3JtZXIgfSBmcm9tICdAbW5hb3Vtb3YvdHlwZXNjcmlwdC1saWIvdHJhbnNmb3JtZXJzL3NldC10cmFuc2Zvcm1lcic7XG5pbXBvcnQgeyBTa2lwUHJpdmF0ZVByb3BlcnR5VHJhbnNmb3JtZXIgfSBmcm9tICdAbW5hb3Vtb3YvdHlwZXNjcmlwdC1saWIvdHJhbnNmb3JtZXJzL3NraXAtcHJpdmF0ZS1wcm9wZXJ0eS10cmFuc2Zvcm1lcic7XG5pbXBvcnQgeyBUd29XYXlNYXBUcmFuc2Zvcm1lciB9IGZyb20gJ0BtbmFvdW1vdi90eXBlc2NyaXB0LWxpYi90cmFuc2Zvcm1lcnMvdHdvLXdheS1tYXAtdHJhbnNmb3JtZXInO1xuaW1wb3J0IHsgVmFsdWVXcmFwcGVyIH0gZnJvbSAnQG1uYW91bW92L3R5cGVzY3JpcHQtbGliL3ZhbHVlLXdyYXBwZXInO1xuXG5pbXBvcnQgdHlwZSB7IERhdGFIYW5kbGVyIH0gZnJvbSAnLi4vZGF0YS1oYW5kbGVyLnRzJztcbmltcG9ydCB0eXBlIHsgUGx1Z2luRXZlbnRTb3VyY2UgfSBmcm9tICcuLi9wbHVnaW4vcGx1Z2luLWV2ZW50LXNvdXJjZS50cyc7XG5cbmltcG9ydCB7IGdldE9ic2lkaWFuTGliRGVidWdnZXIgfSBmcm9tICcuLi9kZWJ1Zy50cyc7XG5pbXBvcnQgeyBEdXJhdGlvblRyYW5zZm9ybWVyIH0gZnJvbSAnLi4vdHJhbnNmb3JtZXJzL2R1cmF0aW9uLXRyYW5zZm9ybWVyLnRzJztcbmltcG9ydCB7IHJlZ2lzdGVyQXN5bmNFdmVudCB9IGZyb20gJy4vYXN5bmMtZXZlbnRzLWNvbXBvbmVudC50cyc7XG5pbXBvcnQgeyBDb21wb25lbnRFeCB9IGZyb20gJy4vY29tcG9uZW50LWV4LnRzJztcblxuY29uc3QgZGVmYXVsdFRyYW5zZm9ybWVyID0gbmV3IEdyb3VwVHJhbnNmb3JtZXIoW1xuICBuZXcgU2tpcFByaXZhdGVQcm9wZXJ0eVRyYW5zZm9ybWVyKCksXG4gIG5ldyBEYXRlVHJhbnNmb3JtZXIoKSxcbiAgbmV3IER1cmF0aW9uVHJhbnNmb3JtZXIoKSxcbiAgbmV3IE1hcFRyYW5zZm9ybWVyKCksXG4gIG5ldyBTZXRUcmFuc2Zvcm1lcigpLFxuICBuZXcgVHdvV2F5TWFwVHJhbnNmb3JtZXIoKVxuXSk7XG5cbi8qKlxuICogQ29uc3RydWN0b3IgcGFyYW1ldGVycyBmb3Ige0BsaW5rIFBsdWdpblNldHRpbmdzQ29tcG9uZW50QmFzZX0uXG4gKlxuICogQHR5cGVQYXJhbSBQbHVnaW5TZXR0aW5ncyAtIFRoZSB0eXBlIG9mIHRoZSBwbHVnaW4gc2V0dGluZ3MuXG4gKi9cbmV4cG9ydCBpbnRlcmZhY2UgUGx1Z2luU2V0dGluZ3NDb21wb25lbnRCYXNlQ29uc3RydWN0b3JQYXJhbXM8UGx1Z2luU2V0dGluZ3M+IHtcbiAgLyoqXG4gICAqIFRoZSBkYXRhIGhhbmRsZXIgZm9yIHRoZSBwbHVnaW4uXG4gICAqL1xuICByZWFkb25seSBkYXRhSGFuZGxlcjogRGF0YUhhbmRsZXI7XG5cbiAgLyoqXG4gICAqIFRoZSBwbHVnaW4gZXZlbnRzLlxuICAgKi9cbiAgcmVhZG9ubHkgcGx1Z2luRXZlbnRTb3VyY2U6IFBsdWdpbkV2ZW50U291cmNlO1xuXG4gIC8qKlxuICAgKiBUaGUgcGx1Z2luIHNldHRpbmdzIGNsYXNzLlxuICAgKi9cbiAgcmVhZG9ubHkgcGx1Z2luU2V0dGluZ3NDbGFzczogQ29uc3RydWN0b3I8UGx1Z2luU2V0dGluZ3MsIFtdPjtcbn1cblxuLyoqXG4gKiBQYXJhbWV0ZXJzIGZvciB7QGxpbmsgUGx1Z2luU2V0dGluZ3NDb21wb25lbnRCYXNlLm9uU2F2ZVNldHRpbmdzfS5cbiAqXG4gKiBAdHlwZVBhcmFtIFBsdWdpblNldHRpbmdzIC0gVGhlIHR5cGUgb2YgdGhlIHBsdWdpbiBzZXR0aW5ncy5cbiAqL1xuZXhwb3J0IGludGVyZmFjZSBQbHVnaW5TZXR0aW5nc0NvbXBvbmVudEJhc2VPblNhdmVTZXR0aW5nc1BhcmFtczxQbHVnaW5TZXR0aW5ncyBleHRlbmRzIG9iamVjdD4ge1xuICAvKipcbiAgICogVGhlIHNhdmUgY29udGV4dC5cbiAgICovXG4gIHJlYWRvbmx5IGNvbnRleHQ6IHVua25vd247XG5cbiAgLyoqXG4gICAqIFRoZSBuZXcgc2V0dGluZ3Mgc3RhdGUuXG4gICAqL1xuICByZWFkb25seSBuZXdTdGF0ZTogUmVhZG9ubHlQbHVnaW5TZXR0aW5nc1N0YXRlPFBsdWdpblNldHRpbmdzPjtcblxuICAvKipcbiAgICogVGhlIG9sZCBzZXR0aW5ncyBzdGF0ZS5cbiAgICovXG4gIHJlYWRvbmx5IG9sZFN0YXRlOiBSZWFkb25seVBsdWdpblNldHRpbmdzU3RhdGU8UGx1Z2luU2V0dGluZ3M+O1xufVxuXG4vKipcbiAqIEEgc25hcHNob3Qgb2YgcGx1Z2luIHNldHRpbmdzIHN0YXRlLCBpbmNsdWRpbmcgcmF3IGlucHV0IHZhbHVlcywgZWZmZWN0aXZlICh2YWxpZGF0ZWQpIHZhbHVlcyxcbiAqIGFuZCBwZXItcHJvcGVydHkgdmFsaWRhdGlvbiBtZXNzYWdlcy5cbiAqXG4gKiBAdHlwZVBhcmFtIFBsdWdpblNldHRpbmdzIC0gVGhlIHR5cGUgb2YgdGhlIHBsdWdpbiBzZXR0aW5ncy5cbiAqL1xuZXhwb3J0IGludGVyZmFjZSBQbHVnaW5TZXR0aW5nc1N0YXRlPFBsdWdpblNldHRpbmdzIGV4dGVuZHMgb2JqZWN0PiB7XG4gIC8qKlxuICAgKiBUaGUgZWZmZWN0aXZlIHNldHRpbmdzIHZhbHVlcyB1c2VkIGJ5IHRoZSBwbHVnaW4uIEludmFsaWQgcHJvcGVydGllcyBhcmUgcmVwbGFjZWQgd2l0aCBkZWZhdWx0cy5cbiAgICovXG4gIHJlYWRvbmx5IGVmZmVjdGl2ZVZhbHVlczogUGx1Z2luU2V0dGluZ3M7XG5cbiAgLyoqXG4gICAqIFRoZSByYXcgaW5wdXQgdmFsdWVzIGFzIGVudGVyZWQgYnkgdGhlIHVzZXIuIE1heSBjb250YWluIGludmFsaWQgdmFsdWVzLlxuICAgKi9cbiAgcmVhZG9ubHkgaW5wdXRWYWx1ZXM6IFBsdWdpblNldHRpbmdzO1xuXG4gIC8qKlxuICAgKiBQZXItcHJvcGVydHkgdmFsaWRhdGlvbiBtZXNzYWdlcy4gRW1wdHkgc3RyaW5nIG1lYW5zIHZhbGlkLlxuICAgKi9cbiAgcmVhZG9ubHkgdmFsaWRhdGlvbk1lc3NhZ2VzOiBSZWNvcmQ8U3RyaW5nS2V5czxQbHVnaW5TZXR0aW5ncz4sIHN0cmluZz47XG59XG5cbi8qKlxuICogUmVhZG9ubHkgdmVyc2lvbiBvZiB7QGxpbmsgUGx1Z2luU2V0dGluZ3N9LlxuICpcbiAqIEB0eXBlUGFyYW0gUGx1Z2luU2V0dGluZ3MgLSBUaGUgdHlwZSBvZiB0aGUgcGx1Z2luIHNldHRpbmdzLlxuICovXG5leHBvcnQgdHlwZSBSZWFkb25seVBsdWdpblNldHRpbmdzPFBsdWdpblNldHRpbmdzIGV4dGVuZHMgb2JqZWN0PiA9IFJlYWRvbmx5RGVlcDxQbHVnaW5TZXR0aW5ncz47XG5cbi8qKlxuICogUmVhZG9ubHkgdmVyc2lvbiBvZiB7QGxpbmsgUGx1Z2luU2V0dGluZ3NTdGF0ZX0gZm9yIHVzZSBpbiBldmVudCBjYWxsYmFja3MgYW5kIHB1YmxpYyBnZXR0ZXJzLlxuICpcbiAqIEB0eXBlUGFyYW0gUGx1Z2luU2V0dGluZ3MgLSBUaGUgdHlwZSBvZiB0aGUgcGx1Z2luIHNldHRpbmdzLlxuICovXG5leHBvcnQgdHlwZSBSZWFkb25seVBsdWdpblNldHRpbmdzU3RhdGU8UGx1Z2luU2V0dGluZ3MgZXh0ZW5kcyBvYmplY3Q+ID0gUmVhZG9ubHlEZWVwPFBsdWdpblNldHRpbmdzU3RhdGU8UGx1Z2luU2V0dGluZ3M+PjtcblxuLyoqXG4gKiBBIHZhbGlkYXRvciBmdW5jdGlvbiBmb3IgYSBzZXR0aW5ncyBwcm9wZXJ0eS5cbiAqXG4gKiBAdHlwZVBhcmFtIFBsdWdpblNldHRpbmdzIC0gVGhlIHBsdWdpbiBzZXR0aW5ncyB0eXBlLlxuICogQHR5cGVQYXJhbSBQcm9wZXJ0eU5hbWUgLSBUaGUgcHJvcGVydHkgbmFtZS5cbiAqL1xuZXhwb3J0IHR5cGUgU2V0dGluZ3NWYWxpZGF0b3I8UGx1Z2luU2V0dGluZ3MgZXh0ZW5kcyBvYmplY3QsIFByb3BlcnR5TmFtZSBleHRlbmRzIFN0cmluZ0tleXM8UGx1Z2luU2V0dGluZ3M+ID0gU3RyaW5nS2V5czxQbHVnaW5TZXR0aW5ncz4+ID0gKFxuICB2YWx1ZTogUGx1Z2luU2V0dGluZ3NbUHJvcGVydHlOYW1lXSxcbiAgc2V0dGluZ3M6IFBsdWdpblNldHRpbmdzXG4pID0+IFByb21pc2FibGU8TWF5YmVSZXR1cm48c3RyaW5nPj47XG5cbmludGVyZmFjZSBQbHVnaW5TZXR0aW5nc0NvbXBvbmVudEJhc2VFdmVudE1hcDxQbHVnaW5TZXR0aW5ncyBleHRlbmRzIG9iamVjdD4ge1xuICByZWFkb25seSBsb2FkU2V0dGluZ3M6IFtcbiAgICBsb2FkZWRTdGF0ZTogUmVhZG9ubHlQbHVnaW5TZXR0aW5nc1N0YXRlPFBsdWdpblNldHRpbmdzPixcbiAgICBpc0luaXRpYWxMb2FkOiBib29sZWFuXG4gIF07XG4gIHJlYWRvbmx5IHNhdmVTZXR0aW5nczogW1xuICAgIG5ld1N0YXRlOiBSZWFkb25seVBsdWdpblNldHRpbmdzU3RhdGU8UGx1Z2luU2V0dGluZ3M+LFxuICAgIG9sZFN0YXRlOiBSZWFkb25seVBsdWdpblNldHRpbmdzU3RhdGU8UGx1Z2luU2V0dGluZ3M+LFxuICAgIGNvbnRleHQ6IHVua25vd25cbiAgXTtcbn1cblxuLyoqXG4gKiBQYXJhbWV0ZXJzIGZvciB7QGxpbmsgUGx1Z2luU2V0dGluZ3NDb21wb25lbnRCYXNlLnNldFByb3BlcnR5SW1wbH0uXG4gKlxuICogQHR5cGVQYXJhbSBQbHVnaW5TZXR0aW5ncyAtIFRoZSB0eXBlIG9mIHRoZSBwbHVnaW4gc2V0dGluZ3MuXG4gKi9cbmludGVyZmFjZSBQbHVnaW5TZXR0aW5nc0NvbXBvbmVudEJhc2VTZXRQcm9wZXJ0eUltcGxQYXJhbXM8UGx1Z2luU2V0dGluZ3MgZXh0ZW5kcyBvYmplY3Q+IHtcbiAgLyoqXG4gICAqIFRoZSBuYW1lIG9mIHRoZSBwcm9wZXJ0eSB0byBzZXQuXG4gICAqL1xuICByZWFkb25seSBwcm9wZXJ0eU5hbWU6IFByb3BlcnR5TmFtZXM8UGx1Z2luU2V0dGluZ3M+O1xuXG4gIC8qKlxuICAgKiBUaGUgdmFsaWRhdGlvbiBtZXNzYWdlLiBFbXB0eSBvciB1bnNldCBtZWFucyB2YWxpZC5cbiAgICovXG4gIHJlYWRvbmx5IHZhbGlkYXRpb25NZXNzYWdlPzogc3RyaW5nIHwgdW5kZWZpbmVkO1xuXG4gIC8qKlxuICAgKiBUaGUgdmFsdWUgdG8gc2V0LlxuICAgKi9cbiAgcmVhZG9ubHkgdmFsdWU6IFByb3BlcnR5VmFsdWVzPFBsdWdpblNldHRpbmdzPjtcbn1cblxudHlwZSBQcm9wZXJ0eU5hbWVzPFBsdWdpblNldHRpbmdzIGV4dGVuZHMgb2JqZWN0PiA9IFN0cmluZ0tleXM8UGx1Z2luU2V0dGluZ3M+O1xuXG50eXBlIFByb3BlcnR5VmFsdWVzPFBsdWdpblNldHRpbmdzIGV4dGVuZHMgb2JqZWN0PiA9IFBsdWdpblNldHRpbmdzW1Byb3BlcnR5TmFtZXM8UGx1Z2luU2V0dGluZ3M+XTtcblxudHlwZSBWYWxpZGF0aW9uUmVzdWx0PFBsdWdpblNldHRpbmdzIGV4dGVuZHMgb2JqZWN0PiA9IFBhcnRpYWw8UmVjb3JkPFN0cmluZ0tleXM8UGx1Z2luU2V0dGluZ3M+LCBzdHJpbmc+PjtcblxuLyoqXG4gKiBCYXNlIGNsYXNzIGZvciBwbHVnaW4gc2V0dGluZ3MgY29tcG9uZW50cy5cbiAqXG4gKiBNYW5hZ2VzIHNldHRpbmdzIGRhdGEsIHBlcnNpc3RlbmNlLCB2YWxpZGF0aW9uLCBhbmQgZXZlbnRzLlxuICogUGx1Z2luIGF1dGhvcnMgZXh0ZW5kIHRoaXMgY2xhc3MgYW5kIHBhc3MgdGhlaXIgc2V0dGluZ3MgY2xhc3MgYXNcbiAqIHtAbGluayBQbHVnaW5TZXR0aW5nc0NvbXBvbmVudEJhc2VDb25zdHJ1Y3RvclBhcmFtcy5wbHVnaW5TZXR0aW5nc0NsYXNzfSwgd2hvc2UgZGVmYXVsdC1jb25zdHJ1Y3RlZCBpbnN0YW5jZSBzdXBwbGllcyB0aGUgZGVmYXVsdHMuXG4gKlxuICogQHR5cGVQYXJhbSBQbHVnaW5TZXR0aW5ncyAtIFRoZSBwbHVnaW4gc2V0dGluZ3MgdHlwZS5cbiAqL1xuLy8gZXNsaW50LWRpc2FibGUtbmV4dC1saW5lIG9ic2lkaWFuLWRldi10b29sa2l0L3JlcXVpcmUtY29tcG9uZW50LXN1ZmZpeCAtLSBOb24tYWJzdHJhY3QgYmFzZSBjbGFzczsgY29uc3VtZXJzIGV4dGVuZCBpdC5cbmV4cG9ydCBjbGFzcyBQbHVnaW5TZXR0aW5nc0NvbXBvbmVudEJhc2U8UGx1Z2luU2V0dGluZ3MgZXh0ZW5kcyBvYmplY3Q+IGV4dGVuZHMgQ29tcG9uZW50RXggaW1wbGVtZW50cyBBc3luY0V2ZW50U291cmNlPFBsdWdpblNldHRpbmdzQ29tcG9uZW50QmFzZUV2ZW50TWFwPFBsdWdpblNldHRpbmdzPj4ge1xuICAvKipcbiAgICogR2V0cyB0aGUgcmVhZG9ubHkgZGVmYXVsdCBzZXR0aW5ncy5cbiAgICpcbiAgICogQHJldHVybnMgVGhlIGRlZmF1bHQgc2V0dGluZ3MgKGFzIGEgcmVhZG9ubHkgb2JqZWN0KS5cbiAgICovXG4gIHB1YmxpYyByZWFkb25seSBkZWZhdWx0U2V0dGluZ3M6IFJlYWRvbmx5RGVlcDxQbHVnaW5TZXR0aW5ncz47XG5cbiAgLyoqXG4gICAqIEdldHMgdGhlIHJlYWRvbmx5IGVmZmVjdGl2ZSBzZXR0aW5ncyAodmFsaWRhdGVkLCB3aXRoIGRlZmF1bHRzIHN1YnN0aXR1dGVkIGZvciBpbnZhbGlkIHZhbHVlcykuXG4gICAqXG4gICAqIEByZXR1cm5zIFRoZSByZWFkb25seSBlZmZlY3RpdmUgc2V0dGluZ3MuXG4gICAqL1xuICBwdWJsaWMgZ2V0IHNldHRpbmdzKCk6IFJlYWRvbmx5RGVlcDxQbHVnaW5TZXR0aW5ncz4ge1xuICAgIHJldHVybiB0aGlzLnNldHRpbmdzU3RhdGUuZWZmZWN0aXZlVmFsdWVzO1xuICB9XG5cbiAgLyoqXG4gICAqIEdldHMgdGhlIGN1cnJlbnQgc2V0dGluZ3Mgc3RhdGUgc25hcHNob3QuXG4gICAqXG4gICAqIEByZXR1cm5zIFRoZSBjdXJyZW50IHNldHRpbmdzIHN0YXRlLlxuICAgKi9cbiAgcHVibGljIGdldCBzZXR0aW5nc1N0YXRlKCk6IFJlYWRvbmx5UGx1Z2luU2V0dGluZ3NTdGF0ZTxQbHVnaW5TZXR0aW5ncz4ge1xuICAgIHJldHVybiB0aGlzLmN1cnJlbnRTdGF0ZSBhcyBSZWFkb25seVBsdWdpblNldHRpbmdzU3RhdGU8UGx1Z2luU2V0dGluZ3M+O1xuICB9XG5cbiAgLyoqXG4gICAqIFRoZSBkYXRhIGhhbmRsZXIgdXNlZCB0byBsb2FkIGFuZCBzYXZlIHRoZSBwbHVnaW4gc2V0dGluZ3MuXG4gICAqL1xuICBwcm90ZWN0ZWQgcmVhZG9ubHkgZGF0YUhhbmRsZXI6IERhdGFIYW5kbGVyO1xuICAvKipcbiAgICogVGhlIHBsdWdpbiBldmVudCBzb3VyY2UgdGhlIGNvbXBvbmVudCBsaXN0ZW5zIHRvIGZvciBleHRlcm5hbCBzZXR0aW5ncyBjaGFuZ2VzLlxuICAgKi9cbiAgcHJvdGVjdGVkIHJlYWRvbmx5IHBsdWdpbkV2ZW50U291cmNlOiBQbHVnaW5FdmVudFNvdXJjZTtcblxuICAvKipcbiAgICogVGhlIHBsdWdpbiBzZXR0aW5ncyBjbGFzcyB1c2VkIHRvIGNvbnN0cnVjdCBzZXR0aW5ncyBpbnN0YW5jZXMuXG4gICAqL1xuICBwcm90ZWN0ZWQgcmVhZG9ubHkgcGx1Z2luU2V0dGluZ3NDbGFzczogQ29uc3RydWN0b3I8UGx1Z2luU2V0dGluZ3MsIFtdPjtcbiAgcHJpdmF0ZSByZWFkb25seSBhc3luY0V2ZW50cyA9IG5ldyBBc3luY0V2ZW50czxQbHVnaW5TZXR0aW5nc0NvbXBvbmVudEJhc2VFdmVudE1hcDxQbHVnaW5TZXR0aW5ncz4+KCk7XG4gIHByaXZhdGUgY3VycmVudFN0YXRlOiBQbHVnaW5TZXR0aW5nc1N0YXRlPFBsdWdpblNldHRpbmdzPjtcblxuICBwcml2YXRlIGlzTG9hZGVkRnJvbUZpbGUgPSBmYWxzZTtcblxuICBwcml2YXRlIGxhc3RTYXZlZFN0YXRlOiBQbHVnaW5TZXR0aW5nc1N0YXRlPFBsdWdpblNldHRpbmdzPjtcblxuICBwcml2YXRlIHJlYWRvbmx5IGxlZ2FjeVNldHRpbmdzQ29udmVydGVyczogKChyZWNvcmQ6IEdlbmVyaWNPYmplY3QpID0+IHZvaWQpW10gPSBbXTtcbiAgcHJpdmF0ZSByZWFkb25seSBsb2FkZWRGcm9tRmlsZVJlc29sdmVyczogKCgpID0+IHZvaWQpW10gPSBbXTtcbiAgcHJpdmF0ZSByZWFkb25seSBwcm9wZXJ0eU5hbWVzOiBQcm9wZXJ0eU5hbWVzPFBsdWdpblNldHRpbmdzPltdO1xuXG4gIHByaXZhdGUgcmVhZG9ubHkgdmFsaWRhdG9ycyA9IG5ldyBNYXA8UHJvcGVydHlOYW1lczxQbHVnaW5TZXR0aW5ncz4sIFNldHRpbmdzVmFsaWRhdG9yPFBsdWdpblNldHRpbmdzPj4oKTtcblxuICAvKipcbiAgICogQ3JlYXRlcyBhIG5ldyBwbHVnaW4gc2V0dGluZ3MgY29tcG9uZW50LlxuICAgKlxuICAgKiBAcGFyYW0gcGFyYW1zIC0gVGhlIGNvbnN0cnVjdG9yIHBhcmFtZXRlcnMuXG4gICAqL1xuICBwdWJsaWMgY29uc3RydWN0b3IocGFyYW1zOiBQbHVnaW5TZXR0aW5nc0NvbXBvbmVudEJhc2VDb25zdHJ1Y3RvclBhcmFtczxQbHVnaW5TZXR0aW5ncz4pIHtcbiAgICBzdXBlcigpO1xuICAgIHRoaXMuZGF0YUhhbmRsZXIgPSBwYXJhbXMuZGF0YUhhbmRsZXI7XG4gICAgdGhpcy5wbHVnaW5TZXR0aW5nc0NsYXNzID0gcGFyYW1zLnBsdWdpblNldHRpbmdzQ2xhc3M7XG4gICAgdGhpcy5wbHVnaW5FdmVudFNvdXJjZSA9IHBhcmFtcy5wbHVnaW5FdmVudFNvdXJjZTtcblxuICAgIHRoaXMuZGVmYXVsdFNldHRpbmdzID0gbmV3IHRoaXMucGx1Z2luU2V0dGluZ3NDbGFzcygpIGFzIFJlYWRvbmx5RGVlcDxQbHVnaW5TZXR0aW5ncz47XG4gICAgdGhpcy5jdXJyZW50U3RhdGUgPSB0aGlzLmNyZWF0ZURlZmF1bHRTdGF0ZSgpO1xuICAgIHRoaXMubGFzdFNhdmVkU3RhdGUgPSB0aGlzLmNyZWF0ZURlZmF1bHRTdGF0ZSgpO1xuICAgIHRoaXMucHJvcGVydHlOYW1lcyA9IGdldEFsbEtleXModGhpcy5jdXJyZW50U3RhdGUuaW5wdXRWYWx1ZXMpO1xuICAgIHRoaXMucmVnaXN0ZXJWYWxpZGF0b3JzKCk7XG4gICAgdGhpcy5yZWdpc3RlckxlZ2FjeVNldHRpbmdzQ29udmVydGVycygpO1xuICB9XG5cbiAgLyoqXG4gICAqIEVkaXRzIHRoZSBwbHVnaW4gc2V0dGluZ3MgYW5kIHNhdmVzIHRoZW0uXG4gICAqXG4gICAqIEBwYXJhbSBzZXR0aW5nc0VkaXRvciAtIFRoZSBlZGl0b3IuXG4gICAqIEBwYXJhbSBjb250ZXh0IC0gVGhlIGNvbnRleHQuXG4gICAqIEByZXR1cm5zIEEge0BsaW5rIFByb21pc2V9IHRoYXQgcmVzb2x2ZXMgd2hlbiB0aGUgc2V0dGluZ3MgYXJlIHNhdmVkLlxuICAgKi9cbiAgcHVibGljIGFzeW5jIGVkaXRBbmRTYXZlKHNldHRpbmdzRWRpdG9yOiAoc2V0dGluZ3M6IFBsdWdpblNldHRpbmdzKSA9PiBQcm9taXNhYmxlPHZvaWQ+LCBjb250ZXh0PzogdW5rbm93bik6IFByb21pc2U8dm9pZD4ge1xuICAgIHRoaXMuZW5zdXJlTG9hZGVkKCk7XG4gICAgYXdhaXQgdGhpcy5lZGl0KHNldHRpbmdzRWRpdG9yKTtcbiAgICBhd2FpdCB0aGlzLnNhdmVUb0ZpbGUoY29udGV4dCk7XG4gIH1cblxuICAvKipcbiAgICogRW5zdXJlcyB0aGUgc2V0dGluZ3MgYXJlIHNhZmUuXG4gICAqXG4gICAqIEl0IHJ1bnMgdmFsaWRhdGlvbiBmb3IgZWFjaCBwcm9wZXJ0eSBhbmQgc2V0cyB0aGUgZGVmYXVsdCB2YWx1ZSBpZiB0aGUgdmFsaWRhdGlvbiBmYWlscy5cbiAgICpcbiAgICogQHBhcmFtIHNldHRpbmdzIC0gVGhlIHNldHRpbmdzLlxuICAgKiBAcmV0dXJucyBBIHtAbGluayBQcm9taXNlfSB0aGF0IHJlc29sdmVzIHdoZW4gdGhlIHNldHRpbmdzIGFyZSBzYWZlLlxuICAgKi9cbiAgcHVibGljIGFzeW5jIGVuc3VyZVNhZmUoc2V0dGluZ3M6IFBsdWdpblNldHRpbmdzKTogUHJvbWlzZTx2b2lkPiB7XG4gICAgY29uc3QgdmFsaWRhdGlvblJlc3VsdCA9IGF3YWl0IHRoaXMudmFsaWRhdGUoc2V0dGluZ3MpO1xuICAgIGNvbnN0IGRlZmF1bHRzID0gdGhpcy5kZWZhdWx0U2V0dGluZ3MgYXMgUGx1Z2luU2V0dGluZ3M7XG4gICAgZm9yIChjb25zdCBwcm9wZXJ0eU5hbWUgb2YgdGhpcy5wcm9wZXJ0eU5hbWVzKSB7XG4gICAgICAvLyBlc2xpbnQtZGlzYWJsZS1uZXh0LWxpbmUgdW5pY29ybi9uby1jb21wdXRlZC1wcm9wZXJ0eS1leGlzdGVuY2UtY2hlY2sgLS0gVGhpcyB0ZXN0cyB3aGV0aGVyIGEgdmFsaWRhdGlvbiBtZXNzYWdlIGlzIG5vbi1lbXB0eSwgbm90IHdoZXRoZXIgdGhlIGtleSBleGlzdHMuXG4gICAgICBpZiAodmFsaWRhdGlvblJlc3VsdFtwcm9wZXJ0eU5hbWVdKSB7XG4gICAgICAgIHNldHRpbmdzW3Byb3BlcnR5TmFtZV0gPSBkZWZhdWx0c1twcm9wZXJ0eU5hbWVdO1xuICAgICAgfVxuICAgIH1cbiAgfVxuXG4gIC8qKlxuICAgKiBHZXRzIGEgc2FmZSBjb3B5IG9mIHRoZSBzZXR0aW5ncy5cbiAgICpcbiAgICogQHBhcmFtIHNldHRpbmdzIC0gVGhlIHNldHRpbmdzLlxuICAgKiBAcmV0dXJucyBBIHtAbGluayBQcm9taXNlfSB0aGF0IHJlc29sdmVzIHRvIHRoZSBzYWZlIGNvcHkgb2YgdGhlIHNldHRpbmdzLlxuICAgKi9cbiAgcHVibGljIGFzeW5jIGdldFNhZmVDb3B5KHNldHRpbmdzOiBQbHVnaW5TZXR0aW5ncyk6IFByb21pc2U8UGx1Z2luU2V0dGluZ3M+IHtcbiAgICBjb25zdCBzYWZlU2V0dGluZ3MgPSBhd2FpdCB0aGlzLmNsb25lU2V0dGluZ3Moc2V0dGluZ3MpO1xuICAgIGF3YWl0IHRoaXMuZW5zdXJlU2FmZShzYWZlU2V0dGluZ3MpO1xuICAgIHJldHVybiBzYWZlU2V0dGluZ3M7XG4gIH1cblxuICAvKipcbiAgICogTG9hZHMgdGhlIHBsdWdpbiBzZXR0aW5ncyBmcm9tIHRoZSBmaWxlLlxuICAgKlxuICAgKiBAcGFyYW0gaXNJbml0aWFsTG9hZCAtIFdoZXRoZXIgdGhlIHNldHRpbmdzIGFyZSBiZWluZyBsb2FkZWQgZm9yIHRoZSBmaXJzdCB0aW1lLiBPbmx5IHRoZSBpbml0aWFsIGxvYWRcbiAgICogd3JpdGVzIHRoZSBub3JtYWxpemVkIHJlY29yZCBiYWNrIHRvIGBkYXRhLmpzb25gOyBhIHJlbG9hZCBhcHBsaWVzIGl0IGluIG1lbW9yeSBvbmx5LlxuICAgKiBAcmV0dXJucyBBIHtAbGluayBQcm9taXNlfSB0aGF0IHJlc29sdmVzIHdoZW4gdGhlIHNldHRpbmdzIGFyZSBsb2FkZWQuXG4gICAqL1xuICBwdWJsaWMgYXN5bmMgbG9hZEZyb21GaWxlKGlzSW5pdGlhbExvYWQ6IGJvb2xlYW4pOiBQcm9taXNlPHZvaWQ+IHtcbiAgICB0aGlzLmVuc3VyZUxvYWRlZCgpO1xuICAgIGNvbnN0IGRhdGEgPSBhd2FpdCB0aGlzLmRhdGFIYW5kbGVyLmxvYWREYXRhKCk7XG4gICAgdGhpcy5sYXN0U2F2ZWRTdGF0ZSA9IHRoaXMuY3JlYXRlRGVmYXVsdFN0YXRlKCk7XG4gICAgdGhpcy5jdXJyZW50U3RhdGUgPSB0aGlzLmNyZWF0ZURlZmF1bHRTdGF0ZSgpO1xuXG4gICAgdHJ5IHtcbiAgICAgIGlmIChkYXRhICE9PSB1bmRlZmluZWQgJiYgZGF0YSAhPT0gbnVsbCAmJiB0eXBlb2YgZGF0YSAhPT0gJ29iamVjdCcpIHtcbiAgICAgICAgY29uc29sZS5lcnJvcihgSW52YWxpZCBzZXR0aW5ncyBmcm9tIGRhdGEuanNvbi4gRXhwZWN0ZWQgT2JqZWN0LCBnb3Q6ICR7dHlwZW9mIGRhdGF9YCk7XG4gICAgICAgIHJldHVybjtcbiAgICAgIH1cblxuICAgICAgLy8gTm90aGluZyBzdG9yZWQgaXMgcmVhZCBhcyBhbiBlbXB0eSByZWNvcmQgcmF0aGVyIHRoYW4gc2tpcHBlZCwgc28gdGhlIHNhdmUgYmVsb3cgd3JpdGVzIHRoZSBmdWxsXG4gICAgICAvLyBkZWZhdWx0IHJlY29yZC4gV2l0aG91dCBpdCBhIHVzZXIgd2hvIG5ldmVyIGNoYW5nZWQgYSBzZXR0aW5nIGhhcyBubyBgZGF0YS5qc29uYCBhdCBhbGwsIGxvb2tzXG4gICAgICAvLyBleGFjdGx5IGxpa2UgYSBmcmVzaCBpbnN0YWxsLCBhbmQgc2lsZW50bHkgcGlja3MgdXAgZXZlcnkgZGVmYXVsdCBhIGxhdGVyIHJlbGVhc2UgY2hhbmdlcy5cbiAgICAgIGNvbnN0IHJhd1JlY29yZCA9IChkYXRhID8/IHt9KSBhcyBHZW5lcmljT2JqZWN0O1xuICAgICAgY29uc3QgcGFyc2VkU2V0dGluZ3MgPSBhd2FpdCB0aGlzLnJhd1JlY29yZFRvU2V0dGluZ3MocmF3UmVjb3JkKTtcbiAgICAgIGNvbnN0IHZhbGlkYXRpb25SZXN1bHQgPSBhd2FpdCB0aGlzLnZhbGlkYXRlKHBhcnNlZFNldHRpbmdzKTtcblxuICAgICAgZm9yIChjb25zdCBwcm9wZXJ0eU5hbWUgb2YgdGhpcy5wcm9wZXJ0eU5hbWVzKSB7XG4gICAgICAgIHRoaXMuc2V0UHJvcGVydHlJbXBsKHtcbiAgICAgICAgICBwcm9wZXJ0eU5hbWUsXG4gICAgICAgICAgdmFsaWRhdGlvbk1lc3NhZ2U6IHZhbGlkYXRpb25SZXN1bHRbcHJvcGVydHlOYW1lXSxcbiAgICAgICAgICB2YWx1ZTogcGFyc2VkU2V0dGluZ3NbcHJvcGVydHlOYW1lXVxuICAgICAgICB9KTtcbiAgICAgIH1cblxuICAgICAgdGhpcy5sYXN0U2F2ZWRTdGF0ZSA9IGF3YWl0IHRoaXMuY2xvbmVTdGF0ZSh0aGlzLmN1cnJlbnRTdGF0ZSk7XG5cbiAgICAgIC8vIEEgY29tcG9uZW50IHRoYXQga25vd3Mgbm8gcHJvcGVydHkgbmFtZXMgY2Fubm90IG5vcm1hbGl6ZSBhbnl0aGluZzogYHNldHRpbmdzVG9SYXdSZWNvcmQoKWAgY2FuXG4gICAgICAvLyBvbmx5IGV2ZXIgcmV0dXJuIGB7fWAsIHNvIHRoZSBzYXZlIGJlbG93IHdvdWxkIG5vdCByZXdyaXRlIGBkYXRhLmpzb25gIC0tIGl0IHdvdWxkIGVtcHR5IGl0LlxuICAgICAgLy8gYFBsdWdpbkJhc2VgIGFkZHMgYSBwbGFjZWhvbGRlciBgUGx1Z2luU2V0dGluZ3NDb21wb25lbnRCYXNlPG9iamVjdD5gIGJlZm9yZSBgb25sb2FkSW1wbCgpYCBzd2Fwc1xuICAgICAgLy8gaW4gdGhlIHBsdWdpbidzIG93biBjb21wb25lbnQsIGFuZCB0aGF0IHBsYWNlaG9sZGVyIGlzIGV4YWN0bHkgdGhpcyBjYXNlOiBpdCByZWFkIGV2ZXJ5IHJlYWxcbiAgICAgIC8vIHNldHRpbmcsIGtlcHQgbm9uZSBvZiB0aGVtLCBhbmQgc2F2ZWQgdGhlIGRpZmZlcmVuY2UgYmFjayBvdmVyIHRoZSBmaWxlLlxuICAgICAgLy9cbiAgICAgIC8vIEEgcmVsb2FkIGNhdXNlZCBieSBhbiBleHRlcm5hbCBjaGFuZ2UgKGEgc3luYyB0b29sLCBhbm90aGVyIGRldmljZSkgYXBwbGllcyB0aGUgbm9ybWFsaXplZFxuICAgICAgLy8gc2V0dGluZ3MgaW4gbWVtb3J5IGFuZCBuZXZlciB3cml0ZXMgdGhlbSBiYWNrLiBUd28gc3luY2VkIGRldmljZXMgd2hvc2Ugbm9ybWFsaXphdGlvbiBkaWZmZXJzXG4gICAgICAvLyAoZGlmZmVyZW50IHBsdWdpbiB2ZXJzaW9ucywgb3IgYW55IG5vcm1hbGl6YXRpb24gdGhhdCBpcyBub3QgYSBmaXhlZCBwb2ludCkgd291bGQgb3RoZXJ3aXNlXG4gICAgICAvLyByZXdyaXRlIGVhY2ggb3RoZXIncyBgZGF0YS5qc29uYCBvbiBldmVyeSByZWxvYWQsIGFuZCB0aGUgc3luYyB0b29sIHdvdWxkIGNhcnJ5IGVhY2ggcmV3cml0ZVxuICAgICAgLy8gYmFjaywgZm9yZXZlciAoYG9ic2lkaWFuLWN1c3RvbS1hdHRhY2htZW50LWxvY2F0aW9uYCAjMTAyKS4gVGhlIGluaXRpYWwgbG9hZCBzdGlsbCB3cml0ZXM6XG4gICAgICAvLyB0aGUgZGVmYXVsdCByZWNvcmQgYW5kIHRoZSBsZWdhY3kgbWlncmF0aW9ucyBkZXBlbmQgb24gaXQuXG4gICAgICBpZiAodGhpcy5wcm9wZXJ0eU5hbWVzLmxlbmd0aCA9PT0gMCB8fCAhaXNJbml0aWFsTG9hZCkge1xuICAgICAgICByZXR1cm47XG4gICAgICB9XG5cbiAgICAgIGNvbnN0IG5ld1JlY29yZCA9IGF3YWl0IHRoaXMuc2V0dGluZ3NUb1Jhd1JlY29yZCh0aGlzLmN1cnJlbnRTdGF0ZS5pbnB1dFZhbHVlcyk7XG5cbiAgICAgIGlmICghaXNEZWVwRXF1YWwobmV3UmVjb3JkLCBkYXRhKSkge1xuICAgICAgICBhd2FpdCB0aGlzLnNhdmVUb0ZpbGVJbXBsKCk7XG4gICAgICB9XG4gICAgfSBmaW5hbGx5IHtcbiAgICAgIHRoaXMubWFya0xvYWRlZEZyb21GaWxlKCk7XG4gICAgICBhd2FpdCB0aGlzLmFzeW5jRXZlbnRzLnRyaWdnZXJBc3luYygnbG9hZFNldHRpbmdzJywgdGhpcy5jdXJyZW50U3RhdGUgYXMgUmVhZG9ubHlQbHVnaW5TZXR0aW5nc1N0YXRlPFBsdWdpblNldHRpbmdzPiwgaXNJbml0aWFsTG9hZCk7XG4gICAgfVxuICB9XG5cbiAgLyoqXG4gICAqIFJlbW92ZSBhbiBldmVudCBsaXN0ZW5lci5cbiAgICpcbiAgICogQHR5cGVQYXJhbSBFdmVudE5hbWUgLSBUaGUgbmFtZSBvZiB0aGUgZXZlbnQuXG4gICAqIEB0eXBlUGFyYW0gQXJndW1lbnRzIC0gVGhlIHR5cGVzIG9mIHRoZSBhcmd1bWVudHMgdGhlIGV2ZW50IGNhbGxiYWNrIGFjY2VwdHMuXG4gICAqIEBwYXJhbSBuYW1lIC0gVGhlIG5hbWUgb2YgdGhlIGV2ZW50LlxuICAgKiBAcGFyYW0gY2FsbGJhY2sgLSBUaGUgY2FsbGJhY2sgdG8gcmVtb3ZlLlxuICAgKi9cbiAgcHVibGljIG9mZjxcbiAgICBFdmVudE5hbWUgZXh0ZW5kcyBrZXlvZiBQbHVnaW5TZXR0aW5nc0NvbXBvbmVudEJhc2VFdmVudE1hcDxQbHVnaW5TZXR0aW5ncz4sXG4gICAgLy8gZXNsaW50LWRpc2FibGUtbmV4dC1saW5lIEB0eXBlc2NyaXB0LWVzbGludC9uby11bm5lY2Vzc2FyeS10eXBlLXBhcmFtZXRlcnMgLS0gV2UgbmVlZCB0byB1c2UgdGhlIGR1bW15IHBhcmFtZXRlciB0byBnZXQgdHlwZSBpbmZlcmVuY2UuXG4gICAgQXJndW1lbnRzIGV4dGVuZHMgRXZlbnROYW1lIGV4dGVuZHMga2V5b2YgUGx1Z2luU2V0dGluZ3NDb21wb25lbnRCYXNlRXZlbnRNYXA8UGx1Z2luU2V0dGluZ3M+ID8gUGx1Z2luU2V0dGluZ3NDb21wb25lbnRCYXNlRXZlbnRNYXA8UGx1Z2luU2V0dGluZ3M+W0V2ZW50TmFtZV1cbiAgICAgIDogdW5rbm93bltdXG4gID4obmFtZTogRXZlbnROYW1lLCBjYWxsYmFjazogKC4uLiRhcmd1bWVudHM6IEFyZ3VtZW50cykgPT4gUHJvbWlzYWJsZTx2b2lkPik6IHZvaWQge1xuICAgIHRoaXMuYXN5bmNFdmVudHMub2ZmKG5hbWUsIGNhbGxiYWNrKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBSZW1vdmUgYW4gZXZlbnQgbGlzdGVuZXIgYnkgcmVmZXJlbmNlLlxuICAgKlxuICAgKiBAcGFyYW0gZXZlbnRSZWYgLSBUaGUgcmVmZXJlbmNlIHRvIHRoZSBldmVudCBsaXN0ZW5lci5cbiAgICovXG4gIHB1YmxpYyBvZmZyZWYoZXZlbnRSZWY6IEFzeW5jRXZlbnRSZWYpOiB2b2lkIHtcbiAgICB0aGlzLmFzeW5jRXZlbnRzLm9mZnJlZihldmVudFJlZik7XG4gIH1cblxuICAvKipcbiAgICogQWRkIGFuIGV2ZW50IGxpc3RlbmVyLlxuICAgKlxuICAgKiBAdHlwZVBhcmFtIEV2ZW50TmFtZSAtIFRoZSBuYW1lIG9mIHRoZSBldmVudC5cbiAgICogQHR5cGVQYXJhbSBBcmd1bWVudHMgLSBUaGUgdHlwZXMgb2YgdGhlIGFyZ3VtZW50cyB0aGUgZXZlbnQgY2FsbGJhY2sgYWNjZXB0cy5cbiAgICogQHBhcmFtIG5hbWUgLSBUaGUgbmFtZSBvZiB0aGUgZXZlbnQuXG4gICAqIEBwYXJhbSBjYWxsYmFjayAtIFRoZSBjYWxsYmFjayB0byBjYWxsIHdoZW4gdGhlIGV2ZW50IGlzIHRyaWdnZXJlZC5cbiAgICogQHBhcmFtIHRoaXNBcmd1bWVudCAtIFRoZSBjb250ZXh0IHBhc3NlZCBhcyBgdGhpc2AgdG8gdGhlIGBjYWxsYmFja2AuXG4gICAqIEByZXR1cm5zIEEgcmVmZXJlbmNlIHRvIHRoZSBldmVudCBsaXN0ZW5lci5cbiAgICpcbiAgICogQHJlbWFya3MgTm90IHJlZmFjdG9yZWQgdG8gcGFyYW1ldGVyLW9iamVjdCBwYXR0ZXJuLCB0byBrZWVwIHRoZSBwYXJpdHkgd2l0aCB7QGxpbmsgb2JzaWRpYW4jRXZlbnRzI29ufSAob3Igb25jZSwgY29ycmVzcG9uZGluZ2x5KS5cbiAgICovXG4gIHB1YmxpYyBvbjxcbiAgICBFdmVudE5hbWUgZXh0ZW5kcyBrZXlvZiBQbHVnaW5TZXR0aW5nc0NvbXBvbmVudEJhc2VFdmVudE1hcDxQbHVnaW5TZXR0aW5ncz4sXG4gICAgLy8gZXNsaW50LWRpc2FibGUtbmV4dC1saW5lIEB0eXBlc2NyaXB0LWVzbGludC9uby11bm5lY2Vzc2FyeS10eXBlLXBhcmFtZXRlcnMgLS0gV2UgbmVlZCB0byB1c2UgdGhlIGR1bW15IHBhcmFtZXRlciB0byBnZXQgdHlwZSBpbmZlcmVuY2UuXG4gICAgQXJndW1lbnRzIGV4dGVuZHMgRXZlbnROYW1lIGV4dGVuZHMga2V5b2YgUGx1Z2luU2V0dGluZ3NDb21wb25lbnRCYXNlRXZlbnRNYXA8UGx1Z2luU2V0dGluZ3M+ID8gUGx1Z2luU2V0dGluZ3NDb21wb25lbnRCYXNlRXZlbnRNYXA8UGx1Z2luU2V0dGluZ3M+W0V2ZW50TmFtZV1cbiAgICAgIDogdW5rbm93bltdXG4gID4obmFtZTogRXZlbnROYW1lLCBjYWxsYmFjazogKC4uLiRhcmd1bWVudHM6IEFyZ3VtZW50cykgPT4gUHJvbWlzYWJsZTx2b2lkPiwgdGhpc0FyZ3VtZW50PzogdW5rbm93bik6IEFzeW5jRXZlbnRSZWYge1xuICAgIHJldHVybiB0aGlzLmFzeW5jRXZlbnRzLm9uKG5hbWUsIGNhbGxiYWNrLCB0aGlzQXJndW1lbnQpO1xuICB9XG5cbiAgLyoqXG4gICAqIFRyaWdnZXIgYW4gZXZlbnQsIGV4ZWN1dGluZyBhbGwgdGhlIGxpc3RlbmVycyBpbiBvcmRlciBldmVuIGlmIHNvbWUgb2YgdGhlbSB0aHJvdyBhbiBlcnJvci5cbiAgICpcbiAgICogQWRkIGFuIGV2ZW50IGxpc3RlbmVyIHRoYXQgd2lsbCBiZSBjYWxsZWQgb25seSBvbmNlLlxuICAgKlxuICAgKiBAdHlwZVBhcmFtIEV2ZW50TmFtZSAtIFRoZSBuYW1lIG9mIHRoZSBldmVudC5cbiAgICogQHR5cGVQYXJhbSBBcmd1bWVudHMgLSBUaGUgdHlwZXMgb2YgdGhlIGFyZ3VtZW50cyB0aGUgZXZlbnQgY2FsbGJhY2sgYWNjZXB0cy5cbiAgICogQHBhcmFtIG5hbWUgLSBUaGUgbmFtZSBvZiB0aGUgZXZlbnQuXG4gICAqIEBwYXJhbSBjYWxsYmFjayAtIFRoZSBjYWxsYmFjayB0byBjYWxsIHdoZW4gdGhlIGV2ZW50IGlzIHRyaWdnZXJlZC5cbiAgICogQHBhcmFtIHRoaXNBcmd1bWVudCAtIFRoZSBjb250ZXh0IHBhc3NlZCBhcyBgdGhpc2AgdG8gdGhlIGBjYWxsYmFja2AuXG4gICAqIEByZXR1cm5zIEEgcmVmZXJlbmNlIHRvIHRoZSBldmVudCBsaXN0ZW5lci5cbiAgICpcbiAgICogQHJlbWFya3MgTm90IHJlZmFjdG9yZWQgdG8gcGFyYW1ldGVyLW9iamVjdCBwYXR0ZXJuLCB0byBrZWVwIHRoZSBwYXJpdHkgd2l0aCB7QGxpbmsgb2JzaWRpYW4jRXZlbnRzI29ufSAob3Igb25jZSwgY29ycmVzcG9uZGluZ2x5KS5cbiAgICovXG4gIHB1YmxpYyBvbmNlPFxuICAgIEV2ZW50TmFtZSBleHRlbmRzIGtleW9mIFBsdWdpblNldHRpbmdzQ29tcG9uZW50QmFzZUV2ZW50TWFwPFBsdWdpblNldHRpbmdzPixcbiAgICAvLyBlc2xpbnQtZGlzYWJsZS1uZXh0LWxpbmUgQHR5cGVzY3JpcHQtZXNsaW50L25vLXVubmVjZXNzYXJ5LXR5cGUtcGFyYW1ldGVycyAtLSBXZSBuZWVkIHRvIHVzZSB0aGUgZHVtbXkgcGFyYW1ldGVyIHRvIGdldCB0eXBlIGluZmVyZW5jZS5cbiAgICBBcmd1bWVudHMgZXh0ZW5kcyBFdmVudE5hbWUgZXh0ZW5kcyBrZXlvZiBQbHVnaW5TZXR0aW5nc0NvbXBvbmVudEJhc2VFdmVudE1hcDxQbHVnaW5TZXR0aW5ncz4gPyBQbHVnaW5TZXR0aW5nc0NvbXBvbmVudEJhc2VFdmVudE1hcDxQbHVnaW5TZXR0aW5ncz5bRXZlbnROYW1lXVxuICAgICAgOiB1bmtub3duW11cbiAgPihuYW1lOiBFdmVudE5hbWUsIGNhbGxiYWNrOiAoLi4uJGFyZ3VtZW50czogQXJndW1lbnRzKSA9PiBQcm9taXNhYmxlPHZvaWQ+LCB0aGlzQXJndW1lbnQ/OiB1bmtub3duKTogQXN5bmNFdmVudFJlZiB7XG4gICAgcmV0dXJuIHRoaXMuYXN5bmNFdmVudHMub25jZShuYW1lLCBjYWxsYmFjaywgdGhpc0FyZ3VtZW50KTtcbiAgfVxuXG4gIC8qKlxuICAgKiBDYWxsZWQgd2hlbiB0aGUgZXh0ZXJuYWwgc2V0dGluZ3MgY2hhbmdlLlxuICAgKlxuICAgKiBAcmV0dXJucyBBIHtAbGluayBQcm9taXNlfSB0aGF0IHJlc29sdmVzIHdoZW4gdGhlIHNldHRpbmdzIGFyZSByZWxvYWRlZC5cbiAgICovXG4gIHB1YmxpYyBhc3luYyBvbkV4dGVybmFsU2V0dGluZ3NDaGFuZ2UoKTogUHJvbWlzZTx2b2lkPiB7XG4gICAgdGhpcy5lbnN1cmVMb2FkZWQoKTtcbiAgICBhd2FpdCB0aGlzLmxvYWRGcm9tRmlsZShmYWxzZSk7XG4gIH1cblxuICAvKipcbiAgICogTG9hZHMgc2V0dGluZ3MgZnJvbSBmaWxlIGFuZCByZWdpc3RlcnMgZXZlbnQgaGFuZGxlcnMuXG4gICAqL1xuICBwdWJsaWMgb3ZlcnJpZGUgYXN5bmMgb25sb2FkQXN5bmMoKTogUHJvbWlzZTx2b2lkPiB7XG4gICAgcmVnaXN0ZXJBc3luY0V2ZW50KHRoaXMsIHRoaXMub24oJ2xvYWRTZXR0aW5ncycsIHRoaXMub25Mb2FkU2V0dGluZ3MuYmluZCh0aGlzKSkpO1xuICAgIHJlZ2lzdGVyQXN5bmNFdmVudCh0aGlzLCB0aGlzLm9uKCdzYXZlU2V0dGluZ3MnLCAobmV3U3RhdGUsIG9sZFN0YXRlLCBjb250ZXh0KSA9PiB0aGlzLm9uU2F2ZVNldHRpbmdzKHsgY29udGV4dCwgbmV3U3RhdGUsIG9sZFN0YXRlIH0pKSk7XG4gICAgcmVnaXN0ZXJBc3luY0V2ZW50KHRoaXMsIHRoaXMucGx1Z2luRXZlbnRTb3VyY2Uub24oJ2V4dGVybmFsU2V0dGluZ3NDaGFuZ2UnLCB0aGlzLm9uRXh0ZXJuYWxTZXR0aW5nc0NoYW5nZS5iaW5kKHRoaXMpKSk7XG4gICAgYXdhaXQgdGhpcy5sb2FkRnJvbUZpbGUodHJ1ZSk7XG4gIH1cblxuICAvKipcbiAgICogUmVnaXN0ZXJzIGEgbGVnYWN5IHNldHRpbmdzIGNvbnZlcnRlci5cbiAgICpcbiAgICogQHR5cGVQYXJhbSBMZWdhY3lTZXR0aW5ncyAtIFRoZSBsZWdhY3kgc2V0dGluZ3MgY2xhc3MuXG4gICAqIEBwYXJhbSBsZWdhY3lTZXR0aW5nc0NsYXNzIC0gVGhlIGxlZ2FjeSBzZXR0aW5ncyBjbGFzcy5cbiAgICogQHBhcmFtIGNvbnZlcnRlciAtIFRoZSBjb252ZXJ0ZXIuXG4gICAqL1xuICBwdWJsaWMgcmVnaXN0ZXJMZWdhY3lTZXR0aW5nc0NvbnZlcnRlcjxMZWdhY3lTZXR0aW5ncyBleHRlbmRzIG9iamVjdD4oXG4gICAgbGVnYWN5U2V0dGluZ3NDbGFzczogbmV3ICgpID0+IExlZ2FjeVNldHRpbmdzLFxuICAgIGNvbnZlcnRlcjogKGxlZ2FjeVNldHRpbmdzOiBQYXJ0aWFsPExlZ2FjeVNldHRpbmdzPiAmIFBhcnRpYWw8UGx1Z2luU2V0dGluZ3M+KSA9PiB2b2lkXG4gICk6IHZvaWQge1xuICAgIGNvbnN0IHRoaXNXcmFwcGVyID0gVmFsdWVXcmFwcGVyLm9mKHRoaXMpO1xuICAgIHRoaXMubGVnYWN5U2V0dGluZ3NDb252ZXJ0ZXJzLnB1c2gobGVnYWN5U2V0dGluZ3NDb252ZXJ0ZXIpO1xuXG4gICAgZnVuY3Rpb24gbGVnYWN5U2V0dGluZ3NDb252ZXJ0ZXIocmVjb3JkOiBHZW5lcmljT2JqZWN0KTogdm9pZCB7XG4gICAgICBjb25zdCBsZWdhY3lTZXR0aW5nc0tleXMgPSBuZXcgU2V0PHN0cmluZz4oT2JqZWN0LmtleXMobmV3IGxlZ2FjeVNldHRpbmdzQ2xhc3MoKSkpO1xuICAgICAgY29uc3QgcGx1Z2luU2V0dGluZ0tleXMgPSBuZXcgU2V0PHN0cmluZz4odGhpc1dyYXBwZXIudmFsdWUucHJvcGVydHlOYW1lcyk7XG4gICAgICBjb25zdCBsZWdhY3lTZXR0aW5ncyA9IHJlY29yZCBhcyBQYXJ0aWFsPExlZ2FjeVNldHRpbmdzPiAmIFBhcnRpYWw8UGx1Z2luU2V0dGluZ3M+O1xuICAgICAgY29udmVydGVyKGxlZ2FjeVNldHRpbmdzKTtcbiAgICAgIGZvciAoY29uc3Qga2V5IG9mIE9iamVjdC5rZXlzKGxlZ2FjeVNldHRpbmdzKSkge1xuICAgICAgICBpZiAocGx1Z2luU2V0dGluZ0tleXMuaGFzKGtleSkgfHwgIWxlZ2FjeVNldHRpbmdzS2V5cy5oYXMoa2V5KSkge1xuICAgICAgICAgIGNvbnRpbnVlO1xuICAgICAgICB9XG5cbiAgICAgICAgLy8gZXNsaW50LWRpc2FibGUtbmV4dC1saW5lIEB0eXBlc2NyaXB0LWVzbGludC9uby1keW5hbWljLWRlbGV0ZSAtLSBXZSBoYXZlIG5vIG90aGVyIHdheSB0byBkZWxldGUgdGhlIHByb3BlcnR5LlxuICAgICAgICBkZWxldGUgcmVjb3JkW2tleV07XG4gICAgICB9XG4gICAgfVxuICB9XG5cbiAgLyoqXG4gICAqIFJlZ2lzdGVycyBhIHZhbGlkYXRvciBmb3IgYSBwcm9wZXJ0eS5cbiAgICpcbiAgICogQHR5cGVQYXJhbSBQcm9wZXJ0eU5hbWUgLSBUaGUgbmFtZSBvZiB0aGUgc2V0dGluZ3MgcHJvcGVydHkuXG4gICAqIEBwYXJhbSBwcm9wZXJ0eU5hbWUgLSBUaGUgbmFtZSBvZiB0aGUgcHJvcGVydHkuXG4gICAqIEBwYXJhbSB2YWxpZGF0b3IgLSBUaGUgdmFsaWRhdG9yLlxuICAgKi9cbiAgcHVibGljIHJlZ2lzdGVyVmFsaWRhdG9yPFByb3BlcnR5TmFtZSBleHRlbmRzIFByb3BlcnR5TmFtZXM8UGx1Z2luU2V0dGluZ3M+PihcbiAgICBwcm9wZXJ0eU5hbWU6IFByb3BlcnR5TmFtZSxcbiAgICB2YWxpZGF0b3I6IFNldHRpbmdzVmFsaWRhdG9yPFBsdWdpblNldHRpbmdzLCBQcm9wZXJ0eU5hbWU+XG4gICk6IHZvaWQge1xuICAgIHRoaXMudmFsaWRhdG9ycy5zZXQocHJvcGVydHlOYW1lLCB2YWxpZGF0b3IgYXMgU2V0dGluZ3NWYWxpZGF0b3I8UGx1Z2luU2V0dGluZ3M+KTtcbiAgfVxuXG4gIC8qKlxuICAgKiBSZXZhbGlkYXRlcyB0aGUgc2V0dGluZ3MuXG4gICAqXG4gICAqIEByZXR1cm5zIFRoZSB2YWxpZGF0aW9uIG1lc3NhZ2VzLlxuICAgKi9cbiAgcHVibGljIGFzeW5jIHJldmFsaWRhdGUoKTogUHJvbWlzZTxSZWNvcmQ8UHJvcGVydHlOYW1lczxQbHVnaW5TZXR0aW5ncz4sIHN0cmluZz4+IHtcbiAgICB0aGlzLmVuc3VyZUxvYWRlZCgpO1xuICAgIGF3YWl0IHRoaXMuZWRpdChub29wKTtcbiAgICByZXR1cm4gdGhpcy5jdXJyZW50U3RhdGUudmFsaWRhdGlvbk1lc3NhZ2VzO1xuICB9XG5cbiAgLyoqXG4gICAqIFNhdmVzIHRoZSBuZXcgcGx1Z2luIHNldHRpbmdzLlxuICAgKlxuICAgKiBAcGFyYW0gY29udGV4dCAtIFRoZSBjb250ZXh0IG9mIHRoZSBzYXZlIHRvIGZpbGUgb3BlcmF0aW9uLlxuICAgKiBAcmV0dXJucyBBIHtAbGluayBQcm9taXNlfSB0aGF0IHJlc29sdmVzIHdoZW4gdGhlIHNldHRpbmdzIGFyZSBzYXZlZC5cbiAgICovXG4gIHB1YmxpYyBhc3luYyBzYXZlVG9GaWxlKGNvbnRleHQ/OiB1bmtub3duKTogUHJvbWlzZTx2b2lkPiB7XG4gICAgdGhpcy5lbnN1cmVMb2FkZWQoKTtcbiAgICBpZiAoaXNEZWVwRXF1YWwodGhpcy5sYXN0U2F2ZWRTdGF0ZS5pbnB1dFZhbHVlcywgdGhpcy5jdXJyZW50U3RhdGUuaW5wdXRWYWx1ZXMpKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgdHJ5IHtcbiAgICAgIGF3YWl0IHRoaXMuc2F2ZVRvRmlsZUltcGwoKTtcbiAgICB9IGNhdGNoIChlcnJvcikge1xuICAgICAgLy8gQSByZWZ1c2VkIHNhdmUgKGFuIG92ZXJzaXplZCBgZGF0YS5qc29uYCwgc2VlIGBQbHVnaW5EYXRhSGFuZGxlcmApIHdyb3RlIG5vdGhpbmcsIHNvIHRoZSBmaWxlIHN0aWxsIGhvbGRzXG4gICAgICAvLyB0aGUgbGFzdCBzYXZlZCBzZXR0aW5ncy4gUHV0IG1lbW9yeSBiYWNrIHRvIG1hdGNoIGl0OiBvdGhlcndpc2UgZXZlcnkgbGF0ZXIgc2F2ZSB3b3VsZCBjYXJyeSB0aGUgcmVqZWN0ZWRcbiAgICAgIC8vIGVkaXQgYWdhaW4gYW5kIGZhaWwgdGhlIHNhbWUgd2F5LCBhbmQgdGhlIHBsdWdpbiB3b3VsZCBydW4gb24gc2V0dGluZ3MgdGhhdCBleGlzdCBub3doZXJlIG9uIGRpc2suXG4gICAgICB0aGlzLmN1cnJlbnRTdGF0ZSA9IGF3YWl0IHRoaXMuY2xvbmVTdGF0ZSh0aGlzLmxhc3RTYXZlZFN0YXRlKTtcbiAgICAgIHRocm93IGVycm9yO1xuICAgIH1cbiAgICBhd2FpdCB0aGlzLmFzeW5jRXZlbnRzLnRyaWdnZXJBc3luYyhcbiAgICAgICdzYXZlU2V0dGluZ3MnLFxuICAgICAgdGhpcy5jdXJyZW50U3RhdGUgYXMgUmVhZG9ubHlQbHVnaW5TZXR0aW5nc1N0YXRlPFBsdWdpblNldHRpbmdzPixcbiAgICAgIHRoaXMubGFzdFNhdmVkU3RhdGUgYXMgUmVhZG9ubHlQbHVnaW5TZXR0aW5nc1N0YXRlPFBsdWdpblNldHRpbmdzPixcbiAgICAgIGNvbnRleHRcbiAgICApO1xuICAgIHRoaXMubGFzdFNhdmVkU3RhdGUgPSBhd2FpdCB0aGlzLmNsb25lU3RhdGUodGhpcy5jdXJyZW50U3RhdGUpO1xuICB9XG5cbiAgLyoqXG4gICAqIFNldHMgdGhlIHZhbHVlIG9mIGEgcHJvcGVydHkuXG4gICAqXG4gICAqIEB0eXBlUGFyYW0gUHJvcGVydHlOYW1lIC0gVGhlIG5hbWUgb2YgdGhlIHByb3BlcnR5LlxuICAgKiBAcGFyYW0gcHJvcGVydHlOYW1lIC0gVGhlIG5hbWUgb2YgdGhlIHByb3BlcnR5LlxuICAgKiBAcGFyYW0gdmFsdWUgLSBUaGUgdmFsdWUgdG8gc2V0LlxuICAgKiBAcmV0dXJucyBBIHtAbGluayBQcm9taXNlfSB0aGF0IHJlc29sdmVzIHRvIHRoZSB2YWxpZGF0aW9uIG1lc3NhZ2UuXG4gICAqL1xuICBwdWJsaWMgYXN5bmMgc2V0UHJvcGVydHk8UHJvcGVydHlOYW1lIGV4dGVuZHMgUHJvcGVydHlOYW1lczxQbHVnaW5TZXR0aW5ncz4+KFxuICAgIHByb3BlcnR5TmFtZTogUHJvcGVydHlOYW1lLFxuICAgIHZhbHVlOiBQbHVnaW5TZXR0aW5nc1tQcm9wZXJ0eU5hbWVdXG4gICk6IFByb21pc2U8c3RyaW5nPiB7XG4gICAgdGhpcy5lbnN1cmVMb2FkZWQoKTtcbiAgICBhd2FpdCB0aGlzLmVkaXQoKHNldHRpbmdzKSA9PiB7XG4gICAgICBzZXR0aW5nc1twcm9wZXJ0eU5hbWVdID0gdmFsdWU7XG4gICAgfSk7XG4gICAgcmV0dXJuIHRoaXMuY3VycmVudFN0YXRlLnZhbGlkYXRpb25NZXNzYWdlc1twcm9wZXJ0eU5hbWVdO1xuICB9XG5cbiAgLyoqXG4gICAqIFZhbGlkYXRlcyB0aGUgc2V0dGluZ3MuXG4gICAqXG4gICAqIEBwYXJhbSBzZXR0aW5ncyAtIFRoZSBzZXR0aW5ncy5cbiAgICogQHJldHVybnMgQSB7QGxpbmsgUHJvbWlzZX0gdGhhdCByZXNvbHZlcyB0byB0aGUgdmFsaWRhdGlvbiByZXN1bHQuXG4gICAqL1xuICBwdWJsaWMgYXN5bmMgdmFsaWRhdGUoc2V0dGluZ3M6IFBsdWdpblNldHRpbmdzKTogUHJvbWlzZTxWYWxpZGF0aW9uUmVzdWx0PFBsdWdpblNldHRpbmdzPj4ge1xuICAgIGNvbnN0IHJlc3VsdDogVmFsaWRhdGlvblJlc3VsdDxQbHVnaW5TZXR0aW5ncz4gPSB7fTtcbiAgICBmb3IgKGNvbnN0IFtwcm9wZXJ0eU5hbWUsIHZhbGlkYXRvcl0gb2YgdGhpcy52YWxpZGF0b3JzKSB7XG4gICAgICBjb25zdCB2YWxpZGF0aW9uTWVzc2FnZSA9IGF3YWl0IHZhbGlkYXRvcihzZXR0aW5nc1twcm9wZXJ0eU5hbWVdLCBzZXR0aW5ncyk7XG4gICAgICBpZiAodmFsaWRhdGlvbk1lc3NhZ2UpIHtcbiAgICAgICAgcmVzdWx0W3Byb3BlcnR5TmFtZV0gPSB2YWxpZGF0aW9uTWVzc2FnZTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICByZXR1cm4gcmVzdWx0O1xuICB9XG5cbiAgLyoqXG4gICAqIFdhaXRzIHVudGlsIHRoZSBzZXR0aW5ncyBoYXZlIGJlZW4gcmVhZCBmcm9tIGBkYXRhLmpzb25gIGF0IGxlYXN0IG9uY2UuXG4gICAqXG4gICAqIEFueXRoaW5nIHRoYXQgcmVhZHMgYSBzZXR0aW5nIGZyb20gb3V0c2lkZSB0aGlzIGNvbXBvbmVudCBoYXMgdG8gd2FpdCBmb3IgdGhpcywgYmVjYXVzZSB1bnRpbCB0aGUgZmlyc3RcbiAgICoge0BsaW5rIGxvYWRGcm9tRmlsZX0gY29tcGxldGVzIHtAbGluayBzZXR0aW5nc30gc3RpbGwgaG9sZHMgdGhlIERFRkFVTFRTIOKAlCByZWFkaW5nIGl0IGVhcmxpZXIgYW5zd2Vyc1xuICAgKiB3aXRoIGEgZGVmYXVsdCByYXRoZXIgdGhhbiB3aXRoIHdoYXQgdGhlIHVzZXIgYWN0dWFsbHkgc3RvcmVkLiBUaGF0IHdpbmRvdyBpcyBlYXN5IHRvIG1pc3MsIHNpbmNlIGl0IGlzXG4gICAqIGVtcHR5IG9uIGEgY29sZCBzdGFydCAodGhlIHdvcmtzcGFjZSBsYXlvdXQgaXMgbm90IHJlYWR5IHlldCwgc28gbm90aGluZyBoYXMgcnVuKSBidXQgd2lkZSBvcGVuIG9uIGFcbiAgICogcnVudGltZSBlbmFibGUgZnJvbSB0aGUgQ29tbXVuaXR5IFBsdWdpbnMgdGFiIG9yIGEgcmUtZW5hYmxlIGFmdGVyIGFuIHVwZGF0ZSwgd2hlcmUgYSBsYXlvdXQtcmVhZHlcbiAgICogaGFuZGxlciBmaXJlcyBpbW1lZGlhdGVseSB3aGlsZSB0aGlzIGNvbXBvbmVudCdzIG93biBhc3luYyBsb2FkIGlzIHN0aWxsIGluIGZsaWdodC5cbiAgICpcbiAgICogUmVzb2x2ZXMgaW1tZWRpYXRlbHkgb25jZSB0aGUgc2V0dGluZ3MgaGF2ZSBsb2FkZWQsIHNvIGEgY2FsbGVyIHRoYXQgYXJyaXZlcyBsYXRlIGlzIG5vdCBzdHJhbmRlZFxuICAgKiB3YWl0aW5nIGZvciBhbiBldmVudCB0aGF0IGhhcyBhbHJlYWR5IGJlZW4gcmFpc2VkLiBMYXRlciByZWxvYWRzIChhbiBleHRlcm5hbCBgZGF0YS5qc29uYCBjaGFuZ2UpIGRvXG4gICAqIG5vdCByZXNldCBpdCDigJQgdGhlIHF1ZXN0aW9uIGl0IGFuc3dlcnMgaXMgd2hldGhlciB0aGUgc2V0dGluZ3MgaGF2ZSBFVkVSIGJlZW4gcmVhZCwgbm90IHdoZXRoZXIgdGhlXG4gICAqIG1vc3QgcmVjZW50IHJlYWQgaGFzIGZpbmlzaGVkLlxuICAgKlxuICAgKiBAcmV0dXJucyBBIHtAbGluayBQcm9taXNlfSB0aGF0IHJlc29sdmVzIG9uY2UgdGhlIHNldHRpbmdzIGhhdmUgYmVlbiBsb2FkZWQgZnJvbSB0aGUgZmlsZS5cbiAgICovXG4gIHB1YmxpYyB3aGVuTG9hZGVkRnJvbUZpbGUoKTogUHJvbWlzZTx2b2lkPiB7XG4gICAgcmV0dXJuIHRoaXMuaXNMb2FkZWRGcm9tRmlsZVxuICAgICAgPyBub29wQXN5bmMoKVxuICAgICAgOiBuZXcgUHJvbWlzZTx2b2lkPigocmVzb2x2ZSkgPT4ge1xuICAgICAgICB0aGlzLmxvYWRlZEZyb21GaWxlUmVzb2x2ZXJzLnB1c2gocmVzb2x2ZSk7XG4gICAgICB9KTtcbiAgfVxuXG4gIC8qKlxuICAgKiBHZXRzIHRoZSB0cmFuc2Zvcm1lci5cbiAgICpcbiAgICogQHJldHVybnMgVGhlIHRyYW5zZm9ybWVyLlxuICAgKi9cbiAgcHJvdGVjdGVkIGdldFRyYW5zZm9ybWVyKCk6IFRyYW5zZm9ybWVyIHtcbiAgICByZXR1cm4gZGVmYXVsdFRyYW5zZm9ybWVyO1xuICB9XG5cbiAgLyoqXG4gICAqIENhbGxlZCB3aGVuIHRoZSBwbHVnaW4gc2V0dGluZ3MgcmVjb3JkIGlzIGxvYWRlZCBmcm9tIGRpc2suXG4gICAqXG4gICAqIEBwYXJhbSByZWNvcmQgLSBUaGUgcmVjb3JkLlxuICAgKi9cbiAgcHJvdGVjdGVkIGFzeW5jIG9uTG9hZFJlY29yZChyZWNvcmQ6IEdlbmVyaWNPYmplY3QpOiBQcm9taXNlPHZvaWQ+IHtcbiAgICBmb3IgKGNvbnN0IGNvbnZlcnRlciBvZiB0aGlzLmxlZ2FjeVNldHRpbmdzQ29udmVydGVycykge1xuICAgICAgY29udmVydGVyKHJlY29yZCk7XG4gICAgfVxuICAgIGF3YWl0IG5vb3BBc3luYygpO1xuICB9XG5cbiAgLyoqXG4gICAqIENhbGxlZCB3aGVuIHNldHRpbmdzIGFyZSBsb2FkZWQgb3IgcmVsb2FkZWQuXG4gICAqXG4gICAqIEBwYXJhbSBfbG9hZGVkU3RhdGUgLSBUaGUgbG9hZGVkIHNldHRpbmdzIHN0YXRlLlxuICAgKiBAcGFyYW0gX2lzSW5pdGlhbExvYWQgLSBXaGV0aGVyIHRoaXMgaXMgdGhlIGluaXRpYWwgbG9hZC5cbiAgICovXG4gIHByb3RlY3RlZCBhc3luYyBvbkxvYWRTZXR0aW5ncyhcbiAgICBfbG9hZGVkU3RhdGU6IFJlYWRvbmx5UGx1Z2luU2V0dGluZ3NTdGF0ZTxQbHVnaW5TZXR0aW5ncz4sXG4gICAgX2lzSW5pdGlhbExvYWQ6IGJvb2xlYW5cbiAgKTogUHJvbWlzZTx2b2lkPiB7XG4gICAgYXdhaXQgbm9vcEFzeW5jKCk7XG4gIH1cblxuICAvKipcbiAgICogQ2FsbGVkIHdoZW4gc2V0dGluZ3MgYXJlIHNhdmVkLlxuICAgKlxuICAgKiBAcGFyYW0gcGFyYW1zIC0gVGhlIHBhcmFtZXRlcnMuXG4gICAqL1xuICBwcm90ZWN0ZWQgYXN5bmMgb25TYXZlU2V0dGluZ3MocGFyYW1zOiBQbHVnaW5TZXR0aW5nc0NvbXBvbmVudEJhc2VPblNhdmVTZXR0aW5nc1BhcmFtczxQbHVnaW5TZXR0aW5ncz4pOiBQcm9taXNlPHZvaWQ+IHtcbiAgICBjb25zdCB7XG4gICAgICBjb250ZXh0OiBfY29udGV4dCxcbiAgICAgIG5ld1N0YXRlOiBfbmV3U3RhdGUsXG4gICAgICBvbGRTdGF0ZTogX29sZFN0YXRlXG4gICAgfSA9IHBhcmFtcztcbiAgICBhd2FpdCBub29wQXN5bmMoKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBDYWxsZWQgd2hlbiB0aGUgcGx1Z2luIHNldHRpbmdzIHJlY29yZCBpcyBhYm91dCB0byBiZSBzYXZlZCB0byBkaXNrLlxuICAgKlxuICAgKiBAcGFyYW0gX3JlY29yZCAtIFRoZSByZWNvcmQuXG4gICAqL1xuICBwcm90ZWN0ZWQgYXN5bmMgb25TYXZpbmdSZWNvcmQoX3JlY29yZDogR2VuZXJpY09iamVjdCk6IFByb21pc2U8dm9pZD4ge1xuICAgIGF3YWl0IG5vb3BBc3luYygpO1xuICB9XG5cbiAgLyoqXG4gICAqIFJlZ2lzdGVycyB0aGUgbGVnYWN5IHNldHRpbmdzIGNvbnZlcnRlcnMuXG4gICAqIE92ZXJyaWRlIHRvIHJlZ2lzdGVyIGxlZ2FjeSBzZXR0aW5ncyBjb252ZXJ0ZXJzLlxuICAgKi9cbiAgcHJvdGVjdGVkIHJlZ2lzdGVyTGVnYWN5U2V0dGluZ3NDb252ZXJ0ZXJzKCk6IHZvaWQge1xuICAgIG5vb3AoKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBSZWdpc3RlcnMgdGhlIHZhbGlkYXRvcnMuXG4gICAqIE92ZXJyaWRlIHRvIHJlZ2lzdGVyIHZhbGlkYXRvcnMgZm9yIHByb3BlcnRpZXMuXG4gICAqL1xuICBwcm90ZWN0ZWQgcmVnaXN0ZXJWYWxpZGF0b3JzKCk6IHZvaWQge1xuICAgIG5vb3AoKTtcbiAgfVxuXG4gIHByaXZhdGUgYXN5bmMgY2xvbmVTZXR0aW5ncyhzZXR0aW5nczogUGx1Z2luU2V0dGluZ3MpOiBQcm9taXNlPFBsdWdpblNldHRpbmdzPiB7XG4gICAgY29uc3QgcmVjb3JkID0gYXdhaXQgdGhpcy5zZXR0aW5nc1RvUmF3UmVjb3JkKHNldHRpbmdzKTtcbiAgICBjb25zdCBqc29uID0gSlNPTi5zdHJpbmdpZnkocmVjb3JkKTtcbiAgICBjb25zdCBjbG9uZVJlY29yZCA9IEpTT04ucGFyc2UoanNvbikgYXMgR2VuZXJpY09iamVjdDtcbiAgICByZXR1cm4gYXdhaXQgdGhpcy5yYXdSZWNvcmRUb1NldHRpbmdzKGNsb25lUmVjb3JkKTtcbiAgfVxuXG4gIHByaXZhdGUgYXN5bmMgY2xvbmVTdGF0ZShcbiAgICBzdGF0ZTogUGx1Z2luU2V0dGluZ3NTdGF0ZTxQbHVnaW5TZXR0aW5ncz5cbiAgKTogUHJvbWlzZTxQbHVnaW5TZXR0aW5nc1N0YXRlPFBsdWdpblNldHRpbmdzPj4ge1xuICAgIHJldHVybiB7XG4gICAgICBlZmZlY3RpdmVWYWx1ZXM6IGF3YWl0IHRoaXMuY2xvbmVTZXR0aW5ncyhzdGF0ZS5lZmZlY3RpdmVWYWx1ZXMpLFxuICAgICAgaW5wdXRWYWx1ZXM6IGF3YWl0IHRoaXMuY2xvbmVTZXR0aW5ncyhzdGF0ZS5pbnB1dFZhbHVlcyksXG4gICAgICB2YWxpZGF0aW9uTWVzc2FnZXM6IHsgLi4uc3RhdGUudmFsaWRhdGlvbk1lc3NhZ2VzIH1cbiAgICB9O1xuICB9XG5cbiAgcHJpdmF0ZSBjcmVhdGVEZWZhdWx0U3RhdGUoKTogUGx1Z2luU2V0dGluZ3NTdGF0ZTxQbHVnaW5TZXR0aW5ncz4ge1xuICAgIHJldHVybiB7XG4gICAgICBlZmZlY3RpdmVWYWx1ZXM6IG5ldyB0aGlzLnBsdWdpblNldHRpbmdzQ2xhc3MoKSxcbiAgICAgIGlucHV0VmFsdWVzOiBuZXcgdGhpcy5wbHVnaW5TZXR0aW5nc0NsYXNzKCksXG4gICAgICB2YWxpZGF0aW9uTWVzc2FnZXM6IGNhc3RUbzxSZWNvcmQ8UHJvcGVydHlOYW1lczxQbHVnaW5TZXR0aW5ncz4sIHN0cmluZz4+KHt9KVxuICAgIH07XG4gIH1cblxuICBwcml2YXRlIGFzeW5jIGVkaXQoc2V0dGluZ3NFZGl0b3I6IChzZXR0aW5nczogUGx1Z2luU2V0dGluZ3MpID0+IFByb21pc2FibGU8dm9pZD4pOiBQcm9taXNlPHZvaWQ+IHtcbiAgICB0cnkge1xuICAgICAgYXdhaXQgc2V0dGluZ3NFZGl0b3IodGhpcy5jdXJyZW50U3RhdGUuaW5wdXRWYWx1ZXMpO1xuICAgIH0gZmluYWxseSB7XG4gICAgICBjb25zdCB2YWxpZGF0aW9uUmVzdWx0ID0gYXdhaXQgdGhpcy52YWxpZGF0ZSh0aGlzLmN1cnJlbnRTdGF0ZS5pbnB1dFZhbHVlcyk7XG4gICAgICBmb3IgKGNvbnN0IHByb3BlcnR5TmFtZSBvZiB0aGlzLnByb3BlcnR5TmFtZXMpIHtcbiAgICAgICAgY29uc3QgdmFsaWRhdGlvbk1lc3NhZ2UgPSB2YWxpZGF0aW9uUmVzdWx0W3Byb3BlcnR5TmFtZV0gPz8gJyc7XG4gICAgICAgIHRoaXMuY3VycmVudFN0YXRlLnZhbGlkYXRpb25NZXNzYWdlc1twcm9wZXJ0eU5hbWVdID0gdmFsaWRhdGlvbk1lc3NhZ2U7XG4gICAgICAgIGNvbnN0IGRlZmF1bHRzID0gdGhpcy5kZWZhdWx0U2V0dGluZ3MgYXMgUGx1Z2luU2V0dGluZ3M7XG4gICAgICAgIHRoaXMuY3VycmVudFN0YXRlLmVmZmVjdGl2ZVZhbHVlc1twcm9wZXJ0eU5hbWVdID0gdmFsaWRhdGlvbk1lc3NhZ2VcbiAgICAgICAgICA/IGRlZmF1bHRzW3Byb3BlcnR5TmFtZV1cbiAgICAgICAgICA6IHRoaXMuY3VycmVudFN0YXRlLmlucHV0VmFsdWVzW3Byb3BlcnR5TmFtZV07XG4gICAgICB9XG4gICAgfVxuICB9XG5cbiAgcHJpdmF0ZSBpc1ZhbGlkUHJvcGVydHlOYW1lKHByb3BlcnR5OiB1bmtub3duKTogcHJvcGVydHkgaXMgUHJvcGVydHlOYW1lczxQbHVnaW5TZXR0aW5ncz4ge1xuICAgIHJldHVybiB0eXBlb2YgcHJvcGVydHkgPT09ICdzdHJpbmcnICYmICh0aGlzLnByb3BlcnR5TmFtZXMgYXMgc3RyaW5nW10pLmluY2x1ZGVzKHByb3BlcnR5KTtcbiAgfVxuXG4gIHByaXZhdGUgbWFya0xvYWRlZEZyb21GaWxlKCk6IHZvaWQge1xuICAgIHRoaXMuaXNMb2FkZWRGcm9tRmlsZSA9IHRydWU7XG4gICAgLy8gRHJhaW5lZCByYXRoZXIgdGhhbiBpdGVyYXRlZCwgc28gdGhlIGxpc3QgZG9lcyBub3Qga2VlcCBldmVyeSBwYXN0IHdhaXRlciBhbGl2ZSBhY3Jvc3MgcmVsb2Fkcy5cbiAgICBjb25zdCByZXNvbHZlcnMgPSB0aGlzLmxvYWRlZEZyb21GaWxlUmVzb2x2ZXJzLnNwbGljZSgwKTtcbiAgICBmb3IgKGNvbnN0IHJlc29sdmUgb2YgcmVzb2x2ZXJzKSB7XG4gICAgICByZXNvbHZlKCk7XG4gICAgfVxuICB9XG5cbiAgcHJpdmF0ZSBhc3luYyByYXdSZWNvcmRUb1NldHRpbmdzKHJhd1JlY29yZDogR2VuZXJpY09iamVjdCk6IFByb21pc2U8UGx1Z2luU2V0dGluZ3M+IHtcbiAgICByYXdSZWNvcmQgPSB0aGlzLmdldFRyYW5zZm9ybWVyKCkudHJhbnNmb3JtT2JqZWN0UmVjdXJzaXZlbHkocmF3UmVjb3JkKTtcbiAgICBhd2FpdCB0aGlzLm9uTG9hZFJlY29yZChyYXdSZWNvcmQpO1xuXG4gICAgY29uc3Qgc2V0dGluZ3MgPSBuZXcgdGhpcy5wbHVnaW5TZXR0aW5nc0NsYXNzKCk7XG4gICAgY29uc3QgZGVmYXVsdHMgPSB0aGlzLmRlZmF1bHRTZXR0aW5ncyBhcyBQbHVnaW5TZXR0aW5ncztcblxuICAgIGZvciAoY29uc3QgW3Byb3BlcnR5TmFtZSwgdmFsdWVdIG9mIE9iamVjdC5lbnRyaWVzKHJhd1JlY29yZCkpIHtcbiAgICAgIGlmICghdGhpcy5pc1ZhbGlkUHJvcGVydHlOYW1lKHByb3BlcnR5TmFtZSkpIHtcbiAgICAgICAgZ2V0T2JzaWRpYW5MaWJEZWJ1Z2dlcignUGx1Z2luU2V0dGluZ3NDb21wb25lbnRCYXNlOnJhd1JlY29yZFRvU2V0dGluZ3MnKShgVW5rbm93biBwcm9wZXJ0eTogJHtwcm9wZXJ0eU5hbWV9YCk7XG4gICAgICAgIGNvbnRpbnVlO1xuICAgICAgfVxuXG4gICAgICAvLyBKU09OIGNhbm5vdCBob2xkIGB1bmRlZmluZWRgLCBzbyBvbmx5IGEgbGVnYWN5IGNvbnZlcnRlciBwcm9kdWNlcyBpdC4gS2VlcCB0aGUgZGVmYXVsdCByYXRoZXIgdGhhblxuICAgICAgLy8gbGV0dGluZyBhIGNvbnZlcnRlciB0aGF0IGFzc2lnbmVkIGEga2V5IGl0IGhhZCBub3RoaW5nIGZvciB3aXBlIGl0IG91dC5cbiAgICAgIGlmICh2YWx1ZSA9PT0gdW5kZWZpbmVkKSB7XG4gICAgICAgIGNvbnRpbnVlO1xuICAgICAgfVxuXG4gICAgICBpZiAodHlwZW9mIHZhbHVlICE9PSB0eXBlb2YgZGVmYXVsdHNbcHJvcGVydHlOYW1lXSkge1xuICAgICAgICBnZXRPYnNpZGlhbkxpYkRlYnVnZ2VyKCdQbHVnaW5TZXR0aW5nc0NvbXBvbmVudEJhc2U6cmF3UmVjb3JkVG9TZXR0aW5ncycpKFxuICAgICAgICAgICdQb3NzaWJsZSBpbnZhbGlkIHZhbHVlIHR5cGUuIEl0IG1pZ2h0IGxlYWQgdG8gYW4gdW5leHBlY3RlZCBiZWhhdmlvciBvZiB0aGUgcGx1Z2luLiBUaGVyZSBpcyBhbHNvIGEgY2hhbmNlIGl0IGlzIGEgZmFsc2UtbmVnYXRpdmUgd2FybmluZywgYXMgd2UgYXJlIHVuYWJsZSB0byBkZXRlcm1pbmUgdGhlIGV4YWN0IHR5cGUgb2YgdGhlIHZhbHVlIGluIHJ1bnRpbWUuJyxcbiAgICAgICAgICB7XG4gICAgICAgICAgICBkZWZhdWx0VmFsdWU6IGRlZmF1bHRzW3Byb3BlcnR5TmFtZV0sXG4gICAgICAgICAgICBwcm9wZXJ0eU5hbWUsXG4gICAgICAgICAgICB2YWx1ZVxuICAgICAgICAgIH1cbiAgICAgICAgKTtcbiAgICAgIH1cblxuICAgICAgc2V0dGluZ3NbcHJvcGVydHlOYW1lXSA9IHZhbHVlIGFzIFByb3BlcnR5VmFsdWVzPFBsdWdpblNldHRpbmdzPjtcbiAgICB9XG5cbiAgICByZXR1cm4gc2V0dGluZ3M7XG4gIH1cblxuICBwcml2YXRlIGFzeW5jIHNhdmVUb0ZpbGVJbXBsKCk6IFByb21pc2U8dm9pZD4ge1xuICAgIGF3YWl0IHRoaXMuZGF0YUhhbmRsZXIuc2F2ZURhdGEoYXdhaXQgdGhpcy5zZXR0aW5nc1RvUmF3UmVjb3JkKHRoaXMuY3VycmVudFN0YXRlLmlucHV0VmFsdWVzKSk7XG4gIH1cblxuICBwcml2YXRlIHNldFByb3BlcnR5SW1wbChwYXJhbXM6IFBsdWdpblNldHRpbmdzQ29tcG9uZW50QmFzZVNldFByb3BlcnR5SW1wbFBhcmFtczxQbHVnaW5TZXR0aW5ncz4pOiB2b2lkIHtcbiAgICBjb25zdCB7XG4gICAgICBwcm9wZXJ0eU5hbWUsXG4gICAgICB2YWxpZGF0aW9uTWVzc2FnZSxcbiAgICAgIHZhbHVlXG4gICAgfSA9IHBhcmFtcztcbiAgICBjb25zdCBkZWZhdWx0cyA9IHRoaXMuZGVmYXVsdFNldHRpbmdzIGFzIFBsdWdpblNldHRpbmdzO1xuICAgIHRoaXMuY3VycmVudFN0YXRlLmlucHV0VmFsdWVzW3Byb3BlcnR5TmFtZV0gPSB2YWx1ZTtcbiAgICB0aGlzLmN1cnJlbnRTdGF0ZS52YWxpZGF0aW9uTWVzc2FnZXNbcHJvcGVydHlOYW1lXSA9IHZhbGlkYXRpb25NZXNzYWdlID8/ICcnO1xuICAgIHRoaXMuY3VycmVudFN0YXRlLmVmZmVjdGl2ZVZhbHVlc1twcm9wZXJ0eU5hbWVdID0gdmFsaWRhdGlvbk1lc3NhZ2UgPyBkZWZhdWx0c1twcm9wZXJ0eU5hbWVdIDogdmFsdWU7XG4gIH1cblxuICBwcml2YXRlIGFzeW5jIHNldHRpbmdzVG9SYXdSZWNvcmQoc2V0dGluZ3M6IFBsdWdpblNldHRpbmdzKTogUHJvbWlzZTxHZW5lcmljT2JqZWN0PiB7XG4gICAgY29uc3QgcmF3UmVjb3JkOiBHZW5lcmljT2JqZWN0ID0ge307XG5cbiAgICBmb3IgKGNvbnN0IHByb3BlcnR5TmFtZSBvZiB0aGlzLnByb3BlcnR5TmFtZXMpIHtcbiAgICAgIHJhd1JlY29yZFtwcm9wZXJ0eU5hbWVdID0gc2V0dGluZ3NbcHJvcGVydHlOYW1lXTtcbiAgICB9XG5cbiAgICBhd2FpdCB0aGlzLm9uU2F2aW5nUmVjb3JkKHJhd1JlY29yZCk7XG5cbiAgICByZXR1cm4gdGhpcy5nZXRUcmFuc2Zvcm1lcigpLnRyYW5zZm9ybU9iamVjdFJlY3Vyc2l2ZWx5KHJhd1JlY29yZCk7XG4gIH1cbn1cbiJdLCJtYXBwaW5ncyI6Ijs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7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
647
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi4uLy4uLy4uLy4uL3NyYy9jb21wb25lbnRzL3BsdWdpbi1zZXR0aW5ncy1jb21wb25lbnQudHMiXSwic291cmNlc0NvbnRlbnQiOlsiLyoqXG4gKiBAZmlsZVxuICpcbiAqIENvbXBvbmVudCB0aGF0IG1hbmFnZXMgcGx1Z2luIHNldHRpbmdzOiBkYXRhLCBwZXJzaXN0ZW5jZSwgdmFsaWRhdGlvbiwgYW5kIGV2ZW50cy5cbiAqXG4gKiBUaGlzIGlzIHRoZSBzaW5nbGUgcHVibGljLWZhY2luZyBzZXR0aW5ncyBBUEkgZm9yIHBsdWdpbiBhdXRob3JzLlxuICogQWxsIHNldHRpbmdzIGxvZ2ljIChsb2FkLCBzYXZlLCB2YWxpZGF0ZSwgdHJhbnNmb3JtLCBjbG9uZSkgaXMgaGFuZGxlZCBkaXJlY3RseVxuICogYnkgdGhpcyBjb21wb25lbnQg4oCUIG5vIHNlcGFyYXRlIG1hbmFnZXIgY2xhc3MgaXMgbmVlZGVkLlxuICovXG5cbmltcG9ydCB0eXBlIHtcbiAgQXN5bmNFdmVudFJlZixcbiAgQXN5bmNFdmVudFNvdXJjZSxcbiAgQ2FsbGJhY2tBcmd1bWVudHNcbn0gZnJvbSAnQG1uYW91bW92L3R5cGVzY3JpcHQtbGliL2FzeW5jLWV2ZW50cyc7XG5pbXBvcnQgdHlwZSB7IFRyYW5zZm9ybWVyIH0gZnJvbSAnQG1uYW91bW92L3R5cGVzY3JpcHQtbGliL3RyYW5zZm9ybWVycy90cmFuc2Zvcm1lcic7XG5pbXBvcnQgdHlwZSB7XG4gIE1heWJlUmV0dXJuLFxuICBTdHJpbmdLZXlzXG59IGZyb20gJ0BtbmFvdW1vdi90eXBlc2NyaXB0LWxpYi90eXBlJztcbmltcG9ydCB0eXBlIHsgR2VuZXJpY09iamVjdCB9IGZyb20gJ0BtbmFvdW1vdi90eXBlc2NyaXB0LWxpYi90eXBlLWd1YXJkcyc7XG5pbXBvcnQgdHlwZSB7XG4gIENvbnN0cnVjdG9yLFxuICBQcm9taXNhYmxlLFxuICBSZWFkb25seURlZXBcbn0gZnJvbSAndHlwZS1mZXN0JztcblxuaW1wb3J0IHsgQXN5bmNFdmVudHMgfSBmcm9tICdAbW5hb3Vtb3YvdHlwZXNjcmlwdC1saWIvYXN5bmMtZXZlbnRzJztcbmltcG9ydCB7XG4gIG5vb3AsXG4gIG5vb3BBc3luY1xufSBmcm9tICdAbW5hb3Vtb3YvdHlwZXNjcmlwdC1saWIvZnVuY3Rpb24nO1xuaW1wb3J0IHtcbiAgY2FzdFRvLFxuICBnZXRBbGxLZXlzLFxuICBpc0RlZXBFcXVhbFxufSBmcm9tICdAbW5hb3Vtb3YvdHlwZXNjcmlwdC1saWIvb2JqZWN0LXV0aWxzJztcbmltcG9ydCB7IERhdGVUcmFuc2Zvcm1lciB9IGZyb20gJ0BtbmFvdW1vdi90eXBlc2NyaXB0LWxpYi90cmFuc2Zvcm1lcnMvZGF0ZS10cmFuc2Zvcm1lcic7XG5pbXBvcnQgeyBHcm91cFRyYW5zZm9ybWVyIH0gZnJvbSAnQG1uYW91bW92L3R5cGVzY3JpcHQtbGliL3RyYW5zZm9ybWVycy9ncm91cC10cmFuc2Zvcm1lcic7XG5pbXBvcnQgeyBNYXBUcmFuc2Zvcm1lciB9IGZyb20gJ0BtbmFvdW1vdi90eXBlc2NyaXB0LWxpYi90cmFuc2Zvcm1lcnMvbWFwLXRyYW5zZm9ybWVyJztcbmltcG9ydCB7IFNldFRyYW5zZm9ybWVyIH0gZnJvbSAnQG1uYW91bW92L3R5cGVzY3JpcHQtbGliL3RyYW5zZm9ybWVycy9zZXQtdHJhbnNmb3JtZXInO1xuaW1wb3J0IHsgU2tpcFByaXZhdGVQcm9wZXJ0eVRyYW5zZm9ybWVyIH0gZnJvbSAnQG1uYW91bW92L3R5cGVzY3JpcHQtbGliL3RyYW5zZm9ybWVycy9za2lwLXByaXZhdGUtcHJvcGVydHktdHJhbnNmb3JtZXInO1xuaW1wb3J0IHsgVHdvV2F5TWFwVHJhbnNmb3JtZXIgfSBmcm9tICdAbW5hb3Vtb3YvdHlwZXNjcmlwdC1saWIvdHJhbnNmb3JtZXJzL3R3by13YXktbWFwLXRyYW5zZm9ybWVyJztcbmltcG9ydCB7IFZhbHVlV3JhcHBlciB9IGZyb20gJ0BtbmFvdW1vdi90eXBlc2NyaXB0LWxpYi92YWx1ZS13cmFwcGVyJztcblxuaW1wb3J0IHR5cGUgeyBEYXRhSGFuZGxlciB9IGZyb20gJy4uL2RhdGEtaGFuZGxlci50cyc7XG5pbXBvcnQgdHlwZSB7IFBsdWdpbkV2ZW50U291cmNlIH0gZnJvbSAnLi4vcGx1Z2luL3BsdWdpbi1ldmVudC1zb3VyY2UudHMnO1xuaW1wb3J0IHR5cGUgeyBTZXR0aW5nc1JlY292ZXJ5Q29weSB9IGZyb20gJy4uL3NldHRpbmdzLXJlY292ZXJ5LnRzJztcblxuaW1wb3J0IHsgUGx1Z2luRGF0YVBhcnNlRXJyb3IgfSBmcm9tICcuLi9kYXRhLWhhbmRsZXIudHMnO1xuaW1wb3J0IHsgZ2V0T2JzaWRpYW5MaWJEZWJ1Z2dlciB9IGZyb20gJy4uL2RlYnVnLnRzJztcbmltcG9ydCB7IFNldHRpbmdzUmVjb3ZlcnlSZWFzb24gfSBmcm9tICcuLi9zZXR0aW5ncy1yZWNvdmVyeS50cyc7XG5pbXBvcnQgeyBEdXJhdGlvblRyYW5zZm9ybWVyIH0gZnJvbSAnLi4vdHJhbnNmb3JtZXJzL2R1cmF0aW9uLXRyYW5zZm9ybWVyLnRzJztcbmltcG9ydCB7IHJlZ2lzdGVyQXN5bmNFdmVudCB9IGZyb20gJy4vYXN5bmMtZXZlbnRzLWNvbXBvbmVudC50cyc7XG5pbXBvcnQgeyBDb21wb25lbnRFeCB9IGZyb20gJy4vY29tcG9uZW50LWV4LnRzJztcblxuLyoqXG4gKiBUaGUgaW5kZW50YXRpb24gT2JzaWRpYW4ncyBgVmF1bHQud3JpdGVKc29uYCB1c2VzIGZvciBgZGF0YS5qc29uYCwgc28gYSByZWNvdmVyeSBjb3B5IHJlYWRzIGxpa2UgdGhlIGZpbGUgZGlkLlxuICovXG5jb25zdCBKU09OX0lOREVOVCA9IDI7XG5cbmNvbnN0IGRlZmF1bHRUcmFuc2Zvcm1lciA9IG5ldyBHcm91cFRyYW5zZm9ybWVyKFtcbiAgbmV3IFNraXBQcml2YXRlUHJvcGVydHlUcmFuc2Zvcm1lcigpLFxuICBuZXcgRGF0ZVRyYW5zZm9ybWVyKCksXG4gIG5ldyBEdXJhdGlvblRyYW5zZm9ybWVyKCksXG4gIG5ldyBNYXBUcmFuc2Zvcm1lcigpLFxuICBuZXcgU2V0VHJhbnNmb3JtZXIoKSxcbiAgbmV3IFR3b1dheU1hcFRyYW5zZm9ybWVyKClcbl0pO1xuXG4vKipcbiAqIENvbnN0cnVjdG9yIHBhcmFtZXRlcnMgZm9yIHtAbGluayBQbHVnaW5TZXR0aW5nc0NvbXBvbmVudEJhc2V9LlxuICpcbiAqIEB0eXBlUGFyYW0gUGx1Z2luU2V0dGluZ3MgLSBUaGUgdHlwZSBvZiB0aGUgcGx1Z2luIHNldHRpbmdzLlxuICovXG5leHBvcnQgaW50ZXJmYWNlIFBsdWdpblNldHRpbmdzQ29tcG9uZW50QmFzZUNvbnN0cnVjdG9yUGFyYW1zPFBsdWdpblNldHRpbmdzPiB7XG4gIC8qKlxuICAgKiBUaGUgZGF0YSBoYW5kbGVyIGZvciB0aGUgcGx1Z2luLlxuICAgKi9cbiAgcmVhZG9ubHkgZGF0YUhhbmRsZXI6IERhdGFIYW5kbGVyO1xuXG4gIC8qKlxuICAgKiBUaGUgcGx1Z2luIGV2ZW50cy5cbiAgICovXG4gIHJlYWRvbmx5IHBsdWdpbkV2ZW50U291cmNlOiBQbHVnaW5FdmVudFNvdXJjZTtcblxuICAvKipcbiAgICogVGhlIHBsdWdpbiBzZXR0aW5ncyBjbGFzcy5cbiAgICovXG4gIHJlYWRvbmx5IHBsdWdpblNldHRpbmdzQ2xhc3M6IENvbnN0cnVjdG9yPFBsdWdpblNldHRpbmdzLCBbXT47XG59XG5cbi8qKlxuICogUGFyYW1ldGVycyBmb3Ige0BsaW5rIFBsdWdpblNldHRpbmdzQ29tcG9uZW50QmFzZS5vblNhdmVTZXR0aW5nc30uXG4gKlxuICogQHR5cGVQYXJhbSBQbHVnaW5TZXR0aW5ncyAtIFRoZSB0eXBlIG9mIHRoZSBwbHVnaW4gc2V0dGluZ3MuXG4gKi9cbmV4cG9ydCBpbnRlcmZhY2UgUGx1Z2luU2V0dGluZ3NDb21wb25lbnRCYXNlT25TYXZlU2V0dGluZ3NQYXJhbXM8UGx1Z2luU2V0dGluZ3MgZXh0ZW5kcyBvYmplY3Q+IHtcbiAgLyoqXG4gICAqIFRoZSBzYXZlIGNvbnRleHQuXG4gICAqL1xuICByZWFkb25seSBjb250ZXh0OiB1bmtub3duO1xuXG4gIC8qKlxuICAgKiBUaGUgbmV3IHNldHRpbmdzIHN0YXRlLlxuICAgKi9cbiAgcmVhZG9ubHkgbmV3U3RhdGU6IFJlYWRvbmx5UGx1Z2luU2V0dGluZ3NTdGF0ZTxQbHVnaW5TZXR0aW5ncz47XG5cbiAgLyoqXG4gICAqIFRoZSBvbGQgc2V0dGluZ3Mgc3RhdGUuXG4gICAqL1xuICByZWFkb25seSBvbGRTdGF0ZTogUmVhZG9ubHlQbHVnaW5TZXR0aW5nc1N0YXRlPFBsdWdpblNldHRpbmdzPjtcbn1cblxuLyoqXG4gKiBBIHNuYXBzaG90IG9mIHBsdWdpbiBzZXR0aW5ncyBzdGF0ZSwgaW5jbHVkaW5nIHJhdyBpbnB1dCB2YWx1ZXMsIGVmZmVjdGl2ZSAodmFsaWRhdGVkKSB2YWx1ZXMsXG4gKiBhbmQgcGVyLXByb3BlcnR5IHZhbGlkYXRpb24gbWVzc2FnZXMuXG4gKlxuICogQHR5cGVQYXJhbSBQbHVnaW5TZXR0aW5ncyAtIFRoZSB0eXBlIG9mIHRoZSBwbHVnaW4gc2V0dGluZ3MuXG4gKi9cbmV4cG9ydCBpbnRlcmZhY2UgUGx1Z2luU2V0dGluZ3NTdGF0ZTxQbHVnaW5TZXR0aW5ncyBleHRlbmRzIG9iamVjdD4ge1xuICAvKipcbiAgICogVGhlIGVmZmVjdGl2ZSBzZXR0aW5ncyB2YWx1ZXMgdXNlZCBieSB0aGUgcGx1Z2luLiBJbnZhbGlkIHByb3BlcnRpZXMgYXJlIHJlcGxhY2VkIHdpdGggZGVmYXVsdHMuXG4gICAqL1xuICByZWFkb25seSBlZmZlY3RpdmVWYWx1ZXM6IFBsdWdpblNldHRpbmdzO1xuXG4gIC8qKlxuICAgKiBUaGUgcmF3IGlucHV0IHZhbHVlcyBhcyBlbnRlcmVkIGJ5IHRoZSB1c2VyLiBNYXkgY29udGFpbiBpbnZhbGlkIHZhbHVlcy5cbiAgICovXG4gIHJlYWRvbmx5IGlucHV0VmFsdWVzOiBQbHVnaW5TZXR0aW5ncztcblxuICAvKipcbiAgICogUGVyLXByb3BlcnR5IHZhbGlkYXRpb24gbWVzc2FnZXMuIEVtcHR5IHN0cmluZyBtZWFucyB2YWxpZC5cbiAgICovXG4gIHJlYWRvbmx5IHZhbGlkYXRpb25NZXNzYWdlczogUmVjb3JkPFN0cmluZ0tleXM8UGx1Z2luU2V0dGluZ3M+LCBzdHJpbmc+O1xufVxuXG4vKipcbiAqIFJlYWRvbmx5IHZlcnNpb24gb2Yge0BsaW5rIFBsdWdpblNldHRpbmdzfS5cbiAqXG4gKiBAdHlwZVBhcmFtIFBsdWdpblNldHRpbmdzIC0gVGhlIHR5cGUgb2YgdGhlIHBsdWdpbiBzZXR0aW5ncy5cbiAqL1xuZXhwb3J0IHR5cGUgUmVhZG9ubHlQbHVnaW5TZXR0aW5nczxQbHVnaW5TZXR0aW5ncyBleHRlbmRzIG9iamVjdD4gPSBSZWFkb25seURlZXA8UGx1Z2luU2V0dGluZ3M+O1xuXG4vKipcbiAqIFJlYWRvbmx5IHZlcnNpb24gb2Yge0BsaW5rIFBsdWdpblNldHRpbmdzU3RhdGV9IGZvciB1c2UgaW4gZXZlbnQgY2FsbGJhY2tzIGFuZCBwdWJsaWMgZ2V0dGVycy5cbiAqXG4gKiBAdHlwZVBhcmFtIFBsdWdpblNldHRpbmdzIC0gVGhlIHR5cGUgb2YgdGhlIHBsdWdpbiBzZXR0aW5ncy5cbiAqL1xuZXhwb3J0IHR5cGUgUmVhZG9ubHlQbHVnaW5TZXR0aW5nc1N0YXRlPFBsdWdpblNldHRpbmdzIGV4dGVuZHMgb2JqZWN0PiA9IFJlYWRvbmx5RGVlcDxQbHVnaW5TZXR0aW5nc1N0YXRlPFBsdWdpblNldHRpbmdzPj47XG5cbi8qKlxuICogQSB2YWxpZGF0b3IgZnVuY3Rpb24gZm9yIGEgc2V0dGluZ3MgcHJvcGVydHkuXG4gKlxuICogQHR5cGVQYXJhbSBQbHVnaW5TZXR0aW5ncyAtIFRoZSBwbHVnaW4gc2V0dGluZ3MgdHlwZS5cbiAqIEB0eXBlUGFyYW0gUHJvcGVydHlOYW1lIC0gVGhlIHByb3BlcnR5IG5hbWUuXG4gKi9cbmV4cG9ydCB0eXBlIFNldHRpbmdzVmFsaWRhdG9yPFBsdWdpblNldHRpbmdzIGV4dGVuZHMgb2JqZWN0LCBQcm9wZXJ0eU5hbWUgZXh0ZW5kcyBTdHJpbmdLZXlzPFBsdWdpblNldHRpbmdzPiA9IFN0cmluZ0tleXM8UGx1Z2luU2V0dGluZ3M+PiA9IChcbiAgdmFsdWU6IFBsdWdpblNldHRpbmdzW1Byb3BlcnR5TmFtZV0sXG4gIHNldHRpbmdzOiBQbHVnaW5TZXR0aW5nc1xuKSA9PiBQcm9taXNhYmxlPE1heWJlUmV0dXJuPG51bGwgfCBzdHJpbmc+PjtcblxuaW50ZXJmYWNlIFBsdWdpblNldHRpbmdzQ29tcG9uZW50QmFzZUV2ZW50TWFwPFBsdWdpblNldHRpbmdzIGV4dGVuZHMgb2JqZWN0PiB7XG4gIHJlYWRvbmx5IGxvYWRTZXR0aW5nczogW1xuICAgIGxvYWRlZFN0YXRlOiBSZWFkb25seVBsdWdpblNldHRpbmdzU3RhdGU8UGx1Z2luU2V0dGluZ3M+LFxuICAgIGlzSW5pdGlhbExvYWQ6IGJvb2xlYW5cbiAgXTtcbiAgcmVhZG9ubHkgc2F2ZVNldHRpbmdzOiBbXG4gICAgbmV3U3RhdGU6IFJlYWRvbmx5UGx1Z2luU2V0dGluZ3NTdGF0ZTxQbHVnaW5TZXR0aW5ncz4sXG4gICAgb2xkU3RhdGU6IFJlYWRvbmx5UGx1Z2luU2V0dGluZ3NTdGF0ZTxQbHVnaW5TZXR0aW5ncz4sXG4gICAgY29udGV4dDogdW5rbm93blxuICBdO1xufVxuXG4vKipcbiAqIFBhcmFtZXRlcnMgZm9yIHtAbGluayBQbHVnaW5TZXR0aW5nc0NvbXBvbmVudEJhc2Uuc2V0UHJvcGVydHlJbXBsfS5cbiAqXG4gKiBAdHlwZVBhcmFtIFBsdWdpblNldHRpbmdzIC0gVGhlIHR5cGUgb2YgdGhlIHBsdWdpbiBzZXR0aW5ncy5cbiAqL1xuaW50ZXJmYWNlIFBsdWdpblNldHRpbmdzQ29tcG9uZW50QmFzZVNldFByb3BlcnR5SW1wbFBhcmFtczxQbHVnaW5TZXR0aW5ncyBleHRlbmRzIG9iamVjdD4ge1xuICAvKipcbiAgICogVGhlIG5hbWUgb2YgdGhlIHByb3BlcnR5IHRvIHNldC5cbiAgICovXG4gIHJlYWRvbmx5IHByb3BlcnR5TmFtZTogUHJvcGVydHlOYW1lczxQbHVnaW5TZXR0aW5ncz47XG5cbiAgLyoqXG4gICAqIFRoZSB2YWxpZGF0aW9uIG1lc3NhZ2UuIEVtcHR5IG9yIHVuc2V0IG1lYW5zIHZhbGlkLlxuICAgKi9cbiAgcmVhZG9ubHkgdmFsaWRhdGlvbk1lc3NhZ2U/OiBzdHJpbmcgfCB1bmRlZmluZWQ7XG5cbiAgLyoqXG4gICAqIFRoZSB2YWx1ZSB0byBzZXQuXG4gICAqL1xuICByZWFkb25seSB2YWx1ZTogUHJvcGVydHlWYWx1ZXM8UGx1Z2luU2V0dGluZ3M+O1xufVxuXG50eXBlIFByb3BlcnR5TmFtZXM8UGx1Z2luU2V0dGluZ3MgZXh0ZW5kcyBvYmplY3Q+ID0gU3RyaW5nS2V5czxQbHVnaW5TZXR0aW5ncz47XG5cbnR5cGUgUHJvcGVydHlWYWx1ZXM8UGx1Z2luU2V0dGluZ3MgZXh0ZW5kcyBvYmplY3Q+ID0gUGx1Z2luU2V0dGluZ3NbUHJvcGVydHlOYW1lczxQbHVnaW5TZXR0aW5ncz5dO1xuXG50eXBlIFZhbGlkYXRpb25SZXN1bHQ8UGx1Z2luU2V0dGluZ3MgZXh0ZW5kcyBvYmplY3Q+ID0gUGFydGlhbDxSZWNvcmQ8U3RyaW5nS2V5czxQbHVnaW5TZXR0aW5ncz4sIHN0cmluZz4+O1xuXG4vKipcbiAqIEJhc2UgY2xhc3MgZm9yIHBsdWdpbiBzZXR0aW5ncyBjb21wb25lbnRzLlxuICpcbiAqIE1hbmFnZXMgc2V0dGluZ3MgZGF0YSwgcGVyc2lzdGVuY2UsIHZhbGlkYXRpb24sIGFuZCBldmVudHMuXG4gKiBQbHVnaW4gYXV0aG9ycyBleHRlbmQgdGhpcyBjbGFzcyBhbmQgcGFzcyB0aGVpciBzZXR0aW5ncyBjbGFzcyBhc1xuICoge0BsaW5rIFBsdWdpblNldHRpbmdzQ29tcG9uZW50QmFzZUNvbnN0cnVjdG9yUGFyYW1zLnBsdWdpblNldHRpbmdzQ2xhc3N9LCB3aG9zZSBkZWZhdWx0LWNvbnN0cnVjdGVkIGluc3RhbmNlIHN1cHBsaWVzIHRoZSBkZWZhdWx0cy5cbiAqXG4gKiBAdHlwZVBhcmFtIFBsdWdpblNldHRpbmdzIC0gVGhlIHBsdWdpbiBzZXR0aW5ncyB0eXBlLlxuICovXG4vLyBlc2xpbnQtZGlzYWJsZS1uZXh0LWxpbmUgb2JzaWRpYW4tZGV2LXRvb2xraXQvcmVxdWlyZS1jb21wb25lbnQtc3VmZml4IC0tIE5vbi1hYnN0cmFjdCBiYXNlIGNsYXNzOyBjb25zdW1lcnMgZXh0ZW5kIGl0LlxuZXhwb3J0IGNsYXNzIFBsdWdpblNldHRpbmdzQ29tcG9uZW50QmFzZTxQbHVnaW5TZXR0aW5ncyBleHRlbmRzIG9iamVjdD4gZXh0ZW5kcyBDb21wb25lbnRFeCBpbXBsZW1lbnRzIEFzeW5jRXZlbnRTb3VyY2U8UGx1Z2luU2V0dGluZ3NDb21wb25lbnRCYXNlRXZlbnRNYXA8UGx1Z2luU2V0dGluZ3M+PiB7XG4gIC8qKlxuICAgKiBHZXRzIHRoZSByZWFkb25seSBkZWZhdWx0IHNldHRpbmdzLlxuICAgKlxuICAgKiBAcmV0dXJucyBUaGUgZGVmYXVsdCBzZXR0aW5ncyAoYXMgYSByZWFkb25seSBvYmplY3QpLlxuICAgKi9cbiAgcHVibGljIHJlYWRvbmx5IGRlZmF1bHRTZXR0aW5nczogUmVhZG9ubHlEZWVwPFBsdWdpblNldHRpbmdzPjtcblxuICAvKipcbiAgICogR2V0cyB0aGUgcmVhZG9ubHkgZWZmZWN0aXZlIHNldHRpbmdzICh2YWxpZGF0ZWQsIHdpdGggZGVmYXVsdHMgc3Vic3RpdHV0ZWQgZm9yIGludmFsaWQgdmFsdWVzKS5cbiAgICpcbiAgICogQHJldHVybnMgVGhlIHJlYWRvbmx5IGVmZmVjdGl2ZSBzZXR0aW5ncy5cbiAgICovXG4gIHB1YmxpYyBnZXQgc2V0dGluZ3MoKTogUmVhZG9ubHlEZWVwPFBsdWdpblNldHRpbmdzPiB7XG4gICAgcmV0dXJuIHRoaXMuc2V0dGluZ3NTdGF0ZS5lZmZlY3RpdmVWYWx1ZXM7XG4gIH1cblxuICAvKipcbiAgICogR2V0cyB0aGUgY3VycmVudCBzZXR0aW5ncyBzdGF0ZSBzbmFwc2hvdC5cbiAgICpcbiAgICogQHJldHVybnMgVGhlIGN1cnJlbnQgc2V0dGluZ3Mgc3RhdGUuXG4gICAqL1xuICBwdWJsaWMgZ2V0IHNldHRpbmdzU3RhdGUoKTogUmVhZG9ubHlQbHVnaW5TZXR0aW5nc1N0YXRlPFBsdWdpblNldHRpbmdzPiB7XG4gICAgcmV0dXJuIHRoaXMuY3VycmVudFN0YXRlIGFzIFJlYWRvbmx5UGx1Z2luU2V0dGluZ3NTdGF0ZTxQbHVnaW5TZXR0aW5ncz47XG4gIH1cblxuICAvKipcbiAgICogVGhlIGRhdGEgaGFuZGxlciB1c2VkIHRvIGxvYWQgYW5kIHNhdmUgdGhlIHBsdWdpbiBzZXR0aW5ncy5cbiAgICovXG4gIHByb3RlY3RlZCByZWFkb25seSBkYXRhSGFuZGxlcjogRGF0YUhhbmRsZXI7XG4gIC8qKlxuICAgKiBUaGUgcGx1Z2luIGV2ZW50IHNvdXJjZSB0aGUgY29tcG9uZW50IGxpc3RlbnMgdG8gZm9yIGV4dGVybmFsIHNldHRpbmdzIGNoYW5nZXMuXG4gICAqL1xuICBwcm90ZWN0ZWQgcmVhZG9ubHkgcGx1Z2luRXZlbnRTb3VyY2U6IFBsdWdpbkV2ZW50U291cmNlO1xuXG4gIC8qKlxuICAgKiBUaGUgcGx1Z2luIHNldHRpbmdzIGNsYXNzIHVzZWQgdG8gY29uc3RydWN0IHNldHRpbmdzIGluc3RhbmNlcy5cbiAgICovXG4gIHByb3RlY3RlZCByZWFkb25seSBwbHVnaW5TZXR0aW5nc0NsYXNzOiBDb25zdHJ1Y3RvcjxQbHVnaW5TZXR0aW5ncywgW10+O1xuICBwcml2YXRlIHJlYWRvbmx5IGFzeW5jRXZlbnRzID0gbmV3IEFzeW5jRXZlbnRzPFBsdWdpblNldHRpbmdzQ29tcG9uZW50QmFzZUV2ZW50TWFwPFBsdWdpblNldHRpbmdzPj4oKTtcbiAgcHJpdmF0ZSBjdXJyZW50U3RhdGU6IFBsdWdpblNldHRpbmdzU3RhdGU8UGx1Z2luU2V0dGluZ3M+O1xuXG4gIHByaXZhdGUgaXNMb2FkZWRGcm9tRmlsZSA9IGZhbHNlO1xuXG4gIHByaXZhdGUgbGFzdFNhdmVkU3RhdGU6IFBsdWdpblNldHRpbmdzU3RhdGU8UGx1Z2luU2V0dGluZ3M+O1xuXG4gIHByaXZhdGUgcmVhZG9ubHkgbGVnYWN5U2V0dGluZ3NDb252ZXJ0ZXJzOiAoKHJlY29yZDogR2VuZXJpY09iamVjdCkgPT4gdm9pZClbXSA9IFtdO1xuICBwcml2YXRlIHJlYWRvbmx5IGxvYWRlZEZyb21GaWxlUmVzb2x2ZXJzOiAoKCkgPT4gdm9pZClbXSA9IFtdO1xuICBwcml2YXRlIHJlYWRvbmx5IHByb3BlcnR5TmFtZXM6IFByb3BlcnR5TmFtZXM8UGx1Z2luU2V0dGluZ3M+W107XG5cbiAgcHJpdmF0ZSByZWFkb25seSB2YWxpZGF0b3JzID0gbmV3IE1hcDxQcm9wZXJ0eU5hbWVzPFBsdWdpblNldHRpbmdzPiwgU2V0dGluZ3NWYWxpZGF0b3I8UGx1Z2luU2V0dGluZ3M+PigpO1xuXG4gIC8qKlxuICAgKiBDcmVhdGVzIGEgbmV3IHBsdWdpbiBzZXR0aW5ncyBjb21wb25lbnQuXG4gICAqXG4gICAqIEBwYXJhbSBwYXJhbXMgLSBUaGUgY29uc3RydWN0b3IgcGFyYW1ldGVycy5cbiAgICovXG4gIHB1YmxpYyBjb25zdHJ1Y3RvcihwYXJhbXM6IFBsdWdpblNldHRpbmdzQ29tcG9uZW50QmFzZUNvbnN0cnVjdG9yUGFyYW1zPFBsdWdpblNldHRpbmdzPikge1xuICAgIHN1cGVyKCk7XG4gICAgdGhpcy5kYXRhSGFuZGxlciA9IHBhcmFtcy5kYXRhSGFuZGxlcjtcbiAgICB0aGlzLnBsdWdpblNldHRpbmdzQ2xhc3MgPSBwYXJhbXMucGx1Z2luU2V0dGluZ3NDbGFzcztcbiAgICB0aGlzLnBsdWdpbkV2ZW50U291cmNlID0gcGFyYW1zLnBsdWdpbkV2ZW50U291cmNlO1xuXG4gICAgdGhpcy5kZWZhdWx0U2V0dGluZ3MgPSBuZXcgdGhpcy5wbHVnaW5TZXR0aW5nc0NsYXNzKCkgYXMgUmVhZG9ubHlEZWVwPFBsdWdpblNldHRpbmdzPjtcbiAgICB0aGlzLmN1cnJlbnRTdGF0ZSA9IHRoaXMuY3JlYXRlRGVmYXVsdFN0YXRlKCk7XG4gICAgdGhpcy5sYXN0U2F2ZWRTdGF0ZSA9IHRoaXMuY3JlYXRlRGVmYXVsdFN0YXRlKCk7XG4gICAgdGhpcy5wcm9wZXJ0eU5hbWVzID0gZ2V0QWxsS2V5cyh0aGlzLmN1cnJlbnRTdGF0ZS5pbnB1dFZhbHVlcyk7XG4gICAgdGhpcy5yZWdpc3RlclZhbGlkYXRvcnMoKTtcbiAgICB0aGlzLnJlZ2lzdGVyTGVnYWN5U2V0dGluZ3NDb252ZXJ0ZXJzKCk7XG4gIH1cblxuICAvKipcbiAgICogRWRpdHMgdGhlIHBsdWdpbiBzZXR0aW5ncyBhbmQgc2F2ZXMgdGhlbS5cbiAgICpcbiAgICogQHBhcmFtIHNldHRpbmdzRWRpdG9yIC0gVGhlIGVkaXRvci5cbiAgICogQHBhcmFtIGNvbnRleHQgLSBUaGUgY29udGV4dC5cbiAgICogQHJldHVybnMgQSB7QGxpbmsgUHJvbWlzZX0gdGhhdCByZXNvbHZlcyB3aGVuIHRoZSBzZXR0aW5ncyBhcmUgc2F2ZWQuXG4gICAqL1xuICBwdWJsaWMgYXN5bmMgZWRpdEFuZFNhdmUoc2V0dGluZ3NFZGl0b3I6IChzZXR0aW5nczogUGx1Z2luU2V0dGluZ3MpID0+IFByb21pc2FibGU8dm9pZD4sIGNvbnRleHQ/OiB1bmtub3duKTogUHJvbWlzZTx2b2lkPiB7XG4gICAgdGhpcy5lbnN1cmVMb2FkZWQoKTtcbiAgICBhd2FpdCB0aGlzLmVkaXQoc2V0dGluZ3NFZGl0b3IpO1xuICAgIGF3YWl0IHRoaXMuc2F2ZVRvRmlsZShjb250ZXh0KTtcbiAgfVxuXG4gIC8qKlxuICAgKiBFbnN1cmVzIHRoZSBzZXR0aW5ncyBhcmUgc2FmZS5cbiAgICpcbiAgICogSXQgcnVucyB2YWxpZGF0aW9uIGZvciBlYWNoIHByb3BlcnR5IGFuZCBzZXRzIHRoZSBkZWZhdWx0IHZhbHVlIGlmIHRoZSB2YWxpZGF0aW9uIGZhaWxzLlxuICAgKlxuICAgKiBAcGFyYW0gc2V0dGluZ3MgLSBUaGUgc2V0dGluZ3MuXG4gICAqIEByZXR1cm5zIEEge0BsaW5rIFByb21pc2V9IHRoYXQgcmVzb2x2ZXMgd2hlbiB0aGUgc2V0dGluZ3MgYXJlIHNhZmUuXG4gICAqL1xuICBwdWJsaWMgYXN5bmMgZW5zdXJlU2FmZShzZXR0aW5nczogUGx1Z2luU2V0dGluZ3MpOiBQcm9taXNlPHZvaWQ+IHtcbiAgICBjb25zdCB2YWxpZGF0aW9uUmVzdWx0ID0gYXdhaXQgdGhpcy52YWxpZGF0ZShzZXR0aW5ncyk7XG4gICAgY29uc3QgZGVmYXVsdHMgPSB0aGlzLmRlZmF1bHRTZXR0aW5ncyBhcyBQbHVnaW5TZXR0aW5ncztcbiAgICBmb3IgKGNvbnN0IHByb3BlcnR5TmFtZSBvZiB0aGlzLnByb3BlcnR5TmFtZXMpIHtcbiAgICAgIC8vIGVzbGludC1kaXNhYmxlLW5leHQtbGluZSB1bmljb3JuL25vLWNvbXB1dGVkLXByb3BlcnR5LWV4aXN0ZW5jZS1jaGVjayAtLSBUaGlzIHRlc3RzIHdoZXRoZXIgYSB2YWxpZGF0aW9uIG1lc3NhZ2UgaXMgbm9uLWVtcHR5LCBub3Qgd2hldGhlciB0aGUga2V5IGV4aXN0cy5cbiAgICAgIGlmICh2YWxpZGF0aW9uUmVzdWx0W3Byb3BlcnR5TmFtZV0pIHtcbiAgICAgICAgc2V0dGluZ3NbcHJvcGVydHlOYW1lXSA9IGRlZmF1bHRzW3Byb3BlcnR5TmFtZV07XG4gICAgICB9XG4gICAgfVxuICB9XG5cbiAgLyoqXG4gICAqIExpc3RzIHRoZSByZWNvdmVyeSBjb3BpZXMgb2YgYGRhdGEuanNvbmAga2VwdCBvbiB0aGlzIGRldmljZTogY29waWVzIG9mIGEgZmlsZSB0aGF0IGRpZCBub3QgcGFyc2UsIGFuZCBvZiBhIGZpbGVcbiAgICogd2hvc2Ugc3RvcmVkIHZhbHVlcyBhIGZpcnN0IHNhdmUgd291bGQgaGF2ZSBkcm9wcGVkIG9yIGNoYW5nZWQuXG4gICAqXG4gICAqIEByZXR1cm5zIFRoZSBjb3BpZXMsIG5ld2VzdCBmaXJzdDsgbm9uZSB3aGVuIHRoZSBkYXRhIGhhbmRsZXIga2VlcHMgbm8gcmVjb3ZlcnkgY29waWVzLlxuICAgKi9cbiAgcHVibGljIGFzeW5jIGdldFJlY292ZXJ5Q29waWVzKCk6IFByb21pc2U8U2V0dGluZ3NSZWNvdmVyeUNvcHlbXT4ge1xuICAgIHJldHVybiBhd2FpdCB0aGlzLmRhdGFIYW5kbGVyLnJlY292ZXJ5U3RvcmU/Lmxpc3QoKSA/PyBbXTtcbiAgfVxuXG4gIC8qKlxuICAgKiBHZXRzIGEgc2FmZSBjb3B5IG9mIHRoZSBzZXR0aW5ncy5cbiAgICpcbiAgICogQHBhcmFtIHNldHRpbmdzIC0gVGhlIHNldHRpbmdzLlxuICAgKiBAcmV0dXJucyBBIHtAbGluayBQcm9taXNlfSB0aGF0IHJlc29sdmVzIHRvIHRoZSBzYWZlIGNvcHkgb2YgdGhlIHNldHRpbmdzLlxuICAgKi9cbiAgcHVibGljIGFzeW5jIGdldFNhZmVDb3B5KHNldHRpbmdzOiBQbHVnaW5TZXR0aW5ncyk6IFByb21pc2U8UGx1Z2luU2V0dGluZ3M+IHtcbiAgICBjb25zdCBzYWZlU2V0dGluZ3MgPSBhd2FpdCB0aGlzLmNsb25lU2V0dGluZ3Moc2V0dGluZ3MpO1xuICAgIGF3YWl0IHRoaXMuZW5zdXJlU2FmZShzYWZlU2V0dGluZ3MpO1xuICAgIHJldHVybiBzYWZlU2V0dGluZ3M7XG4gIH1cblxuICAvKipcbiAgICogTG9hZHMgdGhlIHBsdWdpbiBzZXR0aW5ncyBmcm9tIHRoZSBmaWxlLlxuICAgKlxuICAgKiBAcGFyYW0gaXNJbml0aWFsTG9hZCAtIFdoZXRoZXIgdGhlIHNldHRpbmdzIGFyZSBiZWluZyBsb2FkZWQgZm9yIHRoZSBmaXJzdCB0aW1lLiBPbmx5IHRoZSBpbml0aWFsIGxvYWRcbiAgICogd3JpdGVzIHRoZSBub3JtYWxpemVkIHJlY29yZCBiYWNrIHRvIGBkYXRhLmpzb25gOyBhIHJlbG9hZCBhcHBsaWVzIGl0IGluIG1lbW9yeSBvbmx5LlxuICAgKiBAcmV0dXJucyBBIHtAbGluayBQcm9taXNlfSB0aGF0IHJlc29sdmVzIHdoZW4gdGhlIHNldHRpbmdzIGFyZSBsb2FkZWQuXG4gICAqL1xuICBwdWJsaWMgYXN5bmMgbG9hZEZyb21GaWxlKGlzSW5pdGlhbExvYWQ6IGJvb2xlYW4pOiBQcm9taXNlPHZvaWQ+IHtcbiAgICB0aGlzLmVuc3VyZUxvYWRlZCgpO1xuICAgIGxldCBkYXRhOiB1bmtub3duO1xuICAgIHRyeSB7XG4gICAgICBkYXRhID0gYXdhaXQgdGhpcy5kYXRhSGFuZGxlci5sb2FkRGF0YSgpO1xuICAgIH0gY2F0Y2ggKGVycm9yKSB7XG4gICAgICAvLyBBIGBkYXRhLmpzb25gIHRoYXQgZG9lcyBub3QgcGFyc2UgaXMgTk9UIGFuIGVtcHR5IHJlY29yZDogcmVhZGluZyBpdCBhcyBvbmUgd291bGQgc2F2ZSB0aGUgZGVmYXVsdHMgb3ZlciB0aGVcbiAgICAgIC8vIHVzZXIncyBzZXR0aW5ncy4gVGhlIGZpbGUgaXMgbGVmdCB1bnRvdWNoZWQgZWl0aGVyIHdheS4gV2l0aCBhIHJlY292ZXJ5IGNvcHkga2VwdCwgdGhlIGluaXRpYWwgbG9hZCBydW5zIG9uXG4gICAgICAvLyB0aGUgZGVmYXVsdHMgaW4gbWVtb3J5IGFuZCBhIHJlbG9hZCBrZWVwcyB0aGUgc2V0dGluZ3MgYWxyZWFkeSBpbiBtZW1vcnksIGFuZCBub3RoaW5nIGlzIHdyaXR0ZW4gdW50aWwgdGhlXG4gICAgICAvLyB1c2VyIGNoYW5nZXMgYSBzZXR0aW5nLiBXaXRob3V0IGEgY29weSB0aGUgbG9hZCBmYWlscywgc28gbm90aGluZyBjYW4gZXZlciBiZSBzYXZlZCBvdmVyIHRoZSBvbmx5IGNvcHkuXG4gICAgICBpZiAoIShlcnJvciBpbnN0YW5jZW9mIFBsdWdpbkRhdGFQYXJzZUVycm9yKSB8fCBlcnJvci5yZWNvdmVyeUNvcHkgPT09IG51bGwpIHtcbiAgICAgICAgdGhyb3cgZXJyb3I7XG4gICAgICB9XG4gICAgICBpZiAoaXNJbml0aWFsTG9hZCkge1xuICAgICAgICB0aGlzLmxhc3RTYXZlZFN0YXRlID0gdGhpcy5jcmVhdGVEZWZhdWx0U3RhdGUoKTtcbiAgICAgICAgdGhpcy5jdXJyZW50U3RhdGUgPSB0aGlzLmNyZWF0ZURlZmF1bHRTdGF0ZSgpO1xuICAgICAgfVxuICAgICAgdGhpcy5tYXJrTG9hZGVkRnJvbUZpbGUoKTtcbiAgICAgIGlmIChpc0luaXRpYWxMb2FkKSB7XG4gICAgICAgIGF3YWl0IHRoaXMuYXN5bmNFdmVudHMudHJpZ2dlckFzeW5jKCdsb2FkU2V0dGluZ3MnLCB0aGlzLmN1cnJlbnRTdGF0ZSBhcyBSZWFkb25seVBsdWdpblNldHRpbmdzU3RhdGU8UGx1Z2luU2V0dGluZ3M+LCBpc0luaXRpYWxMb2FkKTtcbiAgICAgIH1cbiAgICAgIHJldHVybjtcbiAgICB9XG4gICAgLy8gVGFrZW4gYmVmb3JlIGFueXRoaW5nIGJlbG93IGNhbiBtdXRhdGUgdGhlIHJlY29yZDogd2hhdCB0aGUgZmlsZSBoZWxkLCBmb3IgYSByZWNvdmVyeSBjb3B5LlxuICAgIGNvbnN0IG9yaWdpbmFsSnNvbiA9IEpTT04uc3RyaW5naWZ5KGRhdGEsIHVuZGVmaW5lZCwgSlNPTl9JTkRFTlQpO1xuICAgIHRoaXMubGFzdFNhdmVkU3RhdGUgPSB0aGlzLmNyZWF0ZURlZmF1bHRTdGF0ZSgpO1xuICAgIHRoaXMuY3VycmVudFN0YXRlID0gdGhpcy5jcmVhdGVEZWZhdWx0U3RhdGUoKTtcblxuICAgIHRyeSB7XG4gICAgICBpZiAoZGF0YSAhPT0gdW5kZWZpbmVkICYmIGRhdGEgIT09IG51bGwgJiYgdHlwZW9mIGRhdGEgIT09ICdvYmplY3QnKSB7XG4gICAgICAgIGNvbnNvbGUuZXJyb3IoYEludmFsaWQgc2V0dGluZ3MgZnJvbSBkYXRhLmpzb24uIEV4cGVjdGVkIE9iamVjdCwgZ290OiAke3R5cGVvZiBkYXRhfWApO1xuICAgICAgICByZXR1cm47XG4gICAgICB9XG5cbiAgICAgIC8vIE5vdGhpbmcgc3RvcmVkIGlzIHJlYWQgYXMgYW4gZW1wdHkgcmVjb3JkIHJhdGhlciB0aGFuIHNraXBwZWQsIHNvIHRoZSBzYXZlIGJlbG93IHdyaXRlcyB0aGUgZnVsbFxuICAgICAgLy8gZGVmYXVsdCByZWNvcmQuIFdpdGhvdXQgaXQgYSB1c2VyIHdobyBuZXZlciBjaGFuZ2VkIGEgc2V0dGluZyBoYXMgbm8gYGRhdGEuanNvbmAgYXQgYWxsLCBsb29rc1xuICAgICAgLy8gZXhhY3RseSBsaWtlIGEgZnJlc2ggaW5zdGFsbCwgYW5kIHNpbGVudGx5IHBpY2tzIHVwIGV2ZXJ5IGRlZmF1bHQgYSBsYXRlciByZWxlYXNlIGNoYW5nZXMuXG4gICAgICBjb25zdCByYXdSZWNvcmQgPSAoZGF0YSA/PyB7fSkgYXMgR2VuZXJpY09iamVjdDtcbiAgICAgIGNvbnN0IHBhcnNlZFNldHRpbmdzID0gYXdhaXQgdGhpcy5yYXdSZWNvcmRUb1NldHRpbmdzKHJhd1JlY29yZCk7XG4gICAgICBjb25zdCB2YWxpZGF0aW9uUmVzdWx0ID0gYXdhaXQgdGhpcy52YWxpZGF0ZShwYXJzZWRTZXR0aW5ncyk7XG5cbiAgICAgIGZvciAoY29uc3QgcHJvcGVydHlOYW1lIG9mIHRoaXMucHJvcGVydHlOYW1lcykge1xuICAgICAgICB0aGlzLnNldFByb3BlcnR5SW1wbCh7XG4gICAgICAgICAgcHJvcGVydHlOYW1lLFxuICAgICAgICAgIHZhbGlkYXRpb25NZXNzYWdlOiB2YWxpZGF0aW9uUmVzdWx0W3Byb3BlcnR5TmFtZV0sXG4gICAgICAgICAgdmFsdWU6IHBhcnNlZFNldHRpbmdzW3Byb3BlcnR5TmFtZV1cbiAgICAgICAgfSk7XG4gICAgICB9XG5cbiAgICAgIHRoaXMubGFzdFNhdmVkU3RhdGUgPSBhd2FpdCB0aGlzLmNsb25lU3RhdGUodGhpcy5jdXJyZW50U3RhdGUpO1xuXG4gICAgICAvLyBBIGNvbXBvbmVudCB0aGF0IGtub3dzIG5vIHByb3BlcnR5IG5hbWVzIGNhbm5vdCBub3JtYWxpemUgYW55dGhpbmc6IGBzZXR0aW5nc1RvUmF3UmVjb3JkKClgIGNhblxuICAgICAgLy8gb25seSBldmVyIHJldHVybiBge31gLCBzbyB0aGUgc2F2ZSBiZWxvdyB3b3VsZCBub3QgcmV3cml0ZSBgZGF0YS5qc29uYCAtLSBpdCB3b3VsZCBlbXB0eSBpdC5cbiAgICAgIC8vIGBQbHVnaW5CYXNlYCBhZGRzIGEgcGxhY2Vob2xkZXIgYFBsdWdpblNldHRpbmdzQ29tcG9uZW50QmFzZTxvYmplY3Q+YCBiZWZvcmUgYG9ubG9hZEltcGwoKWAgc3dhcHNcbiAgICAgIC8vIGluIHRoZSBwbHVnaW4ncyBvd24gY29tcG9uZW50LCBhbmQgdGhhdCBwbGFjZWhvbGRlciBpcyBleGFjdGx5IHRoaXMgY2FzZTogaXQgcmVhZCBldmVyeSByZWFsXG4gICAgICAvLyBzZXR0aW5nLCBrZXB0IG5vbmUgb2YgdGhlbSwgYW5kIHNhdmVkIHRoZSBkaWZmZXJlbmNlIGJhY2sgb3ZlciB0aGUgZmlsZS5cbiAgICAgIC8vXG4gICAgICAvLyBBIHJlbG9hZCBjYXVzZWQgYnkgYW4gZXh0ZXJuYWwgY2hhbmdlIChhIHN5bmMgdG9vbCwgYW5vdGhlciBkZXZpY2UpIGFwcGxpZXMgdGhlIG5vcm1hbGl6ZWRcbiAgICAgIC8vIHNldHRpbmdzIGluIG1lbW9yeSBhbmQgbmV2ZXIgd3JpdGVzIHRoZW0gYmFjay4gVHdvIHN5bmNlZCBkZXZpY2VzIHdob3NlIG5vcm1hbGl6YXRpb24gZGlmZmVyc1xuICAgICAgLy8gKGRpZmZlcmVudCBwbHVnaW4gdmVyc2lvbnMsIG9yIGFueSBub3JtYWxpemF0aW9uIHRoYXQgaXMgbm90IGEgZml4ZWQgcG9pbnQpIHdvdWxkIG90aGVyd2lzZVxuICAgICAgLy8gcmV3cml0ZSBlYWNoIG90aGVyJ3MgYGRhdGEuanNvbmAgb24gZXZlcnkgcmVsb2FkLCBhbmQgdGhlIHN5bmMgdG9vbCB3b3VsZCBjYXJyeSBlYWNoIHJld3JpdGVcbiAgICAgIC8vIGJhY2ssIGZvcmV2ZXIgKGBvYnNpZGlhbi1jdXN0b20tYXR0YWNobWVudC1sb2NhdGlvbmAgIzEwMikuIFRoZSBpbml0aWFsIGxvYWQgc3RpbGwgd3JpdGVzOlxuICAgICAgLy8gdGhlIGRlZmF1bHQgcmVjb3JkIGFuZCB0aGUgbGVnYWN5IG1pZ3JhdGlvbnMgZGVwZW5kIG9uIGl0LlxuICAgICAgaWYgKHRoaXMucHJvcGVydHlOYW1lcy5sZW5ndGggPT09IDAgfHwgIWlzSW5pdGlhbExvYWQpIHtcbiAgICAgICAgcmV0dXJuO1xuICAgICAgfVxuXG4gICAgICBjb25zdCBuZXdSZWNvcmQgPSBhd2FpdCB0aGlzLnNldHRpbmdzVG9SYXdSZWNvcmQodGhpcy5jdXJyZW50U3RhdGUuaW5wdXRWYWx1ZXMpO1xuXG4gICAgICBpZiAoIWlzRGVlcEVxdWFsKG5ld1JlY29yZCwgZGF0YSkgJiYgYXdhaXQgdGhpcy5rZWVwQ29weUJlZm9yZUxvc3N5UmV3cml0ZShvcmlnaW5hbEpzb24sIG5ld1JlY29yZCkpIHtcbiAgICAgICAgYXdhaXQgdGhpcy5zYXZlVG9GaWxlSW1wbCgpO1xuICAgICAgfVxuICAgIH0gZmluYWxseSB7XG4gICAgICB0aGlzLm1hcmtMb2FkZWRGcm9tRmlsZSgpO1xuICAgICAgYXdhaXQgdGhpcy5hc3luY0V2ZW50cy50cmlnZ2VyQXN5bmMoJ2xvYWRTZXR0aW5ncycsIHRoaXMuY3VycmVudFN0YXRlIGFzIFJlYWRvbmx5UGx1Z2luU2V0dGluZ3NTdGF0ZTxQbHVnaW5TZXR0aW5ncz4sIGlzSW5pdGlhbExvYWQpO1xuICAgIH1cbiAgfVxuXG4gIC8qKlxuICAgKiBSZW1vdmUgYW4gZXZlbnQgbGlzdGVuZXIuXG4gICAqXG4gICAqIEB0eXBlUGFyYW0gRXZlbnROYW1lIC0gVGhlIG5hbWUgb2YgdGhlIGV2ZW50LlxuICAgKiBAdHlwZVBhcmFtIEFyZ3VtZW50cyAtIFRoZSB0eXBlcyBvZiB0aGUgYXJndW1lbnRzIHRoZSBldmVudCBjYWxsYmFjayBhY2NlcHRzLlxuICAgKiBAcGFyYW0gbmFtZSAtIFRoZSBuYW1lIG9mIHRoZSBldmVudC5cbiAgICogQHBhcmFtIGNhbGxiYWNrIC0gVGhlIGNhbGxiYWNrIHRvIHJlbW92ZS5cbiAgICovXG4gIHB1YmxpYyBvZmY8XG4gICAgRXZlbnROYW1lIGV4dGVuZHMgU3RyaW5nS2V5czxQbHVnaW5TZXR0aW5nc0NvbXBvbmVudEJhc2VFdmVudE1hcDxQbHVnaW5TZXR0aW5ncz4+LFxuICAgIC8vIGVzbGludC1kaXNhYmxlLW5leHQtbGluZSBAdHlwZXNjcmlwdC1lc2xpbnQvbm8tdW5uZWNlc3NhcnktdHlwZS1wYXJhbWV0ZXJzIC0tIFdlIG5lZWQgdG8gdXNlIHRoZSBkdW1teSBwYXJhbWV0ZXIgdG8gZ2V0IHR5cGUgaW5mZXJlbmNlLlxuICAgIEFyZ3VtZW50cyBleHRlbmRzIENhbGxiYWNrQXJndW1lbnRzPFBsdWdpblNldHRpbmdzQ29tcG9uZW50QmFzZUV2ZW50TWFwPFBsdWdpblNldHRpbmdzPiwgRXZlbnROYW1lPlxuICA+KG5hbWU6IEV2ZW50TmFtZSwgY2FsbGJhY2s6ICguLi4kYXJndW1lbnRzOiBBcmd1bWVudHMpID0+IFByb21pc2FibGU8dm9pZD4pOiB2b2lkIHtcbiAgICB0aGlzLmFzeW5jRXZlbnRzLm9mZihuYW1lLCBjYWxsYmFjayk7XG4gIH1cblxuICAvKipcbiAgICogUmVtb3ZlIGFuIGV2ZW50IGxpc3RlbmVyIGJ5IHJlZmVyZW5jZS5cbiAgICpcbiAgICogQHBhcmFtIGV2ZW50UmVmIC0gVGhlIHJlZmVyZW5jZSB0byB0aGUgZXZlbnQgbGlzdGVuZXIuXG4gICAqL1xuICBwdWJsaWMgb2ZmcmVmKGV2ZW50UmVmOiBBc3luY0V2ZW50UmVmKTogdm9pZCB7XG4gICAgdGhpcy5hc3luY0V2ZW50cy5vZmZyZWYoZXZlbnRSZWYpO1xuICB9XG5cbiAgLyoqXG4gICAqIEFkZCBhbiBldmVudCBsaXN0ZW5lci5cbiAgICpcbiAgICogQHR5cGVQYXJhbSBFdmVudE5hbWUgLSBUaGUgbmFtZSBvZiB0aGUgZXZlbnQuXG4gICAqIEB0eXBlUGFyYW0gQXJndW1lbnRzIC0gVGhlIHR5cGVzIG9mIHRoZSBhcmd1bWVudHMgdGhlIGV2ZW50IGNhbGxiYWNrIGFjY2VwdHMuXG4gICAqIEBwYXJhbSBuYW1lIC0gVGhlIG5hbWUgb2YgdGhlIGV2ZW50LlxuICAgKiBAcGFyYW0gY2FsbGJhY2sgLSBUaGUgY2FsbGJhY2sgdG8gY2FsbCB3aGVuIHRoZSBldmVudCBpcyB0cmlnZ2VyZWQuXG4gICAqIEBwYXJhbSB0aGlzQXJndW1lbnQgLSBUaGUgY29udGV4dCBwYXNzZWQgYXMgYHRoaXNgIHRvIHRoZSBgY2FsbGJhY2tgLlxuICAgKiBAcmV0dXJucyBBIHJlZmVyZW5jZSB0byB0aGUgZXZlbnQgbGlzdGVuZXIuXG4gICAqXG4gICAqIEByZW1hcmtzIE5vdCByZWZhY3RvcmVkIHRvIHBhcmFtZXRlci1vYmplY3QgcGF0dGVybiwgdG8ga2VlcCB0aGUgcGFyaXR5IHdpdGgge0BsaW5rIG9ic2lkaWFuI0V2ZW50cyNvbn0gKG9yIG9uY2UsIGNvcnJlc3BvbmRpbmdseSkuXG4gICAqL1xuICBwdWJsaWMgb248XG4gICAgRXZlbnROYW1lIGV4dGVuZHMgU3RyaW5nS2V5czxQbHVnaW5TZXR0aW5nc0NvbXBvbmVudEJhc2VFdmVudE1hcDxQbHVnaW5TZXR0aW5ncz4+LFxuICAgIC8vIGVzbGludC1kaXNhYmxlLW5leHQtbGluZSBAdHlwZXNjcmlwdC1lc2xpbnQvbm8tdW5uZWNlc3NhcnktdHlwZS1wYXJhbWV0ZXJzIC0tIFdlIG5lZWQgdG8gdXNlIHRoZSBkdW1teSBwYXJhbWV0ZXIgdG8gZ2V0IHR5cGUgaW5mZXJlbmNlLlxuICAgIEFyZ3VtZW50cyBleHRlbmRzIENhbGxiYWNrQXJndW1lbnRzPFBsdWdpblNldHRpbmdzQ29tcG9uZW50QmFzZUV2ZW50TWFwPFBsdWdpblNldHRpbmdzPiwgRXZlbnROYW1lPlxuICA+KG5hbWU6IEV2ZW50TmFtZSwgY2FsbGJhY2s6ICguLi4kYXJndW1lbnRzOiBBcmd1bWVudHMpID0+IFByb21pc2FibGU8dm9pZD4sIHRoaXNBcmd1bWVudD86IHVua25vd24pOiBBc3luY0V2ZW50UmVmIHtcbiAgICByZXR1cm4gdGhpcy5hc3luY0V2ZW50cy5vbihuYW1lLCBjYWxsYmFjaywgdGhpc0FyZ3VtZW50KTtcbiAgfVxuXG4gIC8qKlxuICAgKiBUcmlnZ2VyIGFuIGV2ZW50LCBleGVjdXRpbmcgYWxsIHRoZSBsaXN0ZW5lcnMgaW4gb3JkZXIgZXZlbiBpZiBzb21lIG9mIHRoZW0gdGhyb3cgYW4gZXJyb3IuXG4gICAqXG4gICAqIEFkZCBhbiBldmVudCBsaXN0ZW5lciB0aGF0IHdpbGwgYmUgY2FsbGVkIG9ubHkgb25jZS5cbiAgICpcbiAgICogQHR5cGVQYXJhbSBFdmVudE5hbWUgLSBUaGUgbmFtZSBvZiB0aGUgZXZlbnQuXG4gICAqIEB0eXBlUGFyYW0gQXJndW1lbnRzIC0gVGhlIHR5cGVzIG9mIHRoZSBhcmd1bWVudHMgdGhlIGV2ZW50IGNhbGxiYWNrIGFjY2VwdHMuXG4gICAqIEBwYXJhbSBuYW1lIC0gVGhlIG5hbWUgb2YgdGhlIGV2ZW50LlxuICAgKiBAcGFyYW0gY2FsbGJhY2sgLSBUaGUgY2FsbGJhY2sgdG8gY2FsbCB3aGVuIHRoZSBldmVudCBpcyB0cmlnZ2VyZWQuXG4gICAqIEBwYXJhbSB0aGlzQXJndW1lbnQgLSBUaGUgY29udGV4dCBwYXNzZWQgYXMgYHRoaXNgIHRvIHRoZSBgY2FsbGJhY2tgLlxuICAgKiBAcmV0dXJucyBBIHJlZmVyZW5jZSB0byB0aGUgZXZlbnQgbGlzdGVuZXIuXG4gICAqXG4gICAqIEByZW1hcmtzIE5vdCByZWZhY3RvcmVkIHRvIHBhcmFtZXRlci1vYmplY3QgcGF0dGVybiwgdG8ga2VlcCB0aGUgcGFyaXR5IHdpdGgge0BsaW5rIG9ic2lkaWFuI0V2ZW50cyNvbn0gKG9yIG9uY2UsIGNvcnJlc3BvbmRpbmdseSkuXG4gICAqL1xuICBwdWJsaWMgb25jZTxcbiAgICBFdmVudE5hbWUgZXh0ZW5kcyBTdHJpbmdLZXlzPFBsdWdpblNldHRpbmdzQ29tcG9uZW50QmFzZUV2ZW50TWFwPFBsdWdpblNldHRpbmdzPj4sXG4gICAgLy8gZXNsaW50LWRpc2FibGUtbmV4dC1saW5lIEB0eXBlc2NyaXB0LWVzbGludC9uby11bm5lY2Vzc2FyeS10eXBlLXBhcmFtZXRlcnMgLS0gV2UgbmVlZCB0byB1c2UgdGhlIGR1bW15IHBhcmFtZXRlciB0byBnZXQgdHlwZSBpbmZlcmVuY2UuXG4gICAgQXJndW1lbnRzIGV4dGVuZHMgQ2FsbGJhY2tBcmd1bWVudHM8UGx1Z2luU2V0dGluZ3NDb21wb25lbnRCYXNlRXZlbnRNYXA8UGx1Z2luU2V0dGluZ3M+LCBFdmVudE5hbWU+XG4gID4obmFtZTogRXZlbnROYW1lLCBjYWxsYmFjazogKC4uLiRhcmd1bWVudHM6IEFyZ3VtZW50cykgPT4gUHJvbWlzYWJsZTx2b2lkPiwgdGhpc0FyZ3VtZW50PzogdW5rbm93bik6IEFzeW5jRXZlbnRSZWYge1xuICAgIHJldHVybiB0aGlzLmFzeW5jRXZlbnRzLm9uY2UobmFtZSwgY2FsbGJhY2ssIHRoaXNBcmd1bWVudCk7XG4gIH1cblxuICAvKipcbiAgICogQ2FsbGVkIHdoZW4gdGhlIGV4dGVybmFsIHNldHRpbmdzIGNoYW5nZS5cbiAgICpcbiAgICogQHJldHVybnMgQSB7QGxpbmsgUHJvbWlzZX0gdGhhdCByZXNvbHZlcyB3aGVuIHRoZSBzZXR0aW5ncyBhcmUgcmVsb2FkZWQuXG4gICAqL1xuICBwdWJsaWMgYXN5bmMgb25FeHRlcm5hbFNldHRpbmdzQ2hhbmdlKCk6IFByb21pc2U8dm9pZD4ge1xuICAgIHRoaXMuZW5zdXJlTG9hZGVkKCk7XG4gICAgYXdhaXQgdGhpcy5sb2FkRnJvbUZpbGUoZmFsc2UpO1xuICB9XG5cbiAgLyoqXG4gICAqIExvYWRzIHNldHRpbmdzIGZyb20gZmlsZSBhbmQgcmVnaXN0ZXJzIGV2ZW50IGhhbmRsZXJzLlxuICAgKi9cbiAgcHVibGljIG92ZXJyaWRlIGFzeW5jIG9ubG9hZEFzeW5jKCk6IFByb21pc2U8dm9pZD4ge1xuICAgIHJlZ2lzdGVyQXN5bmNFdmVudCh0aGlzLCB0aGlzLm9uKCdsb2FkU2V0dGluZ3MnLCB0aGlzLm9uTG9hZFNldHRpbmdzLmJpbmQodGhpcykpKTtcbiAgICByZWdpc3RlckFzeW5jRXZlbnQodGhpcywgdGhpcy5vbignc2F2ZVNldHRpbmdzJywgKG5ld1N0YXRlLCBvbGRTdGF0ZSwgY29udGV4dCkgPT4gdGhpcy5vblNhdmVTZXR0aW5ncyh7IGNvbnRleHQsIG5ld1N0YXRlLCBvbGRTdGF0ZSB9KSkpO1xuICAgIHJlZ2lzdGVyQXN5bmNFdmVudCh0aGlzLCB0aGlzLnBsdWdpbkV2ZW50U291cmNlLm9uKCdleHRlcm5hbFNldHRpbmdzQ2hhbmdlJywgdGhpcy5vbkV4dGVybmFsU2V0dGluZ3NDaGFuZ2UuYmluZCh0aGlzKSkpO1xuICAgIGF3YWl0IHRoaXMubG9hZEZyb21GaWxlKHRydWUpO1xuICB9XG5cbiAgLyoqXG4gICAqIFJlZ2lzdGVycyBhIGxlZ2FjeSBzZXR0aW5ncyBjb252ZXJ0ZXIuXG4gICAqXG4gICAqIEB0eXBlUGFyYW0gTGVnYWN5U2V0dGluZ3MgLSBUaGUgbGVnYWN5IHNldHRpbmdzIGNsYXNzLlxuICAgKiBAcGFyYW0gbGVnYWN5U2V0dGluZ3NDbGFzcyAtIFRoZSBsZWdhY3kgc2V0dGluZ3MgY2xhc3MuXG4gICAqIEBwYXJhbSBjb252ZXJ0ZXIgLSBUaGUgY29udmVydGVyLlxuICAgKi9cbiAgcHVibGljIHJlZ2lzdGVyTGVnYWN5U2V0dGluZ3NDb252ZXJ0ZXI8TGVnYWN5U2V0dGluZ3MgZXh0ZW5kcyBvYmplY3Q+KFxuICAgIGxlZ2FjeVNldHRpbmdzQ2xhc3M6IG5ldyAoKSA9PiBMZWdhY3lTZXR0aW5ncyxcbiAgICBjb252ZXJ0ZXI6IChsZWdhY3lTZXR0aW5nczogUGFydGlhbDxMZWdhY3lTZXR0aW5ncz4gJiBQYXJ0aWFsPFBsdWdpblNldHRpbmdzPikgPT4gdm9pZFxuICApOiB2b2lkIHtcbiAgICBjb25zdCB0aGlzV3JhcHBlciA9IFZhbHVlV3JhcHBlci5vZih0aGlzKTtcbiAgICB0aGlzLmxlZ2FjeVNldHRpbmdzQ29udmVydGVycy5wdXNoKGxlZ2FjeVNldHRpbmdzQ29udmVydGVyKTtcblxuICAgIGZ1bmN0aW9uIGxlZ2FjeVNldHRpbmdzQ29udmVydGVyKHJlY29yZDogR2VuZXJpY09iamVjdCk6IHZvaWQge1xuICAgICAgY29uc3QgbGVnYWN5U2V0dGluZ3NLZXlzID0gbmV3IFNldDxzdHJpbmc+KE9iamVjdC5rZXlzKG5ldyBsZWdhY3lTZXR0aW5nc0NsYXNzKCkpKTtcbiAgICAgIGNvbnN0IHBsdWdpblNldHRpbmdLZXlzID0gbmV3IFNldDxzdHJpbmc+KHRoaXNXcmFwcGVyLnZhbHVlLnByb3BlcnR5TmFtZXMpO1xuICAgICAgY29uc3QgbGVnYWN5U2V0dGluZ3MgPSByZWNvcmQgYXMgUGFydGlhbDxMZWdhY3lTZXR0aW5ncz4gJiBQYXJ0aWFsPFBsdWdpblNldHRpbmdzPjtcbiAgICAgIGNvbnZlcnRlcihsZWdhY3lTZXR0aW5ncyk7XG4gICAgICBmb3IgKGNvbnN0IGtleSBvZiBPYmplY3Qua2V5cyhsZWdhY3lTZXR0aW5ncykpIHtcbiAgICAgICAgaWYgKHBsdWdpblNldHRpbmdLZXlzLmhhcyhrZXkpIHx8ICFsZWdhY3lTZXR0aW5nc0tleXMuaGFzKGtleSkpIHtcbiAgICAgICAgICBjb250aW51ZTtcbiAgICAgICAgfVxuXG4gICAgICAgIC8vIGVzbGludC1kaXNhYmxlLW5leHQtbGluZSBAdHlwZXNjcmlwdC1lc2xpbnQvbm8tZHluYW1pYy1kZWxldGUgLS0gV2UgaGF2ZSBubyBvdGhlciB3YXkgdG8gZGVsZXRlIHRoZSBwcm9wZXJ0eS5cbiAgICAgICAgZGVsZXRlIHJlY29yZFtrZXldO1xuICAgICAgfVxuICAgIH1cbiAgfVxuXG4gIC8qKlxuICAgKiBSZWdpc3RlcnMgYSB2YWxpZGF0b3IgZm9yIGEgcHJvcGVydHkuXG4gICAqXG4gICAqIEB0eXBlUGFyYW0gUHJvcGVydHlOYW1lIC0gVGhlIG5hbWUgb2YgdGhlIHNldHRpbmdzIHByb3BlcnR5LlxuICAgKiBAcGFyYW0gcHJvcGVydHlOYW1lIC0gVGhlIG5hbWUgb2YgdGhlIHByb3BlcnR5LlxuICAgKiBAcGFyYW0gdmFsaWRhdG9yIC0gVGhlIHZhbGlkYXRvci5cbiAgICovXG4gIHB1YmxpYyByZWdpc3RlclZhbGlkYXRvcjxQcm9wZXJ0eU5hbWUgZXh0ZW5kcyBQcm9wZXJ0eU5hbWVzPFBsdWdpblNldHRpbmdzPj4oXG4gICAgcHJvcGVydHlOYW1lOiBQcm9wZXJ0eU5hbWUsXG4gICAgdmFsaWRhdG9yOiBTZXR0aW5nc1ZhbGlkYXRvcjxQbHVnaW5TZXR0aW5ncywgUHJvcGVydHlOYW1lPlxuICApOiB2b2lkIHtcbiAgICB0aGlzLnZhbGlkYXRvcnMuc2V0KHByb3BlcnR5TmFtZSwgdmFsaWRhdG9yIGFzIFNldHRpbmdzVmFsaWRhdG9yPFBsdWdpblNldHRpbmdzPik7XG4gIH1cblxuICAvKipcbiAgICogUmVzdG9yZXMgYSByZWNvdmVyeSBjb3B5IG9mIGBkYXRhLmpzb25gIGtlcHQgb24gdGhpcyBkZXZpY2U6IHdyaXRlcyBpdHMgcmVjb3JkIGJhY2sgdG8gdGhlIGZpbGUgYW5kIHJlbG9hZHMgdGhlXG4gICAqIHNldHRpbmdzIGZyb20gaXQuXG4gICAqXG4gICAqIFRoZSBzZXR0aW5ncyBpbiB1c2UgYXJlIGtlcHQgYXMgYSByZWNvdmVyeSBjb3B5IG9mIHRoZWlyIG93biBmaXJzdCwgc28gYSByZXN0b3JlIGxvc2VzIG5vdGhpbmcgZWl0aGVyLlxuICAgKlxuICAgKiBAcGFyYW0gaWQgLSBUaGUgaWQgb2YgdGhlIGNvcHksIGZyb20ge0BsaW5rIGdldFJlY292ZXJ5Q29waWVzfS5cbiAgICogQHJldHVybnMgQSB7QGxpbmsgUHJvbWlzZX0gdGhhdCByZXNvbHZlcyB3aGVuIHRoZSByZXN0b3JlZCBzZXR0aW5ncyBhcmUgbG9hZGVkLlxuICAgKiBAdGhyb3dzIElmIHRoZSBkYXRhIGhhbmRsZXIga2VlcHMgbm8gcmVjb3ZlcnkgY29waWVzLCBubyBjb3B5IGhhcyB0aGF0IGlkLCBvciB0aGUgY29weSBpcyBub3QgdmFsaWQgSlNPTiAoYSBjb3B5XG4gICAqIG9mIGFuIHVucGFyc2VhYmxlIGZpbGUgaGFzIHRvIGJlIHJlcGFpcmVkIGJ5IGhhbmQgZmlyc3QpLlxuICAgKi9cbiAgcHVibGljIGFzeW5jIHJlc3RvcmVSZWNvdmVyeUNvcHkoaWQ6IHN0cmluZyk6IFByb21pc2U8dm9pZD4ge1xuICAgIHRoaXMuZW5zdXJlTG9hZGVkKCk7XG4gICAgY29uc3QgcmVjb3ZlcnlTdG9yZSA9IHRoaXMuZGF0YUhhbmRsZXIucmVjb3ZlcnlTdG9yZTtcbiAgICBpZiAoIXJlY292ZXJ5U3RvcmUpIHtcbiAgICAgIHRocm93IG5ldyBFcnJvcignVGhlIGRhdGEgaGFuZGxlciBrZWVwcyBubyByZWNvdmVyeSBjb3BpZXMuJyk7XG4gICAgfVxuICAgIGNvbnN0IGNvcGllcyA9IGF3YWl0IHJlY292ZXJ5U3RvcmUubGlzdCgpO1xuICAgIGNvbnN0IGNvcHkgPSBjb3BpZXMuZmluZCgoY2FuZGlkYXRlKSA9PiBjYW5kaWRhdGUuaWQgPT09IGlkKTtcbiAgICBpZiAoIWNvcHkpIHtcbiAgICAgIHRocm93IG5ldyBFcnJvcihgTm8gcmVjb3ZlcnkgY29weSBcIiR7aWR9XCIgaXMga2VwdCBvbiB0aGlzIGRldmljZS5gKTtcbiAgICB9XG5cbiAgICBsZXQgZGF0YTogdW5rbm93bjtcbiAgICB0cnkge1xuICAgICAgZGF0YSA9IEpTT04ucGFyc2UoY29weS5yYXdUZXh0KTtcbiAgICB9IGNhdGNoIChlcnJvcikge1xuICAgICAgdGhyb3cgbmV3IEVycm9yKGBSZWNvdmVyeSBjb3B5IFwiJHtpZH1cIiBpcyBub3QgdmFsaWQgSlNPTiwgc28gaXQgY2Fubm90IGJlIHJlc3RvcmVkIGFzIGl0IGlzLmAsIHsgY2F1c2U6IGVycm9yIH0pO1xuICAgIH1cblxuICAgIGNvbnN0IGN1cnJlbnRSZWNvcmQgPSBhd2FpdCB0aGlzLnNldHRpbmdzVG9SYXdSZWNvcmQodGhpcy5jdXJyZW50U3RhdGUuaW5wdXRWYWx1ZXMpO1xuICAgIGF3YWl0IHJlY292ZXJ5U3RvcmUua2VlcCh7XG4gICAgICBwYXRoOiBjb3B5LnBhdGgsXG4gICAgICByYXdUZXh0OiBKU09OLnN0cmluZ2lmeShjdXJyZW50UmVjb3JkLCB1bmRlZmluZWQsIEpTT05fSU5ERU5UKSxcbiAgICAgIHJlYXNvbjogU2V0dGluZ3NSZWNvdmVyeVJlYXNvbi5Mb3NzeVJld3JpdGVcbiAgICB9KTtcbiAgICBhd2FpdCB0aGlzLmRhdGFIYW5kbGVyLnNhdmVEYXRhKGRhdGEpO1xuICAgIGF3YWl0IHRoaXMubG9hZEZyb21GaWxlKGZhbHNlKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBSZXZhbGlkYXRlcyB0aGUgc2V0dGluZ3MuXG4gICAqXG4gICAqIEByZXR1cm5zIFRoZSB2YWxpZGF0aW9uIG1lc3NhZ2VzLlxuICAgKi9cbiAgcHVibGljIGFzeW5jIHJldmFsaWRhdGUoKTogUHJvbWlzZTxSZWNvcmQ8UHJvcGVydHlOYW1lczxQbHVnaW5TZXR0aW5ncz4sIHN0cmluZz4+IHtcbiAgICB0aGlzLmVuc3VyZUxvYWRlZCgpO1xuICAgIGF3YWl0IHRoaXMuZWRpdChub29wKTtcbiAgICByZXR1cm4gdGhpcy5jdXJyZW50U3RhdGUudmFsaWRhdGlvbk1lc3NhZ2VzO1xuICB9XG5cbiAgLyoqXG4gICAqIFNhdmVzIHRoZSBuZXcgcGx1Z2luIHNldHRpbmdzLlxuICAgKlxuICAgKiBAcGFyYW0gY29udGV4dCAtIFRoZSBjb250ZXh0IG9mIHRoZSBzYXZlIHRvIGZpbGUgb3BlcmF0aW9uLlxuICAgKiBAcmV0dXJucyBBIHtAbGluayBQcm9taXNlfSB0aGF0IHJlc29sdmVzIHdoZW4gdGhlIHNldHRpbmdzIGFyZSBzYXZlZC5cbiAgICovXG4gIHB1YmxpYyBhc3luYyBzYXZlVG9GaWxlKGNvbnRleHQ/OiB1bmtub3duKTogUHJvbWlzZTx2b2lkPiB7XG4gICAgdGhpcy5lbnN1cmVMb2FkZWQoKTtcbiAgICBpZiAoaXNEZWVwRXF1YWwodGhpcy5sYXN0U2F2ZWRTdGF0ZS5pbnB1dFZhbHVlcywgdGhpcy5jdXJyZW50U3RhdGUuaW5wdXRWYWx1ZXMpKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgdHJ5IHtcbiAgICAgIGF3YWl0IHRoaXMuc2F2ZVRvRmlsZUltcGwoKTtcbiAgICB9IGNhdGNoIChlcnJvcikge1xuICAgICAgLy8gQSByZWZ1c2VkIHNhdmUgKGFuIG92ZXJzaXplZCBgZGF0YS5qc29uYCwgc2VlIGBQbHVnaW5EYXRhSGFuZGxlcmApIHdyb3RlIG5vdGhpbmcsIHNvIHRoZSBmaWxlIHN0aWxsIGhvbGRzXG4gICAgICAvLyB0aGUgbGFzdCBzYXZlZCBzZXR0aW5ncy4gUHV0IG1lbW9yeSBiYWNrIHRvIG1hdGNoIGl0OiBvdGhlcndpc2UgZXZlcnkgbGF0ZXIgc2F2ZSB3b3VsZCBjYXJyeSB0aGUgcmVqZWN0ZWRcbiAgICAgIC8vIGVkaXQgYWdhaW4gYW5kIGZhaWwgdGhlIHNhbWUgd2F5LCBhbmQgdGhlIHBsdWdpbiB3b3VsZCBydW4gb24gc2V0dGluZ3MgdGhhdCBleGlzdCBub3doZXJlIG9uIGRpc2suXG4gICAgICB0aGlzLmN1cnJlbnRTdGF0ZSA9IGF3YWl0IHRoaXMuY2xvbmVTdGF0ZSh0aGlzLmxhc3RTYXZlZFN0YXRlKTtcbiAgICAgIHRocm93IGVycm9yO1xuICAgIH1cbiAgICBhd2FpdCB0aGlzLmFzeW5jRXZlbnRzLnRyaWdnZXJBc3luYyhcbiAgICAgICdzYXZlU2V0dGluZ3MnLFxuICAgICAgdGhpcy5jdXJyZW50U3RhdGUgYXMgUmVhZG9ubHlQbHVnaW5TZXR0aW5nc1N0YXRlPFBsdWdpblNldHRpbmdzPixcbiAgICAgIHRoaXMubGFzdFNhdmVkU3RhdGUgYXMgUmVhZG9ubHlQbHVnaW5TZXR0aW5nc1N0YXRlPFBsdWdpblNldHRpbmdzPixcbiAgICAgIGNvbnRleHRcbiAgICApO1xuICAgIHRoaXMubGFzdFNhdmVkU3RhdGUgPSBhd2FpdCB0aGlzLmNsb25lU3RhdGUodGhpcy5jdXJyZW50U3RhdGUpO1xuICB9XG5cbiAgLyoqXG4gICAqIFNldHMgdGhlIHZhbHVlIG9mIGEgcHJvcGVydHkuXG4gICAqXG4gICAqIEB0eXBlUGFyYW0gUHJvcGVydHlOYW1lIC0gVGhlIG5hbWUgb2YgdGhlIHByb3BlcnR5LlxuICAgKiBAcGFyYW0gcHJvcGVydHlOYW1lIC0gVGhlIG5hbWUgb2YgdGhlIHByb3BlcnR5LlxuICAgKiBAcGFyYW0gdmFsdWUgLSBUaGUgdmFsdWUgdG8gc2V0LlxuICAgKiBAcmV0dXJucyBBIHtAbGluayBQcm9taXNlfSB0aGF0IHJlc29sdmVzIHRvIHRoZSB2YWxpZGF0aW9uIG1lc3NhZ2UuXG4gICAqL1xuICBwdWJsaWMgYXN5bmMgc2V0UHJvcGVydHk8UHJvcGVydHlOYW1lIGV4dGVuZHMgUHJvcGVydHlOYW1lczxQbHVnaW5TZXR0aW5ncz4+KFxuICAgIHByb3BlcnR5TmFtZTogUHJvcGVydHlOYW1lLFxuICAgIHZhbHVlOiBQbHVnaW5TZXR0aW5nc1tQcm9wZXJ0eU5hbWVdXG4gICk6IFByb21pc2U8c3RyaW5nPiB7XG4gICAgdGhpcy5lbnN1cmVMb2FkZWQoKTtcbiAgICBhd2FpdCB0aGlzLmVkaXQoKHNldHRpbmdzKSA9PiB7XG4gICAgICBzZXR0aW5nc1twcm9wZXJ0eU5hbWVdID0gdmFsdWU7XG4gICAgfSk7XG4gICAgcmV0dXJuIHRoaXMuY3VycmVudFN0YXRlLnZhbGlkYXRpb25NZXNzYWdlc1twcm9wZXJ0eU5hbWVdO1xuICB9XG5cbiAgLyoqXG4gICAqIFZhbGlkYXRlcyB0aGUgc2V0dGluZ3MuXG4gICAqXG4gICAqIEBwYXJhbSBzZXR0aW5ncyAtIFRoZSBzZXR0aW5ncy5cbiAgICogQHJldHVybnMgQSB7QGxpbmsgUHJvbWlzZX0gdGhhdCByZXNvbHZlcyB0byB0aGUgdmFsaWRhdGlvbiByZXN1bHQuXG4gICAqL1xuICBwdWJsaWMgYXN5bmMgdmFsaWRhdGUoc2V0dGluZ3M6IFBsdWdpblNldHRpbmdzKTogUHJvbWlzZTxWYWxpZGF0aW9uUmVzdWx0PFBsdWdpblNldHRpbmdzPj4ge1xuICAgIGNvbnN0IHJlc3VsdDogVmFsaWRhdGlvblJlc3VsdDxQbHVnaW5TZXR0aW5ncz4gPSB7fTtcbiAgICBmb3IgKGNvbnN0IFtwcm9wZXJ0eU5hbWUsIHZhbGlkYXRvcl0gb2YgdGhpcy52YWxpZGF0b3JzKSB7XG4gICAgICBjb25zdCB2YWxpZGF0aW9uTWVzc2FnZSA9IGF3YWl0IHZhbGlkYXRvcihzZXR0aW5nc1twcm9wZXJ0eU5hbWVdLCBzZXR0aW5ncyk7XG4gICAgICBpZiAodmFsaWRhdGlvbk1lc3NhZ2UpIHtcbiAgICAgICAgcmVzdWx0W3Byb3BlcnR5TmFtZV0gPSB2YWxpZGF0aW9uTWVzc2FnZTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICByZXR1cm4gcmVzdWx0O1xuICB9XG5cbiAgLyoqXG4gICAqIFdhaXRzIHVudGlsIHRoZSBzZXR0aW5ncyBoYXZlIGJlZW4gcmVhZCBmcm9tIGBkYXRhLmpzb25gIGF0IGxlYXN0IG9uY2UuXG4gICAqXG4gICAqIEFueXRoaW5nIHRoYXQgcmVhZHMgYSBzZXR0aW5nIGZyb20gb3V0c2lkZSB0aGlzIGNvbXBvbmVudCBoYXMgdG8gd2FpdCBmb3IgdGhpcywgYmVjYXVzZSB1bnRpbCB0aGUgZmlyc3RcbiAgICoge0BsaW5rIGxvYWRGcm9tRmlsZX0gY29tcGxldGVzIHtAbGluayBzZXR0aW5nc30gc3RpbGwgaG9sZHMgdGhlIERFRkFVTFRTIOKAlCByZWFkaW5nIGl0IGVhcmxpZXIgYW5zd2Vyc1xuICAgKiB3aXRoIGEgZGVmYXVsdCByYXRoZXIgdGhhbiB3aXRoIHdoYXQgdGhlIHVzZXIgYWN0dWFsbHkgc3RvcmVkLiBUaGF0IHdpbmRvdyBpcyBlYXN5IHRvIG1pc3MsIHNpbmNlIGl0IGlzXG4gICAqIGVtcHR5IG9uIGEgY29sZCBzdGFydCAodGhlIHdvcmtzcGFjZSBsYXlvdXQgaXMgbm90IHJlYWR5IHlldCwgc28gbm90aGluZyBoYXMgcnVuKSBidXQgd2lkZSBvcGVuIG9uIGFcbiAgICogcnVudGltZSBlbmFibGUgZnJvbSB0aGUgQ29tbXVuaXR5IFBsdWdpbnMgdGFiIG9yIGEgcmUtZW5hYmxlIGFmdGVyIGFuIHVwZGF0ZSwgd2hlcmUgYSBsYXlvdXQtcmVhZHlcbiAgICogaGFuZGxlciBmaXJlcyBpbW1lZGlhdGVseSB3aGlsZSB0aGlzIGNvbXBvbmVudCdzIG93biBhc3luYyBsb2FkIGlzIHN0aWxsIGluIGZsaWdodC5cbiAgICpcbiAgICogUmVzb2x2ZXMgaW1tZWRpYXRlbHkgb25jZSB0aGUgc2V0dGluZ3MgaGF2ZSBsb2FkZWQsIHNvIGEgY2FsbGVyIHRoYXQgYXJyaXZlcyBsYXRlIGlzIG5vdCBzdHJhbmRlZFxuICAgKiB3YWl0aW5nIGZvciBhbiBldmVudCB0aGF0IGhhcyBhbHJlYWR5IGJlZW4gcmFpc2VkLiBMYXRlciByZWxvYWRzIChhbiBleHRlcm5hbCBgZGF0YS5qc29uYCBjaGFuZ2UpIGRvXG4gICAqIG5vdCByZXNldCBpdCDigJQgdGhlIHF1ZXN0aW9uIGl0IGFuc3dlcnMgaXMgd2hldGhlciB0aGUgc2V0dGluZ3MgaGF2ZSBFVkVSIGJlZW4gcmVhZCwgbm90IHdoZXRoZXIgdGhlXG4gICAqIG1vc3QgcmVjZW50IHJlYWQgaGFzIGZpbmlzaGVkLlxuICAgKlxuICAgKiBAcmV0dXJucyBBIHtAbGluayBQcm9taXNlfSB0aGF0IHJlc29sdmVzIG9uY2UgdGhlIHNldHRpbmdzIGhhdmUgYmVlbiBsb2FkZWQgZnJvbSB0aGUgZmlsZS5cbiAgICovXG4gIHB1YmxpYyB3aGVuTG9hZGVkRnJvbUZpbGUoKTogUHJvbWlzZTx2b2lkPiB7XG4gICAgcmV0dXJuIHRoaXMuaXNMb2FkZWRGcm9tRmlsZVxuICAgICAgPyBub29wQXN5bmMoKVxuICAgICAgOiBuZXcgUHJvbWlzZTx2b2lkPigocmVzb2x2ZSkgPT4ge1xuICAgICAgICB0aGlzLmxvYWRlZEZyb21GaWxlUmVzb2x2ZXJzLnB1c2gocmVzb2x2ZSk7XG4gICAgICB9KTtcbiAgfVxuXG4gIC8qKlxuICAgKiBHZXRzIHRoZSB0cmFuc2Zvcm1lci5cbiAgICpcbiAgICogQHJldHVybnMgVGhlIHRyYW5zZm9ybWVyLlxuICAgKi9cbiAgcHJvdGVjdGVkIGdldFRyYW5zZm9ybWVyKCk6IFRyYW5zZm9ybWVyIHtcbiAgICByZXR1cm4gZGVmYXVsdFRyYW5zZm9ybWVyO1xuICB9XG5cbiAgLyoqXG4gICAqIENhbGxlZCB3aGVuIHRoZSBwbHVnaW4gc2V0dGluZ3MgcmVjb3JkIGlzIGxvYWRlZCBmcm9tIGRpc2suXG4gICAqXG4gICAqIEBwYXJhbSByZWNvcmQgLSBUaGUgcmVjb3JkLlxuICAgKi9cbiAgcHJvdGVjdGVkIGFzeW5jIG9uTG9hZFJlY29yZChyZWNvcmQ6IEdlbmVyaWNPYmplY3QpOiBQcm9taXNlPHZvaWQ+IHtcbiAgICBmb3IgKGNvbnN0IGNvbnZlcnRlciBvZiB0aGlzLmxlZ2FjeVNldHRpbmdzQ29udmVydGVycykge1xuICAgICAgY29udmVydGVyKHJlY29yZCk7XG4gICAgfVxuICAgIGF3YWl0IG5vb3BBc3luYygpO1xuICB9XG5cbiAgLyoqXG4gICAqIENhbGxlZCB3aGVuIHNldHRpbmdzIGFyZSBsb2FkZWQgb3IgcmVsb2FkZWQuXG4gICAqXG4gICAqIEBwYXJhbSBfbG9hZGVkU3RhdGUgLSBUaGUgbG9hZGVkIHNldHRpbmdzIHN0YXRlLlxuICAgKiBAcGFyYW0gX2lzSW5pdGlhbExvYWQgLSBXaGV0aGVyIHRoaXMgaXMgdGhlIGluaXRpYWwgbG9hZC5cbiAgICovXG4gIHByb3RlY3RlZCBhc3luYyBvbkxvYWRTZXR0aW5ncyhcbiAgICBfbG9hZGVkU3RhdGU6IFJlYWRvbmx5UGx1Z2luU2V0dGluZ3NTdGF0ZTxQbHVnaW5TZXR0aW5ncz4sXG4gICAgX2lzSW5pdGlhbExvYWQ6IGJvb2xlYW5cbiAgKTogUHJvbWlzZTx2b2lkPiB7XG4gICAgYXdhaXQgbm9vcEFzeW5jKCk7XG4gIH1cblxuICAvKipcbiAgICogQ2FsbGVkIHdoZW4gc2V0dGluZ3MgYXJlIHNhdmVkLlxuICAgKlxuICAgKiBAcGFyYW0gcGFyYW1zIC0gVGhlIHBhcmFtZXRlcnMuXG4gICAqL1xuICBwcm90ZWN0ZWQgYXN5bmMgb25TYXZlU2V0dGluZ3MocGFyYW1zOiBQbHVnaW5TZXR0aW5nc0NvbXBvbmVudEJhc2VPblNhdmVTZXR0aW5nc1BhcmFtczxQbHVnaW5TZXR0aW5ncz4pOiBQcm9taXNlPHZvaWQ+IHtcbiAgICBjb25zdCB7XG4gICAgICBjb250ZXh0OiBfY29udGV4dCxcbiAgICAgIG5ld1N0YXRlOiBfbmV3U3RhdGUsXG4gICAgICBvbGRTdGF0ZTogX29sZFN0YXRlXG4gICAgfSA9IHBhcmFtcztcbiAgICBhd2FpdCBub29wQXN5bmMoKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBDYWxsZWQgd2hlbiB0aGUgcGx1Z2luIHNldHRpbmdzIHJlY29yZCBpcyBhYm91dCB0byBiZSBzYXZlZCB0byBkaXNrLlxuICAgKlxuICAgKiBAcGFyYW0gX3JlY29yZCAtIFRoZSByZWNvcmQuXG4gICAqL1xuICBwcm90ZWN0ZWQgYXN5bmMgb25TYXZpbmdSZWNvcmQoX3JlY29yZDogR2VuZXJpY09iamVjdCk6IFByb21pc2U8dm9pZD4ge1xuICAgIGF3YWl0IG5vb3BBc3luYygpO1xuICB9XG5cbiAgLyoqXG4gICAqIFJlZ2lzdGVycyB0aGUgbGVnYWN5IHNldHRpbmdzIGNvbnZlcnRlcnMuXG4gICAqIE92ZXJyaWRlIHRvIHJlZ2lzdGVyIGxlZ2FjeSBzZXR0aW5ncyBjb252ZXJ0ZXJzLlxuICAgKi9cbiAgcHJvdGVjdGVkIHJlZ2lzdGVyTGVnYWN5U2V0dGluZ3NDb252ZXJ0ZXJzKCk6IHZvaWQge1xuICAgIG5vb3AoKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBSZWdpc3RlcnMgdGhlIHZhbGlkYXRvcnMuXG4gICAqIE92ZXJyaWRlIHRvIHJlZ2lzdGVyIHZhbGlkYXRvcnMgZm9yIHByb3BlcnRpZXMuXG4gICAqL1xuICBwcm90ZWN0ZWQgcmVnaXN0ZXJWYWxpZGF0b3JzKCk6IHZvaWQge1xuICAgIG5vb3AoKTtcbiAgfVxuXG4gIHByaXZhdGUgYXN5bmMgY2xvbmVTZXR0aW5ncyhzZXR0aW5nczogUGx1Z2luU2V0dGluZ3MpOiBQcm9taXNlPFBsdWdpblNldHRpbmdzPiB7XG4gICAgY29uc3QgcmVjb3JkID0gYXdhaXQgdGhpcy5zZXR0aW5nc1RvUmF3UmVjb3JkKHNldHRpbmdzKTtcbiAgICBjb25zdCBqc29uID0gSlNPTi5zdHJpbmdpZnkocmVjb3JkKTtcbiAgICBjb25zdCBjbG9uZVJlY29yZCA9IEpTT04ucGFyc2UoanNvbikgYXMgR2VuZXJpY09iamVjdDtcbiAgICByZXR1cm4gYXdhaXQgdGhpcy5yYXdSZWNvcmRUb1NldHRpbmdzKGNsb25lUmVjb3JkKTtcbiAgfVxuXG4gIHByaXZhdGUgYXN5bmMgY2xvbmVTdGF0ZShcbiAgICBzdGF0ZTogUGx1Z2luU2V0dGluZ3NTdGF0ZTxQbHVnaW5TZXR0aW5ncz5cbiAgKTogUHJvbWlzZTxQbHVnaW5TZXR0aW5nc1N0YXRlPFBsdWdpblNldHRpbmdzPj4ge1xuICAgIHJldHVybiB7XG4gICAgICBlZmZlY3RpdmVWYWx1ZXM6IGF3YWl0IHRoaXMuY2xvbmVTZXR0aW5ncyhzdGF0ZS5lZmZlY3RpdmVWYWx1ZXMpLFxuICAgICAgaW5wdXRWYWx1ZXM6IGF3YWl0IHRoaXMuY2xvbmVTZXR0aW5ncyhzdGF0ZS5pbnB1dFZhbHVlcyksXG4gICAgICB2YWxpZGF0aW9uTWVzc2FnZXM6IHsgLi4uc3RhdGUudmFsaWRhdGlvbk1lc3NhZ2VzIH1cbiAgICB9O1xuICB9XG5cbiAgcHJpdmF0ZSBjcmVhdGVEZWZhdWx0U3RhdGUoKTogUGx1Z2luU2V0dGluZ3NTdGF0ZTxQbHVnaW5TZXR0aW5ncz4ge1xuICAgIHJldHVybiB7XG4gICAgICBlZmZlY3RpdmVWYWx1ZXM6IG5ldyB0aGlzLnBsdWdpblNldHRpbmdzQ2xhc3MoKSxcbiAgICAgIGlucHV0VmFsdWVzOiBuZXcgdGhpcy5wbHVnaW5TZXR0aW5nc0NsYXNzKCksXG4gICAgICB2YWxpZGF0aW9uTWVzc2FnZXM6IGNhc3RUbzxSZWNvcmQ8UHJvcGVydHlOYW1lczxQbHVnaW5TZXR0aW5ncz4sIHN0cmluZz4+KHt9KVxuICAgIH07XG4gIH1cblxuICBwcml2YXRlIGFzeW5jIGVkaXQoc2V0dGluZ3NFZGl0b3I6IChzZXR0aW5nczogUGx1Z2luU2V0dGluZ3MpID0+IFByb21pc2FibGU8dm9pZD4pOiBQcm9taXNlPHZvaWQ+IHtcbiAgICB0cnkge1xuICAgICAgYXdhaXQgc2V0dGluZ3NFZGl0b3IodGhpcy5jdXJyZW50U3RhdGUuaW5wdXRWYWx1ZXMpO1xuICAgIH0gZmluYWxseSB7XG4gICAgICBjb25zdCB2YWxpZGF0aW9uUmVzdWx0ID0gYXdhaXQgdGhpcy52YWxpZGF0ZSh0aGlzLmN1cnJlbnRTdGF0ZS5pbnB1dFZhbHVlcyk7XG4gICAgICBmb3IgKGNvbnN0IHByb3BlcnR5TmFtZSBvZiB0aGlzLnByb3BlcnR5TmFtZXMpIHtcbiAgICAgICAgY29uc3QgdmFsaWRhdGlvbk1lc3NhZ2UgPSB2YWxpZGF0aW9uUmVzdWx0W3Byb3BlcnR5TmFtZV0gPz8gJyc7XG4gICAgICAgIHRoaXMuY3VycmVudFN0YXRlLnZhbGlkYXRpb25NZXNzYWdlc1twcm9wZXJ0eU5hbWVdID0gdmFsaWRhdGlvbk1lc3NhZ2U7XG4gICAgICAgIGNvbnN0IGRlZmF1bHRzID0gdGhpcy5kZWZhdWx0U2V0dGluZ3MgYXMgUGx1Z2luU2V0dGluZ3M7XG4gICAgICAgIHRoaXMuY3VycmVudFN0YXRlLmVmZmVjdGl2ZVZhbHVlc1twcm9wZXJ0eU5hbWVdID0gdmFsaWRhdGlvbk1lc3NhZ2VcbiAgICAgICAgICA/IGRlZmF1bHRzW3Byb3BlcnR5TmFtZV1cbiAgICAgICAgICA6IHRoaXMuY3VycmVudFN0YXRlLmlucHV0VmFsdWVzW3Byb3BlcnR5TmFtZV07XG4gICAgICB9XG4gICAgfVxuICB9XG5cbiAgcHJpdmF0ZSBpc1ZhbGlkUHJvcGVydHlOYW1lKHByb3BlcnR5OiB1bmtub3duKTogcHJvcGVydHkgaXMgUHJvcGVydHlOYW1lczxQbHVnaW5TZXR0aW5ncz4ge1xuICAgIHJldHVybiB0eXBlb2YgcHJvcGVydHkgPT09ICdzdHJpbmcnICYmICh0aGlzLnByb3BlcnR5TmFtZXMgYXMgc3RyaW5nW10pLmluY2x1ZGVzKHByb3BlcnR5KTtcbiAgfVxuXG4gIC8qKlxuICAgKiBLZWVwcyBhIHJlY292ZXJ5IGNvcHkgYmVmb3JlIHRoZSBpbml0aWFsIGxvYWQncyBub3JtYWxpemluZyBzYXZlLCB3aGVuIHRoYXQgc2F2ZSB3b3VsZCBkcm9wIG9yIGNoYW5nZSBhIHN0b3JlZFxuICAgKiB2YWx1ZTogYW4gdW5rbm93biBrZXkgKGEgbmV3ZXIgcGx1Z2luIHZlcnNpb24ncyBzZXR0aW5nKSwgYSBsZWdhY3kgbWlncmF0aW9uLCBhIHZhbHVlIHRoZSB0cmFuc2Zvcm1lciByZXdyaXRlcy5cbiAgICogQWRkaW5nIGRlZmF1bHRzIGZvciBrZXlzIHRoZSBmaWxlIGxhY2tzIGxvc2VzIG5vdGhpbmcgYW5kIGtlZXBzIG5vIGNvcHkuXG4gICAqXG4gICAqIEBwYXJhbSBvcmlnaW5hbEpzb24gLSBUaGUgcmVjb3JkIGFzIHRoZSBmaWxlIGhlbGQgaXQsIHNlcmlhbGl6ZWQgYmVmb3JlIGFueXRoaW5nIGNvdWxkIG11dGF0ZSBpdC5cbiAgICogQHBhcmFtIG5ld1JlY29yZCAtIFRoZSByZWNvcmQgYWJvdXQgdG8gYmUgc2F2ZWQuXG4gICAqIEByZXR1cm5zIFdoZXRoZXIgdGhlIHNhdmUgbWF5IGdvIGFoZWFkOiBub3RoaW5nIHdvdWxkIGJlIGxvc3QsIGEgY29weSB3YXMga2VwdCwgb3IgdGhlIGhhbmRsZXIga2VlcHMgbm8gY29waWVzLlxuICAgKi9cbiAgcHJpdmF0ZSBhc3luYyBrZWVwQ29weUJlZm9yZUxvc3N5UmV3cml0ZShvcmlnaW5hbEpzb246IHN0cmluZyB8IHVuZGVmaW5lZCwgbmV3UmVjb3JkOiBHZW5lcmljT2JqZWN0KTogUHJvbWlzZTxib29sZWFuPiB7XG4gICAgY29uc3QgcmVjb3ZlcnlTdG9yZSA9IHRoaXMuZGF0YUhhbmRsZXIucmVjb3ZlcnlTdG9yZTtcbiAgICBpZiAoIXJlY292ZXJ5U3RvcmUgfHwgb3JpZ2luYWxKc29uID09PSB1bmRlZmluZWQpIHtcbiAgICAgIHJldHVybiB0cnVlO1xuICAgIH1cbiAgICAvLyBgZGF0YS5qc29uYCBoZWxkIGFuIG9iamVjdCBvciBgbnVsbGAgaGVyZTogYW55dGhpbmcgZWxzZSB3YXMgcmVqZWN0ZWQgYmVmb3JlIHRoZSBzYXZlIHdhcyBjb25zaWRlcmVkLlxuICAgIGNvbnN0IG9yaWdpbmFsUmVjb3JkID0gSlNPTi5wYXJzZShvcmlnaW5hbEpzb24pIGFzIEdlbmVyaWNPYmplY3QgfCBudWxsO1xuICAgIGlmIChvcmlnaW5hbFJlY29yZCA9PT0gbnVsbCkge1xuICAgICAgcmV0dXJuIHRydWU7XG4gICAgfVxuICAgIGNvbnN0IGlzTG9zc3kgPSBPYmplY3Qua2V5cyhvcmlnaW5hbFJlY29yZCkuc29tZSgoa2V5KSA9PiAhT2JqZWN0Lmhhc093bihuZXdSZWNvcmQsIGtleSkgfHwgIWlzRGVlcEVxdWFsKG5ld1JlY29yZFtrZXldLCBvcmlnaW5hbFJlY29yZFtrZXldKSk7XG4gICAgaWYgKCFpc0xvc3N5KSB7XG4gICAgICByZXR1cm4gdHJ1ZTtcbiAgICB9XG5cbiAgICB0cnkge1xuICAgICAgYXdhaXQgcmVjb3ZlcnlTdG9yZS5rZWVwKHsgcGF0aDogJ2RhdGEuanNvbicsIHJhd1RleHQ6IG9yaWdpbmFsSnNvbiwgcmVhc29uOiBTZXR0aW5nc1JlY292ZXJ5UmVhc29uLkxvc3N5UmV3cml0ZSB9KTtcbiAgICAgIHJldHVybiB0cnVlO1xuICAgIH0gY2F0Y2ggKGVycm9yKSB7XG4gICAgICBjb25zb2xlLmVycm9yKG5ldyBFcnJvcignQ291bGQgbm90IGtlZXAgYSByZWNvdmVyeSBjb3B5IG9mIGRhdGEuanNvbiwgc28gdGhlIG5vcm1hbGl6ZWQgc2V0dGluZ3Mgd2VyZSBub3Qgc2F2ZWQgb3ZlciBpdC4nLCB7IGNhdXNlOiBlcnJvciB9KSk7XG4gICAgICByZXR1cm4gZmFsc2U7XG4gICAgfVxuICB9XG5cbiAgcHJpdmF0ZSBtYXJrTG9hZGVkRnJvbUZpbGUoKTogdm9pZCB7XG4gICAgdGhpcy5pc0xvYWRlZEZyb21GaWxlID0gdHJ1ZTtcbiAgICAvLyBEcmFpbmVkIHJhdGhlciB0aGFuIGl0ZXJhdGVkLCBzbyB0aGUgbGlzdCBkb2VzIG5vdCBrZWVwIGV2ZXJ5IHBhc3Qgd2FpdGVyIGFsaXZlIGFjcm9zcyByZWxvYWRzLlxuICAgIGNvbnN0IHJlc29sdmVycyA9IHRoaXMubG9hZGVkRnJvbUZpbGVSZXNvbHZlcnMuc3BsaWNlKDApO1xuICAgIGZvciAoY29uc3QgcmVzb2x2ZSBvZiByZXNvbHZlcnMpIHtcbiAgICAgIHJlc29sdmUoKTtcbiAgICB9XG4gIH1cblxuICBwcml2YXRlIGFzeW5jIHJhd1JlY29yZFRvU2V0dGluZ3MocmF3UmVjb3JkOiBHZW5lcmljT2JqZWN0KTogUHJvbWlzZTxQbHVnaW5TZXR0aW5ncz4ge1xuICAgIHJhd1JlY29yZCA9IHRoaXMuZ2V0VHJhbnNmb3JtZXIoKS50cmFuc2Zvcm1PYmplY3RSZWN1cnNpdmVseShyYXdSZWNvcmQpO1xuICAgIGF3YWl0IHRoaXMub25Mb2FkUmVjb3JkKHJhd1JlY29yZCk7XG5cbiAgICBjb25zdCBzZXR0aW5ncyA9IG5ldyB0aGlzLnBsdWdpblNldHRpbmdzQ2xhc3MoKTtcbiAgICBjb25zdCBkZWZhdWx0cyA9IHRoaXMuZGVmYXVsdFNldHRpbmdzIGFzIFBsdWdpblNldHRpbmdzO1xuXG4gICAgZm9yIChjb25zdCBbcHJvcGVydHlOYW1lLCB2YWx1ZV0gb2YgT2JqZWN0LmVudHJpZXMocmF3UmVjb3JkKSkge1xuICAgICAgaWYgKCF0aGlzLmlzVmFsaWRQcm9wZXJ0eU5hbWUocHJvcGVydHlOYW1lKSkge1xuICAgICAgICBnZXRPYnNpZGlhbkxpYkRlYnVnZ2VyKCdQbHVnaW5TZXR0aW5nc0NvbXBvbmVudEJhc2U6cmF3UmVjb3JkVG9TZXR0aW5ncycpKGBVbmtub3duIHByb3BlcnR5OiAke3Byb3BlcnR5TmFtZX1gKTtcbiAgICAgICAgY29udGludWU7XG4gICAgICB9XG5cbiAgICAgIC8vIEpTT04gY2Fubm90IGhvbGQgYHVuZGVmaW5lZGAsIHNvIG9ubHkgYSBsZWdhY3kgY29udmVydGVyIHByb2R1Y2VzIGl0LiBLZWVwIHRoZSBkZWZhdWx0IHJhdGhlciB0aGFuXG4gICAgICAvLyBsZXR0aW5nIGEgY29udmVydGVyIHRoYXQgYXNzaWduZWQgYSBrZXkgaXQgaGFkIG5vdGhpbmcgZm9yIHdpcGUgaXQgb3V0LlxuICAgICAgaWYgKHZhbHVlID09PSB1bmRlZmluZWQpIHtcbiAgICAgICAgY29udGludWU7XG4gICAgICB9XG5cbiAgICAgIGlmICh0eXBlb2YgdmFsdWUgIT09IHR5cGVvZiBkZWZhdWx0c1twcm9wZXJ0eU5hbWVdKSB7XG4gICAgICAgIGdldE9ic2lkaWFuTGliRGVidWdnZXIoJ1BsdWdpblNldHRpbmdzQ29tcG9uZW50QmFzZTpyYXdSZWNvcmRUb1NldHRpbmdzJykoXG4gICAgICAgICAgJ1Bvc3NpYmxlIGludmFsaWQgdmFsdWUgdHlwZS4gSXQgbWlnaHQgbGVhZCB0byBhbiB1bmV4cGVjdGVkIGJlaGF2aW9yIG9mIHRoZSBwbHVnaW4uIFRoZXJlIGlzIGFsc28gYSBjaGFuY2UgaXQgaXMgYSBmYWxzZS1uZWdhdGl2ZSB3YXJuaW5nLCBhcyB3ZSBhcmUgdW5hYmxlIHRvIGRldGVybWluZSB0aGUgZXhhY3QgdHlwZSBvZiB0aGUgdmFsdWUgaW4gcnVudGltZS4nLFxuICAgICAgICAgIHtcbiAgICAgICAgICAgIGRlZmF1bHRWYWx1ZTogZGVmYXVsdHNbcHJvcGVydHlOYW1lXSxcbiAgICAgICAgICAgIHByb3BlcnR5TmFtZSxcbiAgICAgICAgICAgIHZhbHVlXG4gICAgICAgICAgfVxuICAgICAgICApO1xuICAgICAgfVxuXG4gICAgICBzZXR0aW5nc1twcm9wZXJ0eU5hbWVdID0gdmFsdWUgYXMgUHJvcGVydHlWYWx1ZXM8UGx1Z2luU2V0dGluZ3M+O1xuICAgIH1cblxuICAgIHJldHVybiBzZXR0aW5ncztcbiAgfVxuXG4gIHByaXZhdGUgYXN5bmMgc2F2ZVRvRmlsZUltcGwoKTogUHJvbWlzZTx2b2lkPiB7XG4gICAgYXdhaXQgdGhpcy5kYXRhSGFuZGxlci5zYXZlRGF0YShhd2FpdCB0aGlzLnNldHRpbmdzVG9SYXdSZWNvcmQodGhpcy5jdXJyZW50U3RhdGUuaW5wdXRWYWx1ZXMpKTtcbiAgfVxuXG4gIHByaXZhdGUgc2V0UHJvcGVydHlJbXBsKHBhcmFtczogUGx1Z2luU2V0dGluZ3NDb21wb25lbnRCYXNlU2V0UHJvcGVydHlJbXBsUGFyYW1zPFBsdWdpblNldHRpbmdzPik6IHZvaWQge1xuICAgIGNvbnN0IHtcbiAgICAgIHByb3BlcnR5TmFtZSxcbiAgICAgIHZhbGlkYXRpb25NZXNzYWdlLFxuICAgICAgdmFsdWVcbiAgICB9ID0gcGFyYW1zO1xuICAgIGNvbnN0IGRlZmF1bHRzID0gdGhpcy5kZWZhdWx0U2V0dGluZ3MgYXMgUGx1Z2luU2V0dGluZ3M7XG4gICAgdGhpcy5jdXJyZW50U3RhdGUuaW5wdXRWYWx1ZXNbcHJvcGVydHlOYW1lXSA9IHZhbHVlO1xuICAgIHRoaXMuY3VycmVudFN0YXRlLnZhbGlkYXRpb25NZXNzYWdlc1twcm9wZXJ0eU5hbWVdID0gdmFsaWRhdGlvbk1lc3NhZ2UgPz8gJyc7XG4gICAgdGhpcy5jdXJyZW50U3RhdGUuZWZmZWN0aXZlVmFsdWVzW3Byb3BlcnR5TmFtZV0gPSB2YWxpZGF0aW9uTWVzc2FnZSA/IGRlZmF1bHRzW3Byb3BlcnR5TmFtZV0gOiB2YWx1ZTtcbiAgfVxuXG4gIHByaXZhdGUgYXN5bmMgc2V0dGluZ3NUb1Jhd1JlY29yZChzZXR0aW5nczogUGx1Z2luU2V0dGluZ3MpOiBQcm9taXNlPEdlbmVyaWNPYmplY3Q+IHtcbiAgICBjb25zdCByYXdSZWNvcmQ6IEdlbmVyaWNPYmplY3QgPSB7fTtcblxuICAgIGZvciAoY29uc3QgcHJvcGVydHlOYW1lIG9mIHRoaXMucHJvcGVydHlOYW1lcykge1xuICAgICAgcmF3UmVjb3JkW3Byb3BlcnR5TmFtZV0gPSBzZXR0aW5nc1twcm9wZXJ0eU5hbWVdO1xuICAgIH1cblxuICAgIGF3YWl0IHRoaXMub25TYXZpbmdSZWNvcmQocmF3UmVjb3JkKTtcblxuICAgIHJldHVybiB0aGlzLmdldFRyYW5zZm9ybWVyKCkudHJhbnNmb3JtT2JqZWN0UmVjdXJzaXZlbHkocmF3UmVjb3JkKTtcbiAgfVxufVxuIl0sIm1hcHBpbmdzIjoiOzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7OztBQTJCQSxTQUFTLG1CQUFtQjtBQUM1QjtBQUFBLEVBQ0U7QUFBQSxFQUNBO0FBQUEsT0FDSztBQUNQO0FBQUEsRUFDRTtBQUFBLEVBQ0E7QUFBQSxFQUNBO0FBQUEsT0FDSztBQUNQLFNBQVMsdUJBQXVCO0FBQ2hDLFNBQVMsd0JBQXdCO0FBQ2pDLFNB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