sonamu 0.10.11 → 0.10.13

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 (519) hide show
  1. package/dist/ai/agents/agent.d.ts +1 -1
  2. package/dist/ai/agents/agent.d.ts.map +1 -1
  3. package/dist/ai/agents/agent.js +5 -6
  4. package/dist/ai/agents/types.d.ts +1 -1
  5. package/dist/ai/agents/types.d.ts.map +1 -1
  6. package/dist/ai/providers/rtzr/api.js +18 -18
  7. package/dist/ai/providers/rtzr/error.d.ts.map +1 -1
  8. package/dist/ai/providers/rtzr/error.js +17 -15
  9. package/dist/ai/providers/rtzr/model.d.ts.map +1 -1
  10. package/dist/ai/providers/rtzr/model.js +3 -2
  11. package/dist/ai/providers/rtzr/options.d.ts.map +1 -1
  12. package/dist/ai/providers/rtzr/options.js +16 -16
  13. package/dist/ai/providers/rtzr/provider.d.ts.map +1 -1
  14. package/dist/ai/providers/rtzr/provider.js +9 -9
  15. package/dist/ai/providers/rtzr/utils.d.ts.map +1 -1
  16. package/dist/ai/providers/rtzr/utils.js +1 -1
  17. package/dist/api/caster.d.ts.map +1 -1
  18. package/dist/api/caster.js +17 -17
  19. package/dist/api/code-converters.d.ts +4 -2
  20. package/dist/api/code-converters.d.ts.map +1 -1
  21. package/dist/api/code-converters.js +100 -19
  22. package/dist/api/config.d.ts +16 -1
  23. package/dist/api/config.d.ts.map +1 -1
  24. package/dist/api/config.js +28 -21
  25. package/dist/api/context.d.ts +2 -2
  26. package/dist/api/context.d.ts.map +1 -1
  27. package/dist/api/context.js +1 -1
  28. package/dist/api/decorators.d.ts.map +1 -1
  29. package/dist/api/decorators.js +18 -11
  30. package/dist/api/http-validator.d.ts +36 -0
  31. package/dist/api/http-validator.d.ts.map +1 -0
  32. package/dist/api/http-validator.js +72 -0
  33. package/dist/api/index.js +6 -4
  34. package/dist/api/sonamu.d.ts +59 -20
  35. package/dist/api/sonamu.d.ts.map +1 -1
  36. package/dist/api/sonamu.js +250 -106
  37. package/dist/api/websocket-helpers.d.ts +7 -5
  38. package/dist/api/websocket-helpers.d.ts.map +1 -1
  39. package/dist/api/websocket-helpers.js +6 -6
  40. package/dist/auth/audit-log/builders.d.ts.map +1 -1
  41. package/dist/auth/audit-log/builders.js +1 -1
  42. package/dist/auth/audit-log/client-ip.d.ts +1 -1
  43. package/dist/auth/audit-log/client-ip.d.ts.map +1 -1
  44. package/dist/auth/audit-log/client-ip.js +4 -2
  45. package/dist/auth/audit-log/events.d.ts +5 -1
  46. package/dist/auth/audit-log/events.d.ts.map +1 -1
  47. package/dist/auth/audit-log/events.js +1 -1
  48. package/dist/auth/audit-log/plugin.d.ts +0 -8
  49. package/dist/auth/audit-log/plugin.d.ts.map +1 -1
  50. package/dist/auth/audit-log/plugin.js +48 -52
  51. package/dist/auth/audit-log-ingestor.d.ts.map +1 -1
  52. package/dist/auth/audit-log-ingestor.js +16 -12
  53. package/dist/auth/auth-generator.d.ts.map +1 -1
  54. package/dist/auth/auth-generator.js +1 -1
  55. package/dist/auth/better-auth-request.d.ts.map +1 -1
  56. package/dist/auth/better-auth-request.js +6 -5
  57. package/dist/auth/knex-adapter.js +1 -1
  58. package/dist/auth/plugins/entity-definitions/index.d.ts +13 -1
  59. package/dist/auth/plugins/entity-definitions/index.d.ts.map +1 -1
  60. package/dist/auth/plugins/entity-definitions/index.js +1 -1
  61. package/dist/auth/plugins/wrappers/admin.d.ts +1 -1
  62. package/dist/bin/build-config.d.ts +25 -0
  63. package/dist/bin/build-config.d.ts.map +1 -1
  64. package/dist/bin/build-config.js +105 -2
  65. package/dist/bin/cli.js +133 -29
  66. package/dist/bin/compiler-policy.d.ts +3 -0
  67. package/dist/bin/compiler-policy.d.ts.map +1 -0
  68. package/dist/bin/compiler-policy.js +24 -0
  69. package/dist/bin/fixture.d.ts.map +1 -1
  70. package/dist/bin/fixture.js +5 -3
  71. package/dist/bin/test-command.d.ts +22 -1
  72. package/dist/bin/test-command.d.ts.map +1 -1
  73. package/dist/bin/test-command.js +18 -10
  74. package/dist/bin/ts-loader-registration.d.ts +7 -1
  75. package/dist/bin/ts-loader-registration.d.ts.map +1 -1
  76. package/dist/bin/ts-loader-registration.js +13 -4
  77. package/dist/cache/decorator.d.ts.map +1 -1
  78. package/dist/cache/decorator.js +11 -4
  79. package/dist/compress/compress.d.ts.map +1 -1
  80. package/dist/compress/compress.js +1 -1
  81. package/dist/cone/cone-generator.d.ts +14 -1
  82. package/dist/cone/cone-generator.d.ts.map +1 -1
  83. package/dist/cone/cone-generator.js +13 -9
  84. package/dist/database/_batch_update.js +1 -1
  85. package/dist/database/base-model.d.ts +22 -10
  86. package/dist/database/base-model.d.ts.map +1 -1
  87. package/dist/database/base-model.js +26 -16
  88. package/dist/database/base-model.types.d.ts +15 -3
  89. package/dist/database/base-model.types.d.ts.map +1 -1
  90. package/dist/database/db.d.ts +12 -2
  91. package/dist/database/db.d.ts.map +1 -1
  92. package/dist/database/db.js +10 -7
  93. package/dist/database/knex.d.ts.map +1 -1
  94. package/dist/database/knex.js +17 -14
  95. package/dist/database/puri.d.ts +11 -9
  96. package/dist/database/puri.d.ts.map +1 -1
  97. package/dist/database/puri.js +93 -79
  98. package/dist/database/puri.types.d.ts +21 -21
  99. package/dist/database/puri.types.d.ts.map +1 -1
  100. package/dist/database/puri.types.js +1 -1
  101. package/dist/database/upsert-builder.d.ts +12 -10
  102. package/dist/database/upsert-builder.d.ts.map +1 -1
  103. package/dist/database/upsert-builder.js +20 -12
  104. package/dist/dict/sd.d.ts.map +1 -1
  105. package/dist/dict/sd.js +1 -1
  106. package/dist/dict/sonamu-dictionary.d.ts.map +1 -1
  107. package/dist/dict/sonamu-dictionary.js +1 -1
  108. package/dist/dict/utils.d.ts.map +1 -1
  109. package/dist/dict/utils.js +7 -2
  110. package/dist/entity/entity-manager.d.ts +13 -4
  111. package/dist/entity/entity-manager.d.ts.map +1 -1
  112. package/dist/entity/entity-manager.js +19 -11
  113. package/dist/entity/entity-template-cone.d.ts +73 -5
  114. package/dist/entity/entity-template-cone.d.ts.map +1 -1
  115. package/dist/entity/entity-template-cone.js +4 -2
  116. package/dist/entity/entity.d.ts +6 -2
  117. package/dist/entity/entity.d.ts.map +1 -1
  118. package/dist/entity/entity.js +30 -28
  119. package/dist/env.d.ts +3 -1
  120. package/dist/env.d.ts.map +1 -1
  121. package/dist/env.js +1 -1
  122. package/dist/exceptions/error-handler.d.ts.map +1 -1
  123. package/dist/exceptions/error-handler.js +7 -2
  124. package/dist/exceptions/so-exceptions.d.ts +24 -20
  125. package/dist/exceptions/so-exceptions.d.ts.map +1 -1
  126. package/dist/exceptions/so-exceptions.js +4 -2
  127. package/dist/filter/utils.d.ts +7 -2
  128. package/dist/filter/utils.d.ts.map +1 -1
  129. package/dist/filter/utils.js +8 -6
  130. package/dist/index.d.ts +3 -0
  131. package/dist/index.d.ts.map +1 -1
  132. package/dist/index.js +13 -7
  133. package/dist/logger/configure.d.ts.map +1 -1
  134. package/dist/logger/configure.js +10 -10
  135. package/dist/migration/code-generation.d.ts.map +1 -1
  136. package/dist/migration/code-generation.js +50 -46
  137. package/dist/migration/index-where-predicate.d.ts.map +1 -1
  138. package/dist/migration/index-where-predicate.js +22 -8
  139. package/dist/migration/migration-set.d.ts.map +1 -1
  140. package/dist/migration/migration-set.js +1 -1
  141. package/dist/migration/migrator.d.ts +61 -36
  142. package/dist/migration/migrator.d.ts.map +1 -1
  143. package/dist/migration/migrator.js +276 -167
  144. package/dist/migration/postgresql-schema-reader.d.ts.map +1 -1
  145. package/dist/migration/postgresql-schema-reader.js +51 -36
  146. package/dist/migration/slack-confirm.d.ts.map +1 -1
  147. package/dist/migration/slack-confirm.js +1 -1
  148. package/dist/migration/types.d.ts +54 -0
  149. package/dist/migration/types.d.ts.map +1 -1
  150. package/dist/naite/naite-reporter.js +2 -2
  151. package/dist/naite/naite.d.ts +74 -15
  152. package/dist/naite/naite.d.ts.map +1 -1
  153. package/dist/naite/naite.js +5 -19
  154. package/dist/runtime-type.d.ts +6 -0
  155. package/dist/runtime-type.d.ts.map +1 -0
  156. package/dist/runtime-type.js +26 -0
  157. package/dist/ssr/hmr-opt-out.d.ts +26 -0
  158. package/dist/ssr/hmr-opt-out.d.ts.map +1 -0
  159. package/dist/ssr/hmr-opt-out.js +59 -0
  160. package/dist/ssr/renderer.d.ts.map +1 -1
  161. package/dist/ssr/renderer.js +4 -1
  162. package/dist/storage/base-file.js +14 -14
  163. package/dist/storage/buffered-file.d.ts +2 -2
  164. package/dist/storage/buffered-file.d.ts.map +1 -1
  165. package/dist/storage/buffered-file.js +12 -12
  166. package/dist/storage/s3-driver.d.ts.map +1 -1
  167. package/dist/storage/s3-driver.js +1 -1
  168. package/dist/storage/uploaded-file.d.ts +2 -2
  169. package/dist/storage/uploaded-file.d.ts.map +1 -1
  170. package/dist/storage/uploaded-file.js +8 -8
  171. package/dist/stream/sse.js +11 -11
  172. package/dist/stream/ws-core.d.ts +1 -1
  173. package/dist/stream/ws-core.d.ts.map +1 -1
  174. package/dist/stream/ws-delivery.d.ts +1 -1
  175. package/dist/stream/ws-delivery.d.ts.map +1 -1
  176. package/dist/stream/ws-delivery.js +6 -4
  177. package/dist/stream/ws-local-connection-store.d.ts.map +1 -1
  178. package/dist/stream/ws-local-connection-store.js +4 -2
  179. package/dist/stream/ws-presence-store.js +1 -1
  180. package/dist/stream/ws-registry.d.ts +4 -4
  181. package/dist/stream/ws-registry.d.ts.map +1 -1
  182. package/dist/stream/ws-registry.js +4 -2
  183. package/dist/stream/ws-telemetry.d.ts +16 -12
  184. package/dist/stream/ws-telemetry.d.ts.map +1 -1
  185. package/dist/stream/ws-telemetry.js +22 -18
  186. package/dist/stream/ws.d.ts +18 -12
  187. package/dist/stream/ws.d.ts.map +1 -1
  188. package/dist/stream/ws.js +26 -22
  189. package/dist/syncer/api-parser.js +1 -1
  190. package/dist/syncer/checksum.d.ts.map +1 -1
  191. package/dist/syncer/checksum.js +7 -8
  192. package/dist/syncer/code-generator.d.ts.map +1 -1
  193. package/dist/syncer/code-generator.js +13 -14
  194. package/dist/syncer/entity-operations.d.ts.map +1 -1
  195. package/dist/syncer/entity-operations.js +5 -6
  196. package/dist/syncer/file-copy.d.ts +5 -0
  197. package/dist/syncer/file-copy.d.ts.map +1 -0
  198. package/dist/syncer/file-copy.js +36 -0
  199. package/dist/syncer/file-patterns.d.ts +1 -0
  200. package/dist/syncer/file-patterns.d.ts.map +1 -1
  201. package/dist/syncer/file-patterns.js +5 -2
  202. package/dist/syncer/file-tracking.d.ts.map +1 -1
  203. package/dist/syncer/file-tracking.js +5 -4
  204. package/dist/syncer/filesystem-dependencies.d.ts +15 -0
  205. package/dist/syncer/filesystem-dependencies.d.ts.map +1 -0
  206. package/dist/syncer/filesystem-dependencies.js +53 -0
  207. package/dist/syncer/module-loader.d.ts +1 -1
  208. package/dist/syncer/module-loader.d.ts.map +1 -1
  209. package/dist/syncer/module-loader.js +6 -4
  210. package/dist/syncer/syncer-actions.d.ts +4 -0
  211. package/dist/syncer/syncer-actions.d.ts.map +1 -1
  212. package/dist/syncer/syncer-actions.js +34 -17
  213. package/dist/syncer/syncer.d.ts +17 -6
  214. package/dist/syncer/syncer.d.ts.map +1 -1
  215. package/dist/syncer/syncer.js +71 -29
  216. package/dist/syncer/watcher.d.ts.map +1 -1
  217. package/dist/syncer/watcher.js +3 -3
  218. package/dist/tasks/decorator.d.ts +6 -6
  219. package/dist/tasks/decorator.d.ts.map +1 -1
  220. package/dist/tasks/decorator.js +4 -4
  221. package/dist/tasks/step-wrapper.d.ts +6 -4
  222. package/dist/tasks/step-wrapper.d.ts.map +1 -1
  223. package/dist/tasks/step-wrapper.js +5 -5
  224. package/dist/tasks/workflow-manager.d.ts.map +1 -1
  225. package/dist/tasks/workflow-manager.js +13 -7
  226. package/dist/template/entity-converter.d.ts +1 -1
  227. package/dist/template/entity-converter.d.ts.map +1 -1
  228. package/dist/template/entity-converter.js +2 -2
  229. package/dist/template/helpers.d.ts +8 -6
  230. package/dist/template/helpers.d.ts.map +1 -1
  231. package/dist/template/helpers.js +1 -1
  232. package/dist/template/implementations/generated.template.d.ts.map +1 -1
  233. package/dist/template/implementations/generated.template.js +4 -4
  234. package/dist/template/implementations/generated_http.template.d.ts +7 -4
  235. package/dist/template/implementations/generated_http.template.d.ts.map +1 -1
  236. package/dist/template/implementations/generated_http.template.js +21 -21
  237. package/dist/template/implementations/generated_sso.template.d.ts.map +1 -1
  238. package/dist/template/implementations/generated_sso.template.js +6 -3
  239. package/dist/template/implementations/http_validators.template.d.ts +18 -0
  240. package/dist/template/implementations/http_validators.template.d.ts.map +1 -0
  241. package/dist/template/implementations/http_validators.template.js +127 -0
  242. package/dist/template/implementations/model.template.d.ts.map +1 -1
  243. package/dist/template/implementations/model.template.js +1 -1
  244. package/dist/template/implementations/queries.template.js +1 -1
  245. package/dist/template/implementations/sd.template.d.ts.map +1 -1
  246. package/dist/template/implementations/sd.template.js +79 -39
  247. package/dist/template/implementations/services.template.d.ts.map +1 -1
  248. package/dist/template/implementations/services.template.js +6 -4
  249. package/dist/template/implementations/view_form.template.d.ts +6 -1
  250. package/dist/template/implementations/view_form.template.d.ts.map +1 -1
  251. package/dist/template/implementations/view_form.template.js +23 -15
  252. package/dist/template/implementations/view_list.template.d.ts.map +1 -1
  253. package/dist/template/implementations/view_list.template.js +11 -6
  254. package/dist/template/template-manager.d.ts.map +1 -1
  255. package/dist/template/template-manager.js +9 -7
  256. package/dist/template/template-types.d.ts +12 -5
  257. package/dist/template/template-types.d.ts.map +1 -1
  258. package/dist/template/template-types.js +1 -1
  259. package/dist/template/template.d.ts +2 -2
  260. package/dist/template/template.d.ts.map +1 -1
  261. package/dist/template/template.js +6 -4
  262. package/dist/template/zod-converter.d.ts +0 -19
  263. package/dist/template/zod-converter.d.ts.map +1 -1
  264. package/dist/template/zod-converter.js +100 -84
  265. package/dist/testing/_relation-graph.d.ts.map +1 -1
  266. package/dist/testing/_relation-graph.js +2 -1
  267. package/dist/testing/bootstrap.d.ts.map +1 -1
  268. package/dist/testing/bootstrap.js +9 -6
  269. package/dist/testing/data-explorer.d.ts +32 -7
  270. package/dist/testing/data-explorer.d.ts.map +1 -1
  271. package/dist/testing/data-explorer.js +77 -31
  272. package/dist/testing/dev-test-routes.d.ts +8 -1
  273. package/dist/testing/dev-test-routes.d.ts.map +1 -1
  274. package/dist/testing/dev-test-routes.js +125 -108
  275. package/dist/testing/dev-vitest-manager.d.ts +54 -8
  276. package/dist/testing/dev-vitest-manager.d.ts.map +1 -1
  277. package/dist/testing/dev-vitest-manager.js +24 -9
  278. package/dist/testing/faker-mappings.d.ts +412 -1
  279. package/dist/testing/faker-mappings.d.ts.map +1 -1
  280. package/dist/testing/faker-mappings.js +1 -1
  281. package/dist/testing/filesystem.d.ts +2 -0
  282. package/dist/testing/filesystem.d.ts.map +1 -0
  283. package/dist/testing/filesystem.js +7 -0
  284. package/dist/testing/fixture-generator.d.ts +25 -8
  285. package/dist/testing/fixture-generator.d.ts.map +1 -1
  286. package/dist/testing/fixture-generator.js +132 -73
  287. package/dist/testing/fixture-loader.d.ts +3 -1
  288. package/dist/testing/fixture-loader.d.ts.map +1 -1
  289. package/dist/testing/fixture-loader.js +1 -20
  290. package/dist/testing/fixture-manager.d.ts +8 -7
  291. package/dist/testing/fixture-manager.d.ts.map +1 -1
  292. package/dist/testing/fixture-manager.js +91 -59
  293. package/dist/testing/global-setup.d.ts.map +1 -1
  294. package/dist/testing/global-setup.js +5 -2
  295. package/dist/testing/index.d.ts +2 -0
  296. package/dist/testing/index.d.ts.map +1 -1
  297. package/dist/testing/index.js +6 -3
  298. package/dist/types/types.d.ts +101 -99
  299. package/dist/types/types.d.ts.map +1 -1
  300. package/dist/types/types.js +234 -225
  301. package/dist/ui/ai-api.d.ts.map +1 -1
  302. package/dist/ui/ai-api.js +1 -1
  303. package/dist/ui/ai-client.d.ts.map +1 -1
  304. package/dist/ui/ai-client.js +28 -18
  305. package/dist/ui/api.d.ts.map +1 -1
  306. package/dist/ui/api.js +146 -210
  307. package/dist/ui/async-route.d.ts +3 -0
  308. package/dist/ui/async-route.d.ts.map +1 -0
  309. package/dist/ui/async-route.js +12 -0
  310. package/dist/ui/cdd-service.d.ts +9 -7
  311. package/dist/ui/cdd-service.d.ts.map +1 -1
  312. package/dist/ui/cdd-service.js +7 -5
  313. package/dist/ui/migrations-api.d.ts +3 -0
  314. package/dist/ui/migrations-api.d.ts.map +1 -0
  315. package/dist/ui/migrations-api.js +215 -0
  316. package/dist/ui-web/assets/index-D3QNH-Dv.css +1 -0
  317. package/dist/ui-web/assets/index-DV1AAq6W.js +178 -0
  318. package/dist/ui-web/index.html +2 -2
  319. package/dist/utils/formatter.d.ts.map +1 -1
  320. package/dist/utils/formatter.js +7 -5
  321. package/dist/utils/fs-utils.d.ts +3 -3
  322. package/dist/utils/fs-utils.d.ts.map +1 -1
  323. package/dist/utils/fs-utils.js +6 -6
  324. package/dist/utils/model.d.ts +3 -5
  325. package/dist/utils/model.d.ts.map +1 -1
  326. package/dist/utils/model.js +1 -1
  327. package/dist/utils/object-utils.d.ts +1 -1
  328. package/dist/utils/object-utils.d.ts.map +1 -1
  329. package/dist/utils/object-utils.js +17 -16
  330. package/dist/utils/process-utils.d.ts.map +1 -1
  331. package/dist/utils/process-utils.js +4 -2
  332. package/dist/utils/runtime-value.d.ts +13 -0
  333. package/dist/utils/runtime-value.d.ts.map +1 -0
  334. package/dist/utils/runtime-value.js +40 -0
  335. package/dist/utils/sql-parser.d.ts +8 -1
  336. package/dist/utils/sql-parser.d.ts.map +1 -1
  337. package/dist/utils/sql-parser.js +6 -3
  338. package/dist/utils/type-utils.d.ts.map +1 -1
  339. package/dist/utils/type-utils.js +10 -8
  340. package/dist/utils/utils.d.ts +2 -2
  341. package/dist/utils/utils.d.ts.map +1 -1
  342. package/dist/utils/utils.js +11 -8
  343. package/dist/utils/zod-error.d.ts.map +1 -1
  344. package/dist/utils/zod-error.js +7 -4
  345. package/dist/vector/chunking.d.ts.map +1 -1
  346. package/dist/vector/chunking.js +1 -1
  347. package/dist/vector/embedding.d.ts.map +1 -1
  348. package/dist/vector/embedding.js +1 -1
  349. package/dist/vector/types.d.ts +3 -2
  350. package/dist/vector/types.d.ts.map +1 -1
  351. package/package.json +11 -7
  352. package/src/ai/agents/agent.ts +5 -5
  353. package/src/ai/agents/types.ts +1 -1
  354. package/src/ai/providers/rtzr/__tests__/model.test.ts +2 -2
  355. package/src/ai/providers/rtzr/error.ts +5 -3
  356. package/src/ai/providers/rtzr/model.ts +3 -2
  357. package/src/ai/providers/rtzr/options.ts +10 -5
  358. package/src/ai/providers/rtzr/provider.ts +10 -10
  359. package/src/ai/providers/rtzr/utils.ts +3 -1
  360. package/src/api/__tests__/config.test.ts +11 -21
  361. package/src/api/__tests__/sonamu.http-validator.test.ts +512 -0
  362. package/src/api/__tests__/sonamu.websocket.test.ts +51 -41
  363. package/src/api/__tests__/zod-compiler-policy.test.ts +95 -0
  364. package/src/api/caster.ts +6 -8
  365. package/src/api/code-converters.ts +136 -36
  366. package/src/api/config.ts +62 -4
  367. package/src/api/context.ts +3 -3
  368. package/src/api/decorators.ts +28 -17
  369. package/src/api/http-validator.ts +149 -0
  370. package/src/api/sonamu.ts +459 -152
  371. package/src/api/websocket-helpers.ts +24 -17
  372. package/src/auth/audit-log/builders.ts +3 -2
  373. package/src/auth/audit-log/client-ip.ts +4 -2
  374. package/src/auth/audit-log/events.ts +15 -1
  375. package/src/auth/audit-log/plugin.ts +129 -200
  376. package/src/auth/audit-log-ingestor.ts +19 -15
  377. package/src/auth/auth-generator.ts +10 -5
  378. package/src/auth/better-auth-request.ts +4 -3
  379. package/src/auth/knex-adapter.ts +8 -2
  380. package/src/auth/plugins/entity-definitions/index.ts +6 -5
  381. package/src/bin/__tests__/http-validator-benchmark.test.ts +94 -0
  382. package/src/bin/__tests__/test-command.test.ts +9 -15
  383. package/src/bin/__tests__/ts-loader-register.test.ts +15 -17
  384. package/src/bin/__tests__/zod-compiler-build.test.ts +307 -0
  385. package/src/bin/build-config.ts +167 -0
  386. package/src/bin/cli.ts +155 -38
  387. package/src/bin/compiler-policy.ts +35 -0
  388. package/src/bin/fixture.ts +14 -3
  389. package/src/bin/test-command.ts +74 -29
  390. package/src/bin/ts-loader-registration.ts +22 -4
  391. package/src/cache/decorator.ts +10 -3
  392. package/src/compress/compress.ts +17 -4
  393. package/src/cone/cone-generator.ts +34 -6
  394. package/src/database/__tests__/db.test.ts +1 -0
  395. package/src/database/__tests__/puri.test.ts +16 -15
  396. package/src/database/__tests__/transaction-scope.test.ts +5 -0
  397. package/src/database/_batch_update.ts +1 -0
  398. package/src/database/base-model.ts +81 -50
  399. package/src/database/base-model.types.ts +6 -6
  400. package/src/database/db.ts +29 -19
  401. package/src/database/knex.ts +30 -17
  402. package/src/database/puri-subset.test-d.ts +17 -0
  403. package/src/database/puri.ts +181 -143
  404. package/src/database/puri.types.test-d.ts +31 -1
  405. package/src/database/puri.types.ts +23 -21
  406. package/src/database/upsert-builder.ts +75 -53
  407. package/src/dict/sd.ts +15 -5
  408. package/src/dict/sonamu-dictionary.ts +6 -6
  409. package/src/dict/utils.ts +9 -1
  410. package/src/entity/entity-manager.ts +26 -9
  411. package/src/entity/entity-template-cone.ts +5 -10
  412. package/src/entity/entity.ts +50 -34
  413. package/src/env.ts +7 -3
  414. package/src/exceptions/error-handler.ts +17 -2
  415. package/src/exceptions/so-exceptions.ts +26 -20
  416. package/src/filter/utils.ts +21 -11
  417. package/src/index.ts +3 -0
  418. package/src/logger/configure.ts +26 -18
  419. package/src/migration/__tests__/migrator.test.ts +50 -57
  420. package/src/migration/code-generation.ts +132 -104
  421. package/src/migration/index-where-predicate.ts +51 -24
  422. package/src/migration/migration-set.ts +11 -5
  423. package/src/migration/migrator.ts +392 -244
  424. package/src/migration/postgresql-schema-reader.ts +52 -47
  425. package/src/migration/slack-confirm.ts +17 -15
  426. package/src/migration/types.ts +57 -0
  427. package/src/naite/naite-reporter.ts +1 -1
  428. package/src/naite/naite.ts +97 -24
  429. package/src/runtime-type.ts +34 -0
  430. package/src/ssr/hmr-opt-out.ts +78 -0
  431. package/src/ssr/renderer.ts +6 -0
  432. package/src/storage/base-file.ts +13 -13
  433. package/src/storage/buffered-file.ts +11 -11
  434. package/src/storage/s3-driver.ts +4 -1
  435. package/src/storage/uploaded-file.ts +8 -8
  436. package/src/stream/__tests__/ws-contracts.test.ts +4 -2
  437. package/src/stream/__tests__/ws-telemetry.test.ts +1 -1
  438. package/src/stream/__tests__/ws.test.ts +30 -6
  439. package/src/stream/sse.ts +12 -11
  440. package/src/stream/ws-core.ts +1 -1
  441. package/src/stream/ws-delivery.ts +16 -7
  442. package/src/stream/ws-local-connection-store.ts +2 -3
  443. package/src/stream/ws-presence-store.ts +6 -1
  444. package/src/stream/ws-registry.ts +16 -7
  445. package/src/stream/ws-telemetry.ts +66 -43
  446. package/src/stream/ws.ts +73 -39
  447. package/src/syncer/__tests__/api-parser.websocket-type-ref.test.ts +3 -2
  448. package/src/syncer/__tests__/http-validator-registry.test.ts +137 -0
  449. package/src/syncer/api-parser.ts +67 -27
  450. package/src/syncer/checksum.ts +17 -11
  451. package/src/syncer/code-generator.ts +25 -17
  452. package/src/syncer/entity-operations.ts +3 -5
  453. package/src/syncer/file-copy.ts +46 -0
  454. package/src/syncer/file-patterns.ts +11 -8
  455. package/src/syncer/file-tracking.ts +3 -4
  456. package/src/syncer/filesystem-dependencies.ts +73 -0
  457. package/src/syncer/module-loader.ts +8 -4
  458. package/src/syncer/syncer-actions.ts +56 -18
  459. package/src/syncer/syncer.ts +116 -43
  460. package/src/syncer/watcher.ts +8 -4
  461. package/src/tasks/decorator.ts +20 -12
  462. package/src/tasks/step-wrapper.ts +19 -9
  463. package/src/tasks/workflow-manager.ts +15 -9
  464. package/src/template/__tests__/http_validators.template.test.ts +160 -0
  465. package/src/template/__tests__/services.template.mutation.test.ts +24 -23
  466. package/src/template/__tests__/services.template.websocket.test.ts +21 -25
  467. package/src/template/entity-converter.ts +5 -2
  468. package/src/template/helpers.ts +8 -9
  469. package/src/template/implementations/generated.template.ts +5 -4
  470. package/src/template/implementations/generated_http.template.ts +61 -15
  471. package/src/template/implementations/generated_sso.template.ts +15 -4
  472. package/src/template/implementations/http_validators.template.ts +175 -0
  473. package/src/template/implementations/model.template.ts +3 -1
  474. package/src/template/implementations/sd.template.ts +81 -41
  475. package/src/template/implementations/services.template.ts +2 -2
  476. package/src/template/implementations/view_form.template.ts +56 -39
  477. package/src/template/implementations/view_list.template.ts +31 -23
  478. package/src/template/template-manager.ts +15 -13
  479. package/src/template/template-types.ts +13 -5
  480. package/src/template/template.ts +4 -3
  481. package/src/template/zod-converter.ts +206 -91
  482. package/src/testing/__tests__/dev-test-routes.test.ts +85 -25
  483. package/src/testing/__tests__/dev-vitest-manager.test.ts +15 -15
  484. package/src/testing/_relation-graph.ts +4 -1
  485. package/src/testing/bootstrap.ts +12 -5
  486. package/src/testing/data-explorer.ts +102 -53
  487. package/src/testing/dev-test-routes.ts +87 -50
  488. package/src/testing/dev-vitest-manager.ts +88 -32
  489. package/src/testing/faker-mappings.ts +2 -2
  490. package/src/testing/filesystem.ts +1 -0
  491. package/src/testing/fixture-generator.ts +191 -131
  492. package/src/testing/fixture-loader.ts +5 -1
  493. package/src/testing/fixture-manager.ts +129 -90
  494. package/src/testing/global-setup.ts +7 -3
  495. package/src/testing/index.ts +5 -0
  496. package/src/types/__tests__/entity-json-schema-search-text.test.ts +9 -3
  497. package/src/types/types.ts +184 -158
  498. package/src/ui/ai-api.ts +9 -7
  499. package/src/ui/ai-client.ts +61 -56
  500. package/src/ui/api.ts +726 -770
  501. package/src/ui/async-route.ts +4 -0
  502. package/src/ui/cdd-service.ts +35 -12
  503. package/src/ui/migrations-api.ts +381 -0
  504. package/src/utils/formatter.ts +7 -3
  505. package/src/utils/fs-utils.ts +5 -5
  506. package/src/utils/model.ts +4 -5
  507. package/src/utils/object-utils.ts +32 -22
  508. package/src/utils/process-utils.ts +4 -1
  509. package/src/utils/runtime-value.ts +43 -0
  510. package/src/utils/sql-parser.ts +13 -6
  511. package/src/utils/type-utils.ts +9 -7
  512. package/src/utils/utils.ts +19 -21
  513. package/src/utils/zod-error.ts +4 -2
  514. package/src/vector/chunking.ts +6 -1
  515. package/src/vector/embedding.ts +2 -1
  516. package/src/vector/types.ts +4 -2
  517. package/tsdown.api.config.ts +5 -2
  518. package/dist/ui-web/assets/index-CJf8uJYf.js +0 -176
  519. package/dist/ui-web/assets/index-GMMIVGja.css +0 -1
@@ -1,4 +1,5 @@
1
1
  import { __esmMin } from "../_virtual/_rolldown/runtime.js";
2
+ import { init_runtime_value, isFunctionValue, isNumberValue, isObjectValue, isStringValue } from "../utils/runtime-value.js";
2
3
  import { EntityManager, init_entity_manager } from "../entity/entity-manager.js";
3
4
  import { Naite, init_naite } from "../naite/naite.js";
4
5
  import { FUZZY_OPERATORS, init_puri_types } from "./puri.types.js";
@@ -6,7 +7,7 @@ import inflection from "inflection";
6
7
  import assert from "assert";
7
8
  import chalk from "chalk";
8
9
  //#region src/database/puri.ts
9
- function normalizeFuzzyOperator(operator) {
10
+ function parseFuzzyOperator(operator) {
10
11
  const normalized = operator?.trim() ?? "<%";
11
12
  const fuzzyOperator = FUZZY_OPERATORS.find((candidate) => candidate === normalized);
12
13
  if (!fuzzyOperator) throw new Error(`Invalid fuzzy operator: ${operator ?? ""}`);
@@ -38,12 +39,16 @@ function isOrderByEntries(value) {
38
39
  return Array.isArray(value);
39
40
  }
40
41
  function isSqlExpression(value) {
41
- return typeof value === "object" && "_type" in value && value._type === "sql_expression";
42
+ return isObjectValue(value) && "_type" in value && value["_type"] === "sql_expression";
43
+ }
44
+ function isNestedSelectObject(value) {
45
+ return isObjectValue(value) && !("_type" in value);
42
46
  }
43
47
  var Puri, WhereGroup, JoinClauseGroup, ResolvedPuri;
44
48
  var init_puri = __esmMin((() => {
45
49
  init_entity_manager();
46
50
  init_naite();
51
+ init_runtime_value();
47
52
  init_puri_types();
48
53
  Puri = class Puri {
49
54
  knex;
@@ -52,7 +57,7 @@ var init_puri = __esmMin((() => {
52
57
  correlationRegistry = /* @__PURE__ */ new Map();
53
58
  constructor(knex, tableNameOrSource) {
54
59
  this.knex = knex;
55
- if (typeof tableNameOrSource === "string") {
60
+ if (isStringValue(tableNameOrSource)) {
56
61
  this.knexQuery = this.knex(tableNameOrSource).from(tableNameOrSource);
57
62
  this.tableSpec = this.safeGetTableSpec(tableNameOrSource);
58
63
  this.correlationRegistry.set(tableNameOrSource, {
@@ -60,12 +65,12 @@ var init_puri = __esmMin((() => {
60
65
  alias: tableNameOrSource,
61
66
  table: tableNameOrSource
62
67
  });
63
- } else if (typeof tableNameOrSource === "object") {
68
+ } else if (isObjectValue(tableNameOrSource)) {
64
69
  const entries = Object.entries(tableNameOrSource);
65
70
  if (entries.length !== 1) throw new Error("Table spec must have exactly one entry");
66
71
  assert(entries[0]);
67
72
  const [alias, source] = entries[0];
68
- if (typeof source === "string") {
73
+ if (isStringValue(source)) {
69
74
  this.knexQuery = this.knex(source).from({ [alias]: source });
70
75
  this.tableSpec = this.safeGetTableSpec(source);
71
76
  this.correlationRegistry.set(alias, {
@@ -156,7 +161,7 @@ var init_puri = __esmMin((() => {
156
161
  };
157
162
  }
158
163
  static wordSimilarity(column, query) {
159
- if (typeof column === "string") return {
164
+ if (isStringValue(column)) return {
160
165
  _type: "sql_expression",
161
166
  _return: "number",
162
167
  _sql: "word_similarity(?, ??)",
@@ -165,12 +170,12 @@ var init_puri = __esmMin((() => {
165
170
  return {
166
171
  _type: "sql_expression",
167
172
  _return: "number",
168
- _sql: `word_similarity(?, ${column._sql})`,
169
- _params: [query, ...column._params]
173
+ _sql: `word_similarity(?, ${column["_sql"]})`,
174
+ _params: [query, ...column["_params"]]
170
175
  };
171
176
  }
172
177
  static similarity(column, query) {
173
- if (typeof column === "string") return {
178
+ if (isStringValue(column)) return {
174
179
  _type: "sql_expression",
175
180
  _return: "number",
176
181
  _sql: "similarity(??, ?)",
@@ -179,12 +184,12 @@ var init_puri = __esmMin((() => {
179
184
  return {
180
185
  _type: "sql_expression",
181
186
  _return: "number",
182
- _sql: `similarity(${column._sql}, ?)`,
183
- _params: [...column._params, query]
187
+ _sql: `similarity(${column["_sql"]}, ?)`,
188
+ _params: [...column["_params"], query]
184
189
  };
185
190
  }
186
191
  static strictWordSimilarity(column, query) {
187
- if (typeof column === "string") return {
192
+ if (isStringValue(column)) return {
188
193
  _type: "sql_expression",
189
194
  _return: "number",
190
195
  _sql: `strict_word_similarity(?, ??)`,
@@ -193,8 +198,8 @@ var init_puri = __esmMin((() => {
193
198
  return {
194
199
  _type: "sql_expression",
195
200
  _return: "number",
196
- _sql: `strict_word_similarity(?, ${column._sql})`,
197
- _params: [query, ...column._params]
201
+ _sql: `strict_word_similarity(?, ${column["_sql"]})`,
202
+ _params: [query, ...column["_params"]]
198
203
  };
199
204
  }
200
205
  static rawString(sql, params = []) {
@@ -268,10 +273,10 @@ var init_puri = __esmMin((() => {
268
273
  };
269
274
  }
270
275
  static tsRank(column, query, options) {
271
- return Puri._tsRank("ts_rank", column, query, options);
276
+ return Puri["_tsRank"]("ts_rank", column, query, options);
272
277
  }
273
278
  static tsRankCd(column, query, options) {
274
- return Puri._tsRank("ts_rank_cd", column, query, options);
279
+ return Puri["_tsRank"]("ts_rank_cd", column, query, options);
275
280
  }
276
281
  static toTsVector(column, config = "simple") {
277
282
  return {
@@ -289,12 +294,12 @@ var init_puri = __esmMin((() => {
289
294
  sqlTemplate += `ARRAY[${weights.map(() => "?").join(", ")}]::float4[], `;
290
295
  params.push(...weights);
291
296
  }
292
- if (typeof column === "string") {
297
+ if (isStringValue(column)) {
293
298
  sqlTemplate += `??, ${parser}(?, ?)`;
294
299
  params.push(column, config, query);
295
300
  } else {
296
- sqlTemplate += `${column._sql}, ${parser}(?, ?)`;
297
- params.push(...column._params, config, query);
301
+ sqlTemplate += `${column["_sql"]}, ${parser}(?, ?)`;
302
+ params.push(...column["_params"], config, query);
298
303
  }
299
304
  if (normalization) {
300
305
  sqlTemplate += ", ?";
@@ -322,13 +327,13 @@ var init_puri = __esmMin((() => {
322
327
  static highlight(columnOrColumns, query) {
323
328
  const queryArr = Array.isArray(query) ? query : [query];
324
329
  const queryClause = `ARRAY[${queryArr.map(() => "?").join(", ")}]`;
325
- if (typeof columnOrColumns === "string") return Puri.rawString(`pgroonga_highlight_html(??, ${queryClause})`, [columnOrColumns, ...queryArr]);
330
+ if (isStringValue(columnOrColumns)) return Puri.rawString(`pgroonga_highlight_html(??, ${queryClause})`, [columnOrColumns, ...queryArr]);
326
331
  return Puri.rawStringArray(`pgroonga_highlight_html(ARRAY[${columnOrColumns.map(() => "??").join(", ")}], ${queryClause})`, [...columnOrColumns, ...queryArr]);
327
332
  }
328
333
  select(selectObj) {
329
334
  const flatSelect = this.flattenSelect(selectObj);
330
335
  const selectClauses = [];
331
- for (const [alias, columnOrFunction] of Object.entries(flatSelect)) if (typeof columnOrFunction === "object" && columnOrFunction._type === "sql_expression") selectClauses.push(this.knex.raw(`${columnOrFunction._sql} AS "${alias}"`, columnOrFunction._params));
336
+ for (const [alias, columnOrFunction] of Object.entries(flatSelect)) if (isSqlExpression(columnOrFunction)) selectClauses.push(this.knex.raw(`${columnOrFunction["_sql"]} AS "${alias}"`, columnOrFunction["_params"]));
332
337
  else {
333
338
  const columnPath = columnOrFunction;
334
339
  if (alias === columnPath) selectClauses.push(columnPath);
@@ -342,21 +347,20 @@ var init_puri = __esmMin((() => {
342
347
  * 예: { parent: { id: "parent.id", name: "parent.name" } }
343
348
  * → { parent__id: "parent.id", parent__name: "parent.name" }
344
349
  */
345
- flattenSelect(selectObj, prefix = "") {
346
- const flatSelect = {};
350
+ *flattenSelectEntries(selectObj, prefix = "") {
347
351
  for (const [key, value] of Object.entries(selectObj)) {
348
352
  const fullKey = prefix ? `${prefix}__${key}` : key;
349
- if (typeof value === "object" && value !== null && !("_type" in value)) {
350
- const nested = this.flattenSelect(value, fullKey);
351
- Object.assign(flatSelect, nested);
352
- } else flatSelect[fullKey] = value;
353
+ if (isNestedSelectObject(value)) yield* this.flattenSelectEntries(value, fullKey);
354
+ else yield [fullKey, value];
353
355
  }
354
- return flatSelect;
356
+ }
357
+ flattenSelect(selectObj, prefix = "") {
358
+ return Object.fromEntries(this.flattenSelectEntries(selectObj, prefix));
355
359
  }
356
360
  appendSelect(selectObj) {
357
361
  const flatSelect = this.flattenSelect(selectObj);
358
362
  const selectClauses = [];
359
- for (const [alias, columnOrFunction] of Object.entries(flatSelect)) if (typeof columnOrFunction === "object" && columnOrFunction._type === "sql_expression") selectClauses.push(this.knex.raw(`${columnOrFunction._sql} AS ${alias}`, columnOrFunction._params));
363
+ for (const [alias, columnOrFunction] of Object.entries(flatSelect)) if (isSqlExpression(columnOrFunction)) selectClauses.push(this.knex.raw(`${columnOrFunction["_sql"]} AS ${alias}`, columnOrFunction["_params"]));
360
364
  else {
361
365
  const columnPath = columnOrFunction;
362
366
  if (alias === columnPath) selectClauses.push(columnPath);
@@ -380,7 +384,7 @@ var init_puri = __esmMin((() => {
380
384
  }
381
385
  clearJoin(alias) {
382
386
  let removed = false;
383
- this.knexQuery._statements = this.knexQuery._statements.filter((s) => {
387
+ this.knexQuery["_statements"] = this.knexQuery["_statements"].filter((s) => {
384
388
  if ("joinType" in s) {
385
389
  const shouldRemove = this.getKnexJoinAlias(s.table) === alias;
386
390
  removed ||= shouldRemove;
@@ -391,23 +395,23 @@ var init_puri = __esmMin((() => {
391
395
  return this;
392
396
  }
393
397
  join(tableNameOrSpec, ...args) {
394
- return this.__commonJoin("join", tableNameOrSpec, ...args);
398
+ return this["__commonJoin"]("join", tableNameOrSpec, ...args);
395
399
  }
396
400
  ensureJoin(tableNameOrSpec, left, right) {
397
- return this.__ensureJoin("join", tableNameOrSpec, left, right);
401
+ return this["__ensureJoin"]("join", tableNameOrSpec, left, right);
398
402
  }
399
403
  leftJoin(tableNameOrSpec, ...args) {
400
- return this.__commonJoin("leftJoin", tableNameOrSpec, ...args);
404
+ return this["__commonJoin"]("leftJoin", tableNameOrSpec, ...args);
401
405
  }
402
406
  ensureLeftJoin(tableNameOrSpec, left, right) {
403
- return this.__ensureJoin("leftJoin", tableNameOrSpec, left, right);
407
+ return this["__ensureJoin"]("leftJoin", tableNameOrSpec, left, right);
404
408
  }
405
409
  __commonJoin(joinType, tableNameOrSpec, ...args) {
406
410
  const registration = this.createJoinRegistration(joinType, tableNameOrSpec, args);
407
411
  this.assertCorrelationAvailable(registration);
408
- if (typeof tableNameOrSpec === "string") {
412
+ if (isStringValue(tableNameOrSpec)) {
409
413
  const tableName = tableNameOrSpec;
410
- if (args.length === 1 && typeof args[0] === "function") {
414
+ if (args.length === 1 && isFunctionValue(args[0])) {
411
415
  const callback = args[0];
412
416
  this.knexQuery[joinType](tableName, (joinClause) => {
413
417
  callback(new JoinClauseGroup(joinClause));
@@ -416,12 +420,12 @@ var init_puri = __esmMin((() => {
416
420
  const [left, right] = args;
417
421
  this.knexQuery[joinType](tableName, left, right);
418
422
  }
419
- } else if (typeof tableNameOrSpec === "object") {
423
+ } else if (isObjectValue(tableNameOrSpec)) {
420
424
  const entries = Object.entries(tableNameOrSpec);
421
425
  if (entries.length !== 1) throw new Error("Table spec must have exactly one entry");
422
426
  assert(entries[0]);
423
427
  const [[alias, spec]] = entries;
424
- if (typeof spec === "string") if (args.length === 1 && typeof args[0] === "function") {
428
+ if (isStringValue(spec)) if (args.length === 1 && isFunctionValue(args[0])) {
425
429
  const callback = args[0];
426
430
  this.knexQuery[joinType]({ [alias]: spec }, (joinClause) => {
427
431
  callback(new JoinClauseGroup(joinClause));
@@ -430,7 +434,7 @@ var init_puri = __esmMin((() => {
430
434
  const [left, right] = args;
431
435
  this.knexQuery[joinType]({ [alias]: spec }, left, right);
432
436
  }
433
- else if (spec instanceof Puri) if (args.length === 1 && typeof args[0] === "function") {
437
+ else if (spec instanceof Puri) if (args.length === 1 && isFunctionValue(args[0])) {
434
438
  const callback = args[0];
435
439
  this.knexQuery[joinType](spec.rawQuery().as(alias), (joinClause) => {
436
440
  callback(new JoinClauseGroup(joinClause));
@@ -448,26 +452,26 @@ var init_puri = __esmMin((() => {
448
452
  const requested = this.createJoinRegistration(joinType, tableNameOrSpec, [left, right]);
449
453
  if (!requested.reusable) throw new Error(`${joinType === "join" ? "ensureJoin" : "ensureLeftJoin"} only supports physical tables with simple column equality conditions.`);
450
454
  const existing = this.correlationRegistry.get(requested.alias);
451
- if (!existing) return this.__commonJoin(joinType, tableNameOrSpec, left, right);
455
+ if (!existing) return this["__commonJoin"](joinType, tableNameOrSpec, left, right);
452
456
  if (this.isSameJoinRegistration(existing, requested)) return this;
453
457
  throw this.createJoinConflictError(existing, requested);
454
458
  }
455
459
  createJoinRegistration(joinType, tableNameOrSpec, args) {
456
460
  let alias;
457
461
  let table;
458
- if (typeof tableNameOrSpec === "string") {
462
+ if (isStringValue(tableNameOrSpec)) {
459
463
  alias = tableNameOrSpec;
460
464
  table = tableNameOrSpec;
461
- } else if (typeof tableNameOrSpec === "object") {
465
+ } else if (isObjectValue(tableNameOrSpec)) {
462
466
  const entries = Object.entries(tableNameOrSpec);
463
467
  if (entries.length !== 1) throw new Error("Table spec must have exactly one entry");
464
468
  assert(entries[0]);
465
469
  const [[joinAlias, spec]] = entries;
466
470
  alias = joinAlias;
467
- table = typeof spec === "string" ? spec : null;
471
+ table = isStringValue(spec) ? spec : null;
468
472
  } else throw new Error("Invalid arguments");
469
473
  const [left, right] = args;
470
- const reusable = table !== null && args.length === 2 && typeof left === "string" && typeof right === "string";
474
+ const reusable = table !== null && args.length === 2 && isStringValue(left) && isStringValue(right);
471
475
  return {
472
476
  kind: "join",
473
477
  alias,
@@ -506,23 +510,23 @@ var init_puri = __esmMin((() => {
506
510
  for (const [alias, registration] of this.correlationRegistry) if (registration.kind === "join") this.correlationRegistry.delete(alias);
507
511
  }
508
512
  getKnexJoinAlias(table) {
509
- if (typeof table === "string") return table;
510
- if (typeof table === "object" && table !== null) {
511
- if ("_single" in table && typeof table._single === "object" && table._single !== null && "as" in table._single && typeof table._single.as === "string") return table._single.as;
513
+ if (isStringValue(table)) return table;
514
+ if (isObjectValue(table) && table !== null) {
515
+ if ("_single" in table && isObjectValue(table["_single"]) && table["_single"] !== null && "as" in table["_single"] && isStringValue(table["_single"].as)) return table["_single"].as;
512
516
  return Object.keys(table)[0] ?? null;
513
517
  }
514
518
  return null;
515
519
  }
516
520
  where(...args) {
517
521
  const [columnOrConditions, operatorOrValue, value] = args;
518
- if (typeof columnOrConditions === "object") this.knexQuery.where(columnOrConditions);
519
- else if (typeof value === "undefined") {
522
+ if (isObjectValue(columnOrConditions)) this.knexQuery.where(columnOrConditions);
523
+ else if (value === void 0) {
520
524
  if (operatorOrValue === null) {
521
525
  this.knexQuery.whereNull(columnOrConditions);
522
526
  return this;
523
527
  }
524
528
  this.knexQuery.where(columnOrConditions, operatorOrValue);
525
- } else if (typeof value !== "undefined") {
529
+ } else if (value !== void 0) {
526
530
  if (value === null) {
527
531
  if (operatorOrValue === "!=") {
528
532
  this.knexQuery.whereNotNull(columnOrConditions);
@@ -537,11 +541,19 @@ var init_puri = __esmMin((() => {
537
541
  return this;
538
542
  }
539
543
  whereIn(column, values) {
540
- this.knexQuery.whereIn(column, values);
544
+ if (values.length === 0) this.knexQuery.whereRaw("1 = 0");
545
+ else {
546
+ const placeholders = values.map(() => "?").join(", ");
547
+ this.knexQuery.whereRaw(`?? in (${placeholders})`, [String(column), ...values]);
548
+ }
541
549
  return this;
542
550
  }
543
551
  whereNotIn(column, values) {
544
- this.knexQuery.whereNotIn(column, values);
552
+ if (values.length === 0) this.knexQuery.whereRaw("1 = 1");
553
+ else {
554
+ const placeholders = values.map(() => "?").join(", ");
555
+ this.knexQuery.whereRaw(`?? not in (${placeholders})`, [String(column), ...values]);
556
+ }
545
557
  return this;
546
558
  }
547
559
  whereJsonSupersetOf(column, value) {
@@ -574,21 +586,21 @@ var init_puri = __esmMin((() => {
574
586
  return this;
575
587
  }
576
588
  whereTsSearch(column, value, options) {
577
- const opts = typeof options === "string" ? { config: options } : options ?? {};
589
+ const opts = isStringValue(options) ? { config: options } : options ?? {};
578
590
  const parser = opts.parser ?? "websearch_to_tsquery";
579
591
  const config = opts.config ?? "simple";
580
- const columnExpr = typeof column === "object" && column._type === "sql_expression" ? column._sql : String(column);
592
+ const columnExpr = isSqlExpression(column) && column["_type"] === "sql_expression" ? column["_sql"] : String(column);
581
593
  this.knexQuery.whereRaw(`${columnExpr} @@ ${parser}(?, ?)`, [config, value]);
582
594
  return this;
583
595
  }
584
596
  whereFuzzy(column, value, options) {
585
- const operator = normalizeFuzzyOperator(options?.operator);
597
+ const operator = parseFuzzyOperator(options?.operator);
586
598
  if (operator === "%") {
587
- if (typeof column === "object") this.knexQuery.whereRaw(`${column._sql} ${operator} ?`, [...column._params, value]);
599
+ if (isSqlExpression(column)) this.knexQuery.whereRaw(`${column["_sql"]} ${operator} ?`, [...column["_params"], value]);
588
600
  else this.knexQuery.whereRaw(`?? ${operator} ?`, [column, value]);
589
601
  return this;
590
602
  }
591
- if (typeof column === "object") this.knexQuery.whereRaw(`? ${operator} ${column._sql}`, [value, ...column._params]);
603
+ if (isSqlExpression(column)) this.knexQuery.whereRaw(`? ${operator} ${column["_sql"]}`, [value, ...column["_params"]]);
592
604
  else this.knexQuery.whereRaw(`? ${operator} ??`, [value, column]);
593
605
  return this;
594
606
  }
@@ -610,7 +622,7 @@ var init_puri = __esmMin((() => {
610
622
  }
611
623
  orderBy(columnOrColumns, direction = "asc", nulls) {
612
624
  if (isOrderByEntries(columnOrColumns)) {
613
- for (const entry of columnOrColumns) if (typeof entry === "string" || isSqlExpression(entry)) this.applyOrderBy(entry);
625
+ for (const entry of columnOrColumns) if (isStringValue(entry) || isSqlExpression(entry)) this.applyOrderBy(entry);
614
626
  else this.applyOrderBy(entry.column, entry.order, entry.nulls);
615
627
  return this;
616
628
  }
@@ -620,7 +632,7 @@ var init_puri = __esmMin((() => {
620
632
  applyOrderBy(column, direction, nulls) {
621
633
  const normalizedDirection = normalizeOrderByDirection(direction);
622
634
  const normalizedNulls = normalizeOrderByNulls(nulls);
623
- if (typeof column === "object") this.knexQuery.orderByRaw(`${column._sql} ${normalizedDirection}${formatNullsSuffix(normalizedNulls)}`, column._params);
635
+ if (isSqlExpression(column)) this.knexQuery.orderByRaw(`${column["_sql"]} ${normalizedDirection}${formatNullsSuffix(normalizedNulls)}`, column["_params"]);
624
636
  else this.knexQuery.orderBy(column, normalizedDirection, normalizedNulls);
625
637
  }
626
638
  forUpdate() {
@@ -677,7 +689,7 @@ var init_puri = __esmMin((() => {
677
689
  this.knexQuery.whereNotNull(column);
678
690
  this.knexQuery.clear("order");
679
691
  if (distinctOn) {
680
- const existingSubsetCols = this.knexQuery._statements.filter((s) => s.grouping === "columns").flatMap((s) => s.value);
692
+ const existingSubsetCols = this.knexQuery["_statements"].filter((s) => s.grouping === "columns").flatMap((s) => s.value);
681
693
  this.knexQuery.clear("select");
682
694
  this.knexQuery.select(this.knex.raw(`DISTINCT ON (??) ??`, [distinctOn, distinctOn]));
683
695
  existingSubsetCols.map((col) => this.knexQuery.select(col));
@@ -692,7 +704,7 @@ var init_puri = __esmMin((() => {
692
704
  this.knexQuery.select(similarityExpr);
693
705
  this.knexQuery.orderByRaw(`?? ${operator} ?::vector`, [column, vectorLiteral]);
694
706
  }
695
- if (typeof threshold === "number") {
707
+ if (isNumberValue(threshold)) {
696
708
  if (!Number.isFinite(threshold)) throw new Error(`Invalid vectorSimilarity threshold: ${threshold}`);
697
709
  if (distinctOn) {
698
710
  const thresholdOp = method === "l2" ? "<=" : ">=";
@@ -765,12 +777,12 @@ var init_puri = __esmMin((() => {
765
777
  if (!this.tableSpec || !this.tableSpec.jsonColumns.length) return data;
766
778
  const jsonColumns = this.tableSpec.jsonColumns;
767
779
  if (Array.isArray(data)) for (const item of data) for (const column of jsonColumns) {
768
- const value = item[column];
769
- if (value !== void 0 && value !== null) item[column] = serializeJsonColumnValue(this.tableSpec, column, value);
780
+ const value = Object.entries(item).find(([key]) => key === column)?.[1];
781
+ if (value !== void 0 && value !== null) Object.assign(item, { [column]: serializeJsonColumnValue(this.tableSpec, column, value) });
770
782
  }
771
783
  else for (const column of jsonColumns) {
772
- const value = data[column];
773
- if (value !== void 0 && value !== null) data[column] = serializeJsonColumnValue(this.tableSpec, column, value);
784
+ const value = Object.entries(data).find(([key]) => key === column)?.[1];
785
+ if (value !== void 0 && value !== null) Object.assign(data, { [column]: serializeJsonColumnValue(this.tableSpec, column, value) });
774
786
  }
775
787
  return data;
776
788
  }
@@ -950,40 +962,40 @@ var init_puri = __esmMin((() => {
950
962
  return this;
951
963
  }
952
964
  whereTsSearch(...args) {
953
- const opts = typeof args[2] === "string" ? { config: args[2] } : args[2] ?? {};
965
+ const opts = isStringValue(args[2]) ? { config: args[2] } : args[2] ?? {};
954
966
  const parser = opts.parser ?? "websearch_to_tsquery";
955
967
  const config = opts.config ?? "simple";
956
- const columnExpr = typeof args[0] === "object" && args[0]._type === "sql_expression" ? args[0]._sql : String(args[0]);
968
+ const columnExpr = isSqlExpression(args[0]) ? args[0]["_sql"] : String(args[0]);
957
969
  this.builder.whereRaw(`${columnExpr} @@ ${parser}(?, ?)`, [config, args[1]]);
958
970
  return this;
959
971
  }
960
972
  orWhereTsSearch(...args) {
961
- const opts = typeof args[2] === "string" ? { config: args[2] } : args[2] ?? {};
973
+ const opts = isStringValue(args[2]) ? { config: args[2] } : args[2] ?? {};
962
974
  const parser = opts.parser ?? "websearch_to_tsquery";
963
975
  const config = opts.config ?? "simple";
964
- const columnExpr = typeof args[0] === "object" && args[0]._type === "sql_expression" ? args[0]._sql : String(args[0]);
976
+ const columnExpr = isSqlExpression(args[0]) ? args[0]["_sql"] : String(args[0]);
965
977
  this.builder.orWhereRaw(`${columnExpr} @@ ${parser}(?, ?)`, [config, args[1]]);
966
978
  return this;
967
979
  }
968
980
  whereFuzzy(...args) {
969
- const operator = normalizeFuzzyOperator(args[2]?.operator);
981
+ const operator = parseFuzzyOperator(args[2]?.operator);
970
982
  if (operator === "%") {
971
- if (typeof args[0] === "object") this.builder.whereRaw(`${args[0]._sql} ${operator} ?`, [...args[0]._params, args[1]]);
983
+ if (isSqlExpression(args[0])) this.builder.whereRaw(`${args[0]["_sql"]} ${operator} ?`, [...args[0]["_params"], args[1]]);
972
984
  else this.builder.whereRaw(`?? ${operator} ?`, [args[0], args[1]]);
973
985
  return this;
974
986
  }
975
- if (typeof args[0] === "object") this.builder.whereRaw(`? ${operator} ${args[0]._sql}`, [args[1], ...args[0]._params]);
987
+ if (isSqlExpression(args[0])) this.builder.whereRaw(`? ${operator} ${args[0]["_sql"]}`, [args[1], ...args[0]["_params"]]);
976
988
  else this.builder.whereRaw(`? ${operator} ??`, [args[1], args[0]]);
977
989
  return this;
978
990
  }
979
991
  orWhereFuzzy(...args) {
980
- const operator = normalizeFuzzyOperator(args[2]?.operator);
992
+ const operator = parseFuzzyOperator(args[2]?.operator);
981
993
  if (operator === "%") {
982
- if (typeof args[0] === "object") this.builder.orWhereRaw(`${args[0]._sql} ${operator} ?`, [...args[0]._params, args[1]]);
994
+ if (isSqlExpression(args[0])) this.builder.orWhereRaw(`${args[0]["_sql"]} ${operator} ?`, [...args[0]["_params"], args[1]]);
983
995
  else this.builder.orWhereRaw(`?? ${operator} ?`, [args[0], args[1]]);
984
996
  return this;
985
997
  }
986
- if (typeof args[0] === "object") this.builder.orWhereRaw(`? ${operator} ${args[0]._sql}`, [args[1], ...args[0]._params]);
998
+ if (isSqlExpression(args[0])) this.builder.orWhereRaw(`? ${operator} ${args[0]["_sql"]}`, [args[1], ...args[0]["_params"]]);
987
999
  else this.builder.orWhereRaw(`? ${operator} ??`, [args[1], args[0]]);
988
1000
  return this;
989
1001
  }
@@ -1061,8 +1073,10 @@ var init_puri = __esmMin((() => {
1061
1073
  if (Array.isArray(update)) this.knexQuery.onConflict(target).merge(update);
1062
1074
  else {
1063
1075
  const mergeObj = {};
1064
- for (const [key, value] of Object.entries(update)) if (value && typeof value === "object" && "_type" in value && value._type === "sql_expression") mergeObj[key] = this.knex.raw(value._sql);
1065
- else mergeObj[key] = serializeJsonColumnValue(this.tableSpec, key, value);
1076
+ for (const [key, value] of Object.entries(update)) {
1077
+ const mergedValue = isSqlExpression(value) ? this.knex.raw(value["_sql"]) : serializeJsonColumnValue(this.tableSpec, key, value);
1078
+ Object.assign(mergeObj, { [key]: mergedValue });
1079
+ }
1066
1080
  this.knexQuery.onConflict(target).merge(mergeObj);
1067
1081
  }
1068
1082
  }
@@ -1076,6 +1090,6 @@ var init_puri = __esmMin((() => {
1076
1090
  }));
1077
1091
  //#endregion
1078
1092
  init_puri();
1079
- export { JoinClauseGroup, Puri, ResolvedPuri, WhereGroup, init_puri };
1093
+ export { JoinClauseGroup, Puri, ResolvedPuri, WhereGroup, init_puri, parseFuzzyOperator };
1080
1094
 
1081
- //# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoicHVyaS5qcyIsIm5hbWVzIjpbXSwic291cmNlcyI6WyIuLi8uLi9zcmMvZGF0YWJhc2UvcHVyaS50cyJdLCJzb3VyY2VzQ29udGVudCI6WyIvKiBveGxpbnQtZGlzYWJsZSBAdHlwZXNjcmlwdC1lc2xpbnQvbm8tZXhwbGljaXQtYW55ICovIC8vIFB1cmnripQg64uk7JaR7ZWcIO2DgOyeheydhCDsgqzsmqntlZjqs6Ag7J6I7Iq164uI64ukLlxuXG5pbXBvcnQgYXNzZXJ0IGZyb20gXCJhc3NlcnRcIjtcblxuaW1wb3J0IGNoYWxrIGZyb20gXCJjaGFsa1wiO1xuaW1wb3J0IGluZmxlY3Rpb24gZnJvbSBcImluZmxlY3Rpb25cIjtcbmltcG9ydCB7IHR5cGUgS25leCB9IGZyb20gXCJrbmV4XCI7XG5cbmltcG9ydCB7IEVudGl0eU1hbmFnZXIgfSBmcm9tIFwiLi4vZW50aXR5L2VudGl0eS1tYW5hZ2VyXCI7XG5pbXBvcnQgeyB0eXBlIFRhYmxlU3BlYyB9IGZyb20gXCIuLi9lbnRpdHkvZW50aXR5LW1hbmFnZXJcIjtcbmltcG9ydCB7IE5haXRlIH0gZnJvbSBcIi4uL25haXRlL25haXRlXCI7XG5pbXBvcnQgeyB0eXBlIENsZWFyU3RhdGVtZW50cyB9IGZyb20gXCIuL3B1cmktc3Vic2V0LnR5cGVzXCI7XG5pbXBvcnQge1xuICB0eXBlIEF2YWlsYWJsZUNvbHVtbnMsXG4gIHR5cGUgQ29sdW1uS2V5cyxcbiAgdHlwZSBDb21wYXJpc29uT3BlcmF0b3IsXG4gIHR5cGUgRXhwYW5kLFxuICB0eXBlIEV4dHJhY3RDb2x1bW5UeXBlLFxuICB0eXBlIEZ1bGx0ZXh0Q29sdW1ucyxcbiAgdHlwZSBGdXp6eU9wZXJhdG9yLFxuICB0eXBlIEluc2VydERhdGEsXG4gIHR5cGUgSW5zZXJ0UmVzdWx0LFxuICB0eXBlIEpzb25Db2x1bW5zLFxuICB0eXBlIEpzb25TdXBlcnNldFZhbHVlLFxuICB0eXBlIExlZnRKb2luZWRNYXJrZXIsXG4gIHR5cGUgTGVmdEpvaW5NYXJrZXJGb3IsXG4gIHR5cGUgTnVtZXJpY0NvbHVtbnMsXG4gIHR5cGUgT25Db25mbGljdEFjdGlvbixcbiAgdHlwZSBQYXJzZVNlbGVjdE9iamVjdCxcbiAgdHlwZSBSZXN1bHRBdmFpbGFibGVDb2x1bW5zLFxuICB0eXBlIFNlbGVjdEFsbFJlc3VsdCxcbiAgdHlwZSBTZWxlY3RPYmplY3QsXG4gIHR5cGUgU2luZ2xlVGFibGVWYWx1ZSxcbiAgdHlwZSBTcWxFeHByZXNzaW9uLFxuICB0eXBlIFRzSGlnaGxpZ2h0T3B0aW9ucyxcbiAgdHlwZSBUc1F1ZXJ5Q29uZmlnLFxuICB0eXBlIFRzUXVlcnlPcHRpb25zLFxuICB0eXBlIFRzUmFua09wdGlvbnMsXG4gIHR5cGUgVmVjdG9yQ29sdW1ucyxcbiAgdHlwZSBXaGVyZUNvbmRpdGlvbixcbiAgdHlwZSBXaGVyZU9wZXJhdG9yLFxufSBmcm9tIFwiLi9wdXJpLnR5cGVzXCI7XG5pbXBvcnQgeyBGVVpaWV9PUEVSQVRPUlMgfSBmcm9tIFwiLi9wdXJpLnR5cGVzXCI7XG5cbnR5cGUgUHVyaU9yZGVyQnlEaXJlY3Rpb24gPSBcImFzY1wiIHwgXCJkZXNjXCI7XG50eXBlIFB1cmlPcmRlckJ5TnVsbHMgPSBcImZpcnN0XCIgfCBcImxhc3RcIjtcbnR5cGUgUHVyaU9yZGVyQnlFeHByZXNzaW9uID0gU3FsRXhwcmVzc2lvbjxcIm51bWJlclwiPiB8IFNxbEV4cHJlc3Npb248XCJzdHJpbmdcIj47XG50eXBlIFB1cmlPcmRlckJ5SXRlbTxUQ29sdW1uIGV4dGVuZHMgc3RyaW5nPiA9IHtcbiAgY29sdW1uOiBUQ29sdW1uIHwgUHVyaU9yZGVyQnlFeHByZXNzaW9uO1xuICBvcmRlcj86IFB1cmlPcmRlckJ5RGlyZWN0aW9uO1xuICBudWxscz86IFB1cmlPcmRlckJ5TnVsbHM7XG59O1xudHlwZSBQdXJpT3JkZXJCeUVudHJ5PFRDb2x1bW4gZXh0ZW5kcyBzdHJpbmc+ID1cbiAgfCBUQ29sdW1uXG4gIHwgUHVyaU9yZGVyQnlFeHByZXNzaW9uXG4gIHwgUHVyaU9yZGVyQnlJdGVtPFRDb2x1bW4+O1xudHlwZSBQdXJpT3JkZXJCeVJ1bnRpbWVJdGVtID0ge1xuICBjb2x1bW46IHN0cmluZyB8IFB1cmlPcmRlckJ5RXhwcmVzc2lvbjtcbiAgb3JkZXI/OiBQdXJpT3JkZXJCeURpcmVjdGlvbjtcbiAgbnVsbHM/OiBQdXJpT3JkZXJCeU51bGxzO1xufTtcbnR5cGUgUHVyaU9yZGVyQnlSdW50aW1lRW50cnkgPSBzdHJpbmcgfCBQdXJpT3JkZXJCeUV4cHJlc3Npb24gfCBQdXJpT3JkZXJCeVJ1bnRpbWVJdGVtO1xuXG50eXBlIEZyb21SZWdpc3RyYXRpb24gPSB7XG4gIGtpbmQ6IFwiZnJvbVwiO1xuICBhbGlhczogc3RyaW5nO1xuICB0YWJsZTogc3RyaW5nIHwgbnVsbDtcbn07XG5cbnR5cGUgSm9pblJlZ2lzdHJhdGlvbiA9IHtcbiAga2luZDogXCJqb2luXCI7XG4gIGFsaWFzOiBzdHJpbmc7XG4gIHRhYmxlOiBzdHJpbmcgfCBudWxsO1xuICBqb2luVHlwZTogXCJqb2luXCIgfCBcImxlZnRKb2luXCI7XG4gIGxlZnQ6IHN0cmluZyB8IG51bGw7XG4gIHJpZ2h0OiBzdHJpbmcgfCBudWxsO1xuICByZXVzYWJsZTogYm9vbGVhbjtcbn07XG5cbnR5cGUgQ29ycmVsYXRpb25SZWdpc3RyYXRpb24gPSBGcm9tUmVnaXN0cmF0aW9uIHwgSm9pblJlZ2lzdHJhdGlvbjtcblxuZnVuY3Rpb24gbm9ybWFsaXplRnV6enlPcGVyYXRvcihvcGVyYXRvcj86IHN0cmluZyk6IEZ1enp5T3BlcmF0b3Ige1xuICBjb25zdCBub3JtYWxpemVkID0gb3BlcmF0b3I/LnRyaW0oKSA/PyBcIjwlXCI7XG4gIGNvbnN0IGZ1enp5T3BlcmF0b3IgPSBGVVpaWV9PUEVSQVRPUlMuZmluZCgoY2FuZGlkYXRlKSA9PiBjYW5kaWRhdGUgPT09IG5vcm1hbGl6ZWQpO1xuXG4gIGlmICghZnV6enlPcGVyYXRvcikge1xuICAgIHRocm93IG5ldyBFcnJvcihgSW52YWxpZCBmdXp6eSBvcGVyYXRvcjogJHtvcGVyYXRvciA/PyBcIlwifWApO1xuICB9XG5cbiAgcmV0dXJuIGZ1enp5T3BlcmF0b3I7XG59XG5cbmZ1bmN0aW9uIHNlcmlhbGl6ZUpzb25TdXBlcnNldFZhbHVlKHZhbHVlOiB1bmtub3duKTogc3RyaW5nIHtcbiAgY29uc3Qgc2VyaWFsaXplZCA9IEpTT04uc3RyaW5naWZ5KHZhbHVlKTtcblxuICBpZiAoc2VyaWFsaXplZCA9PT0gdW5kZWZpbmVkKSB7XG4gICAgdGhyb3cgbmV3IFR5cGVFcnJvcihcbiAgICAgIFwiUHVyaSBKU09OQiBjb250YWlubWVudCB2YWx1ZSBtdXN0IGJlIEpTT04tc2VyaWFsaXphYmxlOyBKU09OLnN0cmluZ2lmeSByZXR1cm5lZCB1bmRlZmluZWQuXCIsXG4gICAgKTtcbiAgfVxuXG4gIHJldHVybiBzZXJpYWxpemVkO1xufVxuXG5mdW5jdGlvbiBzZXJpYWxpemVKc29uQ29sdW1uVmFsdWUoXG4gIHRhYmxlU3BlYzogVGFibGVTcGVjIHwgbnVsbCxcbiAgY29sdW1uOiBzdHJpbmcsXG4gIHZhbHVlOiB1bmtub3duLFxuKTogdW5rbm93biB7XG4gIGlmICghdGFibGVTcGVjPy5qc29uQ29sdW1ucy5pbmNsdWRlcyhjb2x1bW4pIHx8IHZhbHVlID09PSB1bmRlZmluZWQgfHwgdmFsdWUgPT09IG51bGwpIHtcbiAgICByZXR1cm4gdmFsdWU7XG4gIH1cblxuICByZXR1cm4gSlNPTi5zdHJpbmdpZnkodmFsdWUpO1xufVxuXG5mdW5jdGlvbiBub3JtYWxpemVPcmRlckJ5RGlyZWN0aW9uKGRpcmVjdGlvbjogUHVyaU9yZGVyQnlEaXJlY3Rpb24gPSBcImFzY1wiKTogUHVyaU9yZGVyQnlEaXJlY3Rpb24ge1xuICBpZiAoZGlyZWN0aW9uICE9PSBcImFzY1wiICYmIGRpcmVjdGlvbiAhPT0gXCJkZXNjXCIpIHtcbiAgICB0aHJvdyBuZXcgRXJyb3IoYEludmFsaWQgb3JkZXIgZGlyZWN0aW9uOiAke2RpcmVjdGlvbn1gKTtcbiAgfVxuXG4gIHJldHVybiBkaXJlY3Rpb247XG59XG5cbmZ1bmN0aW9uIG5vcm1hbGl6ZU9yZGVyQnlOdWxscyhudWxscz86IFB1cmlPcmRlckJ5TnVsbHMpOiBQdXJpT3JkZXJCeU51bGxzIHwgdW5kZWZpbmVkIHtcbiAgaWYgKG51bGxzID09PSB1bmRlZmluZWQpIHtcbiAgICByZXR1cm4gdW5kZWZpbmVkO1xuICB9XG5cbiAgaWYgKG51bGxzICE9PSBcImZpcnN0XCIgJiYgbnVsbHMgIT09IFwibGFzdFwiKSB7XG4gICAgdGhyb3cgbmV3IEVycm9yKGBJbnZhbGlkIG9yZGVyIG51bGxzOiAke251bGxzfWApO1xuICB9XG5cbiAgcmV0dXJuIG51bGxzO1xufVxuXG5mdW5jdGlvbiBmb3JtYXROdWxsc1N1ZmZpeChudWxscz86IFB1cmlPcmRlckJ5TnVsbHMpOiBzdHJpbmcge1xuICBpZiAoIW51bGxzKSB7XG4gICAgcmV0dXJuIFwiXCI7XG4gIH1cblxuICByZXR1cm4gYCBOVUxMUyAke251bGxzLnRvVXBwZXJDYXNlKCl9YDtcbn1cblxuZnVuY3Rpb24gaXNPcmRlckJ5RW50cmllcyh2YWx1ZTogdW5rbm93bik6IHZhbHVlIGlzIHJlYWRvbmx5IFB1cmlPcmRlckJ5UnVudGltZUVudHJ5W10ge1xuICByZXR1cm4gQXJyYXkuaXNBcnJheSh2YWx1ZSk7XG59XG5cbmZ1bmN0aW9uIGlzU3FsRXhwcmVzc2lvbih2YWx1ZTogUHVyaU9yZGVyQnlSdW50aW1lRW50cnkpOiB2YWx1ZSBpcyBQdXJpT3JkZXJCeUV4cHJlc3Npb24ge1xuICByZXR1cm4gdHlwZW9mIHZhbHVlID09PSBcIm9iamVjdFwiICYmIFwiX3R5cGVcIiBpbiB2YWx1ZSAmJiB2YWx1ZS5fdHlwZSA9PT0gXCJzcWxfZXhwcmVzc2lvblwiO1xufVxuXG5leHBvcnQgY2xhc3MgUHVyaTxUU2NoZW1hLCBUVGFibGVzIGV4dGVuZHMgUmVjb3JkPHN0cmluZywgYW55PiwgVFJlc3VsdD4ge1xuICBwcml2YXRlIGtuZXhRdWVyeTogS25leC5RdWVyeUJ1aWxkZXI7XG4gIHByaXZhdGUgdGFibGVTcGVjOiBUYWJsZVNwZWMgfCBudWxsID0gbnVsbDtcbiAgcHJpdmF0ZSBjb3JyZWxhdGlvblJlZ2lzdHJ5ID0gbmV3IE1hcDxzdHJpbmcsIENvcnJlbGF0aW9uUmVnaXN0cmF0aW9uPigpO1xuXG4gIC8vIOyDneyEseyekCDsi5zqt7jri4jsspjrk6RcbiAgY29uc3RydWN0b3Ioa25leDogS25leCwgdGFibGVOYW1lOiBzdHJpbmcpO1xuICBjb25zdHJ1Y3RvcihrbmV4OiBLbmV4LCB0YWJsZVNvdXJjZTogUmVjb3JkPHN0cmluZywgc3RyaW5nIHwgUHVyaTxUU2NoZW1hLCBhbnksIGFueT4+KTtcbiAgY29uc3RydWN0b3IoXG4gICAgcHVibGljIGtuZXg6IEtuZXgsXG4gICAgdGFibGVOYW1lT3JTb3VyY2U6IGFueSxcbiAgKSB7XG4gICAgaWYgKHR5cGVvZiB0YWJsZU5hbWVPclNvdXJjZSA9PT0gXCJzdHJpbmdcIikge1xuICAgICAgLy8gQ2FzZTogbmV3IFB1cmkoa25leCwgXCJ1c2Vyc1wiKVxuICAgICAgdGhpcy5rbmV4UXVlcnkgPSB0aGlzLmtuZXgodGFibGVOYW1lT3JTb3VyY2UpLmZyb20odGFibGVOYW1lT3JTb3VyY2UpO1xuICAgICAgdGhpcy50YWJsZVNwZWMgPSB0aGlzLnNhZmVHZXRUYWJsZVNwZWModGFibGVOYW1lT3JTb3VyY2UpO1xuICAgICAgdGhpcy5jb3JyZWxhdGlvblJlZ2lzdHJ5LnNldCh0YWJsZU5hbWVPclNvdXJjZSwge1xuICAgICAgICBraW5kOiBcImZyb21cIixcbiAgICAgICAgYWxpYXM6IHRhYmxlTmFtZU9yU291cmNlLFxuICAgICAgICB0YWJsZTogdGFibGVOYW1lT3JTb3VyY2UsXG4gICAgICB9KTtcbiAgICB9IGVsc2UgaWYgKHR5cGVvZiB0YWJsZU5hbWVPclNvdXJjZSA9PT0gXCJvYmplY3RcIikge1xuICAgICAgY29uc3QgZW50cmllcyA9IE9iamVjdC5lbnRyaWVzKHRhYmxlTmFtZU9yU291cmNlKTtcbiAgICAgIGlmIChlbnRyaWVzLmxlbmd0aCAhPT0gMSkge1xuICAgICAgICB0aHJvdyBuZXcgRXJyb3IoXCJUYWJsZSBzcGVjIG11c3QgaGF2ZSBleGFjdGx5IG9uZSBlbnRyeVwiKTtcbiAgICAgIH1cbiAgICAgIGFzc2VydChlbnRyaWVzWzBdKTtcbiAgICAgIGNvbnN0IFthbGlhcywgc291cmNlXSA9IGVudHJpZXNbMF07XG4gICAgICBpZiAodHlwZW9mIHNvdXJjZSA9PT0gXCJzdHJpbmdcIikge1xuICAgICAgICB0aGlzLmtuZXhRdWVyeSA9IHRoaXMua25leChzb3VyY2UpLmZyb20oeyBbYWxpYXNdOiBzb3VyY2UgfSk7XG4gICAgICAgIHRoaXMudGFibGVTcGVjID0gdGhpcy5zYWZlR2V0VGFibGVTcGVjKHNvdXJjZSk7XG4gICAgICAgIHRoaXMuY29ycmVsYXRpb25SZWdpc3RyeS5zZXQoYWxpYXMsIHsga2luZDogXCJmcm9tXCIsIGFsaWFzLCB0YWJsZTogc291cmNlIH0pO1xuICAgICAgfSBlbHNlIGlmIChzb3VyY2UgaW5zdGFuY2VvZiBQdXJpKSB7XG4gICAgICAgIGNvbnN0IHN1YnF1ZXJ5QnVpbGRlciA9IHNvdXJjZS5yYXdRdWVyeSgpO1xuICAgICAgICB0aGlzLmtuZXhRdWVyeSA9IHRoaXMua25leC5mcm9tKHN1YnF1ZXJ5QnVpbGRlci5hcyhhbGlhcykpO1xuICAgICAgICB0aGlzLmNvcnJlbGF0aW9uUmVnaXN0cnkuc2V0KGFsaWFzLCB7IGtpbmQ6IFwiZnJvbVwiLCBhbGlhcywgdGFibGU6IG51bGwgfSk7XG4gICAgICB9IGVsc2Uge1xuICAgICAgICB0aHJvdyBuZXcgRXJyb3IoXCJJbnZhbGlkIHRhYmxlIHNwZWNpZmljYXRpb25cIik7XG4gICAgICB9XG4gICAgfSBlbHNlIHtcbiAgICAgIHRocm93IG5ldyBFcnJvcihcIkludmFsaWQgdGFibGUgc3BlY2lmaWNhdGlvblwiKTtcbiAgICB9XG4gIH1cblxuICBzYWZlR2V0VGFibGVTcGVjKHRhYmxlTmFtZTogc3RyaW5nKTogVGFibGVTcGVjIHwgbnVsbCB7XG4gICAgdHJ5IHtcbiAgICAgIHJldHVybiBFbnRpdHlNYW5hZ2VyLmdldFRhYmxlU3BlYyh0YWJsZU5hbWUpO1xuICAgIH0gY2F0Y2gge1xuICAgICAgcmV0dXJuIG51bGw7XG4gICAgfVxuICB9XG5cbiAgLy8gU3RhdGljIFNRTCBoZWxwZXIgZnVuY3Rpb25zIGZvciBTRUxFQ1RcbiAgc3RhdGljIGNvdW50KGNvbHVtbjogc3RyaW5nID0gXCIqXCIpOiBTcWxFeHByZXNzaW9uPFwibnVtYmVyXCI+IHtcbiAgICByZXR1cm4ge1xuICAgICAgX3R5cGU6IFwic3FsX2V4cHJlc3Npb25cIixcbiAgICAgIF9yZXR1cm46IFwibnVtYmVyXCIsXG4gICAgICBfc3FsOiBgQ09VTlQoPz8pOjppbnRlZ2VyYCxcbiAgICAgIF9wYXJhbXM6IFtjb2x1bW5dLFxuICAgIH07XG4gIH1cbiAgc3RhdGljIHN1bShjb2x1bW46IHN0cmluZyk6IFNxbEV4cHJlc3Npb248XCJudW1iZXJcIj4ge1xuICAgIHJldHVybiB7XG4gICAgICBfdHlwZTogXCJzcWxfZXhwcmVzc2lvblwiLFxuICAgICAgX3JldHVybjogXCJudW1iZXJcIixcbiAgICAgIF9zcWw6IGBTVU0oPz8pYCxcbiAgICAgIF9wYXJhbXM6IFtjb2x1bW5dLFxuICAgIH07XG4gIH1cbiAgc3RhdGljIGF2Zyhjb2x1bW46IHN0cmluZyk6IFNxbEV4cHJlc3Npb248XCJudW1iZXJcIj4ge1xuICAgIHJldHVybiB7XG4gICAgICBfdHlwZTogXCJzcWxfZXhwcmVzc2lvblwiLFxuICAgICAgX3JldHVybjogXCJudW1iZXJcIixcbiAgICAgIF9zcWw6IGBBVkcoPz8pYCxcbiAgICAgIF9wYXJhbXM6IFtjb2x1bW5dLFxuICAgIH07XG4gIH1cbiAgc3RhdGljIG1heChjb2x1bW46IHN0cmluZyk6IFNxbEV4cHJlc3Npb248XCJudW1iZXJcIj4ge1xuICAgIHJldHVybiB7XG4gICAgICBfdHlwZTogXCJzcWxfZXhwcmVzc2lvblwiLFxuICAgICAgX3JldHVybjogXCJudW1iZXJcIixcbiAgICAgIF9zcWw6IGBNQVgoPz8pYCxcbiAgICAgIF9wYXJhbXM6IFtjb2x1bW5dLFxuICAgIH07XG4gIH1cbiAgc3RhdGljIG1pbihjb2x1bW46IHN0cmluZyk6IFNxbEV4cHJlc3Npb248XCJudW1iZXJcIj4ge1xuICAgIHJldHVybiB7XG4gICAgICBfdHlwZTogXCJzcWxfZXhwcmVzc2lvblwiLFxuICAgICAgX3JldHVybjogXCJudW1iZXJcIixcbiAgICAgIF9zcWw6IGBNSU4oPz8pYCxcbiAgICAgIF9wYXJhbXM6IFtjb2x1bW5dLFxuICAgIH07XG4gIH1cbiAgc3RhdGljIGNvbmNhdCguLi5hcmdzOiBzdHJpbmdbXSk6IFNxbEV4cHJlc3Npb248XCJzdHJpbmdcIj4ge1xuICAgIHJldHVybiB7XG4gICAgICBfdHlwZTogXCJzcWxfZXhwcmVzc2lvblwiLFxuICAgICAgX3JldHVybjogXCJzdHJpbmdcIixcbiAgICAgIF9zcWw6IGBDT05DQVQoJHthcmdzLm1hcCgoKSA9PiBcIj9cIikuam9pbihcIiwgXCIpfSlgLFxuICAgICAgX3BhcmFtczogYXJncyxcbiAgICB9O1xuICB9XG4gIHN0YXRpYyB1cHBlcihjb2x1bW46IHN0cmluZyk6IFNxbEV4cHJlc3Npb248XCJzdHJpbmdcIj4ge1xuICAgIHJldHVybiB7XG4gICAgICBfdHlwZTogXCJzcWxfZXhwcmVzc2lvblwiLFxuICAgICAgX3JldHVybjogXCJzdHJpbmdcIixcbiAgICAgIF9zcWw6IFwiVVBQRVIoPz8pXCIsXG4gICAgICBfcGFyYW1zOiBbY29sdW1uXSxcbiAgICB9O1xuICB9XG4gIHN0YXRpYyBsb3dlcihjb2x1bW46IHN0cmluZyk6IFNxbEV4cHJlc3Npb248XCJzdHJpbmdcIj4ge1xuICAgIHJldHVybiB7XG4gICAgICBfdHlwZTogXCJzcWxfZXhwcmVzc2lvblwiLFxuICAgICAgX3JldHVybjogXCJzdHJpbmdcIixcbiAgICAgIF9zcWw6IFwiTE9XRVIoPz8pXCIsXG4gICAgICBfcGFyYW1zOiBbY29sdW1uXSxcbiAgICB9O1xuICB9XG5cbiAgc3RhdGljIHdvcmRTaW1pbGFyaXR5KFxuICAgIGNvbHVtbjogc3RyaW5nIHwgU3FsRXhwcmVzc2lvbjxcInN0cmluZ1wiPixcbiAgICBxdWVyeTogc3RyaW5nLFxuICApOiBTcWxFeHByZXNzaW9uPFwibnVtYmVyXCI+IHtcbiAgICBpZiAodHlwZW9mIGNvbHVtbiA9PT0gXCJzdHJpbmdcIikge1xuICAgICAgcmV0dXJuIHtcbiAgICAgICAgX3R5cGU6IFwic3FsX2V4cHJlc3Npb25cIixcbiAgICAgICAgX3JldHVybjogXCJudW1iZXJcIixcbiAgICAgICAgX3NxbDogXCJ3b3JkX3NpbWlsYXJpdHkoPywgPz8pXCIsXG4gICAgICAgIF9wYXJhbXM6IFtxdWVyeSwgY29sdW1uXSxcbiAgICAgIH07XG4gICAgfVxuXG4gICAgcmV0dXJuIHtcbiAgICAgIF90eXBlOiBcInNxbF9leHByZXNzaW9uXCIsXG4gICAgICBfcmV0dXJuOiBcIm51bWJlclwiLFxuICAgICAgX3NxbDogYHdvcmRfc2ltaWxhcml0eSg/LCAke2NvbHVtbi5fc3FsfSlgLFxuICAgICAgX3BhcmFtczogW3F1ZXJ5LCAuLi5jb2x1bW4uX3BhcmFtc10sXG4gICAgfTtcbiAgfVxuXG4gIHN0YXRpYyBzaW1pbGFyaXR5KFxuICAgIGNvbHVtbjogc3RyaW5nIHwgU3FsRXhwcmVzc2lvbjxcInN0cmluZ1wiPixcbiAgICBxdWVyeTogc3RyaW5nLFxuICApOiBTcWxFeHByZXNzaW9uPFwibnVtYmVyXCI+IHtcbiAgICBpZiAodHlwZW9mIGNvbHVtbiA9PT0gXCJzdHJpbmdcIikge1xuICAgICAgcmV0dXJuIHtcbiAgICAgICAgX3R5cGU6IFwic3FsX2V4cHJlc3Npb25cIixcbiAgICAgICAgX3JldHVybjogXCJudW1iZXJcIixcbiAgICAgICAgX3NxbDogXCJzaW1pbGFyaXR5KD8/LCA/KVwiLFxuICAgICAgICBfcGFyYW1zOiBbY29sdW1uLCBxdWVyeV0sXG4gICAgICB9O1xuICAgIH1cblxuICAgIHJldHVybiB7XG4gICAgICBfdHlwZTogXCJzcWxfZXhwcmVzc2lvblwiLFxuICAgICAgX3JldHVybjogXCJudW1iZXJcIixcbiAgICAgIF9zcWw6IGBzaW1pbGFyaXR5KCR7Y29sdW1uLl9zcWx9LCA/KWAsXG4gICAgICBfcGFyYW1zOiBbLi4uY29sdW1uLl9wYXJhbXMsIHF1ZXJ5XSxcbiAgICB9O1xuICB9XG5cbiAgc3RhdGljIHN0cmljdFdvcmRTaW1pbGFyaXR5KFxuICAgIGNvbHVtbjogc3RyaW5nIHwgU3FsRXhwcmVzc2lvbjxcInN0cmluZ1wiPixcbiAgICBxdWVyeTogc3RyaW5nLFxuICApOiBTcWxFeHByZXNzaW9uPFwibnVtYmVyXCI+IHtcbiAgICBpZiAodHlwZW9mIGNvbHVtbiA9PT0gXCJzdHJpbmdcIikge1xuICAgICAgcmV0dXJuIHtcbiAgICAgICAgX3R5cGU6IFwic3FsX2V4cHJlc3Npb25cIixcbiAgICAgICAgX3JldHVybjogXCJudW1iZXJcIixcbiAgICAgICAgX3NxbDogYHN0cmljdF93b3JkX3NpbWlsYXJpdHkoPywgPz8pYCxcbiAgICAgICAgX3BhcmFtczogW3F1ZXJ5LCBjb2x1bW5dLFxuICAgICAgfTtcbiAgICB9XG5cbiAgICByZXR1cm4ge1xuICAgICAgX3R5cGU6IFwic3FsX2V4cHJlc3Npb25cIixcbiAgICAgIF9yZXR1cm46IFwibnVtYmVyXCIsXG4gICAgICBfc3FsOiBgc3RyaWN0X3dvcmRfc2ltaWxhcml0eSg/LCAke2NvbHVtbi5fc3FsfSlgLFxuICAgICAgX3BhcmFtczogW3F1ZXJ5LCAuLi5jb2x1bW4uX3BhcmFtc10sXG4gICAgfTtcbiAgfVxuXG4gIC8vIFJhdyBmdW5jdGlvbnMgZm9yIFNFTEVDVFxuICBzdGF0aWMgcmF3U3RyaW5nKHNxbDogc3RyaW5nLCBwYXJhbXM6IEtuZXguUmF3QmluZGluZ1tdID0gW10pOiBTcWxFeHByZXNzaW9uPFwic3RyaW5nXCI+IHtcbiAgICByZXR1cm4geyBfdHlwZTogXCJzcWxfZXhwcmVzc2lvblwiLCBfcmV0dXJuOiBcInN0cmluZ1wiLCBfc3FsOiBzcWwsIF9wYXJhbXM6IHBhcmFtcyB9O1xuICB9XG5cbiAgc3RhdGljIHJhd1N0cmluZ0FycmF5KHNxbDogc3RyaW5nLCBwYXJhbXM6IEtuZXguUmF3QmluZGluZ1tdID0gW10pOiBTcWxFeHByZXNzaW9uPFwic3RyaW5nW11cIj4ge1xuICAgIHJldHVybiB7IF90eXBlOiBcInNxbF9leHByZXNzaW9uXCIsIF9yZXR1cm46IFwic3RyaW5nW11cIiwgX3NxbDogc3FsLCBfcGFyYW1zOiBwYXJhbXMgfTtcbiAgfVxuXG4gIHN0YXRpYyByYXdOdW1iZXIoc3FsOiBzdHJpbmcsIHBhcmFtczogS25leC5SYXdCaW5kaW5nW10gPSBbXSk6IFNxbEV4cHJlc3Npb248XCJudW1iZXJcIj4ge1xuICAgIHJldHVybiB7IF90eXBlOiBcInNxbF9leHByZXNzaW9uXCIsIF9yZXR1cm46IFwibnVtYmVyXCIsIF9zcWw6IHNxbCwgX3BhcmFtczogcGFyYW1zIH07XG4gIH1cblxuICBzdGF0aWMgcmF3Qm9vbGVhbihzcWw6IHN0cmluZywgcGFyYW1zOiBLbmV4LlJhd0JpbmRpbmdbXSA9IFtdKTogU3FsRXhwcmVzc2lvbjxcImJvb2xlYW5cIj4ge1xuICAgIHJldHVybiB7IF90eXBlOiBcInNxbF9leHByZXNzaW9uXCIsIF9yZXR1cm46IFwiYm9vbGVhblwiLCBfc3FsOiBzcWwsIF9wYXJhbXM6IHBhcmFtcyB9O1xuICB9XG5cbiAgc3RhdGljIHJhd0RhdGUoc3FsOiBzdHJpbmcsIHBhcmFtczogS25leC5SYXdCaW5kaW5nW10gPSBbXSk6IFNxbEV4cHJlc3Npb248XCJkYXRlXCI+IHtcbiAgICByZXR1cm4geyBfdHlwZTogXCJzcWxfZXhwcmVzc2lvblwiLCBfcmV0dXJuOiBcImRhdGVcIiwgX3NxbDogc3FsLCBfcGFyYW1zOiBwYXJhbXMgfTtcbiAgfVxuXG4gIC8qKlxuICAgKiBGVFMg6rKA7IOJ7Ja0IO2VmOydtOudvOydtO2MhVxuICAgKlxuICAgKiBAZXhhbXBsZVxuICAgKiAuc2VsZWN0KHtcbiAgICogICB0aXRsZTogUHVyaS5oaWdobGlnaHQoXCJwb3N0cy50aXRsZVwiLCBzZWFyY2gpLFxuICAgKiAgIGNvbnRlbnQ6IFB1cmkuaGlnaGxpZ2h0KFwicG9zdHMuY29udGVudFwiLCBzZWFyY2gsIHtcbiAgICogICAgIHN0YXJ0U2VsOiBcIjxtYXJrPlwiLFxuICAgKiAgICAgc3RvcFNlbDogXCI8L21hcms+XCIsXG4gICAqICAgICBtYXhGcmFnbWVudHM6IDMsXG4gICAqICAgfSksXG4gICAqIH0pXG4gICAqL1xuICBzdGF0aWMgdHNIaWdobGlnaHQoXG4gICAgY29sdW1uOiBzdHJpbmcsXG4gICAgcXVlcnk6IHN0cmluZyxcbiAgICBfb3B0aW9ucz86IFRzSGlnaGxpZ2h0T3B0aW9ucyxcbiAgKTogU3FsRXhwcmVzc2lvbjxcInN0cmluZ1wiPiB7XG4gICAgY29uc3QgeyBwYXJzZXIgPSBcIndlYnNlYXJjaF90b190c3F1ZXJ5XCIsIGNvbmZpZyA9IFwic2ltcGxlXCIsIC4uLm9wdGlvbnMgfSA9IF9vcHRpb25zID8/IHt9O1xuXG4gICAgY29uc3QgaGxPcHRpb25QYXJ0cyA9IE9iamVjdC5lbnRyaWVzKG9wdGlvbnMpLm1hcCgoW2tleSwgdmFsdWVdKSA9PiB7XG4gICAgICByZXR1cm4gYCR7aW5mbGVjdGlvbi5jYW1lbGl6ZShrZXkpfT0ke3ZhbHVlfWA7XG4gICAgfSk7XG5cbiAgICBjb25zdCBobE9wdGlvbnMgPSBobE9wdGlvblBhcnRzLmxlbmd0aCA+IDAgPyBgLCAnJHtobE9wdGlvblBhcnRzLmpvaW4oXCIsIFwiKX0nYCA6IFwiXCI7XG5cbiAgICByZXR1cm4ge1xuICAgICAgX3R5cGU6IFwic3FsX2V4cHJlc3Npb25cIixcbiAgICAgIF9yZXR1cm46IFwic3RyaW5nXCIsXG4gICAgICBfc3FsOiBgdHNfaGVhZGxpbmUoPywgPz8sICR7cGFyc2VyfSg/LCA/KSR7aGxPcHRpb25zfSlgLFxuICAgICAgX3BhcmFtczogW2NvbmZpZywgY29sdW1uLCBjb25maWcsIHF1ZXJ5XSxcbiAgICB9O1xuICB9XG5cbiAgLy8gdHNfcmFua1xuICBzdGF0aWMgdHNSYW5rKFxuICAgIGNvbHVtbjogc3RyaW5nIHwgU3FsRXhwcmVzc2lvbjxcInRzdmVjdG9yXCI+LFxuICAgIHF1ZXJ5OiBzdHJpbmcsXG4gICAgb3B0aW9ucz86IFRzUmFua09wdGlvbnMsXG4gICk6IFNxbEV4cHJlc3Npb248XCJudW1iZXJcIj4ge1xuICAgIHJldHVybiBQdXJpLl90c1JhbmsoXCJ0c19yYW5rXCIsIGNvbHVtbiwgcXVlcnksIG9wdGlvbnMpO1xuICB9XG5cbiAgLy8gdHNfcmFua19jZFxuICBzdGF0aWMgdHNSYW5rQ2QoXG4gICAgY29sdW1uOiBzdHJpbmcgfCBTcWxFeHByZXNzaW9uPFwidHN2ZWN0b3JcIj4sXG4gICAgcXVlcnk6IHN0cmluZyxcbiAgICBvcHRpb25zPzogVHNSYW5rT3B0aW9ucyxcbiAgKTogU3FsRXhwcmVzc2lvbjxcIm51bWJlclwiPiB7XG4gICAgcmV0dXJuIFB1cmkuX3RzUmFuayhcInRzX3JhbmtfY2RcIiwgY29sdW1uLCBxdWVyeSwgb3B0aW9ucyk7XG4gIH1cblxuICBzdGF0aWMgdG9Uc1ZlY3Rvcihjb2x1bW46IHN0cmluZywgY29uZmlnOiBzdHJpbmcgPSBcInNpbXBsZVwiKTogU3FsRXhwcmVzc2lvbjxcInRzdmVjdG9yXCI+IHtcbiAgICByZXR1cm4ge1xuICAgICAgX3R5cGU6IFwic3FsX2V4cHJlc3Npb25cIixcbiAgICAgIF9yZXR1cm46IFwidHN2ZWN0b3JcIixcbiAgICAgIF9zcWw6IGB0b190c3ZlY3Rvcig/LCA/PylgLFxuICAgICAgX3BhcmFtczogW2NvbmZpZywgY29sdW1uXSxcbiAgICB9O1xuICB9XG5cbiAgc3RhdGljIF90c1JhbmsoXG4gICAgdHlwZTogXCJ0c19yYW5rXCIgfCBcInRzX3JhbmtfY2RcIixcbiAgICBjb2x1bW46IHN0cmluZyB8IFNxbEV4cHJlc3Npb248XCJ0c3ZlY3RvclwiPixcbiAgICBxdWVyeTogc3RyaW5nLFxuICAgIG9wdGlvbnM/OiBUc1JhbmtPcHRpb25zLFxuICApOiBTcWxFeHByZXNzaW9uPFwibnVtYmVyXCI+IHtcbiAgICBjb25zdCB7XG4gICAgICBwYXJzZXIgPSBcIndlYnNlYXJjaF90b190c3F1ZXJ5XCIsXG4gICAgICBjb25maWcgPSBcInNpbXBsZVwiLFxuICAgICAgbm9ybWFsaXphdGlvbixcbiAgICAgIHdlaWdodHMsXG4gICAgfSA9IG9wdGlvbnMgPz8ge307XG5cbiAgICBjb25zdCBwYXJhbXMgPSBbXTtcbiAgICBsZXQgc3FsVGVtcGxhdGUgPSBgJHt0eXBlfShgO1xuXG4gICAgaWYgKHdlaWdodHMpIHtcbiAgICAgIHNxbFRlbXBsYXRlICs9IGBBUlJBWVske3dlaWdodHMubWFwKCgpID0+IFwiP1wiKS5qb2luKFwiLCBcIil9XTo6ZmxvYXQ0W10sIGA7XG4gICAgICBwYXJhbXMucHVzaCguLi53ZWlnaHRzKTtcbiAgICB9XG5cbiAgICBpZiAodHlwZW9mIGNvbHVtbiA9PT0gXCJzdHJpbmdcIikge1xuICAgICAgc3FsVGVtcGxhdGUgKz0gYD8/LCAke3BhcnNlcn0oPywgPylgO1xuICAgICAgcGFyYW1zLnB1c2goY29sdW1uLCBjb25maWcsIHF1ZXJ5KTtcbiAgICB9IGVsc2Uge1xuICAgICAgc3FsVGVtcGxhdGUgKz0gYCR7Y29sdW1uLl9zcWx9LCAke3BhcnNlcn0oPywgPylgO1xuICAgICAgcGFyYW1zLnB1c2goLi4uY29sdW1uLl9wYXJhbXMsIGNvbmZpZywgcXVlcnkpO1xuICAgIH1cblxuICAgIGlmIChub3JtYWxpemF0aW9uKSB7XG4gICAgICBzcWxUZW1wbGF0ZSArPSBcIiwgP1wiO1xuICAgICAgcGFyYW1zLnB1c2gobm9ybWFsaXphdGlvbik7XG4gICAgfVxuXG4gICAgc3FsVGVtcGxhdGUgKz0gXCIpXCI7XG5cbiAgICByZXR1cm4geyBfdHlwZTogXCJzcWxfZXhwcmVzc2lvblwiLCBfcmV0dXJuOiBcIm51bWJlclwiLCBfc3FsOiBzcWxUZW1wbGF0ZSwgX3BhcmFtczogcGFyYW1zIH07XG4gIH1cblxuICAvKipcbiAgICogUEdyb29uZ2EgRnVsbFRleHQg7J24642x7IqkIOqygOyDiSDsoJDsiJhcbiAgICpcbiAgICogQGV4YW1wbGVcbiAgICogLnNlbGVjdCh7XG4gICAqICAgc2NvcmU6IFB1cmkuc2NvcmUoKSxcbiAgICogfSlcbiAgICovXG4gIHN0YXRpYyBzY29yZSgpOiBTcWxFeHByZXNzaW9uPFwibnVtYmVyXCI+IHtcbiAgICByZXR1cm4gUHVyaS5yYXdOdW1iZXIoXCJwZ3Jvb25nYV9zY29yZSh0YWJsZW9pZCwgY3RpZClcIik7XG4gIH1cblxuICAvKipcbiAgICogUEdyb29uZ2EgRnVsbFRleHQg7J24642x7IqkIOqygOyDiSDtlZjsnbTrnbzsnbTtjIVcbiAgICpcbiAgICogQGV4YW1wbGVcbiAgICogLnNlbGVjdCh7XG4gICAqICAgdGl0bGU6IFB1cmkuaGlnaGxpZ2h0KFwicG9zdHMudGl0bGVcIiwgc2VhcmNoKSxcbiAgICogfSlcbiAgICovXG4gIHN0YXRpYyBoaWdobGlnaHQoY29sdW1uOiBzdHJpbmcsIHF1ZXJ5OiBzdHJpbmcgfCBzdHJpbmdbXSk6IFNxbEV4cHJlc3Npb248XCJzdHJpbmdcIj47XG4gIHN0YXRpYyBoaWdobGlnaHQoY29sdW1uczogc3RyaW5nW10sIHF1ZXJ5OiBzdHJpbmcgfCBzdHJpbmdbXSk6IFNxbEV4cHJlc3Npb248XCJzdHJpbmdbXVwiPjtcblxuICBzdGF0aWMgaGlnaGxpZ2h0KFxuICAgIGNvbHVtbk9yQ29sdW1uczogc3RyaW5nIHwgc3RyaW5nW10sXG4gICAgcXVlcnk6IHN0cmluZyB8IHN0cmluZ1tdLFxuICApOiBTcWxFeHByZXNzaW9uPFwic3RyaW5nXCI+IHwgU3FsRXhwcmVzc2lvbjxcInN0cmluZ1tdXCI+IHtcbiAgICBjb25zdCBxdWVyeUFyciA9IEFycmF5LmlzQXJyYXkocXVlcnkpID8gcXVlcnkgOiBbcXVlcnldO1xuICAgIGNvbnN0IHF1ZXJ5Q2xhdXNlID0gYEFSUkFZWyR7cXVlcnlBcnIubWFwKCgpID0+IFwiP1wiKS5qb2luKFwiLCBcIil9XWA7XG5cbiAgICAvLyDri6jsnbwg7Lus65+87J24IOqyveyasFxuICAgIGlmICh0eXBlb2YgY29sdW1uT3JDb2x1bW5zID09PSBcInN0cmluZ1wiKSB7XG4gICAgICByZXR1cm4gUHVyaS5yYXdTdHJpbmcoYHBncm9vbmdhX2hpZ2hsaWdodF9odG1sKD8/LCAke3F1ZXJ5Q2xhdXNlfSlgLCBbXG4gICAgICAgIGNvbHVtbk9yQ29sdW1ucyxcbiAgICAgICAgLi4ucXVlcnlBcnIsXG4gICAgICBdKTtcbiAgICB9XG5cbiAgICAvLyDsu6zrn7wg67Cw7Je07J24IOqyveyasFxuICAgIHJldHVybiBQdXJpLnJhd1N0cmluZ0FycmF5KFxuICAgICAgYHBncm9vbmdhX2hpZ2hsaWdodF9odG1sKEFSUkFZWyR7Y29sdW1uT3JDb2x1bW5zLm1hcCgoKSA9PiBcIj8/XCIpLmpvaW4oXCIsIFwiKX1dLCAke3F1ZXJ5Q2xhdXNlfSlgLFxuICAgICAgWy4uLmNvbHVtbk9yQ29sdW1ucywgLi4ucXVlcnlBcnJdLFxuICAgICk7XG4gIH1cblxuICAvLyBTRUxFQ1QgKG92ZXJ3cml0ZSlcbiAgc2VsZWN0PFRTZWxlY3QgZXh0ZW5kcyBTZWxlY3RPYmplY3Q8VFRhYmxlcz4+KFxuICAgIHNlbGVjdE9iajogVFNlbGVjdCxcbiAgKTogUHVyaTxUU2NoZW1hLCBUVGFibGVzLCBQYXJzZVNlbGVjdE9iamVjdDxUVGFibGVzLCBUU2VsZWN0Pj4ge1xuICAgIC8vIOykkeyyqSDqsJ3ssrTrpbwgZmxhdO2VmOqyjCDrs4DtmZhcbiAgICBjb25zdCBmbGF0U2VsZWN0ID0gdGhpcy5mbGF0dGVuU2VsZWN0KHNlbGVjdE9iaik7XG5cbiAgICBjb25zdCBzZWxlY3RDbGF1c2VzOiAoc3RyaW5nIHwgS25leC5SYXcpW10gPSBbXTtcblxuICAgIGZvciAoY29uc3QgW2FsaWFzLCBjb2x1bW5PckZ1bmN0aW9uXSBvZiBPYmplY3QuZW50cmllcyhmbGF0U2VsZWN0KSkge1xuICAgICAgaWYgKHR5cGVvZiBjb2x1bW5PckZ1bmN0aW9uID09PSBcIm9iamVjdFwiICYmIGNvbHVtbk9yRnVuY3Rpb24uX3R5cGUgPT09IFwic3FsX2V4cHJlc3Npb25cIikge1xuICAgICAgICAvLyBTUUwg7ZWo7IiY7J24IOqyveyasFxuICAgICAgICBzZWxlY3RDbGF1c2VzLnB1c2goXG4gICAgICAgICAgdGhpcy5rbmV4LnJhdyhgJHtjb2x1bW5PckZ1bmN0aW9uLl9zcWx9IEFTIFwiJHthbGlhc31cImAsIGNvbHVtbk9yRnVuY3Rpb24uX3BhcmFtcyksXG4gICAgICAgICk7XG4gICAgICB9IGVsc2Uge1xuICAgICAgICAvLyDsnbzrsJgg7Lus65+87J24IOqyveyasFxuICAgICAgICBjb25zdCBjb2x1bW5QYXRoID0gY29sdW1uT3JGdW5jdGlvbiBhcyBzdHJpbmc7XG4gICAgICAgIGlmIChhbGlhcyA9PT0gY29sdW1uUGF0aCkge1xuICAgICAgICAgIC8vIGFsaWFz7JmAIOy7rOufvOuqheydtCDqsJnsnLzrqbQgYWxpYXMg7IOd6561XG4gICAgICAgICAgc2VsZWN0Q2xhdXNlcy5wdXNoKGNvbHVtblBhdGgpO1xuICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgIC8vIGFsaWFzIOyngOyglVxuICAgICAgICAgIHNlbGVjdENsYXVzZXMucHVzaChgJHtjb2x1bW5QYXRofSBBUyAke2FsaWFzfWApO1xuICAgICAgICB9XG4gICAgICB9XG4gICAgfVxuXG4gICAgdGhpcy5rbmV4UXVlcnkuc2VsZWN0KHNlbGVjdENsYXVzZXMpO1xuICAgIHJldHVybiB0aGlzIGFzIGFueTtcbiAgfVxuXG4gIC8qKlxuICAgKiDspJHssqkg6rCd7LK066W8IGZsYXQg6rCd7LK066GcIOuzgO2ZmFxuICAgKiDsmIg6IHsgcGFyZW50OiB7IGlkOiBcInBhcmVudC5pZFwiLCBuYW1lOiBcInBhcmVudC5uYW1lXCIgfSB9XG4gICAqICAg4oaSIHsgcGFyZW50X19pZDogXCJwYXJlbnQuaWRcIiwgcGFyZW50X19uYW1lOiBcInBhcmVudC5uYW1lXCIgfVxuICAgKi9cbiAgcHJpdmF0ZSBmbGF0dGVuU2VsZWN0KHNlbGVjdE9iajogUmVjb3JkPHN0cmluZywgYW55PiwgcHJlZml4ID0gXCJcIik6IFJlY29yZDxzdHJpbmcsIGFueT4ge1xuICAgIGNvbnN0IGZsYXRTZWxlY3Q6IFJlY29yZDxzdHJpbmcsIGFueT4gPSB7fTtcblxuICAgIGZvciAoY29uc3QgW2tleSwgdmFsdWVdIG9mIE9iamVjdC5lbnRyaWVzKHNlbGVjdE9iaikpIHtcbiAgICAgIGNvbnN0IGZ1bGxLZXkgPSBwcmVmaXggPyBgJHtwcmVmaXh9X18ke2tleX1gIDoga2V5O1xuXG4gICAgICBpZiAodHlwZW9mIHZhbHVlID09PSBcIm9iamVjdFwiICYmIHZhbHVlICE9PSBudWxsICYmICEoXCJfdHlwZVwiIGluIHZhbHVlKSkge1xuICAgICAgICAvLyDspJHssqkg6rCd7LK07J24IOqyveyasCAtIOyerOq3gCDsspjrpqxcbiAgICAgICAgY29uc3QgbmVzdGVkID0gdGhpcy5mbGF0dGVuU2VsZWN0KHZhbHVlLCBmdWxsS2V5KTtcbiAgICAgICAgT2JqZWN0LmFzc2lnbihmbGF0U2VsZWN0LCBuZXN0ZWQpO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgLy8g7J2867CYIOqwkuyduCDqsr3smrAgKOy7rOufvCDqsr3roZwg65iQ64qUIFNxbEV4cHJlc3Npb24pXG4gICAgICAgIGZsYXRTZWxlY3RbZnVsbEtleV0gPSB2YWx1ZTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICByZXR1cm4gZmxhdFNlbGVjdDtcbiAgfVxuXG4gIC8vIFNFTEVDVCAoc2VsZWN064qUIG92ZXJ3cml0ZSwgYXBwZW5kU2VsZWN064qUIGFwcGVuZClcbiAgYXBwZW5kU2VsZWN0PFRTZWxlY3QgZXh0ZW5kcyBTZWxlY3RPYmplY3Q8VFRhYmxlcz4+KFxuICAgIHNlbGVjdE9iajogVFNlbGVjdCxcbiAgKTogUHVyaTxUU2NoZW1hLCBUVGFibGVzLCBUUmVzdWx0ICYgUGFyc2VTZWxlY3RPYmplY3Q8VFRhYmxlcywgVFNlbGVjdD4+IHtcbiAgICAvLyDspJHssqkg6rCd7LK066W8IGZsYXTtlZjqsowg67OA7ZmYXG4gICAgY29uc3QgZmxhdFNlbGVjdCA9IHRoaXMuZmxhdHRlblNlbGVjdChzZWxlY3RPYmopO1xuXG4gICAgY29uc3Qgc2VsZWN0Q2xhdXNlczogKHN0cmluZyB8IEtuZXguUmF3KVtdID0gW107XG5cbiAgICBmb3IgKGNvbnN0IFthbGlhcywgY29sdW1uT3JGdW5jdGlvbl0gb2YgT2JqZWN0LmVudHJpZXMoZmxhdFNlbGVjdCkpIHtcbiAgICAgIGlmICh0eXBlb2YgY29sdW1uT3JGdW5jdGlvbiA9PT0gXCJvYmplY3RcIiAmJiBjb2x1bW5PckZ1bmN0aW9uLl90eXBlID09PSBcInNxbF9leHByZXNzaW9uXCIpIHtcbiAgICAgICAgc2VsZWN0Q2xhdXNlcy5wdXNoKFxuICAgICAgICAgIHRoaXMua25leC5yYXcoYCR7Y29sdW1uT3JGdW5jdGlvbi5fc3FsfSBBUyAke2FsaWFzfWAsIGNvbHVtbk9yRnVuY3Rpb24uX3BhcmFtcyksXG4gICAgICAgICk7XG4gICAgICB9IGVsc2Uge1xuICAgICAgICBjb25zdCBjb2x1bW5QYXRoID0gY29sdW1uT3JGdW5jdGlvbiBhcyBzdHJpbmc7XG4gICAgICAgIGlmIChhbGlhcyA9PT0gY29sdW1uUGF0aCkge1xuICAgICAgICAgIHNlbGVjdENsYXVzZXMucHVzaChjb2x1bW5QYXRoKTtcbiAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICBzZWxlY3RDbGF1c2VzLnB1c2godGhpcy5rbmV4LnJlZihjb2x1bW5QYXRoKS5hcyhhbGlhcykpO1xuICAgICAgICB9XG4gICAgICB9XG4gICAgfVxuXG4gICAgdGhpcy5rbmV4UXVlcnkuc2VsZWN0KHNlbGVjdENsYXVzZXMpO1xuICAgIHJldHVybiB0aGlzIGFzIGFueTtcbiAgfVxuXG4gIC8vIFNFTEVDVCAqXG4gIHNlbGVjdEFsbCgpOiBQdXJpPFRTY2hlbWEsIFRUYWJsZXMsIFNlbGVjdEFsbFJlc3VsdDxUVGFibGVzPj4ge1xuICAgIHRoaXMua25leFF1ZXJ5LnNlbGVjdChcIipcIik7XG4gICAgcmV0dXJuIHRoaXMgYXMgYW55O1xuICB9XG5cbiAgLy8gRElTVElOQ1RcbiAgZGlzdGluY3Q8VENvbHVtbnMgZXh0ZW5kcyBBdmFpbGFibGVDb2x1bW5zPFRUYWJsZXM+PiguLi5jb2x1bW5zOiBUQ29sdW1uc1tdKTogdGhpcztcbiAgZGlzdGluY3QoLi4uY29sdW1uczogc3RyaW5nW10pOiB0aGlzIHtcbiAgICB0aGlzLmtuZXhRdWVyeS5kaXN0aW5jdCguLi5jb2x1bW5zKTtcbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIC8vIENMRUFSXG4gIGNsZWFyKHN0YXRlbWVudDogQ2xlYXJTdGF0ZW1lbnRzKTogdGhpcyB7XG4gICAgdGhpcy5rbmV4UXVlcnkuY2xlYXIoc3RhdGVtZW50KTtcbiAgICBpZiAoc3RhdGVtZW50ID09PSBcImpvaW5cIikge1xuICAgICAgdGhpcy5jbGVhckpvaW5SZWdpc3RyYXRpb25zKCk7XG4gICAgfVxuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgLy8ga25leOyXkCDsl4bslrTshJwg7KeB7KCRIOq1rO2YhO2VqFxuICBjbGVhckpvaW4oYWxpYXM6IHN0cmluZyk6IHRoaXMge1xuICAgIGxldCByZW1vdmVkID0gZmFsc2U7XG4gICAgKHRoaXMua25leFF1ZXJ5IGFzIGFueSkuX3N0YXRlbWVudHMgPSAodGhpcy5rbmV4UXVlcnkgYXMgYW55KS5fc3RhdGVtZW50cy5maWx0ZXIoKHM6IGFueSkgPT4ge1xuICAgICAgaWYgKFwiam9pblR5cGVcIiBpbiBzKSB7XG4gICAgICAgIGNvbnN0IHNob3VsZFJlbW92ZSA9IHRoaXMuZ2V0S25leEpvaW5BbGlhcyhzLnRhYmxlKSA9PT0gYWxpYXM7XG4gICAgICAgIHJlbW92ZWQgfHw9IHNob3VsZFJlbW92ZTtcbiAgICAgICAgcmV0dXJuICFzaG91bGRSZW1vdmU7XG4gICAgICB9IGVsc2Uge1xuICAgICAgICByZXR1cm4gdHJ1ZTtcbiAgICAgIH1cbiAgICB9KTtcbiAgICBpZiAocmVtb3ZlZCAmJiB0aGlzLmNvcnJlbGF0aW9uUmVnaXN0cnkuZ2V0KGFsaWFzKT8ua2luZCA9PT0gXCJqb2luXCIpIHtcbiAgICAgIHRoaXMuY29ycmVsYXRpb25SZWdpc3RyeS5kZWxldGUoYWxpYXMpO1xuICAgIH1cbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIC8vIEpPSU46IOyEnOu4jOy/vOumrCArIEFsaWFzXG4gIGpvaW48VEpvaW5BbGlhcyBleHRlbmRzIHN0cmluZywgVFN1YlJlc3VsdD4oXG4gICAgdGFibGVTcGVjOiB7IFtLIGluIFRKb2luQWxpYXNdOiBQdXJpPFRTY2hlbWEsIGFueSwgVFN1YlJlc3VsdD4gfSxcbiAgICBsZWZ0OiBBdmFpbGFibGVDb2x1bW5zPFRUYWJsZXM+LFxuICAgIHJpZ2h0OiBgJHtUSm9pbkFsaWFzfS4ke0NvbHVtbktleXM8VFN1YlJlc3VsdD59YCxcbiAgKTogUHVyaTxcbiAgICBUU2NoZW1hLFxuICAgIFRUYWJsZXMgJiBSZWNvcmQ8VEpvaW5BbGlhcywgVFN1YlJlc3VsdD4sIC8vIOyEnOu4jOy/vOumrOydmCBUUmVzdWx0XG4gICAgVFJlc3VsdFxuICA+O1xuICAvLyBKT0lOOiDthYzsnbTruJQgKyBBbGlhc1xuICBqb2luPFRKb2luVGFibGUgZXh0ZW5kcyBrZXlvZiBUU2NoZW1hLCBUSm9pbkFsaWFzIGV4dGVuZHMgc3RyaW5nPihcbiAgICB0YWJsZVNwZWM6IHsgW0sgaW4gVEpvaW5BbGlhc106IFRKb2luVGFibGUgfSxcbiAgICBsZWZ0OiBBdmFpbGFibGVDb2x1bW5zPFRUYWJsZXM+LFxuICAgIHJpZ2h0OiBgJHtUSm9pbkFsaWFzfS4ke0NvbHVtbktleXM8VFNjaGVtYVtUSm9pblRhYmxlXT59YCxcbiAgKTogUHVyaTxcbiAgICBUU2NoZW1hLFxuICAgIFRUYWJsZXMgJiBSZWNvcmQ8VEpvaW5BbGlhcywgVFNjaGVtYVtUSm9pblRhYmxlXT4sIC8vIFRUYWJsZXMg7ZmV7J6lIVxuICAgIFRSZXN1bHRcbiAgPjtcbiAgLy8gSk9JTjog7YWM7J2067iU66qFXG4gIGpvaW48VEpvaW5UYWJsZSBleHRlbmRzIGtleW9mIFRTY2hlbWE+KFxuICAgIHRhYmxlTmFtZTogVEpvaW5UYWJsZSxcbiAgICBsZWZ0OiBBdmFpbGFibGVDb2x1bW5zPFRUYWJsZXM+LFxuICAgIHJpZ2h0OiBgJHtUSm9pblRhYmxlICYgc3RyaW5nfS4ke0NvbHVtbktleXM8VFNjaGVtYVtUSm9pblRhYmxlXT59YCxcbiAgKTogUHVyaTxcbiAgICBUU2NoZW1hLFxuICAgIFRUYWJsZXMgJiBSZWNvcmQ8VEpvaW5UYWJsZSwgVFNjaGVtYVtUSm9pblRhYmxlXT4sIC8vIO2FjOydtOu4lOuqheydtCDtgqRcbiAgICBUUmVzdWx0XG4gID47XG4gIC8vIEpPSU46IOyEnOu4jOy/vOumrCArIEFsaWFzICsg7L2c67CxXG4gIGpvaW48VEpvaW5BbGlhcyBleHRlbmRzIHN0cmluZywgVFN1YlJlc3VsdD4oXG4gICAgdGFibGVTcGVjOiB7IFtLIGluIFRKb2luQWxpYXNdOiBQdXJpPFRTY2hlbWEsIGFueSwgVFN1YlJlc3VsdD4gfSxcbiAgICBjYWxsYmFjazogKGo6IEpvaW5DbGF1c2VHcm91cDxUVGFibGVzLCBSZWNvcmQ8VEpvaW5BbGlhcywgVFN1YlJlc3VsdD4+KSA9PiB2b2lkLFxuICApOiBQdXJpPFRTY2hlbWEsIFRUYWJsZXMgJiBSZWNvcmQ8VEpvaW5BbGlhcywgVFN1YlJlc3VsdD4sIFRSZXN1bHQ+O1xuICAvLyBKT0lOOiDthYzsnbTruJQgKyBBbGlhcyArIOy9nOuwsVxuICBqb2luPFRKb2luVGFibGUgZXh0ZW5kcyBrZXlvZiBUU2NoZW1hLCBUSm9pbkFsaWFzIGV4dGVuZHMgc3RyaW5nPihcbiAgICB0YWJsZVNwZWM6IHsgW0sgaW4gVEpvaW5BbGlhc106IFRKb2luVGFibGUgfSxcbiAgICBjYWxsYmFjazogKGo6IEpvaW5DbGF1c2VHcm91cDxUVGFibGVzLCBSZWNvcmQ8VEpvaW5BbGlhcywgVFNjaGVtYVtUSm9pblRhYmxlXT4+KSA9PiB2b2lkLFxuICApOiBQdXJpPFRTY2hlbWEsIFRUYWJsZXMgJiBSZWNvcmQ8VEpvaW5BbGlhcywgVFNjaGVtYVtUSm9pblRhYmxlXT4sIFRSZXN1bHQ+O1xuICAvLyBKT0lOOiDthYzsnbTruJTrqoUgKyDsvZzrsLFcbiAgam9pbjxUSm9pblRhYmxlIGV4dGVuZHMga2V5b2YgVFNjaGVtYT4oXG4gICAgdGFibGVOYW1lOiBUSm9pblRhYmxlLFxuICAgIGNhbGxiYWNrOiAoajogSm9pbkNsYXVzZUdyb3VwPFRUYWJsZXMsIFJlY29yZDxUSm9pblRhYmxlLCBUU2NoZW1hW1RKb2luVGFibGVdPj4pID0+IHZvaWQsXG4gICk6IFB1cmk8VFNjaGVtYSwgVFRhYmxlcyAmIFJlY29yZDxUSm9pblRhYmxlLCBUU2NoZW1hW1RKb2luVGFibGVdPiwgVFJlc3VsdD47XG4gIC8vIEpPSU4g7Iuk7KCcIOq1rO2YhFxuICBqb2luKHRhYmxlTmFtZU9yU3BlYzogYW55LCAuLi5hcmdzOiBhbnlbXSk6IGFueSB7XG4gICAgcmV0dXJuIHRoaXMuX19jb21tb25Kb2luKFwiam9pblwiLCB0YWJsZU5hbWVPclNwZWMsIC4uLmFyZ3MpO1xuICB9XG5cbiAgLy8gRU5TVVJFIEpPSU46IO2FjOydtOu4lCArIEFsaWFzXG4gIGVuc3VyZUpvaW48VEpvaW5UYWJsZSBleHRlbmRzIGtleW9mIFRTY2hlbWEsIFRKb2luQWxpYXMgZXh0ZW5kcyBzdHJpbmc+KFxuICAgIHRhYmxlU3BlYzogeyBbSyBpbiBUSm9pbkFsaWFzXTogVEpvaW5UYWJsZSB9LFxuICAgIGxlZnQ6IEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcz4sXG4gICAgcmlnaHQ6IGAke1RKb2luQWxpYXN9LiR7Q29sdW1uS2V5czxUU2NoZW1hW1RKb2luVGFibGVdPn1gLFxuICApOiBQdXJpPFRTY2hlbWEsIFRUYWJsZXMgJiBSZWNvcmQ8VEpvaW5BbGlhcywgVFNjaGVtYVtUSm9pblRhYmxlXT4sIFRSZXN1bHQ+O1xuICAvLyBFTlNVUkUgSk9JTjog7YWM7J2067iU66qFXG4gIGVuc3VyZUpvaW48VEpvaW5UYWJsZSBleHRlbmRzIGtleW9mIFRTY2hlbWE+KFxuICAgIHRhYmxlTmFtZTogVEpvaW5UYWJsZSxcbiAgICBsZWZ0OiBBdmFpbGFibGVDb2x1bW5zPFRUYWJsZXM+LFxuICAgIHJpZ2h0OiBgJHtUSm9pblRhYmxlICYgc3RyaW5nfS4ke0NvbHVtbktleXM8VFNjaGVtYVtUSm9pblRhYmxlXT59YCxcbiAgKTogUHVyaTxUU2NoZW1hLCBUVGFibGVzICYgUmVjb3JkPFRKb2luVGFibGUsIFRTY2hlbWFbVEpvaW5UYWJsZV0+LCBUUmVzdWx0PjtcbiAgZW5zdXJlSm9pbih0YWJsZU5hbWVPclNwZWM6IGFueSwgbGVmdDogc3RyaW5nLCByaWdodDogc3RyaW5nKTogYW55IHtcbiAgICByZXR1cm4gdGhpcy5fX2Vuc3VyZUpvaW4oXCJqb2luXCIsIHRhYmxlTmFtZU9yU3BlYywgbGVmdCwgcmlnaHQpO1xuICB9XG5cbiAgLy8gTEVGVCBKT0lOOiDshJzruIzsv7zrpqwgKyBBbGlhc1xuICBsZWZ0Sm9pbjxUSm9pbkFsaWFzIGV4dGVuZHMgc3RyaW5nLCBUU3ViUmVzdWx0PihcbiAgICB0YWJsZVNwZWM6IHsgW0sgaW4gVEpvaW5BbGlhc106IFB1cmk8VFNjaGVtYSwgYW55LCBUU3ViUmVzdWx0PiB9LFxuICAgIGxlZnQ6IEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcz4sXG4gICAgcmlnaHQ6IGAke1RKb2luQWxpYXN9LiR7Q29sdW1uS2V5czxUU3ViUmVzdWx0Pn1gLFxuICApOiBQdXJpPFRTY2hlbWEsIFRUYWJsZXMgJiBSZWNvcmQ8VEpvaW5BbGlhcywgVFN1YlJlc3VsdCAmIExlZnRKb2luZWRNYXJrZXI+LCBUUmVzdWx0PjsgLy8g7ISc67iM7L+866as7J2YIFRSZXN1bHRcbiAgLy8gTEVGVCBKT0lOOiDthYzsnbTruJQgKyBBbGlhc1xuICAvLyBGSyBudWxsYWJsZSDsl6zrtoDsl5Ag65Sw6528IOyekOuPmeycvOuhnCBMZWZ0Sm9pbmVkTWFya2VyIOqysOyglVxuICBsZWZ0Sm9pbjxcbiAgICBUSm9pblRhYmxlIGV4dGVuZHMga2V5b2YgVFNjaGVtYSxcbiAgICBUSm9pbkFsaWFzIGV4dGVuZHMgc3RyaW5nLFxuICAgIFRMZWZ0IGV4dGVuZHMgQXZhaWxhYmxlQ29sdW1uczxUVGFibGVzPixcbiAgPihcbiAgICB0YWJsZVNwZWM6IHsgW0sgaW4gVEpvaW5BbGlhc106IFRKb2luVGFibGUgfSxcbiAgICBsZWZ0OiBUTGVmdCxcbiAgICByaWdodDogYCR7VEpvaW5BbGlhc30uJHtDb2x1bW5LZXlzPFRTY2hlbWFbVEpvaW5UYWJsZV0+fWAsXG4gICk6IFB1cmk8XG4gICAgVFNjaGVtYSxcbiAgICBUVGFibGVzICYgUmVjb3JkPFRKb2luQWxpYXMsIFRTY2hlbWFbVEpvaW5UYWJsZV0gJiBMZWZ0Sm9pbk1hcmtlckZvcjxUVGFibGVzLCBUTGVmdD4+LFxuICAgIFRSZXN1bHRcbiAgPjtcbiAgLy8gTEVGVCBKT0lOOiDthYzsnbTruJTrqoVcbiAgbGVmdEpvaW48VEpvaW5UYWJsZSBleHRlbmRzIGtleW9mIFRTY2hlbWEsIFRMZWZ0IGV4dGVuZHMgQXZhaWxhYmxlQ29sdW1uczxUVGFibGVzPj4oXG4gICAgdGFibGVOYW1lOiBUSm9pblRhYmxlLFxuICAgIGxlZnQ6IFRMZWZ0LFxuICAgIHJpZ2h0OiBgJHtUSm9pblRhYmxlICYgc3RyaW5nfS4ke0NvbHVtbktleXM8VFNjaGVtYVtUSm9pblRhYmxlXT59YCxcbiAgKTogUHVyaTxcbiAgICBUU2NoZW1hLFxuICAgIFRUYWJsZXMgJiBSZWNvcmQ8VEpvaW5UYWJsZSwgVFNjaGVtYVtUSm9pblRhYmxlXSAmIExlZnRKb2luTWFya2VyRm9yPFRUYWJsZXMsIFRMZWZ0Pj4sXG4gICAgVFJlc3VsdFxuICA+O1xuICAvLyBMRUZUIEpPSU46IOyEnOu4jOy/vOumrCArIEFsaWFzICsg7L2c67CxXG4gIGxlZnRKb2luPFRKb2luQWxpYXMgZXh0ZW5kcyBzdHJpbmcsIFRTdWJSZXN1bHQ+KFxuICAgIHRhYmxlU3BlYzogeyBbSyBpbiBUSm9pbkFsaWFzXTogUHVyaTxUU2NoZW1hLCBhbnksIFRTdWJSZXN1bHQ+IH0sXG4gICAgY2FsbGJhY2s6IChqOiBKb2luQ2xhdXNlR3JvdXA8VFRhYmxlcywgUmVjb3JkPFRKb2luQWxpYXMsIFRTdWJSZXN1bHQ+PikgPT4gdm9pZCxcbiAgKTogUHVyaTxUU2NoZW1hLCBUVGFibGVzICYgUmVjb3JkPFRKb2luQWxpYXMsIFRTdWJSZXN1bHQgJiBMZWZ0Sm9pbmVkTWFya2VyPiwgVFJlc3VsdD47XG4gIC8vIExFRlQgSk9JTjog7YWM7J2067iUICsgQWxpYXMgKyDsvZzrsLFcbiAgbGVmdEpvaW48VEpvaW5UYWJsZSBleHRlbmRzIGtleW9mIFRTY2hlbWEsIFRKb2luQWxpYXMgZXh0ZW5kcyBzdHJpbmc+KFxuICAgIHRhYmxlU3BlYzogeyBbSyBpbiBUSm9pbkFsaWFzXTogVEpvaW5UYWJsZSB9LFxuICAgIGNhbGxiYWNrOiAoajogSm9pbkNsYXVzZUdyb3VwPFRUYWJsZXMsIFJlY29yZDxUSm9pbkFsaWFzLCBUU2NoZW1hW1RKb2luVGFibGVdPj4pID0+IHZvaWQsXG4gICk6IFB1cmk8VFNjaGVtYSwgVFRhYmxlcyAmIFJlY29yZDxUSm9pbkFsaWFzLCBUU2NoZW1hW1RKb2luVGFibGVdICYgTGVmdEpvaW5lZE1hcmtlcj4sIFRSZXN1bHQ+O1xuICAvLyBMRUZUIEpPSU46IO2FjOydtOu4lOuqhSArIOy9nOuwsVxuICBsZWZ0Sm9pbjxUSm9pblRhYmxlIGV4dGVuZHMga2V5b2YgVFNjaGVtYT4oXG4gICAgdGFibGVOYW1lOiBUSm9pblRhYmxlLFxuICAgIGNhbGxiYWNrOiAoajogSm9pbkNsYXVzZUdyb3VwPFRUYWJsZXMsIFJlY29yZDxUSm9pblRhYmxlLCBUU2NoZW1hW1RKb2luVGFibGVdPj4pID0+IHZvaWQsXG4gICk6IFB1cmk8VFNjaGVtYSwgVFRhYmxlcyAmIFJlY29yZDxUSm9pblRhYmxlLCBUU2NoZW1hW1RKb2luVGFibGVdICYgTGVmdEpvaW5lZE1hcmtlcj4sIFRSZXN1bHQ+O1xuICAvLyBMRUZUIEpPSU4g7Iuk7KCcIOq1rO2YhFxuICBsZWZ0Sm9pbih0YWJsZU5hbWVPclNwZWM6IGFueSwgLi4uYXJnczogYW55W10pOiBhbnkge1xuICAgIHJldHVybiB0aGlzLl9fY29tbW9uSm9pbihcImxlZnRKb2luXCIsIHRhYmxlTmFtZU9yU3BlYywgLi4uYXJncyk7XG4gIH1cblxuICAvLyBFTlNVUkUgTEVGVCBKT0lOOiDthYzsnbTruJQgKyBBbGlhc1xuICBlbnN1cmVMZWZ0Sm9pbjxcbiAgICBUSm9pblRhYmxlIGV4dGVuZHMga2V5b2YgVFNjaGVtYSxcbiAgICBUSm9pbkFsaWFzIGV4dGVuZHMgc3RyaW5nLFxuICAgIFRMZWZ0IGV4dGVuZHMgQXZhaWxhYmxlQ29sdW1uczxUVGFibGVzPixcbiAgPihcbiAgICB0YWJsZVNwZWM6IHsgW0sgaW4gVEpvaW5BbGlhc106IFRKb2luVGFibGUgfSxcbiAgICBsZWZ0OiBUTGVmdCxcbiAgICByaWdodDogYCR7VEpvaW5BbGlhc30uJHtDb2x1bW5LZXlzPFRTY2hlbWFbVEpvaW5UYWJsZV0+fWAsXG4gICk6IFB1cmk8XG4gICAgVFNjaGVtYSxcbiAgICBUVGFibGVzICYgUmVjb3JkPFRKb2luQWxpYXMsIFRTY2hlbWFbVEpvaW5UYWJsZV0gJiBMZWZ0Sm9pbk1hcmtlckZvcjxUVGFibGVzLCBUTGVmdD4+LFxuICAgIFRSZXN1bHRcbiAgPjtcbiAgLy8gRU5TVVJFIExFRlQgSk9JTjog7YWM7J2067iU66qFXG4gIGVuc3VyZUxlZnRKb2luPFRKb2luVGFibGUgZXh0ZW5kcyBrZXlvZiBUU2NoZW1hLCBUTGVmdCBleHRlbmRzIEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcz4+KFxuICAgIHRhYmxlTmFtZTogVEpvaW5UYWJsZSxcbiAgICBsZWZ0OiBUTGVmdCxcbiAgICByaWdodDogYCR7VEpvaW5UYWJsZSAmIHN0cmluZ30uJHtDb2x1bW5LZXlzPFRTY2hlbWFbVEpvaW5UYWJsZV0+fWAsXG4gICk6IFB1cmk8XG4gICAgVFNjaGVtYSxcbiAgICBUVGFibGVzICYgUmVjb3JkPFRKb2luVGFibGUsIFRTY2hlbWFbVEpvaW5UYWJsZV0gJiBMZWZ0Sm9pbk1hcmtlckZvcjxUVGFibGVzLCBUTGVmdD4+LFxuICAgIFRSZXN1bHRcbiAgPjtcbiAgZW5zdXJlTGVmdEpvaW4odGFibGVOYW1lT3JTcGVjOiBhbnksIGxlZnQ6IHN0cmluZywgcmlnaHQ6IHN0cmluZyk6IGFueSB7XG4gICAgcmV0dXJuIHRoaXMuX19lbnN1cmVKb2luKFwibGVmdEpvaW5cIiwgdGFibGVOYW1lT3JTcGVjLCBsZWZ0LCByaWdodCk7XG4gIH1cblxuICBfX2NvbW1vbkpvaW4oam9pblR5cGU6IFwiam9pblwiIHwgXCJsZWZ0Sm9pblwiLCB0YWJsZU5hbWVPclNwZWM6IGFueSwgLi4uYXJnczogYW55W10pOiB0aGlzIHtcbiAgICBjb25zdCByZWdpc3RyYXRpb24gPSB0aGlzLmNyZWF0ZUpvaW5SZWdpc3RyYXRpb24oam9pblR5cGUsIHRhYmxlTmFtZU9yU3BlYywgYXJncyk7XG4gICAgdGhpcy5hc3NlcnRDb3JyZWxhdGlvbkF2YWlsYWJsZShyZWdpc3RyYXRpb24pO1xuXG4gICAgaWYgKHR5cGVvZiB0YWJsZU5hbWVPclNwZWMgPT09IFwic3RyaW5nXCIpIHtcbiAgICAgIC8vIENhc2UgMTogam9pbihcInBvc3RzXCIsIC4uLilcbiAgICAgIGNvbnN0IHRhYmxlTmFtZSA9IHRhYmxlTmFtZU9yU3BlYztcblxuICAgICAgaWYgKGFyZ3MubGVuZ3RoID09PSAxICYmIHR5cGVvZiBhcmdzWzBdID09PSBcImZ1bmN0aW9uXCIpIHtcbiAgICAgICAgLy8gam9pbihcInBvc3RzXCIsIGNhbGxiYWNrKVxuICAgICAgICBjb25zdCBjYWxsYmFjayA9IGFyZ3NbMF07XG4gICAgICAgIHRoaXMua25leFF1ZXJ5W2pvaW5UeXBlXSh0YWJsZU5hbWUsIChqb2luQ2xhdXNlKSA9PiB7XG4gICAgICAgICAgY2FsbGJhY2sobmV3IEpvaW5DbGF1c2VHcm91cChqb2luQ2xhdXNlKSk7XG4gICAgICAgIH0pO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgLy8gam9pbihcInBvc3RzXCIsIGxlZnQsIHJpZ2h0KVxuICAgICAgICBjb25zdCBbbGVmdCwgcmlnaHRdID0gYXJncztcbiAgICAgICAgdGhpcy5rbmV4UXVlcnlbam9pblR5cGVdKHRhYmxlTmFtZSwgbGVmdCwgcmlnaHQpO1xuICAgICAgfVxuICAgIH0gZWxzZSBpZiAodHlwZW9mIHRhYmxlTmFtZU9yU3BlYyA9PT0gXCJvYmplY3RcIikge1xuICAgICAgLy8gQ2FzZSAyOiBqb2luKHsgYWxpYXM6IFwidGFibGVcIiB9LCAuLi4pIG9yIGpvaW4oeyBhbGlhczogc3VicXVlcnkgfSwgLi4uKVxuICAgICAgY29uc3QgZW50cmllcyA9IE9iamVjdC5lbnRyaWVzKHRhYmxlTmFtZU9yU3BlYyk7XG4gICAgICBpZiAoZW50cmllcy5sZW5ndGggIT09IDEpIHtcbiAgICAgICAgdGhyb3cgbmV3IEVycm9yKFwiVGFibGUgc3BlYyBtdXN0IGhhdmUgZXhhY3RseSBvbmUgZW50cnlcIik7XG4gICAgICB9XG4gICAgICBhc3NlcnQoZW50cmllc1swXSk7XG4gICAgICBjb25zdCBbW2FsaWFzLCBzcGVjXV0gPSBlbnRyaWVzO1xuXG4gICAgICBpZiAodHlwZW9mIHNwZWMgPT09IFwic3RyaW5nXCIpIHtcbiAgICAgICAgLy8g7YWM7J2067iUOiBqb2luKHsgcDogXCJwb3N0c1wiIH0sIC4uLilcbiAgICAgICAgaWYgKGFyZ3MubGVuZ3RoID09PSAxICYmIHR5cGVvZiBhcmdzWzBdID09PSBcImZ1bmN0aW9uXCIpIHtcbiAgICAgICAgICAvLyBDYWxsYmFja1xuICAgICAgICAgIGNvbnN0IGNhbGxiYWNrID0gYXJnc1swXTtcbiAgICAgICAgICB0aGlzLmtuZXhRdWVyeVtqb2luVHlwZV0oeyBbYWxpYXNdOiBzcGVjIH0sIChqb2luQ2xhdXNlKSA9PiB7XG4gICAgICAgICAgICBjYWxsYmFjayhuZXcgSm9pbkNsYXVzZUdyb3VwKGpvaW5DbGF1c2UpKTtcbiAgICAgICAgICB9KTtcbiAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICAvLyBTaW1wbGVcbiAgICAgICAgICBjb25zdCBbbGVmdCwgcmlnaHRdID0gYXJncztcbiAgICAgICAgICB0aGlzLmtuZXhRdWVyeVtqb2luVHlwZV0oeyBbYWxpYXNdOiBzcGVjIH0sIGxlZnQsIHJpZ2h0KTtcbiAgICAgICAgfVxuICAgICAgfSBlbHNlIGlmIChzcGVjIGluc3RhbmNlb2YgUHVyaSkge1xuICAgICAgICAvLyDshJzruIzsv7zrpqw6IGpvaW4oeyBzcTogc3VicXVlcnkgfSwgLi4uKVxuICAgICAgICBpZiAoYXJncy5sZW5ndGggPT09IDEgJiYgdHlwZW9mIGFyZ3NbMF0gPT09IFwiZnVuY3Rpb25cIikge1xuICAgICAgICAgIC8vIENhbGxiYWNrXG4gICAgICAgICAgY29uc3QgY2FsbGJhY2sgPSBhcmdzWzBdO1xuICAgICAgICAgIHRoaXMua25leFF1ZXJ5W2pvaW5UeXBlXShzcGVjLnJhd1F1ZXJ5KCkuYXMoYWxpYXMpLCAoam9pbkNsYXVzZSkgPT4ge1xuICAgICAgICAgICAgY2FsbGJhY2sobmV3IEpvaW5DbGF1c2VHcm91cChqb2luQ2xhdXNlKSk7XG4gICAgICAgICAgfSk7XG4gICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgLy8gU2ltcGxlXG4gICAgICAgICAgY29uc3QgW2xlZnQsIHJpZ2h0XSA9IGFyZ3M7XG4gICAgICAgICAgdGhpcy5rbmV4UXVlcnlbam9pblR5cGVdKHNwZWMucmF3UXVlcnkoKS5hcyhhbGlhcyksIGxlZnQsIHJpZ2h0KTtcbiAgICAgICAgfVxuICAgICAgfSBlbHNlIHtcbiAgICAgICAgdGhyb3cgbmV3IEVycm9yKFwiSW52YWxpZCB0YWJsZSBzcGVjaWZpY2F0aW9uXCIpO1xuICAgICAgfVxuICAgIH0gZWxzZSB7XG4gICAgICB0aHJvdyBuZXcgRXJyb3IoXCJJbnZhbGlkIGFyZ3VtZW50c1wiKTtcbiAgICB9XG5cbiAgICB0aGlzLmNvcnJlbGF0aW9uUmVnaXN0cnkuc2V0KHJlZ2lzdHJhdGlvbi5hbGlhcywgcmVnaXN0cmF0aW9uKTtcbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIHByaXZhdGUgX19lbnN1cmVKb2luKFxuICAgIGpvaW5UeXBlOiBcImpvaW5cIiB8IFwibGVmdEpvaW5cIixcbiAgICB0YWJsZU5hbWVPclNwZWM6IHN0cmluZyB8IFJlY29yZDxzdHJpbmcsIHN0cmluZz4sXG4gICAgbGVmdDogc3RyaW5nLFxuICAgIHJpZ2h0OiBzdHJpbmcsXG4gICk6IHRoaXMge1xuICAgIGNvbnN0IHJlcXVlc3RlZCA9IHRoaXMuY3JlYXRlSm9pblJlZ2lzdHJhdGlvbihqb2luVHlwZSwgdGFibGVOYW1lT3JTcGVjLCBbbGVmdCwgcmlnaHRdKTtcbiAgICBpZiAoIXJlcXVlc3RlZC5yZXVzYWJsZSkge1xuICAgICAgdGhyb3cgbmV3IEVycm9yKFxuICAgICAgICBgJHtqb2luVHlwZSA9PT0gXCJqb2luXCIgPyBcImVuc3VyZUpvaW5cIiA6IFwiZW5zdXJlTGVmdEpvaW5cIn0gb25seSBzdXBwb3J0cyBwaHlzaWNhbCB0YWJsZXMgd2l0aCBzaW1wbGUgY29sdW1uIGVxdWFsaXR5IGNvbmRpdGlvbnMuYCxcbiAgICAgICk7XG4gICAgfVxuICAgIGNvbnN0IGV4aXN0aW5nID0gdGhpcy5jb3JyZWxhdGlvblJlZ2lzdHJ5LmdldChyZXF1ZXN0ZWQuYWxpYXMpO1xuXG4gICAgaWYgKCFleGlzdGluZykge1xuICAgICAgcmV0dXJuIHRoaXMuX19jb21tb25Kb2luKGpvaW5UeXBlLCB0YWJsZU5hbWVPclNwZWMsIGxlZnQsIHJpZ2h0KTtcbiAgICB9XG5cbiAgICBpZiAodGhpcy5pc1NhbWVKb2luUmVnaXN0cmF0aW9uKGV4aXN0aW5nLCByZXF1ZXN0ZWQpKSB7XG4gICAgICByZXR1cm4gdGhpcztcbiAgICB9XG5cbiAgICB0aHJvdyB0aGlzLmNyZWF0ZUpvaW5Db25mbGljdEVycm9yKGV4aXN0aW5nLCByZXF1ZXN0ZWQpO1xuICB9XG5cbiAgcHJpdmF0ZSBjcmVhdGVKb2luUmVnaXN0cmF0aW9uKFxuICAgIGpvaW5UeXBlOiBcImpvaW5cIiB8IFwibGVmdEpvaW5cIixcbiAgICB0YWJsZU5hbWVPclNwZWM6IGFueSxcbiAgICBhcmdzOiBhbnlbXSxcbiAgKTogSm9pblJlZ2lzdHJhdGlvbiB7XG4gICAgbGV0IGFsaWFzOiBzdHJpbmc7XG4gICAgbGV0IHRhYmxlOiBzdHJpbmcgfCBudWxsO1xuXG4gICAgaWYgKHR5cGVvZiB0YWJsZU5hbWVPclNwZWMgPT09IFwic3RyaW5nXCIpIHtcbiAgICAgIGFsaWFzID0gdGFibGVOYW1lT3JTcGVjO1xuICAgICAgdGFibGUgPSB0YWJsZU5hbWVPclNwZWM7XG4gICAgfSBlbHNlIGlmICh0eXBlb2YgdGFibGVOYW1lT3JTcGVjID09PSBcIm9iamVjdFwiKSB7XG4gICAgICBjb25zdCBlbnRyaWVzID0gT2JqZWN0LmVudHJpZXModGFibGVOYW1lT3JTcGVjKTtcbiAgICAgIGlmIChlbnRyaWVzLmxlbmd0aCAhPT0gMSkge1xuICAgICAgICB0aHJvdyBuZXcgRXJyb3IoXCJUYWJsZSBzcGVjIG11c3QgaGF2ZSBleGFjdGx5IG9uZSBlbnRyeVwiKTtcbiAgICAgIH1cbiAgICAgIGFzc2VydChlbnRyaWVzWzBdKTtcbiAgICAgIGNvbnN0IFtbam9pbkFsaWFzLCBzcGVjXV0gPSBlbnRyaWVzO1xuICAgICAgYWxpYXMgPSBqb2luQWxpYXM7XG4gICAgICB0YWJsZSA9IHR5cGVvZiBzcGVjID09PSBcInN0cmluZ1wiID8gc3BlYyA6IG51bGw7XG4gICAgfSBlbHNlIHtcbiAgICAgIHRocm93IG5ldyBFcnJvcihcIkludmFsaWQgYXJndW1lbnRzXCIpO1xuICAgIH1cblxuICAgIGNvbnN0IFtsZWZ0LCByaWdodF0gPSBhcmdzO1xuICAgIGNvbnN0IHJldXNhYmxlID1cbiAgICAgIHRhYmxlICE9PSBudWxsICYmIGFyZ3MubGVuZ3RoID09PSAyICYmIHR5cGVvZiBsZWZ0ID09PSBcInN0cmluZ1wiICYmIHR5cGVvZiByaWdodCA9PT0gXCJzdHJpbmdcIjtcblxuICAgIHJldHVybiB7XG4gICAgICBraW5kOiBcImpvaW5cIixcbiAgICAgIGFsaWFzLFxuICAgICAgdGFibGUsXG4gICAgICBqb2luVHlwZSxcbiAgICAgIGxlZnQ6IHJldXNhYmxlID8gbGVmdCA6IG51bGwsXG4gICAgICByaWdodDogcmV1c2FibGUgPyByaWdodCA6IG51bGwsXG4gICAgICByZXVzYWJsZSxcbiAgICB9O1xuICB9XG5cbiAgcHJpdmF0ZSBhc3NlcnRDb3JyZWxhdGlvbkF2YWlsYWJsZShyZXF1ZXN0ZWQ6IEpvaW5SZWdpc3RyYXRpb24pOiB2b2lkIHtcbiAgICBjb25zdCBleGlzdGluZyA9IHRoaXMuY29ycmVsYXRpb25SZWdpc3RyeS5nZXQocmVxdWVzdGVkLmFsaWFzKTtcbiAgICBpZiAoZXhpc3RpbmcpIHtcbiAgICAgIGlmICh0aGlzLmlzU2FtZUpvaW5SZWdpc3RyYXRpb24oZXhpc3RpbmcsIHJlcXVlc3RlZCkpIHtcbiAgICAgICAgdGhyb3cgbmV3IEVycm9yKFxuICAgICAgICAgIGBKb2luIGFsaWFzIFwiJHtyZXF1ZXN0ZWQuYWxpYXN9XCIgaXMgYWxyZWFkeSByZWdpc3RlcmVkLiBVc2UgZW5zdXJlSm9pbigpIG9yIGVuc3VyZUxlZnRKb2luKCkgdG8gcmV1c2UgYW4gaWRlbnRpY2FsIGpvaW4uYCxcbiAgICAgICAgKTtcbiAgICAgIH1cbiAgICAgIHRocm93IHRoaXMuY3JlYXRlSm9pbkNvbmZsaWN0RXJyb3IoZXhpc3RpbmcsIHJlcXVlc3RlZCk7XG4gICAgfVxuICB9XG5cbiAgcHJpdmF0ZSBpc1NhbWVKb2luUmVnaXN0cmF0aW9uKFxuICAgIGV4aXN0aW5nOiBDb3JyZWxhdGlvblJlZ2lzdHJhdGlvbixcbiAgICByZXF1ZXN0ZWQ6IEpvaW5SZWdpc3RyYXRpb24sXG4gICk6IGV4aXN0aW5nIGlzIEpvaW5SZWdpc3RyYXRpb24ge1xuICAgIHJldHVybiAoXG4gICAgICBleGlzdGluZy5raW5kID09PSBcImpvaW5cIiAmJlxuICAgICAgZXhpc3RpbmcucmV1c2FibGUgJiZcbiAgICAgIHJlcXVlc3RlZC5yZXVzYWJsZSAmJlxuICAgICAgZXhpc3RpbmcudGFibGUgPT09IHJlcXVlc3RlZC50YWJsZSAmJlxuICAgICAgZXhpc3Rpbmcuam9pblR5cGUgPT09IHJlcXVlc3RlZC5qb2luVHlwZSAmJlxuICAgICAgZXhpc3RpbmcubGVmdCA9PT0gcmVxdWVzdGVkLmxlZnQgJiZcbiAgICAgIGV4aXN0aW5nLnJpZ2h0ID09PSByZXF1ZXN0ZWQucmlnaHRcbiAgICApO1xuICB9XG5cbiAgcHJpdmF0ZSBjcmVhdGVKb2luQ29uZmxpY3RFcnJvcihcbiAgICBleGlzdGluZzogQ29ycmVsYXRpb25SZWdpc3RyYXRpb24sXG4gICAgcmVxdWVzdGVkOiBKb2luUmVnaXN0cmF0aW9uLFxuICApOiBFcnJvciB7XG4gICAgcmV0dXJuIG5ldyBFcnJvcihcbiAgICAgIFtcbiAgICAgICAgYEpvaW4gYWxpYXMgXCIke3JlcXVlc3RlZC5hbGlhc31cIiBpcyBhbHJlYWR5IHJlZ2lzdGVyZWQgd2l0aCBhIGRpZmZlcmVudCBkZWZpbml0aW9uLmAsXG4gICAgICAgIGBFeGlzdGluZzogJHt0aGlzLmZvcm1hdENvcnJlbGF0aW9uUmVnaXN0cmF0aW9uKGV4aXN0aW5nKX1gLFxuICAgICAgICBgUmVxdWVzdGVkOiAke3RoaXMuZm9ybWF0Q29ycmVsYXRpb25SZWdpc3RyYXRpb24ocmVxdWVzdGVkKX1gLFxuICAgICAgXS5qb2luKFwiXFxuXCIpLFxuICAgICk7XG4gIH1cblxuICBwcml2YXRlIGZvcm1hdENvcnJlbGF0aW9uUmVnaXN0cmF0aW9uKHJlZ2lzdHJhdGlvbjogQ29ycmVsYXRpb25SZWdpc3RyYXRpb24pOiBzdHJpbmcge1xuICAgIGlmIChyZWdpc3RyYXRpb24ua2luZCA9PT0gXCJmcm9tXCIpIHtcbiAgICAgIHJldHVybiBgRlJPTSAke3JlZ2lzdHJhdGlvbi50YWJsZSA/PyBcInN1YnF1ZXJ5XCJ9IEFTICR7cmVnaXN0cmF0aW9uLmFsaWFzfWA7XG4gICAgfVxuXG4gICAgY29uc3Qgam9pbktleXdvcmQgPSByZWdpc3RyYXRpb24uam9pblR5cGUgPT09IFwiam9pblwiID8gXCJKT0lOXCIgOiBcIkxFRlQgSk9JTlwiO1xuICAgIGNvbnN0IHNvdXJjZSA9IHJlZ2lzdHJhdGlvbi50YWJsZSA/PyBcIm9wYXF1ZSBzb3VyY2VcIjtcbiAgICBjb25zdCBjb25kaXRpb24gPSByZWdpc3RyYXRpb24ucmV1c2FibGVcbiAgICAgID8gYCBPTiAke3JlZ2lzdHJhdGlvbi5sZWZ0fSA9ICR7cmVnaXN0cmF0aW9uLnJpZ2h0fWBcbiAgICAgIDogXCIgd2l0aCBvcGFxdWUgY29uZGl0aW9uXCI7XG4gICAgcmV0dXJuIGAke2pvaW5LZXl3b3JkfSAke3NvdXJjZX0gQVMgJHtyZWdpc3RyYXRpb24uYWxpYXN9JHtjb25kaXRpb259YDtcbiAgfVxuXG4gIHByaXZhdGUgY2xlYXJKb2luUmVnaXN0cmF0aW9ucygpOiB2b2lkIHtcbiAgICBmb3IgKGNvbnN0IFthbGlhcywgcmVnaXN0cmF0aW9uXSBvZiB0aGlzLmNvcnJlbGF0aW9uUmVnaXN0cnkpIHtcbiAgICAgIGlmIChyZWdpc3RyYXRpb24ua2luZCA9PT0gXCJqb2luXCIpIHtcbiAgICAgICAgdGhpcy5jb3JyZWxhdGlvblJlZ2lzdHJ5LmRlbGV0ZShhbGlhcyk7XG4gICAgICB9XG4gICAgfVxuICB9XG5cbiAgcHJpdmF0ZSBnZXRLbmV4Sm9pbkFsaWFzKHRhYmxlOiB1bmtub3duKTogc3RyaW5nIHwgbnVsbCB7XG4gICAgaWYgKHR5cGVvZiB0YWJsZSA9PT0gXCJzdHJpbmdcIikge1xuICAgICAgcmV0dXJuIHRhYmxlO1xuICAgIH1cbiAgICBpZiAodHlwZW9mIHRhYmxlID09PSBcIm9iamVjdFwiICYmIHRhYmxlICE9PSBudWxsKSB7XG4gICAgICBpZiAoXG4gICAgICAgIFwiX3NpbmdsZVwiIGluIHRhYmxlICYmXG4gICAgICAgIHR5cGVvZiB0YWJsZS5fc2luZ2xlID09PSBcIm9iamVjdFwiICYmXG4gICAgICAgIHRhYmxlLl9zaW5nbGUgIT09IG51bGwgJiZcbiAgICAgICAgXCJhc1wiIGluIHRhYmxlLl9zaW5nbGUgJiZcbiAgICAgICAgdHlwZW9mIHRhYmxlLl9zaW5nbGUuYXMgPT09IFwic3RyaW5nXCJcbiAgICAgICkge1xuICAgICAgICByZXR1cm4gdGFibGUuX3NpbmdsZS5hcztcbiAgICAgIH1cbiAgICAgIHJldHVybiBPYmplY3Qua2V5cyh0YWJsZSlbMF0gPz8gbnVsbDtcbiAgICB9XG4gICAgcmV0dXJuIG51bGw7XG4gIH1cblxuICAvLyBXSEVSRTog6rCd7LK0IC0g7IKs7JqpOiAud2hlcmUoeyBcInUuaWRcIjogMSwgXCJ1LnN0YXR1c1wiOiBcImFjdGl2ZVwiIH0pXG4gIHdoZXJlKGNvbmRpdGlvbnM6IFdoZXJlQ29uZGl0aW9uPFRUYWJsZXM+KTogdGhpcztcbiAgLy8gV0hFUkU6IOy7rOufvCAtIOyCrOyaqTogLndoZXJlKFwidS5pZFwiLCAxKSwgLndoZXJlKFwidS5pZFwiLCBudWxsKVxuICB3aGVyZTxUQ29sdW1uIGV4dGVuZHMgQXZhaWxhYmxlQ29sdW1uczxUVGFibGVzPj4oXG4gICAgY29sdW1uOiBUQ29sdW1uLFxuICAgIHZhbHVlOiBFeHRyYWN0Q29sdW1uVHlwZTxUVGFibGVzLCBUQ29sdW1uICYgc3RyaW5nPixcbiAgKTogdGhpcztcbiAgLy8gV0hFUkU6IOy7rOufvCAtIOyCrOyaqTogLndoZXJlKFwidS5pZFwiLCBcIj5cIiwgMTApLCAud2hlcmUoXCJ1LmlkXCIsIFwiIT1cIiwgbnVsbClcbiAgd2hlcmU8VENvbHVtbiBleHRlbmRzIEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcz4+KFxuICAgIGNvbHVtbjogVENvbHVtbixcbiAgICBvcGVyYXRvcjogV2hlcmVPcGVyYXRvcixcbiAgICB2YWx1ZTogRXh0cmFjdENvbHVtblR5cGU8VFRhYmxlcywgVENvbHVtbiAmIHN0cmluZz4sXG4gICk6IHRoaXM7XG4gIC8vIFdIRVJFOiBTUUwg7ZGc7ZiE7IudIC0g7IKs7JqpOiAud2hlcmUocHVyaS5yYXcoXCJDT05DQVQodS5uYW1lLCB1LmVtYWlsKVwiKSwgXCJsaWtlXCIsIFwiJXRlc3QlXCIpXG4gIHdoZXJlPFRDb2x1bW4gZXh0ZW5kcyBLbmV4LlJhdz4oY29sdW1uOiBUQ29sdW1uLCBvcGVyYXRvcjogV2hlcmVPcGVyYXRvciwgdmFsdWU6IGFueSk6IHRoaXM7XG4gIC8vIFdIRVJFOiDsu6zrn7wgLSDsgqzsmqk6IC53aGVyZShcInUuaWRcIiwgXCJsaWtlXCIsIFwiJXRlc3QlXCIpXG4gIHdoZXJlKC4uLmFyZ3M6IFtjb2x1bW5PckNvbmRpdGlvbnM6IGFueSwgb3BlcmF0b3JPclZhbHVlPzogYW55LCB2YWx1ZT86IGFueV0pOiB0aGlzIHtcbiAgICBjb25zdCBbY29sdW1uT3JDb25kaXRpb25zLCBvcGVyYXRvck9yVmFsdWUsIHZhbHVlXSA9IGFyZ3M7XG4gICAgaWYgKHR5cGVvZiBjb2x1bW5PckNvbmRpdGlvbnMgPT09IFwib2JqZWN0XCIpIHtcbiAgICAgIHRoaXMua25leFF1ZXJ5LndoZXJlKGNvbHVtbk9yQ29uZGl0aW9ucyk7XG4gICAgfSBlbHNlIGlmICh0eXBlb2YgdmFsdWUgPT09IFwidW5kZWZpbmVkXCIpIHtcbiAgICAgIGlmIChvcGVyYXRvck9yVmFsdWUgPT09IG51bGwpIHtcbiAgICAgICAgdGhpcy5rbmV4UXVlcnkud2hlcmVOdWxsKGNvbHVtbk9yQ29uZGl0aW9ucyk7XG4gICAgICAgIHJldHVybiB0aGlzO1xuICAgICAgfVxuICAgICAgdGhpcy5rbmV4UXVlcnkud2hlcmUoY29sdW1uT3JDb25kaXRpb25zLCBvcGVyYXRvck9yVmFsdWUpO1xuICAgIH0gZWxzZSBpZiAodHlwZW9mIHZhbHVlICE9PSBcInVuZGVmaW5lZFwiKSB7XG4gICAgICBpZiAodmFsdWUgPT09IG51bGwpIHtcbiAgICAgICAgaWYgKG9wZXJhdG9yT3JWYWx1ZSA9PT0gXCIhPVwiKSB7XG4gICAgICAgICAgdGhpcy5rbmV4UXVlcnkud2hlcmVOb3ROdWxsKGNvbHVtbk9yQ29uZGl0aW9ucyk7XG4gICAgICAgICAgcmV0dXJuIHRoaXM7XG4gICAgICAgIH0gZWxzZSBpZiAob3BlcmF0b3JPclZhbHVlID09PSBcIj1cIikge1xuICAgICAgICAgIHRoaXMua25leFF1ZXJ5LndoZXJlTnVsbChjb2x1bW5PckNvbmRpdGlvbnMpO1xuICAgICAgICAgIHJldHVybiB0aGlzO1xuICAgICAgICB9XG4gICAgICB9XG4gICAgICB0aGlzLmtuZXhRdWVyeS53aGVyZShjb2x1bW5PckNvbmRpdGlvbnMsIG9wZXJhdG9yT3JWYWx1ZSwgdmFsdWUpO1xuICAgIH0gZWxzZSB7XG4gICAgICB0aGlzLmtuZXhRdWVyeS53aGVyZShjb2x1bW5PckNvbmRpdGlvbnMpO1xuICAgIH1cbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIC8vIFdIRVJFIElOXG4gIHdoZXJlSW48VENvbHVtbiBleHRlbmRzIEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcz4+KFxuICAgIGNvbHVtbjogVENvbHVtbixcbiAgICB2YWx1ZXM6IEV4dHJhY3RDb2x1bW5UeXBlPFRUYWJsZXMsIFRDb2x1bW4gJiBzdHJpbmc+W10sXG4gICk6IFB1cmk8VFNjaGVtYSwgVFRhYmxlcywgVFJlc3VsdD4ge1xuICAgIHRoaXMua25leFF1ZXJ5LndoZXJlSW4oY29sdW1uLCB2YWx1ZXMpO1xuICAgIHJldHVybiB0aGlzIGFzIGFueTtcbiAgfVxuXG4gIC8vIFdIRVJFIE5PVCBJTlxuICB3aGVyZU5vdEluPFRDb2x1bW4gZXh0ZW5kcyBBdmFpbGFibGVDb2x1bW5zPFRUYWJsZXM+PihcbiAgICBjb2x1bW46IFRDb2x1bW4sXG4gICAgdmFsdWVzOiBFeHRyYWN0Q29sdW1uVHlwZTxUVGFibGVzLCBUQ29sdW1uICYgc3RyaW5nPltdLFxuICApOiBQdXJpPFRTY2hlbWEsIFRUYWJsZXMsIFRSZXN1bHQ+IHtcbiAgICB0aGlzLmtuZXhRdWVyeS53aGVyZU5vdEluKGNvbHVtbiwgdmFsdWVzKTtcbiAgICByZXR1cm4gdGhpcyBhcyBhbnk7XG4gIH1cblxuICAvLyBXSEVSRSBKU09OQiBTVVBFUlNFVCAoQD4pXG4gIHdoZXJlSnNvblN1cGVyc2V0T2Y8VENvbHVtbiBleHRlbmRzIEpzb25Db2x1bW5zPFRUYWJsZXM+PihcbiAgICBjb2x1bW46IFRDb2x1bW4sXG4gICAgdmFsdWU6IEpzb25TdXBlcnNldFZhbHVlPEV4dHJhY3RDb2x1bW5UeXBlPFRUYWJsZXMsIFRDb2x1bW4+PixcbiAgKTogdGhpcyB7XG4gICAgdGhpcy5rbmV4UXVlcnkud2hlcmVKc29uU3VwZXJzZXRPZihjb2x1bW4sIHNlcmlhbGl6ZUpzb25TdXBlcnNldFZhbHVlKHZhbHVlKSk7XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICAvLyBXSEVSRSBNQVRDSFxuICB3aGVyZU1hdGNoPFRDb2x1bW4gZXh0ZW5kcyBGdWxsdGV4dENvbHVtbnM8VFRhYmxlcz4+KGNvbHVtbjogVENvbHVtbiwgdmFsdWU6IHN0cmluZyk6IHRoaXMge1xuICAgIHRoaXMua25leFF1ZXJ5LndoZXJlUmF3KGBNQVRDSCAoJHtTdHJpbmcoY29sdW1uKX0pIEFHQUlOU1QgKD8pYCwgW3ZhbHVlXSk7XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICAvKipcbiAgICogUEdyb29uZ2EgRnVsbFRleHQg7J24642x7IqkIOqygOyDiVxuICAgKiAtIOyCrOyaqe2VoCBQR3Jvb25nYSDsnbjrjbHsiqTsmYAg64+Z7J287ZWcIOy7rOufvCDqtazshLHsnLzroZwg6rKA7IOJ7ZW07JW8IOyduOuNseyKpOqwgCDsgqzsmqnrkKnri4jri6QuXG4gICAqXG4gICAqIOuLqOydvCDsu6zrn7wg6rKA7IOJOlxuICAgKiBgYGBzcWxcbiAgICogV0hFUkUgbmFtZSAmQH4gJ3NlYXJjaCdcbiAgICogYGBgXG4gICAqXG4gICAqIOuzte2VqSDsu6zrn7wg6rKA7IOJOlxuICAgKiBgYGBzcWxcbiAgICogV0hFUkUgQVJSQVlbbmFtZTo6dGV4dCwgZGVzY3JpcHRpb246OnRleHRdICZAfiAnc2VhcmNoJ1xuICAgKiBgYGBcbiAgICovXG4gIHdoZXJlU2VhcmNoPFRDb2x1bW4gZXh0ZW5kcyBBdmFpbGFibGVDb2x1bW5zPFRUYWJsZXM+PihcbiAgICBjb2x1bW46IFRDb2x1bW4gfCBUQ29sdW1uW10sXG4gICAgdmFsdWU6IHN0cmluZyxcbiAgICBvcHRpb25zPzoge1xuICAgICAgd2VpZ2h0cz86IG51bWJlcltdOyAvLyDsoJXsiJgg67Cw7Je0XG4gICAgfSxcbiAgKTogdGhpcyB7XG4gICAgY29uc3QgeyB3ZWlnaHRzIH0gPSBvcHRpb25zID8/IHt9O1xuICAgIGNvbnN0IGNvbHVtbkV4cHIgPSBBcnJheS5pc0FycmF5KGNvbHVtbilcbiAgICAgID8gYEFSUkFZWyR7Y29sdW1uLm1hcCgoYykgPT4gYCR7Y306OnRleHRgKS5qb2luKFwiLFwiKX1dYFxuICAgICAgOiBjb2x1bW47XG4gICAgY29uc3QgcGdyb29uZ2FDb25kaXRpb24gPSBgcGdyb29uZ2FfY29uZGl0aW9uKD8ke3dlaWdodHM/Lmxlbmd0aCA/IGAsIHdlaWdodHMgPT4gQVJSQVlbJHt3ZWlnaHRzLmpvaW4oXCIsXCIpfV1gIDogXCJcIn0pYDtcblxuICAgIHRoaXMua25leFF1ZXJ5LndoZXJlUmF3KGAke2NvbHVtbkV4cHJ9ICZAfiAke3Bncm9vbmdhQ29uZGl0aW9ufWAsIFt2YWx1ZV0pO1xuXG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICAvLyBXSEVSRSBGVUxMVEVYVFxuICB3aGVyZVRzU2VhcmNoPFRDb2x1bW4gZXh0ZW5kcyBBdmFpbGFibGVDb2x1bW5zPFRUYWJsZXM+IHwgU3FsRXhwcmVzc2lvbjxcInN0cmluZ1wiPj4oXG4gICAgY29sdW1uOiBUQ29sdW1uLFxuICAgIHZhbHVlOiBzdHJpbmcsXG4gICAgb3B0aW9ucz86IFRzUXVlcnlPcHRpb25zIHwgVHNRdWVyeUNvbmZpZyxcbiAgKTogdGhpcyB7XG4gICAgY29uc3Qgb3B0cyA9XG4gICAgICB0eXBlb2Ygb3B0aW9ucyA9PT0gXCJzdHJpbmdcIiA/ICh7IGNvbmZpZzogb3B0aW9ucyB9IGFzIFRzUXVlcnlPcHRpb25zKSA6IChvcHRpb25zID8/IHt9KTtcblxuICAgIGNvbnN0IHBhcnNlciA9IG9wdHMucGFyc2VyID8/IFwid2Vic2VhcmNoX3RvX3RzcXVlcnlcIjtcbiAgICBjb25zdCBjb25maWcgPSBvcHRzLmNvbmZpZyA/PyBcInNpbXBsZVwiO1xuICAgIGNvbnN0IGNvbHVtbkV4cHIgPVxuICAgICAgdHlwZW9mIGNvbHVtbiA9PT0gXCJvYmplY3RcIiAmJiBjb2x1bW4uX3R5cGUgPT09IFwic3FsX2V4cHJlc3Npb25cIlxuICAgICAgICA/IGNvbHVtbi5fc3FsXG4gICAgICAgIDogU3RyaW5nKGNvbHVtbik7XG5cbiAgICB0aGlzLmtuZXhRdWVyeS53aGVyZVJhdyhgJHtjb2x1bW5FeHByfSBAQCAke3BhcnNlcn0oPywgPylgLCBbY29uZmlnLCB2YWx1ZV0pO1xuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgd2hlcmVGdXp6eTxUQ29sdW1uIGV4dGVuZHMgQXZhaWxhYmxlQ29sdW1uczxUVGFibGVzPiB8IFNxbEV4cHJlc3Npb248XCJzdHJpbmdcIj4+KFxuICAgIGNvbHVtbjogVENvbHVtbixcbiAgICB2YWx1ZTogc3RyaW5nLFxuICAgIG9wdGlvbnM/OiB7XG4gICAgICBvcGVyYXRvcj86IEZ1enp5T3BlcmF0b3I7XG4gICAgfSxcbiAgKTogdGhpcyB7XG4gICAgY29uc3Qgb3BlcmF0b3IgPSBub3JtYWxpemVGdXp6eU9wZXJhdG9yKG9wdGlvbnM/Lm9wZXJhdG9yKTtcblxuICAgIGlmIChvcGVyYXRvciA9PT0gXCIlXCIpIHtcbiAgICAgIGlmICh0eXBlb2YgY29sdW1uID09PSBcIm9iamVjdFwiKSB7XG4gICAgICAgIHRoaXMua25leFF1ZXJ5LndoZXJlUmF3KGAke2NvbHVtbi5fc3FsfSAke29wZXJhdG9yfSA/YCwgWy4uLmNvbHVtbi5fcGFyYW1zLCB2YWx1ZV0pO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgdGhpcy5rbmV4UXVlcnkud2hlcmVSYXcoYD8/ICR7b3BlcmF0b3J9ID9gLCBbY29sdW1uLCB2YWx1ZV0pO1xuICAgICAgfVxuICAgICAgcmV0dXJuIHRoaXM7XG4gICAgfVxuXG4gICAgaWYgKHR5cGVvZiBjb2x1bW4gPT09IFwib2JqZWN0XCIpIHtcbiAgICAgIHRoaXMua25leFF1ZXJ5LndoZXJlUmF3KGA/ICR7b3BlcmF0b3J9ICR7Y29sdW1uLl9zcWx9YCwgW3ZhbHVlLCAuLi5jb2x1bW4uX3BhcmFtc10pO1xuICAgIH0gZWxzZSB7XG4gICAgICB0aGlzLmtuZXhRdWVyeS53aGVyZVJhdyhgPyAke29wZXJhdG9yfSA/P2AsIFt2YWx1ZSwgY29sdW1uXSk7XG4gICAgfVxuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgLy8gV0hFUkUgUkFXXG4gIHdoZXJlUmF3KHNxbDogc3RyaW5nLCBiaW5kaW5ncz86IHJlYWRvbmx5IEtuZXguUmF3QmluZGluZ1tdKTogdGhpcyB7XG4gICAgdGhpcy5rbmV4UXVlcnkud2hlcmVSYXcoc3FsLCBiaW5kaW5ncyk7XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICAvLyBXSEVSRSDqtITtmLgg6re466O57ZWRXG4gIHdoZXJlR3JvdXAoY2FsbGJhY2s6IChnOiBXaGVyZUdyb3VwPFRUYWJsZXM+KSA9PiB2b2lkKTogdGhpcyB7XG4gICAgdGhpcy5rbmV4UXVlcnkud2hlcmUoKGJ1aWxkZXIpID0+IHtcbiAgICAgIGNvbnN0IGdyb3VwID0gbmV3IFdoZXJlR3JvdXA8VFRhYmxlcz4oYnVpbGRlcik7XG4gICAgICBjYWxsYmFjayhncm91cCk7XG4gICAgfSk7XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cbiAgb3JXaGVyZUdyb3VwKGNhbGxiYWNrOiAoZzogV2hlcmVHcm91cDxUVGFibGVzPikgPT4gdm9pZCk6IHRoaXMge1xuICAgIHRoaXMua25leFF1ZXJ5Lm9yV2hlcmUoKGJ1aWxkZXIpID0+IHtcbiAgICAgIGNvbnN0IGdyb3VwID0gbmV3IFdoZXJlR3JvdXA8VFRhYmxlcz4oYnVpbGRlcik7XG4gICAgICBjYWxsYmFjayhncm91cCk7XG4gICAgfSk7XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICAvLyBPUkRFUiBCWSAoU3FsRXhwcmVzc2lvbuycvOuhnOuPhCDtlaAg7IiYIOyeiOyWtOyVvCDtlagpXG4gIG9yZGVyQnk8VENvbHVtbiBleHRlbmRzIFJlc3VsdEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcywgVFJlc3VsdD4+KFxuICAgIGNvbHVtbjogVENvbHVtbiB8IFB1cmlPcmRlckJ5RXhwcmVzc2lvbixcbiAgICBkaXJlY3Rpb24/OiBQdXJpT3JkZXJCeURpcmVjdGlvbixcbiAgICBudWxscz86IFB1cmlPcmRlckJ5TnVsbHMsXG4gICk6IHRoaXM7XG4gIG9yZGVyQnk8VENvbHVtbiBleHRlbmRzIFJlc3VsdEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcywgVFJlc3VsdD4+KFxuICAgIGNvbHVtbnM6IHJlYWRvbmx5IFB1cmlPcmRlckJ5RW50cnk8VENvbHVtbj5bXSxcbiAgKTogdGhpcztcbiAgb3JkZXJCeShcbiAgICBjb2x1bW5PckNvbHVtbnM6IHN0cmluZyB8IFB1cmlPcmRlckJ5RXhwcmVzc2lvbiB8IHJlYWRvbmx5IFB1cmlPcmRlckJ5UnVudGltZUVudHJ5W10sXG4gICAgZGlyZWN0aW9uOiBQdXJpT3JkZXJCeURpcmVjdGlvbiA9IFwiYXNjXCIsXG4gICAgbnVsbHM/OiBQdXJpT3JkZXJCeU51bGxzLFxuICApOiB0aGlzIHtcbiAgICBpZiAoaXNPcmRlckJ5RW50cmllcyhjb2x1bW5PckNvbHVtbnMpKSB7XG4gICAgICBmb3IgKGNvbnN0IGVudHJ5IG9mIGNvbHVtbk9yQ29sdW1ucykge1xuICAgICAgICBpZiAodHlwZW9mIGVudHJ5ID09PSBcInN0cmluZ1wiIHx8IGlzU3FsRXhwcmVzc2lvbihlbnRyeSkpIHtcbiAgICAgICAgICB0aGlzLmFwcGx5T3JkZXJCeShlbnRyeSk7XG4gICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgdGhpcy5hcHBseU9yZGVyQnkoZW50cnkuY29sdW1uLCBlbnRyeS5vcmRlciwgZW50cnkubnVsbHMpO1xuICAgICAgICB9XG4gICAgICB9XG4gICAgICByZXR1cm4gdGhpcztcbiAgICB9XG5cbiAgICB0aGlzLmFwcGx5T3JkZXJCeShjb2x1bW5PckNvbHVtbnMsIGRpcmVjdGlvbiwgbnVsbHMpO1xuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgcHJpdmF0ZSBhcHBseU9yZGVyQnkoXG4gICAgY29sdW1uOiBzdHJpbmcgfCBQdXJpT3JkZXJCeUV4cHJlc3Npb24sXG4gICAgZGlyZWN0aW9uPzogUHVyaU9yZGVyQnlEaXJlY3Rpb24sXG4gICAgbnVsbHM/OiBQdXJpT3JkZXJCeU51bGxzLFxuICApOiB2b2lkIHtcbiAgICBjb25zdCBub3JtYWxpemVkRGlyZWN0aW9uID0gbm9ybWFsaXplT3JkZXJCeURpcmVjdGlvbihkaXJlY3Rpb24pO1xuICAgIGNvbnN0IG5vcm1hbGl6ZWROdWxscyA9IG5vcm1hbGl6ZU9yZGVyQnlOdWxscyhudWxscyk7XG5cbiAgICBpZiAodHlwZW9mIGNvbHVtbiA9PT0gXCJvYmplY3RcIikge1xuICAgICAgdGhpcy5rbmV4UXVlcnkub3JkZXJCeVJhdyhcbiAgICAgICAgYCR7Y29sdW1uLl9zcWx9ICR7bm9ybWFsaXplZERpcmVjdGlvbn0ke2Zvcm1hdE51bGxzU3VmZml4KG5vcm1hbGl6ZWROdWxscyl9YCxcbiAgICAgICAgY29sdW1uLl9wYXJhbXMsXG4gICAgICApO1xuICAgIH0gZWxzZSB7XG4gICAgICB0aGlzLmtuZXhRdWVyeS5vcmRlckJ5KGNvbHVtbiwgbm9ybWFsaXplZERpcmVjdGlvbiwgbm9ybWFsaXplZE51bGxzKTtcbiAgICB9XG4gIH1cblxuICBmb3JVcGRhdGUoKTogdGhpcyB7XG4gICAgdGhpcy5rbmV4UXVlcnkuZm9yVXBkYXRlKCk7XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICBmb3JTaGFyZSgpOiB0aGlzIHtcbiAgICB0aGlzLmtuZXhRdWVyeS5mb3JTaGFyZSgpO1xuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgLyoqXG4gICAqIOuyoe2EsCDsnKDsgqzrj4Qg6rKA7IOJIOyEpOyglVxuICAgKlxuICAgKiAtIFNFTEVDVOyXkCBzaW1pbGFyaXR5IOy7rOufvCDstpTqsIBcbiAgICogLSBXSEVSRSBjb2wgSVMgTk9UIE5VTEwg7LaU6rCAXG4gICAqIC0gdGhyZXNob2xk6rCAIOyeiOycvOuptCBXSEVSRSDsobDqsbQg7LaU6rCAXG4gICAqIC0g6riw7KG0IE9SREVSIEJZ66W8IGNsZWFy7ZWY6rOgIOybkOyLnCDsl7DsgrDsnpDroZwg7KCV66CsIChITlNXIOyduOuNseyKpCDstZzsoIHtmZQpXG4gICAqXG4gICAqIEBwYXJhbSBjb2x1bW4g67Kh7YSwIOy7rOufvCDqsr3roZxcbiAgICogQHBhcmFtIGVtYmVkZGluZyDsv7zrpqwg7J6E67Kg65SpIOuyoe2EsFxuICAgKiBAcGFyYW0gb3B0aW9ucyBtZXRob2QsIHRocmVzaG9sZCwgYXMg65OxIOyYteyFmFxuICAgKlxuICAgKiBAZXhhbXBsZVxuICAgKiBgYGB0eXBlc2NyaXB0XG4gICAqIC8vIGNvc2luZSBzaW1pbGFyaXR5ICjquLDrs7jqsJIpXG4gICAqIHFiLnZlY3RvclNpbWlsYXJpdHkoXCJjb2x1bW5OYW1lXCIsIHF1ZXJ5VmVjdG9yLCB7XG4gICAqICAgbWV0aG9kOiBcImNvc2luZVwiLFxuICAgKiAgIHRocmVzaG9sZDogMC41XG4gICAqIH0pO1xuICAgKlxuICAgKiAvLyBMMiBkaXN0YW5jZVxuICAgKiBxYi52ZWN0b3JTaW1pbGFyaXR5KFwiY29sdW1uTmFtZVwiLCBxdWVyeVZlY3Rvciwge1xuICAgKiAgIG1ldGhvZDogXCJsMlwiLFxuICAgKiAgIHRocmVzaG9sZDogMS41ICAvLyDqsbDrpqzqsIAgMS41IOydtO2VmOyduCDqsrDqs7zrp4xcbiAgICogfSk7XG4gICAqXG4gICAqIC8vIElubmVyIHByb2R1Y3RcbiAgICogcWIudmVjdG9yU2ltaWxhcml0eShcImNvbHVtbk5hbWVcIiwgcXVlcnlWZWN0b3IsIHtcbiAgICogICBtZXRob2Q6IFwiaW5uZXJfcHJvZHVjdFwiLFxuICAgKiAgIHRocmVzaG9sZDogMC43XG4gICAqIH0pO1xuICAgKiBgYGBcbiAgICovXG4gIHZlY3RvclNpbWlsYXJpdHkoXG4gICAgY29sdW1uOiBWZWN0b3JDb2x1bW5zPFRUYWJsZXM+LFxuICAgIGVtYmVkZGluZzogbnVtYmVyW10sXG4gICAgb3B0aW9uczoge1xuICAgICAgbWV0aG9kPzogXCJjb3NpbmVcIiB8IFwibDJcIiB8IFwiaW5uZXJfcHJvZHVjdFwiO1xuICAgICAgdGhyZXNob2xkPzogbnVtYmVyO1xuICAgICAgZGlzdGluY3RPbj86IEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcz47XG4gICAgfSA9IHt9LFxuICApOiBQdXJpPFRTY2hlbWEsIFRUYWJsZXMsIFRSZXN1bHQgJiB7IHNpbWlsYXJpdHk6IG51bWJlciB9PiB7XG4gICAgY29uc3QgeyBtZXRob2QgPSBcImNvc2luZVwiLCB0aHJlc2hvbGQsIGRpc3RpbmN0T24gfSA9IG9wdGlvbnM7XG5cbiAgICBpZiAoXG4gICAgICAhQXJyYXkuaXNBcnJheShlbWJlZGRpbmcpIHx8XG4gICAgICBlbWJlZGRpbmcubGVuZ3RoID09PSAwIHx8XG4gICAgICBlbWJlZGRpbmcuc29tZSgodikgPT4gIU51bWJlci5pc0Zpbml0ZSh2KSlcbiAgICApIHtcbiAgICAgIHRocm93IG5ldyBFcnJvcihcIkludmFsaWQgZW1iZWRkaW5nIHZlY3RvcjogZXhwZWN0ZWQgYSBub24tZW1wdHkgYXJyYXkgb2YgZmluaXRlIG51bWJlcnNcIik7XG4gICAgfVxuXG4gICAgY29uc3QgdmVjdG9yTGl0ZXJhbCA9IEpTT04uc3RyaW5naWZ5KGVtYmVkZGluZy5tYXAoKHYpID0+IE51bWJlcih2KSkpO1xuICAgIGNvbnN0IG9wZXJhdG9yID0geyBjb3NpbmU6IFwiPD0+XCIsIGwyOiBcIjwtPlwiLCBpbm5lcl9wcm9kdWN0OiBcIjwjPlwiIH1bbWV0aG9kXTtcblxuICAgIC8vIG1ldGhvZOuzhCDsl7DsgrDsnpAg67CPIHNpbWlsYXJpdHkg6rOE7IKw7IudXG4gICAgLy8gLSBjb3NpbmU6IDw9PiAoY29zaW5lIGRpc3RhbmNlLCAwfjIpLCBzaW1pbGFyaXR5ID0gMSAtIGRpc3RhbmNlXG4gICAgLy8gLSBsMjogPC0+IChldWNsaWRlYW4gZGlzdGFuY2UpLCBzaW1pbGFyaXR5ID0gZGlzdGFuY2UgKOuCruydhOyImOuhnSDsnKDsgqwpXG4gICAgLy8gLSBpbm5lcl9wcm9kdWN0OiA8Iz4gKG5lZ2F0aXZlIGlubmVyIHByb2R1Y3QpLCBzaW1pbGFyaXR5ID0gLWRpc3RhbmNlICjrhpLsnYTsiJjroZ0g7Jyg7IKsKVxuICAgIGNvbnN0IHNpbWlsYXJpdHlFeHByID1cbiAgICAgIG1ldGhvZCA9PT0gXCJjb3NpbmVcIlxuICAgICAgICA/IHRoaXMua25leC5yYXcoYDEgLSAoPz8gJHtvcGVyYXRvcn0gPzo6dmVjdG9yKSBhcyBzaW1pbGFyaXR5YCwgW2NvbHVtbiwgdmVjdG9yTGl0ZXJhbF0pXG4gICAgICAgIDogbWV0aG9kID09PSBcImwyXCJcbiAgICAgICAgICA/IHRoaXMua25leC5yYXcoYD8/ICR7b3BlcmF0b3J9ID86OnZlY3RvciBhcyBzaW1pbGFyaXR5YCwgW2NvbHVtbiwgdmVjdG9yTGl0ZXJhbF0pXG4gICAgICAgICAgOiB0aGlzLmtuZXgucmF3KGAtKD8/ICR7b3BlcmF0b3J9ID86OnZlY3RvcikgYXMgc2ltaWxhcml0eWAsIFtjb2x1bW4sIHZlY3RvckxpdGVyYWxdKTtcblxuICAgIC8vIFdIRVJFIE5PVCBOVUxMXG4gICAgdGhpcy5rbmV4UXVlcnkud2hlcmVOb3ROdWxsKGNvbHVtbik7XG5cbiAgICAvLyDquLDsobQgT1JERVIgQlkgY2xlYXJcbiAgICB0aGlzLmtuZXhRdWVyeS5jbGVhcihcIm9yZGVyXCIpO1xuICAgIGlmIChkaXN0aW5jdE9uKSB7XG4gICAgICAvLyBESVNUSU5DVCBPTuydgCBTRUxFQ1Qg7KCI7J2YIOunqCDslZ7sl5Ag7JmA7JW8IO2VmOuvgOuhnCwg6riw7KG0IHNlbGVjdChzdWJzZXQg7ZWE65Oc65OkKeulvCDrs7TsobQg7ZuEIGNsZWFy7ZWY6rOgIOuLpOyLnCDstpTqsIBcbiAgICAgIGNvbnN0IGV4aXN0aW5nU3Vic2V0Q29scyA9ICh0aGlzLmtuZXhRdWVyeSBhcyBhbnkpLl9zdGF0ZW1lbnRzXG4gICAgICAgIC5maWx0ZXIoKHM6IGFueSkgPT4gcy5ncm91cGluZyA9PT0gXCJjb2x1bW5zXCIpXG4gICAgICAgIC5mbGF0TWFwKChzOiBhbnkpID0+IHMudmFsdWUpO1xuICAgICAgdGhpcy5rbmV4UXVlcnkuY2xlYXIoXCJzZWxlY3RcIik7XG4gICAgICB0aGlzLmtuZXhRdWVyeS5zZWxlY3QodGhpcy5rbmV4LnJhdyhgRElTVElOQ1QgT04gKD8/KSA/P2AsIFtkaXN0aW5jdE9uLCBkaXN0aW5jdE9uXSkpO1xuICAgICAgZXhpc3RpbmdTdWJzZXRDb2xzLm1hcCgoY29sOiBhbnkpID0+IHRoaXMua25leFF1ZXJ5LnNlbGVjdChjb2wpKTtcbiAgICAgIHRoaXMua25leFF1ZXJ5LnNlbGVjdChzaW1pbGFyaXR5RXhwcik7XG4gICAgICB0aGlzLmtuZXhRdWVyeS5vcmRlckJ5UmF3KGA/PywgPz8gJHtvcGVyYXRvcn0gPzo6dmVjdG9yYCwgW1xuICAgICAgICBkaXN0aW5jdE9uLFxuICAgICAgICBjb2x1bW4sXG4gICAgICAgIHZlY3RvckxpdGVyYWwsXG4gICAgICBdKTtcblxuICAgICAgdGhpcy5rbmV4UXVlcnkgPSB0aGlzLmtuZXhcbiAgICAgICAgLmZyb20odGhpcy5rbmV4UXVlcnkuYXMoXCJkaXN0aW5jdF92ZWN0b3JzXCIpKVxuICAgICAgICAuc2VsZWN0KFwiKlwiKVxuICAgICAgICAub3JkZXJCeShcInNpbWlsYXJpdHlcIiwgXCJkZXNjXCIpO1xuICAgIH0gZWxzZSB7XG4gICAgICB0aGlzLmtuZXhRdWVyeS5zZWxlY3Qoc2ltaWxhcml0eUV4cHIpO1xuICAgICAgdGhpcy5rbmV4UXVlcnkub3JkZXJCeVJhdyhgPz8gJHtvcGVyYXRvcn0gPzo6dmVjdG9yYCwgW2NvbHVtbiwgdmVjdG9yTGl0ZXJhbF0pO1xuICAgIH1cblxuICAgIC8vIHRocmVzaG9sZFxuICAgIGlmICh0eXBlb2YgdGhyZXNob2xkID09PSBcIm51bWJlclwiKSB7XG4gICAgICBpZiAoIU51bWJlci5pc0Zpbml0ZSh0aHJlc2hvbGQpKSB7XG4gICAgICAgIHRocm93IG5ldyBFcnJvcihgSW52YWxpZCB2ZWN0b3JTaW1pbGFyaXR5IHRocmVzaG9sZDogJHt0aHJlc2hvbGR9YCk7XG4gICAgICB9XG5cbiAgICAgIGlmIChkaXN0aW5jdE9uKSB7XG4gICAgICAgIGNvbnN0IHRocmVzaG9sZE9wID0gbWV0aG9kID09PSBcImwyXCIgPyBcIjw9XCIgOiBcIj49XCI7XG4gICAgICAgIHRoaXMua25leFF1ZXJ5LndoZXJlKFwic2ltaWxhcml0eVwiLCB0aHJlc2hvbGRPcCwgdGhyZXNob2xkKTtcbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIGNvbnN0IHRocmVzaG9sZFZhbHVlID1cbiAgICAgICAgICBtZXRob2QgPT09IFwiY29zaW5lXCIgPyAxIC0gdGhyZXNob2xkIDogbWV0aG9kID09PSBcImlubmVyX3Byb2R1Y3RcIiA/IC10aHJlc2hvbGQgOiB0aHJlc2hvbGQ7XG4gICAgICAgIHRoaXMua25leFF1ZXJ5LndoZXJlUmF3KGA/PyAke29wZXJhdG9yfSA/Ojp2ZWN0b3IgPD0gP2AsIFtcbiAgICAgICAgICBjb2x1bW4sXG4gICAgICAgICAgdmVjdG9yTGl0ZXJhbCxcbiAgICAgICAgICB0aHJlc2hvbGRWYWx1ZSxcbiAgICAgICAgXSk7XG4gICAgICB9XG4gICAgfVxuXG4gICAgcmV0dXJuIHRoaXMgYXMgYW55O1xuICB9XG5cbiAgLy8g6riw67O4IOy/vOumrCDrqZTshJzrk5zrk6RcbiAgbGltaXQoY291bnQ6IG51bWJlcik6IHRoaXMge1xuICAgIGlmIChjb3VudCA8IDApIHtcbiAgICAgIHRocm93IG5ldyBFcnJvcihcIkludmFsaWQgbGltaXQ6IG11c3QgYmUgPj0gMFwiKTtcbiAgICB9XG4gICAgdGhpcy5rbmV4UXVlcnkubGltaXQoY291bnQpO1xuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgb2Zmc2V0KGNvdW50OiBudW1iZXIpOiB0aGlzIHtcbiAgICBpZiAoY291bnQgPCAwKSB7XG4gICAgICB0aHJvdyBuZXcgRXJyb3IoXCJJbnZhbGlkIG9mZnNldDogbXVzdCBiZSA+PSAwXCIpO1xuICAgIH1cbiAgICB0aGlzLmtuZXhRdWVyeS5vZmZzZXQoY291bnQpO1xuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgLy8gR1JPVVAgQllcbiAgZ3JvdXBCeTxUQ29sdW1ucyBleHRlbmRzIFJlc3VsdEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcywgVFJlc3VsdD4+KC4uLmNvbHVtbnM6IFRDb2x1bW5zW10pOiB0aGlzO1xuICBncm91cEJ5KC4uLmNvbHVtbnM6IHN0cmluZ1tdKTogdGhpcyB7XG4gICAgdGhpcy5rbmV4UXVlcnkuZ3JvdXBCeSguLi5jb2x1bW5zKTtcbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIC8vIEhBVklOR1xuICBoYXZpbmcoY29uZGl0aW9uOiBzdHJpbmcpOiB0aGlzO1xuICBoYXZpbmc8VENvbHVtbiBleHRlbmRzIFJlc3VsdEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcywgVFJlc3VsdD4+KFxuICAgIGNvbHVtbjogVENvbHVtbixcbiAgICBvcGVyYXRvcjogQ29tcGFyaXNvbk9wZXJhdG9yLFxuICAgIHZhbHVlOiBhbnksXG4gICk6IHRoaXM7XG4gIC8vIEhBVklORyDqtaztmIRcbiAgaGF2aW5nKC4uLmNvbmRpdGlvbnM6IGFueVtdKTogdGhpcyB7XG4gICAgaWYgKGNvbmRpdGlvbnMubGVuZ3RoID09PSAxKSB7XG4gICAgICAvLyBoYXZpbmcoXCJDT1VOVCgqKSA+IDEwXCIpXG4gICAgICB0aGlzLmtuZXhRdWVyeS5oYXZpbmcodGhpcy5rbmV4LnJhdyhjb25kaXRpb25zWzBdKSk7XG4gICAgfSBlbHNlIGlmIChjb25kaXRpb25zLmxlbmd0aCA9PT0gMykge1xuICAgICAgLy8gaGF2aW5nKFwiY291bnRcIiwgXCI+XCIsIDEwKVxuICAgICAgdGhpcy5rbmV4UXVlcnkuaGF2aW5nKFxuICAgICAgICB0aGlzLmtuZXgucmF3KGNvbmRpdGlvbnNbMF0pLFxuICAgICAgICBjb25kaXRpb25zWzFdLFxuICAgICAgICB0aGlzLmtuZXgucmF3KGNvbmRpdGlvbnNbMl0pLFxuICAgICAgKTtcbiAgICB9IGVsc2Uge1xuICAgICAgdGhyb3cgbmV3IEVycm9yKFwiSW52YWxpZCBoYXZpbmcgYXJndW1lbnRzXCIpO1xuICAgIH1cbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIC8vIOyLpO2WiSDrqZTshJzrk5zrk6QgLSB0aGVuYWJsZSDqtaztmIRcbiAgdGhlbjxUUmVzdWx0MSA9IEV4cGFuZDxUUmVzdWx0PltdLCBUUmVzdWx0MiA9IG5ldmVyPihcbiAgICBvbmZ1bGZpbGxlZD86ICgodmFsdWU6IEV4cGFuZDxUUmVzdWx0PltdKSA9PiBUUmVzdWx0MSB8IFByb21pc2VMaWtlPFRSZXN1bHQxPikgfCBudWxsLFxuICAgIG9ucmVqZWN0ZWQ/OiAoKHJlYXNvbjogYW55KSA9PiBUUmVzdWx0MiB8IFByb21pc2VMaWtlPFRSZXN1bHQyPikgfCBudWxsLFxuICApOiBQcm9taXNlPFRSZXN1bHQxIHwgVFJlc3VsdDI+IHtcbiAgICBOYWl0ZS50KFwicHVyaTpleGVjdXRlZC1xdWVyeVwiLCB0aGlzLnRvUXVlcnkoKSk7XG4gICAgcmV0dXJuIHRoaXMua25leFF1ZXJ5LnRoZW4ob25mdWxmaWxsZWQgYXMgYW55LCBvbnJlamVjdGVkKTtcbiAgfVxuICBjYXRjaDxUUmVzdWx0MiA9IG5ldmVyPihcbiAgICBvbnJlamVjdGVkPzogKChyZWFzb246IGFueSkgPT4gVFJlc3VsdDIgfCBQcm9taXNlTGlrZTxUUmVzdWx0Mj4pIHwgbnVsbCxcbiAgKTogUHJvbWlzZTxUUmVzdWx0IHwgVFJlc3VsdDI+IHtcbiAgICByZXR1cm4gdGhpcy5rbmV4UXVlcnkuY2F0Y2gob25yZWplY3RlZCk7XG4gIH1cbiAgZmluYWxseShvbmZpbmFsbHk/OiAoKCkgPT4gdm9pZCkgfCBudWxsKTogUHJvbWlzZTxUUmVzdWx0PiB7XG4gICAgcmV0dXJuIHRoaXMua25leFF1ZXJ5LmZpbmFsbHkob25maW5hbGx5KTtcbiAgfVxuXG4gIC8vIO2VmOuCmOunjCDsv7zrpqxcbiAgZmlyc3QoKTogUmVzb2x2ZWRQdXJpPEV4cGFuZDxUUmVzdWx0PiwgbmV2ZXI+IHtcbiAgICB0aGlzLmtuZXhRdWVyeS5maXJzdCgpO1xuICAgIHJldHVybiBuZXcgUmVzb2x2ZWRQdXJpKHRoaXMua25leFF1ZXJ5LCB0aGlzLmtuZXgsIHRoaXMudGFibGVTcGVjKTtcbiAgfVxuXG4gIC8vIOy/vOumrO2VnCDroIjsvZTrk5zsl5DshJwg7Yq57KCVIOy7rOufvOunjCDstpTstpztlZwg67Cw7Je0IOumrO2EtFxuICBwbHVjazxUQ29sdW1uIGV4dGVuZHMga2V5b2YgVFJlc3VsdCB8IFJlc3VsdEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcywgVFJlc3VsdD4+KFxuICAgIGNvbHVtbjogVENvbHVtbixcbiAgKTogUmVzb2x2ZWRQdXJpPFxuICAgIFRDb2x1bW4gZXh0ZW5kcyBrZXlvZiBUUmVzdWx0XG4gICAgICA/IFRSZXN1bHRbVENvbHVtbl1bXVxuICAgICAgOiBFeHRyYWN0Q29sdW1uVHlwZTxUVGFibGVzLCBUQ29sdW1uICYgc3RyaW5nPltdLFxuICAgIG5ldmVyXG4gID4ge1xuICAgIHRoaXMua25leFF1ZXJ5LnBsdWNrKGNvbHVtbiBhcyBzdHJpbmcpO1xuICAgIHJldHVybiBuZXcgUmVzb2x2ZWRQdXJpKHRoaXMua25leFF1ZXJ5LCB0aGlzLmtuZXgsIHRoaXMudGFibGVTcGVjKTtcbiAgfVxuXG4gIC8vIElOU0VSVCA6IOuLqOydvCDqsJ3ssrRcbiAgaW5zZXJ0KFxuICAgIGRhdGE6IEluc2VydERhdGE8U2luZ2xlVGFibGVWYWx1ZTxUVGFibGVzPj4sXG4gICk6IFJlc29sdmVkUHVyaTxJbnNlcnRSZXN1bHQsIFNpbmdsZVRhYmxlVmFsdWU8VFRhYmxlcz4+O1xuICAvLyBJTlNFUlQ6IOuwsOyXtFxuICBpbnNlcnQoXG4gICAgZGF0YTogSW5zZXJ0RGF0YTxTaW5nbGVUYWJsZVZhbHVlPFRUYWJsZXM+PltdLFxuICApOiBSZXNvbHZlZFB1cmk8SW5zZXJ0UmVzdWx0LCBTaW5nbGVUYWJsZVZhbHVlPFRUYWJsZXM+PjtcbiAgLy8gSU5TRVJUIOyLpOygnCDqtaztmIRcbiAgaW5zZXJ0KFxuICAgIHJhd0RhdGE6IEluc2VydERhdGE8U2luZ2xlVGFibGVWYWx1ZTxUVGFibGVzPj4gfCBJbnNlcnREYXRhPFNpbmdsZVRhYmxlVmFsdWU8VFRhYmxlcz4+W10sXG4gICk6IFJlc29sdmVkUHVyaTxJbnNlcnRSZXN1bHQsIFNpbmdsZVRhYmxlVmFsdWU8VFRhYmxlcz4+IHtcbiAgICAvLyBKU09OIOy7rOufvCBzdHJpbmdpZnkg66Gc7KeB7J2EIOuplOyEnOuTnOuhnCDrtoTrpqztlZjsl6wg7KSR67O1IOygnOqxsFxuICAgIGNvbnN0IHJlZmluZWREYXRhID0gdGhpcy5yZWZpbmVKc29uQ29sdW1ucyhyYXdEYXRhKTtcbiAgICB0aGlzLmtuZXhRdWVyeS5pbnNlcnQocmVmaW5lZERhdGEpO1xuICAgIHJldHVybiBuZXcgUmVzb2x2ZWRQdXJpKHRoaXMua25leFF1ZXJ5LCB0aGlzLmtuZXgsIHRoaXMudGFibGVTcGVjKTtcbiAgfVxuXG4gIC8vIFVQREFURVxuICB1cGRhdGUocmF3RGF0YTogV2hlcmVDb25kaXRpb248VFRhYmxlcz4pOiBSZXNvbHZlZFB1cmk8bnVtYmVyLCBTaW5nbGVUYWJsZVZhbHVlPFRUYWJsZXM+PiB7XG4gICAgLy8gSlNPTiDsu6zrn7wgc3RyaW5naWZ5IOuhnOyngeydhCDrqZTshJzrk5zroZwg67aE66as7ZWY7JesIOykkeuztSDsoJzqsbBcbiAgICBjb25zdCByZWZpbmVkRGF0YSA9IHRoaXMucmVmaW5lSnNvbkNvbHVtbnMocmF3RGF0YSk7XG4gICAgdGhpcy5rbmV4UXVlcnkudXBkYXRlKHJlZmluZWREYXRhKTtcbiAgICByZXR1cm4gbmV3IFJlc29sdmVkUHVyaSh0aGlzLmtuZXhRdWVyeSwgdGhpcy5rbmV4LCB0aGlzLnRhYmxlU3BlYyk7XG4gIH1cblxuICAvKipcbiAgICogSlNPTiDsu6zrn7zsl5Ag64yA7ZW0IHN0cmluZ2lmeSDsspjrpqzrpbwg7IiY7ZaJ7ZWY64qUIOuCtOu2gCDrqZTshJzrk5zsnoXri4jri6QuXG4gICAqIG9iamVjdCDrmJDripQgb2JqZWN0IOuwsOyXtOydhCDrsJvqs6AsIEpTT04g7Lus65+87J20IOyeiOycvOuptCDsp4HroKztmZTtlZjsl6wg67CY7ZmY7ZWp64uI64ukLlxuICAgKiDsp4HsoJEg6rCS7J2EIOuzgOqyve2VmOuvgOuhnCBzaWRlIGVmZmVjdOqwgCDsnojsirXri4jri6QuXG4gICAqL1xuICBwcml2YXRlIHJlZmluZUpzb25Db2x1bW5zKFxuICAgIGRhdGE6IFJlY29yZDxzdHJpbmcsIHVua25vd24+IHwgUmVjb3JkPHN0cmluZywgdW5rbm93bj5bXSxcbiAgKTogdHlwZW9mIGRhdGEge1xuICAgIC8vIHRhYmxlU3BlY+ydtOuCmCBqc29uQ29sdW1ucyDsl4bripQg6rK97JqwIOuwlOuhnCDrsJjtmZhcbiAgICBpZiAoIXRoaXMudGFibGVTcGVjIHx8ICF0aGlzLnRhYmxlU3BlYy5qc29uQ29sdW1ucy5sZW5ndGgpIHtcbiAgICAgIHJldHVybiBkYXRhO1xuICAgIH1cblxuICAgIC8vIOuTseuhneuQnCBUYWJsZVNwZWPsnYQg7Ya17ZW0IEpTT07su6zrn7wg66qp66Gd7J2EIOqwgOyguOyZgCBKU09OLnN0cmluZ2lmeSDsspjrpqxcbiAgICBjb25zdCBqc29uQ29sdW1ucyA9IHRoaXMudGFibGVTcGVjLmpzb25Db2x1bW5zO1xuICAgIGlmIChBcnJheS5pc0FycmF5KGRhdGEpKSB7XG4gICAgICBmb3IgKGNvbnN0IGl0ZW0gb2YgZGF0YSkge1xuICAgICAgICBmb3IgKGNvbnN0IGNvbHVtbiBvZiBqc29uQ29sdW1ucykge1xuICAgICAgICAgIGNvbnN0IHZhbHVlID0gaXRlbVtjb2x1bW5dO1xuICAgICAgICAgIGlmICh2YWx1ZSAhPT0gdW5kZWZpbmVkICYmIHZhbHVlICE9PSBudWxsKSB7XG4gICAgICAgICAgICBpdGVtW2NvbHVtbl0gPSBzZXJpYWxpemVKc29uQ29sdW1uVmFsdWUodGhpcy50YWJsZVNwZWMsIGNvbHVtbiwgdmFsdWUpO1xuICAgICAgICAgIH1cbiAgICAgICAgfVxuICAgICAgfVxuICAgIH0gZWxzZSB7XG4gICAgICBmb3IgKGNvbnN0IGNvbHVtbiBvZiBqc29uQ29sdW1ucykge1xuICAgICAgICBjb25zdCB2YWx1ZSA9IGRhdGFbY29sdW1uXTtcbiAgICAgICAgaWYgKHZhbHVlICE9PSB1bmRlZmluZWQgJiYgdmFsdWUgIT09IG51bGwpIHtcbiAgICAgICAgICBkYXRhW2NvbHVtbl0gPSBzZXJpYWxpemVKc29uQ29sdW1uVmFsdWUodGhpcy50YWJsZVNwZWMsIGNvbHVtbiwgdmFsdWUpO1xuICAgICAgICB9XG4gICAgICB9XG4gICAgfVxuICAgIHJldHVybiBkYXRhO1xuICB9XG5cbiAgLy8gSW5jcmVtZW50XG4gIGluY3JlbWVudDxUQ29sdW1uIGV4dGVuZHMgTnVtZXJpY0NvbHVtbnM8VFRhYmxlcz4+KFxuICAgIGNvbHVtbjogVENvbHVtbixcbiAgICB2YWx1ZTogbnVtYmVyLFxuICApOiBSZXNvbHZlZFB1cmk8bnVtYmVyLCBTaW5nbGVUYWJsZVZhbHVlPFRUYWJsZXM+PiB7XG4gICAgaWYgKHZhbHVlIDw9IDApIHtcbiAgICAgIHRocm93IG5ldyBFcnJvcihcIkluY3JlbWVudCB2YWx1ZSBtdXN0IGJlIGdyZWF0ZXIgdGhhbiAwXCIpO1xuICAgIH1cbiAgICB0aGlzLmtuZXhRdWVyeS5pbmNyZW1lbnQoY29sdW1uLCB2YWx1ZSk7XG4gICAgcmV0dXJuIG5ldyBSZXNvbHZlZFB1cmkodGhpcy5rbmV4UXVlcnksIHRoaXMua25leCwgdGhpcy50YWJsZVNwZWMpO1xuICB9XG4gIC8vIERlY3JlbWVudFxuICBkZWNyZW1lbnQ8VENvbHVtbiBleHRlbmRzIE51bWVyaWNDb2x1bW5zPFRUYWJsZXM+PihcbiAgICBjb2x1bW46IFRDb2x1bW4sXG4gICAgdmFsdWU6IG51bWJlcixcbiAgKTogUmVzb2x2ZWRQdXJpPG51bWJlciwgU2luZ2xlVGFibGVWYWx1ZTxUVGFibGVzPj4ge1xuICAgIGlmICh2YWx1ZSA8PSAwKSB7XG4gICAgICB0aHJvdyBuZXcgRXJyb3IoXCJEZWNyZW1lbnQgdmFsdWUgbXVzdCBiZSBncmVhdGVyIHRoYW4gMFwiKTtcbiAgICB9XG4gICAgdGhpcy5rbmV4UXVlcnkuZGVjcmVtZW50KGNvbHVtbiwgdmFsdWUpO1xuICAgIHJldHVybiBuZXcgUmVzb2x2ZWRQdXJpKHRoaXMua25leFF1ZXJ5LCB0aGlzLmtuZXgsIHRoaXMudGFibGVTcGVjKTtcbiAgfVxuXG4gIC8vIERFTEVURVxuICBkZWxldGUoKTogUmVzb2x2ZWRQdXJpPG51bWJlciwgU2luZ2xlVGFibGVWYWx1ZTxUVGFibGVzPj4ge1xuICAgIHRoaXMua25leFF1ZXJ5LmRlbGV0ZSgpO1xuICAgIHJldHVybiBuZXcgUmVzb2x2ZWRQdXJpKHRoaXMua25leFF1ZXJ5LCB0aGlzLmtuZXgsIHRoaXMudGFibGVTcGVjKTtcbiAgfVxuXG4gIC8vIO2ZleyduCDsv7zrpqwg66as7YS0XG4gIHRvUXVlcnkoKTogc3RyaW5nIHtcbiAgICByZXR1cm4gdGhpcy5rbmV4UXVlcnkudG9RdWVyeSgpO1xuICB9XG5cbiAgLy8g7L+866asIOuUlOuyhOq5hSDroZzqt7gg7Lac66ClXG4gIGRlYnVnKCk6IHRoaXMge1xuICAgIGNvbnNvbGUubG9nKGAke2NoYWxrLmN5YW4oXCJbUHVyaSBEZWJ1Z11cIil9ICR7Y2hhbGsueWVsbG93KHRoaXMudG9RdWVyeSgpKX1gKTtcbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIGNsb25lKCk6IFB1cmk8VFNjaGVtYSwgVFRhYmxlcywgVFJlc3VsdD4ge1xuICAgIC8vICdkdWFsJ+ydgCDrjZTrr7gg7YWM7J2067iU7J2066mwLCDrsJTroZwg7JWE656YIOykhOyXkOyEnCBrbmV4UXVlcnnqsIAg642u7Ja07JSM7JuM7KeR64uI64ukLlxuICAgIGNvbnN0IG5ld1B1cmkgPSBuZXcgUHVyaTxUU2NoZW1hLCBUVGFibGVzLCBUUmVzdWx0Pih0aGlzLmtuZXgsIFwiZHVhbFwiKTtcbiAgICBuZXdQdXJpLmtuZXhRdWVyeSA9IHRoaXMua25leFF1ZXJ5LmNsb25lKCk7XG4gICAgbmV3UHVyaS50YWJsZVNwZWMgPSB0aGlzLnRhYmxlU3BlYztcbiAgICBuZXdQdXJpLmNvcnJlbGF0aW9uUmVnaXN0cnkgPSBuZXcgTWFwKHRoaXMuY29ycmVsYXRpb25SZWdpc3RyeSk7XG4gICAgcmV0dXJuIG5ld1B1cmk7XG4gIH1cblxuICBmb3JtYXRTUUwodW5mb3JtYXR0ZWQ6IHN0cmluZyk6IHN0cmluZyB7XG4gICAgLy8gU1FMIOyYiOyVveyWtCDrqqnroZ1cbiAgICBjb25zdCBrZXl3b3JkcyA9IFtcbiAgICAgIFwiU0VMRUNUXCIsXG4gICAgICBcIkZST01cIixcbiAgICAgIFwiV0hFUkVcIixcbiAgICAgIFwiSU5TRVJUXCIsXG4gICAgICBcIklOVE9cIixcbiAgICAgIFwiVkFMVUVTXCIsXG4gICAgICBcIlVQREFURVwiLFxuICAgICAgXCJERUxFVEVcIixcbiAgICAgIFwiQ1JFQVRFXCIsXG4gICAgICBcIlRBQkxFXCIsXG4gICAgICBcIkFMVEVSXCIsXG4gICAgICBcIkRST1BcIixcbiAgICAgIFwiSk9JTlwiLFxuICAgICAgXCJPTlwiLFxuICAgICAgXCJJTk5FUlwiLFxuICAgICAgXCJMRUZUXCIsXG4gICAgICBcIlJJR0hUXCIsXG4gICAgICBcIkZVTExcIixcbiAgICAgIFwiT1VURVJcIixcbiAgICAgIFwiR1JPVVBcIixcbiAgICAgIFwiQllcIixcbiAgICAgIFwiT1JERVJcIixcbiAgICAgIFwiSEFWSU5HXCIsXG4gICAgICBcIkRJU1RJTkNUXCIsXG4gICAgICBcIkxJTUlUXCIsXG4gICAgICBcIk9GRlNFVFwiLFxuICAgICAgXCJBU1wiLFxuICAgICAgXCJBTkRcIixcbiAgICAgIFwiT1JcIixcbiAgICAgIFwiTk9UXCIsXG4gICAgICBcIklOXCIsXG4gICAgICBcIkxJS0VcIixcbiAgICAgIFwiSVNcIixcbiAgICAgIFwiTlVMTFwiLFxuICAgICAgXCJDQVNFXCIsXG4gICAgICBcIldIRU5cIixcbiAgICAgIFwiVEhFTlwiLFxuICAgICAgXCJFTFNFXCIsXG4gICAgICBcIkVORFwiLFxuICAgICAgXCJVTklPTlwiLFxuICAgICAgXCJBTExcIixcbiAgICAgIFwiRVhJU1RTXCIsXG4gICAgICBcIkJFVFdFRU5cIixcbiAgICBdO1xuXG4gICAgbGV0IGZvcm1hdHRlZCA9IHVuZm9ybWF0dGVkO1xuXG4gICAgLy8g7JiI7JW97Ja066W8IOuMgOusuOyekOuhnCDrs4DtmZhcbiAgICBrZXl3b3Jkcy5mb3JFYWNoKChrZXl3b3JkKSA9PiB7XG4gICAgICBjb25zdCByZWdleCA9IG5ldyBSZWdFeHAoYFxcXFxiJHtrZXl3b3JkfVxcXFxiYCwgXCJnaVwiKTtcbiAgICAgIGZvcm1hdHRlZCA9IGZvcm1hdHRlZC5yZXBsYWNlKHJlZ2V4LCBrZXl3b3JkLnRvVXBwZXJDYXNlKCkpO1xuICAgIH0pO1xuXG4gICAgLy8g7KO87JqUIOygiCDslZ7sl5Ag7KSE67CU6r+IIOy2lOqwgFxuICAgIGNvbnN0IG1ham9yQ2xhdXNlcyA9IFtcbiAgICAgIFwiU0VMRUNUXCIsXG4gICAgICBcIkZST01cIixcbiAgICAgIFwiV0hFUkVcIixcbiAgICAgIFwiR1JPVVAgQllcIixcbiAgICAgIFwiT1JERVIgQllcIixcbiAgICAgIFwiSEFWSU5HXCIsXG4gICAgICBcIkxJTUlUXCIsXG4gICAgICBcIlVOSU9OXCIsXG4gICAgXTtcbiAgICBtYWpvckNsYXVzZXMuZm9yRWFjaCgoY2xhdXNlKSA9PiB7XG4gICAgICBjb25zdCByZWdleCA9IG5ldyBSZWdFeHAoYFxcXFxzKygke2NsYXVzZX0pXFxcXHMrYCwgXCJnaVwiKTtcbiAgICAgIGZvcm1hdHRlZCA9IGZvcm1hdHRlZC5yZXBsYWNlKHJlZ2V4LCBgXFxuJHtjbGF1c2UudG9VcHBlckNhc2UoKX0gYCk7XG4gICAgfSk7XG5cbiAgICAvLyBKT0lOIOygiCDsspjrpqxcbiAgICBmb3JtYXR0ZWQgPSBmb3JtYXR0ZWQucmVwbGFjZSgvXFxzKygoPzpJTk5FUnxMRUZUfFJJR0hUfEZVTEwgT1VURVIpXFxzKyk/Sk9JTlxccysvZ2ksIFwiXFxuJDFKT0lOIFwiKTtcblxuICAgIC8vIEFORCwgT1Ig7KGw6rG0IOyymOumrFxuICAgIGZvcm1hdHRlZCA9IGZvcm1hdHRlZC5yZXBsYWNlKC9cXHMrKEFORHxPUilcXHMrL2dpLCBcIlxcbiAgJDEgXCIpO1xuXG4gICAgLy8g6rSE7Zi4IOyymOumrCDrsI8g65Ok7Jes7JOw6riwXG4gICAgY29uc3QgbGluZXMgPSBmb3JtYXR0ZWQuc3BsaXQoXCJcXG5cIik7XG4gICAgY29uc3QgaW5kZW50ZWRMaW5lcyA9IFtdO1xuICAgIGxldCBpbmRlbnRMZXZlbCA9IDA7XG5cbiAgICBmb3IgKGNvbnN0IGxpbmUgb2YgbGluZXMpIHtcbiAgICAgIGNvbnN0IHRyaW1tZWRMaW5lID0gbGluZS50cmltKCk7XG4gICAgICBpZiAoIXRyaW1tZWRMaW5lKSBjb250aW51ZTtcblxuICAgICAgLy8g64ur64qUIOq0hO2YuOqwgCDsnojsnLzrqbQg65Ok7Jes7JOw6riwIOugiOuyqCDqsJDshoxcbiAgICAgIGNvbnN0IGNsb3NpbmdQYXJlbnMgPSAodHJpbW1lZExpbmUubWF0Y2goL1xcKS9nKSB8fCBbXSkubGVuZ3RoO1xuICAgICAgY29uc3Qgb3BlbmluZ1BhcmVucyA9ICh0cmltbWVkTGluZS5tYXRjaCgvXFwoL2cpIHx8IFtdKS5sZW5ndGg7XG5cbiAgICAgIGlmIChjbG9zaW5nUGFyZW5zID4gMCAmJiBvcGVuaW5nUGFyZW5zID09PSAwKSB7XG4gICAgICAgIGluZGVudExldmVsID0gTWF0aC5tYXgoMCwgaW5kZW50TGV2ZWwgLSBjbG9zaW5nUGFyZW5zKTtcbiAgICAgIH1cblxuICAgICAgLy8g7ZiE7J6sIOuTpOyXrOyTsOq4sCDsoIHsmqlcbiAgICAgIGNvbnN0IGluZGVudCA9IFwiICBcIi5yZXBlYXQoaW5kZW50TGV2ZWwpO1xuICAgICAgaW5kZW50ZWRMaW5lcy5wdXNoKGluZGVudCArIHRyaW1tZWRMaW5lKTtcblxuICAgICAgLy8g7Jes64qUIOq0hO2YuOqwgCDsnojsnLzrqbQg65Ok7Jes7JOw6riwIOugiOuyqCDspp3qsIBcbiAgICAgIGlmIChvcGVuaW5nUGFyZW5zID4gY2xvc2luZ1BhcmVucykge1xuICAgICAgICBpbmRlbnRMZXZlbCArPSBvcGVuaW5nUGFyZW5zIC0gY2xvc2luZ1BhcmVucztcbiAgICAgIH1cbiAgICB9XG5cbiAgICByZXR1cm4gaW5kZW50ZWRMaW5lcy5qb2luKFwiXFxuXCIpLnRyaW0oKTtcbiAgfVxuXG4gIHJhdyhzcWw6IHN0cmluZyk6IEtuZXguUmF3IHtcbiAgICByZXR1cm4gdGhpcy5rbmV4LnJhdyhzcWwpO1xuICB9XG5cbiAgLy8gS25leCDsv7zrpqwg67mM642UIOyngeygkSDsoJHqt7xcbiAgcmF3UXVlcnkoKTogS25leC5RdWVyeUJ1aWxkZXIge1xuICAgIHJldHVybiB0aGlzLmtuZXhRdWVyeTtcbiAgfVxufVxuXG5leHBvcnQgY2xhc3MgV2hlcmVHcm91cDxUVGFibGVzIGV4dGVuZHMgUmVjb3JkPHN0cmluZywgYW55Pj4ge1xuICBjb25zdHJ1Y3Rvcihwcml2YXRlIGJ1aWxkZXI6IEtuZXguUXVlcnlCdWlsZGVyKSB7fVxuXG4gIC8vIHdoZXJlIOuplOyEnOuTnOuTpFxuICB3aGVyZShjb25kaXRpb25zOiBXaGVyZUNvbmRpdGlvbjxUVGFibGVzPik6IHRoaXM7XG4gIHdoZXJlPFRDb2x1bW4gZXh0ZW5kcyBBdmFpbGFibGVDb2x1bW5zPFRUYWJsZXM+PihcbiAgICBjb2x1bW46IFRDb2x1bW4sXG4gICAgdmFsdWU6IEV4dHJhY3RDb2x1bW5UeXBlPFRUYWJsZXMsIFRDb2x1bW4gJiBzdHJpbmc+LFxuICApOiB0aGlzO1xuICB3aGVyZTxUQ29sdW1uIGV4dGVuZHMgQXZhaWxhYmxlQ29sdW1uczxUVGFibGVzPj4oXG4gICAgY29sdW1uOiBUQ29sdW1uLFxuICAgIG9wZXJhdG9yOiBXaGVyZU9wZXJhdG9yLFxuICAgIHZhbHVlOiBFeHRyYWN0Q29sdW1uVHlwZTxUVGFibGVzLCBUQ29sdW1uICYgc3RyaW5nPixcbiAgKTogdGhpcztcbiAgd2hlcmUoLi4uYXJnczogYW55W10pOiBXaGVyZUdyb3VwPFRUYWJsZXM+IHtcbiAgICB0aGlzLmJ1aWxkZXIud2hlcmUoYXJnc1swXSwgLi4uYXJncy5zbGljZSgxKSk7XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICAvLyB3aGVyZUluIC8gd2hlcmVOb3RJbiDrqZTshJzrk5zrk6RcbiAgd2hlcmVJbjxUQ29sdW1uIGV4dGVuZHMgQXZhaWxhYmxlQ29sdW1uczxUVGFibGVzPj4oXG4gICAgY29sdW1uOiBUQ29sdW1uLFxuICAgIHZhbHVlczogRXh0cmFjdENvbHVtblR5cGU8VFRhYmxlcywgVENvbHVtbiAmIHN0cmluZz5bXSxcbiAgKTogdGhpcztcbiAgd2hlcmVJbiguLi5hcmdzOiBhbnlbXSk6IFdoZXJlR3JvdXA8VFRhYmxlcz4ge1xuICAgIHRoaXMuYnVpbGRlci53aGVyZUluKGFyZ3NbMF0sIGFyZ3NbMV0pO1xuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgd2hlcmVOb3RJbjxUQ29sdW1uIGV4dGVuZHMgQXZhaWxhYmxlQ29sdW1uczxUVGFibGVzPj4oXG4gICAgY29sdW1uOiBUQ29sdW1uLFxuICAgIHZhbHVlczogRXh0cmFjdENvbHVtblR5cGU8VFRhYmxlcywgVENvbHVtbiAmIHN0cmluZz5bXSxcbiAgKTogdGhpcztcbiAgd2hlcmVOb3RJbiguLi5hcmdzOiBhbnlbXSk6IFdoZXJlR3JvdXA8VFRhYmxlcz4ge1xuICAgIHRoaXMuYnVpbGRlci53aGVyZU5vdEluKGFyZ3NbMF0sIGFyZ3NbMV0pO1xuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgLy8gb3JXaGVyZSDrqZTshJzrk5zrk6RcbiAgb3JXaGVyZShjb25kaXRpb25zOiBXaGVyZUNvbmRpdGlvbjxUVGFibGVzPik6IHRoaXM7XG4gIG9yV2hlcmU8VENvbHVtbiBleHRlbmRzIEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcz4+KFxuICAgIGNvbHVtbjogVENvbHVtbixcbiAgICB2YWx1ZTogRXh0cmFjdENvbHVtblR5cGU8VFRhYmxlcywgVENvbHVtbiAmIHN0cmluZz4sXG4gICk6IHRoaXM7XG4gIG9yV2hlcmU8VENvbHVtbiBleHRlbmRzIEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcz4+KFxuICAgIGNvbHVtbjogVENvbHVtbixcbiAgICBvcGVyYXRvcjogV2hlcmVPcGVyYXRvcixcbiAgICB2YWx1ZTogRXh0cmFjdENvbHVtblR5cGU8VFRhYmxlcywgVENvbHVtbiAmIHN0cmluZz4sXG4gICk6IHRoaXM7XG4gIG9yV2hlcmUoLi4uYXJnczogYW55W10pOiBXaGVyZUdyb3VwPFRUYWJsZXM+IHtcbiAgICB0aGlzLmJ1aWxkZXIub3JXaGVyZShhcmdzWzBdLCAuLi5hcmdzLnNsaWNlKDEpKTtcbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIC8vIG9yV2hlcmVJbiAvIG9yV2hlcmVOb3RJbiDrqZTshJzrk5zrk6RcbiAgb3JXaGVyZUluPFRDb2x1bW4gZXh0ZW5kcyBBdmFpbGFibGVDb2x1bW5zPFRUYWJsZXM+PihcbiAgICBjb2x1bW46IFRDb2x1bW4sXG4gICAgdmFsdWVzOiBFeHRyYWN0Q29sdW1uVHlwZTxUVGFibGVzLCBUQ29sdW1uICYgc3RyaW5nPltdLFxuICApOiB0aGlzO1xuICBvcldoZXJlSW4oLi4uYXJnczogYW55W10pOiBXaGVyZUdyb3VwPFRUYWJsZXM+IHtcbiAgICB0aGlzLmJ1aWxkZXIub3JXaGVyZUluKGFyZ3NbMF0sIGFyZ3NbMV0pO1xuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgb3JXaGVyZU5vdEluPFRDb2x1bW4gZXh0ZW5kcyBBdmFpbGFibGVDb2x1bW5zPFRUYWJsZXM+PihcbiAgICBjb2x1bW46IFRDb2x1bW4sXG4gICAgdmFsdWVzOiBFeHRyYWN0Q29sdW1uVHlwZTxUVGFibGVzLCBUQ29sdW1uICYgc3RyaW5nPltdLFxuICApOiB0aGlzO1xuICBvcldoZXJlTm90SW4oLi4uYXJnczogYW55W10pOiBXaGVyZUdyb3VwPFRUYWJsZXM+IHtcbiAgICB0aGlzLmJ1aWxkZXIub3JXaGVyZU5vdEluKGFyZ3NbMF0sIGFyZ3NbMV0pO1xuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgLy8gV0hFUkUgSlNPTkIgU1VQRVJTRVQgKEA+KVxuICB3aGVyZUpzb25TdXBlcnNldE9mPFRDb2x1bW4gZXh0ZW5kcyBKc29uQ29sdW1uczxUVGFibGVzPj4oXG4gICAgY29sdW1uOiBUQ29sdW1uLFxuICAgIHZhbHVlOiBKc29uU3VwZXJzZXRWYWx1ZTxFeHRyYWN0Q29sdW1uVHlwZTxUVGFibGVzLCBUQ29sdW1uPj4sXG4gICk6IHRoaXMge1xuICAgIHRoaXMuYnVpbGRlci53aGVyZUpzb25TdXBlcnNldE9mKGNvbHVtbiwgc2VyaWFsaXplSnNvblN1cGVyc2V0VmFsdWUodmFsdWUpKTtcbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIG9yV2hlcmVKc29uU3VwZXJzZXRPZjxUQ29sdW1uIGV4dGVuZHMgSnNvbkNvbHVtbnM8VFRhYmxlcz4+KFxuICAgIGNvbHVtbjogVENvbHVtbixcbiAgICB2YWx1ZTogSnNvblN1cGVyc2V0VmFsdWU8RXh0cmFjdENvbHVtblR5cGU8VFRhYmxlcywgVENvbHVtbj4+LFxuICApOiB0aGlzIHtcbiAgICB0aGlzLmJ1aWxkZXIub3JXaGVyZUpzb25TdXBlcnNldE9mKGNvbHVtbiwgc2VyaWFsaXplSnNvblN1cGVyc2V0VmFsdWUodmFsdWUpKTtcbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIC8vIFdIRVJFIE1BVENIXG4gIHdoZXJlTWF0Y2g8VENvbHVtbiBleHRlbmRzIEZ1bGx0ZXh0Q29sdW1uczxUVGFibGVzPj4oY29sdW1uOiBUQ29sdW1uLCB2YWx1ZTogc3RyaW5nKTogdGhpcztcbiAgd2hlcmVNYXRjaCguLi5hcmdzOiBhbnlbXSk6IHRoaXMge1xuICAgIHRoaXMuYnVpbGRlci53aGVyZVJhdyhgTUFUQ0ggKCR7U3RyaW5nKGFyZ3NbMF0pfSkgQUdBSU5TVCAoPylgLCBbYXJnc1sxXV0pO1xuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgb3JXaGVyZU1hdGNoPFRDb2x1bW4gZXh0ZW5kcyBGdWxsdGV4dENvbHVtbnM8VFRhYmxlcz4+KGNvbHVtbjogVENvbHVtbiwgdmFsdWU6IHN0cmluZyk6IHRoaXM7XG4gIG9yV2hlcmVNYXRjaCguLi5hcmdzOiBhbnlbXSk6IHRoaXMge1xuICAgIHRoaXMuYnVpbGRlci5vcldoZXJlUmF3KGBNQVRDSCAoJHtTdHJpbmcoYXJnc1swXSl9KSBBR0FJTlNUICg/KWAsIFthcmdzWzFdXSk7XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICAvLyBXSEVSRSBTRUFSQ0hcbiAgd2hlcmVTZWFyY2g8VENvbHVtbiBleHRlbmRzIEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcz4+KFxuICAgIGNvbHVtbjogVENvbHVtbiB8IFRDb2x1bW5bXSxcbiAgICB2YWx1ZTogc3RyaW5nLFxuICAgIG9wdGlvbnM/OiB7XG4gICAgICB3ZWlnaHRzPzogbnVtYmVyW107IC8vIOygleyImCDrsLDsl7RcbiAgICB9LFxuICApOiB0aGlzO1xuICB3aGVyZVNlYXJjaCguLi5hcmdzOiBhbnlbXSk6IHRoaXMge1xuICAgIGNvbnN0IHsgd2VpZ2h0cyB9ID0gYXJnc1syXSA/PyB7fTtcbiAgICBjb25zdCBjb2x1bW5FeHByID0gQXJyYXkuaXNBcnJheShhcmdzWzBdKVxuICAgICAgPyBgQVJSQVlbJHthcmdzWzBdLm1hcCgoYykgPT4gYCR7Y306OnRleHRgKS5qb2luKFwiLFwiKX1dYFxuICAgICAgOiBhcmdzWzBdO1xuICAgIGNvbnN0IHBncm9vbmdhQ29uZGl0aW9uID0gYHBncm9vbmdhX2NvbmRpdGlvbig/JHt3ZWlnaHRzPy5sZW5ndGggPyBgLCB3ZWlnaHRzID0+IEFSUkFZWyR7d2VpZ2h0cy5qb2luKFwiLFwiKX1dYCA6IFwiXCJ9KWA7XG4gICAgdGhpcy5idWlsZGVyLndoZXJlUmF3KGAke2NvbHVtbkV4cHJ9ICZAfiAke3Bncm9vbmdhQ29uZGl0aW9ufWAsIFthcmdzWzFdXSk7XG5cbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIG9yV2hlcmVTZWFyY2g8VENvbHVtbiBleHRlbmRzIEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcz4+KFxuICAgIGNvbHVtbjogVENvbHVtbiB8IFRDb2x1bW5bXSxcbiAgICB2YWx1ZTogc3RyaW5nLFxuICAgIG9wdGlvbnM/OiB7XG4gICAgICB3ZWlnaHRzPzogbnVtYmVyW107IC8vIOygleyImCDrsLDsl7RcbiAgICB9LFxuICApOiB0aGlzO1xuICBvcldoZXJlU2VhcmNoKC4uLmFyZ3M6IGFueVtdKTogdGhpcyB7XG4gICAgY29uc3QgeyB3ZWlnaHRzIH0gPSBhcmdzWzJdID8/IHt9O1xuICAgIGNvbnN0IGNvbHVtbkV4cHIgPSBBcnJheS5pc0FycmF5KGFyZ3NbMF0pXG4gICAgICA/IGBBUlJBWVske2FyZ3NbMF0ubWFwKChjKSA9PiBgJHtjfTo6dGV4dGApLmpvaW4oXCIsXCIpfV1gXG4gICAgICA6IGFyZ3NbMF07XG4gICAgY29uc3QgcGdyb29uZ2FDb25kaXRpb24gPSBgcGdyb29uZ2FfY29uZGl0aW9uKD8ke3dlaWdodHM/Lmxlbmd0aCA/IGAsIHdlaWdodHMgPT4gQVJSQVlbJHt3ZWlnaHRzLmpvaW4oXCIsXCIpfV1gIDogXCJcIn0pYDtcbiAgICB0aGlzLmJ1aWxkZXIub3JXaGVyZVJhdyhgJHtjb2x1bW5FeHByfSAmQH4gJHtwZ3Jvb25nYUNvbmRpdGlvbn1gLCBbYXJnc1sxXV0pO1xuXG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICAvLyBXSEVSRSBGVUxMVEVYVFxuICB3aGVyZVRzU2VhcmNoPFRDb2x1bW4gZXh0ZW5kcyBBdmFpbGFibGVDb2x1bW5zPFRUYWJsZXM+IHwgU3FsRXhwcmVzc2lvbjxcInN0cmluZ1wiPj4oXG4gICAgY29sdW1uOiBUQ29sdW1uLFxuICAgIHZhbHVlOiBzdHJpbmcsXG4gICAgb3B0aW9ucz86IFRzUXVlcnlPcHRpb25zIHwgVHNRdWVyeUNvbmZpZyxcbiAgKTogdGhpcztcbiAgd2hlcmVUc1NlYXJjaCguLi5hcmdzOiBhbnlbXSk6IHRoaXMge1xuICAgIGNvbnN0IG9wdHMgPVxuICAgICAgdHlwZW9mIGFyZ3NbMl0gPT09IFwic3RyaW5nXCIgPyAoeyBjb25maWc6IGFyZ3NbMl0gfSBhcyBUc1F1ZXJ5T3B0aW9ucykgOiAoYXJnc1syXSA/PyB7fSk7XG5cbiAgICBjb25zdCBwYXJzZXIgPSBvcHRzLnBhcnNlciA/PyBcIndlYnNlYXJjaF90b190c3F1ZXJ5XCI7XG4gICAgY29uc3QgY29uZmlnID0gb3B0cy5jb25maWcgPz8gXCJzaW1wbGVcIjtcbiAgICBjb25zdCBjb2x1bW5FeHByID1cbiAgICAgIHR5cGVvZiBhcmdzWzBdID09PSBcIm9iamVjdFwiICYmIGFyZ3NbMF0uX3R5cGUgPT09IFwic3FsX2V4cHJlc3Npb25cIlxuICAgICAgICA/IGFyZ3NbMF0uX3NxbFxuICAgICAgICA6IFN0cmluZyhhcmdzWzBdKTtcblxuICAgIHRoaXMuYnVpbGRlci53aGVyZVJhdyhgJHtjb2x1bW5FeHByfSBAQCAke3BhcnNlcn0oPywgPylgLCBbY29uZmlnLCBhcmdzWzFdXSk7XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICBvcldoZXJlVHNTZWFyY2g8VENvbHVtbiBleHRlbmRzIEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcz4gfCBTcWxFeHByZXNzaW9uPFwic3RyaW5nXCI+PihcbiAgICBjb2x1bW46IFRDb2x1bW4sXG4gICAgdmFsdWU6IHN0cmluZyxcbiAgICBvcHRpb25zPzogVHNRdWVyeU9wdGlvbnMgfCBUc1F1ZXJ5Q29uZmlnLFxuICApOiB0aGlzO1xuICBvcldoZXJlVHNTZWFyY2goLi4uYXJnczogYW55W10pOiB0aGlzIHtcbiAgICBjb25zdCBvcHRzID1cbiAgICAgIHR5cGVvZiBhcmdzWzJdID09PSBcInN0cmluZ1wiID8gKHsgY29uZmlnOiBhcmdzWzJdIH0gYXMgVHNRdWVyeU9wdGlvbnMpIDogKGFyZ3NbMl0gPz8ge30pO1xuXG4gICAgY29uc3QgcGFyc2VyID0gb3B0cy5wYXJzZXIgPz8gXCJ3ZWJzZWFyY2hfdG9fdHNxdWVyeVwiO1xuICAgIGNvbnN0IGNvbmZpZyA9IG9wdHMuY29uZmlnID8/IFwic2ltcGxlXCI7XG4gICAgY29uc3QgY29sdW1uRXhwciA9XG4gICAgICB0eXBlb2YgYXJnc1swXSA9PT0gXCJvYmplY3RcIiAmJiBhcmdzWzBdLl90eXBlID09PSBcInNxbF9leHByZXNzaW9uXCJcbiAgICAgICAgPyBhcmdzWzBdLl9zcWxcbiAgICAgICAgOiBTdHJpbmcoYXJnc1swXSk7XG5cbiAgICB0aGlzLmJ1aWxkZXIub3JXaGVyZVJhdyhgJHtjb2x1bW5FeHByfSBAQCAke3BhcnNlcn0oPywgPylgLCBbY29uZmlnLCBhcmdzWzFdXSk7XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICB3aGVyZUZ1enp5PFRDb2x1bW4gZXh0ZW5kcyBBdmFpbGFibGVDb2x1bW5zPFRUYWJsZXM+IHwgU3FsRXhwcmVzc2lvbjxcInN0cmluZ1wiPj4oXG4gICAgY29sdW1uOiBUQ29sdW1uLFxuICAgIHZhbHVlOiBzdHJpbmcsXG4gICAgb3B0aW9ucz86IHtcbiAgICAgIG9wZXJhdG9yPzogRnV6enlPcGVyYXRvcjtcbiAgICB9LFxuICApOiB0aGlzO1xuICB3aGVyZUZ1enp5KC4uLmFyZ3M6IGFueVtdKTogdGhpcyB7XG4gICAgY29uc3Qgb3BlcmF0b3IgPSBub3JtYWxpemVGdXp6eU9wZXJhdG9yKGFyZ3NbMl0/Lm9wZXJhdG9yKTtcblxuICAgIGlmIChvcGVyYXRvciA9PT0gXCIlXCIpIHtcbiAgICAgIGlmICh0eXBlb2YgYXJnc1swXSA9PT0gXCJvYmplY3RcIikge1xuICAgICAgICB0aGlzLmJ1aWxkZXIud2hlcmVSYXcoYCR7YXJnc1swXS5fc3FsfSAke29wZXJhdG9yfSA/YCwgWy4uLmFyZ3NbMF0uX3BhcmFtcywgYXJnc1sxXV0pO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgdGhpcy5idWlsZGVyLndoZXJlUmF3KGA/PyAke29wZXJhdG9yfSA/YCwgW2FyZ3NbMF0sIGFyZ3NbMV1dKTtcbiAgICAgIH1cbiAgICAgIHJldHVybiB0aGlzO1xuICAgIH1cblxuICAgIGlmICh0eXBlb2YgYXJnc1swXSA9PT0gXCJvYmplY3RcIikge1xuICAgICAgdGhpcy5idWlsZGVyLndoZXJlUmF3KGA/ICR7b3BlcmF0b3J9ICR7YXJnc1swXS5fc3FsfWAsIFthcmdzWzFdLCAuLi5hcmdzWzBdLl9wYXJhbXNdKTtcbiAgICB9IGVsc2Uge1xuICAgICAgdGhpcy5idWlsZGVyLndoZXJlUmF3KGA/ICR7b3BlcmF0b3J9ID8/YCwgW2FyZ3NbMV0sIGFyZ3NbMF1dKTtcbiAgICB9XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICBvcldoZXJlRnV6enk8VENvbHVtbiBleHRlbmRzIEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcz4gfCBTcWxFeHByZXNzaW9uPFwic3RyaW5nXCI+PihcbiAgICBjb2x1bW46IFRDb2x1bW4sXG4gICAgdmFsdWU6IHN0cmluZyxcbiAgICBvcHRpb25zPzoge1xuICAgICAgb3BlcmF0b3I/OiBGdXp6eU9wZXJhdG9yO1xuICAgIH0sXG4gICk6IHRoaXM7XG4gIG9yV2hlcmVGdXp6eSguLi5hcmdzOiBhbnlbXSk6IHRoaXMge1xuICAgIGNvbnN0IG9wZXJhdG9yID0gbm9ybWFsaXplRnV6enlPcGVyYXRvcihhcmdzWzJdPy5vcGVyYXRvcik7XG5cbiAgICBpZiAob3BlcmF0b3IgPT09IFwiJVwiKSB7XG4gICAgICBpZiAodHlwZW9mIGFyZ3NbMF0gPT09IFwib2JqZWN0XCIpIHtcbiAgICAgICAgdGhpcy5idWlsZGVyLm9yV2hlcmVSYXcoYCR7YXJnc1swXS5fc3FsfSAke29wZXJhdG9yfSA/YCwgWy4uLmFyZ3NbMF0uX3BhcmFtcywgYXJnc1sxXV0pO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgdGhpcy5idWlsZGVyLm9yV2hlcmVSYXcoYD8/ICR7b3BlcmF0b3J9ID9gLCBbYXJnc1swXSwgYXJnc1sxXV0pO1xuICAgICAgfVxuICAgICAgcmV0dXJuIHRoaXM7XG4gICAgfVxuXG4gICAgaWYgKHR5cGVvZiBhcmdzWzBdID09PSBcIm9iamVjdFwiKSB7XG4gICAgICB0aGlzLmJ1aWxkZXIub3JXaGVyZVJhdyhgPyAke29wZXJhdG9yfSAke2FyZ3NbMF0uX3NxbH1gLCBbYXJnc1sxXSwgLi4uYXJnc1swXS5fcGFyYW1zXSk7XG4gICAgfSBlbHNlIHtcbiAgICAgIHRoaXMuYnVpbGRlci5vcldoZXJlUmF3KGA/ICR7b3BlcmF0b3J9ID8/YCwgW2FyZ3NbMV0sIGFyZ3NbMF1dKTtcbiAgICB9XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICAvLyDspJHssqkg6re466O5XG4gIHdoZXJlR3JvdXAoY2FsbGJhY2s6IChnOiBXaGVyZUdyb3VwPFRUYWJsZXM+KSA9PiB2b2lkKTogdGhpcztcbiAgd2hlcmVHcm91cChjYWxsYmFjazogKGc6IFdoZXJlR3JvdXA8VFRhYmxlcz4pID0+IHZvaWQpOiBXaGVyZUdyb3VwPFRUYWJsZXM+IHtcbiAgICB0aGlzLmJ1aWxkZXIud2hlcmUoKHN1YkJ1aWxkZXIpID0+IHtcbiAgICAgIGNvbnN0IHN1Ykdyb3VwID0gbmV3IFdoZXJlR3JvdXA8VFRhYmxlcz4oc3ViQnVpbGRlcik7XG4gICAgICBjYWxsYmFjayhzdWJHcm91cCk7XG4gICAgfSk7XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cbiAgb3JXaGVyZUdyb3VwKGNhbGxiYWNrOiAoZzogV2hlcmVHcm91cDxUVGFibGVzPikgPT4gdm9pZCk6IHRoaXM7XG4gIG9yV2hlcmVHcm91cChjYWxsYmFjazogKGc6IFdoZXJlR3JvdXA8VFRhYmxlcz4pID0+IHZvaWQpOiBXaGVyZUdyb3VwPFRUYWJsZXM+IHtcbiAgICB0aGlzLmJ1aWxkZXIub3JXaGVyZSgoc3ViQnVpbGRlcikgPT4ge1xuICAgICAgY29uc3Qgc3ViR3JvdXAgPSBuZXcgV2hlcmVHcm91cDxUVGFibGVzPihzdWJCdWlsZGVyKTtcbiAgICAgIGNhbGxiYWNrKHN1Ykdyb3VwKTtcbiAgICB9KTtcbiAgICByZXR1cm4gdGhpcztcbiAgfVxufVxuXG4vLyBKT0lOIOygiCDqt7jro7nsl5DripQgTGVmdOyZgCBSaWdodOyXkCDrjIDtlZwg7Iic7ISc6rCAIO2VhOyalO2VmOyngCDslYrsnLzrr4DroZwsIOuqqOuToCDqsr3smrDsnZgg7IiY66W8IOqzhOyCsO2VtOyVvO2VqC5cbmV4cG9ydCBjbGFzcyBKb2luQ2xhdXNlR3JvdXA8XG4gIFRMZWZ0IGV4dGVuZHMgUmVjb3JkPHN0cmluZywgYW55PixcbiAgVFJpZ2h0IGV4dGVuZHMgUmVjb3JkPHN0cmluZywgYW55Pixcbj4ge1xuICBjb25zdHJ1Y3Rvcihwcml2YXRlIGNhbGxiYWNrOiBLbmV4LkpvaW5DbGF1c2UpIHt9XG5cbiAgLy8gT04oQU5EKTog7Lus65+8ID0g7Lus65+8XG4gIG9uKGxlZnQ6IEF2YWlsYWJsZUNvbHVtbnM8VExlZnQ+LCByaWdodDogQXZhaWxhYmxlQ29sdW1uczxUUmlnaHQ+KTogdGhpcztcbiAgb24obGVmdDogQXZhaWxhYmxlQ29sdW1uczxUUmlnaHQ+LCByaWdodDogQXZhaWxhYmxlQ29sdW1uczxUTGVmdD4pOiB0aGlzO1xuICAvLyBPTihBTkQpOiDsu6zrn7wgPSDqsJJcbiAgb24oXG4gICAgbGVmdDogQXZhaWxhYmxlQ29sdW1uczxUTGVmdD4sXG4gICAgcmlnaHQ6IEV4dHJhY3RDb2x1bW5UeXBlPFRMZWZ0LCBBdmFpbGFibGVDb2x1bW5zPFRMZWZ0PiAmIHN0cmluZz4sXG4gICk6IHRoaXM7XG4gIG9uKFxuICAgIGxlZnQ6IEF2YWlsYWJsZUNvbHVtbnM8VFJpZ2h0PixcbiAgICByaWdodDogRXh0cmFjdENvbHVtblR5cGU8VFJpZ2h0LCBBdmFpbGFibGVDb2x1bW5zPFRSaWdodD4gJiBzdHJpbmc+LFxuICApOiB0aGlzO1xuICAvLyBPTihBTkQpOiDsu6zrn7wgKOyXsOyCsOyekCkg7Lus65+8XG4gIG9uKFxuICAgIGxlZnQ6IEF2YWlsYWJsZUNvbHVtbnM8VExlZnQ+LFxuICAgIG9wZXJhdG9yOiBDb21wYXJpc29uT3BlcmF0b3IsXG4gICAgcmlnaHQ6IEF2YWlsYWJsZUNvbHVtbnM8VFJpZ2h0PixcbiAgKTogdGhpcztcbiAgb24oXG4gICAgbGVmdDogQXZhaWxhYmxlQ29sdW1uczxUUmlnaHQ+LFxuICAgIG9wZXJhdG9yOiBDb21wYXJpc29uT3BlcmF0b3IsXG4gICAgcmlnaHQ6IEF2YWlsYWJsZUNvbHVtbnM8VExlZnQ+LFxuICApOiB0aGlzO1xuICAvLyBPTihBTkQpOiDsu6zrn7wgKOyXsOyCsOyekCkg6rCSXG4gIG9uKFxuICAgIGxlZnQ6IEF2YWlsYWJsZUNvbHVtbnM8VExlZnQ+LFxuICAgIG9wZXJhdG9yOiBDb21wYXJpc29uT3BlcmF0b3IsXG4gICAgcmlnaHQ6IEV4dHJhY3RDb2x1bW5UeXBlPFRMZWZ0LCBBdmFpbGFibGVDb2x1bW5zPFRMZWZ0PiAmIHN0cmluZz4sXG4gICk6IHRoaXM7XG4gIG9uKFxuICAgIGxlZnQ6IEF2YWlsYWJsZUNvbHVtbnM8VFJpZ2h0PixcbiAgICBvcGVyYXRvcjogQ29tcGFyaXNvbk9wZXJhdG9yLFxuICAgIHJpZ2h0OiBFeHRyYWN0Q29sdW1uVHlwZTxUUmlnaHQsIEF2YWlsYWJsZUNvbHVtbnM8VFJpZ2h0PiAmIHN0cmluZz4sXG4gICk6IHRoaXM7XG4gIC8vIE9OKEFORCk6IOy9nOuwsVxuICBvbihjYWxsYmFjazogKG5lc3RlZDogSm9pbkNsYXVzZUdyb3VwPFRMZWZ0LCBUUmlnaHQ+KSA9PiB2b2lkKTogdGhpcztcbiAgb24oY2FsbGJhY2s6IChuZXN0ZWQ6IEpvaW5DbGF1c2VHcm91cDxUUmlnaHQsIFRMZWZ0PikgPT4gdm9pZCk6IHRoaXM7XG4gIC8vIE9OKEFORCkg6rWs7ZiEXG4gIG9uKC4uLmFyZ3M6IGFueVtdKTogdGhpcyB7XG4gICAgdGhpcy5jYWxsYmFjay5vbiguLi4oYXJncyBhcyBbc3RyaW5nLCBzdHJpbmddKSk7XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICAvLyBPTihPUik6IOy7rOufvCA9IOy7rOufvFxuICBvck9uKGxlZnQ6IEF2YWlsYWJsZUNvbHVtbnM8VExlZnQ+LCByaWdodDogQXZhaWxhYmxlQ29sdW1uczxUUmlnaHQ+KTogdGhpcztcbiAgb3JPbihsZWZ0OiBBdmFpbGFibGVDb2x1bW5zPFRSaWdodD4sIHJpZ2h0OiBBdmFpbGFibGVDb2x1bW5zPFRMZWZ0Pik6IHRoaXM7XG4gIC8vIE9OKE9SKTog7Lus65+8ID0g6rCSXG4gIG9yT24oXG4gICAgbGVmdDogQXZhaWxhYmxlQ29sdW1uczxUTGVmdD4sXG4gICAgcmlnaHQ6IEV4dHJhY3RDb2x1bW5UeXBlPFRMZWZ0LCBBdmFpbGFibGVDb2x1bW5zPFRMZWZ0PiAmIHN0cmluZz4sXG4gICk6IHRoaXM7XG4gIG9yT24oXG4gICAgbGVmdDogQXZhaWxhYmxlQ29sdW1uczxUUmlnaHQ+LFxuICAgIHJpZ2h0OiBFeHRyYWN0Q29sdW1uVHlwZTxUUmlnaHQsIEF2YWlsYWJsZUNvbHVtbnM8VFJpZ2h0PiAmIHN0cmluZz4sXG4gICk6IHRoaXM7XG4gIC8vIE9OKE9SKTog7Lus65+8ICjsl7DsgrDsnpApIOy7rOufvFxuICBvck9uKFxuICAgIGxlZnQ6IEF2YWlsYWJsZUNvbHVtbnM8VExlZnQ+LFxuICAgIG9wZXJhdG9yOiBDb21wYXJpc29uT3BlcmF0b3IsXG4gICAgcmlnaHQ6IEF2YWlsYWJsZUNvbHVtbnM8VFJpZ2h0PixcbiAgKTogdGhpcztcbiAgb3JPbihcbiAgICBsZWZ0OiBBdmFpbGFibGVDb2x1bW5zPFRSaWdodD4sXG4gICAgb3BlcmF0b3I6IENvbXBhcmlzb25PcGVyYXRvcixcbiAgICByaWdodDogQXZhaWxhYmxlQ29sdW1uczxUTGVmdD4sXG4gICk6IHRoaXM7XG4gIC8vIE9OKE9SKTog7Lus65+8ICjsl7DsgrDsnpApIOqwklxuICBvck9uKFxuICAgIGxlZnQ6IEF2YWlsYWJsZUNvbHVtbnM8VExlZnQ+LFxuICAgIG9wZXJhdG9yOiBDb21wYXJpc29uT3BlcmF0b3IsXG4gICAgcmlnaHQ6IEV4dHJhY3RDb2x1bW5UeXBlPFRMZWZ0LCBBdmFpbGFibGVDb2x1bW5zPFRMZWZ0PiAmIHN0cmluZz4sXG4gICk6IHRoaXM7XG4gIG9yT24oXG4gICAgbGVmdDogQXZhaWxhYmxlQ29sdW1uczxUUmlnaHQ+LFxuICAgIG9wZXJhdG9yOiBDb21wYXJpc29uT3BlcmF0b3IsXG4gICAgcmlnaHQ6IEV4dHJhY3RDb2x1bW5UeXBlPFRSaWdodCwgQXZhaWxhYmxlQ29sdW1uczxUUmlnaHQ+ICYgc3RyaW5nPixcbiAgKTogdGhpcztcbiAgLy8gT04oT1IpOiDsvZzrsLFcbiAgb3JPbihjYWxsYmFjazogKG5lc3RlZDogSm9pbkNsYXVzZUdyb3VwPFRMZWZ0LCBUUmlnaHQ+KSA9PiB2b2lkKTogdGhpcztcbiAgb3JPbihjYWxsYmFjazogKG5lc3RlZDogSm9pbkNsYXVzZUdyb3VwPFRSaWdodCwgVExlZnQ+KSA9PiB2b2lkKTogdGhpcztcbiAgLy8gT04oT1IpIOq1rO2YhFxuICBvck9uKC4uLmFyZ3M6IGFueVtdKTogdGhpcyB7XG4gICAgdGhpcy5jYWxsYmFjay5vck9uKC4uLihhcmdzIGFzIFtzdHJpbmcsIHN0cmluZ10pKTtcbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIC8vIE9OIFZBTChBTkQpOiDsu6zrn7wgPSDqsJIgKOqwkuydhCDsu6zrn7wg7LC47KGw6rCAIOyVhOuLjCDtjIzrnbzrr7jthLDroZwg67CU7J2465SpKVxuICBvblZhbChjb2x1bW46IEF2YWlsYWJsZUNvbHVtbnM8VExlZnQ+LCB2YWx1ZTogYW55KTogdGhpcztcbiAgb25WYWwoY29sdW1uOiBBdmFpbGFibGVDb2x1bW5zPFRSaWdodD4sIHZhbHVlOiBhbnkpOiB0aGlzO1xuICBvblZhbChjb2x1bW46IEF2YWlsYWJsZUNvbHVtbnM8VExlZnQ+LCBvcGVyYXRvcjogQ29tcGFyaXNvbk9wZXJhdG9yLCB2YWx1ZTogYW55KTogdGhpcztcbiAgb25WYWwoY29sdW1uOiBBdmFpbGFibGVDb2x1bW5zPFRSaWdodD4sIG9wZXJhdG9yOiBDb21wYXJpc29uT3BlcmF0b3IsIHZhbHVlOiBhbnkpOiB0aGlzO1xuICBvblZhbCguLi5hcmdzOiBhbnlbXSk6IHRoaXMge1xuICAgICh0aGlzLmNhbGxiYWNrIGFzIGFueSkub25WYWwoLi4uYXJncyk7XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICAvLyBBTkQgT04gVkFMOiBvblZhbOydmCDrqoXsi5zsoIEgYWxpYXMgKEtuZXgg7Zi47ZmYKVxuICBhbmRPblZhbChjb2x1bW46IEF2YWlsYWJsZUNvbHVtbnM8VExlZnQ+LCB2YWx1ZTogYW55KTogdGhpcztcbiAgYW5kT25WYWwoY29sdW1uOiBBdmFpbGFibGVDb2x1bW5zPFRSaWdodD4sIHZhbHVlOiBhbnkpOiB0aGlzO1xuICBhbmRPblZhbChjb2x1bW46IEF2YWlsYWJsZUNvbHVtbnM8VExlZnQ+LCBvcGVyYXRvcjogQ29tcGFyaXNvbk9wZXJhdG9yLCB2YWx1ZTogYW55KTogdGhpcztcbiAgYW5kT25WYWwoY29sdW1uOiBBdmFpbGFibGVDb2x1bW5zPFRSaWdodD4sIG9wZXJhdG9yOiBDb21wYXJpc29uT3BlcmF0b3IsIHZhbHVlOiBhbnkpOiB0aGlzO1xuICBhbmRPblZhbCguLi5hcmdzOiBhbnlbXSk6IHRoaXMge1xuICAgICh0aGlzLmNhbGxiYWNrIGFzIGFueSkuYW5kT25WYWwoLi4uYXJncyk7XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICAvLyBPUiBPTiBWQUw6IE9SIOyhsOqxtOycvOuhnCDqsJIg67CU7J2465SpXG4gIG9yT25WYWwoY29sdW1uOiBBdmFpbGFibGVDb2x1bW5zPFRMZWZ0PiwgdmFsdWU6IGFueSk6IHRoaXM7XG4gIG9yT25WYWwoY29sdW1uOiBBdmFpbGFibGVDb2x1bW5zPFRSaWdodD4sIHZhbHVlOiBhbnkpOiB0aGlzO1xuICBvck9uVmFsKGNvbHVtbjogQXZhaWxhYmxlQ29sdW1uczxUTGVmdD4sIG9wZXJhdG9yOiBDb21wYXJpc29uT3BlcmF0b3IsIHZhbHVlOiBhbnkpOiB0aGlzO1xuICBvck9uVmFsKGNvbHVtbjogQXZhaWxhYmxlQ29sdW1uczxUUmlnaHQ+LCBvcGVyYXRvcjogQ29tcGFyaXNvbk9wZXJhdG9yLCB2YWx1ZTogYW55KTogdGhpcztcbiAgb3JPblZhbCguLi5hcmdzOiBhbnlbXSk6IHRoaXMge1xuICAgICh0aGlzLmNhbGxiYWNrIGFzIGFueSkub3JPblZhbCguLi5hcmdzKTtcbiAgICByZXR1cm4gdGhpcztcbiAgfVxufVxuXG4vKlxuICBUUmVzb2x2ZWQ6IOy/vOumrCDsi6Ttlokg7ZuEIOuwmO2ZmOuQoCDqsrDqs7wg7YOA7J6FXG4gIFRSZXR1cm5pbmc6IFJFVFVSTklORyDsoIjsl5Ag7IKs7Jqp65CgIO2DgOyehVxuKi9cbmV4cG9ydCBjbGFzcyBSZXNvbHZlZFB1cmk8VFJlc29sdmVkLCBUUmV0dXJuaW5nPiBpbXBsZW1lbnRzIFByb21pc2U8VFJlc29sdmVkPiB7XG4gIGNvbnN0cnVjdG9yKFxuICAgIHB1YmxpYyBrbmV4UXVlcnk6IEtuZXguUXVlcnlCdWlsZGVyLFxuICAgIHByaXZhdGUga25leDogS25leCxcbiAgICBwcml2YXRlIHRhYmxlU3BlYzogVGFibGVTcGVjIHwgbnVsbCA9IG51bGwsXG4gICkge31cblxuICBbU3ltYm9sLnRvU3RyaW5nVGFnXTogc3RyaW5nID0gXCJQcm9taXNlXCI7XG5cbiAgdG9RdWVyeSgpOiBzdHJpbmcge1xuICAgIHJldHVybiB0aGlzLmtuZXhRdWVyeS50b1F1ZXJ5KCk7XG4gIH1cblxuICBkZWJ1ZygpOiB0aGlzIHtcbiAgICBjb25zb2xlLmxvZyhgJHtjaGFsay5jeWFuKFwiW1B1cmkgRGVidWddXCIpfSAke2NoYWxrLnllbGxvdyh0aGlzLnRvUXVlcnkoKSl9YCk7XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICB0aGVuPFRSZXN1bHQxID0gVFJlc29sdmVkLCBUUmVzdWx0MiA9IG5ldmVyPihcbiAgICBvbmZ1bGZpbGxlZD86ICgodmFsdWU6IFRSZXNvbHZlZCkgPT4gVFJlc3VsdDEgfCBQcm9taXNlTGlrZTxUUmVzdWx0MT4pIHwgbnVsbCxcbiAgICBvbnJlamVjdGVkPzogKChyZWFzb246IGFueSkgPT4gVFJlc3VsdDIgfCBQcm9taXNlTGlrZTxUUmVzdWx0Mj4pIHwgbnVsbCxcbiAgKTogUHJvbWlzZTxUUmVzdWx0MSB8IFRSZXN1bHQyPiB7XG4gICAgTmFpdGUudChcInB1cmk6ZXhlY3V0ZWQtcXVlcnlcIiwgdGhpcy50b1F1ZXJ5KCkpO1xuICAgIHJldHVybiB0aGlzLmtuZXhRdWVyeS50aGVuKG9uZnVsZmlsbGVkIGFzIGFueSwgb25yZWplY3RlZCk7XG4gIH1cblxuICBjYXRjaDxUUmVzdWx0MiA9IG5ldmVyPihcbiAgICBvbnJlamVjdGVkPzogKChyZWFzb246IGFueSkgPT4gVFJlc3VsdDIgfCBQcm9taXNlTGlrZTxUUmVzdWx0Mj4pIHwgbnVsbCxcbiAgKTogUHJvbWlzZTxUUmVzb2x2ZWQgfCBUUmVzdWx0Mj4ge1xuICAgIHJldHVybiB0aGlzLmtuZXhRdWVyeS5jYXRjaChvbnJlamVjdGVkKTtcbiAgfVxuXG4gIGZpbmFsbHkob25maW5hbGx5PzogKCgpID0+IHZvaWQpIHwgbnVsbCk6IFByb21pc2U8VFJlc29sdmVkPiB7XG4gICAgcmV0dXJuIHRoaXMua25leFF1ZXJ5LmZpbmFsbHkob25maW5hbGx5KTtcbiAgfVxuXG4gIC8vIE9OIENPTkZMSUNUIC0g7Lus65+8IOq4sOuwmFxuICBvbkNvbmZsaWN0PFRUYWJsZXMgZXh0ZW5kcyBSZWNvcmQ8c3RyaW5nLCBUUmV0dXJuaW5nPj4oXG4gICAgY29sdW1uczogc3RyaW5nIHwgc3RyaW5nW10sXG4gICAgYWN0aW9uPzogT25Db25mbGljdEFjdGlvbjxUVGFibGVzPixcbiAgKTogdGhpcyB7XG4gICAgY29uc3QgdGFyZ2V0ID0gQXJyYXkuaXNBcnJheShjb2x1bW5zKSA/IGNvbHVtbnMgOiBbY29sdW1uc107XG5cbiAgICBpZiAoIWFjdGlvbiB8fCBhY3Rpb24gPT09IFwibm90aGluZ1wiKSB7XG4gICAgICAvLyBETyBOT1RISU5HXG4gICAgICB0aGlzLmtuZXhRdWVyeS5vbkNvbmZsaWN0KHRhcmdldCkuaWdub3JlKCk7XG4gICAgfSBlbHNlIHtcbiAgICAgIC8vIERPIFVQREFURVxuICAgICAgY29uc3QgeyB1cGRhdGUgfSA9IGFjdGlvbjtcblxuICAgICAgLy8gYWN0aW9uLnVwZGF0ZSDrsLDsl7Qg7ZiV7YOcIDogW1wibmFtZVwiLCBcImVtYWlsXCJdXG4gICAgICBpZiAoQXJyYXkuaXNBcnJheSh1cGRhdGUpKSB7XG4gICAgICAgIHRoaXMua25leFF1ZXJ5Lm9uQ29uZmxpY3QodGFyZ2V0KS5tZXJnZSh1cGRhdGUpO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgLy8gYWN0aW9uLnVwZGF0ZSDqsJ3ssrQg7ZiV7YOcOiB7IG5hbWU6IFwiSm9oblwiLCBjb3VudDogcmF3KC4uLikgfVxuICAgICAgICBjb25zdCBtZXJnZU9iajogUmVjb3JkPHN0cmluZywgYW55PiA9IHt9O1xuXG4gICAgICAgIGZvciAoY29uc3QgW2tleSwgdmFsdWVdIG9mIE9iamVjdC5lbnRyaWVzKHVwZGF0ZSkpIHtcbiAgICAgICAgICBpZiAoXG4gICAgICAgICAgICB2YWx1ZSAmJlxuICAgICAgICAgICAgdHlwZW9mIHZhbHVlID09PSBcIm9iamVjdFwiICYmXG4gICAgICAgICAgICBcIl90eXBlXCIgaW4gdmFsdWUgJiZcbiAgICAgICAgICAgIHZhbHVlLl90eXBlID09PSBcInNxbF9leHByZXNzaW9uXCJcbiAgICAgICAgICApIHtcbiAgICAgICAgICAgIC8vIFNxbEV4cHJlc3Npb24g4oaSIGtuZXgucmF3KCnroZwg67OA7ZmYXG4gICAgICAgICAgICBtZXJnZU9ialtrZXldID0gdGhpcy5rbmV4LnJhdygodmFsdWUgYXMgU3FsRXhwcmVzc2lvbjxhbnk+KS5fc3FsKTtcbiAgICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgLy8g7J2867CYIOqwklxuICAgICAgICAgICAgbWVyZ2VPYmpba2V5XSA9IHNlcmlhbGl6ZUpzb25Db2x1bW5WYWx1ZSh0aGlzLnRhYmxlU3BlYywga2V5LCB2YWx1ZSk7XG4gICAgICAgICAgfVxuICAgICAgICB9XG5cbiAgICAgICAgdGhpcy5rbmV4UXVlcnkub25Db25mbGljdCh0YXJnZXQpLm1lcmdlKG1lcmdlT2JqKTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIC8vIFJFVFVSTklORzogXCIqXCIgLSDsoITssrQg7Lus65+8XG4gIHJldHVybmluZyhjb2x1bW46IFwiKlwiKTogUmVzb2x2ZWRQdXJpPFRSZXR1cm5pbmdbXSwgbmV2ZXI+O1xuICAvLyBSRVRVUk5JTkc6IOuLqOydvCDsu6zrn7xcbiAgcmV0dXJuaW5nPFRDb2x1bW4gZXh0ZW5kcyBDb2x1bW5LZXlzPFRSZXR1cm5pbmc+PihcbiAgICBjb2x1bW46IFRDb2x1bW4sXG4gICk6IFJlc29sdmVkUHVyaTxQaWNrPFRSZXR1cm5pbmcsIFRDb2x1bW4+W10sIG5ldmVyPjtcbiAgLy8gUkVUVVJOSU5HOiDrs7XsiJgg7Lus65+8ICjrsLDsl7QpXG4gIHJldHVybmluZzxUQ29sdW1uIGV4dGVuZHMgQ29sdW1uS2V5czxUUmV0dXJuaW5nPj4oXG4gICAgY29sdW1uczogVENvbHVtbltdLFxuICApOiBSZXNvbHZlZFB1cmk8UGljazxUUmV0dXJuaW5nLCBUQ29sdW1uPltdLCBuZXZlcj47XG4gIC8vIFJFVFVSTklORyDqtaztmIRcbiAgcmV0dXJuaW5nKGNvbHVtbk9yQ29sdW1uczogc3RyaW5nIHwgc3RyaW5nW10pOiBSZXNvbHZlZFB1cmk8YW55W10sIG5ldmVyPiB7XG4gICAgdGhpcy5rbmV4UXVlcnkucmV0dXJuaW5nKGNvbHVtbk9yQ29sdW1ucyk7XG4gICAgcmV0dXJuIG5ldyBSZXNvbHZlZFB1cmkodGhpcy5rbmV4UXVlcnksIHRoaXMua25leCwgdGhpcy50YWJsZVNwZWMpO1xuICB9XG59XG4iXSwibWFwcGluZ3MiOiI7Ozs7Ozs7O0FBaUZBLFNBQVMsdUJBQXVC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
1095
+ //# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoicHVyaS5qcyIsIm5hbWVzIjpbXSwic291cmNlcyI6WyIuLi8uLi9zcmMvZGF0YWJhc2UvcHVyaS50cyJdLCJzb3VyY2VzQ29udGVudCI6WyIvKiBveGxpbnQtZGlzYWJsZSBAdHlwZXNjcmlwdC1lc2xpbnQvbm8tZXhwbGljaXQtYW55ICovIC8vIFB1cmnripQg64uk7JaR7ZWcIO2DgOyeheydhCDsgqzsmqntlZjqs6Ag7J6I7Iq164uI64ukLlxuXG5pbXBvcnQgYXNzZXJ0IGZyb20gXCJhc3NlcnRcIjtcblxuaW1wb3J0IGNoYWxrIGZyb20gXCJjaGFsa1wiO1xuaW1wb3J0IGluZmxlY3Rpb24gZnJvbSBcImluZmxlY3Rpb25cIjtcbmltcG9ydCB7IHR5cGUgS25leCB9IGZyb20gXCJrbmV4XCI7XG5cbmltcG9ydCB7IEVudGl0eU1hbmFnZXIgfSBmcm9tIFwiLi4vZW50aXR5L2VudGl0eS1tYW5hZ2VyXCI7XG5pbXBvcnQgeyB0eXBlIFRhYmxlU3BlYyB9IGZyb20gXCIuLi9lbnRpdHkvZW50aXR5LW1hbmFnZXJcIjtcbmltcG9ydCB7IE5haXRlIH0gZnJvbSBcIi4uL25haXRlL25haXRlXCI7XG5pbXBvcnQge1xuICBpc0Z1bmN0aW9uVmFsdWUsXG4gIGlzTnVtYmVyVmFsdWUsXG4gIGlzT2JqZWN0VmFsdWUsXG4gIGlzU3RyaW5nVmFsdWUsXG59IGZyb20gXCIuLi91dGlscy9ydW50aW1lLXZhbHVlXCI7XG5pbXBvcnQgeyB0eXBlIENsZWFyU3RhdGVtZW50cyB9IGZyb20gXCIuL3B1cmktc3Vic2V0LnR5cGVzXCI7XG5pbXBvcnQge1xuICB0eXBlIEF2YWlsYWJsZUNvbHVtbnMsXG4gIHR5cGUgQ29sdW1uS2V5cyxcbiAgdHlwZSBDb21wYXJpc29uT3BlcmF0b3IsXG4gIHR5cGUgRXhwYW5kLFxuICB0eXBlIEV4dHJhY3RDb2x1bW5UeXBlLFxuICB0eXBlIEZ1bGx0ZXh0Q29sdW1ucyxcbiAgdHlwZSBGdXp6eU9wZXJhdG9yLFxuICB0eXBlIEluc2VydERhdGEsXG4gIHR5cGUgSW5zZXJ0UmVzdWx0LFxuICB0eXBlIEpzb25Db2x1bW5zLFxuICB0eXBlIEpzb25TdXBlcnNldFZhbHVlLFxuICB0eXBlIExlZnRKb2luZWRNYXJrZXIsXG4gIHR5cGUgTGVmdEpvaW5NYXJrZXJGb3IsXG4gIHR5cGUgTnVtZXJpY0NvbHVtbnMsXG4gIHR5cGUgT25Db25mbGljdEFjdGlvbixcbiAgdHlwZSBQYXJzZVNlbGVjdE9iamVjdCxcbiAgdHlwZSBSZXN1bHRBdmFpbGFibGVDb2x1bW5zLFxuICB0eXBlIFNlbGVjdEFsbFJlc3VsdCxcbiAgdHlwZSBTZWxlY3RPYmplY3QsXG4gIHR5cGUgU2VsZWN0VmFsdWUsXG4gIHR5cGUgU2luZ2xlVGFibGVWYWx1ZSxcbiAgdHlwZSBTcWxFeHByZXNzaW9uLFxuICB0eXBlIFRzSGlnaGxpZ2h0T3B0aW9ucyxcbiAgdHlwZSBUc1F1ZXJ5Q29uZmlnLFxuICB0eXBlIFRzUXVlcnlPcHRpb25zLFxuICB0eXBlIFRzUmFua09wdGlvbnMsXG4gIHR5cGUgVmVjdG9yQ29sdW1ucyxcbiAgdHlwZSBXaGVyZUNvbmRpdGlvbixcbiAgdHlwZSBXaGVyZU9wZXJhdG9yLFxufSBmcm9tIFwiLi9wdXJpLnR5cGVzXCI7XG5pbXBvcnQgeyBGVVpaWV9PUEVSQVRPUlMgfSBmcm9tIFwiLi9wdXJpLnR5cGVzXCI7XG5cbnR5cGUgUHVyaU9yZGVyQnlEaXJlY3Rpb24gPSBcImFzY1wiIHwgXCJkZXNjXCI7XG50eXBlIFB1cmlPcmRlckJ5TnVsbHMgPSBcImZpcnN0XCIgfCBcImxhc3RcIjtcbnR5cGUgUHVyaU9yZGVyQnlFeHByZXNzaW9uID0gU3FsRXhwcmVzc2lvbjxcIm51bWJlclwiPiB8IFNxbEV4cHJlc3Npb248XCJzdHJpbmdcIj47XG50eXBlIFB1cmlPcmRlckJ5SXRlbTxUQ29sdW1uIGV4dGVuZHMgc3RyaW5nPiA9IHtcbiAgY29sdW1uOiBUQ29sdW1uIHwgUHVyaU9yZGVyQnlFeHByZXNzaW9uO1xuICBvcmRlcj86IFB1cmlPcmRlckJ5RGlyZWN0aW9uO1xuICBudWxscz86IFB1cmlPcmRlckJ5TnVsbHM7XG59O1xudHlwZSBQdXJpT3JkZXJCeUVudHJ5PFRDb2x1bW4gZXh0ZW5kcyBzdHJpbmc+ID1cbiAgfCBUQ29sdW1uXG4gIHwgUHVyaU9yZGVyQnlFeHByZXNzaW9uXG4gIHwgUHVyaU9yZGVyQnlJdGVtPFRDb2x1bW4+O1xudHlwZSBQdXJpT3JkZXJCeVJ1bnRpbWVJdGVtID0ge1xuICBjb2x1bW46IHN0cmluZyB8IFB1cmlPcmRlckJ5RXhwcmVzc2lvbjtcbiAgb3JkZXI/OiBQdXJpT3JkZXJCeURpcmVjdGlvbjtcbiAgbnVsbHM/OiBQdXJpT3JkZXJCeU51bGxzO1xufTtcbnR5cGUgUHVyaU9yZGVyQnlSdW50aW1lRW50cnkgPSBzdHJpbmcgfCBQdXJpT3JkZXJCeUV4cHJlc3Npb24gfCBQdXJpT3JkZXJCeVJ1bnRpbWVJdGVtO1xuXG50eXBlIEZyb21SZWdpc3RyYXRpb24gPSB7XG4gIGtpbmQ6IFwiZnJvbVwiO1xuICBhbGlhczogc3RyaW5nO1xuICB0YWJsZTogc3RyaW5nIHwgbnVsbDtcbn07XG5cbnR5cGUgSm9pblJlZ2lzdHJhdGlvbiA9IHtcbiAga2luZDogXCJqb2luXCI7XG4gIGFsaWFzOiBzdHJpbmc7XG4gIHRhYmxlOiBzdHJpbmcgfCBudWxsO1xuICBqb2luVHlwZTogXCJqb2luXCIgfCBcImxlZnRKb2luXCI7XG4gIGxlZnQ6IHN0cmluZyB8IG51bGw7XG4gIHJpZ2h0OiBzdHJpbmcgfCBudWxsO1xuICByZXVzYWJsZTogYm9vbGVhbjtcbn07XG5cbnR5cGUgQ29ycmVsYXRpb25SZWdpc3RyYXRpb24gPSBGcm9tUmVnaXN0cmF0aW9uIHwgSm9pblJlZ2lzdHJhdGlvbjtcblxuZXhwb3J0IGZ1bmN0aW9uIHBhcnNlRnV6enlPcGVyYXRvcihvcGVyYXRvcj86IHN0cmluZyk6IEZ1enp5T3BlcmF0b3Ige1xuICBjb25zdCBub3JtYWxpemVkID0gb3BlcmF0b3I/LnRyaW0oKSA/PyBcIjwlXCI7XG4gIGNvbnN0IGZ1enp5T3BlcmF0b3IgPSBGVVpaWV9PUEVSQVRPUlMuZmluZCgoY2FuZGlkYXRlKSA9PiBjYW5kaWRhdGUgPT09IG5vcm1hbGl6ZWQpO1xuXG4gIGlmICghZnV6enlPcGVyYXRvcikge1xuICAgIHRocm93IG5ldyBFcnJvcihgSW52YWxpZCBmdXp6eSBvcGVyYXRvcjogJHtvcGVyYXRvciA/PyBcIlwifWApO1xuICB9XG5cbiAgcmV0dXJuIGZ1enp5T3BlcmF0b3I7XG59XG5cbmZ1bmN0aW9uIHNlcmlhbGl6ZUpzb25TdXBlcnNldFZhbHVlPFZhbHVlPih2YWx1ZTogVmFsdWUpOiBzdHJpbmcge1xuICBjb25zdCBzZXJpYWxpemVkID0gSlNPTi5zdHJpbmdpZnkodmFsdWUpO1xuXG4gIGlmIChzZXJpYWxpemVkID09PSB1bmRlZmluZWQpIHtcbiAgICB0aHJvdyBuZXcgVHlwZUVycm9yKFxuICAgICAgXCJQdXJpIEpTT05CIGNvbnRhaW5tZW50IHZhbHVlIG11c3QgYmUgSlNPTi1zZXJpYWxpemFibGU7IEpTT04uc3RyaW5naWZ5IHJldHVybmVkIHVuZGVmaW5lZC5cIixcbiAgICApO1xuICB9XG5cbiAgcmV0dXJuIHNlcmlhbGl6ZWQ7XG59XG5cbmZ1bmN0aW9uIHNlcmlhbGl6ZUpzb25Db2x1bW5WYWx1ZTxWYWx1ZT4oXG4gIHRhYmxlU3BlYzogVGFibGVTcGVjIHwgbnVsbCxcbiAgY29sdW1uOiBzdHJpbmcsXG4gIHZhbHVlOiBWYWx1ZSxcbik6IFZhbHVlIHwgc3RyaW5nIHtcbiAgaWYgKCF0YWJsZVNwZWM/Lmpzb25Db2x1bW5zLmluY2x1ZGVzKGNvbHVtbikgfHwgdmFsdWUgPT09IHVuZGVmaW5lZCB8fCB2YWx1ZSA9PT0gbnVsbCkge1xuICAgIHJldHVybiB2YWx1ZTtcbiAgfVxuXG4gIHJldHVybiBKU09OLnN0cmluZ2lmeSh2YWx1ZSk7XG59XG5cbmZ1bmN0aW9uIG5vcm1hbGl6ZU9yZGVyQnlEaXJlY3Rpb24oZGlyZWN0aW9uOiBQdXJpT3JkZXJCeURpcmVjdGlvbiA9IFwiYXNjXCIpOiBQdXJpT3JkZXJCeURpcmVjdGlvbiB7XG4gIGlmIChkaXJlY3Rpb24gIT09IFwiYXNjXCIgJiYgZGlyZWN0aW9uICE9PSBcImRlc2NcIikge1xuICAgIHRocm93IG5ldyBFcnJvcihgSW52YWxpZCBvcmRlciBkaXJlY3Rpb246ICR7ZGlyZWN0aW9ufWApO1xuICB9XG5cbiAgcmV0dXJuIGRpcmVjdGlvbjtcbn1cblxuZnVuY3Rpb24gbm9ybWFsaXplT3JkZXJCeU51bGxzKG51bGxzPzogUHVyaU9yZGVyQnlOdWxscyk6IFB1cmlPcmRlckJ5TnVsbHMgfCB1bmRlZmluZWQge1xuICBpZiAobnVsbHMgPT09IHVuZGVmaW5lZCkge1xuICAgIHJldHVybiB1bmRlZmluZWQ7XG4gIH1cblxuICBpZiAobnVsbHMgIT09IFwiZmlyc3RcIiAmJiBudWxscyAhPT0gXCJsYXN0XCIpIHtcbiAgICB0aHJvdyBuZXcgRXJyb3IoYEludmFsaWQgb3JkZXIgbnVsbHM6ICR7bnVsbHN9YCk7XG4gIH1cblxuICByZXR1cm4gbnVsbHM7XG59XG5cbmZ1bmN0aW9uIGZvcm1hdE51bGxzU3VmZml4KG51bGxzPzogUHVyaU9yZGVyQnlOdWxscyk6IHN0cmluZyB7XG4gIGlmICghbnVsbHMpIHtcbiAgICByZXR1cm4gXCJcIjtcbiAgfVxuXG4gIHJldHVybiBgIE5VTExTICR7bnVsbHMudG9VcHBlckNhc2UoKX1gO1xufVxuXG5mdW5jdGlvbiBpc09yZGVyQnlFbnRyaWVzPFZhbHVlPihcbiAgdmFsdWU6IFZhbHVlLFxuKTogdmFsdWUgaXMgVmFsdWUgJiByZWFkb25seSBQdXJpT3JkZXJCeVJ1bnRpbWVFbnRyeVtdIHtcbiAgcmV0dXJuIEFycmF5LmlzQXJyYXkodmFsdWUpO1xufVxuXG5mdW5jdGlvbiBpc1NxbEV4cHJlc3Npb248VmFsdWU+KHZhbHVlOiBWYWx1ZSk6IHZhbHVlIGlzIFZhbHVlICYgUHVyaU9yZGVyQnlFeHByZXNzaW9uIHtcbiAgcmV0dXJuIGlzT2JqZWN0VmFsdWUodmFsdWUpICYmIFwiX3R5cGVcIiBpbiB2YWx1ZSAmJiB2YWx1ZVtcIl90eXBlXCJdID09PSBcInNxbF9leHByZXNzaW9uXCI7XG59XG5cbmZ1bmN0aW9uIGlzTmVzdGVkU2VsZWN0T2JqZWN0PFRUYWJsZXMgZXh0ZW5kcyBvYmplY3Q+KFxuICB2YWx1ZTogU2VsZWN0VmFsdWU8VFRhYmxlcz4gfCBTZWxlY3RPYmplY3Q8VFRhYmxlcz4sXG4pOiB2YWx1ZSBpcyBTZWxlY3RPYmplY3Q8VFRhYmxlcz4ge1xuICByZXR1cm4gaXNPYmplY3RWYWx1ZSh2YWx1ZSkgJiYgIShcIl90eXBlXCIgaW4gdmFsdWUpO1xufVxuXG5leHBvcnQgY2xhc3MgUHVyaTxUU2NoZW1hLCBUVGFibGVzIGV4dGVuZHMgb2JqZWN0LCBUUmVzdWx0PiB7XG4gIHByaXZhdGUga25leFF1ZXJ5OiBLbmV4LlF1ZXJ5QnVpbGRlcjtcbiAgcHJpdmF0ZSB0YWJsZVNwZWM6IFRhYmxlU3BlYyB8IG51bGwgPSBudWxsO1xuICBwcml2YXRlIGNvcnJlbGF0aW9uUmVnaXN0cnkgPSBuZXcgTWFwPHN0cmluZywgQ29ycmVsYXRpb25SZWdpc3RyYXRpb24+KCk7XG5cbiAgLy8g7IOd7ISx7J6QIOyLnOq3uOuLiOyymOuTpFxuICBjb25zdHJ1Y3RvcihrbmV4OiBLbmV4LCB0YWJsZU5hbWU6IHN0cmluZyk7XG4gIGNvbnN0cnVjdG9yKGtuZXg6IEtuZXgsIHRhYmxlU291cmNlOiBSZWNvcmQ8c3RyaW5nLCBzdHJpbmcgfCBQdXJpPFRTY2hlbWEsIGFueSwgYW55Pj4pO1xuICBjb25zdHJ1Y3RvcihcbiAgICBwdWJsaWMga25leDogS25leCxcbiAgICB0YWJsZU5hbWVPclNvdXJjZTogYW55LFxuICApIHtcbiAgICBpZiAoaXNTdHJpbmdWYWx1ZSh0YWJsZU5hbWVPclNvdXJjZSkpIHtcbiAgICAgIC8vIENhc2U6IG5ldyBQdXJpKGtuZXgsIFwidXNlcnNcIilcbiAgICAgIHRoaXMua25leFF1ZXJ5ID0gdGhpcy5rbmV4KHRhYmxlTmFtZU9yU291cmNlKS5mcm9tKHRhYmxlTmFtZU9yU291cmNlKTtcbiAgICAgIHRoaXMudGFibGVTcGVjID0gdGhpcy5zYWZlR2V0VGFibGVTcGVjKHRhYmxlTmFtZU9yU291cmNlKTtcbiAgICAgIHRoaXMuY29ycmVsYXRpb25SZWdpc3RyeS5zZXQodGFibGVOYW1lT3JTb3VyY2UsIHtcbiAgICAgICAga2luZDogXCJmcm9tXCIsXG4gICAgICAgIGFsaWFzOiB0YWJsZU5hbWVPclNvdXJjZSxcbiAgICAgICAgdGFibGU6IHRhYmxlTmFtZU9yU291cmNlLFxuICAgICAgfSk7XG4gICAgfSBlbHNlIGlmIChpc09iamVjdFZhbHVlKHRhYmxlTmFtZU9yU291cmNlKSkge1xuICAgICAgY29uc3QgZW50cmllcyA9IE9iamVjdC5lbnRyaWVzKHRhYmxlTmFtZU9yU291cmNlKTtcbiAgICAgIGlmIChlbnRyaWVzLmxlbmd0aCAhPT0gMSkge1xuICAgICAgICB0aHJvdyBuZXcgRXJyb3IoXCJUYWJsZSBzcGVjIG11c3QgaGF2ZSBleGFjdGx5IG9uZSBlbnRyeVwiKTtcbiAgICAgIH1cbiAgICAgIGFzc2VydChlbnRyaWVzWzBdKTtcbiAgICAgIGNvbnN0IFthbGlhcywgc291cmNlXSA9IGVudHJpZXNbMF07XG4gICAgICBpZiAoaXNTdHJpbmdWYWx1ZShzb3VyY2UpKSB7XG4gICAgICAgIHRoaXMua25leFF1ZXJ5ID0gdGhpcy5rbmV4KHNvdXJjZSkuZnJvbSh7IFthbGlhc106IHNvdXJjZSB9KTtcbiAgICAgICAgdGhpcy50YWJsZVNwZWMgPSB0aGlzLnNhZmVHZXRUYWJsZVNwZWMoc291cmNlKTtcbiAgICAgICAgdGhpcy5jb3JyZWxhdGlvblJlZ2lzdHJ5LnNldChhbGlhcywgeyBraW5kOiBcImZyb21cIiwgYWxpYXMsIHRhYmxlOiBzb3VyY2UgfSk7XG4gICAgICB9IGVsc2UgaWYgKHNvdXJjZSBpbnN0YW5jZW9mIFB1cmkpIHtcbiAgICAgICAgY29uc3Qgc3VicXVlcnlCdWlsZGVyID0gc291cmNlLnJhd1F1ZXJ5KCk7XG4gICAgICAgIHRoaXMua25leFF1ZXJ5ID0gdGhpcy5rbmV4LmZyb20oc3VicXVlcnlCdWlsZGVyLmFzKGFsaWFzKSk7XG4gICAgICAgIHRoaXMuY29ycmVsYXRpb25SZWdpc3RyeS5zZXQoYWxpYXMsIHsga2luZDogXCJmcm9tXCIsIGFsaWFzLCB0YWJsZTogbnVsbCB9KTtcbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIHRocm93IG5ldyBFcnJvcihcIkludmFsaWQgdGFibGUgc3BlY2lmaWNhdGlvblwiKTtcbiAgICAgIH1cbiAgICB9IGVsc2Uge1xuICAgICAgdGhyb3cgbmV3IEVycm9yKFwiSW52YWxpZCB0YWJsZSBzcGVjaWZpY2F0aW9uXCIpO1xuICAgIH1cbiAgfVxuXG4gIHNhZmVHZXRUYWJsZVNwZWModGFibGVOYW1lOiBzdHJpbmcpOiBUYWJsZVNwZWMgfCBudWxsIHtcbiAgICB0cnkge1xuICAgICAgcmV0dXJuIEVudGl0eU1hbmFnZXIuZ2V0VGFibGVTcGVjKHRhYmxlTmFtZSk7XG4gICAgfSBjYXRjaCB7XG4gICAgICByZXR1cm4gbnVsbDtcbiAgICB9XG4gIH1cblxuICAvLyBTdGF0aWMgU1FMIGhlbHBlciBmdW5jdGlvbnMgZm9yIFNFTEVDVFxuICBzdGF0aWMgY291bnQoY29sdW1uOiBzdHJpbmcgPSBcIipcIik6IFNxbEV4cHJlc3Npb248XCJudW1iZXJcIj4ge1xuICAgIHJldHVybiB7XG4gICAgICBfdHlwZTogXCJzcWxfZXhwcmVzc2lvblwiLFxuICAgICAgX3JldHVybjogXCJudW1iZXJcIixcbiAgICAgIF9zcWw6IGBDT1VOVCg/Pyk6OmludGVnZXJgLFxuICAgICAgX3BhcmFtczogW2NvbHVtbl0sXG4gICAgfTtcbiAgfVxuICBzdGF0aWMgc3VtKGNvbHVtbjogc3RyaW5nKTogU3FsRXhwcmVzc2lvbjxcIm51bWJlclwiPiB7XG4gICAgcmV0dXJuIHtcbiAgICAgIF90eXBlOiBcInNxbF9leHByZXNzaW9uXCIsXG4gICAgICBfcmV0dXJuOiBcIm51bWJlclwiLFxuICAgICAgX3NxbDogYFNVTSg/PylgLFxuICAgICAgX3BhcmFtczogW2NvbHVtbl0sXG4gICAgfTtcbiAgfVxuICBzdGF0aWMgYXZnKGNvbHVtbjogc3RyaW5nKTogU3FsRXhwcmVzc2lvbjxcIm51bWJlclwiPiB7XG4gICAgcmV0dXJuIHtcbiAgICAgIF90eXBlOiBcInNxbF9leHByZXNzaW9uXCIsXG4gICAgICBfcmV0dXJuOiBcIm51bWJlclwiLFxuICAgICAgX3NxbDogYEFWRyg/PylgLFxuICAgICAgX3BhcmFtczogW2NvbHVtbl0sXG4gICAgfTtcbiAgfVxuICBzdGF0aWMgbWF4KGNvbHVtbjogc3RyaW5nKTogU3FsRXhwcmVzc2lvbjxcIm51bWJlclwiPiB7XG4gICAgcmV0dXJuIHtcbiAgICAgIF90eXBlOiBcInNxbF9leHByZXNzaW9uXCIsXG4gICAgICBfcmV0dXJuOiBcIm51bWJlclwiLFxuICAgICAgX3NxbDogYE1BWCg/PylgLFxuICAgICAgX3BhcmFtczogW2NvbHVtbl0sXG4gICAgfTtcbiAgfVxuICBzdGF0aWMgbWluKGNvbHVtbjogc3RyaW5nKTogU3FsRXhwcmVzc2lvbjxcIm51bWJlclwiPiB7XG4gICAgcmV0dXJuIHtcbiAgICAgIF90eXBlOiBcInNxbF9leHByZXNzaW9uXCIsXG4gICAgICBfcmV0dXJuOiBcIm51bWJlclwiLFxuICAgICAgX3NxbDogYE1JTig/PylgLFxuICAgICAgX3BhcmFtczogW2NvbHVtbl0sXG4gICAgfTtcbiAgfVxuICBzdGF0aWMgY29uY2F0KC4uLmFyZ3M6IHN0cmluZ1tdKTogU3FsRXhwcmVzc2lvbjxcInN0cmluZ1wiPiB7XG4gICAgcmV0dXJuIHtcbiAgICAgIF90eXBlOiBcInNxbF9leHByZXNzaW9uXCIsXG4gICAgICBfcmV0dXJuOiBcInN0cmluZ1wiLFxuICAgICAgX3NxbDogYENPTkNBVCgke2FyZ3MubWFwKCgpID0+IFwiP1wiKS5qb2luKFwiLCBcIil9KWAsXG4gICAgICBfcGFyYW1zOiBhcmdzLFxuICAgIH07XG4gIH1cbiAgc3RhdGljIHVwcGVyKGNvbHVtbjogc3RyaW5nKTogU3FsRXhwcmVzc2lvbjxcInN0cmluZ1wiPiB7XG4gICAgcmV0dXJuIHtcbiAgICAgIF90eXBlOiBcInNxbF9leHByZXNzaW9uXCIsXG4gICAgICBfcmV0dXJuOiBcInN0cmluZ1wiLFxuICAgICAgX3NxbDogXCJVUFBFUig/PylcIixcbiAgICAgIF9wYXJhbXM6IFtjb2x1bW5dLFxuICAgIH07XG4gIH1cbiAgc3RhdGljIGxvd2VyKGNvbHVtbjogc3RyaW5nKTogU3FsRXhwcmVzc2lvbjxcInN0cmluZ1wiPiB7XG4gICAgcmV0dXJuIHtcbiAgICAgIF90eXBlOiBcInNxbF9leHByZXNzaW9uXCIsXG4gICAgICBfcmV0dXJuOiBcInN0cmluZ1wiLFxuICAgICAgX3NxbDogXCJMT1dFUig/PylcIixcbiAgICAgIF9wYXJhbXM6IFtjb2x1bW5dLFxuICAgIH07XG4gIH1cblxuICBzdGF0aWMgd29yZFNpbWlsYXJpdHkoXG4gICAgY29sdW1uOiBzdHJpbmcgfCBTcWxFeHByZXNzaW9uPFwic3RyaW5nXCI+LFxuICAgIHF1ZXJ5OiBzdHJpbmcsXG4gICk6IFNxbEV4cHJlc3Npb248XCJudW1iZXJcIj4ge1xuICAgIGlmIChpc1N0cmluZ1ZhbHVlKGNvbHVtbikpIHtcbiAgICAgIHJldHVybiB7XG4gICAgICAgIF90eXBlOiBcInNxbF9leHByZXNzaW9uXCIsXG4gICAgICAgIF9yZXR1cm46IFwibnVtYmVyXCIsXG4gICAgICAgIF9zcWw6IFwid29yZF9zaW1pbGFyaXR5KD8sID8/KVwiLFxuICAgICAgICBfcGFyYW1zOiBbcXVlcnksIGNvbHVtbl0sXG4gICAgICB9O1xuICAgIH1cblxuICAgIHJldHVybiB7XG4gICAgICBfdHlwZTogXCJzcWxfZXhwcmVzc2lvblwiLFxuICAgICAgX3JldHVybjogXCJudW1iZXJcIixcbiAgICAgIF9zcWw6IGB3b3JkX3NpbWlsYXJpdHkoPywgJHtjb2x1bW5bXCJfc3FsXCJdfSlgLFxuICAgICAgX3BhcmFtczogW3F1ZXJ5LCAuLi5jb2x1bW5bXCJfcGFyYW1zXCJdXSxcbiAgICB9O1xuICB9XG5cbiAgc3RhdGljIHNpbWlsYXJpdHkoXG4gICAgY29sdW1uOiBzdHJpbmcgfCBTcWxFeHByZXNzaW9uPFwic3RyaW5nXCI+LFxuICAgIHF1ZXJ5OiBzdHJpbmcsXG4gICk6IFNxbEV4cHJlc3Npb248XCJudW1iZXJcIj4ge1xuICAgIGlmIChpc1N0cmluZ1ZhbHVlKGNvbHVtbikpIHtcbiAgICAgIHJldHVybiB7XG4gICAgICAgIF90eXBlOiBcInNxbF9leHByZXNzaW9uXCIsXG4gICAgICAgIF9yZXR1cm46IFwibnVtYmVyXCIsXG4gICAgICAgIF9zcWw6IFwic2ltaWxhcml0eSg/PywgPylcIixcbiAgICAgICAgX3BhcmFtczogW2NvbHVtbiwgcXVlcnldLFxuICAgICAgfTtcbiAgICB9XG5cbiAgICByZXR1cm4ge1xuICAgICAgX3R5cGU6IFwic3FsX2V4cHJlc3Npb25cIixcbiAgICAgIF9yZXR1cm46IFwibnVtYmVyXCIsXG4gICAgICBfc3FsOiBgc2ltaWxhcml0eSgke2NvbHVtbltcIl9zcWxcIl19LCA/KWAsXG4gICAgICBfcGFyYW1zOiBbLi4uY29sdW1uW1wiX3BhcmFtc1wiXSwgcXVlcnldLFxuICAgIH07XG4gIH1cblxuICBzdGF0aWMgc3RyaWN0V29yZFNpbWlsYXJpdHkoXG4gICAgY29sdW1uOiBzdHJpbmcgfCBTcWxFeHByZXNzaW9uPFwic3RyaW5nXCI+LFxuICAgIHF1ZXJ5OiBzdHJpbmcsXG4gICk6IFNxbEV4cHJlc3Npb248XCJudW1iZXJcIj4ge1xuICAgIGlmIChpc1N0cmluZ1ZhbHVlKGNvbHVtbikpIHtcbiAgICAgIHJldHVybiB7XG4gICAgICAgIF90eXBlOiBcInNxbF9leHByZXNzaW9uXCIsXG4gICAgICAgIF9yZXR1cm46IFwibnVtYmVyXCIsXG4gICAgICAgIF9zcWw6IGBzdHJpY3Rfd29yZF9zaW1pbGFyaXR5KD8sID8/KWAsXG4gICAgICAgIF9wYXJhbXM6IFtxdWVyeSwgY29sdW1uXSxcbiAgICAgIH07XG4gICAgfVxuXG4gICAgcmV0dXJuIHtcbiAgICAgIF90eXBlOiBcInNxbF9leHByZXNzaW9uXCIsXG4gICAgICBfcmV0dXJuOiBcIm51bWJlclwiLFxuICAgICAgX3NxbDogYHN0cmljdF93b3JkX3NpbWlsYXJpdHkoPywgJHtjb2x1bW5bXCJfc3FsXCJdfSlgLFxuICAgICAgX3BhcmFtczogW3F1ZXJ5LCAuLi5jb2x1bW5bXCJfcGFyYW1zXCJdXSxcbiAgICB9O1xuICB9XG5cbiAgLy8gUmF3IGZ1bmN0aW9ucyBmb3IgU0VMRUNUXG4gIHN0YXRpYyByYXdTdHJpbmcoc3FsOiBzdHJpbmcsIHBhcmFtczogS25leC5SYXdCaW5kaW5nW10gPSBbXSk6IFNxbEV4cHJlc3Npb248XCJzdHJpbmdcIj4ge1xuICAgIHJldHVybiB7IF90eXBlOiBcInNxbF9leHByZXNzaW9uXCIsIF9yZXR1cm46IFwic3RyaW5nXCIsIF9zcWw6IHNxbCwgX3BhcmFtczogcGFyYW1zIH07XG4gIH1cblxuICBzdGF0aWMgcmF3U3RyaW5nQXJyYXkoc3FsOiBzdHJpbmcsIHBhcmFtczogS25leC5SYXdCaW5kaW5nW10gPSBbXSk6IFNxbEV4cHJlc3Npb248XCJzdHJpbmdbXVwiPiB7XG4gICAgcmV0dXJuIHsgX3R5cGU6IFwic3FsX2V4cHJlc3Npb25cIiwgX3JldHVybjogXCJzdHJpbmdbXVwiLCBfc3FsOiBzcWwsIF9wYXJhbXM6IHBhcmFtcyB9O1xuICB9XG5cbiAgc3RhdGljIHJhd051bWJlcihzcWw6IHN0cmluZywgcGFyYW1zOiBLbmV4LlJhd0JpbmRpbmdbXSA9IFtdKTogU3FsRXhwcmVzc2lvbjxcIm51bWJlclwiPiB7XG4gICAgcmV0dXJuIHsgX3R5cGU6IFwic3FsX2V4cHJlc3Npb25cIiwgX3JldHVybjogXCJudW1iZXJcIiwgX3NxbDogc3FsLCBfcGFyYW1zOiBwYXJhbXMgfTtcbiAgfVxuXG4gIHN0YXRpYyByYXdCb29sZWFuKHNxbDogc3RyaW5nLCBwYXJhbXM6IEtuZXguUmF3QmluZGluZ1tdID0gW10pOiBTcWxFeHByZXNzaW9uPFwiYm9vbGVhblwiPiB7XG4gICAgcmV0dXJuIHsgX3R5cGU6IFwic3FsX2V4cHJlc3Npb25cIiwgX3JldHVybjogXCJib29sZWFuXCIsIF9zcWw6IHNxbCwgX3BhcmFtczogcGFyYW1zIH07XG4gIH1cblxuICBzdGF0aWMgcmF3RGF0ZShzcWw6IHN0cmluZywgcGFyYW1zOiBLbmV4LlJhd0JpbmRpbmdbXSA9IFtdKTogU3FsRXhwcmVzc2lvbjxcImRhdGVcIj4ge1xuICAgIHJldHVybiB7IF90eXBlOiBcInNxbF9leHByZXNzaW9uXCIsIF9yZXR1cm46IFwiZGF0ZVwiLCBfc3FsOiBzcWwsIF9wYXJhbXM6IHBhcmFtcyB9O1xuICB9XG5cbiAgLyoqXG4gICAqIEZUUyDqsoDsg4nslrQg7ZWY7J2065287J207YyFXG4gICAqXG4gICAqIEBleGFtcGxlXG4gICAqIC5zZWxlY3Qoe1xuICAgKiAgIHRpdGxlOiBQdXJpLmhpZ2hsaWdodChcInBvc3RzLnRpdGxlXCIsIHNlYXJjaCksXG4gICAqICAgY29udGVudDogUHVyaS5oaWdobGlnaHQoXCJwb3N0cy5jb250ZW50XCIsIHNlYXJjaCwge1xuICAgKiAgICAgc3RhcnRTZWw6IFwiPG1hcms+XCIsXG4gICAqICAgICBzdG9wU2VsOiBcIjwvbWFyaz5cIixcbiAgICogICAgIG1heEZyYWdtZW50czogMyxcbiAgICogICB9KSxcbiAgICogfSlcbiAgICovXG4gIHN0YXRpYyB0c0hpZ2hsaWdodChcbiAgICBjb2x1bW46IHN0cmluZyxcbiAgICBxdWVyeTogc3RyaW5nLFxuICAgIF9vcHRpb25zPzogVHNIaWdobGlnaHRPcHRpb25zLFxuICApOiBTcWxFeHByZXNzaW9uPFwic3RyaW5nXCI+IHtcbiAgICBjb25zdCB7IHBhcnNlciA9IFwid2Vic2VhcmNoX3RvX3RzcXVlcnlcIiwgY29uZmlnID0gXCJzaW1wbGVcIiwgLi4ub3B0aW9ucyB9ID0gX29wdGlvbnMgPz8ge307XG5cbiAgICBjb25zdCBobE9wdGlvblBhcnRzID0gT2JqZWN0LmVudHJpZXMob3B0aW9ucykubWFwKChba2V5LCB2YWx1ZV0pID0+IHtcbiAgICAgIHJldHVybiBgJHtpbmZsZWN0aW9uLmNhbWVsaXplKGtleSl9PSR7dmFsdWV9YDtcbiAgICB9KTtcblxuICAgIGNvbnN0IGhsT3B0aW9ucyA9IGhsT3B0aW9uUGFydHMubGVuZ3RoID4gMCA/IGAsICcke2hsT3B0aW9uUGFydHMuam9pbihcIiwgXCIpfSdgIDogXCJcIjtcblxuICAgIHJldHVybiB7XG4gICAgICBfdHlwZTogXCJzcWxfZXhwcmVzc2lvblwiLFxuICAgICAgX3JldHVybjogXCJzdHJpbmdcIixcbiAgICAgIF9zcWw6IGB0c19oZWFkbGluZSg/LCA/PywgJHtwYXJzZXJ9KD8sID8pJHtobE9wdGlvbnN9KWAsXG4gICAgICBfcGFyYW1zOiBbY29uZmlnLCBjb2x1bW4sIGNvbmZpZywgcXVlcnldLFxuICAgIH07XG4gIH1cblxuICAvLyB0c19yYW5rXG4gIHN0YXRpYyB0c1JhbmsoXG4gICAgY29sdW1uOiBzdHJpbmcgfCBTcWxFeHByZXNzaW9uPFwidHN2ZWN0b3JcIj4sXG4gICAgcXVlcnk6IHN0cmluZyxcbiAgICBvcHRpb25zPzogVHNSYW5rT3B0aW9ucyxcbiAgKTogU3FsRXhwcmVzc2lvbjxcIm51bWJlclwiPiB7XG4gICAgcmV0dXJuIFB1cmlbXCJfdHNSYW5rXCJdKFwidHNfcmFua1wiLCBjb2x1bW4sIHF1ZXJ5LCBvcHRpb25zKTtcbiAgfVxuXG4gIC8vIHRzX3JhbmtfY2RcbiAgc3RhdGljIHRzUmFua0NkKFxuICAgIGNvbHVtbjogc3RyaW5nIHwgU3FsRXhwcmVzc2lvbjxcInRzdmVjdG9yXCI+LFxuICAgIHF1ZXJ5OiBzdHJpbmcsXG4gICAgb3B0aW9ucz86IFRzUmFua09wdGlvbnMsXG4gICk6IFNxbEV4cHJlc3Npb248XCJudW1iZXJcIj4ge1xuICAgIHJldHVybiBQdXJpW1wiX3RzUmFua1wiXShcInRzX3JhbmtfY2RcIiwgY29sdW1uLCBxdWVyeSwgb3B0aW9ucyk7XG4gIH1cblxuICBzdGF0aWMgdG9Uc1ZlY3Rvcihjb2x1bW46IHN0cmluZywgY29uZmlnOiBzdHJpbmcgPSBcInNpbXBsZVwiKTogU3FsRXhwcmVzc2lvbjxcInRzdmVjdG9yXCI+IHtcbiAgICByZXR1cm4ge1xuICAgICAgX3R5cGU6IFwic3FsX2V4cHJlc3Npb25cIixcbiAgICAgIF9yZXR1cm46IFwidHN2ZWN0b3JcIixcbiAgICAgIF9zcWw6IGB0b190c3ZlY3Rvcig/LCA/PylgLFxuICAgICAgX3BhcmFtczogW2NvbmZpZywgY29sdW1uXSxcbiAgICB9O1xuICB9XG5cbiAgc3RhdGljIF90c1JhbmsoXG4gICAgdHlwZTogXCJ0c19yYW5rXCIgfCBcInRzX3JhbmtfY2RcIixcbiAgICBjb2x1bW46IHN0cmluZyB8IFNxbEV4cHJlc3Npb248XCJ0c3ZlY3RvclwiPixcbiAgICBxdWVyeTogc3RyaW5nLFxuICAgIG9wdGlvbnM/OiBUc1JhbmtPcHRpb25zLFxuICApOiBTcWxFeHByZXNzaW9uPFwibnVtYmVyXCI+IHtcbiAgICBjb25zdCB7XG4gICAgICBwYXJzZXIgPSBcIndlYnNlYXJjaF90b190c3F1ZXJ5XCIsXG4gICAgICBjb25maWcgPSBcInNpbXBsZVwiLFxuICAgICAgbm9ybWFsaXphdGlvbixcbiAgICAgIHdlaWdodHMsXG4gICAgfSA9IG9wdGlvbnMgPz8ge307XG5cbiAgICBjb25zdCBwYXJhbXMgPSBbXTtcbiAgICBsZXQgc3FsVGVtcGxhdGUgPSBgJHt0eXBlfShgO1xuXG4gICAgaWYgKHdlaWdodHMpIHtcbiAgICAgIHNxbFRlbXBsYXRlICs9IGBBUlJBWVske3dlaWdodHMubWFwKCgpID0+IFwiP1wiKS5qb2luKFwiLCBcIil9XTo6ZmxvYXQ0W10sIGA7XG4gICAgICBwYXJhbXMucHVzaCguLi53ZWlnaHRzKTtcbiAgICB9XG5cbiAgICBpZiAoaXNTdHJpbmdWYWx1ZShjb2x1bW4pKSB7XG4gICAgICBzcWxUZW1wbGF0ZSArPSBgPz8sICR7cGFyc2VyfSg/LCA/KWA7XG4gICAgICBwYXJhbXMucHVzaChjb2x1bW4sIGNvbmZpZywgcXVlcnkpO1xuICAgIH0gZWxzZSB7XG4gICAgICBzcWxUZW1wbGF0ZSArPSBgJHtjb2x1bW5bXCJfc3FsXCJdfSwgJHtwYXJzZXJ9KD8sID8pYDtcbiAgICAgIHBhcmFtcy5wdXNoKC4uLmNvbHVtbltcIl9wYXJhbXNcIl0sIGNvbmZpZywgcXVlcnkpO1xuICAgIH1cblxuICAgIGlmIChub3JtYWxpemF0aW9uKSB7XG4gICAgICBzcWxUZW1wbGF0ZSArPSBcIiwgP1wiO1xuICAgICAgcGFyYW1zLnB1c2gobm9ybWFsaXphdGlvbik7XG4gICAgfVxuXG4gICAgc3FsVGVtcGxhdGUgKz0gXCIpXCI7XG5cbiAgICByZXR1cm4geyBfdHlwZTogXCJzcWxfZXhwcmVzc2lvblwiLCBfcmV0dXJuOiBcIm51bWJlclwiLCBfc3FsOiBzcWxUZW1wbGF0ZSwgX3BhcmFtczogcGFyYW1zIH07XG4gIH1cblxuICAvKipcbiAgICogUEdyb29uZ2EgRnVsbFRleHQg7J24642x7IqkIOqygOyDiSDsoJDsiJhcbiAgICpcbiAgICogQGV4YW1wbGVcbiAgICogLnNlbGVjdCh7XG4gICAqICAgc2NvcmU6IFB1cmkuc2NvcmUoKSxcbiAgICogfSlcbiAgICovXG4gIHN0YXRpYyBzY29yZSgpOiBTcWxFeHByZXNzaW9uPFwibnVtYmVyXCI+IHtcbiAgICByZXR1cm4gUHVyaS5yYXdOdW1iZXIoXCJwZ3Jvb25nYV9zY29yZSh0YWJsZW9pZCwgY3RpZClcIik7XG4gIH1cblxuICAvKipcbiAgICogUEdyb29uZ2EgRnVsbFRleHQg7J24642x7IqkIOqygOyDiSDtlZjsnbTrnbzsnbTtjIVcbiAgICpcbiAgICogQGV4YW1wbGVcbiAgICogLnNlbGVjdCh7XG4gICAqICAgdGl0bGU6IFB1cmkuaGlnaGxpZ2h0KFwicG9zdHMudGl0bGVcIiwgc2VhcmNoKSxcbiAgICogfSlcbiAgICovXG4gIHN0YXRpYyBoaWdobGlnaHQoY29sdW1uOiBzdHJpbmcsIHF1ZXJ5OiBzdHJpbmcgfCBzdHJpbmdbXSk6IFNxbEV4cHJlc3Npb248XCJzdHJpbmdcIj47XG4gIHN0YXRpYyBoaWdobGlnaHQoY29sdW1uczogc3RyaW5nW10sIHF1ZXJ5OiBzdHJpbmcgfCBzdHJpbmdbXSk6IFNxbEV4cHJlc3Npb248XCJzdHJpbmdbXVwiPjtcblxuICBzdGF0aWMgaGlnaGxpZ2h0KFxuICAgIGNvbHVtbk9yQ29sdW1uczogc3RyaW5nIHwgc3RyaW5nW10sXG4gICAgcXVlcnk6IHN0cmluZyB8IHN0cmluZ1tdLFxuICApOiBTcWxFeHByZXNzaW9uPFwic3RyaW5nXCI+IHwgU3FsRXhwcmVzc2lvbjxcInN0cmluZ1tdXCI+IHtcbiAgICBjb25zdCBxdWVyeUFyciA9IEFycmF5LmlzQXJyYXkocXVlcnkpID8gcXVlcnkgOiBbcXVlcnldO1xuICAgIGNvbnN0IHF1ZXJ5Q2xhdXNlID0gYEFSUkFZWyR7cXVlcnlBcnIubWFwKCgpID0+IFwiP1wiKS5qb2luKFwiLCBcIil9XWA7XG5cbiAgICAvLyDri6jsnbwg7Lus65+87J24IOqyveyasFxuICAgIGlmIChpc1N0cmluZ1ZhbHVlKGNvbHVtbk9yQ29sdW1ucykpIHtcbiAgICAgIHJldHVybiBQdXJpLnJhd1N0cmluZyhgcGdyb29uZ2FfaGlnaGxpZ2h0X2h0bWwoPz8sICR7cXVlcnlDbGF1c2V9KWAsIFtcbiAgICAgICAgY29sdW1uT3JDb2x1bW5zLFxuICAgICAgICAuLi5xdWVyeUFycixcbiAgICAgIF0pO1xuICAgIH1cblxuICAgIC8vIOy7rOufvCDrsLDsl7Tsnbgg6rK97JqwXG4gICAgcmV0dXJuIFB1cmkucmF3U3RyaW5nQXJyYXkoXG4gICAgICBgcGdyb29uZ2FfaGlnaGxpZ2h0X2h0bWwoQVJSQVlbJHtjb2x1bW5PckNvbHVtbnMubWFwKCgpID0+IFwiPz9cIikuam9pbihcIiwgXCIpfV0sICR7cXVlcnlDbGF1c2V9KWAsXG4gICAgICBbLi4uY29sdW1uT3JDb2x1bW5zLCAuLi5xdWVyeUFycl0sXG4gICAgKTtcbiAgfVxuXG4gIC8vIFNFTEVDVCAob3ZlcndyaXRlKVxuICBzZWxlY3Q8VFNlbGVjdCBleHRlbmRzIFNlbGVjdE9iamVjdDxUVGFibGVzPj4oXG4gICAgc2VsZWN0T2JqOiBUU2VsZWN0LFxuICApOiBQdXJpPFRTY2hlbWEsIFRUYWJsZXMsIFBhcnNlU2VsZWN0T2JqZWN0PFRUYWJsZXMsIFRTZWxlY3Q+PiB7XG4gICAgLy8g7KSR7LKpIOqwneyytOulvCBmbGF07ZWY6rKMIOuzgO2ZmFxuICAgIGNvbnN0IGZsYXRTZWxlY3QgPSB0aGlzLmZsYXR0ZW5TZWxlY3Qoc2VsZWN0T2JqKTtcblxuICAgIGNvbnN0IHNlbGVjdENsYXVzZXM6IChzdHJpbmcgfCBLbmV4LlJhdylbXSA9IFtdO1xuXG4gICAgZm9yIChjb25zdCBbYWxpYXMsIGNvbHVtbk9yRnVuY3Rpb25dIG9mIE9iamVjdC5lbnRyaWVzKGZsYXRTZWxlY3QpKSB7XG4gICAgICBpZiAoaXNTcWxFeHByZXNzaW9uKGNvbHVtbk9yRnVuY3Rpb24pKSB7XG4gICAgICAgIC8vIFNRTCDtlajsiJjsnbgg6rK97JqwXG4gICAgICAgIHNlbGVjdENsYXVzZXMucHVzaChcbiAgICAgICAgICB0aGlzLmtuZXgucmF3KGAke2NvbHVtbk9yRnVuY3Rpb25bXCJfc3FsXCJdfSBBUyBcIiR7YWxpYXN9XCJgLCBjb2x1bW5PckZ1bmN0aW9uW1wiX3BhcmFtc1wiXSksXG4gICAgICAgICk7XG4gICAgICB9IGVsc2Uge1xuICAgICAgICAvLyDsnbzrsJgg7Lus65+87J24IOqyveyasFxuICAgICAgICAvLyBTQUZFVFk6IOy/vOumrCDruYzrjZTsnZgg7KCc64Sk66atIOqzhOyVveqzvCDshKDtlokg6rKA7Kad7J20IOydtCDtg4DsnoXsnYQg67O07J6l7ZWp64uI64ukLlxuICAgICAgICBjb25zdCBjb2x1bW5QYXRoID0gY29sdW1uT3JGdW5jdGlvbiBhcyBzdHJpbmc7XG4gICAgICAgIGlmIChhbGlhcyA9PT0gY29sdW1uUGF0aCkge1xuICAgICAgICAgIC8vIGFsaWFz7JmAIOy7rOufvOuqheydtCDqsJnsnLzrqbQgYWxpYXMg7IOd6561XG4gICAgICAgICAgc2VsZWN0Q2xhdXNlcy5wdXNoKGNvbHVtblBhdGgpO1xuICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgIC8vIGFsaWFzIOyngOyglVxuICAgICAgICAgIHNlbGVjdENsYXVzZXMucHVzaChgJHtjb2x1bW5QYXRofSBBUyAke2FsaWFzfWApO1xuICAgICAgICB9XG4gICAgICB9XG4gICAgfVxuXG4gICAgdGhpcy5rbmV4UXVlcnkuc2VsZWN0KHNlbGVjdENsYXVzZXMpO1xuICAgIC8vIFNBRkVUWTog7L+866asIOu5jOuNlOydmCDsoJzrhKTrpq0g6rOE7JW96rO8IOyEoO2WiSDqsoDspp3snbQg7J20IO2DgOyeheydhCDrs7TsnqXtlanri4jri6QuXG4gICAgcmV0dXJuIHRoaXMgYXMgYW55O1xuICB9XG5cbiAgLyoqXG4gICAqIOykkeyyqSDqsJ3ssrTrpbwgZmxhdCDqsJ3ssrTroZwg67OA7ZmYXG4gICAqIOyYiDogeyBwYXJlbnQ6IHsgaWQ6IFwicGFyZW50LmlkXCIsIG5hbWU6IFwicGFyZW50Lm5hbWVcIiB9IH1cbiAgICogICDihpIgeyBwYXJlbnRfX2lkOiBcInBhcmVudC5pZFwiLCBwYXJlbnRfX25hbWU6IFwicGFyZW50Lm5hbWVcIiB9XG4gICAqL1xuICBwcml2YXRlICpmbGF0dGVuU2VsZWN0RW50cmllcyhcbiAgICBzZWxlY3RPYmo6IFNlbGVjdE9iamVjdDxUVGFibGVzPixcbiAgICBwcmVmaXggPSBcIlwiLFxuICApOiBHZW5lcmF0b3I8W3N0cmluZywgU2VsZWN0VmFsdWU8VFRhYmxlcz5dLCB2b2lkPiB7XG4gICAgZm9yIChjb25zdCBba2V5LCB2YWx1ZV0gb2YgT2JqZWN0LmVudHJpZXMoc2VsZWN0T2JqKSkge1xuICAgICAgY29uc3QgZnVsbEtleSA9IHByZWZpeCA/IGAke3ByZWZpeH1fXyR7a2V5fWAgOiBrZXk7XG5cbiAgICAgIGlmIChpc05lc3RlZFNlbGVjdE9iamVjdCh2YWx1ZSkpIHtcbiAgICAgICAgeWllbGQqIHRoaXMuZmxhdHRlblNlbGVjdEVudHJpZXModmFsdWUsIGZ1bGxLZXkpO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgeWllbGQgW2Z1bGxLZXksIHZhbHVlXTtcbiAgICAgIH1cbiAgICB9XG4gIH1cblxuICBwcml2YXRlIGZsYXR0ZW5TZWxlY3Qoc2VsZWN0T2JqOiBTZWxlY3RPYmplY3Q8VFRhYmxlcz4sIHByZWZpeCA9IFwiXCIpIHtcbiAgICByZXR1cm4gT2JqZWN0LmZyb21FbnRyaWVzKHRoaXMuZmxhdHRlblNlbGVjdEVudHJpZXMoc2VsZWN0T2JqLCBwcmVmaXgpKTtcbiAgfVxuXG4gIC8vIFNFTEVDVCAoc2VsZWN064qUIG92ZXJ3cml0ZSwgYXBwZW5kU2VsZWN064qUIGFwcGVuZClcbiAgYXBwZW5kU2VsZWN0PFRTZWxlY3QgZXh0ZW5kcyBTZWxlY3RPYmplY3Q8VFRhYmxlcz4+KFxuICAgIHNlbGVjdE9iajogVFNlbGVjdCxcbiAgKTogUHVyaTxUU2NoZW1hLCBUVGFibGVzLCBUUmVzdWx0ICYgUGFyc2VTZWxlY3RPYmplY3Q8VFRhYmxlcywgVFNlbGVjdD4+IHtcbiAgICAvLyDspJHssqkg6rCd7LK066W8IGZsYXTtlZjqsowg67OA7ZmYXG4gICAgY29uc3QgZmxhdFNlbGVjdCA9IHRoaXMuZmxhdHRlblNlbGVjdChzZWxlY3RPYmopO1xuXG4gICAgY29uc3Qgc2VsZWN0Q2xhdXNlczogKHN0cmluZyB8IEtuZXguUmF3KVtdID0gW107XG5cbiAgICBmb3IgKGNvbnN0IFthbGlhcywgY29sdW1uT3JGdW5jdGlvbl0gb2YgT2JqZWN0LmVudHJpZXMoZmxhdFNlbGVjdCkpIHtcbiAgICAgIGlmIChpc1NxbEV4cHJlc3Npb24oY29sdW1uT3JGdW5jdGlvbikpIHtcbiAgICAgICAgc2VsZWN0Q2xhdXNlcy5wdXNoKFxuICAgICAgICAgIHRoaXMua25leC5yYXcoYCR7Y29sdW1uT3JGdW5jdGlvbltcIl9zcWxcIl19IEFTICR7YWxpYXN9YCwgY29sdW1uT3JGdW5jdGlvbltcIl9wYXJhbXNcIl0pLFxuICAgICAgICApO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgLy8gU0FGRVRZOiDsv7zrpqwg67mM642U7J2YIOygnOuEpOumrSDqs4Tslb3qs7wg7ISg7ZaJIOqygOymneydtCDsnbQg7YOA7J6F7J2EIOuztOyepe2VqeuLiOuLpC5cbiAgICAgICAgY29uc3QgY29sdW1uUGF0aCA9IGNvbHVtbk9yRnVuY3Rpb24gYXMgc3RyaW5nO1xuICAgICAgICBpZiAoYWxpYXMgPT09IGNvbHVtblBhdGgpIHtcbiAgICAgICAgICBzZWxlY3RDbGF1c2VzLnB1c2goY29sdW1uUGF0aCk7XG4gICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgc2VsZWN0Q2xhdXNlcy5wdXNoKHRoaXMua25leC5yZWYoY29sdW1uUGF0aCkuYXMoYWxpYXMpKTtcbiAgICAgICAgfVxuICAgICAgfVxuICAgIH1cblxuICAgIHRoaXMua25leFF1ZXJ5LnNlbGVjdChzZWxlY3RDbGF1c2VzKTtcbiAgICAvLyBTQUZFVFk6IOy/vOumrCDruYzrjZTsnZgg7KCc64Sk66atIOqzhOyVveqzvCDshKDtlokg6rKA7Kad7J20IOydtCDtg4DsnoXsnYQg67O07J6l7ZWp64uI64ukLlxuICAgIHJldHVybiB0aGlzIGFzIGFueTtcbiAgfVxuXG4gIC8vIFNFTEVDVCAqXG4gIHNlbGVjdEFsbCgpOiBQdXJpPFRTY2hlbWEsIFRUYWJsZXMsIFNlbGVjdEFsbFJlc3VsdDxUVGFibGVzPj4ge1xuICAgIHRoaXMua25leFF1ZXJ5LnNlbGVjdChcIipcIik7XG4gICAgLy8gU0FGRVRZOiDsv7zrpqwg67mM642U7J2YIOygnOuEpOumrSDqs4Tslb3qs7wg7ISg7ZaJIOqygOymneydtCDsnbQg7YOA7J6F7J2EIOuztOyepe2VqeuLiOuLpC5cbiAgICByZXR1cm4gdGhpcyBhcyBhbnk7XG4gIH1cblxuICAvLyBESVNUSU5DVFxuICBkaXN0aW5jdDxUQ29sdW1ucyBleHRlbmRzIEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcz4+KC4uLmNvbHVtbnM6IFRDb2x1bW5zW10pOiB0aGlzO1xuICBkaXN0aW5jdCguLi5jb2x1bW5zOiBzdHJpbmdbXSk6IHRoaXMge1xuICAgIHRoaXMua25leFF1ZXJ5LmRpc3RpbmN0KC4uLmNvbHVtbnMpO1xuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgLy8gQ0xFQVJcbiAgY2xlYXIoc3RhdGVtZW50OiBDbGVhclN0YXRlbWVudHMpOiB0aGlzIHtcbiAgICB0aGlzLmtuZXhRdWVyeS5jbGVhcihzdGF0ZW1lbnQpO1xuICAgIGlmIChzdGF0ZW1lbnQgPT09IFwiam9pblwiKSB7XG4gICAgICB0aGlzLmNsZWFySm9pblJlZ2lzdHJhdGlvbnMoKTtcbiAgICB9XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICAvLyBrbmV47JeQIOyXhuyWtOyEnCDsp4HsoJEg6rWs7ZiE7ZWoXG4gIGNsZWFySm9pbihhbGlhczogc3RyaW5nKTogdGhpcyB7XG4gICAgbGV0IHJlbW92ZWQgPSBmYWxzZTtcbiAgICAvLyBTQUZFVFk6IOy/vOumrCDruYzrjZTsnZgg7KCc64Sk66atIOqzhOyVveqzvCDshKDtlokg6rKA7Kad7J20IOydtCDtg4DsnoXsnYQg67O07J6l7ZWp64uI64ukLlxuICAgICh0aGlzLmtuZXhRdWVyeSBhcyBhbnkpW1wiX3N0YXRlbWVudHNcIl0gPSAodGhpcy5rbmV4UXVlcnkgYXMgYW55KVtcIl9zdGF0ZW1lbnRzXCJdLmZpbHRlcihcbiAgICAgIChzOiBhbnkpID0+IHtcbiAgICAgICAgaWYgKFwiam9pblR5cGVcIiBpbiBzKSB7XG4gICAgICAgICAgY29uc3Qgc2hvdWxkUmVtb3ZlID0gdGhpcy5nZXRLbmV4Sm9pbkFsaWFzKHMudGFibGUpID09PSBhbGlhcztcbiAgICAgICAgICByZW1vdmVkIHx8PSBzaG91bGRSZW1vdmU7XG4gICAgICAgICAgcmV0dXJuICFzaG91bGRSZW1vdmU7XG4gICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgcmV0dXJuIHRydWU7XG4gICAgICAgIH1cbiAgICAgIH0sXG4gICAgKTtcbiAgICBpZiAocmVtb3ZlZCAmJiB0aGlzLmNvcnJlbGF0aW9uUmVnaXN0cnkuZ2V0KGFsaWFzKT8ua2luZCA9PT0gXCJqb2luXCIpIHtcbiAgICAgIHRoaXMuY29ycmVsYXRpb25SZWdpc3RyeS5kZWxldGUoYWxpYXMpO1xuICAgIH1cbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIC8vIEpPSU46IOyEnOu4jOy/vOumrCArIEFsaWFzXG4gIGpvaW48VEpvaW5BbGlhcyBleHRlbmRzIHN0cmluZywgVFN1YlJlc3VsdD4oXG4gICAgdGFibGVTcGVjOiB7IFtLIGluIFRKb2luQWxpYXNdOiBQdXJpPFRTY2hlbWEsIGFueSwgVFN1YlJlc3VsdD4gfSxcbiAgICBsZWZ0OiBBdmFpbGFibGVDb2x1bW5zPFRUYWJsZXM+LFxuICAgIHJpZ2h0OiBgJHtUSm9pbkFsaWFzfS4ke0NvbHVtbktleXM8VFN1YlJlc3VsdD59YCxcbiAgKTogUHVyaTxcbiAgICBUU2NoZW1hLFxuICAgIFRUYWJsZXMgJiBSZWNvcmQ8VEpvaW5BbGlhcywgVFN1YlJlc3VsdD4sIC8vIOyEnOu4jOy/vOumrOydmCBUUmVzdWx0XG4gICAgVFJlc3VsdFxuICA+O1xuICAvLyBKT0lOOiDthYzsnbTruJQgKyBBbGlhc1xuICBqb2luPFRKb2luVGFibGUgZXh0ZW5kcyBrZXlvZiBUU2NoZW1hLCBUSm9pbkFsaWFzIGV4dGVuZHMgc3RyaW5nPihcbiAgICB0YWJsZVNwZWM6IHsgW0sgaW4gVEpvaW5BbGlhc106IFRKb2luVGFibGUgfSxcbiAgICBsZWZ0OiBBdmFpbGFibGVDb2x1bW5zPFRUYWJsZXM+LFxuICAgIHJpZ2h0OiBgJHtUSm9pbkFsaWFzfS4ke0NvbHVtbktleXM8VFNjaGVtYVtUSm9pblRhYmxlXT59YCxcbiAgKTogUHVyaTxcbiAgICBUU2NoZW1hLFxuICAgIFRUYWJsZXMgJiBSZWNvcmQ8VEpvaW5BbGlhcywgVFNjaGVtYVtUSm9pblRhYmxlXT4sIC8vIFRUYWJsZXMg7ZmV7J6lIVxuICAgIFRSZXN1bHRcbiAgPjtcbiAgLy8gSk9JTjog7YWM7J2067iU66qFXG4gIGpvaW48VEpvaW5UYWJsZSBleHRlbmRzIGtleW9mIFRTY2hlbWE+KFxuICAgIHRhYmxlTmFtZTogVEpvaW5UYWJsZSxcbiAgICBsZWZ0OiBBdmFpbGFibGVDb2x1bW5zPFRUYWJsZXM+LFxuICAgIHJpZ2h0OiBgJHtUSm9pblRhYmxlICYgc3RyaW5nfS4ke0NvbHVtbktleXM8VFNjaGVtYVtUSm9pblRhYmxlXT59YCxcbiAgKTogUHVyaTxcbiAgICBUU2NoZW1hLFxuICAgIFRUYWJsZXMgJiBSZWNvcmQ8VEpvaW5UYWJsZSwgVFNjaGVtYVtUSm9pblRhYmxlXT4sIC8vIO2FjOydtOu4lOuqheydtCDtgqRcbiAgICBUUmVzdWx0XG4gID47XG4gIC8vIEpPSU46IOyEnOu4jOy/vOumrCArIEFsaWFzICsg7L2c67CxXG4gIGpvaW48VEpvaW5BbGlhcyBleHRlbmRzIHN0cmluZywgVFN1YlJlc3VsdD4oXG4gICAgdGFibGVTcGVjOiB7IFtLIGluIFRKb2luQWxpYXNdOiBQdXJpPFRTY2hlbWEsIGFueSwgVFN1YlJlc3VsdD4gfSxcbiAgICBjYWxsYmFjazogKGo6IEpvaW5DbGF1c2VHcm91cDxUVGFibGVzLCBSZWNvcmQ8VEpvaW5BbGlhcywgVFN1YlJlc3VsdD4+KSA9PiB2b2lkLFxuICApOiBQdXJpPFRTY2hlbWEsIFRUYWJsZXMgJiBSZWNvcmQ8VEpvaW5BbGlhcywgVFN1YlJlc3VsdD4sIFRSZXN1bHQ+O1xuICAvLyBKT0lOOiDthYzsnbTruJQgKyBBbGlhcyArIOy9nOuwsVxuICBqb2luPFRKb2luVGFibGUgZXh0ZW5kcyBrZXlvZiBUU2NoZW1hLCBUSm9pbkFsaWFzIGV4dGVuZHMgc3RyaW5nPihcbiAgICB0YWJsZVNwZWM6IHsgW0sgaW4gVEpvaW5BbGlhc106IFRKb2luVGFibGUgfSxcbiAgICBjYWxsYmFjazogKGo6IEpvaW5DbGF1c2VHcm91cDxUVGFibGVzLCBSZWNvcmQ8VEpvaW5BbGlhcywgVFNjaGVtYVtUSm9pblRhYmxlXT4+KSA9PiB2b2lkLFxuICApOiBQdXJpPFRTY2hlbWEsIFRUYWJsZXMgJiBSZWNvcmQ8VEpvaW5BbGlhcywgVFNjaGVtYVtUSm9pblRhYmxlXT4sIFRSZXN1bHQ+O1xuICAvLyBKT0lOOiDthYzsnbTruJTrqoUgKyDsvZzrsLFcbiAgam9pbjxUSm9pblRhYmxlIGV4dGVuZHMga2V5b2YgVFNjaGVtYT4oXG4gICAgdGFibGVOYW1lOiBUSm9pblRhYmxlLFxuICAgIGNhbGxiYWNrOiAoajogSm9pbkNsYXVzZUdyb3VwPFRUYWJsZXMsIFJlY29yZDxUSm9pblRhYmxlLCBUU2NoZW1hW1RKb2luVGFibGVdPj4pID0+IHZvaWQsXG4gICk6IFB1cmk8VFNjaGVtYSwgVFRhYmxlcyAmIFJlY29yZDxUSm9pblRhYmxlLCBUU2NoZW1hW1RKb2luVGFibGVdPiwgVFJlc3VsdD47XG4gIC8vIEpPSU4g7Iuk7KCcIOq1rO2YhFxuICBqb2luKHRhYmxlTmFtZU9yU3BlYzogYW55LCAuLi5hcmdzOiBhbnlbXSk6IGFueSB7XG4gICAgcmV0dXJuIHRoaXNbXCJfX2NvbW1vbkpvaW5cIl0oXCJqb2luXCIsIHRhYmxlTmFtZU9yU3BlYywgLi4uYXJncyk7XG4gIH1cblxuICAvLyBFTlNVUkUgSk9JTjog7YWM7J2067iUICsgQWxpYXNcbiAgZW5zdXJlSm9pbjxUSm9pblRhYmxlIGV4dGVuZHMga2V5b2YgVFNjaGVtYSwgVEpvaW5BbGlhcyBleHRlbmRzIHN0cmluZz4oXG4gICAgdGFibGVTcGVjOiB7IFtLIGluIFRKb2luQWxpYXNdOiBUSm9pblRhYmxlIH0sXG4gICAgbGVmdDogQXZhaWxhYmxlQ29sdW1uczxUVGFibGVzPixcbiAgICByaWdodDogYCR7VEpvaW5BbGlhc30uJHtDb2x1bW5LZXlzPFRTY2hlbWFbVEpvaW5UYWJsZV0+fWAsXG4gICk6IFB1cmk8VFNjaGVtYSwgVFRhYmxlcyAmIFJlY29yZDxUSm9pbkFsaWFzLCBUU2NoZW1hW1RKb2luVGFibGVdPiwgVFJlc3VsdD47XG4gIC8vIEVOU1VSRSBKT0lOOiDthYzsnbTruJTrqoVcbiAgZW5zdXJlSm9pbjxUSm9pblRhYmxlIGV4dGVuZHMga2V5b2YgVFNjaGVtYT4oXG4gICAgdGFibGVOYW1lOiBUSm9pblRhYmxlLFxuICAgIGxlZnQ6IEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcz4sXG4gICAgcmlnaHQ6IGAke1RKb2luVGFibGUgJiBzdHJpbmd9LiR7Q29sdW1uS2V5czxUU2NoZW1hW1RKb2luVGFibGVdPn1gLFxuICApOiBQdXJpPFRTY2hlbWEsIFRUYWJsZXMgJiBSZWNvcmQ8VEpvaW5UYWJsZSwgVFNjaGVtYVtUSm9pblRhYmxlXT4sIFRSZXN1bHQ+O1xuICBlbnN1cmVKb2luKHRhYmxlTmFtZU9yU3BlYzogYW55LCBsZWZ0OiBzdHJpbmcsIHJpZ2h0OiBzdHJpbmcpOiBhbnkge1xuICAgIHJldHVybiB0aGlzW1wiX19lbnN1cmVKb2luXCJdKFwiam9pblwiLCB0YWJsZU5hbWVPclNwZWMsIGxlZnQsIHJpZ2h0KTtcbiAgfVxuXG4gIC8vIExFRlQgSk9JTjog7ISc67iM7L+866asICsgQWxpYXNcbiAgbGVmdEpvaW48VEpvaW5BbGlhcyBleHRlbmRzIHN0cmluZywgVFN1YlJlc3VsdD4oXG4gICAgdGFibGVTcGVjOiB7IFtLIGluIFRKb2luQWxpYXNdOiBQdXJpPFRTY2hlbWEsIGFueSwgVFN1YlJlc3VsdD4gfSxcbiAgICBsZWZ0OiBBdmFpbGFibGVDb2x1bW5zPFRUYWJsZXM+LFxuICAgIHJpZ2h0OiBgJHtUSm9pbkFsaWFzfS4ke0NvbHVtbktleXM8VFN1YlJlc3VsdD59YCxcbiAgKTogUHVyaTxUU2NoZW1hLCBUVGFibGVzICYgUmVjb3JkPFRKb2luQWxpYXMsIFRTdWJSZXN1bHQgJiBMZWZ0Sm9pbmVkTWFya2VyPiwgVFJlc3VsdD47IC8vIOyEnOu4jOy/vOumrOydmCBUUmVzdWx0XG4gIC8vIExFRlQgSk9JTjog7YWM7J2067iUICsgQWxpYXNcbiAgLy8gRksgbnVsbGFibGUg7Jes67aA7JeQIOuUsOudvCDsnpDrj5nsnLzroZwgTGVmdEpvaW5lZE1hcmtlciDqsrDsoJVcbiAgbGVmdEpvaW48XG4gICAgVEpvaW5UYWJsZSBleHRlbmRzIGtleW9mIFRTY2hlbWEsXG4gICAgVEpvaW5BbGlhcyBleHRlbmRzIHN0cmluZyxcbiAgICBUTGVmdCBleHRlbmRzIEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcz4sXG4gID4oXG4gICAgdGFibGVTcGVjOiB7IFtLIGluIFRKb2luQWxpYXNdOiBUSm9pblRhYmxlIH0sXG4gICAgbGVmdDogVExlZnQsXG4gICAgcmlnaHQ6IGAke1RKb2luQWxpYXN9LiR7Q29sdW1uS2V5czxUU2NoZW1hW1RKb2luVGFibGVdPn1gLFxuICApOiBQdXJpPFxuICAgIFRTY2hlbWEsXG4gICAgVFRhYmxlcyAmIFJlY29yZDxUSm9pbkFsaWFzLCBUU2NoZW1hW1RKb2luVGFibGVdICYgTGVmdEpvaW5NYXJrZXJGb3I8VFRhYmxlcywgVExlZnQ+PixcbiAgICBUUmVzdWx0XG4gID47XG4gIC8vIExFRlQgSk9JTjog7YWM7J2067iU66qFXG4gIGxlZnRKb2luPFRKb2luVGFibGUgZXh0ZW5kcyBrZXlvZiBUU2NoZW1hLCBUTGVmdCBleHRlbmRzIEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcz4+KFxuICAgIHRhYmxlTmFtZTogVEpvaW5UYWJsZSxcbiAgICBsZWZ0OiBUTGVmdCxcbiAgICByaWdodDogYCR7VEpvaW5UYWJsZSAmIHN0cmluZ30uJHtDb2x1bW5LZXlzPFRTY2hlbWFbVEpvaW5UYWJsZV0+fWAsXG4gICk6IFB1cmk8XG4gICAgVFNjaGVtYSxcbiAgICBUVGFibGVzICYgUmVjb3JkPFRKb2luVGFibGUsIFRTY2hlbWFbVEpvaW5UYWJsZV0gJiBMZWZ0Sm9pbk1hcmtlckZvcjxUVGFibGVzLCBUTGVmdD4+LFxuICAgIFRSZXN1bHRcbiAgPjtcbiAgLy8gTEVGVCBKT0lOOiDshJzruIzsv7zrpqwgKyBBbGlhcyArIOy9nOuwsVxuICBsZWZ0Sm9pbjxUSm9pbkFsaWFzIGV4dGVuZHMgc3RyaW5nLCBUU3ViUmVzdWx0PihcbiAgICB0YWJsZVNwZWM6IHsgW0sgaW4gVEpvaW5BbGlhc106IFB1cmk8VFNjaGVtYSwgYW55LCBUU3ViUmVzdWx0PiB9LFxuICAgIGNhbGxiYWNrOiAoajogSm9pbkNsYXVzZUdyb3VwPFRUYWJsZXMsIFJlY29yZDxUSm9pbkFsaWFzLCBUU3ViUmVzdWx0Pj4pID0+IHZvaWQsXG4gICk6IFB1cmk8VFNjaGVtYSwgVFRhYmxlcyAmIFJlY29yZDxUSm9pbkFsaWFzLCBUU3ViUmVzdWx0ICYgTGVmdEpvaW5lZE1hcmtlcj4sIFRSZXN1bHQ+O1xuICAvLyBMRUZUIEpPSU46IO2FjOydtOu4lCArIEFsaWFzICsg7L2c67CxXG4gIGxlZnRKb2luPFRKb2luVGFibGUgZXh0ZW5kcyBrZXlvZiBUU2NoZW1hLCBUSm9pbkFsaWFzIGV4dGVuZHMgc3RyaW5nPihcbiAgICB0YWJsZVNwZWM6IHsgW0sgaW4gVEpvaW5BbGlhc106IFRKb2luVGFibGUgfSxcbiAgICBjYWxsYmFjazogKGo6IEpvaW5DbGF1c2VHcm91cDxUVGFibGVzLCBSZWNvcmQ8VEpvaW5BbGlhcywgVFNjaGVtYVtUSm9pblRhYmxlXT4+KSA9PiB2b2lkLFxuICApOiBQdXJpPFRTY2hlbWEsIFRUYWJsZXMgJiBSZWNvcmQ8VEpvaW5BbGlhcywgVFNjaGVtYVtUSm9pblRhYmxlXSAmIExlZnRKb2luZWRNYXJrZXI+LCBUUmVzdWx0PjtcbiAgLy8gTEVGVCBKT0lOOiDthYzsnbTruJTrqoUgKyDsvZzrsLFcbiAgbGVmdEpvaW48VEpvaW5UYWJsZSBleHRlbmRzIGtleW9mIFRTY2hlbWE+KFxuICAgIHRhYmxlTmFtZTogVEpvaW5UYWJsZSxcbiAgICBjYWxsYmFjazogKGo6IEpvaW5DbGF1c2VHcm91cDxUVGFibGVzLCBSZWNvcmQ8VEpvaW5UYWJsZSwgVFNjaGVtYVtUSm9pblRhYmxlXT4+KSA9PiB2b2lkLFxuICApOiBQdXJpPFRTY2hlbWEsIFRUYWJsZXMgJiBSZWNvcmQ8VEpvaW5UYWJsZSwgVFNjaGVtYVtUSm9pblRhYmxlXSAmIExlZnRKb2luZWRNYXJrZXI+LCBUUmVzdWx0PjtcbiAgLy8gTEVGVCBKT0lOIOyLpOygnCDqtaztmIRcbiAgbGVmdEpvaW4odGFibGVOYW1lT3JTcGVjOiBhbnksIC4uLmFyZ3M6IGFueVtdKTogYW55IHtcbiAgICByZXR1cm4gdGhpc1tcIl9fY29tbW9uSm9pblwiXShcImxlZnRKb2luXCIsIHRhYmxlTmFtZU9yU3BlYywgLi4uYXJncyk7XG4gIH1cblxuICAvLyBFTlNVUkUgTEVGVCBKT0lOOiDthYzsnbTruJQgKyBBbGlhc1xuICBlbnN1cmVMZWZ0Sm9pbjxcbiAgICBUSm9pblRhYmxlIGV4dGVuZHMga2V5b2YgVFNjaGVtYSxcbiAgICBUSm9pbkFsaWFzIGV4dGVuZHMgc3RyaW5nLFxuICAgIFRMZWZ0IGV4dGVuZHMgQXZhaWxhYmxlQ29sdW1uczxUVGFibGVzPixcbiAgPihcbiAgICB0YWJsZVNwZWM6IHsgW0sgaW4gVEpvaW5BbGlhc106IFRKb2luVGFibGUgfSxcbiAgICBsZWZ0OiBUTGVmdCxcbiAgICByaWdodDogYCR7VEpvaW5BbGlhc30uJHtDb2x1bW5LZXlzPFRTY2hlbWFbVEpvaW5UYWJsZV0+fWAsXG4gICk6IFB1cmk8XG4gICAgVFNjaGVtYSxcbiAgICBUVGFibGVzICYgUmVjb3JkPFRKb2luQWxpYXMsIFRTY2hlbWFbVEpvaW5UYWJsZV0gJiBMZWZ0Sm9pbk1hcmtlckZvcjxUVGFibGVzLCBUTGVmdD4+LFxuICAgIFRSZXN1bHRcbiAgPjtcbiAgLy8gRU5TVVJFIExFRlQgSk9JTjog7YWM7J2067iU66qFXG4gIGVuc3VyZUxlZnRKb2luPFRKb2luVGFibGUgZXh0ZW5kcyBrZXlvZiBUU2NoZW1hLCBUTGVmdCBleHRlbmRzIEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcz4+KFxuICAgIHRhYmxlTmFtZTogVEpvaW5UYWJsZSxcbiAgICBsZWZ0OiBUTGVmdCxcbiAgICByaWdodDogYCR7VEpvaW5UYWJsZSAmIHN0cmluZ30uJHtDb2x1bW5LZXlzPFRTY2hlbWFbVEpvaW5UYWJsZV0+fWAsXG4gICk6IFB1cmk8XG4gICAgVFNjaGVtYSxcbiAgICBUVGFibGVzICYgUmVjb3JkPFRKb2luVGFibGUsIFRTY2hlbWFbVEpvaW5UYWJsZV0gJiBMZWZ0Sm9pbk1hcmtlckZvcjxUVGFibGVzLCBUTGVmdD4+LFxuICAgIFRSZXN1bHRcbiAgPjtcbiAgZW5zdXJlTGVmdEpvaW4odGFibGVOYW1lT3JTcGVjOiBhbnksIGxlZnQ6IHN0cmluZywgcmlnaHQ6IHN0cmluZyk6IGFueSB7XG4gICAgcmV0dXJuIHRoaXNbXCJfX2Vuc3VyZUpvaW5cIl0oXCJsZWZ0Sm9pblwiLCB0YWJsZU5hbWVPclNwZWMsIGxlZnQsIHJpZ2h0KTtcbiAgfVxuXG4gIF9fY29tbW9uSm9pbihqb2luVHlwZTogXCJqb2luXCIgfCBcImxlZnRKb2luXCIsIHRhYmxlTmFtZU9yU3BlYzogYW55LCAuLi5hcmdzOiBhbnlbXSk6IHRoaXMge1xuICAgIGNvbnN0IHJlZ2lzdHJhdGlvbiA9IHRoaXMuY3JlYXRlSm9pblJlZ2lzdHJhdGlvbihqb2luVHlwZSwgdGFibGVOYW1lT3JTcGVjLCBhcmdzKTtcbiAgICB0aGlzLmFzc2VydENvcnJlbGF0aW9uQXZhaWxhYmxlKHJlZ2lzdHJhdGlvbik7XG5cbiAgICBpZiAoaXNTdHJpbmdWYWx1ZSh0YWJsZU5hbWVPclNwZWMpKSB7XG4gICAgICAvLyBDYXNlIDE6IGpvaW4oXCJwb3N0c1wiLCAuLi4pXG4gICAgICBjb25zdCB0YWJsZU5hbWUgPSB0YWJsZU5hbWVPclNwZWM7XG5cbiAgICAgIGlmIChhcmdzLmxlbmd0aCA9PT0gMSAmJiBpc0Z1bmN0aW9uVmFsdWUoYXJnc1swXSkpIHtcbiAgICAgICAgLy8gam9pbihcInBvc3RzXCIsIGNhbGxiYWNrKVxuICAgICAgICBjb25zdCBjYWxsYmFjayA9IGFyZ3NbMF07XG4gICAgICAgIHRoaXMua25leFF1ZXJ5W2pvaW5UeXBlXSh0YWJsZU5hbWUsIChqb2luQ2xhdXNlKSA9PiB7XG4gICAgICAgICAgY2FsbGJhY2sobmV3IEpvaW5DbGF1c2VHcm91cChqb2luQ2xhdXNlKSk7XG4gICAgICAgIH0pO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgLy8gam9pbihcInBvc3RzXCIsIGxlZnQsIHJpZ2h0KVxuICAgICAgICBjb25zdCBbbGVmdCwgcmlnaHRdID0gYXJncztcbiAgICAgICAgdGhpcy5rbmV4UXVlcnlbam9pblR5cGVdKHRhYmxlTmFtZSwgbGVmdCwgcmlnaHQpO1xuICAgICAgfVxuICAgIH0gZWxzZSBpZiAoaXNPYmplY3RWYWx1ZSh0YWJsZU5hbWVPclNwZWMpKSB7XG4gICAgICAvLyBDYXNlIDI6IGpvaW4oeyBhbGlhczogXCJ0YWJsZVwiIH0sIC4uLikgb3Igam9pbih7IGFsaWFzOiBzdWJxdWVyeSB9LCAuLi4pXG4gICAgICBjb25zdCBlbnRyaWVzID0gT2JqZWN0LmVudHJpZXModGFibGVOYW1lT3JTcGVjKTtcbiAgICAgIGlmIChlbnRyaWVzLmxlbmd0aCAhPT0gMSkge1xuICAgICAgICB0aHJvdyBuZXcgRXJyb3IoXCJUYWJsZSBzcGVjIG11c3QgaGF2ZSBleGFjdGx5IG9uZSBlbnRyeVwiKTtcbiAgICAgIH1cbiAgICAgIGFzc2VydChlbnRyaWVzWzBdKTtcbiAgICAgIGNvbnN0IFtbYWxpYXMsIHNwZWNdXSA9IGVudHJpZXM7XG5cbiAgICAgIGlmIChpc1N0cmluZ1ZhbHVlKHNwZWMpKSB7XG4gICAgICAgIC8vIO2FjOydtOu4lDogam9pbih7IHA6IFwicG9zdHNcIiB9LCAuLi4pXG4gICAgICAgIGlmIChhcmdzLmxlbmd0aCA9PT0gMSAmJiBpc0Z1bmN0aW9uVmFsdWUoYXJnc1swXSkpIHtcbiAgICAgICAgICAvLyBDYWxsYmFja1xuICAgICAgICAgIGNvbnN0IGNhbGxiYWNrID0gYXJnc1swXTtcbiAgICAgICAgICB0aGlzLmtuZXhRdWVyeVtqb2luVHlwZV0oeyBbYWxpYXNdOiBzcGVjIH0sIChqb2luQ2xhdXNlKSA9PiB7XG4gICAgICAgICAgICBjYWxsYmFjayhuZXcgSm9pbkNsYXVzZUdyb3VwKGpvaW5DbGF1c2UpKTtcbiAgICAgICAgICB9KTtcbiAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICAvLyBTaW1wbGVcbiAgICAgICAgICBjb25zdCBbbGVmdCwgcmlnaHRdID0gYXJncztcbiAgICAgICAgICB0aGlzLmtuZXhRdWVyeVtqb2luVHlwZV0oeyBbYWxpYXNdOiBzcGVjIH0sIGxlZnQsIHJpZ2h0KTtcbiAgICAgICAgfVxuICAgICAgfSBlbHNlIGlmIChzcGVjIGluc3RhbmNlb2YgUHVyaSkge1xuICAgICAgICAvLyDshJzruIzsv7zrpqw6IGpvaW4oeyBzcTogc3VicXVlcnkgfSwgLi4uKVxuICAgICAgICBpZiAoYXJncy5sZW5ndGggPT09IDEgJiYgaXNGdW5jdGlvblZhbHVlKGFyZ3NbMF0pKSB7XG4gICAgICAgICAgLy8gQ2FsbGJhY2tcbiAgICAgICAgICBjb25zdCBjYWxsYmFjayA9IGFyZ3NbMF07XG4gICAgICAgICAgdGhpcy5rbmV4UXVlcnlbam9pblR5cGVdKHNwZWMucmF3UXVlcnkoKS5hcyhhbGlhcyksIChqb2luQ2xhdXNlKSA9PiB7XG4gICAgICAgICAgICBjYWxsYmFjayhuZXcgSm9pbkNsYXVzZUdyb3VwKGpvaW5DbGF1c2UpKTtcbiAgICAgICAgICB9KTtcbiAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICAvLyBTaW1wbGVcbiAgICAgICAgICBjb25zdCBbbGVmdCwgcmlnaHRdID0gYXJncztcbiAgICAgICAgICB0aGlzLmtuZXhRdWVyeVtqb2luVHlwZV0oc3BlYy5yYXdRdWVyeSgpLmFzKGFsaWFzKSwgbGVmdCwgcmlnaHQpO1xuICAgICAgICB9XG4gICAgICB9IGVsc2Uge1xuICAgICAgICB0aHJvdyBuZXcgRXJyb3IoXCJJbnZhbGlkIHRhYmxlIHNwZWNpZmljYXRpb25cIik7XG4gICAgICB9XG4gICAgfSBlbHNlIHtcbiAgICAgIHRocm93IG5ldyBFcnJvcihcIkludmFsaWQgYXJndW1lbnRzXCIpO1xuICAgIH1cblxuICAgIHRoaXMuY29ycmVsYXRpb25SZWdpc3RyeS5zZXQocmVnaXN0cmF0aW9uLmFsaWFzLCByZWdpc3RyYXRpb24pO1xuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgcHJpdmF0ZSBfX2Vuc3VyZUpvaW4oXG4gICAgam9pblR5cGU6IFwiam9pblwiIHwgXCJsZWZ0Sm9pblwiLFxuICAgIHRhYmxlTmFtZU9yU3BlYzogc3RyaW5nIHwgUmVjb3JkPHN0cmluZywgc3RyaW5nPixcbiAgICBsZWZ0OiBzdHJpbmcsXG4gICAgcmlnaHQ6IHN0cmluZyxcbiAgKTogdGhpcyB7XG4gICAgY29uc3QgcmVxdWVzdGVkID0gdGhpcy5jcmVhdGVKb2luUmVnaXN0cmF0aW9uKGpvaW5UeXBlLCB0YWJsZU5hbWVPclNwZWMsIFtsZWZ0LCByaWdodF0pO1xuICAgIGlmICghcmVxdWVzdGVkLnJldXNhYmxlKSB7XG4gICAgICB0aHJvdyBuZXcgRXJyb3IoXG4gICAgICAgIGAke2pvaW5UeXBlID09PSBcImpvaW5cIiA/IFwiZW5zdXJlSm9pblwiIDogXCJlbnN1cmVMZWZ0Sm9pblwifSBvbmx5IHN1cHBvcnRzIHBoeXNpY2FsIHRhYmxlcyB3aXRoIHNpbXBsZSBjb2x1bW4gZXF1YWxpdHkgY29uZGl0aW9ucy5gLFxuICAgICAgKTtcbiAgICB9XG4gICAgY29uc3QgZXhpc3RpbmcgPSB0aGlzLmNvcnJlbGF0aW9uUmVnaXN0cnkuZ2V0KHJlcXVlc3RlZC5hbGlhcyk7XG5cbiAgICBpZiAoIWV4aXN0aW5nKSB7XG4gICAgICByZXR1cm4gdGhpc1tcIl9fY29tbW9uSm9pblwiXShqb2luVHlwZSwgdGFibGVOYW1lT3JTcGVjLCBsZWZ0LCByaWdodCk7XG4gICAgfVxuXG4gICAgaWYgKHRoaXMuaXNTYW1lSm9pblJlZ2lzdHJhdGlvbihleGlzdGluZywgcmVxdWVzdGVkKSkge1xuICAgICAgcmV0dXJuIHRoaXM7XG4gICAgfVxuXG4gICAgdGhyb3cgdGhpcy5jcmVhdGVKb2luQ29uZmxpY3RFcnJvcihleGlzdGluZywgcmVxdWVzdGVkKTtcbiAgfVxuXG4gIHByaXZhdGUgY3JlYXRlSm9pblJlZ2lzdHJhdGlvbihcbiAgICBqb2luVHlwZTogXCJqb2luXCIgfCBcImxlZnRKb2luXCIsXG4gICAgdGFibGVOYW1lT3JTcGVjOiBhbnksXG4gICAgYXJnczogYW55W10sXG4gICk6IEpvaW5SZWdpc3RyYXRpb24ge1xuICAgIGxldCBhbGlhczogc3RyaW5nO1xuICAgIGxldCB0YWJsZTogc3RyaW5nIHwgbnVsbDtcblxuICAgIGlmIChpc1N0cmluZ1ZhbHVlKHRhYmxlTmFtZU9yU3BlYykpIHtcbiAgICAgIGFsaWFzID0gdGFibGVOYW1lT3JTcGVjO1xuICAgICAgdGFibGUgPSB0YWJsZU5hbWVPclNwZWM7XG4gICAgfSBlbHNlIGlmIChpc09iamVjdFZhbHVlKHRhYmxlTmFtZU9yU3BlYykpIHtcbiAgICAgIGNvbnN0IGVudHJpZXMgPSBPYmplY3QuZW50cmllcyh0YWJsZU5hbWVPclNwZWMpO1xuICAgICAgaWYgKGVudHJpZXMubGVuZ3RoICE9PSAxKSB7XG4gICAgICAgIHRocm93IG5ldyBFcnJvcihcIlRhYmxlIHNwZWMgbXVzdCBoYXZlIGV4YWN0bHkgb25lIGVudHJ5XCIpO1xuICAgICAgfVxuICAgICAgYXNzZXJ0KGVudHJpZXNbMF0pO1xuICAgICAgY29uc3QgW1tqb2luQWxpYXMsIHNwZWNdXSA9IGVudHJpZXM7XG4gICAgICBhbGlhcyA9IGpvaW5BbGlhcztcbiAgICAgIHRhYmxlID0gaXNTdHJpbmdWYWx1ZShzcGVjKSA/IHNwZWMgOiBudWxsO1xuICAgIH0gZWxzZSB7XG4gICAgICB0aHJvdyBuZXcgRXJyb3IoXCJJbnZhbGlkIGFyZ3VtZW50c1wiKTtcbiAgICB9XG5cbiAgICBjb25zdCBbbGVmdCwgcmlnaHRdID0gYXJncztcbiAgICBjb25zdCByZXVzYWJsZSA9XG4gICAgICB0YWJsZSAhPT0gbnVsbCAmJiBhcmdzLmxlbmd0aCA9PT0gMiAmJiBpc1N0cmluZ1ZhbHVlKGxlZnQpICYmIGlzU3RyaW5nVmFsdWUocmlnaHQpO1xuXG4gICAgcmV0dXJuIHtcbiAgICAgIGtpbmQ6IFwiam9pblwiLFxuICAgICAgYWxpYXMsXG4gICAgICB0YWJsZSxcbiAgICAgIGpvaW5UeXBlLFxuICAgICAgbGVmdDogcmV1c2FibGUgPyBsZWZ0IDogbnVsbCxcbiAgICAgIHJpZ2h0OiByZXVzYWJsZSA/IHJpZ2h0IDogbnVsbCxcbiAgICAgIHJldXNhYmxlLFxuICAgIH07XG4gIH1cblxuICBwcml2YXRlIGFzc2VydENvcnJlbGF0aW9uQXZhaWxhYmxlKHJlcXVlc3RlZDogSm9pblJlZ2lzdHJhdGlvbik6IHZvaWQge1xuICAgIGNvbnN0IGV4aXN0aW5nID0gdGhpcy5jb3JyZWxhdGlvblJlZ2lzdHJ5LmdldChyZXF1ZXN0ZWQuYWxpYXMpO1xuICAgIGlmIChleGlzdGluZykge1xuICAgICAgaWYgKHRoaXMuaXNTYW1lSm9pblJlZ2lzdHJhdGlvbihleGlzdGluZywgcmVxdWVzdGVkKSkge1xuICAgICAgICB0aHJvdyBuZXcgRXJyb3IoXG4gICAgICAgICAgYEpvaW4gYWxpYXMgXCIke3JlcXVlc3RlZC5hbGlhc31cIiBpcyBhbHJlYWR5IHJlZ2lzdGVyZWQuIFVzZSBlbnN1cmVKb2luKCkgb3IgZW5zdXJlTGVmdEpvaW4oKSB0byByZXVzZSBhbiBpZGVudGljYWwgam9pbi5gLFxuICAgICAgICApO1xuICAgICAgfVxuICAgICAgdGhyb3cgdGhpcy5jcmVhdGVKb2luQ29uZmxpY3RFcnJvcihleGlzdGluZywgcmVxdWVzdGVkKTtcbiAgICB9XG4gIH1cblxuICBwcml2YXRlIGlzU2FtZUpvaW5SZWdpc3RyYXRpb24oXG4gICAgZXhpc3Rpbmc6IENvcnJlbGF0aW9uUmVnaXN0cmF0aW9uLFxuICAgIHJlcXVlc3RlZDogSm9pblJlZ2lzdHJhdGlvbixcbiAgKTogZXhpc3RpbmcgaXMgSm9pblJlZ2lzdHJhdGlvbiB7XG4gICAgcmV0dXJuIChcbiAgICAgIGV4aXN0aW5nLmtpbmQgPT09IFwiam9pblwiICYmXG4gICAgICBleGlzdGluZy5yZXVzYWJsZSAmJlxuICAgICAgcmVxdWVzdGVkLnJldXNhYmxlICYmXG4gICAgICBleGlzdGluZy50YWJsZSA9PT0gcmVxdWVzdGVkLnRhYmxlICYmXG4gICAgICBleGlzdGluZy5qb2luVHlwZSA9PT0gcmVxdWVzdGVkLmpvaW5UeXBlICYmXG4gICAgICBleGlzdGluZy5sZWZ0ID09PSByZXF1ZXN0ZWQubGVmdCAmJlxuICAgICAgZXhpc3RpbmcucmlnaHQgPT09IHJlcXVlc3RlZC5yaWdodFxuICAgICk7XG4gIH1cblxuICBwcml2YXRlIGNyZWF0ZUpvaW5Db25mbGljdEVycm9yKFxuICAgIGV4aXN0aW5nOiBDb3JyZWxhdGlvblJlZ2lzdHJhdGlvbixcbiAgICByZXF1ZXN0ZWQ6IEpvaW5SZWdpc3RyYXRpb24sXG4gICk6IEVycm9yIHtcbiAgICByZXR1cm4gbmV3IEVycm9yKFxuICAgICAgW1xuICAgICAgICBgSm9pbiBhbGlhcyBcIiR7cmVxdWVzdGVkLmFsaWFzfVwiIGlzIGFscmVhZHkgcmVnaXN0ZXJlZCB3aXRoIGEgZGlmZmVyZW50IGRlZmluaXRpb24uYCxcbiAgICAgICAgYEV4aXN0aW5nOiAke3RoaXMuZm9ybWF0Q29ycmVsYXRpb25SZWdpc3RyYXRpb24oZXhpc3RpbmcpfWAsXG4gICAgICAgIGBSZXF1ZXN0ZWQ6ICR7dGhpcy5mb3JtYXRDb3JyZWxhdGlvblJlZ2lzdHJhdGlvbihyZXF1ZXN0ZWQpfWAsXG4gICAgICBdLmpvaW4oXCJcXG5cIiksXG4gICAgKTtcbiAgfVxuXG4gIHByaXZhdGUgZm9ybWF0Q29ycmVsYXRpb25SZWdpc3RyYXRpb24ocmVnaXN0cmF0aW9uOiBDb3JyZWxhdGlvblJlZ2lzdHJhdGlvbik6IHN0cmluZyB7XG4gICAgaWYgKHJlZ2lzdHJhdGlvbi5raW5kID09PSBcImZyb21cIikge1xuICAgICAgcmV0dXJuIGBGUk9NICR7cmVnaXN0cmF0aW9uLnRhYmxlID8/IFwic3VicXVlcnlcIn0gQVMgJHtyZWdpc3RyYXRpb24uYWxpYXN9YDtcbiAgICB9XG5cbiAgICBjb25zdCBqb2luS2V5d29yZCA9IHJlZ2lzdHJhdGlvbi5qb2luVHlwZSA9PT0gXCJqb2luXCIgPyBcIkpPSU5cIiA6IFwiTEVGVCBKT0lOXCI7XG4gICAgY29uc3Qgc291cmNlID0gcmVnaXN0cmF0aW9uLnRhYmxlID8/IFwib3BhcXVlIHNvdXJjZVwiO1xuICAgIGNvbnN0IGNvbmRpdGlvbiA9IHJlZ2lzdHJhdGlvbi5yZXVzYWJsZVxuICAgICAgPyBgIE9OICR7cmVnaXN0cmF0aW9uLmxlZnR9ID0gJHtyZWdpc3RyYXRpb24ucmlnaHR9YFxuICAgICAgOiBcIiB3aXRoIG9wYXF1ZSBjb25kaXRpb25cIjtcbiAgICByZXR1cm4gYCR7am9pbktleXdvcmR9ICR7c291cmNlfSBBUyAke3JlZ2lzdHJhdGlvbi5hbGlhc30ke2NvbmRpdGlvbn1gO1xuICB9XG5cbiAgcHJpdmF0ZSBjbGVhckpvaW5SZWdpc3RyYXRpb25zKCk6IHZvaWQge1xuICAgIGZvciAoY29uc3QgW2FsaWFzLCByZWdpc3RyYXRpb25dIG9mIHRoaXMuY29ycmVsYXRpb25SZWdpc3RyeSkge1xuICAgICAgaWYgKHJlZ2lzdHJhdGlvbi5raW5kID09PSBcImpvaW5cIikge1xuICAgICAgICB0aGlzLmNvcnJlbGF0aW9uUmVnaXN0cnkuZGVsZXRlKGFsaWFzKTtcbiAgICAgIH1cbiAgICB9XG4gIH1cblxuICBwcml2YXRlIGdldEtuZXhKb2luQWxpYXM8VmFsdWU+KHRhYmxlOiBWYWx1ZSk6IHN0cmluZyB8IG51bGwge1xuICAgIGlmIChpc1N0cmluZ1ZhbHVlKHRhYmxlKSkge1xuICAgICAgcmV0dXJuIHRhYmxlO1xuICAgIH1cbiAgICBpZiAoaXNPYmplY3RWYWx1ZSh0YWJsZSkgJiYgdGFibGUgIT09IG51bGwpIHtcbiAgICAgIGlmIChcbiAgICAgICAgXCJfc2luZ2xlXCIgaW4gdGFibGUgJiZcbiAgICAgICAgaXNPYmplY3RWYWx1ZSh0YWJsZVtcIl9zaW5nbGVcIl0pICYmXG4gICAgICAgIHRhYmxlW1wiX3NpbmdsZVwiXSAhPT0gbnVsbCAmJlxuICAgICAgICBcImFzXCIgaW4gdGFibGVbXCJfc2luZ2xlXCJdICYmXG4gICAgICAgIGlzU3RyaW5nVmFsdWUodGFibGVbXCJfc2luZ2xlXCJdLmFzKVxuICAgICAgKSB7XG4gICAgICAgIHJldHVybiB0YWJsZVtcIl9zaW5nbGVcIl0uYXM7XG4gICAgICB9XG4gICAgICByZXR1cm4gT2JqZWN0LmtleXModGFibGUpWzBdID8/IG51bGw7XG4gICAgfVxuICAgIHJldHVybiBudWxsO1xuICB9XG5cbiAgLy8gV0hFUkU6IOqwneyytCAtIOyCrOyaqTogLndoZXJlKHsgXCJ1LmlkXCI6IDEsIFwidS5zdGF0dXNcIjogXCJhY3RpdmVcIiB9KVxuICB3aGVyZShjb25kaXRpb25zOiBXaGVyZUNvbmRpdGlvbjxUVGFibGVzPik6IHRoaXM7XG4gIC8vIFdIRVJFOiDsu6zrn7wgLSDsgqzsmqk6IC53aGVyZShcInUuaWRcIiwgMSksIC53aGVyZShcInUuaWRcIiwgbnVsbClcbiAgd2hlcmU8VENvbHVtbiBleHRlbmRzIEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcz4+KFxuICAgIGNvbHVtbjogVENvbHVtbixcbiAgICB2YWx1ZTogRXh0cmFjdENvbHVtblR5cGU8VFRhYmxlcywgVENvbHVtbiAmIHN0cmluZz4sXG4gICk6IHRoaXM7XG4gIC8vIFdIRVJFOiDsu6zrn7wgLSDsgqzsmqk6IC53aGVyZShcInUuaWRcIiwgXCI+XCIsIDEwKSwgLndoZXJlKFwidS5pZFwiLCBcIiE9XCIsIG51bGwpXG4gIHdoZXJlPFRDb2x1bW4gZXh0ZW5kcyBBdmFpbGFibGVDb2x1bW5zPFRUYWJsZXM+PihcbiAgICBjb2x1bW46IFRDb2x1bW4sXG4gICAgb3BlcmF0b3I6IFdoZXJlT3BlcmF0b3IsXG4gICAgdmFsdWU6IEV4dHJhY3RDb2x1bW5UeXBlPFRUYWJsZXMsIFRDb2x1bW4gJiBzdHJpbmc+LFxuICApOiB0aGlzO1xuICAvLyBXSEVSRTogU1FMIO2RnO2YhOyLnSAtIOyCrOyaqTogLndoZXJlKHB1cmkucmF3KFwiQ09OQ0FUKHUubmFtZSwgdS5lbWFpbClcIiksIFwibGlrZVwiLCBcIiV0ZXN0JVwiKVxuICB3aGVyZTxUQ29sdW1uIGV4dGVuZHMgS25leC5SYXc+KGNvbHVtbjogVENvbHVtbiwgb3BlcmF0b3I6IFdoZXJlT3BlcmF0b3IsIHZhbHVlOiBhbnkpOiB0aGlzO1xuICAvLyBXSEVSRTog7Lus65+8IC0g7IKs7JqpOiAud2hlcmUoXCJ1LmlkXCIsIFwibGlrZVwiLCBcIiV0ZXN0JVwiKVxuICB3aGVyZSguLi5hcmdzOiBbY29sdW1uT3JDb25kaXRpb25zOiBhbnksIG9wZXJhdG9yT3JWYWx1ZT86IGFueSwgdmFsdWU/OiBhbnldKTogdGhpcyB7XG4gICAgY29uc3QgW2NvbHVtbk9yQ29uZGl0aW9ucywgb3BlcmF0b3JPclZhbHVlLCB2YWx1ZV0gPSBhcmdzO1xuICAgIGlmIChpc09iamVjdFZhbHVlKGNvbHVtbk9yQ29uZGl0aW9ucykpIHtcbiAgICAgIHRoaXMua25leFF1ZXJ5LndoZXJlKGNvbHVtbk9yQ29uZGl0aW9ucyk7XG4gICAgfSBlbHNlIGlmICh2YWx1ZSA9PT0gdW5kZWZpbmVkKSB7XG4gICAgICBpZiAob3BlcmF0b3JPclZhbHVlID09PSBudWxsKSB7XG4gICAgICAgIHRoaXMua25leFF1ZXJ5LndoZXJlTnVsbChjb2x1bW5PckNvbmRpdGlvbnMpO1xuICAgICAgICByZXR1cm4gdGhpcztcbiAgICAgIH1cbiAgICAgIHRoaXMua25leFF1ZXJ5LndoZXJlKGNvbHVtbk9yQ29uZGl0aW9ucywgb3BlcmF0b3JPclZhbHVlKTtcbiAgICB9IGVsc2UgaWYgKHZhbHVlICE9PSB1bmRlZmluZWQpIHtcbiAgICAgIGlmICh2YWx1ZSA9PT0gbnVsbCkge1xuICAgICAgICBpZiAob3BlcmF0b3JPclZhbHVlID09PSBcIiE9XCIpIHtcbiAgICAgICAgICB0aGlzLmtuZXhRdWVyeS53aGVyZU5vdE51bGwoY29sdW1uT3JDb25kaXRpb25zKTtcbiAgICAgICAgICByZXR1cm4gdGhpcztcbiAgICAgICAgfSBlbHNlIGlmIChvcGVyYXRvck9yVmFsdWUgPT09IFwiPVwiKSB7XG4gICAgICAgICAgdGhpcy5rbmV4UXVlcnkud2hlcmVOdWxsKGNvbHVtbk9yQ29uZGl0aW9ucyk7XG4gICAgICAgICAgcmV0dXJuIHRoaXM7XG4gICAgICAgIH1cbiAgICAgIH1cbiAgICAgIHRoaXMua25leFF1ZXJ5LndoZXJlKGNvbHVtbk9yQ29uZGl0aW9ucywgb3BlcmF0b3JPclZhbHVlLCB2YWx1ZSk7XG4gICAgfSBlbHNlIHtcbiAgICAgIHRoaXMua25leFF1ZXJ5LndoZXJlKGNvbHVtbk9yQ29uZGl0aW9ucyk7XG4gICAgfVxuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgLy8gV0hFUkUgSU5cbiAgd2hlcmVJbjxUQ29sdW1uIGV4dGVuZHMgQXZhaWxhYmxlQ29sdW1uczxUVGFibGVzPj4oXG4gICAgY29sdW1uOiBUQ29sdW1uLFxuICAgIHZhbHVlczogKEV4dHJhY3RDb2x1bW5UeXBlPFRUYWJsZXMsIFRDb2x1bW4gJiBzdHJpbmc+ICYgS25leC5WYWx1ZSlbXSxcbiAgKTogUHVyaTxUU2NoZW1hLCBUVGFibGVzLCBUUmVzdWx0PiB7XG4gICAgLy8gS25leOydmCDruYTslrQg7J6I64qUIElOIOuwsOyXtCDsspjrpqzsmYAg64+Z7J287ZWY6rKMIO2VreyDgSDqsbDsp5Psnbgg7KGw6rG07J2EIOyDneyEse2VqeuLiOuLpC5cbiAgICBpZiAodmFsdWVzLmxlbmd0aCA9PT0gMCkge1xuICAgICAgdGhpcy5rbmV4UXVlcnkud2hlcmVSYXcoXCIxID0gMFwiKTtcbiAgICB9IGVsc2Uge1xuICAgICAgY29uc3QgcGxhY2Vob2xkZXJzID0gdmFsdWVzLm1hcCgoKSA9PiBcIj9cIikuam9pbihcIiwgXCIpO1xuICAgICAgdGhpcy5rbmV4UXVlcnkud2hlcmVSYXcoYD8/IGluICgke3BsYWNlaG9sZGVyc30pYCwgW1N0cmluZyhjb2x1bW4pLCAuLi52YWx1ZXNdKTtcbiAgICB9XG4gICAgLy8gU0FGRVRZOiDsv7zrpqwg67mM642U7J2YIOygnOuEpOumrSDqs4Tslb3qs7wg7ISg7ZaJIOqygOymneydtCDsnbQg7YOA7J6F7J2EIOuztOyepe2VqeuLiOuLpC5cbiAgICByZXR1cm4gdGhpcyBhcyBhbnk7XG4gIH1cblxuICAvLyBXSEVSRSBOT1QgSU5cbiAgd2hlcmVOb3RJbjxUQ29sdW1uIGV4dGVuZHMgQXZhaWxhYmxlQ29sdW1uczxUVGFibGVzPj4oXG4gICAgY29sdW1uOiBUQ29sdW1uLFxuICAgIHZhbHVlczogKEV4dHJhY3RDb2x1bW5UeXBlPFRUYWJsZXMsIFRDb2x1bW4gJiBzdHJpbmc+ICYgS25leC5WYWx1ZSlbXSxcbiAgKTogUHVyaTxUU2NoZW1hLCBUVGFibGVzLCBUUmVzdWx0PiB7XG4gICAgLy8gS25leOydmCDruYTslrQg7J6I64qUIE5PVCBJTiDrsLDsl7Qg7LKY66as7JmAIOuPmeydvO2VmOqyjCDtla3sg4Eg7LC47J24IOyhsOqxtOydhCDsg53shLHtlanri4jri6QuXG4gICAgaWYgKHZhbHVlcy5sZW5ndGggPT09IDApIHtcbiAgICAgIHRoaXMua25leFF1ZXJ5LndoZXJlUmF3KFwiMSA9IDFcIik7XG4gICAgfSBlbHNlIHtcbiAgICAgIGNvbnN0IHBsYWNlaG9sZGVycyA9IHZhbHVlcy5tYXAoKCkgPT4gXCI/XCIpLmpvaW4oXCIsIFwiKTtcbiAgICAgIHRoaXMua25leFF1ZXJ5LndoZXJlUmF3KGA/PyBub3QgaW4gKCR7cGxhY2Vob2xkZXJzfSlgLCBbU3RyaW5nKGNvbHVtbiksIC4uLnZhbHVlc10pO1xuICAgIH1cbiAgICAvLyBTQUZFVFk6IOy/vOumrCDruYzrjZTsnZgg7KCc64Sk66atIOqzhOyVveqzvCDshKDtlokg6rKA7Kad7J20IOydtCDtg4DsnoXsnYQg67O07J6l7ZWp64uI64ukLlxuICAgIHJldHVybiB0aGlzIGFzIGFueTtcbiAgfVxuXG4gIC8vIFdIRVJFIEpTT05CIFNVUEVSU0VUIChAPilcbiAgd2hlcmVKc29uU3VwZXJzZXRPZjxUQ29sdW1uIGV4dGVuZHMgSnNvbkNvbHVtbnM8VFRhYmxlcz4+KFxuICAgIGNvbHVtbjogVENvbHVtbixcbiAgICB2YWx1ZTogSnNvblN1cGVyc2V0VmFsdWU8RXh0cmFjdENvbHVtblR5cGU8VFRhYmxlcywgVENvbHVtbj4+LFxuICApOiB0aGlzIHtcbiAgICB0aGlzLmtuZXhRdWVyeS53aGVyZUpzb25TdXBlcnNldE9mKGNvbHVtbiwgc2VyaWFsaXplSnNvblN1cGVyc2V0VmFsdWUodmFsdWUpKTtcbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIC8vIFdIRVJFIE1BVENIXG4gIHdoZXJlTWF0Y2g8VENvbHVtbiBleHRlbmRzIEZ1bGx0ZXh0Q29sdW1uczxUVGFibGVzPj4oY29sdW1uOiBUQ29sdW1uLCB2YWx1ZTogc3RyaW5nKTogdGhpcyB7XG4gICAgdGhpcy5rbmV4UXVlcnkud2hlcmVSYXcoYE1BVENIICgke1N0cmluZyhjb2x1bW4pfSkgQUdBSU5TVCAoPylgLCBbdmFsdWVdKTtcbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIC8qKlxuICAgKiBQR3Jvb25nYSBGdWxsVGV4dCDsnbjrjbHsiqQg6rKA7IOJXG4gICAqIC0g7IKs7Jqp7ZWgIFBHcm9vbmdhIOyduOuNseyKpOyZgCDrj5nsnbztlZwg7Lus65+8IOq1rOyEseycvOuhnCDqsoDsg4ntlbTslbwg7J24642x7Iqk6rCAIOyCrOyaqeuQqeuLiOuLpC5cbiAgICpcbiAgICog64uo7J28IOy7rOufvCDqsoDsg4k6XG4gICAqIGBgYHNxbFxuICAgKiBXSEVSRSBuYW1lICZAfiAnc2VhcmNoJ1xuICAgKiBgYGBcbiAgICpcbiAgICog67O17ZWpIOy7rOufvCDqsoDsg4k6XG4gICAqIGBgYHNxbFxuICAgKiBXSEVSRSBBUlJBWVtuYW1lOjp0ZXh0LCBkZXNjcmlwdGlvbjo6dGV4dF0gJkB+ICdzZWFyY2gnXG4gICAqIGBgYFxuICAgKi9cbiAgd2hlcmVTZWFyY2g8VENvbHVtbiBleHRlbmRzIEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcz4+KFxuICAgIGNvbHVtbjogVENvbHVtbiB8IFRDb2x1bW5bXSxcbiAgICB2YWx1ZTogc3RyaW5nLFxuICAgIG9wdGlvbnM/OiB7XG4gICAgICB3ZWlnaHRzPzogbnVtYmVyW107IC8vIOygleyImCDrsLDsl7RcbiAgICB9LFxuICApOiB0aGlzIHtcbiAgICBjb25zdCB7IHdlaWdodHMgfSA9IG9wdGlvbnMgPz8ge307XG4gICAgY29uc3QgY29sdW1uRXhwciA9IEFycmF5LmlzQXJyYXkoY29sdW1uKVxuICAgICAgPyBgQVJSQVlbJHtjb2x1bW4ubWFwKChjKSA9PiBgJHtjfTo6dGV4dGApLmpvaW4oXCIsXCIpfV1gXG4gICAgICA6IGNvbHVtbjtcbiAgICBjb25zdCBwZ3Jvb25nYUNvbmRpdGlvbiA9IGBwZ3Jvb25nYV9jb25kaXRpb24oPyR7d2VpZ2h0cz8ubGVuZ3RoID8gYCwgd2VpZ2h0cyA9PiBBUlJBWVske3dlaWdodHMuam9pbihcIixcIil9XWAgOiBcIlwifSlgO1xuXG4gICAgdGhpcy5rbmV4UXVlcnkud2hlcmVSYXcoYCR7Y29sdW1uRXhwcn0gJkB+ICR7cGdyb29uZ2FDb25kaXRpb259YCwgW3ZhbHVlXSk7XG5cbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIC8vIFdIRVJFIEZVTExURVhUXG4gIHdoZXJlVHNTZWFyY2g8VENvbHVtbiBleHRlbmRzIEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcz4gfCBTcWxFeHByZXNzaW9uPFwic3RyaW5nXCI+PihcbiAgICBjb2x1bW46IFRDb2x1bW4sXG4gICAgdmFsdWU6IHN0cmluZyxcbiAgICBvcHRpb25zPzogVHNRdWVyeU9wdGlvbnMgfCBUc1F1ZXJ5Q29uZmlnLFxuICApOiB0aGlzIHtcbiAgICBjb25zdCBvcHRzID1cbiAgICAgIC8vIFNBRkVUWTog7L+866asIOu5jOuNlOydmCDsoJzrhKTrpq0g6rOE7JW96rO8IOyEoO2WiSDqsoDspp3snbQg7J20IO2DgOyeheydhCDrs7TsnqXtlanri4jri6QuXG4gICAgICBpc1N0cmluZ1ZhbHVlKG9wdGlvbnMpID8gKHsgY29uZmlnOiBvcHRpb25zIH0gYXMgVHNRdWVyeU9wdGlvbnMpIDogKG9wdGlvbnMgPz8ge30pO1xuXG4gICAgY29uc3QgcGFyc2VyID0gb3B0cy5wYXJzZXIgPz8gXCJ3ZWJzZWFyY2hfdG9fdHNxdWVyeVwiO1xuICAgIGNvbnN0IGNvbmZpZyA9IG9wdHMuY29uZmlnID8/IFwic2ltcGxlXCI7XG4gICAgY29uc3QgY29sdW1uRXhwciA9XG4gICAgICBpc1NxbEV4cHJlc3Npb24oY29sdW1uKSAmJiBjb2x1bW5bXCJfdHlwZVwiXSA9PT0gXCJzcWxfZXhwcmVzc2lvblwiXG4gICAgICAgID8gY29sdW1uW1wiX3NxbFwiXVxuICAgICAgICA6IFN0cmluZyhjb2x1bW4pO1xuXG4gICAgdGhpcy5rbmV4UXVlcnkud2hlcmVSYXcoYCR7Y29sdW1uRXhwcn0gQEAgJHtwYXJzZXJ9KD8sID8pYCwgW2NvbmZpZywgdmFsdWVdKTtcbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIHdoZXJlRnV6enk8VENvbHVtbiBleHRlbmRzIEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcz4gfCBTcWxFeHByZXNzaW9uPFwic3RyaW5nXCI+PihcbiAgICBjb2x1bW46IFRDb2x1bW4sXG4gICAgdmFsdWU6IHN0cmluZyxcbiAgICBvcHRpb25zPzoge1xuICAgICAgb3BlcmF0b3I/OiBGdXp6eU9wZXJhdG9yO1xuICAgIH0sXG4gICk6IHRoaXMge1xuICAgIGNvbnN0IG9wZXJhdG9yID0gcGFyc2VGdXp6eU9wZXJhdG9yKG9wdGlvbnM/Lm9wZXJhdG9yKTtcblxuICAgIGlmIChvcGVyYXRvciA9PT0gXCIlXCIpIHtcbiAgICAgIGlmIChpc1NxbEV4cHJlc3Npb24oY29sdW1uKSkge1xuICAgICAgICB0aGlzLmtuZXhRdWVyeS53aGVyZVJhdyhgJHtjb2x1bW5bXCJfc3FsXCJdfSAke29wZXJhdG9yfSA/YCwgWy4uLmNvbHVtbltcIl9wYXJhbXNcIl0sIHZhbHVlXSk7XG4gICAgICB9IGVsc2Uge1xuICAgICAgICB0aGlzLmtuZXhRdWVyeS53aGVyZVJhdyhgPz8gJHtvcGVyYXRvcn0gP2AsIFtjb2x1bW4sIHZhbHVlXSk7XG4gICAgICB9XG4gICAgICByZXR1cm4gdGhpcztcbiAgICB9XG5cbiAgICBpZiAoaXNTcWxFeHByZXNzaW9uKGNvbHVtbikpIHtcbiAgICAgIHRoaXMua25leFF1ZXJ5LndoZXJlUmF3KGA/ICR7b3BlcmF0b3J9ICR7Y29sdW1uW1wiX3NxbFwiXX1gLCBbdmFsdWUsIC4uLmNvbHVtbltcIl9wYXJhbXNcIl1dKTtcbiAgICB9IGVsc2Uge1xuICAgICAgdGhpcy5rbmV4UXVlcnkud2hlcmVSYXcoYD8gJHtvcGVyYXRvcn0gPz9gLCBbdmFsdWUsIGNvbHVtbl0pO1xuICAgIH1cbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIC8vIFdIRVJFIFJBV1xuICB3aGVyZVJhdyhzcWw6IHN0cmluZywgYmluZGluZ3M/OiByZWFkb25seSBLbmV4LlJhd0JpbmRpbmdbXSk6IHRoaXMge1xuICAgIHRoaXMua25leFF1ZXJ5LndoZXJlUmF3KHNxbCwgYmluZGluZ3MpO1xuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgLy8gV0hFUkUg6rSE7Zi4IOq3uOujue2VkVxuICB3aGVyZUdyb3VwKGNhbGxiYWNrOiAoZzogV2hlcmVHcm91cDxUVGFibGVzPikgPT4gdm9pZCk6IHRoaXMge1xuICAgIHRoaXMua25leFF1ZXJ5LndoZXJlKChidWlsZGVyKSA9PiB7XG4gICAgICBjb25zdCBncm91cCA9IG5ldyBXaGVyZUdyb3VwPFRUYWJsZXM+KGJ1aWxkZXIpO1xuICAgICAgY2FsbGJhY2soZ3JvdXApO1xuICAgIH0pO1xuICAgIHJldHVybiB0aGlzO1xuICB9XG4gIG9yV2hlcmVHcm91cChjYWxsYmFjazogKGc6IFdoZXJlR3JvdXA8VFRhYmxlcz4pID0+IHZvaWQpOiB0aGlzIHtcbiAgICB0aGlzLmtuZXhRdWVyeS5vcldoZXJlKChidWlsZGVyKSA9PiB7XG4gICAgICBjb25zdCBncm91cCA9IG5ldyBXaGVyZUdyb3VwPFRUYWJsZXM+KGJ1aWxkZXIpO1xuICAgICAgY2FsbGJhY2soZ3JvdXApO1xuICAgIH0pO1xuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgLy8gT1JERVIgQlkgKFNxbEV4cHJlc3Npb27snLzroZzrj4Qg7ZWgIOyImCDsnojslrTslbwg7ZWoKVxuICBvcmRlckJ5PFRDb2x1bW4gZXh0ZW5kcyBSZXN1bHRBdmFpbGFibGVDb2x1bW5zPFRUYWJsZXMsIFRSZXN1bHQ+PihcbiAgICBjb2x1bW46IFRDb2x1bW4gfCBQdXJpT3JkZXJCeUV4cHJlc3Npb24sXG4gICAgZGlyZWN0aW9uPzogUHVyaU9yZGVyQnlEaXJlY3Rpb24sXG4gICAgbnVsbHM/OiBQdXJpT3JkZXJCeU51bGxzLFxuICApOiB0aGlzO1xuICBvcmRlckJ5PFRDb2x1bW4gZXh0ZW5kcyBSZXN1bHRBdmFpbGFibGVDb2x1bW5zPFRUYWJsZXMsIFRSZXN1bHQ+PihcbiAgICBjb2x1bW5zOiByZWFkb25seSBQdXJpT3JkZXJCeUVudHJ5PFRDb2x1bW4+W10sXG4gICk6IHRoaXM7XG4gIG9yZGVyQnkoXG4gICAgY29sdW1uT3JDb2x1bW5zOiBzdHJpbmcgfCBQdXJpT3JkZXJCeUV4cHJlc3Npb24gfCByZWFkb25seSBQdXJpT3JkZXJCeVJ1bnRpbWVFbnRyeVtdLFxuICAgIGRpcmVjdGlvbjogUHVyaU9yZGVyQnlEaXJlY3Rpb24gPSBcImFzY1wiLFxuICAgIG51bGxzPzogUHVyaU9yZGVyQnlOdWxscyxcbiAgKTogdGhpcyB7XG4gICAgaWYgKGlzT3JkZXJCeUVudHJpZXMoY29sdW1uT3JDb2x1bW5zKSkge1xuICAgICAgZm9yIChjb25zdCBlbnRyeSBvZiBjb2x1bW5PckNvbHVtbnMpIHtcbiAgICAgICAgaWYgKGlzU3RyaW5nVmFsdWUoZW50cnkpIHx8IGlzU3FsRXhwcmVzc2lvbihlbnRyeSkpIHtcbiAgICAgICAgICB0aGlzLmFwcGx5T3JkZXJCeShlbnRyeSk7XG4gICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgdGhpcy5hcHBseU9yZGVyQnkoZW50cnkuY29sdW1uLCBlbnRyeS5vcmRlciwgZW50cnkubnVsbHMpO1xuICAgICAgICB9XG4gICAgICB9XG4gICAgICByZXR1cm4gdGhpcztcbiAgICB9XG5cbiAgICB0aGlzLmFwcGx5T3JkZXJCeShjb2x1bW5PckNvbHVtbnMsIGRpcmVjdGlvbiwgbnVsbHMpO1xuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgcHJpdmF0ZSBhcHBseU9yZGVyQnkoXG4gICAgY29sdW1uOiBzdHJpbmcgfCBQdXJpT3JkZXJCeUV4cHJlc3Npb24sXG4gICAgZGlyZWN0aW9uPzogUHVyaU9yZGVyQnlEaXJlY3Rpb24sXG4gICAgbnVsbHM/OiBQdXJpT3JkZXJCeU51bGxzLFxuICApOiB2b2lkIHtcbiAgICBjb25zdCBub3JtYWxpemVkRGlyZWN0aW9uID0gbm9ybWFsaXplT3JkZXJCeURpcmVjdGlvbihkaXJlY3Rpb24pO1xuICAgIGNvbnN0IG5vcm1hbGl6ZWROdWxscyA9IG5vcm1hbGl6ZU9yZGVyQnlOdWxscyhudWxscyk7XG5cbiAgICBpZiAoaXNTcWxFeHByZXNzaW9uKGNvbHVtbikpIHtcbiAgICAgIHRoaXMua25leFF1ZXJ5Lm9yZGVyQnlSYXcoXG4gICAgICAgIGAke2NvbHVtbltcIl9zcWxcIl19ICR7bm9ybWFsaXplZERpcmVjdGlvbn0ke2Zvcm1hdE51bGxzU3VmZml4KG5vcm1hbGl6ZWROdWxscyl9YCxcbiAgICAgICAgY29sdW1uW1wiX3BhcmFtc1wiXSxcbiAgICAgICk7XG4gICAgfSBlbHNlIHtcbiAgICAgIHRoaXMua25leFF1ZXJ5Lm9yZGVyQnkoY29sdW1uLCBub3JtYWxpemVkRGlyZWN0aW9uLCBub3JtYWxpemVkTnVsbHMpO1xuICAgIH1cbiAgfVxuXG4gIGZvclVwZGF0ZSgpOiB0aGlzIHtcbiAgICB0aGlzLmtuZXhRdWVyeS5mb3JVcGRhdGUoKTtcbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIGZvclNoYXJlKCk6IHRoaXMge1xuICAgIHRoaXMua25leFF1ZXJ5LmZvclNoYXJlKCk7XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICAvKipcbiAgICog67Kh7YSwIOycoOyCrOuPhCDqsoDsg4kg7ISk7KCVXG4gICAqXG4gICAqIC0gU0VMRUNU7JeQIHNpbWlsYXJpdHkg7Lus65+8IOy2lOqwgFxuICAgKiAtIFdIRVJFIGNvbCBJUyBOT1QgTlVMTCDstpTqsIBcbiAgICogLSB0aHJlc2hvbGTqsIAg7J6I7Jy866m0IFdIRVJFIOyhsOqxtCDstpTqsIBcbiAgICogLSDquLDsobQgT1JERVIgQlnrpbwgY2xlYXLtlZjqs6Ag7JuQ7IucIOyXsOyCsOyekOuhnCDsoJXroKwgKEhOU1cg7J24642x7IqkIOy1nOygge2ZlClcbiAgICpcbiAgICogQHBhcmFtIGNvbHVtbiDrsqHthLAg7Lus65+8IOqyveuhnFxuICAgKiBAcGFyYW0gZW1iZWRkaW5nIOy/vOumrCDsnoTrsqDrlKkg67Kh7YSwXG4gICAqIEBwYXJhbSBvcHRpb25zIG1ldGhvZCwgdGhyZXNob2xkLCBhcyDrk7Eg7Ji17IWYXG4gICAqXG4gICAqIEBleGFtcGxlXG4gICAqIGBgYHR5cGVzY3JpcHRcbiAgICogLy8gY29zaW5lIHNpbWlsYXJpdHkgKOq4sOuzuOqwkilcbiAgICogcWIudmVjdG9yU2ltaWxhcml0eShcImNvbHVtbk5hbWVcIiwgcXVlcnlWZWN0b3IsIHtcbiAgICogICBtZXRob2Q6IFwiY29zaW5lXCIsXG4gICAqICAgdGhyZXNob2xkOiAwLjVcbiAgICogfSk7XG4gICAqXG4gICAqIC8vIEwyIGRpc3RhbmNlXG4gICAqIHFiLnZlY3RvclNpbWlsYXJpdHkoXCJjb2x1bW5OYW1lXCIsIHF1ZXJ5VmVjdG9yLCB7XG4gICAqICAgbWV0aG9kOiBcImwyXCIsXG4gICAqICAgdGhyZXNob2xkOiAxLjUgIC8vIOqxsOumrOqwgCAxLjUg7J207ZWY7J24IOqysOqzvOunjFxuICAgKiB9KTtcbiAgICpcbiAgICogLy8gSW5uZXIgcHJvZHVjdFxuICAgKiBxYi52ZWN0b3JTaW1pbGFyaXR5KFwiY29sdW1uTmFtZVwiLCBxdWVyeVZlY3Rvciwge1xuICAgKiAgIG1ldGhvZDogXCJpbm5lcl9wcm9kdWN0XCIsXG4gICAqICAgdGhyZXNob2xkOiAwLjdcbiAgICogfSk7XG4gICAqIGBgYFxuICAgKi9cbiAgdmVjdG9yU2ltaWxhcml0eShcbiAgICBjb2x1bW46IFZlY3RvckNvbHVtbnM8VFRhYmxlcz4sXG4gICAgZW1iZWRkaW5nOiBudW1iZXJbXSxcbiAgICBvcHRpb25zOiB7XG4gICAgICBtZXRob2Q/OiBcImNvc2luZVwiIHwgXCJsMlwiIHwgXCJpbm5lcl9wcm9kdWN0XCI7XG4gICAgICB0aHJlc2hvbGQ/OiBudW1iZXI7XG4gICAgICBkaXN0aW5jdE9uPzogQXZhaWxhYmxlQ29sdW1uczxUVGFibGVzPjtcbiAgICB9ID0ge30sXG4gICk6IFB1cmk8VFNjaGVtYSwgVFRhYmxlcywgVFJlc3VsdCAmIHsgc2ltaWxhcml0eTogbnVtYmVyIH0+IHtcbiAgICBjb25zdCB7IG1ldGhvZCA9IFwiY29zaW5lXCIsIHRocmVzaG9sZCwgZGlzdGluY3RPbiB9ID0gb3B0aW9ucztcblxuICAgIGlmIChcbiAgICAgICFBcnJheS5pc0FycmF5KGVtYmVkZGluZykgfHxcbiAgICAgIGVtYmVkZGluZy5sZW5ndGggPT09IDAgfHxcbiAgICAgIGVtYmVkZGluZy5zb21lKCh2KSA9PiAhTnVtYmVyLmlzRmluaXRlKHYpKVxuICAgICkge1xuICAgICAgdGhyb3cgbmV3IEVycm9yKFwiSW52YWxpZCBlbWJlZGRpbmcgdmVjdG9yOiBleHBlY3RlZCBhIG5vbi1lbXB0eSBhcnJheSBvZiBmaW5pdGUgbnVtYmVyc1wiKTtcbiAgICB9XG5cbiAgICBjb25zdCB2ZWN0b3JMaXRlcmFsID0gSlNPTi5zdHJpbmdpZnkoZW1iZWRkaW5nLm1hcCgodikgPT4gTnVtYmVyKHYpKSk7XG4gICAgY29uc3Qgb3BlcmF0b3IgPSB7IGNvc2luZTogXCI8PT5cIiwgbDI6IFwiPC0+XCIsIGlubmVyX3Byb2R1Y3Q6IFwiPCM+XCIgfVttZXRob2RdO1xuXG4gICAgLy8gbWV0aG9k67OEIOyXsOyCsOyekCDrsI8gc2ltaWxhcml0eSDqs4TsgrDsi51cbiAgICAvLyAtIGNvc2luZTogPD0+IChjb3NpbmUgZGlzdGFuY2UsIDB+MiksIHNpbWlsYXJpdHkgPSAxIC0gZGlzdGFuY2VcbiAgICAvLyAtIGwyOiA8LT4gKGV1Y2xpZGVhbiBkaXN0YW5jZSksIHNpbWlsYXJpdHkgPSBkaXN0YW5jZSAo64Ku7J2E7IiY66GdIOycoOyCrClcbiAgICAvLyAtIGlubmVyX3Byb2R1Y3Q6IDwjPiAobmVnYXRpdmUgaW5uZXIgcHJvZHVjdCksIHNpbWlsYXJpdHkgPSAtZGlzdGFuY2UgKOuGkuydhOyImOuhnSDsnKDsgqwpXG4gICAgY29uc3Qgc2ltaWxhcml0eUV4cHIgPVxuICAgICAgbWV0aG9kID09PSBcImNvc2luZVwiXG4gICAgICAgID8gdGhpcy5rbmV4LnJhdyhgMSAtICg/PyAke29wZXJhdG9yfSA/Ojp2ZWN0b3IpIGFzIHNpbWlsYXJpdHlgLCBbY29sdW1uLCB2ZWN0b3JMaXRlcmFsXSlcbiAgICAgICAgOiBtZXRob2QgPT09IFwibDJcIlxuICAgICAgICAgID8gdGhpcy5rbmV4LnJhdyhgPz8gJHtvcGVyYXRvcn0gPzo6dmVjdG9yIGFzIHNpbWlsYXJpdHlgLCBbY29sdW1uLCB2ZWN0b3JMaXRlcmFsXSlcbiAgICAgICAgICA6IHRoaXMua25leC5yYXcoYC0oPz8gJHtvcGVyYXRvcn0gPzo6dmVjdG9yKSBhcyBzaW1pbGFyaXR5YCwgW2NvbHVtbiwgdmVjdG9yTGl0ZXJhbF0pO1xuXG4gICAgLy8gV0hFUkUgTk9UIE5VTExcbiAgICB0aGlzLmtuZXhRdWVyeS53aGVyZU5vdE51bGwoY29sdW1uKTtcblxuICAgIC8vIOq4sOyhtCBPUkRFUiBCWSBjbGVhclxuICAgIHRoaXMua25leFF1ZXJ5LmNsZWFyKFwib3JkZXJcIik7XG4gICAgaWYgKGRpc3RpbmN0T24pIHtcbiAgICAgIC8vIERJU1RJTkNUIE9O7J2AIFNFTEVDVCDsoIjsnZgg66eoIOyVnuyXkCDsmYDslbwg7ZWY66+A66GcLCDquLDsobQgc2VsZWN0KHN1YnNldCDtlYTrk5zrk6Qp66W8IOuztOyhtCDtm4QgY2xlYXLtlZjqs6Ag64uk7IucIOy2lOqwgFxuICAgICAgLy8gU0FGRVRZOiDsv7zrpqwg67mM642U7J2YIOygnOuEpOumrSDqs4Tslb3qs7wg7ISg7ZaJIOqygOymneydtCDsnbQg7YOA7J6F7J2EIOuztOyepe2VqeuLiOuLpC5cbiAgICAgIGNvbnN0IGV4aXN0aW5nU3Vic2V0Q29scyA9ICh0aGlzLmtuZXhRdWVyeSBhcyBhbnkpW1wiX3N0YXRlbWVudHNcIl1cbiAgICAgICAgLmZpbHRlcigoczogYW55KSA9PiBzLmdyb3VwaW5nID09PSBcImNvbHVtbnNcIilcbiAgICAgICAgLmZsYXRNYXAoKHM6IGFueSkgPT4gcy52YWx1ZSk7XG4gICAgICB0aGlzLmtuZXhRdWVyeS5jbGVhcihcInNlbGVjdFwiKTtcbiAgICAgIHRoaXMua25leFF1ZXJ5LnNlbGVjdCh0aGlzLmtuZXgucmF3KGBESVNUSU5DVCBPTiAoPz8pID8/YCwgW2Rpc3RpbmN0T24sIGRpc3RpbmN0T25dKSk7XG4gICAgICBleGlzdGluZ1N1YnNldENvbHMubWFwKChjb2w6IGFueSkgPT4gdGhpcy5rbmV4UXVlcnkuc2VsZWN0KGNvbCkpO1xuICAgICAgdGhpcy5rbmV4UXVlcnkuc2VsZWN0KHNpbWlsYXJpdHlFeHByKTtcbiAgICAgIHRoaXMua25leFF1ZXJ5Lm9yZGVyQnlSYXcoYD8/LCA/PyAke29wZXJhdG9yfSA/Ojp2ZWN0b3JgLCBbXG4gICAgICAgIGRpc3RpbmN0T24sXG4gICAgICAgIGNvbHVtbixcbiAgICAgICAgdmVjdG9yTGl0ZXJhbCxcbiAgICAgIF0pO1xuXG4gICAgICB0aGlzLmtuZXhRdWVyeSA9IHRoaXMua25leFxuICAgICAgICAuZnJvbSh0aGlzLmtuZXhRdWVyeS5hcyhcImRpc3RpbmN0X3ZlY3RvcnNcIikpXG4gICAgICAgIC5zZWxlY3QoXCIqXCIpXG4gICAgICAgIC5vcmRlckJ5KFwic2ltaWxhcml0eVwiLCBcImRlc2NcIik7XG4gICAgfSBlbHNlIHtcbiAgICAgIHRoaXMua25leFF1ZXJ5LnNlbGVjdChzaW1pbGFyaXR5RXhwcik7XG4gICAgICB0aGlzLmtuZXhRdWVyeS5vcmRlckJ5UmF3KGA/PyAke29wZXJhdG9yfSA/Ojp2ZWN0b3JgLCBbY29sdW1uLCB2ZWN0b3JMaXRlcmFsXSk7XG4gICAgfVxuXG4gICAgLy8gdGhyZXNob2xkXG4gICAgaWYgKGlzTnVtYmVyVmFsdWUodGhyZXNob2xkKSkge1xuICAgICAgaWYgKCFOdW1iZXIuaXNGaW5pdGUodGhyZXNob2xkKSkge1xuICAgICAgICB0aHJvdyBuZXcgRXJyb3IoYEludmFsaWQgdmVjdG9yU2ltaWxhcml0eSB0aHJlc2hvbGQ6ICR7dGhyZXNob2xkfWApO1xuICAgICAgfVxuXG4gICAgICBpZiAoZGlzdGluY3RPbikge1xuICAgICAgICBjb25zdCB0aHJlc2hvbGRPcCA9IG1ldGhvZCA9PT0gXCJsMlwiID8gXCI8PVwiIDogXCI+PVwiO1xuICAgICAgICB0aGlzLmtuZXhRdWVyeS53aGVyZShcInNpbWlsYXJpdHlcIiwgdGhyZXNob2xkT3AsIHRocmVzaG9sZCk7XG4gICAgICB9IGVsc2Uge1xuICAgICAgICBjb25zdCB0aHJlc2hvbGRWYWx1ZSA9XG4gICAgICAgICAgbWV0aG9kID09PSBcImNvc2luZVwiID8gMSAtIHRocmVzaG9sZCA6IG1ldGhvZCA9PT0gXCJpbm5lcl9wcm9kdWN0XCIgPyAtdGhyZXNob2xkIDogdGhyZXNob2xkO1xuICAgICAgICB0aGlzLmtuZXhRdWVyeS53aGVyZVJhdyhgPz8gJHtvcGVyYXRvcn0gPzo6dmVjdG9yIDw9ID9gLCBbXG4gICAgICAgICAgY29sdW1uLFxuICAgICAgICAgIHZlY3RvckxpdGVyYWwsXG4gICAgICAgICAgdGhyZXNob2xkVmFsdWUsXG4gICAgICAgIF0pO1xuICAgICAgfVxuICAgIH1cblxuICAgIC8vIFNBRkVUWTog7L+866asIOu5jOuNlOydmCDsoJzrhKTrpq0g6rOE7JW96rO8IOyEoO2WiSDqsoDspp3snbQg7J20IO2DgOyeheydhCDrs7TsnqXtlanri4jri6QuXG4gICAgcmV0dXJuIHRoaXMgYXMgYW55O1xuICB9XG5cbiAgLy8g6riw67O4IOy/vOumrCDrqZTshJzrk5zrk6RcbiAgbGltaXQoY291bnQ6IG51bWJlcik6IHRoaXMge1xuICAgIGlmIChjb3VudCA8IDApIHtcbiAgICAgIHRocm93IG5ldyBFcnJvcihcIkludmFsaWQgbGltaXQ6IG11c3QgYmUgPj0gMFwiKTtcbiAgICB9XG4gICAgdGhpcy5rbmV4UXVlcnkubGltaXQoY291bnQpO1xuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgb2Zmc2V0KGNvdW50OiBudW1iZXIpOiB0aGlzIHtcbiAgICBpZiAoY291bnQgPCAwKSB7XG4gICAgICB0aHJvdyBuZXcgRXJyb3IoXCJJbnZhbGlkIG9mZnNldDogbXVzdCBiZSA+PSAwXCIpO1xuICAgIH1cbiAgICB0aGlzLmtuZXhRdWVyeS5vZmZzZXQoY291bnQpO1xuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgLy8gR1JPVVAgQllcbiAgZ3JvdXBCeTxUQ29sdW1ucyBleHRlbmRzIFJlc3VsdEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcywgVFJlc3VsdD4+KC4uLmNvbHVtbnM6IFRDb2x1bW5zW10pOiB0aGlzO1xuICBncm91cEJ5KC4uLmNvbHVtbnM6IHN0cmluZ1tdKTogdGhpcyB7XG4gICAgdGhpcy5rbmV4UXVlcnkuZ3JvdXBCeSguLi5jb2x1bW5zKTtcbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIC8vIEhBVklOR1xuICBoYXZpbmcoY29uZGl0aW9uOiBzdHJpbmcpOiB0aGlzO1xuICBoYXZpbmc8VENvbHVtbiBleHRlbmRzIFJlc3VsdEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcywgVFJlc3VsdD4+KFxuICAgIGNvbHVtbjogVENvbHVtbixcbiAgICBvcGVyYXRvcjogQ29tcGFyaXNvbk9wZXJhdG9yLFxuICAgIHZhbHVlOiBhbnksXG4gICk6IHRoaXM7XG4gIC8vIEhBVklORyDqtaztmIRcbiAgaGF2aW5nKC4uLmNvbmRpdGlvbnM6IGFueVtdKTogdGhpcyB7XG4gICAgaWYgKGNvbmRpdGlvbnMubGVuZ3RoID09PSAxKSB7XG4gICAgICAvLyBoYXZpbmcoXCJDT1VOVCgqKSA+IDEwXCIpXG4gICAgICB0aGlzLmtuZXhRdWVyeS5oYXZpbmcodGhpcy5rbmV4LnJhdyhjb25kaXRpb25zWzBdKSk7XG4gICAgfSBlbHNlIGlmIChjb25kaXRpb25zLmxlbmd0aCA9PT0gMykge1xuICAgICAgLy8gaGF2aW5nKFwiY291bnRcIiwgXCI+XCIsIDEwKVxuICAgICAgdGhpcy5rbmV4UXVlcnkuaGF2aW5nKFxuICAgICAgICB0aGlzLmtuZXgucmF3KGNvbmRpdGlvbnNbMF0pLFxuICAgICAgICBjb25kaXRpb25zWzFdLFxuICAgICAgICB0aGlzLmtuZXgucmF3KGNvbmRpdGlvbnNbMl0pLFxuICAgICAgKTtcbiAgICB9IGVsc2Uge1xuICAgICAgdGhyb3cgbmV3IEVycm9yKFwiSW52YWxpZCBoYXZpbmcgYXJndW1lbnRzXCIpO1xuICAgIH1cbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIC8vIOyLpO2WiSDrqZTshJzrk5zrk6QgLSB0aGVuYWJsZSDqtaztmIRcbiAgdGhlbjxUUmVzdWx0MSA9IEV4cGFuZDxUUmVzdWx0PltdLCBUUmVzdWx0MiA9IG5ldmVyPihcbiAgICBvbmZ1bGZpbGxlZD86ICgodmFsdWU6IEV4cGFuZDxUUmVzdWx0PltdKSA9PiBUUmVzdWx0MSB8IFByb21pc2VMaWtlPFRSZXN1bHQxPikgfCBudWxsLFxuICAgIG9ucmVqZWN0ZWQ/OiAoKHJlYXNvbjogYW55KSA9PiBUUmVzdWx0MiB8IFByb21pc2VMaWtlPFRSZXN1bHQyPikgfCBudWxsLFxuICApOiBQcm9taXNlPFRSZXN1bHQxIHwgVFJlc3VsdDI+IHtcbiAgICBOYWl0ZS50KFwicHVyaTpleGVjdXRlZC1xdWVyeVwiLCB0aGlzLnRvUXVlcnkoKSk7XG4gICAgLy8gU0FGRVRZOiDsv7zrpqwg67mM642U7J2YIOygnOuEpOumrSDqs4Tslb3qs7wg7ISg7ZaJIOqygOymneydtCDsnbQg7YOA7J6F7J2EIOuztOyepe2VqeuLiOuLpC5cbiAgICByZXR1cm4gdGhpcy5rbmV4UXVlcnkudGhlbihvbmZ1bGZpbGxlZCBhcyBhbnksIG9ucmVqZWN0ZWQpO1xuICB9XG4gIGNhdGNoPFRSZXN1bHQyID0gbmV2ZXI+KFxuICAgIG9ucmVqZWN0ZWQ/OiAoKHJlYXNvbjogYW55KSA9PiBUUmVzdWx0MiB8IFByb21pc2VMaWtlPFRSZXN1bHQyPikgfCBudWxsLFxuICApOiBQcm9taXNlPFRSZXN1bHQgfCBUUmVzdWx0Mj4ge1xuICAgIHJldHVybiB0aGlzLmtuZXhRdWVyeS5jYXRjaChvbnJlamVjdGVkKTtcbiAgfVxuICBmaW5hbGx5KG9uZmluYWxseT86ICgoKSA9PiB2b2lkKSB8IG51bGwpOiBQcm9taXNlPFRSZXN1bHQ+IHtcbiAgICByZXR1cm4gdGhpcy5rbmV4UXVlcnkuZmluYWxseShvbmZpbmFsbHkpO1xuICB9XG5cbiAgLy8g7ZWY64KY66eMIOy/vOumrFxuICBmaXJzdCgpOiBSZXNvbHZlZFB1cmk8RXhwYW5kPFRSZXN1bHQ+LCBuZXZlcj4ge1xuICAgIHRoaXMua25leFF1ZXJ5LmZpcnN0KCk7XG4gICAgcmV0dXJuIG5ldyBSZXNvbHZlZFB1cmkodGhpcy5rbmV4UXVlcnksIHRoaXMua25leCwgdGhpcy50YWJsZVNwZWMpO1xuICB9XG5cbiAgLy8g7L+866as7ZWcIOugiOy9lOuTnOyXkOyEnCDtirnsoJUg7Lus65+866eMIOy2lOy2nO2VnCDrsLDsl7Qg66as7YS0XG4gIHBsdWNrPFRDb2x1bW4gZXh0ZW5kcyBrZXlvZiBUUmVzdWx0IHwgUmVzdWx0QXZhaWxhYmxlQ29sdW1uczxUVGFibGVzLCBUUmVzdWx0Pj4oXG4gICAgY29sdW1uOiBUQ29sdW1uLFxuICApOiBSZXNvbHZlZFB1cmk8XG4gICAgVENvbHVtbiBleHRlbmRzIGtleW9mIFRSZXN1bHRcbiAgICAgID8gVFJlc3VsdFtUQ29sdW1uXVtdXG4gICAgICA6IEV4dHJhY3RDb2x1bW5UeXBlPFRUYWJsZXMsIFRDb2x1bW4gJiBzdHJpbmc+W10sXG4gICAgbmV2ZXJcbiAgPiB7XG4gICAgLy8gU0FGRVRZOiDsv7zrpqwg67mM642U7J2YIOygnOuEpOumrSDqs4Tslb3qs7wg7ISg7ZaJIOqygOymneydtCDsnbQg7YOA7J6F7J2EIOuztOyepe2VqeuLiOuLpC5cbiAgICB0aGlzLmtuZXhRdWVyeS5wbHVjayhjb2x1bW4gYXMgc3RyaW5nKTtcbiAgICByZXR1cm4gbmV3IFJlc29sdmVkUHVyaSh0aGlzLmtuZXhRdWVyeSwgdGhpcy5rbmV4LCB0aGlzLnRhYmxlU3BlYyk7XG4gIH1cblxuICAvLyBJTlNFUlQgOiDri6jsnbwg6rCd7LK0XG4gIGluc2VydChcbiAgICBkYXRhOiBJbnNlcnREYXRhPFNpbmdsZVRhYmxlVmFsdWU8VFRhYmxlcz4+LFxuICApOiBSZXNvbHZlZFB1cmk8SW5zZXJ0UmVzdWx0LCBTaW5nbGVUYWJsZVZhbHVlPFRUYWJsZXM+PjtcbiAgLy8gSU5TRVJUOiDrsLDsl7RcbiAgaW5zZXJ0KFxuICAgIGRhdGE6IEluc2VydERhdGE8U2luZ2xlVGFibGVWYWx1ZTxUVGFibGVzPj5bXSxcbiAgKTogUmVzb2x2ZWRQdXJpPEluc2VydFJlc3VsdCwgU2luZ2xlVGFibGVWYWx1ZTxUVGFibGVzPj47XG4gIC8vIElOU0VSVCDsi6TsoJwg6rWs7ZiEXG4gIGluc2VydChcbiAgICByYXdEYXRhOiBJbnNlcnREYXRhPFNpbmdsZVRhYmxlVmFsdWU8VFRhYmxlcz4+IHwgSW5zZXJ0RGF0YTxTaW5nbGVUYWJsZVZhbHVlPFRUYWJsZXM+PltdLFxuICApOiBSZXNvbHZlZFB1cmk8SW5zZXJ0UmVzdWx0LCBTaW5nbGVUYWJsZVZhbHVlPFRUYWJsZXM+PiB7XG4gICAgLy8gSlNPTiDsu6zrn7wgc3RyaW5naWZ5IOuhnOyngeydhCDrqZTshJzrk5zroZwg67aE66as7ZWY7JesIOykkeuztSDsoJzqsbBcbiAgICBjb25zdCByZWZpbmVkRGF0YSA9IHRoaXMucmVmaW5lSnNvbkNvbHVtbnMocmF3RGF0YSk7XG4gICAgdGhpcy5rbmV4UXVlcnkuaW5zZXJ0KHJlZmluZWREYXRhKTtcbiAgICByZXR1cm4gbmV3IFJlc29sdmVkUHVyaSh0aGlzLmtuZXhRdWVyeSwgdGhpcy5rbmV4LCB0aGlzLnRhYmxlU3BlYyk7XG4gIH1cblxuICAvLyBVUERBVEVcbiAgdXBkYXRlKHJhd0RhdGE6IFdoZXJlQ29uZGl0aW9uPFRUYWJsZXM+KTogUmVzb2x2ZWRQdXJpPG51bWJlciwgU2luZ2xlVGFibGVWYWx1ZTxUVGFibGVzPj4ge1xuICAgIC8vIEpTT04g7Lus65+8IHN0cmluZ2lmeSDroZzsp4HsnYQg66mU7ISc65Oc66GcIOu2hOumrO2VmOyXrCDspJHrs7Ug7KCc6rGwXG4gICAgY29uc3QgcmVmaW5lZERhdGEgPSB0aGlzLnJlZmluZUpzb25Db2x1bW5zKHJhd0RhdGEpO1xuICAgIHRoaXMua25leFF1ZXJ5LnVwZGF0ZShyZWZpbmVkRGF0YSk7XG4gICAgcmV0dXJuIG5ldyBSZXNvbHZlZFB1cmkodGhpcy5rbmV4UXVlcnksIHRoaXMua25leCwgdGhpcy50YWJsZVNwZWMpO1xuICB9XG5cbiAgLyoqXG4gICAqIEpTT04g7Lus65+87JeQIOuMgO2VtCBzdHJpbmdpZnkg7LKY66as66W8IOyImO2Wie2VmOuKlCDrgrTrtoAg66mU7ISc65Oc7J6F64uI64ukLlxuICAgKiBvYmplY3Qg65iQ64qUIG9iamVjdCDrsLDsl7TsnYQg67Cb6rOgLCBKU09OIOy7rOufvOydtCDsnojsnLzrqbQg7KeB66Cs7ZmU7ZWY7JesIOuwmO2ZmO2VqeuLiOuLpC5cbiAgICog7KeB7KCRIOqwkuydhCDrs4Dqsr3tlZjrr4DroZwgc2lkZSBlZmZlY3TqsIAg7J6I7Iq164uI64ukLlxuICAgKi9cbiAgcHJpdmF0ZSByZWZpbmVKc29uQ29sdW1uczxSb3cgZXh0ZW5kcyBvYmplY3Q+KGRhdGE6IFJvdyB8IFJvd1tdKTogdHlwZW9mIGRhdGEge1xuICAgIC8vIHRhYmxlU3BlY+ydtOuCmCBqc29uQ29sdW1ucyDsl4bripQg6rK97JqwIOuwlOuhnCDrsJjtmZhcbiAgICBpZiAoIXRoaXMudGFibGVTcGVjIHx8ICF0aGlzLnRhYmxlU3BlYy5qc29uQ29sdW1ucy5sZW5ndGgpIHtcbiAgICAgIHJldHVybiBkYXRhO1xuICAgIH1cblxuICAgIC8vIOuTseuhneuQnCBUYWJsZVNwZWPsnYQg7Ya17ZW0IEpTT07su6zrn7wg66qp66Gd7J2EIOqwgOyguOyZgCBKU09OLnN0cmluZ2lmeSDsspjrpqxcbiAgICBjb25zdCBqc29uQ29sdW1ucyA9IHRoaXMudGFibGVTcGVjLmpzb25Db2x1bW5zO1xuICAgIGlmIChBcnJheS5pc0FycmF5KGRhdGEpKSB7XG4gICAgICBmb3IgKGNvbnN0IGl0ZW0gb2YgZGF0YSkge1xuICAgICAgICBmb3IgKGNvbnN0IGNvbHVtbiBvZiBqc29uQ29sdW1ucykge1xuICAgICAgICAgIGNvbnN0IHZhbHVlID0gT2JqZWN0LmVudHJpZXMoaXRlbSkuZmluZCgoW2tleV0pID0+IGtleSA9PT0gY29sdW1uKT8uWzFdO1xuICAgICAgICAgIGlmICh2YWx1ZSAhPT0gdW5kZWZpbmVkICYmIHZhbHVlICE9PSBudWxsKSB7XG4gICAgICAgICAgICBPYmplY3QuYXNzaWduKGl0ZW0sIHtcbiAgICAgICAgICAgICAgW2NvbHVtbl06IHNlcmlhbGl6ZUpzb25Db2x1bW5WYWx1ZSh0aGlzLnRhYmxlU3BlYywgY29sdW1uLCB2YWx1ZSksXG4gICAgICAgICAgICB9KTtcbiAgICAgICAgICB9XG4gICAgICAgIH1cbiAgICAgIH1cbiAgICB9IGVsc2Uge1xuICAgICAgZm9yIChjb25zdCBjb2x1bW4gb2YganNvbkNvbHVtbnMpIHtcbiAgICAgICAgY29uc3QgdmFsdWUgPSBPYmplY3QuZW50cmllcyhkYXRhKS5maW5kKChba2V5XSkgPT4ga2V5ID09PSBjb2x1bW4pPy5bMV07XG4gICAgICAgIGlmICh2YWx1ZSAhPT0gdW5kZWZpbmVkICYmIHZhbHVlICE9PSBudWxsKSB7XG4gICAgICAgICAgT2JqZWN0LmFzc2lnbihkYXRhLCB7XG4gICAgICAgICAgICBbY29sdW1uXTogc2VyaWFsaXplSnNvbkNvbHVtblZhbHVlKHRoaXMudGFibGVTcGVjLCBjb2x1bW4sIHZhbHVlKSxcbiAgICAgICAgICB9KTtcbiAgICAgICAgfVxuICAgICAgfVxuICAgIH1cbiAgICByZXR1cm4gZGF0YTtcbiAgfVxuXG4gIC8vIEluY3JlbWVudFxuICBpbmNyZW1lbnQ8VENvbHVtbiBleHRlbmRzIE51bWVyaWNDb2x1bW5zPFRUYWJsZXM+PihcbiAgICBjb2x1bW46IFRDb2x1bW4sXG4gICAgdmFsdWU6IG51bWJlcixcbiAgKTogUmVzb2x2ZWRQdXJpPG51bWJlciwgU2luZ2xlVGFibGVWYWx1ZTxUVGFibGVzPj4ge1xuICAgIGlmICh2YWx1ZSA8PSAwKSB7XG4gICAgICB0aHJvdyBuZXcgRXJyb3IoXCJJbmNyZW1lbnQgdmFsdWUgbXVzdCBiZSBncmVhdGVyIHRoYW4gMFwiKTtcbiAgICB9XG4gICAgdGhpcy5rbmV4UXVlcnkuaW5jcmVtZW50KGNvbHVtbiwgdmFsdWUpO1xuICAgIHJldHVybiBuZXcgUmVzb2x2ZWRQdXJpKHRoaXMua25leFF1ZXJ5LCB0aGlzLmtuZXgsIHRoaXMudGFibGVTcGVjKTtcbiAgfVxuICAvLyBEZWNyZW1lbnRcbiAgZGVjcmVtZW50PFRDb2x1bW4gZXh0ZW5kcyBOdW1lcmljQ29sdW1uczxUVGFibGVzPj4oXG4gICAgY29sdW1uOiBUQ29sdW1uLFxuICAgIHZhbHVlOiBudW1iZXIsXG4gICk6IFJlc29sdmVkUHVyaTxudW1iZXIsIFNpbmdsZVRhYmxlVmFsdWU8VFRhYmxlcz4+IHtcbiAgICBpZiAodmFsdWUgPD0gMCkge1xuICAgICAgdGhyb3cgbmV3IEVycm9yKFwiRGVjcmVtZW50IHZhbHVlIG11c3QgYmUgZ3JlYXRlciB0aGFuIDBcIik7XG4gICAgfVxuICAgIHRoaXMua25leFF1ZXJ5LmRlY3JlbWVudChjb2x1bW4sIHZhbHVlKTtcbiAgICByZXR1cm4gbmV3IFJlc29sdmVkUHVyaSh0aGlzLmtuZXhRdWVyeSwgdGhpcy5rbmV4LCB0aGlzLnRhYmxlU3BlYyk7XG4gIH1cblxuICAvLyBERUxFVEVcbiAgZGVsZXRlKCk6IFJlc29sdmVkUHVyaTxudW1iZXIsIFNpbmdsZVRhYmxlVmFsdWU8VFRhYmxlcz4+IHtcbiAgICB0aGlzLmtuZXhRdWVyeS5kZWxldGUoKTtcbiAgICByZXR1cm4gbmV3IFJlc29sdmVkUHVyaSh0aGlzLmtuZXhRdWVyeSwgdGhpcy5rbmV4LCB0aGlzLnRhYmxlU3BlYyk7XG4gIH1cblxuICAvLyDtmZXsnbgg7L+866asIOumrO2EtFxuICB0b1F1ZXJ5KCk6IHN0cmluZyB7XG4gICAgcmV0dXJuIHRoaXMua25leFF1ZXJ5LnRvUXVlcnkoKTtcbiAgfVxuXG4gIC8vIOy/vOumrCDrlJTrsoTquYUg66Gc6re4IOy2nOugpVxuICBkZWJ1ZygpOiB0aGlzIHtcbiAgICBjb25zb2xlLmxvZyhgJHtjaGFsay5jeWFuKFwiW1B1cmkgRGVidWddXCIpfSAke2NoYWxrLnllbGxvdyh0aGlzLnRvUXVlcnkoKSl9YCk7XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICBjbG9uZSgpOiBQdXJpPFRTY2hlbWEsIFRUYWJsZXMsIFRSZXN1bHQ+IHtcbiAgICAvLyAnZHVhbCfsnYAg642U66+4IO2FjOydtOu4lOydtOupsCwg67CU66GcIOyVhOuemCDspITsl5DshJwga25leFF1ZXJ56rCAIOuNruyWtOyUjOybjOynkeuLiOuLpC5cbiAgICBjb25zdCBuZXdQdXJpID0gbmV3IFB1cmk8VFNjaGVtYSwgVFRhYmxlcywgVFJlc3VsdD4odGhpcy5rbmV4LCBcImR1YWxcIik7XG4gICAgbmV3UHVyaS5rbmV4UXVlcnkgPSB0aGlzLmtuZXhRdWVyeS5jbG9uZSgpO1xuICAgIG5ld1B1cmkudGFibGVTcGVjID0gdGhpcy50YWJsZVNwZWM7XG4gICAgbmV3UHVyaS5jb3JyZWxhdGlvblJlZ2lzdHJ5ID0gbmV3IE1hcCh0aGlzLmNvcnJlbGF0aW9uUmVnaXN0cnkpO1xuICAgIHJldHVybiBuZXdQdXJpO1xuICB9XG5cbiAgZm9ybWF0U1FMKHVuZm9ybWF0dGVkOiBzdHJpbmcpOiBzdHJpbmcge1xuICAgIC8vIFNRTCDsmIjslb3slrQg66qp66GdXG4gICAgY29uc3Qga2V5d29yZHMgPSBbXG4gICAgICBcIlNFTEVDVFwiLFxuICAgICAgXCJGUk9NXCIsXG4gICAgICBcIldIRVJFXCIsXG4gICAgICBcIklOU0VSVFwiLFxuICAgICAgXCJJTlRPXCIsXG4gICAgICBcIlZBTFVFU1wiLFxuICAgICAgXCJVUERBVEVcIixcbiAgICAgIFwiREVMRVRFXCIsXG4gICAgICBcIkNSRUFURVwiLFxuICAgICAgXCJUQUJMRVwiLFxuICAgICAgXCJBTFRFUlwiLFxuICAgICAgXCJEUk9QXCIsXG4gICAgICBcIkpPSU5cIixcbiAgICAgIFwiT05cIixcbiAgICAgIFwiSU5ORVJcIixcbiAgICAgIFwiTEVGVFwiLFxuICAgICAgXCJSSUdIVFwiLFxuICAgICAgXCJGVUxMXCIsXG4gICAgICBcIk9VVEVSXCIsXG4gICAgICBcIkdST1VQXCIsXG4gICAgICBcIkJZXCIsXG4gICAgICBcIk9SREVSXCIsXG4gICAgICBcIkhBVklOR1wiLFxuICAgICAgXCJESVNUSU5DVFwiLFxuICAgICAgXCJMSU1JVFwiLFxuICAgICAgXCJPRkZTRVRcIixcbiAgICAgIFwiQVNcIixcbiAgICAgIFwiQU5EXCIsXG4gICAgICBcIk9SXCIsXG4gICAgICBcIk5PVFwiLFxuICAgICAgXCJJTlwiLFxuICAgICAgXCJMSUtFXCIsXG4gICAgICBcIklTXCIsXG4gICAgICBcIk5VTExcIixcbiAgICAgIFwiQ0FTRVwiLFxuICAgICAgXCJXSEVOXCIsXG4gICAgICBcIlRIRU5cIixcbiAgICAgIFwiRUxTRVwiLFxuICAgICAgXCJFTkRcIixcbiAgICAgIFwiVU5JT05cIixcbiAgICAgIFwiQUxMXCIsXG4gICAgICBcIkVYSVNUU1wiLFxuICAgICAgXCJCRVRXRUVOXCIsXG4gICAgXTtcblxuICAgIGxldCBmb3JtYXR0ZWQgPSB1bmZvcm1hdHRlZDtcblxuICAgIC8vIOyYiOyVveyWtOulvCDrjIDrrLjsnpDroZwg67OA7ZmYXG4gICAga2V5d29yZHMuZm9yRWFjaCgoa2V5d29yZCkgPT4ge1xuICAgICAgY29uc3QgcmVnZXggPSBuZXcgUmVnRXhwKGBcXFxcYiR7a2V5d29yZH1cXFxcYmAsIFwiZ2lcIik7XG4gICAgICBmb3JtYXR0ZWQgPSBmb3JtYXR0ZWQucmVwbGFjZShyZWdleCwga2V5d29yZC50b1VwcGVyQ2FzZSgpKTtcbiAgICB9KTtcblxuICAgIC8vIOyjvOyalCDsoIgg7JWe7JeQIOykhOuwlOq/iCDstpTqsIBcbiAgICBjb25zdCBtYWpvckNsYXVzZXMgPSBbXG4gICAgICBcIlNFTEVDVFwiLFxuICAgICAgXCJGUk9NXCIsXG4gICAgICBcIldIRVJFXCIsXG4gICAgICBcIkdST1VQIEJZXCIsXG4gICAgICBcIk9SREVSIEJZXCIsXG4gICAgICBcIkhBVklOR1wiLFxuICAgICAgXCJMSU1JVFwiLFxuICAgICAgXCJVTklPTlwiLFxuICAgIF07XG4gICAgbWFqb3JDbGF1c2VzLmZvckVhY2goKGNsYXVzZSkgPT4ge1xuICAgICAgY29uc3QgcmVnZXggPSBuZXcgUmVnRXhwKGBcXFxccysoJHtjbGF1c2V9KVxcXFxzK2AsIFwiZ2lcIik7XG4gICAgICBmb3JtYXR0ZWQgPSBmb3JtYXR0ZWQucmVwbGFjZShyZWdleCwgYFxcbiR7Y2xhdXNlLnRvVXBwZXJDYXNlKCl9IGApO1xuICAgIH0pO1xuXG4gICAgLy8gSk9JTiDsoIgg7LKY66asXG4gICAgZm9ybWF0dGVkID0gZm9ybWF0dGVkLnJlcGxhY2UoL1xccysoKD86SU5ORVJ8TEVGVHxSSUdIVHxGVUxMIE9VVEVSKVxccyspP0pPSU5cXHMrL2dpLCBcIlxcbiQxSk9JTiBcIik7XG5cbiAgICAvLyBBTkQsIE9SIOyhsOqxtCDsspjrpqxcbiAgICBmb3JtYXR0ZWQgPSBmb3JtYXR0ZWQucmVwbGFjZSgvXFxzKyhBTkR8T1IpXFxzKy9naSwgXCJcXG4gICQxIFwiKTtcblxuICAgIC8vIOq0hO2YuCDsspjrpqwg67CPIOuTpOyXrOyTsOq4sFxuICAgIGNvbnN0IGxpbmVzID0gZm9ybWF0dGVkLnNwbGl0KFwiXFxuXCIpO1xuICAgIGNvbnN0IGluZGVudGVkTGluZXMgPSBbXTtcbiAgICBsZXQgaW5kZW50TGV2ZWwgPSAwO1xuXG4gICAgZm9yIChjb25zdCBsaW5lIG9mIGxpbmVzKSB7XG4gICAgICBjb25zdCB0cmltbWVkTGluZSA9IGxpbmUudHJpbSgpO1xuICAgICAgaWYgKCF0cmltbWVkTGluZSkgY29udGludWU7XG5cbiAgICAgIC8vIOuLq+uKlCDqtITtmLjqsIAg7J6I7Jy866m0IOuTpOyXrOyTsOq4sCDroIjrsqgg6rCQ7IaMXG4gICAgICBjb25zdCBjbG9zaW5nUGFyZW5zID0gKHRyaW1tZWRMaW5lLm1hdGNoKC9cXCkvZykgfHwgW10pLmxlbmd0aDtcbiAgICAgIGNvbnN0IG9wZW5pbmdQYXJlbnMgPSAodHJpbW1lZExpbmUubWF0Y2goL1xcKC9nKSB8fCBbXSkubGVuZ3RoO1xuXG4gICAgICBpZiAoY2xvc2luZ1BhcmVucyA+IDAgJiYgb3BlbmluZ1BhcmVucyA9PT0gMCkge1xuICAgICAgICBpbmRlbnRMZXZlbCA9IE1hdGgubWF4KDAsIGluZGVudExldmVsIC0gY2xvc2luZ1BhcmVucyk7XG4gICAgICB9XG5cbiAgICAgIC8vIO2YhOyerCDrk6Tsl6zsk7DquLAg7KCB7JqpXG4gICAgICBjb25zdCBpbmRlbnQgPSBcIiAgXCIucmVwZWF0KGluZGVudExldmVsKTtcbiAgICAgIGluZGVudGVkTGluZXMucHVzaChpbmRlbnQgKyB0cmltbWVkTGluZSk7XG5cbiAgICAgIC8vIOyXrOuKlCDqtITtmLjqsIAg7J6I7Jy866m0IOuTpOyXrOyTsOq4sCDroIjrsqgg7Kad6rCAXG4gICAgICBpZiAob3BlbmluZ1BhcmVucyA+IGNsb3NpbmdQYXJlbnMpIHtcbiAgICAgICAgaW5kZW50TGV2ZWwgKz0gb3BlbmluZ1BhcmVucyAtIGNsb3NpbmdQYXJlbnM7XG4gICAgICB9XG4gICAgfVxuXG4gICAgcmV0dXJuIGluZGVudGVkTGluZXMuam9pbihcIlxcblwiKS50cmltKCk7XG4gIH1cblxuICByYXcoc3FsOiBzdHJpbmcpOiBLbmV4LlJhdyB7XG4gICAgcmV0dXJuIHRoaXMua25leC5yYXcoc3FsKTtcbiAgfVxuXG4gIC8vIEtuZXgg7L+866asIOu5jOuNlCDsp4HsoJEg7KCR6re8XG4gIHJhd1F1ZXJ5KCk6IEtuZXguUXVlcnlCdWlsZGVyIHtcbiAgICByZXR1cm4gdGhpcy5rbmV4UXVlcnk7XG4gIH1cbn1cblxuZXhwb3J0IGNsYXNzIFdoZXJlR3JvdXA8VFRhYmxlcyBleHRlbmRzIG9iamVjdD4ge1xuICBjb25zdHJ1Y3Rvcihwcml2YXRlIGJ1aWxkZXI6IEtuZXguUXVlcnlCdWlsZGVyKSB7fVxuXG4gIC8vIHdoZXJlIOuplOyEnOuTnOuTpFxuICB3aGVyZShjb25kaXRpb25zOiBXaGVyZUNvbmRpdGlvbjxUVGFibGVzPik6IHRoaXM7XG4gIHdoZXJlPFRDb2x1bW4gZXh0ZW5kcyBBdmFpbGFibGVDb2x1bW5zPFRUYWJsZXM+PihcbiAgICBjb2x1bW46IFRDb2x1bW4sXG4gICAgdmFsdWU6IEV4dHJhY3RDb2x1bW5UeXBlPFRUYWJsZXMsIFRDb2x1bW4gJiBzdHJpbmc+LFxuICApOiB0aGlzO1xuICB3aGVyZTxUQ29sdW1uIGV4dGVuZHMgQXZhaWxhYmxlQ29sdW1uczxUVGFibGVzPj4oXG4gICAgY29sdW1uOiBUQ29sdW1uLFxuICAgIG9wZXJhdG9yOiBXaGVyZU9wZXJhdG9yLFxuICAgIHZhbHVlOiBFeHRyYWN0Q29sdW1uVHlwZTxUVGFibGVzLCBUQ29sdW1uICYgc3RyaW5nPixcbiAgKTogdGhpcztcbiAgd2hlcmUoLi4uYXJnczogYW55W10pOiBXaGVyZUdyb3VwPFRUYWJsZXM+IHtcbiAgICB0aGlzLmJ1aWxkZXIud2hlcmUoYXJnc1swXSwgLi4uYXJncy5zbGljZSgxKSk7XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICAvLyB3aGVyZUluIC8gd2hlcmVOb3RJbiDrqZTshJzrk5zrk6RcbiAgd2hlcmVJbjxUQ29sdW1uIGV4dGVuZHMgQXZhaWxhYmxlQ29sdW1uczxUVGFibGVzPj4oXG4gICAgY29sdW1uOiBUQ29sdW1uLFxuICAgIHZhbHVlczogKEV4dHJhY3RDb2x1bW5UeXBlPFRUYWJsZXMsIFRDb2x1bW4gJiBzdHJpbmc+ICYgS25leC5WYWx1ZSlbXSxcbiAgKTogdGhpcztcbiAgd2hlcmVJbiguLi5hcmdzOiBhbnlbXSk6IFdoZXJlR3JvdXA8VFRhYmxlcz4ge1xuICAgIHRoaXMuYnVpbGRlci53aGVyZUluKGFyZ3NbMF0sIGFyZ3NbMV0pO1xuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgd2hlcmVOb3RJbjxUQ29sdW1uIGV4dGVuZHMgQXZhaWxhYmxlQ29sdW1uczxUVGFibGVzPj4oXG4gICAgY29sdW1uOiBUQ29sdW1uLFxuICAgIHZhbHVlczogKEV4dHJhY3RDb2x1bW5UeXBlPFRUYWJsZXMsIFRDb2x1bW4gJiBzdHJpbmc+ICYgS25leC5WYWx1ZSlbXSxcbiAgKTogdGhpcztcbiAgd2hlcmVOb3RJbiguLi5hcmdzOiBhbnlbXSk6IFdoZXJlR3JvdXA8VFRhYmxlcz4ge1xuICAgIHRoaXMuYnVpbGRlci53aGVyZU5vdEluKGFyZ3NbMF0sIGFyZ3NbMV0pO1xuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgLy8gb3JXaGVyZSDrqZTshJzrk5zrk6RcbiAgb3JXaGVyZShjb25kaXRpb25zOiBXaGVyZUNvbmRpdGlvbjxUVGFibGVzPik6IHRoaXM7XG4gIG9yV2hlcmU8VENvbHVtbiBleHRlbmRzIEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcz4+KFxuICAgIGNvbHVtbjogVENvbHVtbixcbiAgICB2YWx1ZTogRXh0cmFjdENvbHVtblR5cGU8VFRhYmxlcywgVENvbHVtbiAmIHN0cmluZz4sXG4gICk6IHRoaXM7XG4gIG9yV2hlcmU8VENvbHVtbiBleHRlbmRzIEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcz4+KFxuICAgIGNvbHVtbjogVENvbHVtbixcbiAgICBvcGVyYXRvcjogV2hlcmVPcGVyYXRvcixcbiAgICB2YWx1ZTogRXh0cmFjdENvbHVtblR5cGU8VFRhYmxlcywgVENvbHVtbiAmIHN0cmluZz4sXG4gICk6IHRoaXM7XG4gIG9yV2hlcmUoLi4uYXJnczogYW55W10pOiBXaGVyZUdyb3VwPFRUYWJsZXM+IHtcbiAgICB0aGlzLmJ1aWxkZXIub3JXaGVyZShhcmdzWzBdLCAuLi5hcmdzLnNsaWNlKDEpKTtcbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIC8vIG9yV2hlcmVJbiAvIG9yV2hlcmVOb3RJbiDrqZTshJzrk5zrk6RcbiAgb3JXaGVyZUluPFRDb2x1bW4gZXh0ZW5kcyBBdmFpbGFibGVDb2x1bW5zPFRUYWJsZXM+PihcbiAgICBjb2x1bW46IFRDb2x1bW4sXG4gICAgdmFsdWVzOiAoRXh0cmFjdENvbHVtblR5cGU8VFRhYmxlcywgVENvbHVtbiAmIHN0cmluZz4gJiBLbmV4LlZhbHVlKVtdLFxuICApOiB0aGlzO1xuICBvcldoZXJlSW4oLi4uYXJnczogYW55W10pOiBXaGVyZUdyb3VwPFRUYWJsZXM+IHtcbiAgICB0aGlzLmJ1aWxkZXIub3JXaGVyZUluKGFyZ3NbMF0sIGFyZ3NbMV0pO1xuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgb3JXaGVyZU5vdEluPFRDb2x1bW4gZXh0ZW5kcyBBdmFpbGFibGVDb2x1bW5zPFRUYWJsZXM+PihcbiAgICBjb2x1bW46IFRDb2x1bW4sXG4gICAgdmFsdWVzOiAoRXh0cmFjdENvbHVtblR5cGU8VFRhYmxlcywgVENvbHVtbiAmIHN0cmluZz4gJiBLbmV4LlZhbHVlKVtdLFxuICApOiB0aGlzO1xuICBvcldoZXJlTm90SW4oLi4uYXJnczogYW55W10pOiBXaGVyZUdyb3VwPFRUYWJsZXM+IHtcbiAgICB0aGlzLmJ1aWxkZXIub3JXaGVyZU5vdEluKGFyZ3NbMF0sIGFyZ3NbMV0pO1xuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgLy8gV0hFUkUgSlNPTkIgU1VQRVJTRVQgKEA+KVxuICB3aGVyZUpzb25TdXBlcnNldE9mPFRDb2x1bW4gZXh0ZW5kcyBKc29uQ29sdW1uczxUVGFibGVzPj4oXG4gICAgY29sdW1uOiBUQ29sdW1uLFxuICAgIHZhbHVlOiBKc29uU3VwZXJzZXRWYWx1ZTxFeHRyYWN0Q29sdW1uVHlwZTxUVGFibGVzLCBUQ29sdW1uPj4sXG4gICk6IHRoaXMge1xuICAgIHRoaXMuYnVpbGRlci53aGVyZUpzb25TdXBlcnNldE9mKGNvbHVtbiwgc2VyaWFsaXplSnNvblN1cGVyc2V0VmFsdWUodmFsdWUpKTtcbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIG9yV2hlcmVKc29uU3VwZXJzZXRPZjxUQ29sdW1uIGV4dGVuZHMgSnNvbkNvbHVtbnM8VFRhYmxlcz4+KFxuICAgIGNvbHVtbjogVENvbHVtbixcbiAgICB2YWx1ZTogSnNvblN1cGVyc2V0VmFsdWU8RXh0cmFjdENvbHVtblR5cGU8VFRhYmxlcywgVENvbHVtbj4+LFxuICApOiB0aGlzIHtcbiAgICB0aGlzLmJ1aWxkZXIub3JXaGVyZUpzb25TdXBlcnNldE9mKGNvbHVtbiwgc2VyaWFsaXplSnNvblN1cGVyc2V0VmFsdWUodmFsdWUpKTtcbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIC8vIFdIRVJFIE1BVENIXG4gIHdoZXJlTWF0Y2g8VENvbHVtbiBleHRlbmRzIEZ1bGx0ZXh0Q29sdW1uczxUVGFibGVzPj4oY29sdW1uOiBUQ29sdW1uLCB2YWx1ZTogc3RyaW5nKTogdGhpcztcbiAgd2hlcmVNYXRjaCguLi5hcmdzOiBhbnlbXSk6IHRoaXMge1xuICAgIHRoaXMuYnVpbGRlci53aGVyZVJhdyhgTUFUQ0ggKCR7U3RyaW5nKGFyZ3NbMF0pfSkgQUdBSU5TVCAoPylgLCBbYXJnc1sxXV0pO1xuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgb3JXaGVyZU1hdGNoPFRDb2x1bW4gZXh0ZW5kcyBGdWxsdGV4dENvbHVtbnM8VFRhYmxlcz4+KGNvbHVtbjogVENvbHVtbiwgdmFsdWU6IHN0cmluZyk6IHRoaXM7XG4gIG9yV2hlcmVNYXRjaCguLi5hcmdzOiBhbnlbXSk6IHRoaXMge1xuICAgIHRoaXMuYnVpbGRlci5vcldoZXJlUmF3KGBNQVRDSCAoJHtTdHJpbmcoYXJnc1swXSl9KSBBR0FJTlNUICg/KWAsIFthcmdzWzFdXSk7XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICAvLyBXSEVSRSBTRUFSQ0hcbiAgd2hlcmVTZWFyY2g8VENvbHVtbiBleHRlbmRzIEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcz4+KFxuICAgIGNvbHVtbjogVENvbHVtbiB8IFRDb2x1bW5bXSxcbiAgICB2YWx1ZTogc3RyaW5nLFxuICAgIG9wdGlvbnM/OiB7XG4gICAgICB3ZWlnaHRzPzogbnVtYmVyW107IC8vIOygleyImCDrsLDsl7RcbiAgICB9LFxuICApOiB0aGlzO1xuICB3aGVyZVNlYXJjaCguLi5hcmdzOiBhbnlbXSk6IHRoaXMge1xuICAgIGNvbnN0IHsgd2VpZ2h0cyB9ID0gYXJnc1syXSA/PyB7fTtcbiAgICBjb25zdCBjb2x1bW5FeHByID0gQXJyYXkuaXNBcnJheShhcmdzWzBdKVxuICAgICAgPyBgQVJSQVlbJHthcmdzWzBdLm1hcCgoYykgPT4gYCR7Y306OnRleHRgKS5qb2luKFwiLFwiKX1dYFxuICAgICAgOiBhcmdzWzBdO1xuICAgIGNvbnN0IHBncm9vbmdhQ29uZGl0aW9uID0gYHBncm9vbmdhX2NvbmRpdGlvbig/JHt3ZWlnaHRzPy5sZW5ndGggPyBgLCB3ZWlnaHRzID0+IEFSUkFZWyR7d2VpZ2h0cy5qb2luKFwiLFwiKX1dYCA6IFwiXCJ9KWA7XG4gICAgdGhpcy5idWlsZGVyLndoZXJlUmF3KGAke2NvbHVtbkV4cHJ9ICZAfiAke3Bncm9vbmdhQ29uZGl0aW9ufWAsIFthcmdzWzFdXSk7XG5cbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIG9yV2hlcmVTZWFyY2g8VENvbHVtbiBleHRlbmRzIEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcz4+KFxuICAgIGNvbHVtbjogVENvbHVtbiB8IFRDb2x1bW5bXSxcbiAgICB2YWx1ZTogc3RyaW5nLFxuICAgIG9wdGlvbnM/OiB7XG4gICAgICB3ZWlnaHRzPzogbnVtYmVyW107IC8vIOygleyImCDrsLDsl7RcbiAgICB9LFxuICApOiB0aGlzO1xuICBvcldoZXJlU2VhcmNoKC4uLmFyZ3M6IGFueVtdKTogdGhpcyB7XG4gICAgY29uc3QgeyB3ZWlnaHRzIH0gPSBhcmdzWzJdID8/IHt9O1xuICAgIGNvbnN0IGNvbHVtbkV4cHIgPSBBcnJheS5pc0FycmF5KGFyZ3NbMF0pXG4gICAgICA/IGBBUlJBWVske2FyZ3NbMF0ubWFwKChjKSA9PiBgJHtjfTo6dGV4dGApLmpvaW4oXCIsXCIpfV1gXG4gICAgICA6IGFyZ3NbMF07XG4gICAgY29uc3QgcGdyb29uZ2FDb25kaXRpb24gPSBgcGdyb29uZ2FfY29uZGl0aW9uKD8ke3dlaWdodHM/Lmxlbmd0aCA/IGAsIHdlaWdodHMgPT4gQVJSQVlbJHt3ZWlnaHRzLmpvaW4oXCIsXCIpfV1gIDogXCJcIn0pYDtcbiAgICB0aGlzLmJ1aWxkZXIub3JXaGVyZVJhdyhgJHtjb2x1bW5FeHByfSAmQH4gJHtwZ3Jvb25nYUNvbmRpdGlvbn1gLCBbYXJnc1sxXV0pO1xuXG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICAvLyBXSEVSRSBGVUxMVEVYVFxuICB3aGVyZVRzU2VhcmNoPFRDb2x1bW4gZXh0ZW5kcyBBdmFpbGFibGVDb2x1bW5zPFRUYWJsZXM+IHwgU3FsRXhwcmVzc2lvbjxcInN0cmluZ1wiPj4oXG4gICAgY29sdW1uOiBUQ29sdW1uLFxuICAgIHZhbHVlOiBzdHJpbmcsXG4gICAgb3B0aW9ucz86IFRzUXVlcnlPcHRpb25zIHwgVHNRdWVyeUNvbmZpZyxcbiAgKTogdGhpcztcbiAgd2hlcmVUc1NlYXJjaCguLi5hcmdzOiBhbnlbXSk6IHRoaXMge1xuICAgIGNvbnN0IG9wdHMgPVxuICAgICAgLy8gU0FGRVRZOiDsv7zrpqwg67mM642U7J2YIOygnOuEpOumrSDqs4Tslb3qs7wg7ISg7ZaJIOqygOymneydtCDsnbQg7YOA7J6F7J2EIOuztOyepe2VqeuLiOuLpC5cbiAgICAgIGlzU3RyaW5nVmFsdWUoYXJnc1syXSkgPyAoeyBjb25maWc6IGFyZ3NbMl0gfSBhcyBUc1F1ZXJ5T3B0aW9ucykgOiAoYXJnc1syXSA/PyB7fSk7XG5cbiAgICBjb25zdCBwYXJzZXIgPSBvcHRzLnBhcnNlciA/PyBcIndlYnNlYXJjaF90b190c3F1ZXJ5XCI7XG4gICAgY29uc3QgY29uZmlnID0gb3B0cy5jb25maWcgPz8gXCJzaW1wbGVcIjtcbiAgICBjb25zdCBjb2x1bW5FeHByID0gaXNTcWxFeHByZXNzaW9uKGFyZ3NbMF0pID8gYXJnc1swXVtcIl9zcWxcIl0gOiBTdHJpbmcoYXJnc1swXSk7XG5cbiAgICB0aGlzLmJ1aWxkZXIud2hlcmVSYXcoYCR7Y29sdW1uRXhwcn0gQEAgJHtwYXJzZXJ9KD8sID8pYCwgW2NvbmZpZywgYXJnc1sxXV0pO1xuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgb3JXaGVyZVRzU2VhcmNoPFRDb2x1bW4gZXh0ZW5kcyBBdmFpbGFibGVDb2x1bW5zPFRUYWJsZXM+IHwgU3FsRXhwcmVzc2lvbjxcInN0cmluZ1wiPj4oXG4gICAgY29sdW1uOiBUQ29sdW1uLFxuICAgIHZhbHVlOiBzdHJpbmcsXG4gICAgb3B0aW9ucz86IFRzUXVlcnlPcHRpb25zIHwgVHNRdWVyeUNvbmZpZyxcbiAgKTogdGhpcztcbiAgb3JXaGVyZVRzU2VhcmNoKC4uLmFyZ3M6IGFueVtdKTogdGhpcyB7XG4gICAgY29uc3Qgb3B0cyA9XG4gICAgICAvLyBTQUZFVFk6IOy/vOumrCDruYzrjZTsnZgg7KCc64Sk66atIOqzhOyVveqzvCDshKDtlokg6rKA7Kad7J20IOydtCDtg4DsnoXsnYQg67O07J6l7ZWp64uI64ukLlxuICAgICAgaXNTdHJpbmdWYWx1ZShhcmdzWzJdKSA/ICh7IGNvbmZpZzogYXJnc1syXSB9IGFzIFRzUXVlcnlPcHRpb25zKSA6IChhcmdzWzJdID8/IHt9KTtcblxuICAgIGNvbnN0IHBhcnNlciA9IG9wdHMucGFyc2VyID8/IFwid2Vic2VhcmNoX3RvX3RzcXVlcnlcIjtcbiAgICBjb25zdCBjb25maWcgPSBvcHRzLmNvbmZpZyA/PyBcInNpbXBsZVwiO1xuICAgIGNvbnN0IGNvbHVtbkV4cHIgPSBpc1NxbEV4cHJlc3Npb24oYXJnc1swXSkgPyBhcmdzWzBdW1wiX3NxbFwiXSA6IFN0cmluZyhhcmdzWzBdKTtcblxuICAgIHRoaXMuYnVpbGRlci5vcldoZXJlUmF3KGAke2NvbHVtbkV4cHJ9IEBAICR7cGFyc2VyfSg/LCA/KWAsIFtjb25maWcsIGFyZ3NbMV1dKTtcbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIHdoZXJlRnV6enk8VENvbHVtbiBleHRlbmRzIEF2YWlsYWJsZUNvbHVtbnM8VFRhYmxlcz4gfCBTcWxFeHByZXNzaW9uPFwic3RyaW5nXCI+PihcbiAgICBjb2x1bW46IFRDb2x1bW4sXG4gICAgdmFsdWU6IHN0cmluZyxcbiAgICBvcHRpb25zPzoge1xuICAgICAgb3BlcmF0b3I/OiBGdXp6eU9wZXJhdG9yO1xuICAgIH0sXG4gICk6IHRoaXM7XG4gIHdoZXJlRnV6enkoLi4uYXJnczogYW55W10pOiB0aGlzIHtcbiAgICBjb25zdCBvcGVyYXRvciA9IHBhcnNlRnV6enlPcGVyYXRvcihhcmdzWzJdPy5vcGVyYXRvcik7XG5cbiAgICBpZiAob3BlcmF0b3IgPT09IFwiJVwiKSB7XG4gICAgICBpZiAoaXNTcWxFeHByZXNzaW9uKGFyZ3NbMF0pKSB7XG4gICAgICAgIHRoaXMuYnVpbGRlci53aGVyZVJhdyhgJHthcmdzWzBdW1wiX3NxbFwiXX0gJHtvcGVyYXRvcn0gP2AsIFsuLi5hcmdzWzBdW1wiX3BhcmFtc1wiXSwgYXJnc1sxXV0pO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgdGhpcy5idWlsZGVyLndoZXJlUmF3KGA/PyAke29wZXJhdG9yfSA/YCwgW2FyZ3NbMF0sIGFyZ3NbMV1dKTtcbiAgICAgIH1cbiAgICAgIHJldHVybiB0aGlzO1xuICAgIH1cblxuICAgIGlmIChpc1NxbEV4cHJlc3Npb24oYXJnc1swXSkpIHtcbiAgICAgIHRoaXMuYnVpbGRlci53aGVyZVJhdyhgPyAke29wZXJhdG9yfSAke2FyZ3NbMF1bXCJfc3FsXCJdfWAsIFthcmdzWzFdLCAuLi5hcmdzWzBdW1wiX3BhcmFtc1wiXV0pO1xuICAgIH0gZWxzZSB7XG4gICAgICB0aGlzLmJ1aWxkZXIud2hlcmVSYXcoYD8gJHtvcGVyYXRvcn0gPz9gLCBbYXJnc1sxXSwgYXJnc1swXV0pO1xuICAgIH1cbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIG9yV2hlcmVGdXp6eTxUQ29sdW1uIGV4dGVuZHMgQXZhaWxhYmxlQ29sdW1uczxUVGFibGVzPiB8IFNxbEV4cHJlc3Npb248XCJzdHJpbmdcIj4+KFxuICAgIGNvbHVtbjogVENvbHVtbixcbiAgICB2YWx1ZTogc3RyaW5nLFxuICAgIG9wdGlvbnM/OiB7XG4gICAgICBvcGVyYXRvcj86IEZ1enp5T3BlcmF0b3I7XG4gICAgfSxcbiAgKTogdGhpcztcbiAgb3JXaGVyZUZ1enp5KC4uLmFyZ3M6IGFueVtdKTogdGhpcyB7XG4gICAgY29uc3Qgb3BlcmF0b3IgPSBwYXJzZUZ1enp5T3BlcmF0b3IoYXJnc1syXT8ub3BlcmF0b3IpO1xuXG4gICAgaWYgKG9wZXJhdG9yID09PSBcIiVcIikge1xuICAgICAgaWYgKGlzU3FsRXhwcmVzc2lvbihhcmdzWzBdKSkge1xuICAgICAgICB0aGlzLmJ1aWxkZXIub3JXaGVyZVJhdyhgJHthcmdzWzBdW1wiX3NxbFwiXX0gJHtvcGVyYXRvcn0gP2AsIFtcbiAgICAgICAgICAuLi5hcmdzWzBdW1wiX3BhcmFtc1wiXSxcbiAgICAgICAgICBhcmdzWzFdLFxuICAgICAgICBdKTtcbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIHRoaXMuYnVpbGRlci5vcldoZXJlUmF3KGA/PyAke29wZXJhdG9yfSA/YCwgW2FyZ3NbMF0sIGFyZ3NbMV1dKTtcbiAgICAgIH1cbiAgICAgIHJldHVybiB0aGlzO1xuICAgIH1cblxuICAgIGlmIChpc1NxbEV4cHJlc3Npb24oYXJnc1swXSkpIHtcbiAgICAgIHRoaXMuYnVpbGRlci5vcldoZXJlUmF3KGA/ICR7b3BlcmF0b3J9ICR7YXJnc1swXVtcIl9zcWxcIl19YCwgW2FyZ3NbMV0sIC4uLmFyZ3NbMF1bXCJfcGFyYW1zXCJdXSk7XG4gICAgfSBlbHNlIHtcbiAgICAgIHRoaXMuYnVpbGRlci5vcldoZXJlUmF3KGA/ICR7b3BlcmF0b3J9ID8/YCwgW2FyZ3NbMV0sIGFyZ3NbMF1dKTtcbiAgICB9XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICAvLyDspJHssqkg6re466O5XG4gIHdoZXJlR3JvdXAoY2FsbGJhY2s6IChnOiBXaGVyZUdyb3VwPFRUYWJsZXM+KSA9PiB2b2lkKTogdGhpcztcbiAgd2hlcmVHcm91cChjYWxsYmFjazogKGc6IFdoZXJlR3JvdXA8VFRhYmxlcz4pID0+IHZvaWQpOiBXaGVyZUdyb3VwPFRUYWJsZXM+IHtcbiAgICB0aGlzLmJ1aWxkZXIud2hlcmUoKHN1YkJ1aWxkZXIpID0+IHtcbiAgICAgIGNvbnN0IHN1Ykdyb3VwID0gbmV3IFdoZXJlR3JvdXA8VFRhYmxlcz4oc3ViQnVpbGRlcik7XG4gICAgICBjYWxsYmFjayhzdWJHcm91cCk7XG4gICAgfSk7XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cbiAgb3JXaGVyZUdyb3VwKGNhbGxiYWNrOiAoZzogV2hlcmVHcm91cDxUVGFibGVzPikgPT4gdm9pZCk6IHRoaXM7XG4gIG9yV2hlcmVHcm91cChjYWxsYmFjazogKGc6IFdoZXJlR3JvdXA8VFRhYmxlcz4pID0+IHZvaWQpOiBXaGVyZUdyb3VwPFRUYWJsZXM+IHtcbiAgICB0aGlzLmJ1aWxkZXIub3JXaGVyZSgoc3ViQnVpbGRlcikgPT4ge1xuICAgICAgY29uc3Qgc3ViR3JvdXAgPSBuZXcgV2hlcmVHcm91cDxUVGFibGVzPihzdWJCdWlsZGVyKTtcbiAgICAgIGNhbGxiYWNrKHN1Ykdyb3VwKTtcbiAgICB9KTtcbiAgICByZXR1cm4gdGhpcztcbiAgfVxufVxuXG4vLyBKT0lOIOygiCDqt7jro7nsl5DripQgTGVmdOyZgCBSaWdodOyXkCDrjIDtlZwg7Iic7ISc6rCAIO2VhOyalO2VmOyngCDslYrsnLzrr4DroZwsIOuqqOuToCDqsr3smrDsnZgg7IiY66W8IOqzhOyCsO2VtOyVvO2VqC5cbmV4cG9ydCBjbGFzcyBKb2luQ2xhdXNlR3JvdXA8VExlZnQgZXh0ZW5kcyBvYmplY3QsIFRSaWdodCBleHRlbmRzIG9iamVjdD4ge1xuICBjb25zdHJ1Y3Rvcihwcml2YXRlIGNhbGxiYWNrOiBLbmV4LkpvaW5DbGF1c2UpIHt9XG5cbiAgLy8gT04oQU5EKTog7Lus65+8ID0g7Lus65+8XG4gIG9uKGxlZnQ6IEF2YWlsYWJsZUNvbHVtbnM8VExlZnQ+LCByaWdodDogQXZhaWxhYmxlQ29sdW1uczxUUmlnaHQ+KTogdGhpcztcbiAgb24obGVmdDogQXZhaWxhYmxlQ29sdW1uczxUUmlnaHQ+LCByaWdodDogQXZhaWxhYmxlQ29sdW1uczxUTGVmdD4pOiB0aGlzO1xuICAvLyBPTihBTkQpOiDsu6zrn7wgPSDqsJJcbiAgb24oXG4gICAgbGVmdDogQXZhaWxhYmxlQ29sdW1uczxUTGVmdD4sXG4gICAgcmlnaHQ6IEV4dHJhY3RDb2x1bW5UeXBlPFRMZWZ0LCBBdmFpbGFibGVDb2x1bW5zPFRMZWZ0PiAmIHN0cmluZz4sXG4gICk6IHRoaXM7XG4gIG9uKFxuICAgIGxlZnQ6IEF2YWlsYWJsZUNvbHVtbnM8VFJpZ2h0PixcbiAgICByaWdodDogRXh0cmFjdENvbHVtblR5cGU8VFJpZ2h0LCBBdmFpbGFibGVDb2x1bW5zPFRSaWdodD4gJiBzdHJpbmc+LFxuICApOiB0aGlzO1xuICAvLyBPTihBTkQpOiDsu6zrn7wgKOyXsOyCsOyekCkg7Lus65+8XG4gIG9uKFxuICAgIGxlZnQ6IEF2YWlsYWJsZUNvbHVtbnM8VExlZnQ+LFxuICAgIG9wZXJhdG9yOiBDb21wYXJpc29uT3BlcmF0b3IsXG4gICAgcmlnaHQ6IEF2YWlsYWJsZUNvbHVtbnM8VFJpZ2h0PixcbiAgKTogdGhpcztcbiAgb24oXG4gICAgbGVmdDogQXZhaWxhYmxlQ29sdW1uczxUUmlnaHQ+LFxuICAgIG9wZXJhdG9yOiBDb21wYXJpc29uT3BlcmF0b3IsXG4gICAgcmlnaHQ6IEF2YWlsYWJsZUNvbHVtbnM8VExlZnQ+LFxuICApOiB0aGlzO1xuICAvLyBPTihBTkQpOiDsu6zrn7wgKOyXsOyCsOyekCkg6rCSXG4gIG9uKFxuICAgIGxlZnQ6IEF2YWlsYWJsZUNvbHVtbnM8VExlZnQ+LFxuICAgIG9wZXJhdG9yOiBDb21wYXJpc29uT3BlcmF0b3IsXG4gICAgcmlnaHQ6IEV4dHJhY3RDb2x1bW5UeXBlPFRMZWZ0LCBBdmFpbGFibGVDb2x1bW5zPFRMZWZ0PiAmIHN0cmluZz4sXG4gICk6IHRoaXM7XG4gIG9uKFxuICAgIGxlZnQ6IEF2YWlsYWJsZUNvbHVtbnM8VFJpZ2h0PixcbiAgICBvcGVyYXRvcjogQ29tcGFyaXNvbk9wZXJhdG9yLFxuICAgIHJpZ2h0OiBFeHRyYWN0Q29sdW1uVHlwZTxUUmlnaHQsIEF2YWlsYWJsZUNvbHVtbnM8VFJpZ2h0PiAmIHN0cmluZz4sXG4gICk6IHRoaXM7XG4gIC8vIE9OKEFORCk6IOy9nOuwsVxuICBvbihjYWxsYmFjazogKG5lc3RlZDogSm9pbkNsYXVzZUdyb3VwPFRMZWZ0LCBUUmlnaHQ+KSA9PiB2b2lkKTogdGhpcztcbiAgb24oY2FsbGJhY2s6IChuZXN0ZWQ6IEpvaW5DbGF1c2VHcm91cDxUUmlnaHQsIFRMZWZ0PikgPT4gdm9pZCk6IHRoaXM7XG4gIC8vIE9OKEFORCkg6rWs7ZiEXG4gIG9uKC4uLmFyZ3M6IGFueVtdKTogdGhpcyB7XG4gICAgLy8gU0FGRVRZOiDsv7zrpqwg67mM642U7J2YIOygnOuEpOumrSDqs4Tslb3qs7wg7ISg7ZaJIOqygOymneydtCDsnbQg7YOA7J6F7J2EIOuztOyepe2VqeuLiOuLpC5cbiAgICB0aGlzLmNhbGxiYWNrLm9uKC4uLihhcmdzIGFzIFtzdHJpbmcsIHN0cmluZ10pKTtcbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIC8vIE9OKE9SKTog7Lus65+8ID0g7Lus65+8XG4gIG9yT24obGVmdDogQXZhaWxhYmxlQ29sdW1uczxUTGVmdD4sIHJpZ2h0OiBBdmFpbGFibGVDb2x1bW5zPFRSaWdodD4pOiB0aGlzO1xuICBvck9uKGxlZnQ6IEF2YWlsYWJsZUNvbHVtbnM8VFJpZ2h0PiwgcmlnaHQ6IEF2YWlsYWJsZUNvbHVtbnM8VExlZnQ+KTogdGhpcztcbiAgLy8gT04oT1IpOiDsu6zrn7wgPSDqsJJcbiAgb3JPbihcbiAgICBsZWZ0OiBBdmFpbGFibGVDb2x1bW5zPFRMZWZ0PixcbiAgICByaWdodDogRXh0cmFjdENvbHVtblR5cGU8VExlZnQsIEF2YWlsYWJsZUNvbHVtbnM8VExlZnQ+ICYgc3RyaW5nPixcbiAgKTogdGhpcztcbiAgb3JPbihcbiAgICBsZWZ0OiBBdmFpbGFibGVDb2x1bW5zPFRSaWdodD4sXG4gICAgcmlnaHQ6IEV4dHJhY3RDb2x1bW5UeXBlPFRSaWdodCwgQXZhaWxhYmxlQ29sdW1uczxUUmlnaHQ+ICYgc3RyaW5nPixcbiAgKTogdGhpcztcbiAgLy8gT04oT1IpOiDsu6zrn7wgKOyXsOyCsOyekCkg7Lus65+8XG4gIG9yT24oXG4gICAgbGVmdDogQXZhaWxhYmxlQ29sdW1uczxUTGVmdD4sXG4gICAgb3BlcmF0b3I6IENvbXBhcmlzb25PcGVyYXRvcixcbiAgICByaWdodDogQXZhaWxhYmxlQ29sdW1uczxUUmlnaHQ+LFxuICApOiB0aGlzO1xuICBvck9uKFxuICAgIGxlZnQ6IEF2YWlsYWJsZUNvbHVtbnM8VFJpZ2h0PixcbiAgICBvcGVyYXRvcjogQ29tcGFyaXNvbk9wZXJhdG9yLFxuICAgIHJpZ2h0OiBBdmFpbGFibGVDb2x1bW5zPFRMZWZ0PixcbiAgKTogdGhpcztcbiAgLy8gT04oT1IpOiDsu6zrn7wgKOyXsOyCsOyekCkg6rCSXG4gIG9yT24oXG4gICAgbGVmdDogQXZhaWxhYmxlQ29sdW1uczxUTGVmdD4sXG4gICAgb3BlcmF0b3I6IENvbXBhcmlzb25PcGVyYXRvcixcbiAgICByaWdodDogRXh0cmFjdENvbHVtblR5cGU8VExlZnQsIEF2YWlsYWJsZUNvbHVtbnM8VExlZnQ+ICYgc3RyaW5nPixcbiAgKTogdGhpcztcbiAgb3JPbihcbiAgICBsZWZ0OiBBdmFpbGFibGVDb2x1bW5zPFRSaWdodD4sXG4gICAgb3BlcmF0b3I6IENvbXBhcmlzb25PcGVyYXRvcixcbiAgICByaWdodDogRXh0cmFjdENvbHVtblR5cGU8VFJpZ2h0LCBBdmFpbGFibGVDb2x1bW5zPFRSaWdodD4gJiBzdHJpbmc+LFxuICApOiB0aGlzO1xuICAvLyBPTihPUik6IOy9nOuwsVxuICBvck9uKGNhbGxiYWNrOiAobmVzdGVkOiBKb2luQ2xhdXNlR3JvdXA8VExlZnQsIFRSaWdodD4pID0+IHZvaWQpOiB0aGlzO1xuICBvck9uKGNhbGxiYWNrOiAobmVzdGVkOiBKb2luQ2xhdXNlR3JvdXA8VFJpZ2h0LCBUTGVmdD4pID0+IHZvaWQpOiB0aGlzO1xuICAvLyBPTihPUikg6rWs7ZiEXG4gIG9yT24oLi4uYXJnczogYW55W10pOiB0aGlzIHtcbiAgICAvLyBTQUZFVFk6IOy/vOumrCDruYzrjZTsnZgg7KCc64Sk66atIOqzhOyVveqzvCDshKDtlokg6rKA7Kad7J20IOydtCDtg4DsnoXsnYQg67O07J6l7ZWp64uI64ukLlxuICAgIHRoaXMuY2FsbGJhY2sub3JPbiguLi4oYXJncyBhcyBbc3RyaW5nLCBzdHJpbmddKSk7XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICAvLyBPTiBWQUwoQU5EKTog7Lus65+8ID0g6rCSICjqsJLsnYQg7Lus65+8IOywuOyhsOqwgCDslYTri4wg7YyM652866+47YSw66GcIOuwlOyduOuUqSlcbiAgb25WYWwoY29sdW1uOiBBdmFpbGFibGVDb2x1bW5zPFRMZWZ0PiwgdmFsdWU6IGFueSk6IHRoaXM7XG4gIG9uVmFsKGNvbHVtbjogQXZhaWxhYmxlQ29sdW1uczxUUmlnaHQ+LCB2YWx1ZTogYW55KTogdGhpcztcbiAgb25WYWwoY29sdW1uOiBBdmFpbGFibGVDb2x1bW5zPFRMZWZ0Piwgb3BlcmF0b3I6IENvbXBhcmlzb25PcGVyYXRvciwgdmFsdWU6IGFueSk6IHRoaXM7XG4gIG9uVmFsKGNvbHVtbjogQXZhaWxhYmxlQ29sdW1uczxUUmlnaHQ+LCBvcGVyYXRvcjogQ29tcGFyaXNvbk9wZXJhdG9yLCB2YWx1ZTogYW55KTogdGhpcztcbiAgb25WYWwoLi4uYXJnczogYW55W10pOiB0aGlzIHtcbiAgICAvLyBTQUZFVFk6IOy/vOumrCDruYzrjZTsnZgg7KCc64Sk66atIOqzhOyVveqzvCDshKDtlokg6rKA7Kad7J20IOydtCDtg4DsnoXsnYQg67O07J6l7ZWp64uI64ukLlxuICAgICh0aGlzLmNhbGxiYWNrIGFzIGFueSkub25WYWwoLi4uYXJncyk7XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICAvLyBBTkQgT04gVkFMOiBvblZhbOydmCDrqoXsi5zsoIEgYWxpYXMgKEtuZXgg7Zi47ZmYKVxuICBhbmRPblZhbChjb2x1bW46IEF2YWlsYWJsZUNvbHVtbnM8VExlZnQ+LCB2YWx1ZTogYW55KTogdGhpcztcbiAgYW5kT25WYWwoY29sdW1uOiBBdmFpbGFibGVDb2x1bW5zPFRSaWdodD4sIHZhbHVlOiBhbnkpOiB0aGlzO1xuICBhbmRPblZhbChjb2x1bW46IEF2YWlsYWJsZUNvbHVtbnM8VExlZnQ+LCBvcGVyYXRvcjogQ29tcGFyaXNvbk9wZXJhdG9yLCB2YWx1ZTogYW55KTogdGhpcztcbiAgYW5kT25WYWwoY29sdW1uOiBBdmFpbGFibGVDb2x1bW5zPFRSaWdodD4sIG9wZXJhdG9yOiBDb21wYXJpc29uT3BlcmF0b3IsIHZhbHVlOiBhbnkpOiB0aGlzO1xuICBhbmRPblZhbCguLi5hcmdzOiBhbnlbXSk6IHRoaXMge1xuICAgIC8vIFNBRkVUWTog7L+866asIOu5jOuNlOydmCDsoJzrhKTrpq0g6rOE7JW96rO8IOyEoO2WiSDqsoDspp3snbQg7J20IO2DgOyeheydhCDrs7TsnqXtlanri4jri6QuXG4gICAgKHRoaXMuY2FsbGJhY2sgYXMgYW55KS5hbmRPblZhbCguLi5hcmdzKTtcbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIC8vIE9SIE9OIFZBTDogT1Ig7KGw6rG07Jy866GcIOqwkiDrsJTsnbjrlKlcbiAgb3JPblZhbChjb2x1bW46IEF2YWlsYWJsZUNvbHVtbnM8VExlZnQ+LCB2YWx1ZTogYW55KTogdGhpcztcbiAgb3JPblZhbChjb2x1bW46IEF2YWlsYWJsZUNvbHVtbnM8VFJpZ2h0PiwgdmFsdWU6IGFueSk6IHRoaXM7XG4gIG9yT25WYWwoY29sdW1uOiBBdmFpbGFibGVDb2x1bW5zPFRMZWZ0Piwgb3BlcmF0b3I6IENvbXBhcmlzb25PcGVyYXRvciwgdmFsdWU6IGFueSk6IHRoaXM7XG4gIG9yT25WYWwoY29sdW1uOiBBdmFpbGFibGVDb2x1bW5zPFRSaWdodD4sIG9wZXJhdG9yOiBDb21wYXJpc29uT3BlcmF0b3IsIHZhbHVlOiBhbnkpOiB0aGlzO1xuICBvck9uVmFsKC4uLmFyZ3M6IGFueVtdKTogdGhpcyB7XG4gICAgLy8gU0FGRVRZOiDsv7zrpqwg67mM642U7J2YIOygnOuEpOumrSDqs4Tslb3qs7wg7ISg7ZaJIOqygOymneydtCDsnbQg7YOA7J6F7J2EIOuztOyepe2VqeuLiOuLpC5cbiAgICAodGhpcy5jYWxsYmFjayBhcyBhbnkpLm9yT25WYWwoLi4uYXJncyk7XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cbn1cblxuLypcbiAgVFJlc29sdmVkOiDsv7zrpqwg7Iuk7ZaJIO2bhCDrsJjtmZjrkKAg6rKw6rO8IO2DgOyehVxuICBUUmV0dXJuaW5nOiBSRVRVUk5JTkcg7KCI7JeQIOyCrOyaqeuQoCDtg4DsnoVcbiovXG5leHBvcnQgY2xhc3MgUmVzb2x2ZWRQdXJpPFRSZXNvbHZlZCwgVFJldHVybmluZz4gaW1wbGVtZW50cyBQcm9taXNlPFRSZXNvbHZlZD4ge1xuICBjb25zdHJ1Y3RvcihcbiAgICBwdWJsaWMga25leFF1ZXJ5OiBLbmV4LlF1ZXJ5QnVpbGRlcixcbiAgICBwcml2YXRlIGtuZXg6IEtuZXgsXG4gICAgcHJpdmF0ZSB0YWJsZVNwZWM6IFRhYmxlU3BlYyB8IG51bGwgPSBudWxsLFxuICApIHt9XG5cbiAgW1N5bWJvbC50b1N0cmluZ1RhZ106IHN0cmluZyA9IFwiUHJvbWlzZVwiO1xuXG4gIHRvUXVlcnkoKTogc3RyaW5nIHtcbiAgICByZXR1cm4gdGhpcy5rbmV4UXVlcnkudG9RdWVyeSgpO1xuICB9XG5cbiAgZGVidWcoKTogdGhpcyB7XG4gICAgY29uc29sZS5sb2coYCR7Y2hhbGsuY3lhbihcIltQdXJpIERlYnVnXVwiKX0gJHtjaGFsay55ZWxsb3codGhpcy50b1F1ZXJ5KCkpfWApO1xuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgdGhlbjxUUmVzdWx0MSA9IFRSZXNvbHZlZCwgVFJlc3VsdDIgPSBuZXZlcj4oXG4gICAgb25mdWxmaWxsZWQ/OiAoKHZhbHVlOiBUUmVzb2x2ZWQpID0+IFRSZXN1bHQxIHwgUHJvbWlzZUxpa2U8VFJlc3VsdDE+KSB8IG51bGwsXG4gICAgb25yZWplY3RlZD86ICgocmVhc29uOiBhbnkpID0+IFRSZXN1bHQyIHwgUHJvbWlzZUxpa2U8VFJlc3VsdDI+KSB8IG51bGwsXG4gICk6IFByb21pc2U8VFJlc3VsdDEgfCBUUmVzdWx0Mj4ge1xuICAgIE5haXRlLnQoXCJwdXJpOmV4ZWN1dGVkLXF1ZXJ5XCIsIHRoaXMudG9RdWVyeSgpKTtcbiAgICAvLyBTQUZFVFk6IOy/vOumrCDruYzrjZTsnZgg7KCc64Sk66atIOqzhOyVveqzvCDshKDtlokg6rKA7Kad7J20IOydtCDtg4DsnoXsnYQg67O07J6l7ZWp64uI64ukLlxuICAgIHJldHVybiB0aGlzLmtuZXhRdWVyeS50aGVuKG9uZnVsZmlsbGVkIGFzIGFueSwgb25yZWplY3RlZCk7XG4gIH1cblxuICBjYXRjaDxUUmVzdWx0MiA9IG5ldmVyPihcbiAgICBvbnJlamVjdGVkPzogKChyZWFzb246IGFueSkgPT4gVFJlc3VsdDIgfCBQcm9taXNlTGlrZTxUUmVzdWx0Mj4pIHwgbnVsbCxcbiAgKTogUHJvbWlzZTxUUmVzb2x2ZWQgfCBUUmVzdWx0Mj4ge1xuICAgIHJldHVybiB0aGlzLmtuZXhRdWVyeS5jYXRjaChvbnJlamVjdGVkKTtcbiAgfVxuXG4gIGZpbmFsbHkob25maW5hbGx5PzogKCgpID0+IHZvaWQpIHwgbnVsbCk6IFByb21pc2U8VFJlc29sdmVkPiB7XG4gICAgcmV0dXJuIHRoaXMua25leFF1ZXJ5LmZpbmFsbHkob25maW5hbGx5KTtcbiAgfVxuXG4gIC8vIE9OIENPTkZMSUNUIC0g7Lus65+8IOq4sOuwmFxuICBvbkNvbmZsaWN0PFRUYWJsZXMgZXh0ZW5kcyBSZWNvcmQ8c3RyaW5nLCBUUmV0dXJuaW5nPj4oXG4gICAgY29sdW1uczogc3RyaW5nIHwgc3RyaW5nW10sXG4gICAgYWN0aW9uPzogT25Db25mbGljdEFjdGlvbjxUVGFibGVzPixcbiAgKTogdGhpcyB7XG4gICAgY29uc3QgdGFyZ2V0ID0gQXJyYXkuaXNBcnJheShjb2x1bW5zKSA/IGNvbHVtbnMgOiBbY29sdW1uc107XG5cbiAgICBpZiAoIWFjdGlvbiB8fCBhY3Rpb24gPT09IFwibm90aGluZ1wiKSB7XG4gICAgICAvLyBETyBOT1RISU5HXG4gICAgICB0aGlzLmtuZXhRdWVyeS5vbkNvbmZsaWN0KHRhcmdldCkuaWdub3JlKCk7XG4gICAgfSBlbHNlIHtcbiAgICAgIC8vIERPIFVQREFURVxuICAgICAgY29uc3QgeyB1cGRhdGUgfSA9IGFjdGlvbjtcblxuICAgICAgLy8gYWN0aW9uLnVwZGF0ZSDrsLDsl7Qg7ZiV7YOcIDogW1wibmFtZVwiLCBcImVtYWlsXCJdXG4gICAgICBpZiAoQXJyYXkuaXNBcnJheSh1cGRhdGUpKSB7XG4gICAgICAgIHRoaXMua25leFF1ZXJ5Lm9uQ29uZmxpY3QodGFyZ2V0KS5tZXJnZSh1cGRhdGUpO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgLy8gYWN0aW9uLnVwZGF0ZSDqsJ3ssrQg7ZiV7YOcOiB7IG5hbWU6IFwiSm9oblwiLCBjb3VudDogcmF3KC4uLikgfVxuICAgICAgICBjb25zdCBtZXJnZU9iaiA9IHt9O1xuXG4gICAgICAgIGZvciAoY29uc3QgW2tleSwgdmFsdWVdIG9mIE9iamVjdC5lbnRyaWVzKHVwZGF0ZSkpIHtcbiAgICAgICAgICBjb25zdCBtZXJnZWRWYWx1ZSA9IGlzU3FsRXhwcmVzc2lvbih2YWx1ZSlcbiAgICAgICAgICAgID8gdGhpcy5rbmV4LnJhdyh2YWx1ZVtcIl9zcWxcIl0pXG4gICAgICAgICAgICA6IHNlcmlhbGl6ZUpzb25Db2x1bW5WYWx1ZSh0aGlzLnRhYmxlU3BlYywga2V5LCB2YWx1ZSk7XG4gICAgICAgICAgT2JqZWN0LmFzc2lnbihtZXJnZU9iaiwgeyBba2V5XTogbWVyZ2VkVmFsdWUgfSk7XG4gICAgICAgIH1cblxuICAgICAgICB0aGlzLmtuZXhRdWVyeS5vbkNvbmZsaWN0KHRhcmdldCkubWVyZ2UobWVyZ2VPYmopO1xuICAgICAgfVxuICAgIH1cblxuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgLy8gUkVUVVJOSU5HOiBcIipcIiAtIOyghOyytCDsu6zrn7xcbiAgcmV0dXJuaW5nKGNvbHVtbjogXCIqXCIpOiBSZXNvbHZlZFB1cmk8VFJldHVybmluZ1tdLCBuZXZlcj47XG4gIC8vIFJFVFVSTklORzog64uo7J28IOy7rOufvFxuICByZXR1cm5pbmc8VENvbHVtbiBleHRlbmRzIENvbHVtbktleXM8VFJldHVybmluZz4+KFxuICAgIGNvbHVtbjogVENvbHVtbixcbiAgKTogUmVzb2x2ZWRQdXJpPFBpY2s8VFJldHVybmluZywgVENvbHVtbj5bXSwgbmV2ZXI+O1xuICAvLyBSRVRVUk5JTkc6IOuzteyImCDsu6zrn7wgKOuwsOyXtClcbiAgcmV0dXJuaW5nPFRDb2x1bW4gZXh0ZW5kcyBDb2x1bW5LZXlzPFRSZXR1cm5pbmc+PihcbiAgICBjb2x1bW5zOiBUQ29sdW1uW10sXG4gICk6IFJlc29sdmVkUHVyaTxQaWNrPFRSZXR1cm5pbmcsIFRDb2x1bW4+W10sIG5ldmVyPjtcbiAgLy8gUkVUVVJOSU5HIOq1rO2YhFxuICByZXR1cm5pbmcoY29sdW1uT3JDb2x1bW5zOiBzdHJpbmcgfCBzdHJpbmdbXSk6IFJlc29sdmVkUHVyaTxhbnlbXSwgbmV2ZXI+IHtcbiAgICB0aGlzLmtuZXhRdWVyeS5yZXR1cm5pbmcoY29sdW1uT3JDb2x1bW5zKTtcbiAgICByZXR1cm4gbmV3IFJlc29sdmVkUHVyaSh0aGlzLmtuZXhRdWVyeSwgdGhp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