@jax-data-science/sci-image-visualizer 0.8.2 → 0.9.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (525) hide show
  1. package/README.md +201 -460
  2. package/esm2022/index.mjs +28 -15
  3. package/esm2022/lib/channel-histogram/channel-histogram.component.mjs +163 -91
  4. package/esm2022/lib/contracts/capabilities.contract.mjs +4 -3
  5. package/esm2022/lib/contracts/cell-segmenter.contract.mjs +1 -1
  6. package/esm2022/lib/contracts/channel-histogram-api.contract.mjs +5 -1
  7. package/esm2022/lib/contracts/color.mjs +60 -0
  8. package/esm2022/lib/contracts/colormap-lut.mjs +213 -57
  9. package/esm2022/lib/contracts/coordinate-transform.contract.mjs +1 -1
  10. package/esm2022/lib/contracts/display-types.mjs +11 -1
  11. package/esm2022/lib/contracts/instance-segmenter.contract.mjs +1 -1
  12. package/esm2022/lib/contracts/intensity.mjs +48 -5
  13. package/esm2022/lib/contracts/plot-type-contribution.contract.mjs +1 -1
  14. package/esm2022/lib/contracts/plot-type.mjs +134 -17
  15. package/esm2022/lib/contracts/ports/image-state.port.mjs +4 -1
  16. package/esm2022/lib/contracts/ports/preferences.port.mjs +5 -1
  17. package/esm2022/lib/contracts/ports/region-io.port.mjs +2 -1
  18. package/esm2022/lib/contracts/ports/spatial-data.port.mjs +5 -1
  19. package/esm2022/lib/contracts/ports/tile-access.port.mjs +2 -1
  20. package/esm2022/lib/contracts/region-editor-api.contract.mjs +1 -1
  21. package/esm2022/lib/contracts/region-overlay.contract.mjs +1 -1
  22. package/esm2022/lib/contracts/sam.contract.mjs +1 -1
  23. package/esm2022/lib/contracts/semantic-segmenter.contract.mjs +1 -1
  24. package/esm2022/lib/contracts/spatial-dataset.contract.mjs +3 -1
  25. package/esm2022/lib/contracts/toolbar-tool.contract.mjs +6 -4
  26. package/esm2022/lib/contracts/visualizer.contract.mjs +1 -1
  27. package/esm2022/lib/contracts/viz-config.mjs +2 -1
  28. package/esm2022/lib/geometry/contour.mjs +63 -0
  29. package/esm2022/lib/geometry/raster.mjs +98 -0
  30. package/esm2022/lib/geometry/ring.mjs +201 -0
  31. package/esm2022/lib/hex-color-picker/hex-color-picker.component.mjs +202 -102
  32. package/esm2022/lib/implementations/base-store-visualizer.mjs +201 -48
  33. package/esm2022/lib/implementations/napari-js/napari-axes-gizmo.mjs +65 -0
  34. package/esm2022/lib/implementations/napari-js/napari-display-state.mjs +136 -0
  35. package/esm2022/lib/implementations/napari-js/napari-helpers.mjs +199 -0
  36. package/esm2022/lib/implementations/napari-js/napari-image-2d-scene.mjs +602 -0
  37. package/esm2022/lib/implementations/napari-js/napari-loading-badge.mjs +3 -4
  38. package/esm2022/lib/implementations/napari-js/napari-loading-state.mjs +66 -0
  39. package/esm2022/lib/implementations/napari-js/napari-region-overlay.mjs +157 -591
  40. package/esm2022/lib/implementations/napari-js/napari-scene.mjs +2 -0
  41. package/esm2022/lib/implementations/napari-js/napari-spatial-2d-scene.mjs +614 -0
  42. package/esm2022/lib/implementations/napari-js/napari-spatial-3d-scene.mjs +769 -0
  43. package/esm2022/lib/implementations/napari-js/napari-spatial-encoding.mjs +199 -0
  44. package/esm2022/lib/implementations/napari-js/napari-spatial-hover.mjs +263 -0
  45. package/esm2022/lib/implementations/napari-js/napari-spatial-scene.mjs +159 -0
  46. package/esm2022/lib/implementations/napari-js/napari-spatial-tiles.mjs +106 -1408
  47. package/esm2022/lib/implementations/napari-js/napari-spatial-tooltip.mjs +2 -2
  48. package/esm2022/lib/implementations/napari-js/napari-surface-scene.mjs +271 -0
  49. package/esm2022/lib/implementations/napari-js/napari-tile-client.mjs +562 -0
  50. package/esm2022/lib/implementations/napari-js/napari-tool-bridge.mjs +344 -0
  51. package/esm2022/lib/implementations/napari-js/napari-visualizer.service.mjs +361 -4184
  52. package/esm2022/lib/implementations/napari-js/napari-volume-scene.mjs +439 -0
  53. package/esm2022/lib/implementations/napari-js/napari-volume-z-handle.mjs +6 -6
  54. package/esm2022/lib/implementations/napari-js/region-overlay/overlay-projection.mjs +96 -0
  55. package/esm2022/lib/implementations/napari-js/region-overlay/region-edit.mjs +35 -0
  56. package/esm2022/lib/implementations/napari-js/region-overlay/region-svg-renderer.mjs +182 -0
  57. package/esm2022/lib/implementations/napari-js/spatial-tiles/categorical-lookup.mjs +30 -0
  58. package/esm2022/lib/implementations/napari-js/spatial-tiles/cell-layers.mjs +274 -0
  59. package/esm2022/lib/implementations/napari-js/spatial-tiles/density-layer.mjs +144 -0
  60. package/esm2022/lib/implementations/napari-js/spatial-tiles/layer-groups.mjs +165 -0
  61. package/esm2022/lib/implementations/napari-js/spatial-tiles/plan-context.mjs +78 -0
  62. package/esm2022/lib/implementations/napari-js/spatial-tiles/transcript-hover.mjs +182 -0
  63. package/esm2022/lib/implementations/napari-js/spatial-tiles/transcript-jobs.mjs +369 -0
  64. package/esm2022/lib/implementations/napari-js/spatial-tiles/transcript-layers.mjs +306 -0
  65. package/esm2022/lib/implementations/osd/display-pipeline.mjs +102 -40
  66. package/esm2022/lib/implementations/osd/histogram-sampler.mjs +56 -31
  67. package/esm2022/lib/implementations/osd/openseadragon-viewer-options.mjs +128 -0
  68. package/esm2022/lib/implementations/osd/openseadragon-visualizer.service.mjs +333 -1685
  69. package/esm2022/lib/implementations/osd/osd-coordinate-transform.mjs +1 -1
  70. package/esm2022/lib/implementations/osd/osd-coords.mjs +5 -6
  71. package/esm2022/lib/implementations/osd/osd-export.mjs +122 -0
  72. package/esm2022/lib/implementations/osd/osd-lib.mjs +15 -1
  73. package/esm2022/lib/implementations/osd/osd-navigator-chrome.mjs +205 -0
  74. package/esm2022/lib/implementations/osd/osd-pixel-readback.mjs +68 -0
  75. package/esm2022/lib/implementations/osd/osd-region-overlay-draw.mjs +153 -0
  76. package/esm2022/lib/implementations/osd/osd-region-overlay.mjs +185 -718
  77. package/esm2022/lib/implementations/osd/osd-scale-bar.mjs +52 -60
  78. package/esm2022/lib/implementations/osd/osd-tile-source.mjs +105 -0
  79. package/esm2022/lib/implementations/osd/osd-viewer-like.mjs +2 -0
  80. package/esm2022/lib/implementations/osd/osd-viewer-mount.mjs +44 -0
  81. package/esm2022/lib/implementations/osd/osd-viewport.mjs +184 -0
  82. package/esm2022/lib/implementations/osd/osd-zoom.mjs +7 -1
  83. package/esm2022/lib/implementations/osd/simple-source.mjs +395 -0
  84. package/esm2022/lib/implementations/osd/slice-cache.mjs +53 -48
  85. package/esm2022/lib/implementations/osd/tile-client.mjs +32 -11
  86. package/esm2022/lib/implementations/osd/tile-recolor.mjs +330 -0
  87. package/esm2022/lib/implementations/plotly/omics-trace-builders.mjs +161 -73
  88. package/esm2022/lib/implementations/plotly/plotly-coordinate-transform.mjs +1 -1
  89. package/esm2022/lib/implementations/plotly/plotly-image-loader.mjs +112 -0
  90. package/esm2022/lib/implementations/plotly/plotly-image-recolor.mjs +178 -0
  91. package/esm2022/lib/implementations/plotly/plotly-intensity-inset.mjs +33 -0
  92. package/esm2022/lib/implementations/plotly/plotly-isosurface-controls.mjs +83 -0
  93. package/esm2022/lib/implementations/plotly/plotly-layouts.mjs +121 -0
  94. package/esm2022/lib/implementations/plotly/plotly-readback.mjs +117 -0
  95. package/esm2022/lib/implementations/plotly/plotly-region-overlay.mjs +19 -10
  96. package/esm2022/lib/implementations/plotly/plotly-shape-projection.mjs +223 -0
  97. package/esm2022/lib/implementations/plotly/plotly-trace-builders.mjs +79 -19
  98. package/esm2022/lib/implementations/plotly/plotly-zoom-controller.mjs +223 -0
  99. package/esm2022/lib/implementations/plotly/plotly.service.mjs +439 -1655
  100. package/esm2022/lib/implementations/region-centroids.mjs +47 -0
  101. package/esm2022/lib/implementations/simple-slice-access.service.mjs +22 -12
  102. package/esm2022/lib/implementations/spatial-data-http/spatial-data-http.service.mjs +172 -92
  103. package/esm2022/lib/implementations/spatial-data-http/spatial-wire.mjs +103 -22
  104. package/esm2022/lib/implementations/tile-server/index.mjs +6 -0
  105. package/esm2022/lib/implementations/tile-server/native-histogram.mjs +30 -0
  106. package/esm2022/lib/implementations/tile-server/poll-descriptor.mjs +65 -0
  107. package/esm2022/lib/implementations/tile-server/tile-protocol.mjs +42 -0
  108. package/esm2022/lib/implementations/tile-server/transport.mjs +135 -0
  109. package/esm2022/lib/intensity/intensity-profile.mjs +107 -0
  110. package/esm2022/lib/intensity/intensity-profile.service.mjs +223 -0
  111. package/esm2022/lib/intensity-inset/intensity-inset.component.mjs +133 -0
  112. package/esm2022/lib/models/bezier.mjs +1 -11
  113. package/esm2022/lib/models/class-preset.mjs +41 -3
  114. package/esm2022/lib/models/geometry.mjs +27 -164
  115. package/esm2022/lib/models/polygon-edit.mjs +254 -0
  116. package/esm2022/lib/models/polygon-factory.mjs +118 -0
  117. package/esm2022/lib/models/region-clone.mjs +68 -0
  118. package/esm2022/lib/models/region-geojson.mjs +373 -0
  119. package/esm2022/lib/models/region.mjs +34 -33
  120. package/esm2022/lib/models/shape.mjs +18 -16
  121. package/esm2022/lib/plot-mode/contribution-host.mjs +297 -0
  122. package/esm2022/lib/plot-mode/plot-mode-controller.mjs +9 -6
  123. package/esm2022/lib/plot-mode/plot-type-menu.mjs +85 -0
  124. package/esm2022/lib/plot-mode/tool-params-model.mjs +87 -0
  125. package/esm2022/lib/plot.utilities.mjs +296 -473
  126. package/esm2022/lib/processing/image-crop.mjs +1 -1
  127. package/esm2022/lib/processing/processing-image.mjs +28 -15
  128. package/esm2022/lib/provide-visualization.mjs +40 -14
  129. package/esm2022/lib/region-editor/classes-panel/classes-panel.component.mjs +99 -0
  130. package/esm2022/lib/region-editor/file-stem.mjs +13 -0
  131. package/esm2022/lib/region-editor/manage-classes-dialog/manage-classes-dialog.component.mjs +118 -0
  132. package/esm2022/lib/region-editor/mask-export.service.mjs +98 -0
  133. package/esm2022/lib/region-editor/mask-raster.mjs +11 -5
  134. package/esm2022/lib/region-editor/region-color-dialog/region-color-dialog.component.mjs +56 -0
  135. package/esm2022/lib/region-editor/region-editor-help/region-editor-help.component.mjs +28 -0
  136. package/esm2022/lib/region-editor/region-editor.component.mjs +402 -651
  137. package/esm2022/lib/region-editor/region-metrics.mjs +68 -0
  138. package/esm2022/lib/region-editor/region-persistence.service.mjs +134 -0
  139. package/esm2022/lib/region-editor/region-table/region-table.component.mjs +153 -0
  140. package/esm2022/lib/region-editor/save-mask-dialog/save-mask-dialog.component.mjs +91 -0
  141. package/esm2022/lib/region-editor/save-regions-dialog/save-regions-dialog.component.mjs +92 -0
  142. package/esm2022/lib/region-ops.service.mjs +28 -70
  143. package/esm2022/lib/region-overlay/region-geometry.mjs +360 -0
  144. package/esm2022/lib/region-overlay/region-hit-test.mjs +103 -0
  145. package/esm2022/lib/region-overlay/svg-region-renderer.mjs +228 -0
  146. package/esm2022/lib/render-orchestrator.mjs +14 -11
  147. package/esm2022/lib/render-session.mjs +207 -0
  148. package/esm2022/lib/routing-visualizer.service.mjs +459 -411
  149. package/esm2022/lib/spatial/density-raster.mjs +14 -0
  150. package/esm2022/lib/spatial/embedding-compute-coordinator.mjs +239 -0
  151. package/esm2022/lib/spatial/embedding-compute.mjs +43 -10
  152. package/esm2022/lib/spatial/gene-search.mjs +1 -1
  153. package/esm2022/lib/spatial/glyphs.mjs +97 -0
  154. package/esm2022/lib/spatial/lod.mjs +187 -0
  155. package/esm2022/lib/spatial/spatial-controls.facade.mjs +200 -0
  156. package/esm2022/lib/spatial/spatial-density.mjs +25 -16
  157. package/esm2022/lib/spatial/spatial-encoding.mjs +26 -82
  158. package/esm2022/lib/spatial/spatial-expression.mjs +43 -42
  159. package/esm2022/lib/spatial/spatial-framing.mjs +1 -1
  160. package/esm2022/lib/spatial/spatial-heatmap.mjs +6 -3
  161. package/esm2022/lib/spatial/spatial-hover.mjs +5 -33
  162. package/esm2022/lib/spatial/spatial-panel-model.mjs +282 -0
  163. package/esm2022/lib/spatial/spatial-sections.mjs +1 -1
  164. package/esm2022/lib/spatial/spatial-selection.mjs +33 -46
  165. package/esm2022/lib/spatial/spatial-tile-merge.mjs +219 -0
  166. package/esm2022/lib/spatial/spatial-tiles.mjs +12 -648
  167. package/esm2022/lib/spatial/spatial-volume-image.mjs +2 -4
  168. package/esm2022/lib/spatial/stats.mjs +71 -0
  169. package/esm2022/lib/spatial/transcript-grouping.mjs +307 -0
  170. package/esm2022/lib/spatial-controls/spatial-cells-panel/spatial-cells-panel.component.mjs +150 -0
  171. package/esm2022/lib/spatial-controls/spatial-charts/chart-data-model.mjs +309 -0
  172. package/esm2022/lib/spatial-controls/spatial-charts/chart-help.mjs +145 -0
  173. package/esm2022/lib/spatial-controls/spatial-charts/plotly-chart-host.mjs +158 -0
  174. package/esm2022/lib/spatial-controls/spatial-charts/spatial-chart-window/spatial-chart-window.component.mjs +47 -0
  175. package/esm2022/lib/spatial-controls/spatial-charts/spatial-charts.component.mjs +297 -802
  176. package/esm2022/lib/spatial-controls/spatial-charts/spatial-embedding-controls/spatial-embedding-controls.component.mjs +89 -0
  177. package/esm2022/lib/spatial-controls/spatial-charts/spatial-heatmap-controls/spatial-heatmap-controls.component.mjs +52 -0
  178. package/esm2022/lib/spatial-controls/spatial-controls.component.mjs +143 -1238
  179. package/esm2022/lib/spatial-controls/spatial-gene-picker.mjs +153 -0
  180. package/esm2022/lib/spatial-controls/spatial-gene-tree/spatial-gene-tree.component.mjs +241 -0
  181. package/esm2022/lib/spatial-controls/spatial-groups-panel/spatial-groups-panel.component.mjs +193 -0
  182. package/esm2022/lib/spatial-controls/spatial-key/spatial-key.component.mjs +132 -0
  183. package/esm2022/lib/spatial-controls/spatial-key/spatial-key.model.mjs +67 -0
  184. package/esm2022/lib/spatial-controls/spatial-marker-genes-form/spatial-marker-genes-form.component.mjs +147 -0
  185. package/esm2022/lib/spatial-controls/spatial-observations-panel/spatial-observations-panel.component.mjs +300 -0
  186. package/esm2022/lib/spatial-controls/spatial-transcripts-panel/spatial-transcripts-panel.component.mjs +370 -0
  187. package/esm2022/lib/store/class-color.util.mjs +46 -3
  188. package/esm2022/lib/store/region-history.mjs +146 -0
  189. package/esm2022/lib/store/region-scope-cache.mjs +140 -0
  190. package/esm2022/lib/store/region-selection.mjs +82 -0
  191. package/esm2022/lib/store/region-store.service.mjs +279 -675
  192. package/esm2022/lib/store/spatial-selection.service.mjs +2 -2
  193. package/esm2022/lib/store/visualizer-store.service.mjs +49 -71
  194. package/esm2022/lib/toast-outlets.mjs +5 -4
  195. package/esm2022/lib/toolbar/brush/brush-tool.service.mjs +92 -434
  196. package/esm2022/lib/toolbar/canvas-tools.mjs +20 -0
  197. package/esm2022/lib/toolbar/crop/slide-crop.mjs +26 -42
  198. package/esm2022/lib/toolbar/plot-type-selector/plot-type-selector.component.mjs +85 -0
  199. package/esm2022/lib/toolbar/region-tools/region-tool-buttons.mjs +74 -0
  200. package/esm2022/lib/toolbar/region-tools/region-tools.component.mjs +114 -0
  201. package/esm2022/lib/toolbar/segmentation/cell-segment-tool.service.mjs +74 -78
  202. package/esm2022/lib/toolbar/segmentation/cellpose-segmenter.service.mjs +50 -8
  203. package/esm2022/lib/toolbar/segmentation/onnx-sam-session.mjs +61 -42
  204. package/esm2022/lib/toolbar/segmentation/pending-calls.mjs +47 -0
  205. package/esm2022/lib/toolbar/segmentation/sam-model-registry.mjs +12 -4
  206. package/esm2022/lib/toolbar/segmentation/sam-onnx-core.mjs +70 -14
  207. package/esm2022/lib/toolbar/segmentation/sam-point-tool.service.mjs +135 -172
  208. package/esm2022/lib/toolbar/segmentation/sam-prompt.mjs +9 -90
  209. package/esm2022/lib/toolbar/segmentation/sam-session.service.mjs +183 -0
  210. package/esm2022/lib/toolbar/segmentation/sam-tool.service.mjs +95 -150
  211. package/esm2022/lib/toolbar/segmentation/segmentation-commit.mjs +12 -0
  212. package/esm2022/lib/toolbar/segmentation/segmentation-runner.mjs +108 -0
  213. package/esm2022/lib/toolbar/segmentation-tools/segmentation-tools.component.mjs +155 -0
  214. package/esm2022/lib/toolbar/stack-controls/stack-controls.component.mjs +81 -0
  215. package/esm2022/lib/toolbar/tool-kit/async-tool-status.mjs +37 -0
  216. package/esm2022/lib/toolbar/tool-kit/canvas-tool-manager.mjs +63 -0
  217. package/esm2022/lib/toolbar/tool-kit/canvas-tool.mjs +2 -0
  218. package/esm2022/lib/toolbar/tool-kit/frame-pixels.mjs +108 -0
  219. package/esm2022/lib/toolbar/tool-kit/mask-stroke-editor.mjs +306 -0
  220. package/esm2022/lib/toolbar/tool-kit/matrix-frame.mjs +61 -0
  221. package/esm2022/lib/toolbar/tool-kit/tool-overlay.mjs +140 -0
  222. package/esm2022/lib/toolbar/tool-kit/undo-gesture.mjs +24 -0
  223. package/esm2022/lib/toolbar/tool-slider/tool-slider.component.mjs +63 -0
  224. package/esm2022/lib/toolbar/toolbar-help-dialog/toolbar-help-dialog.component.mjs +50 -0
  225. package/esm2022/lib/toolbar/toolbar.component.mjs +68 -117
  226. package/esm2022/lib/toolbar/vertex-eraser/vertex-eraser-tool.service.mjs +93 -115
  227. package/esm2022/lib/toolbar/view-controls/view-controls.component.mjs +107 -0
  228. package/esm2022/lib/toolbar/wand/wand-region-grow.mjs +321 -0
  229. package/esm2022/lib/toolbar/wand/wand-tool.service.mjs +121 -416
  230. package/esm2022/lib/toolbar/wand/wand.service.mjs +30 -894
  231. package/esm2022/lib/toolbar/zoom-to-box/zoom-to-box-tool.service.mjs +48 -90
  232. package/esm2022/lib/util/mark-for-check.mjs +17 -0
  233. package/esm2022/lib/util/supersede.mjs +56 -0
  234. package/esm2022/lib/visualization.module.mjs +39 -141
  235. package/esm2022/lib/visualizer/floating-drag.directive.mjs +58 -0
  236. package/esm2022/lib/visualizer/region-actions.mjs +149 -0
  237. package/esm2022/lib/visualizer/region-load.mjs +60 -0
  238. package/esm2022/lib/visualizer/spatial-dataset-binder.mjs +163 -0
  239. package/esm2022/lib/visualizer/tool-modes.mjs +113 -0
  240. package/esm2022/lib/visualizer/viewer-shortcuts.mjs +167 -0
  241. package/esm2022/lib/visualizer/visualizer-context-menu.mjs +119 -0
  242. package/esm2022/lib/visualizer.component.mjs +480 -1902
  243. package/esm2022/lib/workers/spatial-math-ops.mjs +43 -0
  244. package/esm2022/lib/workers/spatial-math-worker.mjs +10 -0
  245. package/esm2022/lib/workers/spatial-math.mjs +190 -0
  246. package/fesm2022/jax-data-science-sci-image-visualizer-jax-data-science-sci-image-visualizer-Csxlnq7I.mjs +41083 -0
  247. package/fesm2022/jax-data-science-sci-image-visualizer-jax-data-science-sci-image-visualizer-Csxlnq7I.mjs.map +1 -0
  248. package/fesm2022/jax-data-science-sci-image-visualizer-onnx-sam-session-Bkujqg7m.mjs +238 -0
  249. package/fesm2022/jax-data-science-sci-image-visualizer-onnx-sam-session-Bkujqg7m.mjs.map +1 -0
  250. package/fesm2022/jax-data-science-sci-image-visualizer-spatial-math-worker-BzVFFqGS.mjs +12 -0
  251. package/fesm2022/jax-data-science-sci-image-visualizer-spatial-math-worker-BzVFFqGS.mjs.map +1 -0
  252. package/fesm2022/jax-data-science-sci-image-visualizer.mjs +41 -34430
  253. package/fesm2022/jax-data-science-sci-image-visualizer.mjs.map +1 -1
  254. package/fesm2022/mask.worker.js +36 -917
  255. package/fesm2022/onnx-sam.worker.js +52 -16
  256. package/fesm2022/spatial-math.worker.js +471 -0
  257. package/fesm2022/tsne.worker.js +32 -15
  258. package/index.d.ts +13 -10
  259. package/lib/channel-histogram/channel-histogram.component.d.ts +53 -43
  260. package/lib/contracts/capabilities.contract.d.ts +4 -2
  261. package/lib/contracts/cell-segmenter.contract.d.ts +1 -0
  262. package/lib/contracts/channel-histogram-api.contract.d.ts +4 -0
  263. package/lib/contracts/color.d.ts +27 -0
  264. package/lib/contracts/colormap-lut.d.ts +19 -4
  265. package/lib/contracts/coordinate-transform.contract.d.ts +3 -3
  266. package/lib/contracts/display-types.d.ts +21 -0
  267. package/lib/contracts/instance-segmenter.contract.d.ts +5 -0
  268. package/lib/contracts/intensity.d.ts +13 -2
  269. package/lib/contracts/plot-type.d.ts +3 -1
  270. package/lib/contracts/ports/image-state.port.d.ts +6 -2
  271. package/lib/contracts/ports/preferences.port.d.ts +4 -0
  272. package/lib/contracts/ports/region-io.port.d.ts +1 -0
  273. package/lib/contracts/ports/spatial-data.port.d.ts +4 -10
  274. package/lib/contracts/ports/tile-access.port.d.ts +1 -0
  275. package/lib/contracts/region-editor-api.contract.d.ts +1 -1
  276. package/lib/contracts/region-overlay.contract.d.ts +5 -0
  277. package/lib/contracts/sam.contract.d.ts +7 -0
  278. package/lib/contracts/semantic-segmenter.contract.d.ts +6 -0
  279. package/lib/contracts/spatial-dataset.contract.d.ts +19 -6
  280. package/lib/contracts/toolbar-tool.contract.d.ts +1 -0
  281. package/lib/contracts/visualizer.contract.d.ts +221 -54
  282. package/lib/contracts/viz-config.d.ts +1 -0
  283. package/lib/geometry/contour.d.ts +24 -0
  284. package/lib/geometry/raster.d.ts +42 -0
  285. package/lib/geometry/ring.d.ts +67 -0
  286. package/lib/hex-color-picker/hex-color-picker.component.d.ts +61 -27
  287. package/lib/implementations/base-store-visualizer.d.ts +61 -15
  288. package/lib/implementations/napari-js/napari-axes-gizmo.d.ts +36 -0
  289. package/lib/implementations/napari-js/napari-display-state.d.ts +76 -0
  290. package/lib/implementations/napari-js/napari-helpers.d.ts +129 -0
  291. package/lib/implementations/napari-js/napari-image-2d-scene.d.ts +162 -0
  292. package/lib/implementations/napari-js/napari-loading-badge.d.ts +0 -1
  293. package/lib/implementations/napari-js/napari-loading-state.d.ts +30 -0
  294. package/lib/implementations/napari-js/napari-region-overlay.d.ts +62 -70
  295. package/lib/implementations/napari-js/napari-scene.d.ts +93 -0
  296. package/lib/implementations/napari-js/napari-spatial-2d-scene.d.ts +163 -0
  297. package/lib/implementations/napari-js/napari-spatial-3d-scene.d.ts +212 -0
  298. package/lib/implementations/napari-js/napari-spatial-encoding.d.ts +114 -0
  299. package/lib/implementations/napari-js/napari-spatial-hover.d.ts +89 -0
  300. package/lib/implementations/napari-js/napari-spatial-scene.d.ts +118 -0
  301. package/lib/implementations/napari-js/napari-spatial-tiles.d.ts +56 -263
  302. package/lib/implementations/napari-js/napari-spatial-tooltip.d.ts +1 -1
  303. package/lib/implementations/napari-js/napari-surface-scene.d.ts +76 -0
  304. package/lib/implementations/napari-js/napari-tile-client.d.ts +214 -0
  305. package/lib/implementations/napari-js/napari-tool-bridge.d.ts +179 -0
  306. package/lib/implementations/napari-js/napari-visualizer.service.d.ts +121 -878
  307. package/lib/implementations/napari-js/napari-volume-scene.d.ts +104 -0
  308. package/lib/implementations/napari-js/napari-volume-z-handle.d.ts +8 -12
  309. package/lib/implementations/napari-js/region-overlay/overlay-projection.d.ts +59 -0
  310. package/lib/implementations/napari-js/region-overlay/region-edit.d.ts +15 -0
  311. package/lib/implementations/napari-js/region-overlay/region-svg-renderer.d.ts +54 -0
  312. package/lib/implementations/napari-js/spatial-tiles/categorical-lookup.d.ts +26 -0
  313. package/lib/implementations/napari-js/spatial-tiles/cell-layers.d.ts +70 -0
  314. package/lib/implementations/napari-js/spatial-tiles/density-layer.d.ts +61 -0
  315. package/lib/implementations/napari-js/spatial-tiles/layer-groups.d.ts +67 -0
  316. package/lib/implementations/napari-js/spatial-tiles/plan-context.d.ts +38 -0
  317. package/lib/implementations/napari-js/spatial-tiles/transcript-hover.d.ts +71 -0
  318. package/lib/implementations/napari-js/spatial-tiles/transcript-jobs.d.ts +105 -0
  319. package/lib/implementations/napari-js/spatial-tiles/transcript-layers.d.ts +56 -0
  320. package/lib/implementations/osd/display-pipeline.d.ts +38 -9
  321. package/lib/implementations/osd/histogram-sampler.d.ts +22 -12
  322. package/lib/implementations/osd/openseadragon-viewer-options.d.ts +35 -0
  323. package/lib/implementations/osd/openseadragon-visualizer.service.d.ts +78 -354
  324. package/lib/implementations/osd/osd-coordinate-transform.d.ts +2 -1
  325. package/lib/implementations/osd/osd-coords.d.ts +6 -4
  326. package/lib/implementations/osd/osd-export.d.ts +36 -0
  327. package/lib/implementations/osd/osd-lib.d.ts +7 -0
  328. package/lib/implementations/osd/osd-navigator-chrome.d.ts +69 -0
  329. package/lib/implementations/osd/osd-pixel-readback.d.ts +22 -0
  330. package/lib/implementations/osd/osd-region-overlay-draw.d.ts +37 -0
  331. package/lib/implementations/osd/osd-region-overlay.d.ts +36 -48
  332. package/lib/implementations/osd/osd-scale-bar.d.ts +8 -6
  333. package/lib/implementations/osd/osd-tile-source.d.ts +49 -0
  334. package/lib/implementations/osd/osd-viewer-like.d.ts +100 -0
  335. package/lib/implementations/osd/osd-viewer-mount.d.ts +14 -0
  336. package/lib/implementations/osd/osd-viewport.d.ts +77 -0
  337. package/lib/implementations/osd/osd-zoom.d.ts +6 -0
  338. package/lib/implementations/osd/simple-source.d.ts +161 -0
  339. package/lib/implementations/osd/slice-cache.d.ts +12 -3
  340. package/lib/implementations/osd/tile-client.d.ts +11 -14
  341. package/lib/implementations/osd/tile-recolor.d.ts +141 -0
  342. package/lib/implementations/plotly/omics-trace-builders.d.ts +32 -20
  343. package/lib/implementations/plotly/plotly-image-loader.d.ts +49 -0
  344. package/lib/implementations/plotly/plotly-image-recolor.d.ts +75 -0
  345. package/lib/implementations/plotly/plotly-intensity-inset.d.ts +8 -0
  346. package/lib/implementations/plotly/plotly-isosurface-controls.d.ts +38 -0
  347. package/lib/implementations/plotly/plotly-layouts.d.ts +188 -0
  348. package/lib/implementations/plotly/plotly-readback.d.ts +41 -0
  349. package/lib/implementations/plotly/plotly-region-overlay.d.ts +2 -2
  350. package/lib/implementations/plotly/plotly-shape-projection.d.ts +92 -0
  351. package/lib/implementations/plotly/plotly-trace-builders.d.ts +23 -12
  352. package/lib/implementations/plotly/plotly-zoom-controller.d.ts +86 -0
  353. package/lib/implementations/plotly/plotly.service.d.ts +136 -401
  354. package/lib/implementations/region-centroids.d.ts +14 -0
  355. package/lib/implementations/simple-slice-access.service.d.ts +7 -4
  356. package/lib/implementations/spatial-data-http/spatial-data-http.service.d.ts +42 -18
  357. package/lib/implementations/spatial-data-http/spatial-wire.d.ts +34 -9
  358. package/lib/implementations/tile-server/index.d.ts +5 -0
  359. package/lib/implementations/tile-server/native-histogram.d.ts +25 -0
  360. package/lib/implementations/tile-server/poll-descriptor.d.ts +39 -0
  361. package/lib/implementations/tile-server/tile-protocol.d.ts +80 -0
  362. package/lib/implementations/tile-server/transport.d.ts +62 -0
  363. package/lib/intensity/intensity-profile.d.ts +66 -0
  364. package/lib/intensity/intensity-profile.service.d.ts +108 -0
  365. package/lib/intensity-inset/intensity-inset.component.d.ts +58 -0
  366. package/lib/models/bezier.d.ts +0 -5
  367. package/lib/models/class-preset.d.ts +18 -0
  368. package/lib/models/geometry.d.ts +14 -48
  369. package/lib/models/polygon-edit.d.ts +72 -0
  370. package/lib/models/polygon-factory.d.ts +40 -0
  371. package/lib/models/region-clone.d.ts +20 -0
  372. package/lib/models/region-geojson.d.ts +17 -0
  373. package/lib/models/region.d.ts +40 -4
  374. package/lib/models/shape.d.ts +8 -0
  375. package/lib/plot-mode/contribution-host.d.ts +125 -0
  376. package/lib/plot-mode/plot-type-menu.d.ts +60 -0
  377. package/lib/plot-mode/tool-params-model.d.ts +49 -0
  378. package/lib/plot.utilities.d.ts +19 -30
  379. package/lib/processing/processing-image.d.ts +5 -2
  380. package/lib/provide-visualization.d.ts +19 -2
  381. package/lib/region-editor/classes-panel/classes-panel.component.d.ts +56 -0
  382. package/lib/region-editor/file-stem.d.ts +7 -0
  383. package/lib/region-editor/manage-classes-dialog/manage-classes-dialog.component.d.ts +45 -0
  384. package/lib/region-editor/mask-export.service.d.ts +54 -0
  385. package/lib/region-editor/mask-raster.d.ts +2 -8
  386. package/lib/region-editor/region-color-dialog/region-color-dialog.component.d.ts +29 -0
  387. package/lib/region-editor/region-editor-help/region-editor-help.component.d.ts +11 -0
  388. package/lib/region-editor/region-editor.component.d.ts +166 -199
  389. package/lib/region-editor/region-metrics.d.ts +26 -0
  390. package/lib/region-editor/region-persistence.service.d.ts +69 -0
  391. package/lib/region-editor/region-table/region-table.component.d.ts +83 -0
  392. package/lib/region-editor/save-mask-dialog/save-mask-dialog.component.d.ts +36 -0
  393. package/lib/region-editor/save-regions-dialog/save-regions-dialog.component.d.ts +37 -0
  394. package/lib/region-ops.service.d.ts +1 -7
  395. package/lib/region-overlay/region-geometry.d.ts +157 -0
  396. package/lib/region-overlay/region-hit-test.d.ts +38 -0
  397. package/lib/region-overlay/svg-region-renderer.d.ts +110 -0
  398. package/lib/render-orchestrator.d.ts +6 -2
  399. package/lib/render-session.d.ts +75 -0
  400. package/lib/routing-visualizer.service.d.ts +110 -58
  401. package/lib/spatial/density-raster.d.ts +6 -0
  402. package/lib/spatial/embedding-compute-coordinator.d.ts +123 -0
  403. package/lib/spatial/embedding-compute.d.ts +21 -2
  404. package/lib/spatial/glyphs.d.ts +16 -0
  405. package/lib/spatial/lod.d.ts +94 -0
  406. package/lib/spatial/spatial-controls.facade.d.ts +64 -0
  407. package/lib/spatial/spatial-density.d.ts +15 -5
  408. package/lib/spatial/spatial-encoding.d.ts +11 -44
  409. package/lib/spatial/spatial-expression.d.ts +40 -22
  410. package/lib/spatial/spatial-framing.d.ts +1 -0
  411. package/lib/spatial/spatial-heatmap.d.ts +2 -0
  412. package/lib/spatial/spatial-hover.d.ts +4 -16
  413. package/lib/spatial/spatial-panel-model.d.ts +135 -0
  414. package/lib/spatial/spatial-selection.d.ts +21 -26
  415. package/lib/spatial/spatial-tile-merge.d.ts +41 -0
  416. package/lib/spatial/spatial-tiles.d.ts +9 -256
  417. package/lib/spatial/stats.d.ts +38 -0
  418. package/lib/spatial/transcript-grouping.d.ts +119 -0
  419. package/lib/spatial-controls/spatial-cells-panel/spatial-cells-panel.component.d.ts +64 -0
  420. package/lib/spatial-controls/spatial-charts/chart-data-model.d.ts +153 -0
  421. package/lib/spatial-controls/spatial-charts/chart-help.d.ts +69 -0
  422. package/lib/spatial-controls/spatial-charts/plotly-chart-host.d.ts +98 -0
  423. package/lib/spatial-controls/spatial-charts/spatial-chart-window/spatial-chart-window.component.d.ts +26 -0
  424. package/lib/spatial-controls/spatial-charts/spatial-charts.component.d.ts +101 -260
  425. package/lib/spatial-controls/spatial-charts/spatial-embedding-controls/spatial-embedding-controls.component.d.ts +43 -0
  426. package/lib/spatial-controls/spatial-charts/spatial-heatmap-controls/spatial-heatmap-controls.component.d.ts +27 -0
  427. package/lib/spatial-controls/spatial-controls.component.d.ts +68 -448
  428. package/lib/spatial-controls/spatial-gene-picker.d.ts +86 -0
  429. package/lib/spatial-controls/spatial-gene-tree/spatial-gene-tree.component.d.ts +102 -0
  430. package/lib/spatial-controls/spatial-groups-panel/spatial-groups-panel.component.d.ts +72 -0
  431. package/lib/spatial-controls/spatial-key/spatial-key.component.d.ts +66 -0
  432. package/lib/spatial-controls/spatial-key/spatial-key.model.d.ts +33 -0
  433. package/lib/spatial-controls/spatial-marker-genes-form/spatial-marker-genes-form.component.d.ts +64 -0
  434. package/lib/spatial-controls/spatial-observations-panel/spatial-observations-panel.component.d.ts +117 -0
  435. package/lib/spatial-controls/spatial-transcripts-panel/spatial-transcripts-panel.component.d.ts +142 -0
  436. package/lib/store/class-color.util.d.ts +35 -1
  437. package/lib/store/region-history.d.ts +66 -0
  438. package/lib/store/region-scope-cache.d.ts +63 -0
  439. package/lib/store/region-selection.d.ts +36 -0
  440. package/lib/store/region-store.service.d.ts +104 -112
  441. package/lib/store/visualizer-store.service.d.ts +22 -33
  442. package/lib/toast-outlets.d.ts +4 -3
  443. package/lib/toolbar/brush/brush-tool.service.d.ts +31 -98
  444. package/lib/toolbar/canvas-tools.d.ts +20 -0
  445. package/lib/toolbar/crop/slide-crop.d.ts +10 -4
  446. package/lib/toolbar/plot-type-selector/plot-type-selector.component.d.ts +38 -0
  447. package/lib/toolbar/region-tools/region-tool-buttons.d.ts +21 -0
  448. package/lib/toolbar/region-tools/region-tools.component.d.ts +60 -0
  449. package/lib/toolbar/segmentation/cell-segment-tool.service.d.ts +10 -14
  450. package/lib/toolbar/segmentation/cellpose-segmenter.service.d.ts +12 -2
  451. package/lib/toolbar/segmentation/onnx-sam-session.d.ts +22 -3
  452. package/lib/toolbar/segmentation/pending-calls.d.ts +31 -0
  453. package/lib/toolbar/segmentation/sam-model-registry.d.ts +9 -3
  454. package/lib/toolbar/segmentation/sam-onnx-core.d.ts +18 -5
  455. package/lib/toolbar/segmentation/sam-point-tool.service.d.ts +46 -32
  456. package/lib/toolbar/segmentation/sam-prompt.d.ts +7 -31
  457. package/lib/toolbar/segmentation/sam-session.service.d.ts +74 -0
  458. package/lib/toolbar/segmentation/sam-tool.service.d.ts +23 -30
  459. package/lib/toolbar/segmentation/segmentation-commit.d.ts +8 -0
  460. package/lib/toolbar/segmentation/segmentation-runner.d.ts +52 -0
  461. package/lib/toolbar/segmentation-tools/segmentation-tools.component.d.ts +87 -0
  462. package/lib/toolbar/stack-controls/stack-controls.component.d.ts +40 -0
  463. package/lib/toolbar/tool-kit/async-tool-status.d.ts +21 -0
  464. package/lib/toolbar/tool-kit/canvas-tool-manager.d.ts +36 -0
  465. package/lib/toolbar/tool-kit/canvas-tool.d.ts +86 -0
  466. package/lib/toolbar/tool-kit/frame-pixels.d.ts +45 -0
  467. package/lib/toolbar/tool-kit/mask-stroke-editor.d.ts +125 -0
  468. package/lib/toolbar/tool-kit/matrix-frame.d.ts +40 -0
  469. package/lib/toolbar/tool-kit/tool-overlay.d.ts +60 -0
  470. package/lib/toolbar/tool-kit/undo-gesture.d.ts +17 -0
  471. package/lib/toolbar/tool-slider/tool-slider.component.d.ts +33 -0
  472. package/lib/toolbar/toolbar-help-dialog/toolbar-help-dialog.component.d.ts +24 -0
  473. package/lib/toolbar/toolbar.component.d.ts +47 -83
  474. package/lib/toolbar/vertex-eraser/vertex-eraser-tool.service.d.ts +33 -40
  475. package/lib/toolbar/view-controls/view-controls.component.d.ts +54 -0
  476. package/lib/toolbar/wand/wand-region-grow.d.ts +49 -0
  477. package/lib/toolbar/wand/wand-tool.service.d.ts +39 -124
  478. package/lib/toolbar/wand/wand.service.d.ts +22 -116
  479. package/lib/toolbar/zoom-to-box/zoom-to-box-tool.service.d.ts +17 -37
  480. package/lib/util/mark-for-check.d.ts +11 -0
  481. package/lib/util/supersede.d.ts +53 -0
  482. package/lib/visualization.module.d.ts +18 -39
  483. package/lib/visualizer/floating-drag.directive.d.ts +30 -0
  484. package/lib/visualizer/region-actions.d.ts +54 -0
  485. package/lib/visualizer/region-load.d.ts +27 -0
  486. package/lib/visualizer/spatial-dataset-binder.d.ts +74 -0
  487. package/lib/visualizer/tool-modes.d.ts +49 -0
  488. package/lib/visualizer/viewer-shortcuts.d.ts +71 -0
  489. package/lib/visualizer/visualizer-context-menu.d.ts +55 -0
  490. package/lib/visualizer.component.d.ts +201 -447
  491. package/lib/workers/spatial-math-ops.d.ts +65 -0
  492. package/lib/workers/spatial-math-worker.d.ts +7 -0
  493. package/lib/workers/spatial-math.d.ts +74 -0
  494. package/package.json +12 -3
  495. package/src/lib/styles/_viz-icons-rules.scss +73 -0
  496. package/src/lib/styles/viz-icons.scss +14 -0
  497. package/esm2022/lib/implementations/napari-js/napari-axes-labels.mjs +0 -97
  498. package/esm2022/lib/implementations/napari-js/napari-navigator.mjs +0 -195
  499. package/esm2022/lib/implementations/napari-js/napari-scale-bar.mjs +0 -92
  500. package/fesm2022/jax-data-science-sci-image-visualizer-onnx-sam-session-BwP-A11m.mjs +0 -329
  501. package/fesm2022/jax-data-science-sci-image-visualizer-onnx-sam-session-BwP-A11m.mjs.map +0 -1
  502. package/lib/implementations/napari-js/napari-axes-labels.d.ts +0 -49
  503. package/lib/implementations/napari-js/napari-navigator.d.ts +0 -72
  504. package/lib/implementations/napari-js/napari-scale-bar.d.ts +0 -35
  505. package/src/lib/assets/cell-detection.svg +0 -37
  506. package/src/lib/assets/click.svg +0 -1
  507. package/src/lib/assets/colormap-luts.json +0 -1
  508. package/src/lib/assets/edit-selection-white.svg +0 -47
  509. package/src/lib/assets/icons/colormap-earth.png +0 -0
  510. package/src/lib/assets/icons/colormap-placeholder.png +0 -0
  511. package/src/lib/assets/icons/colormap-pubu.png +0 -0
  512. package/src/lib/assets/interactive-segmentation-cursor.svg +0 -1
  513. package/src/lib/assets/picture-segmentation.svg +0 -43
  514. package/src/lib/assets/test/download-379.svg +0 -1
  515. package/src/lib/assets/test/download-98.svg +0 -1
  516. package/src/lib/assets/test/json-1.svg +0 -1
  517. package/src/lib/assets/test/load-53.svg +0 -1
  518. package/src/lib/assets/test/mask-44.svg +0 -1
  519. package/src/lib/assets/test/mask-download-44.svg +0 -15
  520. package/src/lib/assets/test/mask-save-44.svg +0 -11
  521. package/src/lib/assets/test/overlay-1.svg +0 -1
  522. package/src/lib/assets/test/overlay-4.svg +0 -1
  523. package/src/lib/assets/test/region-26.svg +0 -1
  524. package/src/lib/assets/test/save-56.svg +0 -1
  525. package/src/lib/assets/test/upload-43.svg +0 -1
@@ -1,4 +1,5 @@
1
1
  import { NO_CATEGORY } from '../../contracts/spatial-dataset.contract';
2
+ import { parseCssColor, rgbToHex } from '../../contracts/color';
2
3
  const DEFAULT_COLOR = '#0072B2';
3
4
  /** Plotly renders every point of a violin/box; past this we thin the input.
4
5
  * 84k cells x a violin per category is otherwise seconds of layout. */
@@ -27,6 +28,58 @@ function thin(values, max = MAX_POINTS_PER_TRACE) {
27
28
  out.push(values[Math.floor(i * step)]);
28
29
  return out;
29
30
  }
31
+ /** Bin-count bounds for the pre-binned histogram (square-root rule in between). */
32
+ const HISTOGRAM_MIN_BINS = 10;
33
+ const HISTOGRAM_MAX_BINS = 100;
34
+ /**
35
+ * Bin the finite (optionally log-scaled) values in TS, once, into bins shared by the
36
+ * full distribution and the selection.
37
+ *
38
+ * Handing Plotly all N values as a `number[]` made it re-bin every one of them on each
39
+ * selection change — at millions of observations, the dominant cost of a lasso. Shared
40
+ * bins also keep the two overlaid bars directly comparable.
41
+ */
42
+ function histogramBins(input, selection) {
43
+ const { values, log } = input;
44
+ const at = (i) => {
45
+ const v = values[i];
46
+ return log ? Math.log1p(Math.max(0, v)) : v;
47
+ };
48
+ let lo = Infinity;
49
+ let hi = -Infinity;
50
+ let count = 0;
51
+ for (let i = 0; i < values.length; i++) {
52
+ if (!Number.isFinite(values[i]))
53
+ continue;
54
+ const v = at(i);
55
+ if (v < lo)
56
+ lo = v;
57
+ if (v > hi)
58
+ hi = v;
59
+ count++;
60
+ }
61
+ if (count === 0) {
62
+ return { centers: [], edges: [], width: 1, all: [], selected: selection ? [] : null };
63
+ }
64
+ // One bar, one unit wide, for a flat distribution: there is no spread to bin.
65
+ const flat = !(hi > lo);
66
+ const bins = flat ? 1 : Math.min(HISTOGRAM_MAX_BINS, Math.max(HISTOGRAM_MIN_BINS, Math.ceil(Math.sqrt(count))));
67
+ const start = flat ? lo - 0.5 : lo;
68
+ const width = flat ? 1 : (hi - lo) / bins;
69
+ const all = new Array(bins).fill(0);
70
+ const selected = selection ? new Array(bins).fill(0) : null;
71
+ for (let i = 0; i < values.length; i++) {
72
+ if (!Number.isFinite(values[i]))
73
+ continue;
74
+ // The maximum lands in the last bin rather than one past it.
75
+ const b = Math.min(bins - 1, Math.floor((at(i) - start) / width));
76
+ all[b]++;
77
+ if (selected && selection[i])
78
+ selected[b]++;
79
+ }
80
+ const edges = all.map((_, b) => [start + b * width, start + (b + 1) * width]);
81
+ return { centers: edges.map(([a, z]) => (a + z) / 2), edges, width, all, selected };
82
+ }
30
83
  /** Values per category, finite and optionally selection-restricted. */
31
84
  function byCategory(input, group, restrict) {
32
85
  const buckets = group.categories.map(() => []);
@@ -58,7 +111,7 @@ function activeSelection(selection) {
58
111
  /**
59
112
  * Traces for one chart kind.
60
113
  *
61
- * - **histogram** — the full distribution, plus an overlaid *Selected* trace
114
+ * - **histogram** — the full distribution as pre-binned bars, plus an overlaid *Selected* trace
62
115
  * when a selection exists, so the two are directly comparable. That
63
116
  * comparison is the whole point of linking the chart to the map.
64
117
  * - **violin / box** — one per category when grouped, otherwise a single trace.
@@ -69,22 +122,29 @@ export function buildOmicsTraces(kind, input) {
69
122
  const selection = activeSelection(input.selection);
70
123
  const color = input.color ?? DEFAULT_COLOR;
71
124
  if (kind === 'histogram') {
72
- const traces = [{
73
- type: 'histogram',
74
- x: prepare(input, null),
75
- name: 'All',
125
+ // Pre-binned bars rather than a Plotly `histogram` of every value: see `histogramBins`.
126
+ const bins = histogramBins(input, selection);
127
+ const bar = (counts, name) => ({
128
+ type: 'bar',
129
+ x: bins.centers,
130
+ y: counts,
131
+ width: bins.width,
132
+ customdata: bins.edges,
133
+ name,
134
+ hovertemplate: `%{y} obs<br>%{customdata[0]:.4g} – %{customdata[1]:.4g}<extra>${name}</extra>`,
135
+ });
136
+ const traces = [
137
+ {
138
+ ...bar(bins.all, 'All'),
76
139
  marker: { color, line: { width: 0 } },
77
140
  opacity: selection ? 0.55 : 1,
78
- hovertemplate: '%{y} obs<br>%{x}<extra>All</extra>',
79
- }];
80
- if (selection) {
141
+ },
142
+ ];
143
+ if (bins.selected) {
81
144
  traces.push({
82
- type: 'histogram',
83
- x: prepare(input, selection),
84
- name: 'Selected',
145
+ ...bar(bins.selected, 'Selected'),
85
146
  marker: { color: '#D55E00', line: { width: 0 } },
86
147
  opacity: 0.85,
87
- hovertemplate: '%{y} obs<br>%{x}<extra>Selected</extra>',
88
148
  });
89
149
  }
90
150
  return traces;
@@ -98,7 +158,7 @@ export function buildOmicsTraces(kind, input) {
98
158
  };
99
159
  if (input.group) {
100
160
  const buckets = byCategory(input, input.group, selection);
101
- return buckets
161
+ return (buckets
102
162
  // Drop empty categories: an empty violin renders as a stray tick with a
103
163
  // label, which reads as data.
104
164
  .map((values, i) => ({ values, i }))
@@ -109,18 +169,20 @@ export function buildOmicsTraces(kind, input) {
109
169
  name: input.group.categories[b.i],
110
170
  marker: { color: input.group.colors[b.i] ?? color },
111
171
  line: { color: input.group.colors[b.i] ?? color },
112
- }));
172
+ })));
113
173
  }
114
174
  const values = thin(prepare(input, selection));
115
175
  if (values.length === 0)
116
176
  return [];
117
- return [{
177
+ return [
178
+ {
118
179
  ...shared,
119
180
  y: values,
120
181
  name: selection ? 'Selected' : 'All',
121
182
  marker: { color },
122
183
  line: { color },
123
- }];
184
+ },
185
+ ];
124
186
  }
125
187
  /** Layout for a chart kind — axis titles reflect the log toggle. */
126
188
  export function omicsLayout(kind, input) {
@@ -198,13 +260,14 @@ export function countByCategory(input) {
198
260
  * the legend implies without answering. Horizontal, because taxonomy labels are
199
261
  * long, and sorted, because rank is what the chart is read for.
200
262
  */
201
- export function buildCountTraces(input) {
202
- const { labels, colors, totals, selected } = countByCategory(input);
263
+ export function buildCountTraces(input, counts = countByCategory(input)) {
264
+ const { labels, colors, totals, selected } = counts;
203
265
  const selection = activeSelection(input.selection);
204
266
  // Plotly draws the first category at the BOTTOM of a horizontal axis, so
205
267
  // reverse to put the biggest bar at the top where the eye starts.
206
268
  const flip = (a) => a.slice().reverse();
207
- const traces = [{
269
+ const traces = [
270
+ {
208
271
  type: 'bar',
209
272
  orientation: 'h',
210
273
  x: flip(totals),
@@ -213,7 +276,8 @@ export function buildCountTraces(input) {
213
276
  marker: { color: flip(colors) },
214
277
  opacity: selection ? 0.45 : 1,
215
278
  hovertemplate: '%{x} obs<extra>%{y}</extra>',
216
- }];
279
+ },
280
+ ];
217
281
  if (selection) {
218
282
  traces.push({
219
283
  type: 'bar',
@@ -227,8 +291,12 @@ export function buildCountTraces(input) {
227
291
  }
228
292
  return traces;
229
293
  }
230
- export function countsLayout(input) {
231
- const { labels } = countByCategory(input);
294
+ /**
295
+ * Layout for {@link buildCountTraces}. Pass the same `counts` to both rather than letting
296
+ * each run its own full pass over the codes.
297
+ */
298
+ export function countsLayout(input, counts = countByCategory(input)) {
299
+ const { labels } = counts;
232
300
  return {
233
301
  // Room for the labels, and a height that grows with the bar count so 25
234
302
  // categories are not crushed into the same box as 3.
@@ -276,18 +344,11 @@ const EMBEDDING_MUTED_OPACITY = 0.15;
276
344
  * the same effect is produced by mixing toward the paper instead.
277
345
  */
278
346
  function towardPaper(hex, amount) {
279
- const clean = hex.replace('#', '');
280
- const full = clean.length === 3
281
- ? clean.split('').map((c) => c + c).join('')
282
- : clean;
283
- const n = Number.parseInt(full, 16);
284
- if (!Number.isFinite(n) || full.length !== 6)
347
+ const rgb = parseCssColor(hex);
348
+ if (!rgb)
285
349
  return hex;
286
350
  const mix = (c) => Math.round(c + (255 - c) * amount);
287
- const r = mix((n >> 16) & 0xff);
288
- const g = mix((n >> 8) & 0xff);
289
- const b = mix(n & 0xff);
290
- return `#${((r << 16) | (g << 8) | b).toString(16).padStart(6, '0')}`;
351
+ return rgbToHex([mix(rgb[0]), mix(rgb[1]), mix(rgb[2])]);
291
352
  }
292
353
  const DEFAULT_EMBEDDING_POINT_SIZE = 4;
293
354
  export function buildEmbeddingTraces(input) {
@@ -301,9 +362,10 @@ export function buildEmbeddingTraces(input) {
301
362
  // own scene, which is why a third dimension cannot just be added to the former. It
302
363
  // costs more per point, so it suits this scale and not millions.
303
364
  const type = z ? 'scatter3d' : 'scattergl';
304
- const markerSize = z ? Math.max(1, (input.size ?? DEFAULT_EMBEDDING_POINT_SIZE) - 2)
365
+ const markerSize = z
366
+ ? Math.max(1, (input.size ?? DEFAULT_EMBEDDING_POINT_SIZE) - 2)
305
367
  : (input.size ?? DEFAULT_EMBEDDING_POINT_SIZE);
306
- const opacityFor = (i) => !selection || selection[i] ? 1 : EMBEDDING_MUTED_OPACITY;
368
+ const opacityFor = (i) => (!selection || selection[i] ? 1 : EMBEDDING_MUTED_OPACITY);
307
369
  const isSelected = (i) => !selection || selection[i] === 1;
308
370
  // In 3D the dimming has to be in the COLOUR, since a per-point opacity array is
309
371
  // ignored there. Cached per input colour: 19k lookups of the same few categories.
@@ -318,15 +380,25 @@ export function buildEmbeddingTraces(input) {
318
380
  dimCache.set(hex, dimmed);
319
381
  return dimmed;
320
382
  };
321
- /** Per-point opacity, which only the 2D trace types honour. */
322
- const opacityArray = (indices) => selection && !z ? indices.map(opacityFor) : undefined;
383
+ /** Per-point opacity is honoured only by the 2D trace types. */
384
+ const perPointOpacity = !!selection && !z;
385
+ /** Every observation's opacity, built once for the single-trace paths. */
386
+ const allOpacity = () => perPointOpacity ? { opacity: Array.from({ length: n }, (_, i) => opacityFor(i)) } : {};
387
+ /** The single-trace coordinates. `scattergl` takes the typed arrays as they are; the
388
+ * 3D trace is handed plain arrays. */
389
+ const coords = () => z
390
+ ? {
391
+ x: Array.from(x.subarray(0, n)),
392
+ y: Array.from(y.subarray(0, n)),
393
+ z: Array.from(z.subarray(0, n)),
394
+ }
395
+ : { x: x.subarray(0, n), y: y.subarray(0, n) };
323
396
  if (!categories || categories.names.length === 0) {
324
- return [{
397
+ return [
398
+ {
325
399
  type,
326
400
  mode: 'markers',
327
- x: Array.from(x.subarray(0, n)),
328
- y: Array.from(y.subarray(0, n)),
329
- ...(z ? { z: Array.from(z.subarray(0, n)) } : {}),
401
+ ...coords(),
330
402
  // The OBSERVATION index per point, carried through so a lasso can be turned back
331
403
  // into a selection. Plotly reports a selected point by its position within its
332
404
  // trace, which is not the observation index once the points are split by category.
@@ -335,39 +407,34 @@ export function buildEmbeddingTraces(input) {
335
407
  size: markerSize,
336
408
  // A flat colour normally; per point once a selection has to dim some of them in
337
409
  // 3D, where opacity arrays are ignored.
338
- color: selection && z
339
- ? Array.from({ length: n }, (_, i) => shade('#4c72b0', i))
340
- : '#4c72b0',
341
- ...(opacityArray(Array.from({ length: n }, (_, i) => i))
342
- ? { opacity: Array.from({ length: n }, (_, i) => opacityFor(i)) }
343
- : {}),
410
+ color: selection && z ? Array.from({ length: n }, (_, i) => shade('#4c72b0', i)) : '#4c72b0',
411
+ ...allOpacity(),
344
412
  },
345
413
  hoverinfo: 'none',
346
414
  showlegend: false,
347
- }];
415
+ },
416
+ ];
348
417
  }
349
418
  const { codes, names, colors } = categories;
350
419
  if (names.length > EMBEDDING_MAX_LEGEND_CATEGORIES) {
351
420
  // One trace, per-point colour. Hover still names the category, which is the part that
352
421
  // matters; the legend is what is lost.
353
- return [{
422
+ return [
423
+ {
354
424
  type,
355
425
  mode: 'markers',
356
- x: Array.from(x.subarray(0, n)),
357
- y: Array.from(y.subarray(0, n)),
358
- ...(z ? { z: Array.from(z.subarray(0, n)) } : {}),
426
+ ...coords(),
359
427
  marker: {
360
428
  size: markerSize,
361
429
  color: Array.from({ length: n }, (_, i) => shade(colors[codes[i]] ?? '#999999', i)),
362
- ...(opacityArray(Array.from({ length: n }, (_, i) => i))
363
- ? { opacity: Array.from({ length: n }, (_, i) => opacityFor(i)) }
364
- : {}),
430
+ ...allOpacity(),
365
431
  },
366
432
  customdata: Array.from({ length: n }, (_, i) => i),
367
433
  text: Array.from({ length: n }, (_, i) => names[codes[i]] ?? 'unassigned'),
368
434
  hovertemplate: '%{text}<extra></extra>',
369
435
  showlegend: false,
370
- }];
436
+ },
437
+ ];
371
438
  }
372
439
  // One trace per category: the legend entries toggle, so a population can be isolated by
373
440
  // clicking rather than by re-colouring the whole plot.
@@ -394,10 +461,8 @@ export function buildEmbeddingTraces(input) {
394
461
  customdata: idx,
395
462
  marker: {
396
463
  size: markerSize,
397
- color: selection && z
398
- ? idx.map((i) => shade(colors[c] ?? '#999999', i))
399
- : (colors[c] ?? '#999999'),
400
- ...(opacityArray(idx) ? { opacity: idx.map(opacityFor) } : {}),
464
+ color: selection && z ? idx.map((i) => shade(colors[c] ?? '#999999', i)) : (colors[c] ?? '#999999'),
465
+ ...(perPointOpacity ? { opacity: idx.map(opacityFor) } : {}),
401
466
  },
402
467
  // Split per category regardless, so hover names it and a future isolate control
403
468
  // has something to toggle; only the legend's VISIBILITY depends on the count.
@@ -456,25 +521,35 @@ export function embeddingLayout(input) {
456
521
  r: 8,
457
522
  t: 8,
458
523
  // Room for the legend only when one is drawn; otherwise the axis title alone.
459
- b: (input.categories?.names.length ?? 0) > 0
460
- && (input.categories?.names.length ?? 0) <= EMBEDDING_MAX_LEGEND_SHOWN ? 64 : 40,
524
+ b: (input.categories?.names.length ?? 0) > 0 &&
525
+ (input.categories?.names.length ?? 0) <= EMBEDDING_MAX_LEGEND_SHOWN
526
+ ? 64
527
+ : 40,
461
528
  },
462
529
  // Equal aspect: an embedding's axes carry no units, so distances are only comparable if the
463
530
  // two are scaled alike. Stretching one axis to fill the panel invents structure.
464
531
  xaxis: {
465
- title: { text: axisTitle(stem, 1, vr) }, zeroline: false, ticks: 'outside',
532
+ title: { text: axisTitle(stem, 1, vr) },
533
+ zeroline: false,
534
+ ticks: 'outside',
466
535
  ...(input.view?.ranges ? { range: input.view.ranges.x, autorange: false } : {}),
467
536
  },
468
537
  yaxis: {
469
- title: { text: axisTitle(stem, 2, vr) }, zeroline: false, ticks: 'outside',
470
- scaleanchor: 'x', scaleratio: 1,
538
+ title: { text: axisTitle(stem, 2, vr) },
539
+ zeroline: false,
540
+ ticks: 'outside',
541
+ scaleanchor: 'x',
542
+ scaleratio: 1,
471
543
  ...(input.view?.ranges ? { range: input.view.ranges.y, autorange: false } : {}),
472
544
  },
473
545
  legend: {
474
546
  orientation: 'h',
475
547
  itemsizing: 'constant',
476
548
  font: { size: 9 },
477
- yanchor: 'top', y: -0.16, xanchor: 'left', x: 0,
549
+ yanchor: 'top',
550
+ y: -0.16,
551
+ xanchor: 'left',
552
+ x: 0,
478
553
  },
479
554
  hovermode: 'closest',
480
555
  };
@@ -491,6 +566,20 @@ const HEATMAP_SEQUENTIAL = [
491
566
  [0.5, '#6BAED6'],
492
567
  [1, '#08306B'],
493
568
  ];
569
+ /**
570
+ * Genes × groups mean expression, as a Plotly heatmap.
571
+ *
572
+ * The matrix itself is computed by the pure `heatmapMatrix` in
573
+ * `spatial/spatial-heatmap.ts`; this only shapes it for Plotly. Kept in the
574
+ * matrix's own row-major order and flipped once here, because Plotly draws
575
+ * `z[0]` at the BOTTOM of the y axis while the caller lists genes top-down.
576
+ *
577
+ * The colour scale is its own, NOT the map's `continuousColormap`. This is a
578
+ * different quantity — a z-scored mean per group, not a per-cell value — so
579
+ * sharing one scale would invite reading a heatmap cell as if it were a marker
580
+ * colour. Diverging and centred on zero, because after z-scoring the sign is
581
+ * the reading: above or below this gene's average across the groups.
582
+ */
494
583
  export function buildHeatmapTraces(input) {
495
584
  const { rows, cols, values, counts } = input;
496
585
  if (rows.length === 0 || cols.length === 0)
@@ -521,10 +610,9 @@ export function buildHeatmapTraces(input) {
521
610
  zmax = peak > 0 ? peak : 1;
522
611
  zmin = -zmax;
523
612
  }
524
- const hover = counts
525
- ? cols.map((label, c) => `${label} · ${counts[c]} cells`)
526
- : cols;
527
- return [{
613
+ const hover = counts ? cols.map((label, c) => `${label} · ${counts[c]} cells`) : cols;
614
+ return [
615
+ {
528
616
  type: 'heatmap',
529
617
  z,
530
618
  x: cols,
@@ -537,7 +625,8 @@ export function buildHeatmapTraces(input) {
537
625
  hoverongaps: false,
538
626
  colorbar: { title: { text: unit, side: 'right' }, thickness: 10, len: 0.9 },
539
627
  hovertemplate: `%{y}<br>%{customdata}<br>${unit} %{z:.2f}<extra></extra>`,
540
- }];
628
+ },
629
+ ];
541
630
  }
542
631
  export function heatmapLayout(input) {
543
632
  return {
@@ -545,11 +634,10 @@ export function heatmapLayout(input) {
545
634
  margin: { t: 10, r: 10, b: 90, l: 8 },
546
635
  autosize: true,
547
636
  hovermode: 'closest',
548
- xaxis: { automargin: true, tickangle: -45, tickfont: { size: 10 },
549
- title: { text: input.groupLabel ?? '' } },
637
+ xaxis: { automargin: true, tickangle: -45, tickfont: { size: 10 }, title: { text: input.groupLabel ?? '' } },
550
638
  yaxis: { automargin: true, tickfont: { size: 10 } },
551
639
  // Grows with the gene count so 3 rows are not stretched to 20 rows' height.
552
640
  height: Math.max(180, 24 * input.rows.length + 110),
553
641
  };
554
642
  }
555
- //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoib21pY3MtdHJhY2UtYnVpbGRlcnMuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi8uLi9zcmMvbGliL2ltcGxlbWVudGF0aW9ucy9wbG90bHkvb21pY3MtdHJhY2UtYnVpbGRlcnMudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUFFLFdBQVcsRUFBRSxNQUFNLDBDQUEwQyxDQUFDO0FBd0N2RSxNQUFNLGFBQWEsR0FBRyxTQUFTLENBQUM7QUFDaEM7d0VBQ3dFO0FBQ3hFLE1BQU0sb0JBQW9CLEdBQUcsTUFBTSxDQUFDO0FBRXBDLCtFQUErRTtBQUMvRSxTQUFTLE9BQU8sQ0FBQyxLQUFzQixFQUFFLFFBQTJCO0lBQ2xFLE1BQU0sRUFBRSxNQUFNLEVBQUUsR0FBRyxFQUFFLEdBQUcsS0FBSyxDQUFDO0lBQzlCLE1BQU0sR0FBRyxHQUFhLEVBQUUsQ0FBQztJQUN6QixLQUFLLElBQUksQ0FBQyxHQUFHLENBQUMsRUFBRSxDQUFDLEdBQUcsTUFBTSxDQUFDLE1BQU0sRUFBRSxDQUFDLEVBQUUsRUFBRSxDQUFDO1FBQ3ZDLElBQUksUUFBUSxJQUFJLENBQUMsUUFBUSxDQUFDLENBQUMsQ0FBQztZQUFFLFNBQVM7UUFDdkMsTUFBTSxDQUFDLEdBQUcsTUFBTSxDQUFDLENBQUMsQ0FBQyxDQUFDO1FBQ3BCLElBQUksQ0FBQyxNQUFNLENBQUMsUUFBUSxDQUFDLENBQUMsQ0FBQztZQUFFLFNBQVM7UUFDbEMsR0FBRyxDQUFDLElBQUksQ0FBQyxHQUFHLENBQUMsQ0FBQyxDQUFDLElBQUksQ0FBQyxLQUFLLENBQUMsSUFBSSxDQUFDLEdBQUcsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUM7SUFDakQsQ0FBQztJQUNELE9BQU8sR0FBRyxDQUFDO0FBQ2IsQ0FBQztBQUVELHlFQUF5RTtBQUN6RSxTQUFTLElBQUksQ0FBQyxNQUFnQixFQUFFLEdBQUcsR0FB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QUEwQjtTQUMxRSxDQUFDLENBQUM7QUFDTCxDQUFDO0FBRUQsTUFBTSxVQUFVLGFBQWEsQ0FBQyxLQUF3QjtJQUNwRCxPQUFPO1FBQ0wsMEVBQTBFO1FBQzFFLE1BQU0sRUFBRSxFQUFFLENBQUMsRUFBRSxFQUFFLEVBQUUsQ0FBQyxFQUFFLEVBQUUsRUFBRSxDQUFDLEVBQUUsRUFBRSxFQUFFLENBQUMsRUFBRSxDQUFDLEVBQUU7UUFDckMsUUFBUSxFQUFFLElBQUk7UUFDZCxTQUFTLEVBQUUsU0FBUztRQUNwQixLQUFLLEVBQUUsRUFBRSxVQUFVLEVBQUUsSUFBSSxFQUFFLFNBQVMsRUFBRSxDQUFDLEVBQUUsRUFBRSxRQUFRLEVBQUUsRUFBRSxJQUFJLEVBQUUsRUFBRSxFQUFFO1lBQy9ELEtBQUssRUFBRSxFQUFFLElBQUksRUFBRSxLQUFLLENBQUMsVUFBVSxJQUFJLEVBQUUsRUFBRSxFQUFFO1FBQzNDLEtBQUssRUFBRSxFQUFFLFVBQVUsRUFBRSxJQUFJLEVBQUUsUUFBUSxFQUFFLEVBQUUsSUFBSSxFQUFFLEVBQUUsRUFBRSxFQUFFO1FBQ25ELDRFQUE0RTtRQUM1RSxNQUFNLEVBQUUsSUFBSSxDQUFDLEdBQUcsQ0FBQyxHQUFHLEVBQUUsRUFBRSxHQUFHLEtBQUssQ0FBQyxJQUFJLENBQUMsTUFBTSxHQUFHLEdBQUcsQ0FBQztLQUNwRCxDQUFDO0FBQ0osQ0FBQyIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IE5PX0NBVEVHT1JZIH0gZnJvbSAnLi4vLi4vY29udHJhY3RzL3NwYXRpYWwtZGF0YXNldC5jb250cmFjdCc7XG5cbi8qKlxuICogUGxvdGx5IHRyYWNlcyBmb3IgdGhlIDEtRCBkaXN0cmlidXRpb24gY2hhcnRzIG92ZXIgc3BhdGlhbC1vbWljcyB2YWx1ZXM6XG4gKiBoaXN0b2dyYW0sIHZpb2xpbiBhbmQgYm94LlxuICpcbiAqIFB1cmUsIGxpa2UgYHBsb3RseS10cmFjZS1idWlsZGVycy50c2Ag4oCUIGFuZCBkZWxpYmVyYXRlbHkgU0VQQVJBVEUgZnJvbSBpdCxcbiAqIGJlY2F1c2UgdGhhdCBtb2R1bGUncyBgVHJhY2VCdWlsZElucHV0YCBpcyBpbWFnZS1tYXRyaXggc2hhcGVkIChgZnJhbWVzYCxcbiAqIGB3aWR0aGAsIGByYXRpb3NgLCBgdHJ1ZUltYWdlU2l6ZWApIGFuZCBjYW5ub3QgZXhwcmVzcyBcIm9uZSB2YWx1ZSBwZXJcbiAqIG9ic2VydmF0aW9uXCIuIEZvcmNpbmcgdGhlIHR3byB0b2dldGhlciB3b3VsZCBtYWtlIGJvdGggd29yc2UuXG4gKlxuICogVmlvbGluIGFuZCBib3ggbmVlZCBubyBidW5kbGluZyB3b3JrOiBgcGxvdGx5LmpzLWRpc3QtbWluYCBpcyB0aGUgZnVsbFxuICogZGlzdHJpYnV0aW9uIGFuZCBhbHJlYWR5IGNhcnJpZXMgYm90aCB0cmFjZSB0eXBlcy5cbiAqL1xuXG5leHBvcnQgdHlwZSBPbWljc0NoYXJ0S2luZCA9XG4gIHwgJ2hpc3RvZ3JhbScgfCAndmlvbGluJyB8ICdib3gnIHwgJ2NvdW50cycgfCAnaGVhdG1hcCcgfCAnZW1iZWRkaW5nJztcblxuLyoqIFBlci1vYnNlcnZhdGlvbiBncm91cGluZyBmb3IgYSB2aW9saW4vYm94LCBvciBhbiBvdmVybGFpZCBoaXN0b2dyYW0uICovXG5leHBvcnQgaW50ZXJmYWNlIE9taWNzR3JvdXBpbmcge1xuICBjb2RlczogVWludDE2QXJyYXk7XG4gIGNhdGVnb3JpZXM6IHN0cmluZ1tdO1xuICAvKiogYCNycmdnYmJgIHBlciBjYXRlZ29yeSwgaW5kZXgtYWxpZ25lZCDigJQgdGhlIHNhbWUgY29sb3VycyB0aGUgbWFwIHVzZXMuICovXG4gIGNvbG9yczogc3RyaW5nW107XG59XG5cbmV4cG9ydCBpbnRlcmZhY2UgT21pY3NUcmFjZUlucHV0IHtcbiAgLyoqIFRoZSB2YWx1ZXMgYmVpbmcgY2hhcnRlZCAoYW4gYW5ub3RhdGlvbiBjb2x1bW4gb3IgYSBnZW5lIHZlY3RvcikuICovXG4gIHZhbHVlczogRmxvYXQzMkFycmF5O1xuICAvKiogQXhpcyBsYWJlbCBmb3IgdGhlIHZhbHVlIOKAlCB0aGUgY29sdW1uIG9yIGdlbmUgbmFtZS4gKi9cbiAgbmFtZTogc3RyaW5nO1xuICBncm91cD86IE9taWNzR3JvdXBpbmcgfCBudWxsO1xuICAvKiogYDFgIG1hcmtzIGEgc2VsZWN0ZWQgb2JzZXJ2YXRpb24uIFdoZW4gcHJlc2VudCwgdGhlIGNoYXJ0cyBuYXJyb3cgdG8gaXQuICovXG4gIHNlbGVjdGlvbj86IFVpbnQ4QXJyYXkgfCBudWxsO1xuICAvKiogUGxvdCBgbG9nMXAodmFsdWUpYCBpbnN0ZWFkIG9mIHRoZSByYXcgdmFsdWUuICovXG4gIGxvZz86IGJvb2xlYW47XG4gIC8qKiBDb2xvdXIgZm9yIHRoZSB1bmdyb3VwZWQgdHJhY2UuICovXG4gIGNvbG9yPzogc3RyaW5nO1xufVxuXG5jb25zdCBERUZBVUxUX0NPTE9SID0gJyMwMDcyQjInO1xuLyoqIFBsb3RseSByZW5kZXJzIGV2ZXJ5IHBvaW50IG9mIGEgdmlvbGluL2JveDsgcGFzdCB0aGlzIHdlIHRoaW4gdGhlIGlucHV0LlxuICogIDg0ayBjZWxscyB4IGEgdmlvbGluIHBlciBjYXRlZ29yeSBpcyBvdGhlcndpc2Ugc2Vjb25kcyBvZiBsYXlvdXQuICovXG5jb25zdCBNQVhfUE9JTlRTX1BFUl9UUkFDRSA9IDIwXzAwMDtcblxuLyoqIEZpbml0ZSB2YWx1ZXMgb25seSwgb3B0aW9uYWxseSBsb2ctc2NhbGVkIGFuZCByZXN0cmljdGVkIHRvIGEgc2VsZWN0aW9uLiAqL1xuZnVuY3Rpb24gcHJlcGFyZShpbnB1dDogT21pY3NUcmFjZUlucHV0LCByZXN0cmljdDogVWludDhBcnJheSB8IG51bGwpOiBudW1iZXJbXSB7XG4gIGNvbnN0IHsgdmFsdWVzLCBsb2cgfSA9IGlucHV0O1xuICBjb25zdCBvdXQ6IG51bWJlcltdID0gW107XG4gIGZvciAobGV0IGkgPSAwOyBpIDwgdmFsdWVzLmxlbmd0aDsgaSsrKSB7XG4gICAgaWYgKHJlc3RyaWN0ICYmICFyZXN0cmljdFtpXSkgY29udGludWU7XG4gICAgY29uc3QgdiA9IHZhbHVlc1tpXTtcbiAgICBpZiAoIU51bWJlci5pc0Zpbml0ZSh2KSkgY29udGludWU7XG4gICAgb3V0LnB1c2gobG9nID8gTWF0aC5sb2cxcChNYXRoLm1heCgwLCB2KSkgOiB2KTtcbiAgfVxuICByZXR1cm4gb3V0O1xufVxuXG4vKiogRXZlbmx5IHRoaW4gYSBzYW1wbGUgdG8gYG1heGAgcG9pbnRzLCBwcmVzZXJ2aW5nIGl0cyBkaXN0cmlidXRpb24uICovXG5mdW5jdGlvbiB0aGluKHZhbHVlczogbnVtYmVyW10sIG1heCA9IE1BWF9QT0lOVFNfUEVSX1RSQUNFKTogbnVtYmVyW10ge1xuICBpZiAodmFsdWVzLmxlbmd0aCA8PSBtYXgpIHJldHVybiB2YWx1ZXM7XG4gIGNvbnN0IHN0ZXAgPSB2YWx1ZXMubGVuZ3RoIC8gbWF4O1xuICBjb25zdCBvdXQ6IG51bWJlcltdID0gW107XG4gIGZvciAobGV0IGkgPSAwOyBpIDwgbWF4OyBpKyspIG91dC5wdXNoKHZhbHVlc1tNYXRoLmZsb29yKGkgKiBzdGVwKV0pO1xuICByZXR1cm4gb3V0O1xufVxuXG4vKiogVmFsdWVzIHBlciBjYXRlZ29yeSwgZmluaXRlIGFuZCBvcHRpb25hbGx5IHNlbGVjdGlvbi1yZXN0cmljdGVkLiAqL1xuZnVuY3Rpb24gYnlDYXRlZ29yeShcbiAgaW5wdXQ6IE9taWNzVHJhY2VJbnB1dCwgZ3JvdXA6IE9taWNzR3JvdXBpbmcsIHJlc3RyaWN0OiBVaW50OEFycmF5IHwgbnVsbCxcbik6IG51bWJlcltdW10ge1xuICBjb25zdCBidWNrZXRzOiBudW1iZXJbXVtdID0gZ3JvdXAuY2F0ZWdvcmllcy5tYXAoKCkgPT4gW10pO1xuICBjb25zdCB7IHZhbHVlcywgbG9nIH0gPSBpbnB1dDtcbiAgZm9yIChsZXQgaSA9IDA7IGkgPCB2YWx1ZXMubGVuZ3RoOyBpKyspIHtcbiAgICBpZiAocmVzdHJpY3QgJiYgIXJlc3RyaWN0W2ldKSBjb250aW51ZTtcbiAgICBjb25zdCBjb2RlID0gZ3JvdXAuY29kZXNbaV07XG4gICAgLy8gTk9fQ0FURUdPUlkgaGFzIG5vIGJ1Y2tldCBieSBkZWZpbml0aW9uOyBhbiBvdXQtb2YtcmFuZ2UgY29kZSB3b3VsZFxuICAgIC8vIG90aGVyd2lzZSBzaWxlbnRseSBsYW5kIGluIHRoZSB3cm9uZyBvbmUuXG4gICAgaWYgKGNvZGUgPT09IE5PX0NBVEVHT1JZIHx8IGNvZGUgPj0gYnVja2V0cy5sZW5ndGgpIGNvbnRpbnVlO1xuICAgIGNvbnN0IHYgPSB2YWx1ZXNbaV07XG4gICAgaWYgKCFOdW1iZXIuaXNGaW5pdGUodikpIGNvbnRpbnVlO1xuICAgIGJ1Y2tldHNbY29kZV0ucHVzaChsb2cgPyBNYXRoLmxvZzFwKE1hdGgubWF4KDAsIHYpKSA6IHYpO1xuICB9XG4gIHJldHVybiBidWNrZXRzO1xufVxuXG4vKiogVHJ1ZSB3aGVuIHRoZSBzZWxlY3Rpb24gYWN0dWFsbHkgcmVzdHJpY3RzIGFueXRoaW5nLiAqL1xuZnVuY3Rpb24gYWN0aXZlU2VsZWN0aW9uKHNlbGVjdGlvbjogVWludDhBcnJheSB8IG51bGwgfCB1bmRlZmluZWQpOiBVaW50OEFycmF5IHwgbnVsbCB7XG4gIGlmICghc2VsZWN0aW9uKSByZXR1cm4gbnVsbDtcbiAgZm9yIChsZXQgaSA9IDA7IGkgPCBzZWxlY3Rpb24ubGVuZ3RoOyBpKyspIGlmIChzZWxlY3Rpb25baV0pIHJldHVybiBzZWxlY3Rpb247XG4gIHJldHVybiBudWxsO1xufVxuXG4vKipcbiAqIFRyYWNlcyBmb3Igb25lIGNoYXJ0IGtpbmQuXG4gKlxuICogLSAqKmhpc3RvZ3JhbSoqIOKAlCB0aGUgZnVsbCBkaXN0cmlidXRpb24sIHBsdXMgYW4gb3ZlcmxhaWQgKlNlbGVjdGVkKiB0cmFjZVxuICogICB3aGVuIGEgc2VsZWN0aW9uIGV4aXN0cywgc28gdGhlIHR3byBhcmUgZGlyZWN0bHkgY29tcGFyYWJsZS4gVGhhdFxuICogICBjb21wYXJpc29uIGlzIHRoZSB3aG9sZSBwb2ludCBvZiBsaW5raW5nIHRoZSBjaGFydCB0byB0aGUgbWFwLlxuICogLSAqKnZpb2xpbiAvIGJveCoqIOKAlCBvbmUgcGVyIGNhdGVnb3J5IHdoZW4gZ3JvdXBlZCwgb3RoZXJ3aXNlIGEgc2luZ2xlIHRyYWNlLlxuICogICBUaGVzZSBuYXJyb3cgVE8gdGhlIHNlbGVjdGlvbiByYXRoZXIgdGhhbiBvdmVybGF5aW5nIGl0OiBhIHZpb2xpbiBwZXJcbiAqICAgY2F0ZWdvcnkgcGVyIHNlbGVjdGlvbiBzdGF0ZSBpcyB1bnJlYWRhYmxlLlxuICovXG5leHBvcnQgZnVuY3Rpb24gYnVpbGRPbWljc1RyYWNlcyhraW5kOiBPbWljc0NoYXJ0S2luZCwgaW5wdXQ6IE9taWNzVHJhY2VJbnB1dCk6IHVua25vd25bXSB7XG4gIGNvbnN0IHNlbGVjdGlvbiA9IGFjdGl2ZVNlbGVjdGlvbihpbnB1dC5zZWxlY3Rpb24pO1xuICBjb25zdCBjb2xvciA9IGlucHV0LmNvbG9yID8/IERFRkFVTFRfQ09MT1I7XG5cbiAgaWYgKGtpbmQgPT09ICdoaXN0b2dyYW0nKSB7XG4gICAgY29uc3QgdHJhY2VzOiB1bmtub3duW10gPSBbe1xuICAgICAgdHlwZTogJ2hpc3RvZ3JhbScsXG4gICAgICB4OiBwcmVwYXJlKGlucHV0LCBudWxsKSxcbiAgICAgIG5hbWU6ICdBbGwnLFxuICAgICAgbWFya2VyOiB7IGNvbG9yLCBsaW5lOiB7IHdpZHRoOiAwIH0gfSxcbiAgICAgIG9wYWNpdHk6IHNlbGVjdGlvbiA/IDAuNTUgOiAxLFxuICAgICAgaG92ZXJ0ZW1wbGF0ZTogJyV7eX0gb2JzPGJyPiV7eH08ZXh0cmE+QWxsPC9leHRyYT4nLFxuICAgIH1dO1xuICAgIGlmIChzZWxlY3Rpb24pIHtcbiAgICAgIHRyYWNlcy5wdXNoKHtcbiAgICAgICAgdHlwZTogJ2hpc3RvZ3JhbScsXG4gICAgICAgIHg6IHByZXBhcmUoaW5wdXQsIHNlbGVjdGlvbiksXG4gICAgICAgIG5hbWU6ICdTZWxlY3RlZCcsXG4gICAgICAgIG1hcmtlcjogeyBjb2xvcjogJyNENTVFMDAnLCBsaW5lOiB7IHdpZHRoOiAwIH0gfSxcbiAgICAgICAgb3BhY2l0eTogMC44NSxcbiAgICAgICAgaG92ZXJ0ZW1wbGF0ZTogJyV7eX0gb2JzPGJyPiV7eH08ZXh0cmE+U2VsZWN0ZWQ8L2V4dHJhPicsXG4gICAgICB9KTtcbiAgICB9XG4gICAgcmV0dXJuIHRyYWNlcztcbiAgfVxuXG4gIGNvbnN0IHR5cGUgPSBraW5kOyAvLyAndmlvbGluJyB8ICdib3gnXG4gIGNvbnN0IHNoYXJlZCA9IHtcbiAgICB0eXBlLFxuICAgIC4uLih0eXBlID09PSAndmlvbGluJ1xuICAgICAgPyB7IGJveDogeyB2aXNpYmxlOiB0cnVlIH0sIG1lYW5saW5lOiB7IHZpc2libGU6IHRydWUgfSwgcG9pbnRzOiBmYWxzZSBhcyBjb25zdCB9XG4gICAgICA6IHsgYm94cG9pbnRzOiBmYWxzZSBhcyBjb25zdCB9KSxcbiAgfTtcblxuICBpZiAoaW5wdXQuZ3JvdXApIHtcbiAgICBjb25zdCBidWNrZXRzID0gYnlDYXRlZ29yeShpbnB1dCwgaW5wdXQuZ3JvdXAsIHNlbGVjdGlvbik7XG4gICAgcmV0dXJuIGJ1Y2tldHNcbiAgICAgIC8vIERyb3AgZW1wdHkgY2F0ZWdvcmllczogYW4gZW1wdHkgdmlvbGluIHJlbmRlcnMgYXMgYSBzdHJheSB0aWNrIHdpdGggYVxuICAgICAgLy8gbGFiZWwsIHdoaWNoIHJlYWRzIGFzIGRhdGEuXG4gICAgICAubWFwKCh2YWx1ZXMsIGkpID0+ICh7IHZhbHVlcywgaSB9KSlcbiAgICAgIC5maWx0ZXIoKGIpID0+IGIudmFsdWVzLmxlbmd0aCA+IDApXG4gICAgICAubWFwKChiKSA9PiAoe1xuICAgICAgICAuLi5zaGFyZWQsXG4gICAgICAgIHk6IHRoaW4oYi52YWx1ZXMpLFxuICAgICAgICBuYW1lOiBpbnB1dC5ncm91cCEuY2F0ZWdvcmllc1tiLmldLFxuICAgICAgICBtYXJrZXI6IHsgY29sb3I6IGlucHV0Lmdyb3VwIS5jb2xvcnNbYi5pXSA/PyBjb2xvciB9LFxuICAgICAgICBsaW5lOiB7IGNvbG9yOiBpbnB1dC5ncm91cCEuY29sb3JzW2IuaV0gPz8gY29sb3IgfSxcbiAgICAgIH0pKTtcbiAgfVxuXG4gIGNvbnN0IHZhbHVlcyA9IHRoaW4ocHJlcGFyZShpbnB1dCwgc2VsZWN0aW9uKSk7XG4gIGlmICh2YWx1ZXMubGVuZ3RoID09PSAwKSByZXR1cm4gW107XG4gIHJldHVybiBbe1xuICAgIC4uLnNoYXJlZCxcbiAgICB5OiB2YWx1ZXMsXG4gICAgbmFtZTogc2VsZWN0aW9uID8gJ1NlbGVjdGVkJyA6ICdBbGwnLFxuICAgIG1hcmtlcjogeyBjb2xvciB9LFxuICAgIGxpbmU6IHsgY29sb3IgfSxcbiAgfV07XG59XG5cbi8qKiBMYXlvdXQgZm9yIGEgY2hhcnQga2luZCDigJQgYXhpcyB0aXRsZXMgcmVmbGVjdCB0aGUgbG9nIHRvZ2dsZS4gKi9cbmV4cG9ydCBmdW5jdGlvbiBvbWljc0xheW91dChraW5kOiBPbWljc0NoYXJ0S2luZCwgaW5wdXQ6IE9taWNzVHJhY2VJbnB1dCk6IHVua25vd24ge1xuICBjb25zdCBsYWJlbCA9IGlucHV0LmxvZyA/IGBsb2cxcCgke2lucHV0Lm5hbWV9KWAgOiBpbnB1dC5uYW1lO1xuICBjb25zdCBiYXNlID0ge1xuICAgIG1hcmdpbjogeyB0OiAxMCwgcjogMTAsIGI6IDQwLCBsOiA1MiB9LFxuICAgIGF1dG9zaXplOiB0cnVlLFxuICAgIHNob3dsZWdlbmQ6IGtpbmQgPT09ICdoaXN0b2dyYW0nICYmICEhYWN0aXZlU2VsZWN0aW9uKGlucHV0LnNlbGVjdGlvbiksXG4gICAgbGVnZW5kOiB7IG9yaWVudGF0aW9uOiAnaCcsIHk6IDEuMTIsIHg6IDAgfSxcbiAgICBiYXJnYXA6IDAuMDIsXG4gICAgaG92ZXJtb2RlOiAnY2xvc2VzdCcsXG4gIH07XG4gIGlmIChraW5kID09PSAnaGlzdG9ncmFtJykge1xuICAgIHJldHVybiB7XG4gICAgICAuLi5iYXNlLFxuICAgICAgYmFybW9kZTogJ292ZXJsYXknLFxuICAgICAgeGF4aXM6IHsgdGl0bGU6IHsgdGV4dDogbGFiZWwgfSB9LFxuICAgICAgeWF4aXM6IHsgdGl0bGU6IHsgdGV4dDogJ29ic2VydmF0aW9ucycgfSB9LFxuICAgIH07XG4gIH1cbiAgcmV0dXJuIHtcbiAgICAuLi5iYXNlLFxuICAgIHhheGlzOiB7IGF1dG9tYXJnaW46IHRydWUgfSxcbiAgICB5YXhpczogeyB0aXRsZTogeyB0ZXh0OiBsYWJlbCB9LCB6ZXJvbGluZTogZmFsc2UgfSxcbiAgfTtcbn1cblxuLyoqIFdoZXRoZXIgYSBjaGFydCBraW5kIG5lZWRzIGEgY2F0ZWdvcmljYWwgZ3JvdXBpbmcgdG8gYmUgd29ydGggc2hvd2luZy4gKi9cbmV4cG9ydCBmdW5jdGlvbiBiZW5lZml0c0Zyb21Hcm91cGluZyhraW5kOiBPbWljc0NoYXJ0S2luZCk6IGJvb2xlYW4ge1xuICByZXR1cm4ga2luZCA9PT0gJ3Zpb2xpbicgfHwga2luZCA9PT0gJ2JveCc7XG59XG5cbi8qKiBDYXRlZ29yaWVzIHNob3duIGFzIGJhcnMgYmVmb3JlIHRoZSB0YWlsIGlzIGZvbGRlZCBpbnRvIG9uZSBcIm90aGVyXCIuICovXG5jb25zdCBNQVhfQ09VTlRfQkFSUyA9IDI1O1xuXG5leHBvcnQgaW50ZXJmYWNlIE9taWNzQ291bnRJbnB1dCB7XG4gIC8qKiBUaGUgY2F0ZWdvcmljYWwgYmVpbmcgY291bnRlZCwgd2l0aCB0aGUgbWFwJ3Mgb3duIGNvbG91cnMuICovXG4gIGdyb3VwOiBPbWljc0dyb3VwaW5nO1xuICAvKiogYDFgIG1hcmtzIGEgc2VsZWN0ZWQgb2JzZXJ2YXRpb247IHdoZW4gcHJlc2VudCB0aGUgYmFycyBzaG93IHRoZSBzZWxlY3Rpb25cbiAgICogIGFnYWluc3QgdGhlIHRvdGFsLiAqL1xuICBzZWxlY3Rpb24/OiBVaW50OEFycmF5IHwgbnVsbDtcbiAgLyoqIEJhcnMgYmVmb3JlIHRoZSB0YWlsIGlzIGFnZ3JlZ2F0ZWQuICovXG4gIG1heD86IG51bWJlcjtcbn1cblxuLyoqIFBlci1jYXRlZ29yeSBjb3VudHMsIGJpZ2dlc3QgZmlyc3QsIHdpdGggdGhlIHRhaWwgZm9sZGVkIGludG8gb25lIGJhci4gKi9cbmV4cG9ydCBmdW5jdGlvbiBjb3VudEJ5Q2F0ZWdvcnkoXG4gIGlucHV0OiBPbWljc0NvdW50SW5wdXQsXG4pOiB7IGxhYmVsczogc3RyaW5nW107IGNvbG9yczogc3RyaW5nW107IHRvdGFsczogbnVtYmVyW107IHNlbGVjdGVkOiBudW1iZXJbXSB9IHtcbiAgY29uc3QgeyBjb2RlcywgY2F0ZWdvcmllcywgY29sb3JzIH0gPSBpbnB1dC5ncm91cDtcbiAgY29uc3Qgc2VsZWN0aW9uID0gYWN0aXZlU2VsZWN0aW9uKGlucHV0LnNlbGVjdGlvbik7XG4gIGNvbnN0IHRvdGFscyA9IG5ldyBGbG9hdDY0QXJyYXkoY2F0ZWdvcmllcy5sZW5ndGgpO1xuICBjb25zdCBzZWxlY3RlZCA9IG5ldyBGbG9hdDY0QXJyYXkoY2F0ZWdvcmllcy5sZW5ndGgpO1xuICBmb3IgKGxldCBpID0gMDsgaSA8IGNvZGVzLmxlbmd0aDsgaSsrKSB7XG4gICAgY29uc3QgYyA9IGNvZGVzW2ldO1xuICAgIGlmIChjID09PSBOT19DQVRFR09SWSB8fCBjID49IGNhdGVnb3JpZXMubGVuZ3RoKSBjb250aW51ZTtcbiAgICB0b3RhbHNbY10rKztcbiAgICBpZiAoc2VsZWN0aW9uICYmIHNlbGVjdGlvbltpXSkgc2VsZWN0ZWRbY10rKztcbiAgfVxuXG4gIGNvbnN0IHJhbmtlZCA9IEFycmF5LmZyb20odG90YWxzLCAobiwgYykgPT4gKHsgYywgbiB9KSlcbiAgICAuZmlsdGVyKChyKSA9PiByLm4gPiAwKVxuICAgIC5zb3J0KChhLCBiKSA9PiBiLm4gLSBhLm4pO1xuICBjb25zdCBtYXggPSBpbnB1dC5tYXggPz8gTUFYX0NPVU5UX0JBUlM7XG4gIGNvbnN0IGhlYWQgPSByYW5rZWQuc2xpY2UoMCwgbWF4KTtcbiAgY29uc3QgdGFpbCA9IHJhbmtlZC5zbGljZShtYXgpO1xuXG4gIGNvbnN0IG91dCA9IHtcbiAgICBsYWJlbHM6IGhlYWQubWFwKChyKSA9PiBjYXRlZ29yaWVzW3IuY10pLFxuICAgIGNvbG9yczogaGVhZC5tYXAoKHIpID0+IGNvbG9yc1tyLmNdID8/IERFRkFVTFRfQ09MT1IpLFxuICAgIHRvdGFsczogaGVhZC5tYXAoKHIpID0+IHIubiksXG4gICAgc2VsZWN0ZWQ6IGhlYWQubWFwKChyKSA9PiBzZWxlY3RlZFtyLmNdKSxcbiAgfTtcbiAgLy8gVGhlIHRhaWwgaXMgYWdncmVnYXRlZCByYXRoZXIgdGhhbiBkcm9wcGVkOiAzMzggc3ViY2xhc3NlcyBkbyBub3QgZml0IGFcbiAgLy8gcmVhZGFibGUgYXhpcywgYnV0IHNpbGVudGx5IHNob3dpbmcgMjUgb2YgdGhlbSB3b3VsZCBtaXNzdGF0ZSB0aGUgd2hvbGUuXG4gIGlmICh0YWlsLmxlbmd0aCkge1xuICAgIG91dC5sYWJlbHMucHVzaChgb3RoZXIgKCR7dGFpbC5sZW5ndGh9IGNhdGVnb3JpZXMpYCk7XG4gICAgb3V0LmNvbG9ycy5wdXNoKCcjOWU5ZTllJyk7XG4gICAgb3V0LnRvdGFscy5wdXNoKHRhaWwucmVkdWNlKChhLCByKSA9PiBhICsgci5uLCAwKSk7XG4gICAgb3V0LnNlbGVjdGVkLnB1c2godGFpbC5yZWR1Y2UoKGEsIHIpID0+IGEgKyBzZWxlY3RlZFtyLmNdLCAwKSk7XG4gIH1cbiAgcmV0dXJuIG91dDtcbn1cblxuLyoqXG4gKiBCYXJzIG9mIHBlci1jYXRlZ29yeSBjZWxsIGNvdW50cyDigJQgdGhlIGRpc3RyaWJ1dGlvbiBhIENBVEVHT1JJQ0FMIGNvbG91clxuICogc291cmNlIGhhcy5cbiAqXG4gKiBBIGhpc3RvZ3JhbSBvZiBhIGNhdGVnb3J5IGNvZGUgd291bGQgYmUgbWVhbmluZ2xlc3MgKHRoZSBjb2RlcyBhcmUgbGFiZWxzLCBub3RcbiAqIG1hZ25pdHVkZXMpLCBidXQgXCJob3cgbWFueSBjZWxscyBwZXIgY2xhc3NcIiBpcyBhIHJlYWwgcXVlc3Rpb24sIGFuZCB0aGUgc2FtZSBvbmVcbiAqIHRoZSBsZWdlbmQgaW1wbGllcyB3aXRob3V0IGFuc3dlcmluZy4gSG9yaXpvbnRhbCwgYmVjYXVzZSB0YXhvbm9teSBsYWJlbHMgYXJlXG4gKiBsb25nLCBhbmQgc29ydGVkLCBiZWNhdXNlIHJhbmsgaXMgd2hhdCB0aGUgY2hhcnQgaXMgcmVhZCBmb3IuXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBidWlsZENvdW50VHJhY2VzKGlucHV0OiBPbWljc0NvdW50SW5wdXQpOiB1bmtub3duW10ge1xuICBjb25zdCB7IGxhYmVscywgY29sb3JzLCB0b3RhbHMsIHNlbGVjdGVkIH0gPSBjb3VudEJ5Q2F0ZWdvcnkoaW5wdXQpO1xuICBjb25zdCBzZWxlY3Rpb24gPSBhY3RpdmVTZWxlY3Rpb24oaW5wdXQuc2VsZWN0aW9uKTtcbiAgLy8gUGxvdGx5IGRyYXdzIHRoZSBmaXJzdCBjYXRlZ29yeSBhdCB0aGUgQk9UVE9NIG9mIGEgaG9yaXpvbnRhbCBheGlzLCBzb1xuICAvLyByZXZlcnNlIHRvIHB1dCB0aGUgYmlnZ2VzdCBiYXIgYXQgdGhlIHRvcCB3aGVyZSB0aGUgZXllIHN0YXJ0cy5cbiAgY29uc3QgZmxpcCA9IDxUPihhOiBUW10pOiBUW10gPT4gYS5zbGljZSgpLnJldmVyc2UoKTtcbiAgY29uc3QgdHJhY2VzOiB1bmtub3duW10gPSBbe1xuICAgIHR5cGU6ICdiYXInLFxuICAgIG9yaWVudGF0aW9uOiAnaCcsXG4gICAgeDogZmxpcCh0b3RhbHMpLFxuICAgIHk6IGZsaXAobGFiZWxzKSxcbiAgICBuYW1lOiBzZWxlY3Rpb24gPyAnQWxsJyA6ICdDZWxscycsXG4gICAgbWFya2VyOiB7IGNvbG9yOiBmbGlwKGNvbG9ycykgfSxcbiAgICBvcGFjaXR5OiBzZWxlY3Rpb24gPyAwLjQ1IDogMSxcbiAgICBob3ZlcnRlbXBsYXRlOiAnJXt4fSBvYnM8ZXh0cmE+JXt5fTwvZXh0cmE+JyxcbiAgfV07XG4gIGlmIChzZWxlY3Rpb24pIHtcbiAgICB0cmFjZXMucHVzaCh7XG4gICAgICB0eXBlOiAnYmFyJyxcbiAgICAgIG9yaWVudGF0aW9uOiAnaCcsXG4gICAgICB4OiBmbGlwKHNlbGVjdGVkKSxcbiAgICAgIHk6IGZsaXAobGFiZWxzKSxcbiAgICAgIG5hbWU6ICdTZWxlY3RlZCcsXG4gICAgICBtYXJrZXI6IHsgY29sb3I6IGZsaXAoY29sb3JzKSB9LFxuICAgICAgaG92ZXJ0ZW1wbGF0ZTogJyV7eH0gb2JzPGV4dHJhPiV7eX0gwrcgc2VsZWN0ZWQ8L2V4dHJhPicsXG4gICAgfSk7XG4gIH1cbiAgcmV0dXJuIHRyYWNlcztcbn1cblxuZXhwb3J0IGZ1bmN0aW9uIGNvdW50c0xheW91dChpbnB1dDogT21pY3NDb3VudElucHV0ICYgeyBuYW1lOiBzdHJpbmcgfSk6IHVua25vd24ge1xuICBjb25zdCB7IGxhYmVscyB9ID0gY291bnRCeUNhdGVnb3J5KGlucHV0KTtcbiAgcmV0dXJuIHtcbiAgICAvLyBSb29tIGZvciB0aGUgbGFiZWxzLCBhbmQgYSBoZWlnaHQgdGhhdCBncm93cyB3aXRoIHRoZSBiYXIgY291bnQgc28gMjVcbiAgICAvLyBjYXRlZ29yaWVzIGFyZSBub3QgY3J1c2hlZCBpbnRvIHRoZSBzYW1lIGJveCBhcyAzLlxuICAgIG1hcmdpbjogeyB0OiAxMCwgcjogMTAsIGI6IDQwLCBsOiA4IH0sXG4gICAgYXV0b3NpemU6IHRydWUsXG4gICAgLy8gT3ZlcmxhaWQsIG5vdCBzdGFja2VkOiB0aGUgc2VsZWN0ZWQgYmFyIHJlYWRzIGFnYWluc3QgdGhlIHRvdGFsIGl0IGNhbWVcbiAgICAvLyBmcm9tLCB3aGljaCBpcyB0aGUgY29tcGFyaXNvbiBiZWluZyBtYWRlLlxuICAgIGJhcm1vZGU6ICdvdmVybGF5JyxcbiAgICBzaG93bGVnZW5kOiAhIWFjdGl2ZVNlbGVjdGlvbihpbnB1dC5zZWxlY3Rpb24pLFxuICAgIGxlZ2VuZDogeyBvcmllbnRhdGlvbjogJ2gnLCB5OiAxLjEyLCB4OiAwIH0sXG4gICAgaG92ZXJtb2RlOiAnY2xvc2VzdCcsXG4gICAgeGF4aXM6IHsgdGl0bGU6IHsgdGV4dDogJ29ic2VydmF0aW9ucycgfSB9LFxuICAgIHlheGlzOiB7IGF1dG9tYXJnaW46IHRydWUsIHRpY2tsYWJlbHBvc2l0aW9uOiAnaW5zaWRlJywgdGlja2ZvbnQ6IHsgc2l6ZTogMTAgfSB9LFxuICAgIGhlaWdodDogTWF0aC5tYXgoMTgwLCAyMiAqIGxhYmVscy5sZW5ndGggKyA2MCksXG4gIH07XG59XG5cbi8vIOKUgOKUgCBoZWF0bWFwIOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgFxuXG4vKipcbiAqIEdlbmVzIMOXIGdyb3VwcyBtZWFuIGV4cHJlc3Npb24sIGFzIGEgUGxvdGx5IGhlYXRtYXAuXG4gKlxuICogVGhlIG1hdHJpeCBpdHNlbGYgaXMgY29tcHV0ZWQgYnkgdGhlIHB1cmUgYGhlYXRtYXBNYXRyaXhgIGluXG4gKiBgc3BhdGlhbC9zcGF0aWFsLWhlYXRtYXAudHNgOyB0aGlzIG9ubHkgc2hhcGVzIGl0IGZvciBQbG90bHkuIEtlcHQgaW4gdGhlXG4gKiBtYXRyaXgncyBvd24gcm93LW1ham9yIG9yZGVyIGFuZCBmbGlwcGVkIG9uY2UgaGVyZSwgYmVjYXVzZSBQbG90bHkgZHJhd3NcbiAqIGB6WzBdYCBhdCB0aGUgQk9UVE9NIG9mIHRoZSB5IGF4aXMgd2hpbGUgdGhlIGNhbGxlciBsaXN0cyBnZW5lcyB0b3AtZG93bi5cbiAqXG4gKiBUaGUgY29sb3VyIHNjYWxlIGlzIGl0cyBvd24sIE5PVCB0aGUgbWFwJ3MgYGNvbnRpbnVvdXNDb2xvcm1hcGAuIFRoaXMgaXMgYVxuICogZGlmZmVyZW50IHF1YW50aXR5IOKAlCBhIHotc2NvcmVkIG1lYW4gcGVyIGdyb3VwLCBub3QgYSBwZXItY2VsbCB2YWx1ZSDigJQgc29cbiAqIHNoYXJpbmcgb25lIHNjYWxlIHdvdWxkIGludml0ZSByZWFkaW5nIGEgaGVhdG1hcCBjZWxsIGFzIGlmIGl0IHdlcmUgYSBtYXJrZXJcbiAqIGNvbG91ci4gRGl2ZXJnaW5nIGFuZCBjZW50cmVkIG9uIHplcm8sIGJlY2F1c2UgYWZ0ZXIgei1zY29yaW5nIHRoZSBzaWduIGlzXG4gKiB0aGUgcmVhZGluZzogYWJvdmUgb3IgYmVsb3cgdGhpcyBnZW5lJ3MgYXZlcmFnZSBhY3Jvc3MgdGhlIGdyb3Vwcy5cbiAqL1xuLyoqXG4gKiBBbiBlbWJlZGRpbmcgc2NhdHRlciDigJQgYSBVTUFQLCB0LVNORSBvciBQQ0EgcGxhbmUgb3ZlciB0aGUgc2FtZSBvYnNlcnZhdGlvbnMuXG4gKlxuICogQW5zd2VycyBhIGRpZmZlcmVudCBxdWVzdGlvbiBmcm9tIHRoZSBtYXA6IHRoZSBtYXAgc2F5cyBXSEVSRSBhIHBvcHVsYXRpb24gc2l0cyBpbiB0aGUgdGlzc3VlLFxuICogdGhlIGVtYmVkZGluZyBzYXlzIHdoaWNoIHBvcHVsYXRpb25zIHRoZXJlIGFyZSBhbmQgaG93IGNsb3NlIHRoZXkgYXJlIGluIGV4cHJlc3Npb24uIFJlYWQgc2lkZVxuICogYnkgc2lkZSwgYW5kIHNlbGVjdGluZyBpbiBvbmUgaGlnaGxpZ2h0aW5nIHRoZSBvdGhlciwgaXMgdGhlIHdob2xlIHBvaW50IG9mIGhhdmluZyBib3RoLlxuICovXG5leHBvcnQgaW50ZXJmYWNlIE9taWNzRW1iZWRkaW5nSW5wdXQge1xuICAvKiogRW1iZWRkaW5nIGNvb3JkaW5hdGVzLCBpbmRleC1hbGlnbmVkIHdpdGggdGhlIG9ic2VydmF0aW9ucy4gKi9cbiAgeDogRmxvYXQzMkFycmF5O1xuICB5OiBGbG9hdDMyQXJyYXk7XG4gIC8qKlxuICAgKiBUaGlyZCBkaW1lbnNpb24sIHdoZW4gdGhlIGVtYmVkZGluZyBoYXMgb25lLlxuICAgKlxuICAgKiBJdHMgcHJlc2VuY2UgaXMgd2hhdCBzd2l0Y2hlcyB0aGUgcGxvdCB0byBhIHJvdGF0YWJsZSAzRCBzY2F0dGVyLiBBIDNEIGVtYmVkZGluZyBpc1xuICAgKiBhbHdheXMgQ09NUFVURUQg4oCUIGV2ZXJ5IGVtYmVkZGluZyBwdWJsaXNoZWQgd2l0aCBhIHNwYXRpYWwgZGF0YXNldCBpcyAyRCwgYmVjYXVzZSBhXG4gICAqIFVNQVAgZXhpc3RzIHRvIGJlIGxvb2tlZCBhdCDigJQgc28gYGRlcml2ZWRgIGlzIGV4cGVjdGVkIGFsb25nc2lkZSBpdC5cbiAgICovXG4gIHo/OiBGbG9hdDMyQXJyYXk7XG4gIC8qKiBBeGlzIGxhYmVsIHN0ZW0sIGUuZy4gXCJVTUFQXCIg4oCUIHRoZSBheGVzIGJlY29tZSBcIlVNQVAgMVwiIC8gXCJVTUFQIDJcIi4gKi9cbiAgbGFiZWw6IHN0cmluZztcbiAgLyoqIENvbG91ciBieSBhIGNhdGVnb3JpY2FsIGNvbHVtbjogcGVyLW9ic2VydmF0aW9uIGNvZGVzIHBsdXMgdGhlIGNhdGVnb3J5IG5hbWVzL2NvbG91cnMuICovXG4gIGNhdGVnb3JpZXM/OiB7XG4gICAgY29kZXM6IFVpbnQxNkFycmF5O1xuICAgIG5hbWVzOiByZWFkb25seSBzdHJpbmdbXTtcbiAgICBjb2xvcnM6IHJlYWRvbmx5IHN0cmluZ1tdO1xuICB9O1xuICAvKiogTWFya2VyIGRpYW1ldGVyIGluIHB4LiAqL1xuICBzaXplPzogbnVtYmVyO1xuICAvKipcbiAgICogU2VsZWN0aW9uIG1hc2sgb3ZlciB0aGUgb2JzZXJ2YXRpb25zLiBXaGVuIHByZXNlbnQsIHVuc2VsZWN0ZWQgcG9pbnRzIGFyZSBkaW1tZWQgcmF0aGVyIHRoYW5cbiAgICogZHJvcHBlZDogdGhlIHNoYXBlIG9mIHRoZSB3aG9sZSBlbWJlZGRpbmcgaXMgdGhlIGNvbnRleHQgdGhhdCBtYWtlcyBhIHNlbGVjdGlvbiBsZWdpYmxlLCBhbmRcbiAgICogcmVtb3ZpbmcgaXQgd291bGQgbGVhdmUgYSBoYW5kZnVsIG9mIGRvdHMgZmxvYXRpbmcgaW4gYW4gZW1wdHkgcGxhbmUuXG4gICAqL1xuICBzZWxlY3Rpb24/OiBVaW50OEFycmF5O1xuICAvKiogVHJ1ZSB3aGVuIHRoZSBjb29yZGluYXRlcyB3ZXJlIGNvbXB1dGVkIGhlcmUgcmF0aGVyIHRoYW4gcHVibGlzaGVkIHdpdGggdGhlIGRhdGFzZXQuICovXG4gIGRlcml2ZWQ/OiBib29sZWFuO1xuICAvKipcbiAgICogRnJhY3Rpb24gb2YgdmFyaWFuY2UgcGVyIGF4aXMsIGZvciBhIExJTkVBUiBlbWJlZGRpbmcuXG4gICAqXG4gICAqIFByZXNlbnQgZm9yIGEgUENBIGFuZCBhYnNlbnQgZm9yIGEgVU1BUCwgYW5kIHRoYXQgZGlmZmVyZW5jZSBpcyB0aGUgcG9pbnQgb2Ygc2hvd2luZ1xuICAgKiBhIFBDQSBhdCBhbGw6IGl0cyBheGVzIGFyZSBvcmRlcmVkIGFuZCBlYWNoIGV4cGxhaW5zIGEgbWVhc3VyYWJsZSBzaGFyZSBvZiB0aGVcbiAgICogdmFyaWFuY2UsIHNvIFwiUEMxICgyMyUpXCIgc2F5cyBzb21ldGhpbmcgYSByZWFkZXIgY2FuIGFjdCBvbi4gQSBVTUFQJ3MgY29vcmRpbmF0ZXMgYXJlXG4gICAqIGFuIGFyYml0cmFyeSBvdXRwdXQgb2YgYW4gb3B0aW1pc2F0aW9uIOKAlCB1bm9yZGVyZWQsIHVuaXRsZXNzLCBhbmQgcmVwcm9kdWNpYmxlIG9ubHlcbiAgICogdXAgdG8gYSByb3RhdGlvbiDigJQgc28gdGhlcmUgaXMgbm90aGluZyB0byBsYWJlbCB0aGVtIHdpdGguXG4gICAqL1xuICB2YXJpYW5jZVJhdGlvPzogbnVtYmVyW107XG4gIC8qKlxuICAgKiBUaGUgdmlldyB0byBrZWVwIGFjcm9zcyBhIHJlZHJhdy5cbiAgICpcbiAgICogYFBsb3RseS5yZWFjdGAgcmVzZXRzIHRoZSAzRCBzY2VuZSBjYW1lcmEgYW5kIGFueSB6b29tZWQgMkQgYXhpcyByYW5nZSB1bmxlc3MgdGhlXG4gICAqIGxheW91dCBjYXJyaWVzIHRoZW0sIHNvIHJlY29sb3VyaW5nIG9yIHNlbGVjdGluZyB3b3VsZCB0aHJvdyBhd2F5IGFuIG9yaWVudGF0aW9uIHRoZVxuICAgKiB1c2VyIGhhZCBzZXQgdXAuIFJvdGF0aW5nIGEgY2xvdWQgdG8gc2VlIGEgc3RydWN0dXJlIGFuZCBsb3NpbmcgaXQgb24gdGhlIG5leHQgY2xpY2tcbiAgICogbWFrZXMgdGhlIHBsb3QgdW51c2FibGUgZm9yIHRoZSB0aGluZyBpdCBpcyBmb3IuXG4gICAqXG4gICAqIGBjYW1lcmFgIGlzIGEgM0Qgc2NlbmUgY2FtZXJhOyBgcmFuZ2VzYCBhcmUgMkQgYXhpcyByYW5nZXMsIGFuZCBhcmUgb25seSBwYXNzZWQgd2hlblxuICAgKiB0aGUgdXNlciBoYXMgYWN0dWFsbHkgem9vbWVkIOKAlCBmcmVlemluZyBhbiBhdXRvcmFuZ2VkIGF4aXMgd291bGQgc3RvcCB0aGUgcGxvdFxuICAgKiByZS1maXR0aW5nIHdoZW4gdGhlIGRhdGEgY2hhbmdlcy5cbiAgICovXG4gIHZpZXc/OiB7IGNhbWVyYT86IHVua25vd247IHJhbmdlcz86IHsgeDogdW5rbm93bjsgeTogdW5rbm93biB9IH07XG59XG5cbi8qKlxuICogUGFzdCB0aGlzIG1hbnkgY2F0ZWdvcmllcywgb25lIHRyYWNlIGVhY2ggc3RvcHMgYmVpbmcgd29ydGggaXQuXG4gKlxuICogQSB0cmFjZSBwZXIgY2F0ZWdvcnkgYnV5cyBhIGxlZ2VuZCB3aG9zZSBlbnRyaWVzIHRvZ2dsZSDigJQgY2xpY2sgb25lIHRvIGlzb2xhdGUgYSBwb3B1bGF0aW9uLFxuICogd2hpY2ggaXMgaG93IHRoZXNlIHBsb3RzIGFyZSBhY3R1YWxseSByZWFkLiBCdXQgUGxvdGx5IGhvbGRzIHBlci10cmFjZSBzdGF0ZSwgYW5kIGEgbGVnZW5kIG9mXG4gKiBodW5kcmVkcyBvZiBlbnRyaWVzIGlzIHVucmVhZGFibGUgYW55d2F5ICh0aGUgQUJDIGF0bGFzIGhhcyAzMzggc3ViY2xhc3NlcyksIHNvIGJleW9uZCB0aGUgY2FwXG4gKiBldmVyeXRoaW5nIGdvZXMgaW50byBPTkUgdHJhY2Ugd2l0aCBhIHBlci1wb2ludCBjb2xvdXI6IG5vIGxlZ2VuZCwgYnV0IGl0IHN0aWxsIGRyYXdzLlxuICovXG5leHBvcnQgY29uc3QgRU1CRURESU5HX01BWF9MRUdFTkRfQ0FURUdPUklFUyA9IDQwO1xuXG4vKipcbiAqIENhdGVnb3JpZXMgcGFzdCB3aGljaCB0aGUgbGVnZW5kIGlzIG5vdCBEUkFXTiwgdGhvdWdoIHRoZSB0cmFjZXMgc3RheSBzcGxpdC5cbiAqXG4gKiBBIGxlZ2VuZCBpcyBvbmx5IHdvcnRoIGl0cyBzcGFjZSBpZiBpdCBmaXRzLiBzZXFGSVNIJ3MgMjIgY2VsbCB0eXBlcyBzdGFjayBpbnRvIG9uZSB0YWxsXG4gKiBjb2x1bW4gaW4gYSBkb2NrZWQgcGFuZWwsIG92ZXJsYXBwaW5nIHRoZSBheGlzIHRpdGxlIGFuZCBydW5uaW5nIG9mZiB0aGUgYm90dG9tIOKAlCBhbmRcbiAqIHRoZSBjb2xvdXJzIGFscmVhZHkgbWF0Y2ggdGhlIG1hcCwgd2hvc2Ugb3duIHBhbmVsIGxpc3RzIHRoZW0sIHdoaWxlIGhvdmVyIG5hbWVzIHRoZVxuICogY2F0ZWdvcnkgdW5kZXIgdGhlIGN1cnNvci4gU28gcGFzdCB0aGlzIHRoZSBwbG90IHRha2VzIHRoZSB3aG9sZSBwYW5lbCBhbmQgdGhlIGxlZ2VuZFxuICogaXMgZHJvcHBlZCByYXRoZXIgdGhhbiBzaG93biBiYWRseS5cbiAqL1xuZXhwb3J0IGNvbnN0IEVNQkVERElOR19NQVhfTEVHRU5EX1NIT1dOID0gMTA7XG5cbi8qKiBEaW1taW5nIGFwcGxpZWQgdG8gdW5zZWxlY3RlZCBwb2ludHMsIG1hdGNoaW5nIHRoZSBtYXAncyBtdXRlZCBvcGFjaXR5LiAqL1xuY29uc3QgRU1CRURESU5HX01VVEVEX09QQUNJVFkgPSAwLjE1O1xuXG4vKipcbiAqIE1peCBhIGhleCBjb2xvdXIgdG93YXJkIHdoaXRlIGJ5IGBhbW91bnRgLlxuICpcbiAqIEhvdyB1bnNlbGVjdGVkIHBvaW50cyBhcmUgZGltbWVkIGluIDNELiBgc2NhdHRlcjNkYCBhY2NlcHRzIGBtYXJrZXIub3BhY2l0eWAgb25seSBhcyBhXG4gKiBTQ0FMQVIg4oCUIGEgcGVyLXBvaW50IGFycmF5IGlzIHNpbGVudGx5IGNvbGxhcHNlZCB0byB0aGUgZmlyc3QgdmFsdWUsIHZlcmlmaWVkIGFnYWluc3RcbiAqIHRoZSBidW5kbGVkIFBsb3RseSDigJQgc28gdGhlIHBlci1wb2ludCBvcGFjaXR5IHRoYXQgZGltcyB0aGUgMkQgcGxvdCBkb2VzIG5vdGhpbmcgdGhlcmUsXG4gKiBhbmQgYSBzZWxlY3Rpb24gYXBwZWFyZWQgdG8gaGlnaGxpZ2h0IG5vdGhpbmcgaW4gM0QuIENvbG91ciBhcnJheXMgQVJFIGhvbm91cmVkLCBzb1xuICogdGhlIHNhbWUgZWZmZWN0IGlzIHByb2R1Y2VkIGJ5IG1peGluZyB0b3dhcmQgdGhlIHBhcGVyIGluc3RlYWQuXG4gKi9cbmZ1bmN0aW9uIHRvd2FyZFBhcGVyKGhleDogc3RyaW5nLCBhbW91bnQ6IG51bWJlcik6IHN0cmluZyB7XG4gIGNvbnN0IGNsZWFuID0gaGV4LnJlcGxhY2UoJyMnLCAnJyk7XG4gIGNvbnN0IGZ1bGwgPSBjbGVhbi5sZW5ndGggPT09IDNcbiAgICA/IGNsZWFuLnNwbGl0KCcnKS5tYXAoKGMpID0+IGMgKyBjKS5qb2luKCcnKVxuICAgIDogY2xlYW47XG4gIGNvbnN0IG4gPSBOdW1iZXIucGFyc2VJbnQoZnVsbCwgMTYpO1xuICBpZiAoIU51bWJlci5pc0Zpbml0ZShuKSB8fCBmdWxsLmxlbmd0aCAhPT0gNikgcmV0dXJuIGhleDtcbiAgY29uc3QgbWl4ID0gKGM6IG51bWJlcik6IG51bWJlciA9PiBNYXRoLnJvdW5kKGMgKyAoMjU1IC0gYykgKiBhbW91bnQpO1xuICBjb25zdCByID0gbWl4KChuID4+IDE2KSAmIDB4ZmYpO1xuICBjb25zdCBnID0gbWl4KChuID4+IDgpICYgMHhmZik7XG4gIGNvbnN0IGIgPSBtaXgobiAmIDB4ZmYpO1xuICByZXR1cm4gYCMkeygociA8PCAxNikgfCAoZyA8PCA4KSB8IGIpLnRvU3RyaW5nKDE2KS5wYWRTdGFydCg2LCAnMCcpfWA7XG59XG5cbmNvbnN0IERFRkFVTFRfRU1CRURESU5HX1BPSU5UX1NJWkUgPSA0O1xuXG5leHBvcnQgZnVuY3Rpb24gYnVpbGRFbWJlZGRpbmdUcmFjZXMoaW5wdXQ6IE9taWNzRW1iZWRkaW5nSW5wdXQpOiB1bmtub3duW10ge1xuICBjb25zdCB7IHgsIHksIGNhdGVnb3JpZXMsIHNlbGVjdGlvbiB9ID0gaW5wdXQ7XG4gIGNvbnN0IG4gPSBNYXRoLm1pbih4Lmxlbmd0aCwgeS5sZW5ndGgpO1xuICBpZiAobiA9PT0gMCkgcmV0dXJuIFtdO1xuICBjb25zdCB6ID0gaW5wdXQuejtcbiAgLy8gYHNjYXR0ZXJnbGAgZm9yIHRoZSBwbGFuZSDigJQgMTBeNC0xMF42IHBvaW50cywgd2hpY2ggdGhlIFNWRyByZW5kZXJlciB3b3VsZCBub3RcbiAgLy8gc3Vydml2ZS4gYHNjYXR0ZXIzZGAgZm9yIHRoZSBjbG91ZDogV2ViR0wgdG9vLCBidXQgYSBkaWZmZXJlbnQgdHJhY2UgdHlwZSB3aXRoIGl0c1xuICAvLyBvd24gc2NlbmUsIHdoaWNoIGlzIHdoeSBhIHRoaXJkIGRpbWVuc2lvbiBjYW5ub3QganVzdCBiZSBhZGRlZCB0byB0aGUgZm9ybWVyLiBJdFxuICAvLyBjb3N0cyBtb3JlIHBlciBwb2ludCwgc28gaXQgc3VpdHMgdGhpcyBzY2FsZSBhbmQgbm90IG1pbGxpb25zLlxuICBjb25zdCB0eXBlID0geiA/ICdzY2F0dGVyM2QnIDogJ3NjYXR0ZXJnbCc7XG4gIGNvbnN0IG1hcmtlclNpemUgPSB6ID8gTWF0aC5tYXgoMSwgKGlucHV0LnNpemUgPz8gREVGQVVMVF9FTUJFRERJTkdfUE9JTlRfU0laRSkgLSAyKVxuICAgIDogKGlucHV0LnNpemUgPz8gREVGQVVMVF9FTUJFRERJTkdfUE9JTlRfU0laRSk7XG4gIGNvbnN0IG9wYWNpdHlGb3IgPSAoaTogbnVtYmVyKTogbnVtYmVyID0+XG4gICAgIXNlbGVjdGlvbiB8fCBzZWxlY3Rpb25baV0gPyAxIDogRU1CRURESU5HX01VVEVEX09QQUNJVFk7XG4gIGNvbnN0IGlzU2VsZWN0ZWQgPSAoaTogbnVtYmVyKTogYm9vbGVhbiA9PiAhc2VsZWN0aW9uIHx8IHNlbGVjdGlvbltpXSA9PT0gMTtcbiAgLy8gSW4gM0QgdGhlIGRpbW1pbmcgaGFzIHRvIGJlIGluIHRoZSBDT0xPVVIsIHNpbmNlIGEgcGVyLXBvaW50IG9wYWNpdHkgYXJyYXkgaXNcbiAgLy8gaWdub3JlZCB0aGVyZS4gQ2FjaGVkIHBlciBpbnB1dCBjb2xvdXI6IDE5ayBsb29rdXBzIG9mIHRoZSBzYW1lIGZldyBjYXRlZ29yaWVzLlxuICBjb25zdCBkaW1DYWNoZSA9IG5ldyBNYXA8c3RyaW5nLCBzdHJpbmc+KCk7XG4gIGNvbnN0IHNoYWRlID0gKGhleDogc3RyaW5nLCBpOiBudW1iZXIpOiBzdHJpbmcgPT4ge1xuICAgIGlmICgheiB8fCBpc1NlbGVjdGVkKGkpKSByZXR1cm4gaGV4O1xuICAgIGNvbnN0IGhpdCA9IGRpbUNhY2hlLmdldChoZXgpO1xuICAgIGlmIChoaXQpIHJldHVybiBoaXQ7XG4gICAgY29uc3QgZGltbWVkID0gdG93YXJkUGFwZXIoaGV4LCAxIC0gRU1CRURESU5HX01VVEVEX09QQUNJVFkpO1xuICAgIGRpbUNhY2hlLnNldChoZXgsIGRpbW1lZCk7XG4gICAgcmV0dXJuIGRpbW1lZDtcbiAgfTtcbiAgLyoqIFBlci1wb2ludCBvcGFjaXR5LCB3aGljaCBvbmx5IHRoZSAyRCB0cmFjZSB0eXBlcyBob25vdXIuICovXG4gIGNvbnN0IG9wYWNpdHlBcnJheSA9IChpbmRpY2VzOiByZWFkb25seSBudW1iZXJbXSk6IG51bWJlcltdIHwgdW5kZWZpbmVkID0+XG4gICAgc2VsZWN0aW9uICYmICF6ID8gaW5kaWNlcy5tYXAob3BhY2l0eUZvcikgOiB1bmRlZmluZWQ7XG5cbiAgaWYgKCFjYXRlZ29yaWVzIHx8IGNhdGVnb3JpZXMubmFtZXMubGVuZ3RoID09PSAwKSB7XG4gICAgcmV0dXJuIFt7XG4gICAgICB0eXBlLFxuICAgICAgbW9kZTogJ21hcmtlcnMnLFxuICAgICAgeDogQXJyYXkuZnJvbSh4LnN1YmFycmF5KDAsIG4pKSxcbiAgICAgIHk6IEFycmF5LmZyb20oeS5zdWJhcnJheSgwLCBuKSksXG4gICAgICAuLi4oeiA/IHsgejogQXJyYXkuZnJvbSh6LnN1YmFycmF5KDAsIG4pKSB9IDoge30pLFxuICAgICAgLy8gVGhlIE9CU0VSVkFUSU9OIGluZGV4IHBlciBwb2ludCwgY2FycmllZCB0aHJvdWdoIHNvIGEgbGFzc28gY2FuIGJlIHR1cm5lZCBiYWNrXG4gICAgICAvLyBpbnRvIGEgc2VsZWN0aW9uLiBQbG90bHkgcmVwb3J0cyBhIHNlbGVjdGVkIHBvaW50IGJ5IGl0cyBwb3NpdGlvbiB3aXRoaW4gaXRzXG4gICAgICAvLyB0cmFjZSwgd2hpY2ggaXMgbm90IHRoZSBvYnNlcnZhdGlvbiBpbmRleCBvbmNlIHRoZSBwb2ludHMgYXJlIHNwbGl0IGJ5IGNhdGVnb3J5LlxuICAgICAgY3VzdG9tZGF0YTogQXJyYXkuZnJvbSh7IGxlbmd0aDogbiB9LCAoXywgaSkgPT4gaSksXG4gICAgICBtYXJrZXI6IHtcbiAgICAgICAgc2l6ZTogbWFya2VyU2l6ZSxcbiAgICAgICAgLy8gQSBmbGF0IGNvbG91ciBub3JtYWxseTsgcGVyIHBvaW50IG9uY2UgYSBzZWxlY3Rpb24gaGFzIHRvIGRpbSBzb21lIG9mIHRoZW0gaW5cbiAgICAgICAgLy8gM0QsIHdoZXJlIG9wYWNpdHkgYXJyYXlzIGFyZSBpZ25vcmVkLlxuICAgICAgICBjb2xvcjogc2VsZWN0aW9uICYmIHpcbiAgICAgICAgICA/IEFycmF5LmZyb20oeyBsZW5ndGg6IG4gfSwgKF8sIGkpID0+IHNoYWRlKCcjNGM3MmIwJywgaSkpXG4gICAgICAgICAgOiAnIzRjNzJiMCcsXG4gICAgICAgIC4uLihvcGFjaXR5QXJyYXkoQXJyYXkuZnJvbSh7IGxlbmd0aDogbiB9LCAoXywgaSkgPT4gaSkpXG4gICAgICAgICAgPyB7IG9wYWNpdHk6IEFycmF5LmZyb20oeyBsZW5ndGg6IG4gfSwgKF8sIGkpID0+IG9wYWNpdHlGb3IoaSkpIH1cbiAgICAgICAgICA6IHt9KSxcbiAgICAgIH0sXG4gICAgICBob3ZlcmluZm86ICdub25lJyxcbiAgICAgIHNob3dsZWdlbmQ6IGZhbHNlLFxuICAgIH1dO1xuICB9XG5cbiAgY29uc3QgeyBjb2RlcywgbmFtZXMsIGNvbG9ycyB9ID0gY2F0ZWdvcmllcztcbiAgaWYgKG5hbWVzLmxlbmd0aCA+IEVNQkVERElOR19NQVhfTEVHRU5EX0NBVEVHT1JJRVMpIHtcbiAgICAvLyBPbmUgdHJhY2UsIHBlci1wb2ludCBjb2xvdXIuIEhvdmVyIHN0aWxsIG5hbWVzIHRoZSBjYXRlZ29yeSwgd2hpY2ggaXMgdGhlIHBhcnQgdGhhdFxuICAgIC8vIG1hdHRlcnM7IHRoZSBsZWdlbmQgaXMgd2hhdCBpcyBsb3N0LlxuICAgIHJldHVybiBbe1xuICAgICAgdHlwZSxcbiAgICAgIG1vZGU6ICdtYXJrZXJzJyxcbiAgICAgIHg6IEFycmF5LmZyb20oeC5zdWJhcnJheSgwLCBuKSksXG4gICAgICB5OiBBcnJheS5mcm9tKHkuc3ViYXJyYXkoMCwgbikpLFxuICAgICAgLi4uKHogPyB7IHo6IEFycmF5LmZyb20oei5zdWJhcnJheSgwLCBuKSkgfSA6IHt9KSxcbiAgICAgIG1hcmtlcjoge1xuICAgICAgICBzaXplOiBtYXJrZXJTaXplLFxuICAgICAgICBjb2xvcjogQXJyYXkuZnJvbSh7IGxlbmd0aDogbiB9LCAoXywgaSkgPT4gc2hhZGUoY29sb3JzW2NvZGVzW2ldXSA/PyAnIzk5OTk5OScsIGkpKSxcbiAgICAgICAgLi4uKG9wYWNpdHlBcnJheShBcnJheS5mcm9tKHsgbGVuZ3RoOiBuIH0sIChfLCBpKSA9PiBpKSlcbiAgICAgICAgICA/IHsgb3BhY2l0eTogQXJyYXkuZnJvbSh7IGxlbmd0aDogbiB9LCAoXywgaSkgPT4gb3BhY2l0eUZvcihpKSkgfVxuICAgICAgICAgIDoge30pLFxuICAgICAgfSxcbiAgICAgIGN1c3RvbWRhdGE6IEFycmF5LmZyb20oeyBsZW5ndGg6IG4gfSwgKF8sIGkpID0+IGkpLFxuICAgICAgdGV4dDogQXJyYXkuZnJvbSh7IGxlbmd0aDogbiB9LCAoXywgaSkgPT4gbmFtZXNbY29kZXNbaV1dID8/ICd1bmFzc2lnbmVkJyksXG4gICAgICBob3ZlcnRlbXBsYXRlOiAnJXt0ZXh0fTxleHRyYT48L2V4dHJhPicsXG4gICAgICBzaG93bGVnZW5kOiBmYWxzZSxcbiAgICB9XTtcbiAgfVxuXG4gIC8vIE9uZSB0cmFjZSBwZXIgY2F0ZWdvcnk6IHRoZSBsZWdlbmQgZW50cmllcyB0b2dnbGUsIHNvIGEgcG9wdWxhdGlvbiBjYW4gYmUgaXNvbGF0ZWQgYnlcbiAgLy8gY2xpY2tpbmcgcmF0aGVyIHRoYW4gYnkgcmUtY29sb3VyaW5nIHRoZSB3aG9sZSBwbG90LlxuICBjb25zdCBidWNrZXRzOiBudW1iZXJbXVtdID0gbmFtZXMubWFwKCgpID0+IFtdKTtcbiAgZm9yIChsZXQgaSA9IDA7IGkgPCBuOyBpKyspIHtcbiAgICBjb25zdCBjID0gY29kZXNbaV07XG4gICAgLy8gTk9fQ0FURUdPUlksIG9yIGEgY29kZSBwYXN0IHRoZSBsaXN0LCBpcyB1bmFzc2lnbmVkIOKAlCBkcm9wcGVkIHJhdGhlciB0aGFuIGRyYXduIGluIGFcbiAgICAvLyBjb2xvdXIgdGhhdCB3b3VsZCByZWFkIGFzIGEgcG9wdWxhdGlvbiBvZiBpdHMgb3duLlxuICAgIGlmIChjIDwgYnVja2V0cy5sZW5ndGgpIGJ1Y2tldHNbY10ucHVzaChpKTtcbiAgfVxuICByZXR1cm4gYnVja2V0c1xuICAgIC5tYXAoKGlkeCwgYykgPT4gKHsgaWR4LCBjIH0pKVxuICAgIC5maWx0ZXIoKHsgaWR4IH0pID0+IGlkeC5sZW5ndGggPiAwKVxuICAgIC5tYXAoKHsgaWR4LCBjIH0pID0+ICh7XG4gICAgICB0eXBlLFxuICAgICAgbW9kZTogJ21hcmtlcnMnLFxuICAgICAgbmFtZTogbmFtZXNbY10sXG4gICAgICB4OiBpZHgubWFwKChpKSA9PiB4W2ldKSxcbiAgICAgIHk6IGlkeC5tYXAoKGkpID0+IHlbaV0pLFxuICAgICAgLi4uKHogPyB7IHo6IGlkeC5tYXAoKGkpID0+IHpbaV0pIH0gOiB7fSksXG4gICAgICAvLyBUaGlzIHRyYWNlJ3MgcG9pbnRzIEFSRSBhIHN1YnNldCwgc28gdGhlIG9ic2VydmF0aW9uIGluZGV4IGhhcyB0byB0cmF2ZWwgd2l0aFxuICAgICAgLy8gdGhlbTsgYHBvaW50SW5kZXhgIGFsb25lIHdvdWxkIGFkZHJlc3MgdGhlIHdyb25nIGNlbGwuXG4gICAgICBjdXN0b21kYXRhOiBpZHgsXG4gICAgICBtYXJrZXI6IHtcbiAgICAgICAgc2l6ZTogbWFya2VyU2l6ZSxcbiAgICAgICAgY29sb3I6IHNlbGVjdGlvbiAmJiB6XG4gICAgICAgICAgPyBpZHgubWFwKChpKSA9PiBzaGFkZShjb2xvcnNbY10gPz8gJyM5OTk5OTknLCBpKSlcbiAgICAgICAgICA6IChjb2xvcnNbY10gPz8gJyM5OTk5OTknKSxcbiAgICAgICAgLi4uKG9wYWNpdHlBcnJheShpZHgpID8geyBvcGFjaXR5OiBpZHgubWFwKG9wYWNpdHlGb3IpIH0gOiB7fSksXG4gICAgICB9LFxuICAgICAgLy8gU3BsaXQgcGVyIGNhdGVnb3J5IHJlZ2FyZGxlc3MsIHNvIGhvdmVyIG5hbWVzIGl0IGFuZCBhIGZ1dHVyZSBpc29sYXRlIGNvbnRyb2xcbiAgICAgIC8vIGhhcyBzb21ldGhpbmcgdG8gdG9nZ2xlOyBvbmx5IHRoZSBsZWdlbmQncyBWSVNJQklMSVRZIGRlcGVuZHMgb24gdGhlIGNvdW50LlxuICAgICAgc2hvd2xlZ2VuZDogbmFtZXMubGVuZ3RoIDw9IEVNQkVERElOR19NQVhfTEVHRU5EX1NIT1dOLFxuICAgICAgaG92ZXJ0ZW1wbGF0ZTogYCR7bmFtZXNbY119PGV4dHJhPjwvZXh0cmE+YCxcbiAgICB9KSk7XG59XG5cbi8qKlxuICogQXhpcyB0aXRsZTogdGhlIGVtYmVkZGluZydzIG5hbWUsIHRoZSBheGlzIG51bWJlciwgYW5kIGl0cyB2YXJpYW5jZSBzaGFyZSB3aGVuIHRoZXJlIGlzXG4gKiBvbmUgdG8gcmVwb3J0LlxuICovXG5mdW5jdGlvbiBheGlzVGl0bGUoc3RlbTogc3RyaW5nLCBheGlzOiBudW1iZXIsIHZhcmlhbmNlUmF0aW8/OiBudW1iZXJbXSk6IHN0cmluZyB7XG4gIGNvbnN0IHNoYXJlID0gdmFyaWFuY2VSYXRpbz8uW2F4aXMgLSAxXTtcbiAgaWYgKHNoYXJlID09PSB1bmRlZmluZWQgfHwgIU51bWJlci5pc0Zpbml0ZShzaGFyZSkpIHJldHVybiBgJHtzdGVtfSAke2F4aXN9YDtcbiAgLy8gT25lIGRlY2ltYWw6IHRoZSBkaWZmZXJlbmNlIGJldHdlZW4gMjMuNCUgYW5kIDIzJSBpcyB3b3J0aCBzZWVpbmcgd2hlbiBjb21wYXJpbmdcbiAgLy8gY29tcG9uZW50cywgYW5kIG1vcmUgZGlnaXRzIHRoYW4gdGhhdCBpcyBub2lzZSBmcm9tIHRoZSBlc3RpbWF0ZS5cbiAgcmV0dXJuIGAke3N0ZW19ICR7YXhpc30gKCR7KHNoYXJlICogMTAwKS50b0ZpeGVkKDEpfSUpYDtcbn1cblxuZXhwb3J0IGZ1bmN0aW9uIGVtYmVkZGluZ0xheW91dChpbnB1dDogT21pY3NFbWJlZGRpbmdJbnB1dCk6IHVua25vd24ge1xuICBjb25zdCBzdGVtID0gaW5wdXQubGFiZWwgfHwgJ0VtYmVkZGluZyc7XG4gIGNvbnN0IHZyID0gaW5wdXQudmFyaWFuY2VSYXRpbztcbiAgLy8gTm8gYW5ub3RhdGlvbiBmb3IgYSBkZXJpdmVkIGVtYmVkZGluZy4gVGhhdCBhIHJlY29tcHV0ZWQgVU1BUCBpcyBub3QgdGhlIHB1Ymxpc2hlZFxuICAvLyBwaWN0dXJlIGRvZXMgbmVlZCBzYXlpbmcg4oCUIGJ1dCB0aGUgcGFuZWwncyBjYXB0aW9uIGFscmVhZHkgc2F5cyBpdCwgYW5kIHJlcGVhdGluZyBpdFxuICAvLyBvdmVyIHRoZSBwbG90IGNvc3QgYSBzdHJpcCBvZiB0aGUgcGFuZWwncyBoZWlnaHQgYW5kLCBpbiB0aGUgM0Qgc2NlbmUsIHNhdCBvbiB0b3Agb2ZcbiAgLy8gdGhlIGNsb3VkLiBPbmUgc3RhdGVtZW50LCBpbiB0aGUgY2FwdGlvbi5cblxuICBpZiAoaW5wdXQueikge1xuICAgIHJldHVybiB7XG4gICAgICBhdXRvc2l6ZTogdHJ1ZSxcbiAgICAgIC8vIEEgM0Qgc2NlbmUgaGFzIG5vIG1hcmdpbnMgdG8gc3BlYWsgb2Y7IHRoZSBheGVzIGxpdmUgaW5zaWRlIGl0LlxuICAgICAgbWFyZ2luOiB7IGw6IDAsIHI6IDAsIHQ6IDAsIGI6IDAgfSxcbiAgICAgIHNjZW5lOiB7XG4gICAgICAgIHhheGlzOiB7IHRpdGxlOiB7IHRleHQ6IGF4aXNUaXRsZShzdGVtLCAxLCB2cikgfSB9LFxuICAgICAgICB5YXhpczogeyB0aXRsZTogeyB0ZXh0OiBheGlzVGl0bGUoc3RlbSwgMiwgdnIpIH0gfSxcbiAgICAgICAgemF4aXM6IHsgdGl0bGU6IHsgdGV4dDogYXhpc1RpdGxlKHN0ZW0sIDMsIHZyKSB9IH0sXG4gICAgICAgIC8vIENhcnJpZWQgYWNyb3NzIHRoZSByZWRyYXcsIG9yIGV2ZXJ5IHJlY29sb3VyIHNuYXBzIHRoZSBjbG91ZCBiYWNrIHRvIGl0c1xuICAgICAgICAvLyBkZWZhdWx0IG9yaWVudGF0aW9uLlxuICAgICAgICAuLi4oaW5wdXQudmlldz8uY2FtZXJhID8geyBjYW1lcmE6IGlucHV0LnZpZXcuY2FtZXJhIH0gOiB7fSksXG4gICAgICAgIC8vIEVxdWFsIGFzcGVjdCBmb3IgdGhlIHNhbWUgcmVhc29uIGFzIHRoZSBwbGFuZTogdGhlIGF4ZXMgY2Fycnkgbm8gdW5pdHMsIHNvXG4gICAgICAgIC8vIGRpc3RhbmNlcyBvbmx5IGNvbXBhcmUgaWYgYWxsIHRocmVlIGFyZSBzY2FsZWQgYWxpa2UuIGBkYXRhYCBrZWVwcyB0aGUgY2xvdWQnc1xuICAgICAgICAvLyBvd24gcHJvcG9ydGlvbnMgaW5zdGVhZCBvZiBzdHJldGNoaW5nIGl0IGludG8gdGhlIGN1YmUuXG4gICAgICAgIGFzcGVjdG1vZGU6ICdkYXRhJyxcbiAgICAgIH0sXG4gICAgICBzaG93bGVnZW5kOiBmYWxzZSxcbiAgICAgIGhvdmVybW9kZTogJ2Nsb3Nlc3QnLFxuICAgIH07XG4gIH1cblxuICByZXR1cm4ge1xuICAgIGF1dG9zaXplOiB0cnVlLFxuICAgIC8vIEJvdHRvbSBtYXJnaW4gY2FycmllcyB0aGUgbGVnZW5kOiBsYWlkIG91dCBCRUxPVyB0aGUgcGxvdCByYXRoZXIgdGhhbiBiZXNpZGUgaXQuXG4gICAgLy8gQSB2ZXJ0aWNhbCBsZWdlbmQgb2YgMjIgY2VsbCB0eXBlcyB0b29rIGhhbGYgYSBkb2NrZWQgcGFuZWwncyB3aWR0aCBhbmQgc3F1ZWV6ZWRcbiAgICAvLyB0aGUgZW1iZWRkaW5nIGludG8gYSBjb3JuZXIg4oCUIGFuZCB0aGUgc2hhcGVzIG9mIHRoZSBjbHVzdGVycyBhcmUgdGhlIHRoaW5nIGJlaW5nXG4gICAgLy8gcmVhZCBoZXJlLCB3aGlsZSB0aGUgbGFiZWxzIGFyZSBhIGxvb2t1cC5cbiAgICBtYXJnaW46IHtcbiAgICAgIGw6IDQ0LFxuICAgICAgcjogOCxcbiAgICAgIHQ6IDgsXG4gICAgICAvLyBSb29tIGZvciB0aGUgbGVnZW5kIG9ubHkgd2hlbiBvbmUgaXMgZHJhd247IG90aGVyd2lzZSB0aGUgYXhpcyB0aXRsZSBhbG9uZS5cbiAgICAgIGI6IChpbnB1dC5jYXRlZ29yaWVzPy5uYW1lcy5sZW5ndGggPz8gMCkgPiAwXG4gICAgICAgICYmIChpbnB1dC5jYXRlZ29yaWVzPy5uYW1lcy5sZW5ndGggPz8gMCkgPD0gRU1CRURESU5HX01BWF9MRUdFTkRfU0hPV04gPyA2NCA6IDQwLFxuICAgIH0sXG4gICAgLy8gRXF1YWwgYXNwZWN0OiBhbiBlbWJlZGRpbmcncyBheGVzIGNhcnJ5IG5vIHVuaXRzLCBzbyBkaXN0YW5jZXMgYXJlIG9ubHkgY29tcGFyYWJsZSBpZiB0aGVcbiAgICAvLyB0d28gYXJlIHNjYWxlZCBhbGlrZS4gU3RyZXRjaGluZyBvbmUgYXhpcyB0byBmaWxsIHRoZSBwYW5lbCBpbnZlbnRzIHN0cnVjdHVyZS5cbiAgICB4YXhpczoge1xuICAgICAgdGl0bGU6IHsgdGV4dDogYXhpc1RpdGxlKHN0ZW0sIDEsIHZyKSB9LCB6ZXJvbGluZTogZmFsc2UsIHRpY2tzOiAnb3V0c2lkZScsXG4gICAgICAuLi4oaW5wdXQudmlldz8ucmFuZ2VzID8geyByYW5nZTogaW5wdXQudmlldy5yYW5nZXMueCwgYXV0b3JhbmdlOiBmYWxzZSB9IDoge30pLFxuICAgIH0sXG4gICAgeWF4aXM6IHtcbiAgICAgIHRpdGxlOiB7IHRleHQ6IGF4aXNUaXRsZShzdGVtLCAyLCB2cikgfSwgemVyb2xpbmU6IGZhbHNlLCB0aWNrczogJ291dHNpZGUnLFxuICAgICAgc2NhbGVhbmNob3I6ICd4Jywgc2NhbGVyYXRpbzogMSxcbiAgICAgIC4uLihpbnB1dC52aWV3Py5yYW5nZXMgPyB7IHJhbmdlOiBpbnB1dC52aWV3LnJhbmdlcy55LCBhdXRvcmFuZ2U6IGZhbHNlIH0gOiB7fSksXG4gICAgfSxcbiAgICBsZWdlbmQ6IHtcbiAgICAgIG9yaWVudGF0aW9uOiAnaCcsXG4gICAgICBpdGVtc2l6aW5nOiAnY29uc3RhbnQnLFxuICAgICAgZm9udDogeyBzaXplOiA5IH0sXG4gICAgICB5YW5jaG9yOiAndG9wJywgeTogLTAuMTYsIHhhbmNob3I6ICdsZWZ0JywgeDogMCxcbiAgICB9LFxuICAgIGhvdmVybW9kZTogJ2Nsb3Nlc3QnLFxuICB9O1xufVxuXG5leHBvcnQgaW50ZXJmYWNlIE9taWNzSGVhdG1hcElucHV0IHtcbiAgcm93czogc3RyaW5nW107XG4gIGNvbHM6IHN0cmluZ1tdO1xuICAvKiogYHJvd3MubGVuZ3RoIMOXIGNvbHMubGVuZ3RoYCwgcm93LW1ham9yOyBgTmFOYCB3aGVyZSBub3RoaW5nIHdhcyBtZWFzdXJlZC4gKi9cbiAgdmFsdWVzOiBGbG9hdDMyQXJyYXk7XG4gIC8qKiBDZWxscyBiZWhpbmQgZWFjaCBjb2x1bW4sIGZvciB0aGUgaG92ZXIuICovXG4gIGNvdW50cz86IFVpbnQzMkFycmF5O1xuICAvKiogVHJ1ZSB3aGVuIGB2YWx1ZXNgIGFyZSB6LXNjb3Jlcywgd2hpY2ggc2V0cyB0aGUgc2NhbGUgYW5kIHRoZSBsYWJlbHMuICovXG4gIHpTY29yZWQ/OiBib29sZWFuO1xuICAvKiogQ29sdW1uIGF4aXMgdGl0bGUg4oCUIHRoZSBncm91cGluZyBjb2x1bW4ncyBuYW1lLCBvciBcImNlbGxcIi4gKi9cbiAgZ3JvdXBMYWJlbD86IHN0cmluZztcbn1cblxuLyoqIERpdmVyZ2luZywgY2VudHJlZDogYWZ0ZXIgei1zY29yaW5nLCB0aGUgc2lnbiBjYXJyaWVzIHRoZSBtZWFuaW5nLiAqL1xuY29uc3QgSEVBVE1BUF9ESVZFUkdJTkc6IFtudW1iZXIsIHN0cmluZ11bXSA9IFtcbiAgWzAsICcjMjE2NkFDJ10sXG4gIFswLjUsICcjRjdGN0Y3J10sXG4gIFsxLCAnI0IyMTgyQiddLFxuXTtcbi8qKiBTZXF1ZW50aWFsLCBmb3IgcmF3IG1lYW5zIHdoZXJlIHplcm8gaXMgdGhlIGJvdHRvbSByYXRoZXIgdGhhbiB0aGUgbWlkZGxlLiAqL1xuY29uc3QgSEVBVE1BUF9TRVFVRU5USUFMOiBbbnVtYmVyLCBzdHJpbmddW10gPSBbXG4gIFswLCAnI0Y3RkJGRiddLFxuICBbMC41LCAnIzZCQUVENiddLFxuICBbMSwgJyMwODMwNkInXSxcbl07XG5cbmV4cG9ydCBmdW5jdGlvbiBidWlsZEhlYXRtYXBUcmFjZXMoaW5wdXQ6IE9taWNzSGVhdG1hcElucHV0KTogdW5rbm93bltdIHtcbiAgY29uc3QgeyByb3dzLCBjb2xzLCB2YWx1ZXMsIGNvdW50cyB9ID0gaW5wdXQ7XG4gIGlmIChyb3dzLmxlbmd0aCA9PT0gMCB8fCBjb2xzLmxlbmd0aCA9PT0gMCkgcmV0dXJuIFtdO1xuICAvLyBQbG90bHkgd2FudHMgeiBhcyBhbiBhcnJheSBvZiByb3dzLCBib3R0b20tdXA7IE5hTiByZW5kZXJzIGFzIGEgZ2FwLlxuICBjb25zdCB6OiAobnVtYmVyIHwgbnVsbClbXVtdID0gW107XG4gIGZvciAobGV0IHIgPSByb3dzLmxlbmd0aCAtIDE7IHIgPj0gMDsgci0tKSB7XG4gICAgY29uc3QgbGluZTogKG51bWJlciB8IG51bGwpW10gPSBbXTtcbiAgICBmb3IgKGxldCBjID0gMDsgYyA8IGNvbHMubGVuZ3RoOyBjKyspIHtcbiAgICAgIGNvbnN0IHYgPSB2YWx1ZXNbciAqIGNvbHMubGVuZ3RoICsgY107XG4gICAgICBsaW5lLnB1c2goTnVtYmVyLmlzRmluaXRlKHYpID8gdiA6IG51bGwpO1xuICAgIH1cbiAgICB6LnB1c2gobGluZSk7XG4gIH1cbiAgY29uc3QgeSA9IHJvd3Muc2xpY2UoKS5yZXZlcnNlKCk7XG4gIGNvbnN0IHVuaXQgPSBpbnB1dC56U2NvcmVkID8gJ3onIDogJ21lYW4nO1xuICAvLyBTeW1tZXRyaWMgYWJvdXQgemVybyB3aGVuIHotc2NvcmVkLCBzbyB0aGUgc2FtZSBtYWduaXR1ZGUgcmVhZHMgdGhlIHNhbWVcbiAgLy8gd2hpY2hldmVyIHNpZGUgb2YgdGhlIGdlbmUncyBhdmVyYWdlIGl0IGZhbGxzIG9uLlxuICBsZXQgem1pbjogbnVtYmVyIHwgdW5kZWZpbmVkO1xuICBsZXQgem1heDogbnVtYmVyIHwgdW5kZWZpbmVkO1xuICBpZiAoaW5wdXQuelNjb3JlZCkge1xuICAgIGxldCBwZWFrID0gMDtcbiAgICBmb3IgKGxldCBpID0gMDsgaSA8IHZhbHVlcy5sZW5ndGg7IGkrKykge1xuICAgICAgY29uc3QgdiA9IE1hdGguYWJzKHZhbHVlc1tpXSk7XG4gICAgICBpZiAoTnVtYmVyLmlzRmluaXRlKHYpICYmIHYgPiBwZWFrKSBwZWFrID0gdjtcbiAgICB9XG4gICAgem1heCA9IHBlYWsgPiAwID8gcGVhayA6IDE7XG4gICAgem1pbiA9IC16bWF4O1xuICB9XG4gIGNvbnN0IGhvdmVyID0gY291bnRzXG4gICAgPyBjb2xzLm1hcCgobGFiZWwsIGMpID0+IGAke2xhYmVsfSDCtyAke2NvdW50c1tjXX0gY2VsbHNgKVxuICAgIDogY29scztcbiAgcmV0dXJuIFt7XG4gICAgdHlwZTogJ2hlYXRtYXAnLFxuICAgIHosXG4gICAgeDogY29scyxcbiAgICB5LFxuICAgIGN1c3RvbWRhdGE6IHoubWFwKCgpID0+IGhvdmVyKSxcbiAgICBjb2xvcnNjYWxlOiBpbnB1dC56U2NvcmVkID8gSEVBVE1BUF9ESVZFUkdJTkcgOiBIRUFUTUFQX1NFUVVFTlRJQUwsXG4gICAgLi4uKHptaW4gIT09IHVuZGVmaW5lZCA/IHsgem1pbiwgem1heCB9IDoge30pLFxuICAgIC8vIEEgZ2FwIGhhcyBubyBjb2xvdXIgcmF0aGVyIHRoYW4gdGhlIHNjYWxlJ3MgYm90dG9tOiBub3RoaW5nIHdhcyBtZWFzdXJlZFxuICAgIC8vIHRoZXJlLCB3aGljaCBpcyBub3QgdGhlIHNhbWUgYXMgYSBsb3cgbWVhbi5cbiAgICBob3Zlcm9uZ2FwczogZmFsc2UsXG4gICAgY29sb3JiYXI6IHsgdGl0bGU6IHsgdGV4dDogdW5pdCwgc2lkZTogJ3JpZ2h0JyB9LCB0aGlja25lc3M6IDEwLCBsZW46IDAuOSB9LFxuICAgIGhvdmVydGVtcGxhdGU6IGAle3l9PGJyPiV7Y3VzdG9tZGF0YX08YnI+JHt1bml0fSAle3o6LjJmfTxleHRyYT48L2V4dHJhPmAsXG4gIH1dO1xufVxuXG5leHBvcnQgZnVuY3Rpb24gaGVhdG1hcExheW91dChpbnB1dDogT21pY3NIZWF0bWFwSW5wdXQpOiB1bmtub3duIHtcbiAgcmV0dXJuIHtcbiAgICAvLyBMZWZ0IG1hcmdpbiBncm93cyB3aXRoIHRoZSBsb25nZXN0IGdlbmUgbmFtZTsgdGhlIGxhYmVscyBhcmUgdGhlIHBvaW50LlxuICAgIG1hcmdpbjogeyB0OiAxMCwgcjogMTAsIGI6IDkwLCBsOiA4IH0sXG4gICAgYXV0b3NpemU6IHRydWUsXG4gICAgaG92ZXJtb2RlOiAnY2xvc2VzdCcsXG4gICAgeGF4aXM6IHsgYXV0b21hcmdpbjogdHJ1ZSwgdGlja2FuZ2xlOiAtNDUsIHRpY2tmb250OiB7IHNpemU6IDEwIH0sXG4gICAgICB0aXRsZTogeyB0ZXh0OiBpbnB1dC5ncm91cExhYmVsID8/ICcnIH0gfSxcbiAgICB5YXhpczogeyBhdXRvbWFyZ2luOiB0cnVlLCB0aWNrZm9udDogeyBzaXplOiAxMCB9IH0sXG4gICAgLy8gR3Jvd3Mgd2l0aCB0aGUgZ2VuZSBjb3VudCBzbyAzIHJvd3MgYXJlIG5vdCBzdHJldGNoZWQgdG8gMjAgcm93cycgaGVpZ2h0LlxuICAgIGhlaWdodDogTWF0aC5tYXgoMTgwLCAyNCAqIGlucHV0LnJvd3MubGVuZ3RoICsgMTEwKSxcbiAgfTtcbn1cbiJdfQ==
643
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoib21pY3MtdHJhY2UtYnVpbGRlcnMuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi8uLi9zcmMvbGliL2ltcGxlbWVudGF0aW9ucy9wbG90bHkvb21pY3MtdHJhY2UtYnVpbGRlcnMudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUFFLFdBQVcsRUFBRSxNQUFNLDBDQUEwQyxDQUFDO0FBQ3ZFLE9BQU8sRUFBRSxhQUFhLEVBQUUsUUFBUSxFQUFFLE1BQU0sdUJBQXVCLENBQUM7QUE2Q2hFLE1BQU0sYUFBYSxHQUFHLFNBQVMsQ0FBQztBQUNoQzt3RUFDd0U7QUFDeEUsTUFBTSxvQkFBb0IsR0FBRyxNQUFNLENBQUM7QUFFcEMsK0VBQStFO0FBQy9FLFNBQVMsT0FBTyxDQUFDLEtBQXNCLEVBQUUsUUFBMkI7SUFDbEUsTUFBTSxFQUFFLE1BQU0sRUFBRSxHQUFHLEVBQUUsR0FBRyxLQUFLLENBQUM7SUFDOUIsTUFBTSxHQUFHLEdBQWEsRUFBRSxDQUFDO0lBQ3pCLEtBQUssSUFBSSxDQUFDLEdBQUcsQ0FBQyxFQUFFLENBQUMsR0FBRyxNQUFNLENBQUMsTUFBTSxFQUFFLENBQUMsRUFBRSxFQUFFLENBQUM7UUFDdkMsSUFBSSxRQUFRLElBQUksQ0FBQyxRQUFRLENBQUMsQ0FBQyxDQUFDO1lBQUUsU0FBUztRQUN2QyxNQUFNLENBQUMsR0FBRyxNQUFNLENBQUMsQ0FBQyxDQUFDLENBQUM7UUFDcEIsSUFBSSxDQUFDLE1BQU0sQ0FBQyxRQUFRLENBQUMsQ0FBQyxDQUFDO1lBQUUsU0FBUztRQUNsQyxHQUFHLENBQUMsSUFBSSxDQUFDLEdBQUcsQ0FBQyxDQUFDLENBQUMsSUFBSSxDQUFDLEtBQUssQ0FBQyxJQUFJLENBQUMsR0FBRyxDQUFDLENBQUMsRUFBRSxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQztJQUNqRCxDQUFDO0lBQ0QsT0FBTyxHQUFHLENBQUM7QUFDYixDQUFD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QUksQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLEVBQUUsR0FBRyxFQUFFLENBQUMsR0FBRyxJQUFJLENBQUM7SUFDMUMsTUFBTSxHQUFHLEdBQUcsSUFBSSxLQUFLLENBQVMsSUFBSSxDQUFDLENBQUMsSUFBSSxDQUFDLENBQUMsQ0FBQyxDQUFDO0lBQzVDLE1BQU0sUUFBUSxHQUFHLFNBQVMsQ0FBQyxDQUFDLENBQUMsSUFBSSxLQUFLLENBQVMsSUFBSSxDQUFDLENBQUMsSUFBSSxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxJQUFJLENBQUM7SUFDcEUsS0FBSyxJQUFJLENBQUMsR0FBRyxDQUFDLEVBQUUsQ0FBQyxHQUFHLE1BQU0sQ0FBQyxNQUFNLEVBQUUsQ0FBQyxFQUFFLEVBQUUsQ0FBQztRQUN2QyxJQUFJLENBQUMsTUFBTSxDQUFDLFFBQVEsQ0FBQyxNQUFNLENBQUMsQ0FBQyxDQUFDLENBQUM7WUFBRSxTQUFTO1FBQzFDLDZEQUE2RDtRQUM3RCxNQUFNLENBQUMsR0FBRyxJQUFJLENBQUMsR0FBRyxDQUFDLElBQUksR0FBRyxDQUFDLEVBQUUsSUFBSSxDQUFDLEtBQUssQ0FBQyxDQUFDLEVBQUUsQ0FBQyxDQUFDLENBQUMsR0FBRyxLQUFLLENBQUMsR0FBRyxLQUFLLENBQUMsQ0FBQyxDQUFDO1FBQ2xFLEdBQUcsQ0FBQyxDQUFDLENBQUMsRUFBRSxDQUFDO1FBQ1QsSUFBSSxRQUFRLElBQUksU0FBVSxDQUFDLENBQUMsQ0FBQztZQUFFLFFBQVEsQ0FBQyxDQUFDLENBQUMsRUFBRSxDQUFDO0lBQy9DLENBQUM7SUFDRCxNQUFNLEtBQUssR0FBRyxHQUFHLENBQUMsR0FBRyxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQUMsRUFBb0IsRUFBRSxDQUFDLENBQUMsS0FBSyxHQUFHLENBQUMsR0FBRyxLQUFLLEVBQUUsS0FBSyxHQUFHLENBQUMsQ0FBQyxHQUFHLENBQUMsQ0FBQyxHQUFHLEtBQUssQ0FBQyxDQUFDLENBQUM7SUFDaEcsT0FBTyxFQUFFLE9BQU8sRUFBRSxLQUFLLENBQUMsR0FBRyxDQUFDLENBQUMsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxDQUFDLEVBQUUsRUFBRSxDQUFDLENBQUMsQ0FBQyxHQUFHLENBQUMsQ0FBQyxHQUFHLENBQUMsQ0FBQyxFQUFFLEtBQUssRUFBRSxLQUFLLEVBQUUsR0FBRyxFQUFFLFFBQVEsRUFBRSxDQUFDO0FBQ3RGLENBQUM7QUFFRCx1RUFBdUU7QUFDdkUsU0FBUyxVQUFVLENBQUMsS0FBc0IsRUFBRSxLQUFvQixFQUFFLFFBQTJCO0lBQzNGLE1BQU0sT0FBTyxHQUFlLEtBQUssQ0FBQyxVQUFVLENBQUMsR0FBRyxDQUFDLEdBQUcsRUFBRSxDQUFDLEVBQUUsQ0FBQyxDQUFDO0lBQzNELE1BQU0sRUFBRSxNQUFNLEVBQUUsR0FBRyxFQUFFLEdBQUcsS0FBSyxDQUFDO0lBQzlCLEtBQUssSUFBSSxDQUFDLEdBQUcsQ0FBQyxFQUFFLENBQUMsR0FBRyxNQUFNLENBQUMsTUFBTSxFQUFFLENBQUMsRUFBRSxFQUFFLENBQUM7UUFDdkMsSUFBSSxRQUFRLElBQUksQ0FBQyxRQUFRLENBQUMsQ0FBQyxDQUFDO1lBQUUsU0FBUztRQUN2QyxNQUFNLElBQUksR0FBRyxLQUFLLENBQUMsS0FBSyxDQUFDLENBQUMsQ0FBQyxDQUFDO1FBQzVCLHNFQUFzRTtRQUN0RSw0Q0FBNEM7UUFDNUMsSUFBSSxJQUFJLEtBQUssV0FBVyxJQUFJLElBQUksSUFBSSxPQUFPLENBQUMsTUFBTTtZQUFFLFNBQVM7UUFDN0QsTUFBTSxDQUFDLEdBQUcsTUFBTSxDQUFDLENBQUMsQ0FBQyxDQUFDO1FBQ3BCLElBQUksQ0FBQyxNQUFNLENBQUMsUUFBUSxDQUFDLENBQUMsQ0FBQztZQUFFLFNBQVM7UUFDbEMsT0FBTyxDQUFDLElBQUksQ0FBQyxDQUFDLElBQUksQ0FBQyxHQUFHLENBQUMsQ0FBQyxDQUFDLElBQUksQ0FBQyxLQUFLLENBQUMsSUFBSSxDQUFDLEdBQUcsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FB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QTBFO1FBQzFFLE1BQU0sRUFBRSxFQUFFLENBQUMsRUFBRSxFQUFFLEVBQUUsQ0FBQyxFQUFFLEVBQUUsRUFBRSxDQUFDLEVBQUUsRUFBRSxFQUFFLENBQUMsRUFBRSxDQUFDLEVBQUU7UUFDckMsUUFBUSxFQUFFLElBQUk7UUFDZCxTQUFTLEVBQUUsU0FBUztRQUNwQixLQUFLLEVBQUUsRUFBRSxVQUFVLEVBQUUsSUFBSSxFQUFFLFNBQVMsRUFBRSxDQUFDLEVBQUUsRUFBRSxRQUFRLEVBQUUsRUFBRSxJQUFJLEVBQUUsRUFBRSxFQUFFLEVBQUUsS0FBSyxFQUFFLEVBQUUsSUFBSSxFQUFFLEtBQUssQ0FBQyxVQUFVLElBQUksRUFBRSxFQUFFLEVBQUU7UUFDNUcsS0FBSyxFQUFFLEVBQUUsVUFBVSxFQUFFLElBQUksRUFBRSxRQUFRLEVBQUUsRUFBRSxJQUFJLEVBQUUsRUFBRSxFQUFFLEVBQUU7UUFDbkQsNEVBQTRFO1FBQzVFLE1BQU0sRUFBRSxJQUFJLENBQUMsR0FBRyxDQUFDLEdBQUcsRUFBRSxFQUFFLEdBQUcsS0FBSyxDQUFDLElBQUksQ0FBQyxNQUFNLEdBQUcsR0FBRyxDQUFDO0tBQ3BELENBQUM7QUFDSixDQUFDIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgTk9fQ0FURUdPUlkgfSBmcm9tICcuLi8uLi9jb250cmFjdHMvc3BhdGlhbC1kYXRhc2V0LmNvbnRyYWN0JztcbmltcG9ydCB7IHBhcnNlQ3NzQ29sb3IsIHJnYlRvSGV4IH0gZnJvbSAnLi4vLi4vY29udHJhY3RzL2NvbG9yJztcblxuLyoqXG4gKiBQbG90bHkgdHJhY2VzIGZvciB0aGUgMS1EIGRpc3RyaWJ1dGlvbiBjaGFydHMgb3ZlciBzcGF0aWFsLW9taWNzIHZhbHVlczpcbiAqIGhpc3RvZ3JhbSwgdmlvbGluIGFuZCBib3guXG4gKlxuICogUHVyZSwgbGlrZSBgcGxvdGx5LXRyYWNlLWJ1aWxkZXJzLnRzYCDigJQgYW5kIGRlbGliZXJhdGVseSBTRVBBUkFURSBmcm9tIGl0LFxuICogYmVjYXVzZSB0aGF0IG1vZHVsZSdzIGBUcmFjZUJ1aWxkSW5wdXRgIGlzIGltYWdlLW1hdHJpeCBzaGFwZWQgKGBmcmFtZXNgLFxuICogYHdpZHRoYCwgYHJhdGlvc2AsIGB0cnVlSW1hZ2VTaXplYCkgYW5kIGNhbm5vdCBleHByZXNzIFwib25lIHZhbHVlIHBlclxuICogb2JzZXJ2YXRpb25cIi4gRm9yY2luZyB0aGUgdHdvIHRvZ2V0aGVyIHdvdWxkIG1ha2UgYm90aCB3b3JzZS5cbiAqXG4gKiBWaW9saW4gYW5kIGJveCBuZWVkIG5vIGJ1bmRsaW5nIHdvcms6IGBwbG90bHkuanMtZGlzdC1taW5gIGlzIHRoZSBmdWxsXG4gKiBkaXN0cmlidXRpb24gYW5kIGFscmVhZHkgY2FycmllcyBib3RoIHRyYWNlIHR5cGVzLlxuICovXG5cbmV4cG9ydCB0eXBlIE9taWNzQ2hhcnRLaW5kID0gJ2hpc3RvZ3JhbScgfCAndmlvbGluJyB8ICdib3gnIHwgJ2NvdW50cycgfCAnaGVhdG1hcCcgfCAnZW1iZWRkaW5nJztcblxuLyoqIFBlci1vYnNlcnZhdGlvbiBncm91cGluZyBmb3IgYSB2aW9saW4vYm94LCBvciBhbiBvdmVybGFpZCBoaXN0b2dyYW0uICovXG5leHBvcnQgaW50ZXJmYWNlIE9taWNzR3JvdXBpbmcge1xuICBjb2RlczogVWludDE2QXJyYXk7XG4gIGNhdGVnb3JpZXM6IHN0cmluZ1tdO1xuICAvKiogYCNycmdnYmJgIHBlciBjYXRlZ29yeSwgaW5kZXgtYWxpZ25lZCDigJQgdGhlIHNhbWUgY29sb3VycyB0aGUgbWFwIHVzZXMuICovXG4gIGNvbG9yczogc3RyaW5nW107XG59XG5cbi8qKlxuICogV2hhdCB7QGxpbmsgYnVpbGRPbWljc1RyYWNlc30gLyB7QGxpbmsgb21pY3NMYXlvdXR9IGNoYXJ0OiBvbmUgdmFsdWUgcGVyXG4gKiBvYnNlcnZhdGlvbiAoY2VsbC9zcG90KSwgd2l0aCB0aGUgb3B0aW9uYWwgZ3JvdXBpbmcgYW5kIHNlbGVjdGlvblxuICogaW5kZXgtYWxpZ25lZCB0byBpdC4gTm9uLWZpbml0ZSB2YWx1ZXMgKE5hTiBmb3IgYSBtaXNzaW5nIG1lYXN1cmVtZW50KSBhcmVcbiAqIGxlZnQgb3V0IG9mIGV2ZXJ5IGNoYXJ0LlxuICovXG5leHBvcnQgaW50ZXJmYWNlIE9taWNzVHJhY2VJbnB1dCB7XG4gIC8qKiBUaGUgdmFsdWVzIGJlaW5nIGNoYXJ0ZWQgKGFuIGFubm90YXRpb24gY29sdW1uIG9yIGEgZ2VuZSB2ZWN0b3IpLiAqL1xuICB2YWx1ZXM6IEZsb2F0MzJBcnJheTtcbiAgLyoqIEF4aXMgbGFiZWwgZm9yIHRoZSB2YWx1ZSDigJQgdGhlIGNvbHVtbiBvciBnZW5lIG5hbWUuICovXG4gIG5hbWU6IHN0cmluZztcbiAgZ3JvdXA/OiBPbWljc0dyb3VwaW5nIHwgbnVsbDtcbiAgLyoqIGAxYCBtYXJrcyBhIHNlbGVjdGVkIG9ic2VydmF0aW9uLiBXaGVuIHByZXNlbnQsIHRoZSBjaGFydHMgbmFycm93IHRvIGl0LiAqL1xuICBzZWxlY3Rpb24/OiBVaW50OEFycmF5IHwgbnVsbDtcbiAgLyoqIFBsb3QgYGxvZzFwKHZhbHVlKWAgaW5zdGVhZCBvZiB0aGUgcmF3IHZhbHVlLiAqL1xuICBsb2c/OiBib29sZWFuO1xuICAvKiogQ29sb3VyIGZvciB0aGUgdW5ncm91cGVkIHRyYWNlLiAqL1xuICBjb2xvcj86IHN0cmluZztcbn1cblxuY29uc3QgREVGQVVMVF9DT0xPUiA9ICcjMDA3MkIyJztcbi8qKiBQbG90bHkgcmVuZGVycyBldmVyeSBwb2ludCBvZiBhIHZpb2xpbi9ib3g7IHBhc3QgdGhpcyB3ZSB0aGluIHRoZSBpbnB1dC5cbiAqICA4NGsgY2VsbHMgeCBhIHZpb2xpbiBwZXIgY2F0ZWdvcnkgaXMgb3RoZXJ3aXNlIHNlY29uZHMgb2YgbGF5b3V0LiAqL1xuY29uc3QgTUFYX1BPSU5UU19QRVJfVFJBQ0UgPSAyMF8wMDA7XG5cbi8qKiBGaW5pdGUgdmFsdWVzIG9ubHksIG9wdGlvbmFsbHkgbG9nLXNjYWxlZCBhbmQgcmVzdHJpY3RlZCB0byBhIHNlbGVjdGlvbi4gKi9cbmZ1bmN0aW9uIHByZXBhcmUoaW5wdXQ6IE9taWNzVHJhY2VJbnB1dCwgcmVzdHJpY3Q6IFVpbnQ4QXJyYXkgfCBudWxsKTogbnVtYmVyW10ge1xuICBjb25zdCB7IHZhbHVlcywgbG9nIH0gPSBpbnB1dDtcbiAgY29uc3Qgb3V0OiBudW1iZXJbXSA9IFtdO1xuICBmb3IgKGxldCBpID0gMDsgaSA8IHZhbHVlcy5sZW5ndGg7IGkrKykge1xuICAgIGlmIChyZXN0cmljdCAmJiAhcmVzdHJpY3RbaV0pIGNvbnRpbnVlO1xuICAgIGNvbnN0IHYgPSB2YWx1ZXNbaV07XG4gICAgaWYgKCFOdW1iZXIuaXNGaW5pdGUodikpIGNvbnRpbnVlO1xuICAgIG91dC5wdXNoKGxvZyA/IE1hdGgubG9nMXAoTWF0aC5tYXgoMCwgdikpIDogdik7XG4gIH1cbiAgcmV0dXJuIG91dDtcbn1cblxuLyoqIEV2ZW5seSB0aGluIGEgc2FtcGxlIHRvIGBtYXhgIHBvaW50cywgcHJlc2VydmluZyBpdHMgZGlzdHJpYnV0aW9uLiAqL1xuZnVuY3Rpb24gdGhpbih2YWx1ZXM6IG51bWJlcltdLCBtYXggPSBNQVhfUE9JTlRTX1BFUl9UUkFDRSk6IG51bWJlcltdIHtcbiAgaWYgKHZhbHVlcy5sZW5ndGggPD0gbWF4KSByZXR1cm4gdmFsdWVzO1xuICBjb25zdCBzdGVwID0gdmFsdWVzLmxlbmd0aCAvIG1heDtcbiAgY29uc3Qgb3V0OiBudW1iZXJbXSA9IFtdO1xuICBmb3IgKGxldCBpID0gMDsgaSA8IG1heDsgaSsrKSBvdXQucHVzaCh2YWx1ZXNbTWF0aC5mbG9vcihpICogc3RlcCldKTtcbiAgcmV0dXJuIG91dDtcbn1cblxuLyoqIEJpbi1jb3VudCBib3VuZHMgZm9yIHRoZSBwcmUtYmlubmVkIGhpc3RvZ3JhbSAoc3F1YXJlLXJvb3QgcnVsZSBpbiBiZXR3ZWVuKS4gKi9cbmNvbnN0IEhJU1RPR1JBTV9NSU5fQklOUyA9IDEwO1xuY29uc3QgSElTVE9HUkFNX01BWF9CSU5TID0gMTAwO1xuXG5pbnRlcmZhY2UgSGlzdG9ncmFtQmlucyB7XG4gIC8qKiBCaW4gY2VudHJlcywgZm9yIHRoZSBiYXJzJyB4LiAqL1xuICBjZW50ZXJzOiBudW1iZXJbXTtcbiAgLyoqIGBbbG8sIGhpXWAgcGVyIGJpbiwgZm9yIHRoZSBob3Zlci4gKi9cbiAgZWRnZXM6IFtudW1iZXIsIG51bWJlcl1bXTtcbiAgd2lkdGg6IG51bWJlcjtcbiAgYWxsOiBudW1iZXJbXTtcbiAgc2VsZWN0ZWQ6IG51bWJlcltdIHwgbnVsbDtcbn1cblxuLyoqXG4gKiBCaW4gdGhlIGZpbml0ZSAob3B0aW9uYWxseSBsb2ctc2NhbGVkKSB2YWx1ZXMgaW4gVFMsIG9uY2UsIGludG8gYmlucyBzaGFyZWQgYnkgdGhlXG4gKiBmdWxsIGRpc3RyaWJ1dGlvbiBhbmQgdGhlIHNlbGVjdGlvbi5cbiAqXG4gKiBIYW5kaW5nIFBsb3RseSBhbGwgTiB2YWx1ZXMgYXMgYSBgbnVtYmVyW11gIG1hZGUgaXQgcmUtYmluIGV2ZXJ5IG9uZSBvZiB0aGVtIG9uIGVhY2hcbiAqIHNlbGVjdGlvbiBjaGFuZ2Ug4oCUIGF0IG1pbGxpb25zIG9mIG9ic2VydmF0aW9ucywgdGhlIGRvbWluYW50IGNvc3Qgb2YgYSBsYXNzby4gU2hhcmVkXG4gKiBiaW5zIGFsc28ga2VlcCB0aGUgdHdvIG92ZXJsYWlkIGJhcnMgZGlyZWN0bHkgY29tcGFyYWJsZS5cbiAqL1xuZnVuY3Rpb24gaGlzdG9ncmFtQmlucyhpbnB1dDogT21pY3NUcmFjZUlucHV0LCBzZWxlY3Rpb246IFVpbnQ4QXJyYXkgfCBudWxsKTogSGlzdG9ncmFtQmlucyB7XG4gIGNvbnN0IHsgdmFsdWVzLCBsb2cgfSA9IGlucHV0O1xuICBjb25zdCBhdCA9IChpOiBudW1iZXIpOiBudW1iZXIgPT4ge1xuICAgIGNvbnN0IHYgPSB2YWx1ZXNbaV07XG4gICAgcmV0dXJuIGxvZyA/IE1hdGgubG9nMXAoTWF0aC5tYXgoMCwgdikpIDogdjtcbiAgfTtcbiAgbGV0IGxvID0gSW5maW5pdHk7XG4gIGxldCBoaSA9IC1JbmZpbml0eTtcbiAgbGV0IGNvdW50ID0gMDtcbiAgZm9yIChsZXQgaSA9IDA7IGkgPCB2YWx1ZXMubGVuZ3RoOyBpKyspIHtcbiAgICBpZiAoIU51bWJlci5pc0Zpbml0ZSh2YWx1ZXNbaV0pKSBjb250aW51ZTtcbiAgICBjb25zdCB2ID0gYXQoaSk7XG4gICAgaWYgKHYgPCBsbykgbG8gPSB2O1xuICAgIGlmICh2ID4gaGkpIGhpID0gdjtcbiAgICBjb3VudCsrO1xuICB9XG4gIGlmIChjb3VudCA9PT0gMCkge1xuICAgIHJldHVybiB7IGNlbnRlcnM6IFtdLCBlZGdlczogW10sIHdpZHRoOiAxLCBhbGw6IFtdLCBzZWxlY3RlZDogc2VsZWN0aW9uID8gW10gOiBudWxsIH07XG4gIH1cbiAgLy8gT25lIGJhciwgb25lIHVuaXQgd2lkZSwgZm9yIGEgZmxhdCBkaXN0cmlidXRpb246IHRoZXJlIGlzIG5vIHNwcmVhZCB0byBiaW4uXG4gIGNvbnN0IGZsYXQgPSAhKGhpID4gbG8pO1xuICBjb25zdCBiaW5zID0gZmxhdCA/IDEgOiBNYXRoLm1pbihISVNUT0dSQU1fTUFYX0JJTlMsIE1hdGgubWF4KEhJU1RPR1JBTV9NSU5fQklOUywgTWF0aC5jZWlsKE1hdGguc3FydChjb3VudCkpKSk7XG4gIGNvbnN0IHN0YXJ0ID0gZmxhdCA/IGxvIC0gMC41IDogbG87XG4gIGNvbnN0IHdpZHRoID0gZmxhdCA/IDEgOiAoaGkgLSBsbykgLyBiaW5zO1xuICBjb25zdCBhbGwgPSBuZXcgQXJyYXk8bnVtYmVyPihiaW5zKS5maWxsKDApO1xuICBjb25zdCBzZWxlY3RlZCA9IHNlbGVjdGlvbiA/IG5ldyBBcnJheTxudW1iZXI+KGJpbnMpLmZpbGwoMCkgOiBudWxsO1xuICBmb3IgKGxldCBpID0gMDsgaSA8IHZhbHVlcy5sZW5ndGg7IGkrKykge1xuICAgIGlmICghTnVtYmVyLmlzRmluaXRlKHZhbHVlc1tpXSkpIGNvbnRpbnVlO1xuICAgIC8vIFRoZSBtYXhpbXVtIGxhbmRzIGluIHRoZSBsYXN0IGJpbiByYXRoZXIgdGhhbiBvbmUgcGFzdCBpdC5cbiAgICBjb25zdCBiID0gTWF0aC5taW4oYmlucyAtIDEsIE1hdGguZmxvb3IoKGF0KGkpIC0gc3RhcnQpIC8gd2lkdGgpKTtcbiAgICBhbGxbYl0rKztcbiAgICBpZiAoc2VsZWN0ZWQgJiYgc2VsZWN0aW9uIVtpXSkgc2VsZWN0ZWRbYl0rKztcbiAgfVxuICBjb25zdCBlZGdlcyA9IGFsbC5tYXAoKF8sIGIpOiBbbnVtYmVyLCBudW1iZXJdID0+IFtzdGFydCArIGIgKiB3aWR0aCwgc3RhcnQgKyAoYiArIDEpICogd2lkdGhdKTtcbiAgcmV0dXJuIHsgY2VudGVyczogZWRnZXMubWFwKChbYSwgel0pID0+IChhICsgeikgLyAyKSwgZWRnZXMsIHdpZHRoLCBhbGwsIHNlbGVjdGVkIH07XG59XG5cbi8qKiBWYWx1ZXMgcGVyIGNhdGVnb3J5LCBmaW5pdGUgYW5kIG9wdGlvbmFsbHkgc2VsZWN0aW9uLXJlc3RyaWN0ZWQuICovXG5mdW5jdGlvbiBieUNhdGVnb3J5KGlucHV0OiBPbWljc1RyYWNlSW5wdXQsIGdyb3VwOiBPbWljc0dyb3VwaW5nLCByZXN0cmljdDogVWludDhBcnJheSB8IG51bGwpOiBudW1iZXJbXVtdIHtcbiAgY29uc3QgYnVja2V0czogbnVtYmVyW11bXSA9IGdyb3VwLmNhdGVnb3JpZXMubWFwKCgpID0+IFtdKTtcbiAgY29uc3QgeyB2YWx1ZXMsIGxvZyB9ID0gaW5wdXQ7XG4gIGZvciAobGV0IGkgPSAwOyBpIDwgdmFsdWVzLmxlbmd0aDsgaSsrKSB7XG4gICAgaWYgKHJlc3RyaWN0ICYmICFyZXN0cmljdFtpXSkgY29udGludWU7XG4gICAgY29uc3QgY29kZSA9IGdyb3VwLmNvZGVzW2ldO1xuICAgIC8vIE5PX0NBVEVHT1JZIGhhcyBubyBidWNrZXQgYnkgZGVmaW5pdGlvbjsgYW4gb3V0LW9mLXJhbmdlIGNvZGUgd291bGRcbiAgICAvLyBvdGhlcndpc2Ugc2lsZW50bHkgbGFuZCBpbiB0aGUgd3Jvbmcgb25lLlxuICAgIGlmIChjb2RlID09PSBOT19DQVRFR09SWSB8fCBjb2RlID49IGJ1Y2tldHMubGVuZ3RoKSBjb250aW51ZTtcbiAgICBjb25zdCB2ID0gdmFsdWVzW2ldO1xuICAgIGlmICghTnVtYmVyLmlzRmluaXRlKHYpKSBjb250aW51ZTtcbiAgICBidWNrZXRzW2NvZGVdLnB1c2gobG9nID8gTWF0aC5sb2cxcChNYXRoLm1heCgwLCB2KSkgOiB2KTtcbiAgfVxuICByZXR1cm4gYnVja2V0cztcbn1cblxuLyoqIFRydWUgd2hlbiB0aGUgc2VsZWN0aW9uIGFjdHVhbGx5IHJlc3RyaWN0cyBhbnl0aGluZy4gKi9cbmZ1bmN0aW9uIGFjdGl2ZVNlbGVjdGlvbihzZWxlY3Rpb246IFVpbnQ4QXJyYXkgfCBudWxsIHwgdW5kZWZpbmVkKTogVWludDhBcnJheSB8IG51bGwge1xuICBpZiAoIXNlbGVjdGlvbikgcmV0dXJuIG51bGw7XG4gIGZvciAobGV0IGkgPSAwOyBpIDwgc2VsZWN0aW9uLmxlbmd0aDsgaSsrKSBpZiAoc2VsZWN0aW9uW2ldKSByZXR1cm4gc2VsZWN0aW9uO1xuICByZXR1cm4gbnVsbDtcbn1cblxuLyoqXG4gKiBUcmFjZXMgZm9yIG9uZSBjaGFydCBraW5kLlxuICpcbiAqIC0gKipoaXN0b2dyYW0qKiDigJQgdGhlIGZ1bGwgZGlzdHJpYnV0aW9uIGFzIHByZS1iaW5uZWQgYmFycywgcGx1cyBhbiBvdmVybGFpZCAqU2VsZWN0ZWQqIHRyYWNlXG4gKiAgIHdoZW4gYSBzZWxlY3Rpb24gZXhpc3RzLCBzbyB0aGUgdHdvIGFyZSBkaXJlY3RseSBjb21wYXJhYmxlLiBUaGF0XG4gKiAgIGNvbXBhcmlzb24gaXMgdGhlIHdob2xlIHBvaW50IG9mIGxpbmtpbmcgdGhlIGNoYXJ0IHRvIHRoZSBtYXAuXG4gKiAtICoqdmlvbGluIC8gYm94Kiog4oCUIG9uZSBwZXIgY2F0ZWdvcnkgd2hlbiBncm91cGVkLCBvdGhlcndpc2UgYSBzaW5nbGUgdHJhY2UuXG4gKiAgIFRoZXNlIG5hcnJvdyBUTyB0aGUgc2VsZWN0aW9uIHJhdGhlciB0aGFuIG92ZXJsYXlpbmcgaXQ6IGEgdmlvbGluIHBlclxuICogICBjYXRlZ29yeSBwZXIgc2VsZWN0aW9uIHN0YXRlIGlzIHVucmVhZGFibGUuXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBidWlsZE9taWNzVHJhY2VzKGtpbmQ6IE9taWNzQ2hhcnRLaW5kLCBpbnB1dDogT21pY3NUcmFjZUlucHV0KTogdW5rbm93bltdIHtcbiAgY29uc3Qgc2VsZWN0aW9uID0gYWN0aXZlU2VsZWN0aW9uKGlucHV0LnNlbGVjdGlvbik7XG4gIGNvbnN0IGNvbG9yID0gaW5wdXQuY29sb3IgPz8gREVGQVVMVF9DT0xPUjtcblxuICBpZiAoa2luZCA9PT0gJ2hpc3RvZ3JhbScpIHtcbiAgICAvLyBQcmUtYmlubmVkIGJhcnMgcmF0aGVyIHRoYW4gYSBQbG90bHkgYGhpc3RvZ3JhbWAgb2YgZXZlcnkgdmFsdWU6IHNlZSBgaGlzdG9ncmFtQmluc2AuXG4gICAgY29uc3QgYmlucyA9IGhpc3RvZ3JhbUJpbnMoaW5wdXQsIHNlbGVjdGlvbik7XG4gICAgY29uc3QgYmFyID0gKGNvdW50czogbnVtYmVyW10sIG5hbWU6IHN0cmluZykgPT4gKHtcbiAgICAgIHR5cGU6ICdiYXInLFxuICAgICAgeDogYmlucy5jZW50ZXJzLFxuICAgICAgeTogY291bnRzLFxuICAgICAgd2lkdGg6IGJpbnMud2lkdGgsXG4gICAgICBjdXN0b21kYXRhOiBiaW5zLmVkZ2VzLFxuICAgICAgbmFtZSxcbiAgICAgIGhvdmVydGVtcGxhdGU6IGAle3l9IG9iczxicj4le2N1c3RvbWRhdGFbMF06LjRnfSDigJMgJXtjdXN0b21kYXRhWzFdOi40Z308ZXh0cmE+JHtuYW1lfTwvZXh0cmE+YCxcbiAgICB9KTtcbiAgICBjb25zdCB0cmFjZXM6IHVua25vd25bXSA9IFtcbiAgICAgIHtcbiAgICAgICAgLi4uYmFyKGJpbnMuYWxsLCAnQWxsJyksXG4gICAgICAgIG1hcmtlcjogeyBjb2xvciwgbGluZTogeyB3aWR0aDogMCB9IH0sXG4gICAgICAgIG9wYWNpdHk6IHNlbGVjdGlvbiA/IDAuNTUgOiAxLFxuICAgICAgfSxcbiAgICBdO1xuICAgIGlmIChiaW5zLnNlbGVjdGVkKSB7XG4gICAgICB0cmFjZXMucHVzaCh7XG4gICAgICAgIC4uLmJhcihiaW5zLnNlbGVjdGVkLCAnU2VsZWN0ZWQnKSxcbiAgICAgICAgbWFya2VyOiB7IGNvbG9yOiAnI0Q1NUUwMCcsIGxpbmU6IHsgd2lkdGg6IDAgfSB9LFxuICAgICAgICBvcGFjaXR5OiAwLjg1LFxuICAgICAgfSk7XG4gICAgfVxuICAgIHJldHVybiB0cmFjZXM7XG4gIH1cblxuICBjb25zdCB0eXBlID0ga2luZDsgLy8gJ3Zpb2xpbicgfCAnYm94J1xuICBjb25zdCBzaGFyZWQgPSB7XG4gICAgdHlwZSxcbiAgICAuLi4odHlwZSA9PT0gJ3Zpb2xpbidcbiAgICAgID8geyBib3g6IHsgdmlzaWJsZTogdHJ1ZSB9LCBtZWFubGluZTogeyB2aXNpYmxlOiB0cnVlIH0sIHBvaW50czogZmFsc2UgYXMgY29uc3QgfVxuICAgICAgOiB7IGJveHBvaW50czogZmFsc2UgYXMgY29uc3QgfSksXG4gIH07XG5cbiAgaWYgKGlucHV0Lmdyb3VwKSB7XG4gICAgY29uc3QgYnVja2V0cyA9IGJ5Q2F0ZWdvcnkoaW5wdXQsIGlucHV0Lmdyb3VwLCBzZWxlY3Rpb24pO1xuICAgIHJldHVybiAoXG4gICAgICBidWNrZXRzXG4gICAgICAgIC8vIERyb3AgZW1wdHkgY2F0ZWdvcmllczogYW4gZW1wdHkgdmlvbGluIHJlbmRlcnMgYXMgYSBzdHJheSB0aWNrIHdpdGggYVxuICAgICAgICAvLyBsYWJlbCwgd2hpY2ggcmVhZHMgYXMgZGF0YS5cbiAgICAgICAgLm1hcCgodmFsdWVzLCBpKSA9PiAoeyB2YWx1ZXMsIGkgfSkpXG4gICAgICAgIC5maWx0ZXIoKGIpID0+IGIudmFsdWVzLmxlbmd0aCA+IDApXG4gICAgICAgIC5tYXAoKGIpID0+ICh7XG4gICAgICAgICAgLi4uc2hhcmVkLFxuICAgICAgICAgIHk6IHRoaW4oYi52YWx1ZXMpLFxuICAgICAgICAgIG5hbWU6IGlucHV0Lmdyb3VwIS5jYXRlZ29yaWVzW2IuaV0sXG4gICAgICAgICAgbWFya2VyOiB7IGNvbG9yOiBpbnB1dC5ncm91cCEuY29sb3JzW2IuaV0gPz8gY29sb3IgfSxcbiAgICAgICAgICBsaW5lOiB7IGNvbG9yOiBpbnB1dC5ncm91cCEuY29sb3JzW2IuaV0gPz8gY29sb3IgfSxcbiAgICAgICAgfSkpXG4gICAgKTtcbiAgfVxuXG4gIGNvbnN0IHZhbHVlcyA9IHRoaW4ocHJlcGFyZShpbnB1dCwgc2VsZWN0aW9uKSk7XG4gIGlmICh2YWx1ZXMubGVuZ3RoID09PSAwKSByZXR1cm4gW107XG4gIHJldHVybiBbXG4gICAge1xuICAgICAgLi4uc2hhcmVkLFxuICAgICAgeTogdmFsdWVzLFxuICAgICAgbmFtZTogc2VsZWN0aW9uID8gJ1NlbGVjdGVkJyA6ICdBbGwnLFxuICAgICAgbWFya2VyOiB7IGNvbG9yIH0sXG4gICAgICBsaW5lOiB7IGNvbG9yIH0sXG4gICAgfSxcbiAgXTtcbn1cblxuLyoqIExheW91dCBmb3IgYSBjaGFydCBraW5kIOKAlCBheGlzIHRpdGxlcyByZWZsZWN0IHRoZSBsb2cgdG9nZ2xlLiAqL1xuZXhwb3J0IGZ1bmN0aW9uIG9taWNzTGF5b3V0KGtpbmQ6IE9taWNzQ2hhcnRLaW5kLCBpbnB1dDogT21pY3NUcmFjZUlucHV0KTogdW5rbm93biB7XG4gIGNvbnN0IGxhYmVsID0gaW5wdXQubG9nID8gYGxvZzFwKCR7aW5wdXQubmFtZX0pYCA6IGlucHV0Lm5hbWU7XG4gIGNvbnN0IGJhc2UgPSB7XG4gICAgbWFyZ2luOiB7IHQ6IDEwLCByOiAxMCwgYjogNDAsIGw6IDUyIH0sXG4gICAgYXV0b3NpemU6IHRydWUsXG4gICAgc2hvd2xlZ2VuZDoga2luZCA9PT0gJ2hpc3RvZ3JhbScgJiYgISFhY3RpdmVTZWxlY3Rpb24oaW5wdXQuc2VsZWN0aW9uKSxcbiAgICBsZWdlbmQ6IHsgb3JpZW50YXRpb246ICdoJywgeTogMS4xMiwgeDogMCB9LFxuICAgIGJhcmdhcDogMC4wMixcbiAgICBob3Zlcm1vZGU6ICdjbG9zZXN0JyxcbiAgfTtcbiAgaWYgKGtpbmQgPT09ICdoaXN0b2dyYW0nKSB7XG4gICAgcmV0dXJuIHtcbiAgICAgIC4uLmJhc2UsXG4gICAgICBiYXJtb2RlOiAnb3ZlcmxheScsXG4gICAgICB4YXhpczogeyB0aXRsZTogeyB0ZXh0OiBsYWJlbCB9IH0sXG4gICAgICB5YXhpczogeyB0aXRsZTogeyB0ZXh0OiAnb2JzZXJ2YXRpb25zJyB9IH0sXG4gICAgfTtcbiAgfVxuICByZXR1cm4ge1xuICAgIC4uLmJhc2UsXG4gICAgeGF4aXM6IHsgYXV0b21hcmdpbjogdHJ1ZSB9LFxuICAgIHlheGlzOiB7IHRpdGxlOiB7IHRleHQ6IGxhYmVsIH0sIHplcm9saW5lOiBmYWxzZSB9LFxuICB9O1xufVxuXG4vKiogV2hldGhlciBhIGNoYXJ0IGtpbmQgbmVlZHMgYSBjYXRlZ29yaWNhbCBncm91cGluZyB0byBiZSB3b3J0aCBzaG93aW5nLiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGJlbmVmaXRzRnJvbUdyb3VwaW5nKGtpbmQ6IE9taWNzQ2hhcnRLaW5kKTogYm9vbGVhbiB7XG4gIHJldHVybiBraW5kID09PSAndmlvbGluJyB8fCBraW5kID09PSAnYm94Jztcbn1cblxuLyoqIENhdGVnb3JpZXMgc2hvd24gYXMgYmFycyBiZWZvcmUgdGhlIHRhaWwgaXMgZm9sZGVkIGludG8gb25lIFwib3RoZXJcIi4gKi9cbmNvbnN0IE1BWF9DT1VOVF9CQVJTID0gMjU7XG5cbmV4cG9ydCBpbnRlcmZhY2UgT21pY3NDb3VudElucHV0IHtcbiAgLyoqIFRoZSBjYXRlZ29yaWNhbCBiZWluZyBjb3VudGVkLCB3aXRoIHRoZSBtYXAncyBvd24gY29sb3Vycy4gKi9cbiAgZ3JvdXA6IE9taWNzR3JvdXBpbmc7XG4gIC8qKiBgMWAgbWFya3MgYSBzZWxlY3RlZCBvYnNlcnZhdGlvbjsgd2hlbiBwcmVzZW50IHRoZSBiYXJzIHNob3cgdGhlIHNlbGVjdGlvblxuICAgKiAgYWdhaW5zdCB0aGUgdG90YWwuICovXG4gIHNlbGVjdGlvbj86IFVpbnQ4QXJyYXkgfCBudWxsO1xuICAvKiogQmFycyBiZWZvcmUgdGhlIHRhaWwgaXMgYWdncmVnYXRlZC4gKi9cbiAgbWF4PzogbnVtYmVyO1xufVxuXG4vKiogV2hhdCB7QGxpbmsgY291bnRCeUNhdGVnb3J5fSByZXR1cm5zLiAqL1xuZXhwb3J0IGludGVyZmFjZSBDYXRlZ29yeUNvdW50cyB7XG4gIGxhYmVsczogc3RyaW5nW107XG4gIGNvbG9yczogc3RyaW5nW107XG4gIHRvdGFsczogbnVtYmVyW107XG4gIHNlbGVjdGVkOiBudW1iZXJbXTtcbn1cblxuLyoqIFBlci1jYXRlZ29yeSBjb3VudHMsIGJpZ2dlc3QgZmlyc3QsIHdpdGggdGhlIHRhaWwgZm9sZGVkIGludG8gb25lIGJhci4gKi9cbmV4cG9ydCBmdW5jdGlvbiBjb3VudEJ5Q2F0ZWdvcnkoaW5wdXQ6IE9taWNzQ291bnRJbnB1dCk6IENhdGVnb3J5Q291bnRzIHtcbiAgY29uc3QgeyBjb2RlcywgY2F0ZWdvcmllcywgY29sb3JzIH0gPSBpbnB1dC5ncm91cDtcbiAgY29uc3Qgc2VsZWN0aW9uID0gYWN0aXZlU2VsZWN0aW9uKGlucHV0LnNlbGVjdGlvbik7XG4gIGNvbnN0IHRvdGFscyA9IG5ldyBGbG9hdDY0QXJyYXkoY2F0ZWdvcmllcy5sZW5ndGgpO1xuICBjb25zdCBzZWxlY3RlZCA9IG5ldyBGbG9hdDY0QXJyYXkoY2F0ZWdvcmllcy5sZW5ndGgpO1xuICBmb3IgKGxldCBpID0gMDsgaSA8IGNvZGVzLmxlbmd0aDsgaSsrKSB7XG4gICAgY29uc3QgYyA9IGNvZGVzW2ldO1xuICAgIGlmIChjID09PSBOT19DQVRFR09SWSB8fCBjID49IGNhdGVnb3JpZXMubGVuZ3RoKSBjb250aW51ZTtcbiAgICB0b3RhbHNbY10rKztcbiAgICBpZiAoc2VsZWN0aW9uICYmIHNlbGVjdGlvbltpXSkgc2VsZWN0ZWRbY10rKztcbiAgfVxuXG4gIGNvbnN0IHJhbmtlZCA9IEFycmF5LmZyb20odG90YWxzLCAobiwgYykgPT4gKHsgYywgbiB9KSlcbiAgICAuZmlsdGVyKChyKSA9PiByLm4gPiAwKVxuICAgIC5zb3J0KChhLCBiKSA9PiBiLm4gLSBhLm4pO1xuICBjb25zdCBtYXggPSBpbnB1dC5tYXggPz8gTUFYX0NPVU5UX0JBUlM7XG4gIGNvbnN0IGhlYWQgPSByYW5rZWQuc2xpY2UoMCwgbWF4KTtcbiAgY29uc3QgdGFpbCA9IHJhbmtlZC5zbGljZShtYXgpO1xuXG4gIGNvbnN0IG91dCA9IHtcbiAgICBsYWJlbHM6IGhlYWQubWFwKChyKSA9PiBjYXRlZ29yaWVzW3IuY10pLFxuICAgIGNvbG9yczogaGVhZC5tYXAoKHIpID0+IGNvbG9yc1tyLmNdID8/IERFRkFVTFRfQ09MT1IpLFxuICAgIHRvdGFsczogaGVhZC5tYXAoKHIpID0+IHIubiksXG4gICAgc2VsZWN0ZWQ6IGhlYWQubWFwKChyKSA9PiBzZWxlY3RlZFtyLmNdKSxcbiAgfTtcbiAgLy8gVGhlIHRhaWwgaXMgYWdncmVnYXRlZCByYXRoZXIgdGhhbiBkcm9wcGVkOiAzMzggc3ViY2xhc3NlcyBkbyBub3QgZml0IGFcbiAgLy8gcmVhZGFibGUgYXhpcywgYnV0IHNpbGVudGx5IHNob3dpbmcgMjUgb2YgdGhlbSB3b3VsZCBtaXNzdGF0ZSB0aGUgd2hvbGUuXG4gIGlmICh0YWlsLmxlbmd0aCkge1xuICAgIG91dC5sYWJlbHMucHVzaChgb3RoZXIgKCR7dGFpbC5sZW5ndGh9IGNhdGVnb3JpZXMpYCk7XG4gICAgb3V0LmNvbG9ycy5wdXNoKCcjOWU5ZTllJyk7XG4gICAgb3V0LnRvdGFscy5wdXNoKHRhaWwucmVkdWNlKChhLCByKSA9PiBhICsgci5uLCAwKSk7XG4gICAgb3V0LnNlbGVjdGVkLnB1c2godGFpbC5yZWR1Y2UoKGEsIHIpID0+IGEgKyBzZWxlY3RlZFtyLmNdLCAwKSk7XG4gIH1cbiAgcmV0dXJuIG91dDtcbn1cblxuLyoqXG4gKiBCYXJzIG9mIHBlci1jYXRlZ29yeSBjZWxsIGNvdW50cyDigJQgdGhlIGRpc3RyaWJ1dGlvbiBhIENBVEVHT1JJQ0FMIGNvbG91clxuICogc291cmNlIGhhcy5cbiAqXG4gKiBBIGhpc3RvZ3JhbSBvZiBhIGNhdGVnb3J5IGNvZGUgd291bGQgYmUgbWVhbmluZ2xlc3MgKHRoZSBjb2RlcyBhcmUgbGFiZWxzLCBub3RcbiAqIG1hZ25pdHVkZXMpLCBidXQgXCJob3cgbWFueSBjZWxscyBwZXIgY2xhc3NcIiBpcyBhIHJlYWwgcXVlc3Rpb24sIGFuZCB0aGUgc2FtZSBvbmVcbiAqIHRoZSBsZWdlbmQgaW1wbGllcyB3aXRob3V0IGFuc3dlcmluZy4gSG9yaXpvbnRhbCwgYmVjYXVzZSB0YXhvbm9teSBsYWJlbHMgYXJlXG4gKiBsb25nLCBhbmQgc29ydGVkLCBiZWNhdXNlIHJhbmsgaXMgd2hhdCB0aGUgY2hhcnQgaXMgcmVhZCBmb3IuXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBidWlsZENvdW50VHJhY2VzKFxuICBpbnB1dDogT21pY3NDb3VudElucHV0LFxuICBjb3VudHM6IENhdGVnb3J5Q291bnRzID0gY291bnRCeUNhdGVnb3J5KGlucHV0KSxcbik6IHVua25vd25bXSB7XG4gIGNvbnN0IHsgbGFiZWxzLCBjb2xvcnMsIHRvdGFscywgc2VsZWN0ZWQgfSA9IGNvdW50cztcbiAgY29uc3Qgc2VsZWN0aW9uID0gYWN0aXZlU2VsZWN0aW9uKGlucHV0LnNlbGVjdGlvbik7XG4gIC8vIFBsb3RseSBkcmF3cyB0aGUgZmlyc3QgY2F0ZWdvcnkgYXQgdGhlIEJPVFRPTSBvZiBhIGhvcml6b250YWwgYXhpcywgc29cbiAgLy8gcmV2ZXJzZSB0byBwdXQgdGhlIGJpZ2dlc3QgYmFyIGF0IHRoZSB0b3Agd2hlcmUgdGhlIGV5ZSBzdGFydHMuXG4gIGNvbnN0IGZsaXAgPSA8VD4oYTogVFtdKTogVFtdID0+IGEuc2xpY2UoKS5yZXZlcnNlKCk7XG4gIGNvbnN0IHRyYWNlczogdW5rbm93bltdID0gW1xuICAgIHtcbiAgICAgIHR5cGU6ICdiYXInLFxuICAgICAgb3JpZW50YXRpb246ICdoJyxcbiAgICAgIHg6IGZsaXAodG90YWxzKSxcbiAgICAgIHk6IGZsaXAobGFiZWxzKSxcbiAgICAgIG5hbWU6IHNlbGVjdGlvbiA/ICdBbGwnIDogJ0NlbGxzJyxcbiAgICAgIG1hcmtlcjogeyBjb2xvcjogZmxpcChjb2xvcnMpIH0sXG4gICAgICBvcGFjaXR5OiBzZWxlY3Rpb24gPyAwLjQ1IDogMSxcbiAgICAgIGhvdmVydGVtcGxhdGU6ICcle3h9IG9iczxleHRyYT4le3l9PC9leHRyYT4nLFxuICAgIH0sXG4gIF07XG4gIGlmIChzZWxlY3Rpb24pIHtcbiAgICB0cmFjZXMucHVzaCh7XG4gICAgICB0eXBlOiAnYmFyJyxcbiAgICAgIG9yaWVudGF0aW9uOiAnaCcsXG4gICAgICB4OiBmbGlwKHNlbGVjdGVkKSxcbiAgICAgIHk6IGZsaXAobGFiZWxzKSxcbiAgICAgIG5hbWU6ICdTZWxlY3RlZCcsXG4gICAgICBtYXJrZXI6IHsgY29sb3I6IGZsaXAoY29sb3JzKSB9LFxuICAgICAgaG92ZXJ0ZW1wbGF0ZTogJyV7eH0gb2JzPGV4dHJhPiV7eX0gwrcgc2VsZWN0ZWQ8L2V4dHJhPicsXG4gICAgfSk7XG4gIH1cbiAgcmV0dXJuIHRyYWNlcztcbn1cblxuLyoqXG4gKiBMYXlvdXQgZm9yIHtAbGluayBidWlsZENvdW50VHJhY2VzfS4gUGFzcyB0aGUgc2FtZSBgY291bnRzYCB0byBib3RoIHJhdGhlciB0aGFuIGxldHRpbmdcbiAqIGVhY2ggcnVuIGl0cyBvd24gZnVsbCBwYXNzIG92ZXIgdGhlIGNvZGVzLlxuICovXG5leHBvcnQgZnVuY3Rpb24gY291bnRzTGF5b3V0KFxuICBpbnB1dDogT21pY3NDb3VudElucHV0ICYgeyBuYW1lOiBzdHJpbmcgfSxcbiAgY291bnRzOiBDYXRlZ29yeUNvdW50cyA9IGNvdW50QnlDYXRlZ29yeShpbnB1dCksXG4pOiB1bmtub3duIHtcbiAgY29uc3QgeyBsYWJlbHMgfSA9IGNvdW50cztcbiAgcmV0dXJuIHtcbiAgICAvLyBSb29tIGZvciB0aGUgbGFiZWxzLCBhbmQgYSBoZWlnaHQgdGhhdCBncm93cyB3aXRoIHRoZSBiYXIgY291bnQgc28gMjVcbiAgICAvLyBjYXRlZ29yaWVzIGFyZSBub3QgY3J1c2hlZCBpbnRvIHRoZSBzYW1lIGJveCBhcyAzLlxuICAgIG1hcmdpbjogeyB0OiAxMCwgcjogMTAsIGI6IDQwLCBsOiA4IH0sXG4gICAgYXV0b3NpemU6IHRydWUsXG4gICAgLy8gT3ZlcmxhaWQsIG5vdCBzdGFja2VkOiB0aGUgc2VsZWN0ZWQgYmFyIHJlYWRzIGFnYWluc3QgdGhlIHRvdGFsIGl0IGNhbWVcbiAgICAvLyBmcm9tLCB3aGljaCBpcyB0aGUgY29tcGFyaXNvbiBiZWluZyBtYWRlLlxuICAgIGJhcm1vZGU6ICdvdmVybGF5JyxcbiAgICBzaG93bGVnZW5kOiAhIWFjdGl2ZVNlbGVjdGlvbihpbnB1dC5zZWxlY3Rpb24pLFxuICAgIGxlZ2VuZDogeyBvcmllbnRhdGlvbjogJ2gnLCB5OiAxLjEyLCB4OiAwIH0sXG4gICAgaG92ZXJtb2RlOiAnY2xvc2VzdCcsXG4gICAgeGF4aXM6IHsgdGl0bGU6IHsgdGV4dDogJ29ic2VydmF0aW9ucycgfSB9LFxuICAgIHlheGlzOiB7IGF1dG9tYXJnaW46IHRydWUsIHRpY2tsYWJlbHBvc2l0aW9uOiAnaW5zaWRlJywgdGlja2ZvbnQ6IHsgc2l6ZTogMTAgfSB9LFxuICAgIGhlaWdodDogTWF0aC5tYXgoMTgwLCAyMiAqIGxhYmVscy5sZW5ndGggKyA2MCksXG4gIH07XG59XG5cbi8vIOKUgOKUgCBlbWJlZGRpbmcg4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSAXG5cbi8qKlxuICogQW4gZW1iZWRkaW5nIHNjYXR0ZXIg4oCUIGEgVU1BUCwgdC1TTkUgb3IgUENBIHBsYW5lIG92ZXIgdGhlIHNhbWUgb2JzZXJ2YXRpb25zLlxuICpcbiAqIEFuc3dlcnMgYSBkaWZmZXJlbnQgcXVlc3Rpb24gZnJvbSB0aGUgbWFwOiB0aGUgbWFwIHNheXMgV0hFUkUgYSBwb3B1bGF0aW9uIHNpdHMgaW4gdGhlIHRpc3N1ZSxcbiAqIHRoZSBlbWJlZGRpbmcgc2F5cyB3aGljaCBwb3B1bGF0aW9ucyB0aGVyZSBhcmUgYW5kIGhvdyBjbG9zZSB0aGV5IGFyZSBpbiBleHByZXNzaW9uLiBSZWFkIHNpZGVcbiAqIGJ5IHNpZGUsIGFuZCBzZWxlY3RpbmcgaW4gb25lIGhpZ2hsaWdodGluZyB0aGUgb3RoZXIsIGlzIHRoZSB3aG9sZSBwb2ludCBvZiBoYXZpbmcgYm90aC5cbiAqL1xuZXhwb3J0IGludGVyZmFjZSBPbWljc0VtYmVkZGluZ0lucHV0IHtcbiAgLyoqIEVtYmVkZGluZyBjb29yZGluYXRlcywgaW5kZXgtYWxpZ25lZCB3aXRoIHRoZSBvYnNlcnZhdGlvbnMuICovXG4gIHg6IEZsb2F0MzJBcnJheTtcbiAgeTogRmxvYXQzMkFycmF5O1xuICAvKipcbiAgICogVGhpcmQgZGltZW5zaW9uLCB3aGVuIHRoZSBlbWJlZGRpbmcgaGFzIG9uZS5cbiAgICpcbiAgICogSXRzIHByZXNlbmNlIGlzIHdoYXQgc3dpdGNoZXMgdGhlIHBsb3QgdG8gYSByb3RhdGFibGUgM0Qgc2NhdHRlci4gQSAzRCBlbWJlZGRpbmcgaXNcbiAgICogYWx3YXlzIENPTVBVVEVEIOKAlCBldmVyeSBlbWJlZGRpbmcgcHVibGlzaGVkIHdpdGggYSBzcGF0aWFsIGRhdGFzZXQgaXMgMkQsIGJlY2F1c2UgYVxuICAgKiBVTUFQIGV4aXN0cyB0byBiZSBsb29rZWQgYXQg4oCUIHNvIGBkZXJpdmVkYCBpcyBleHBlY3RlZCBhbG9uZ3NpZGUgaXQuXG4gICAqL1xuICB6PzogRmxvYXQzMkFycmF5O1xuICAvKiogQXhpcyBsYWJlbCBzdGVtLCBlLmcuIFwiVU1BUFwiIOKAlCB0aGUgYXhlcyBiZWNvbWUgXCJVTUFQIDFcIiAvIFwiVU1BUCAyXCIuICovXG4gIGxhYmVsOiBzdHJpbmc7XG4gIC8qKiBDb2xvdXIgYnkgYSBjYXRlZ29yaWNhbCBjb2x1bW46IHBlci1vYnNlcnZhdGlvbiBjb2RlcyBwbHVzIHRoZSBjYXRlZ29yeSBuYW1lcy9jb2xvdXJzLiAqL1xuICBjYXRlZ29yaWVzPzoge1xuICAgIGNvZGVzOiBVaW50MTZBcnJheTtcbiAgICBuYW1lczogcmVhZG9ubHkgc3RyaW5nW107XG4gICAgY29sb3JzOiByZWFkb25seSBzdHJpbmdbXTtcbiAgfTtcbiAgLyoqIE1hcmtlciBkaWFtZXRlciBpbiBweC4gKi9cbiAgc2l6ZT86IG51bWJlcjtcbiAgLyoqXG4gICAqIFNlbGVjdGlvbiBtYXNrIG92ZXIgdGhlIG9ic2VydmF0aW9ucy4gV2hlbiBwcmVzZW50LCB1bnNlbGVjdGVkIHBvaW50cyBhcmUgZGltbWVkIHJhdGhlciB0aGFuXG4gICAqIGRyb3BwZWQ6IHRoZSBzaGFwZSBvZiB0aGUgd2hvbGUgZW1iZWRkaW5nIGlzIHRoZSBjb250ZXh0IHRoYXQgbWFrZXMgYSBzZWxlY3Rpb24gbGVnaWJsZSwgYW5kXG4gICAqIHJlbW92aW5nIGl0IHdvdWxkIGxlYXZlIGEgaGFuZGZ1bCBvZiBkb3RzIGZsb2F0aW5nIGluIGFuIGVtcHR5IHBsYW5lLlxuICAgKi9cbiAgc2VsZWN0aW9uPzogVWludDhBcnJheTtcbiAgLyoqIFRydWUgd2hlbiB0aGUgY29vcmRpbmF0ZXMgd2VyZSBjb21wdXRlZCBoZXJlIHJhdGhlciB0aGFuIHB1Ymxpc2hlZCB3aXRoIHRoZSBkYXRhc2V0LiAqL1xuICBkZXJpdmVkPzogYm9vbGVhbjtcbiAgLyoqXG4gICAqIEZyYWN0aW9uIG9mIHZhcmlhbmNlIHBlciBheGlzLCBmb3IgYSBMSU5FQVIgZW1iZWRkaW5nLlxuICAgKlxuICAgKiBQcmVzZW50IGZvciBhIFBDQSBhbmQgYWJzZW50IGZvciBhIFVNQVAsIGFuZCB0aGF0IGRpZmZlcmVuY2UgaXMgdGhlIHBvaW50IG9mIHNob3dpbmdcbiAgICogYSBQQ0EgYXQgYWxsOiBpdHMgYXhlcyBhcmUgb3JkZXJlZCBhbmQgZWFjaCBleHBsYWlucyBhIG1lYXN1cmFibGUgc2hhcmUgb2YgdGhlXG4gICAqIHZhcmlhbmNlLCBzbyBcIlBDMSAoMjMlKVwiIHNheXMgc29tZXRoaW5nIGEgcmVhZGVyIGNhbiBhY3Qgb24uIEEgVU1BUCdzIGNvb3JkaW5hdGVzIGFyZVxuICAgKiBhbiBhcmJpdHJhcnkgb3V0cHV0IG9mIGFuIG9wdGltaXNhdGlvbiDigJQgdW5vcmRlcmVkLCB1bml0bGVzcywgYW5kIHJlcHJvZHVjaWJsZSBvbmx5XG4gICAqIHVwIHRvIGEgcm90YXRpb24g4oCUIHNvIHRoZXJlIGlzIG5vdGhpbmcgdG8gbGFiZWwgdGhlbSB3aXRoLlxuICAgKi9cbiAgdmFyaWFuY2VSYXRpbz86IG51bWJlcltdO1xuICAvKipcbiAgICogVGhlIHZpZXcgdG8ga2VlcCBhY3Jvc3MgYSByZWRyYXcuXG4gICAqXG4gICAqIGBQbG90bHkucmVhY3RgIHJlc2V0cyB0aGUgM0Qgc2NlbmUgY2FtZXJhIGFuZCBhbnkgem9vbWVkIDJEIGF4aXMgcmFuZ2UgdW5sZXNzIHRoZVxuICAgKiBsYXlvdXQgY2FycmllcyB0aGVtLCBzbyByZWNvbG91cmluZyBvciBzZWxlY3Rpbmcgd291bGQgdGhyb3cgYXdheSBhbiBvcmllbnRhdGlvbiB0aGVcbiAgICogdXNlciBoYWQgc2V0IHVwLiBSb3RhdGluZyBhIGNsb3VkIHRvIHNlZSBhIHN0cnVjdHVyZSBhbmQgbG9zaW5nIGl0IG9uIHRoZSBuZXh0IGNsaWNrXG4gICAqIG1ha2VzIHRoZSBwbG90IHVudXNhYmxlIGZvciB0aGUgdGhpbmcgaXQgaXMgZm9yLlxuICAgKlxuICAgKiBgY2FtZXJhYCBpcyBhIDNEIHNjZW5lIGNhbWVyYTsgYHJhbmdlc2AgYXJlIDJEIGF4aXMgcmFuZ2VzLCBhbmQgYXJlIG9ubHkgcGFzc2VkIHdoZW5cbiAgICogdGhlIHVzZXIgaGFzIGFjdHVhbGx5IHpvb21lZCDigJQgZnJlZXppbmcgYW4gYXV0b3JhbmdlZCBheGlzIHdvdWxkIHN0b3AgdGhlIHBsb3RcbiAgICogcmUtZml0dGluZyB3aGVuIHRoZSBkYXRhIGNoYW5nZXMuXG4gICAqL1xuICB2aWV3PzogeyBjYW1lcmE/OiB1bmtub3duOyByYW5nZXM/OiB7IHg6IHVua25vd247IHk6IHVua25vd24gfSB9O1xufVxuXG4vKipcbiAqIFBhc3QgdGhpcyBtYW55IGNhdGVnb3JpZXMsIG9uZSB0cmFjZSBlYWNoIHN0b3BzIGJlaW5nIHdvcnRoIGl0LlxuICpcbiAqIEEgdHJhY2UgcGVyIGNhdGVnb3J5IGJ1eXMgYSBsZWdlbmQgd2hvc2UgZW50cmllcyB0b2dnbGUg4oCUIGNsaWNrIG9uZSB0byBpc29sYXRlIGEgcG9wdWxhdGlvbixcbiAqIHdoaWNoIGlzIGhvdyB0aGVzZSBwbG90cyBhcmUgYWN0dWFsbHkgcmVhZC4gQnV0IFBsb3RseSBob2xkcyBwZXItdHJhY2Ugc3RhdGUsIGFuZCBhIGxlZ2VuZCBvZlxuICogaHVuZHJlZHMgb2YgZW50cmllcyBpcyB1bnJlYWRhYmxlIGFueXdheSAodGhlIEFCQyBhdGxhcyBoYXMgMzM4IHN1YmNsYXNzZXMpLCBzbyBiZXlvbmQgdGhlIGNhcFxuICogZXZlcnl0aGluZyBnb2VzIGludG8gT05FIHRyYWNlIHdpdGggYSBwZXItcG9pbnQgY29sb3VyOiBubyBsZWdlbmQsIGJ1dCBpdCBzdGlsbCBkcmF3cy5cbiAqL1xuZXhwb3J0IGNvbnN0IEVNQkVERElOR19NQVhfTEVHRU5EX0NBVEVHT1JJRVMgPSA0MDtcblxuLyoqXG4gKiBDYXRlZ29yaWVzIHBhc3Qgd2hpY2ggdGhlIGxlZ2VuZCBpcyBub3QgRFJBV04sIHRob3VnaCB0aGUgdHJhY2VzIHN0YXkgc3BsaXQuXG4gKlxuICogQSBsZWdlbmQgaXMgb25seSB3b3J0aCBpdHMgc3BhY2UgaWYgaXQgZml0cy4gc2VxRklTSCdzIDIyIGNlbGwgdHlwZXMgc3RhY2sgaW50byBvbmUgdGFsbFxuICogY29sdW1uIGluIGEgZG9ja2VkIHBhbmVsLCBvdmVybGFwcGluZyB0aGUgYXhpcyB0aXRsZSBhbmQgcnVubmluZyBvZmYgdGhlIGJvdHRvbSDigJQgYW5kXG4gKiB0aGUgY29sb3VycyBhbHJlYWR5IG1hdGNoIHRoZSBtYXAsIHdob3NlIG93biBwYW5lbCBsaXN0cyB0aGVtLCB3aGlsZSBob3ZlciBuYW1lcyB0aGVcbiAqIGNhdGVnb3J5IHVuZGVyIHRoZSBjdXJzb3IuIFNvIHBhc3QgdGhpcyB0aGUgcGxvdCB0YWtlcyB0aGUgd2hvbGUgcGFuZWwgYW5kIHRoZSBsZWdlbmRcbiAqIGlzIGRyb3BwZWQgcmF0aGVyIHRoYW4gc2hvd24gYmFkbHkuXG4gKi9cbmV4cG9ydCBjb25zdCBFTUJFRERJTkdfTUFYX0xFR0VORF9TSE9XTiA9IDEwO1xuXG4vKiogRGltbWluZyBhcHBsaWVkIHRvIHVuc2VsZWN0ZWQgcG9pbnRzLCBtYXRjaGluZyB0aGUgbWFwJ3MgbXV0ZWQgb3BhY2l0eS4gKi9cbmNvbnN0IEVNQkVERElOR19NVVRFRF9PUEFDSVRZID0gMC4xNTtcblxuLyoqXG4gKiBNaXggYSBoZXggY29sb3VyIHRvd2FyZCB3aGl0ZSBieSBgYW1vdW50YC5cbiAqXG4gKiBIb3cgdW5zZWxlY3RlZCBwb2ludHMgYXJlIGRpbW1lZCBpbiAzRC4gYHNjYXR0ZXIzZGAgYWNjZXB0cyBgbWFya2VyLm9wYWNpdHlgIG9ubHkgYXMgYVxuICogU0NBTEFSIOKAlCBhIHBlci1wb2ludCBhcnJheSBpcyBzaWxlbnRseSBjb2xsYXBzZWQgdG8gdGhlIGZpcnN0IHZhbHVlLCB2ZXJpZmllZCBhZ2FpbnN0XG4gKiB0aGUgYnVuZGxlZCBQbG90bHkg4oCUIHNvIHRoZSBwZXItcG9pbnQgb3BhY2l0eSB0aGF0IGRpbXMgdGhlIDJEIHBsb3QgZG9lcyBub3RoaW5nIHRoZXJlLFxuICogYW5kIGEgc2VsZWN0aW9uIGFwcGVhcmVkIHRvIGhpZ2hsaWdodCBub3RoaW5nIGluIDNELiBDb2xvdXIgYXJyYXlzIEFSRSBob25vdXJlZCwgc29cbiAqIHRoZSBzYW1lIGVmZmVjdCBpcyBwcm9kdWNlZCBieSBtaXhpbmcgdG93YXJkIHRoZSBwYXBlciBpbnN0ZWFkLlxuICovXG5mdW5jdGlvbiB0b3dhcmRQYXBlcihoZXg6IHN0cmluZywgYW1vdW50OiBudW1iZXIpOiBzdHJpbmcge1xuICBjb25zdCByZ2IgPSBwYXJzZUNzc0NvbG9yKGhleCk7XG4gIGlmICghcmdiKSByZXR1cm4gaGV4O1xuICBjb25zdCBtaXggPSAoYzogbnVtYmVyKTogbnVtYmVyID0+IE1hdGgucm91bmQoYyArICgyNTUgLSBjKSAqIGFtb3VudCk7XG4gIHJldHVybiByZ2JUb0hleChbbWl4KHJnYlswXSksIG1peChyZ2JbMV0pLCBtaXgocmdiWzJdKV0pO1xufVxuXG5jb25zdCBERUZBVUxUX0VNQkVERElOR19QT0lOVF9TSVpFID0gNDtcblxuZXhwb3J0IGZ1bmN0aW9uIGJ1aWxkRW1iZWRkaW5nVHJhY2VzKGlucHV0OiBPbWljc0VtYmVkZGluZ0lucHV0KTogdW5rbm93bltdIHtcbiAgY29uc3QgeyB4LCB5LCBjYXRlZ29yaWVzLCBzZWxlY3Rpb24gfSA9IGlucHV0O1xuICBjb25zdCBuID0gTWF0aC5taW4oeC5sZW5ndGgsIHkubGVuZ3RoKTtcbiAgaWYgKG4gPT09IDApIHJldHVybiBbXTtcbiAgY29uc3QgeiA9IGlucHV0Lno7XG4gIC8vIGBzY2F0dGVyZ2xgIGZvciB0aGUgcGxhbmUg4oCUIDEwXjQtMTBeNiBwb2ludHMsIHdoaWNoIHRoZSBTVkcgcmVuZGVyZXIgd291bGQgbm90XG4gIC8vIHN1cnZpdmUuIGBzY2F0dGVyM2RgIGZvciB0aGUgY2xvdWQ6IFdlYkdMIHRvbywgYnV0IGEgZGlmZmVyZW50IHRyYWNlIHR5cGUgd2l0aCBpdHNcbiAgLy8gb3duIHNjZW5lLCB3aGljaCBpcyB3aHkgYSB0aGlyZCBkaW1lbnNpb24gY2Fubm90IGp1c3QgYmUgYWRkZWQgdG8gdGhlIGZvcm1lci4gSXRcbiAgLy8gY29zdHMgbW9yZSBwZXIgcG9pbnQsIHNvIGl0IHN1aXRzIHRoaXMgc2NhbGUgYW5kIG5vdCBtaWxsaW9ucy5cbiAgY29uc3QgdHlwZSA9IHogPyAnc2NhdHRlcjNkJyA6ICdzY2F0dGVyZ2wnO1xuICBjb25zdCBtYXJrZXJTaXplID0gelxuICAgID8gTWF0aC5tYXgoMSwgKGlucHV0LnNpemUgPz8gREVGQVVMVF9FTUJFRERJTkdfUE9JTlRfU0laRSkgLSAyKVxuICAgIDogKGlucHV0LnNpemUgPz8gREVGQVVMVF9FTUJFRERJTkdfUE9JTlRfU0laRSk7XG4gIGNvbnN0IG9wYWNpdHlGb3IgPSAoaTogbnVtYmVyKTogbnVtYmVyID0+ICghc2VsZWN0aW9uIHx8IHNlbGVjdGlvbltpXSA/IDEgOiBFTUJFRERJTkdfTVVURURfT1BBQ0lUWSk7XG4gIGNvbnN0IGlzU2VsZWN0ZWQgPSAoaTogbnVtYmVyKTogYm9vbGVhbiA9PiAhc2VsZWN0aW9uIHx8IHNlbGVjdGlvbltpXSA9PT0gMTtcbiAgLy8gSW4gM0QgdGhlIGRpbW1pbmcgaGFzIHRvIGJlIGluIHRoZSBDT0xPVVIsIHNpbmNlIGEgcGVyLXBvaW50IG9wYWNpdHkgYXJyYXkgaXNcbiAgLy8gaWdub3JlZCB0aGVyZS4gQ2FjaGVkIHBlciBpbnB1dCBjb2xvdXI6IDE5ayBsb29rdXBzIG9mIHRoZSBzYW1lIGZldyBjYXRlZ29yaWVzLlxuICBjb25zdCBkaW1DYWNoZSA9IG5ldyBNYXA8c3RyaW5nLCBzdHJpbmc+KCk7XG4gIGNvbnN0IHNoYWRlID0gKGhleDogc3RyaW5nLCBpOiBudW1iZXIpOiBzdHJpbmcgPT4ge1xuICAgIGlmICgheiB8fCBpc1NlbGVjdGVkKGkpKSByZXR1cm4gaGV4O1xuICAgIGNvbnN0IGhpdCA9IGRpbUNhY2hlLmdldChoZXgpO1xuICAgIGlmIChoaXQpIHJldHVybiBoaXQ7XG4gICAgY29uc3QgZGltbWVkID0gdG93YXJkUGFwZXIoaGV4LCAxIC0gRU1CRURESU5HX01VVEVEX09QQUNJVFkpO1xuICAgIGRpbUNhY2hlLnNldChoZXgsIGRpbW1lZCk7XG4gICAgcmV0dXJuIGRpbW1lZDtcbiAgfTtcbiAgLyoqIFBlci1wb2ludCBvcGFjaXR5IGlzIGhvbm91cmVkIG9ubHkgYnkgdGhlIDJEIHRyYWNlIHR5cGVzLiAqL1xuICBjb25zdCBwZXJQb2ludE9wYWNpdHkgPSAhIXNlbGVjdGlvbiAmJiAhejtcbiAgLyoqIEV2ZXJ5IG9ic2VydmF0aW9uJ3Mgb3BhY2l0eSwgYnVpbHQgb25jZSBmb3IgdGhlIHNpbmdsZS10cmFjZSBwYXRocy4gKi9cbiAgY29uc3QgYWxsT3BhY2l0eSA9ICgpOiB7IG9wYWNpdHk/OiBudW1iZXJbXSB9ID0+XG4gICAgcGVyUG9pbnRPcGFjaXR5ID8geyBvcGFjaXR5OiBBcnJheS5mcm9tKHsgbGVuZ3RoOiBuIH0sIChfLCBpKSA9PiBvcGFjaXR5Rm9yKGkpKSB9IDoge307XG4gIC8qKiBUaGUgc2luZ2xlLXRyYWNlIGNvb3JkaW5hdGVzLiBgc2NhdHRlcmdsYCB0YWtlcyB0aGUgdHlwZWQgYXJyYXlzIGFzIHRoZXkgYXJlOyB0aGVcbiAgICogIDNEIHRyYWNlIGlzIGhhbmRlZCBwbGFpbiBhcnJheXMuICovXG4gIGNvbnN0IGNvb3JkcyA9ICgpOiBSZWNvcmQ8c3RyaW5nLCB1bmtub3duPiA9PlxuICAgIHpcbiAgICAgID8ge1xuICAgICAgICAgIHg6IEFycmF5LmZyb20oeC5zdWJhcnJheSgwLCBuKSksXG4gICAgICAgICAgeTogQXJyYXkuZnJvbSh5LnN1YmFycmF5KDAsIG4pKSxcbiAgICAgICAgICB6OiBBcnJheS5mcm9tKHouc3ViYXJyYXkoMCwgbikpLFxuICAgICAgICB9XG4gICAgICA6IHsgeDogeC5zdWJhcnJheSgwLCBuKSwgeTogeS5zdWJhcnJheSgwLCBuKSB9O1xuXG4gIGlmICghY2F0ZWdvcmllcyB8fCBjYXRlZ29yaWVzLm5hbWVzLmxlbmd0aCA9PT0gMCkge1xuICAgIHJldHVybiBbXG4gICAgICB7XG4gICAgICAgIHR5cGUsXG4gICAgICAgIG1vZGU6ICdtYXJrZXJzJyxcbiAgICAgICAgLi4uY29vcmRzKCksXG4gICAgICAgIC8vIFRoZSBPQlNFUlZBVElPTiBpbmRleCBwZXIgcG9pbnQsIGNhcnJpZWQgdGhyb3VnaCBzbyBhIGxhc3NvIGNhbiBiZSB0dXJuZWQgYmFja1xuICAgICAgICAvLyBpbnRvIGEgc2VsZWN0aW9uLiBQbG90bHkgcmVwb3J0cyBhIHNlbGVjdGVkIHBvaW50IGJ5IGl0cyBwb3NpdGlvbiB3aXRoaW4gaXRzXG4gICAgICAgIC8vIHRyYWNlLCB3aGljaCBpcyBub3QgdGhlIG9ic2VydmF0aW9uIGluZGV4IG9uY2UgdGhlIHBvaW50cyBhcmUgc3BsaXQgYnkgY2F0ZWdvcnkuXG4gICAgICAgIGN1c3RvbWRhdGE6IEFycmF5LmZyb20oeyBsZW5ndGg6IG4gfSwgKF8sIGkpID0+IGkpLFxuICAgICAgICBtYXJrZXI6IHtcbiAgICAgICAgICBzaXplOiBtYXJrZXJTaXplLFxuICAgICAgICAgIC8vIEEgZmxhdCBjb2xvdXIgbm9ybWFsbHk7IHBlciBwb2ludCBvbmNlIGEgc2VsZWN0aW9uIGhhcyB0byBkaW0gc29tZSBvZiB0aGVtIGluXG4gICAgICAgICAgLy8gM0QsIHdoZXJlIG9wYWNpdHkgYXJyYXlzIGFyZSBpZ25vcmVkLlxuICAgICAgICAgIGNvbG9yOiBzZWxlY3Rpb24gJiYgeiA/IEFycmF5LmZyb20oeyBsZW5ndGg6IG4gfSwgKF8sIGkpID0+IHNoYWRlKCcjNGM3MmIwJywgaSkpIDogJyM0YzcyYjAnLFxuICAgICAgICAgIC4uLmFsbE9wYWNpdHkoKSxcbiAgICAgICAgfSxcbiAgICAgICAgaG92ZXJpbmZvOiAnbm9uZScsXG4gICAgICAgIHNob3dsZWdlbmQ6IGZhbHNlLFxuICAgICAgfSxcbiAgICBdO1xuICB9XG5cbiAgY29uc3QgeyBjb2RlcywgbmFtZXMsIGNvbG9ycyB9ID0gY2F0ZWdvcmllcztcbiAgaWYgKG5hbWVzLmxlbmd0aCA+IEVNQkVERElOR19NQVhfTEVHRU5EX0NBVEVHT1JJRVMpIHtcbiAgICAvLyBPbmUgdHJhY2UsIHBlci1wb2ludCBjb2xvdXIuIEhvdmVyIHN0aWxsIG5hbWVzIHRoZSBjYXRlZ29yeSwgd2hpY2ggaXMgdGhlIHBhcnQgdGhhdFxuICAgIC8vIG1hdHRlcnM7IHRoZSBsZWdlbmQgaXMgd2hhdCBpcyBsb3N0LlxuICAgIHJldHVybiBbXG4gICAgICB7XG4gICAgICAgIHR5cGUsXG4gICAgICAgIG1vZGU6ICdtYXJrZXJzJyxcbiAgICAgICAgLi4uY29vcmRzKCksXG4gICAgICAgIG1hcmtlcjoge1xuICAgICAgICAgIHNpemU6IG1hcmtlclNpemUsXG4gICAgICAgICAgY29sb3I6IEFycmF5LmZyb20oeyBsZW5ndGg6IG4gfSwgKF8sIGkpID0+IHNoYWRlKGNvbG9yc1tjb2Rlc1tpXV0gPz8gJyM5OTk5OTknLCBpKSksXG4gICAgICAgICAgLi4uYWxsT3BhY2l0eSgpLFxuICAgICAgICB9LFxuICAgICAgICBjdXN0b21kYXRhOiBBcnJheS5mcm9tKHsgbGVuZ3RoOiBuIH0sIChfLCBpKSA9PiBpKSxcbiAgICAgICAgdGV4dDogQXJyYXkuZnJvbSh7IGxlbmd0aDogbiB9LCAoXywgaSkgPT4gbmFtZXNbY29kZXNbaV1dID8/ICd1bmFzc2lnbmVkJyksXG4gICAgICAgIGhvdmVydGVtcGxhdGU6ICcle3RleHR9PGV4dHJhPjwvZXh0cmE+JyxcbiAgICAgICAgc2hvd2xlZ2VuZDogZmFsc2UsXG4gICAgICB9LFxuICAgIF07XG4gIH1cblxuICAvLyBPbmUgdHJhY2UgcGVyIGNhdGVnb3J5OiB0aGUgbGVnZW5kIGVudHJpZXMgdG9nZ2xlLCBzbyBhIHBvcHVsYXRpb24gY2FuIGJlIGlzb2xhdGVkIGJ5XG4gIC8vIGNsaWNraW5nIHJhdGhlciB0aGFuIGJ5IHJlLWNvbG91cmluZyB0aGUgd2hvbGUgcGxvdC5cbiAgY29uc3QgYnVja2V0czogbnVtYmVyW11bXSA9IG5hbWVzLm1hcCgoKSA9PiBbXSk7XG4gIGZvciAobGV0IGkgPSAwOyBpIDwgbjsgaSsrKSB7XG4gICAgY29uc3QgYyA9IGNvZGVzW2ldO1xuICAgIC8vIE5PX0NBVEVHT1JZLCBvciBhIGNvZGUgcGFzdCB0aGUgbGlzdCwgaXMgdW5hc3NpZ25lZCDigJQgZHJvcHBlZCByYXRoZXIgdGhhbiBkcmF3biBpbiBhXG4gICAgLy8gY29sb3VyIHRoYXQgd291bGQgcmVhZCBhcyBhIHBvcHVsYXRpb24gb2YgaXRzIG93bi5cbiAgICBpZiAoYyA8IGJ1Y2tldHMubGVuZ3RoKSBidWNrZXRzW2NdLnB1c2goaSk7XG4gIH1cbiAgcmV0dXJuIGJ1Y2tldHNcbiAgICAubWFwKChpZHgsIGMpID0+ICh7IGlkeCwgYyB9KSlcbiAgICAuZmlsdGVyKCh7IGlkeCB9KSA9PiBpZHgubGVuZ3RoID4gMClcbiAgICAubWFwKCh7IGlkeCwgYyB9KSA9PiAoe1xuICAgICAgdHlwZSxcbiAgICAgIG1vZGU6ICdtYXJrZXJzJyxcbiAgICAgIG5hbWU6IG5hbWVzW2NdLFxuICAgICAgeDogaWR4Lm1hcCgoaSkgPT4geFtpXSksXG4gICAgICB5OiBpZHgubWFwKChpKSA9PiB5W2ldKSxcbiAgICAgIC4uLih6ID8geyB6OiBpZHgubWFwKChpKSA9PiB6W2ldKSB9IDoge30pLFxuICAgICAgLy8gVGhpcyB0cmFjZSdzIHBvaW50cyBBUkUgYSBzdWJzZXQsIHNvIHRoZSBvYnNlcnZhdGlvbiBpbmRleCBoYXMgdG8gdHJhdmVsIHdpdGhcbiAgICAgIC8vIHRoZW07IGBwb2ludEluZGV4YCBhbG9uZSB3b3VsZCBhZGRyZXNzIHRoZSB3cm9uZyBjZWxsLlxuICAgICAgY3VzdG9tZGF0YTogaWR4LFxuICAgICAgbWFya2VyOiB7XG4gICAgICAgIHNpemU6IG1hcmtlclNpemUsXG4gICAgICAgIGNvbG9yOiBzZWxlY3Rpb24gJiYgeiA/IGlkeC5tYXAoKGkpID0+IHNoYWRlKGNvbG9yc1tjXSA/PyAnIzk5OTk5OScsIGkpKSA6IChjb2xvcnNbY10gPz8gJyM5OTk5OTknKSxcbiAgICAgICAgLi4uKHBlclBvaW50T3BhY2l0eSA/IHsgb3BhY2l0eTogaWR4Lm1hcChvcGFjaXR5Rm9yKSB9IDoge30pLFxuICAgICAgfSxcbiAgICAgIC8vIFNwbGl0IHBlciBjYXRlZ29yeSByZWdhcmRsZXNzLCBzbyBob3ZlciBuYW1lcyBpdCBhbmQgYSBmdXR1cmUgaXNvbGF0ZSBjb250cm9sXG4gICAgICAvLyBoYXMgc29tZXRoaW5nIHRvIHRvZ2dsZTsgb25seSB0aGUgbGVnZW5kJ3MgVklTSUJJTElUWSBkZXBlbmRzIG9uIHRoZSBjb3VudC5cbiAgICAgIHNob3dsZWdlbmQ6IG5hbWVzLmxlbmd0aCA8PSBFTUJFRERJTkdfTUFYX0xFR0VORF9TSE9XTixcbiAgICAgIGhvdmVydGVtcGxhdGU6IGAke25hbWVzW2NdfTxleHRyYT48L2V4dHJhPmAsXG4gICAgfSkpO1xufVxuXG4vKipcbiAqIEF4aXMgdGl0bGU6IHRoZSBlbWJlZGRpbmcncyBuYW1lLCB0aGUgYXhpcyBudW1iZXIsIGFuZCBpdHMgdmFyaWFuY2Ugc2hhcmUgd2hlbiB0aGVyZSBpc1xuICogb25lIHRvIHJlcG9ydC5cbiAqL1xuZnVuY3Rpb24gYXhpc1RpdGxlKHN0ZW06IHN0cmluZywgYXhpczogbnVtYmVyLCB2YXJpYW5jZVJhdGlvPzogbnVtYmVyW10pOiBzdHJpbmcge1xuICBjb25zdCBzaGFyZSA9IHZhcmlhbmNlUmF0aW8/LltheGlzIC0gMV07XG4gIGlmIChzaGFyZSA9PT0gdW5kZWZpbmVkIHx8ICFOdW1iZXIuaXNGaW5pdGUoc2hhcmUpKSByZXR1cm4gYCR7c3RlbX0gJHtheGlzfWA7XG4gIC8vIE9uZSBkZWNpbWFsOiB0aGUgZGlmZmVyZW5jZSBiZXR3ZWVuIDIzLjQlIGFuZCAyMyUgaXMgd29ydGggc2VlaW5nIHdoZW4gY29tcGFyaW5nXG4gIC8vIGNvbXBvbmVudHMsIGFuZCBtb3JlIGRpZ2l0cyB0aGFuIHRoYXQgaXMgbm9pc2UgZnJvbSB0aGUgZXN0aW1hdGUuXG4gIHJldHVybiBgJHtzdGVtfSAke2F4aXN9ICgkeyhzaGFyZSAqIDEwMCkudG9GaXhlZCgxKX0lKWA7XG59XG5cbmV4cG9ydCBmdW5jdGlvbiBlbWJlZGRpbmdMYXlvdXQoaW5wdXQ6IE9taWNzRW1iZWRkaW5nSW5wdXQpOiB1bmtub3duIHtcbiAgY29uc3Qgc3RlbSA9IGlucHV0LmxhYmVsIHx8ICdFbWJlZGRpbmcnO1xuICBjb25zdCB2ciA9IGlucHV0LnZhcmlhbmNlUmF0aW87XG4gIC8vIE5vIGFubm90YXRpb24gZm9yIGEgZGVyaXZlZCBlbWJlZGRpbmcuIFRoYXQgYSByZWNvbXB1dGVkIFVNQVAgaXMgbm90IHRoZSBwdWJsaXNoZWRcbiAgLy8gcGljdHVyZSBkb2VzIG5lZWQgc2F5aW5nIOKAlCBidXQgdGhlIHBhbmVsJ3MgY2FwdGlvbiBhbHJlYWR5IHNheXMgaXQsIGFuZCByZXBlYXRpbmcgaXRcbiAgLy8gb3ZlciB0aGUgcGxvdCBjb3N0IGEgc3RyaXAgb2YgdGhlIHBhbmVsJ3MgaGVpZ2h0IGFuZCwgaW4gdGhlIDNEIHNjZW5lLCBzYXQgb24gdG9wIG9mXG4gIC8vIHRoZSBjbG91ZC4gT25lIHN0YXRlbWVudCwgaW4gdGhlIGNhcHRpb24uXG5cbiAgaWYgKGlucHV0LnopIHtcbiAgICByZXR1cm4ge1xuICAgICAgYXV0b3NpemU6IHRydWUsXG4gICAgICAvLyBBIDNEIHNjZW5lIGhhcyBubyBtYXJnaW5zIHRvIHNwZWFrIG9mOyB0aGUgYXhlcyBsaXZlIGluc2lkZSBpdC5cbiAgICAgIG1hcmdpbjogeyBsOiAwLCByOiAwLCB0OiAwLCBiOiAwIH0sXG4gICAgICBzY2VuZToge1xuICAgICAgICB4YXhpczogeyB0aXRsZTogeyB0ZXh0OiBheGlzVGl0bGUoc3RlbSwgMSwgdnIpIH0gfSxcbiAgICAgICAgeWF4aXM6IHsgdGl0bGU6IHsgdGV4dDogYXhpc1RpdGxlKHN0ZW0sIDIsIHZyKSB9IH0sXG4gICAgICAgIHpheGlzOiB7IHRpdGxlOiB7IHRleHQ6IGF4aXNUaXRsZShzdGVtLCAzLCB2cikgfSB9LFxuICAgICAgICAvLyBDYXJyaWVkIGFjcm9zcyB0aGUgcmVkcmF3LCBvciBldmVyeSByZWNvbG91ciBzbmFwcyB0aGUgY2xvdWQgYmFjayB0byBpdHNcbiAgICAgICAgLy8gZGVmYXVsdCBvcmllbnRhdGlvbi5cbiAgICAgICAgLi4uKGlucHV0LnZpZXc/LmNhbWVyYSA/IHsgY2FtZXJhOiBpbnB1dC52aWV3LmNhbWVyYSB9IDoge30pLFxuICAgICAgICAvLyBFcXVhbCBhc3BlY3QgZm9yIHRoZSBzYW1lIHJlYXNvbiBhcyB0aGUgcGxhbmU6IHRoZSBheGVzIGNhcnJ5IG5vIHVuaXRzLCBzb1xuICAgICAgICAvLyBkaXN0YW5jZXMgb25seSBjb21wYXJlIGlmIGFsbCB0aHJlZSBhcmUgc2NhbGVkIGFsaWtlLiBgZGF0YWAga2VlcHMgdGhlIGNsb3VkJ3NcbiAgICAgICAgLy8gb3duIHByb3BvcnRpb25zIGluc3RlYWQgb2Ygc3RyZXRjaGluZyBpdCBpbnRvIHRoZSBjdWJlLlxuICAgICAgICBhc3BlY3Rtb2RlOiAnZGF0YScsXG4gICAgICB9LFxuICAgICAgc2hvd2xlZ2VuZDogZmFsc2UsXG4gICAgICBob3Zlcm1vZGU6ICdjbG9zZXN0JyxcbiAgICB9O1xuICB9XG5cbiAgcmV0dXJuIHtcbiAgICBhdXRvc2l6ZTogdHJ1ZSxcbiAgICAvLyBCb3R0b20gbWFyZ2luIGNhcnJpZXMgdGhlIGxlZ2VuZDogbGFpZCBvdXQgQkVMT1cgdGhlIHBsb3QgcmF0aGVyIHRoYW4gYmVzaWRlIGl0LlxuICAgIC8vIEEgdmVydGljYWwgbGVnZW5kIG9mIDIyIGNlbGwgdHlwZXMgdG9vayBoYWxmIGEgZG9ja2VkIHBhbmVsJ3Mgd2lkdGggYW5kIHNxdWVlemVkXG4gICAgLy8gdGhlIGVtYmVkZGluZyBpbnRvIGEgY29ybmVyIOKAlCBhbmQgdGhlIHNoYXBlcyBvZiB0aGUgY2x1c3RlcnMgYXJlIHRoZSB0aGluZyBiZWluZ1xuICAgIC8vIHJlYWQgaGVyZSwgd2hpbGUgdGhlIGxhYmVscyBhcmUgYSBsb29rdXAuXG4gICAgbWFyZ2luOiB7XG4gICAgICBsOiA0NCxcbiAgICAgIHI6IDgsXG4gICAgICB0OiA4LFxuICAgICAgLy8gUm9vbSBmb3IgdGhlIGxlZ2VuZCBvbmx5IHdoZW4gb25lIGlzIGRyYXduOyBvdGhlcndpc2UgdGhlIGF4aXMgdGl0bGUgYWxvbmUuXG4gICAgICBiOlxuICAgICAgICAoaW5wdXQuY2F0ZWdvcmllcz8ubmFtZXMubGVuZ3RoID8/IDApID4gMCAmJlxuICAgICAgICAoaW5wdXQuY2F0ZWdvcmllcz8ubmFtZXMubGVuZ3RoID8/IDApIDw9IEVNQkVERElOR19NQVhfTEVHRU5EX1NIT1dOXG4gICAgICAgICAgPyA2NFxuICAgICAgICAgIDogNDAsXG4gICAgfSxcbiAgICAvLyBFcXVhbCBhc3BlY3Q6IGFuIGVtYmVkZGluZydzIGF4ZXMgY2Fycnkgbm8gdW5pdHMsIHNvIGRpc3RhbmNlcyBhcmUgb25seSBjb21wYXJhYmxlIGlmIHRoZVxuICAgIC8vIHR3byBhcmUgc2NhbGVkIGFsaWtlLiBTdHJldGNoaW5nIG9uZSBheGlzIHRvIGZpbGwgdGhlIHBhbmVsIGludmVudHMgc3RydWN0dXJlLlxuICAgIHhheGlzOiB7XG4gICAgICB0aXRsZTogeyB0ZXh0OiBheGlzVGl0bGUoc3RlbSwgMSwgdnIpIH0sXG4gICAgICB6ZXJvbGluZTogZmFsc2UsXG4gICAgICB0aWNrczogJ291dHNpZGUnLFxuICAgICAgLi4uKGlucHV0LnZpZXc/LnJhbmdlcyA/IHsgcmFuZ2U6IGlucHV0LnZpZXcucmFuZ2VzLngsIGF1dG9yYW5nZTogZmFsc2UgfSA6IHt9KSxcbiAgICB9LFxuICAgIHlheGlzOiB7XG4gICAgICB0aXRsZTogeyB0ZXh0OiBheGlzVGl0bGUoc3RlbSwgMiwgdnIpIH0sXG4gICAgICB6ZXJvbGluZTogZmFsc2UsXG4gICAgICB0aWNrczogJ291dHNpZGUnLFxuICAgICAgc2NhbGVhbmNob3I6ICd4JyxcbiAgICAgIHNjYWxlcmF0aW86IDEsXG4gICAgICAuLi4oaW5wdXQudmlldz8ucmFuZ2VzID8geyByYW5nZTogaW5wdXQudmlldy5yYW5nZXMueSwgYXV0b3JhbmdlOiBmYWxzZSB9IDoge30pLFxuICAgIH0sXG4gICAgbGVnZW5kOiB7XG4gICAgICBvcmllbnRhdGlvbjogJ2gnLFxuICAgICAgaXRlbXNpemluZzogJ2NvbnN0YW50JyxcbiAgICAgIGZvbnQ6IHsgc2l6ZTogOSB9LFxuICAgICAgeWFuY2hvcjogJ3RvcCcsXG4gICAgICB5OiAtMC4xNixcbiAgICAgIHhhbmNob3I6ICdsZWZ0JyxcbiAgICAgIHg6IDAsXG4gICAgfSxcbiAgICBob3Zlcm1vZGU6ICdjbG9zZXN0JyxcbiAgfTtcbn1cblxuLy8g4pSA4pSAIGhlYXRtYXAg4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSAXG5cbmV4cG9ydCBpbnRlcmZhY2UgT21pY3NIZWF0bWFwSW5wdXQge1xuICByb3dzOiBzdHJpbmdbXTtcbiAgY29sczogc3RyaW5nW107XG4gIC8qKiBgcm93cy5sZW5ndGggw5cgY29scy5sZW5ndGhgLCByb3ctbWFqb3I7IGBOYU5gIHdoZXJlIG5vdGhpbmcgd2FzIG1lYXN1cmVkLiAqL1xuICB2YWx1ZXM6IEZsb2F0MzJBcnJheTtcbiAgLyoqIENlbGxzIGJlaGluZCBlYWNoIGNvbHVtbiwgZm9yIHRoZSBob3Zlci4gKi9cbiAgY291bnRzPzogVWludDMyQXJyYXk7XG4gIC8qKiBUcnVlIHdoZW4gYHZhbHVlc2AgYXJlIHotc2NvcmVzLCB3aGljaCBzZXRzIHRoZSBzY2FsZSBhbmQgdGhlIGxhYmVscy4gKi9cbiAgelNjb3JlZD86IGJvb2xlYW47XG4gIC8qKiBDb2x1bW4gYXhpcyB0aXRsZSDigJQgdGhlIGdyb3VwaW5nIGNvbHVtbidzIG5hbWUsIG9yIFwiY2VsbFwiLiAqL1xuICBncm91cExhYmVsPzogc3RyaW5nO1xufVxuXG4vKiogRGl2ZXJnaW5nLCBjZW50cmVkOiBhZnRlciB6LXNjb3JpbmcsIHRoZSBzaWduIGNhcnJpZXMgdGhlIG1lYW5pbmcuICovXG5jb25zdCBIRUFUTUFQX0RJVkVSR0lORzogW251bWJlciwgc3RyaW5nXVtdID0gW1xuICBbMCwgJyMyMTY2QUMnXSxcbiAgWzAuNSwgJyNGN0Y3RjcnXSxcbiAgWzEsICcjQjIxODJCJ10sXG5dO1xuLyoqIFNlcXVlbnRpYWwsIGZvciByYXcgbWVhbnMgd2hlcmUgemVybyBpcyB0aGUgYm90dG9tIHJhdGhlciB0aGFuIHRoZSBtaWRkbGUuICovXG5jb25zdCBIRUFUTUFQX1NFUVVFTlRJQUw6IFtudW1iZXIsIHN0cmluZ11bXSA9IFtcbiAgWzAsICcjRjdGQkZGJ10sXG4gIFswLjUsICcjNkJBRUQ2J10sXG4gIFsxLCAnIzA4MzA2QiddLFxuXTtcblxuLyoqXG4gKiBHZW5lcyDDlyBncm91cHMgbWVhbiBleHByZXNzaW9uLCBhcyBhIFBsb3RseSBoZWF0bWFwLlxuICpcbiAqIFRoZSBtYXRyaXggaXRzZWxmIGlzIGNvbXB1dGVkIGJ5IHRoZSBwdXJlIGBoZWF0bWFwTWF0cml4YCBpblxuICogYHNwYXRpYWwvc3BhdGlhbC1oZWF0bWFwLnRzYDsgdGhpcyBvbmx5IHNoYXBlcyBpdCBmb3IgUGxvdGx5LiBLZXB0IGluIHRoZVxuICogbWF0cml4J3Mgb3duIHJvdy1tYWpvciBvcmRlciBhbmQgZmxpcHBlZCBvbmNlIGhlcmUsIGJlY2F1c2UgUGxvdGx5IGRyYXdzXG4gKiBgelswXWAgYXQgdGhlIEJPVFRPTSBvZiB0aGUgeSBheGlzIHdoaWxlIHRoZSBjYWxsZXIgbGlzdHMgZ2VuZXMgdG9wLWRvd24uXG4gKlxuICogVGhlIGNvbG91ciBzY2FsZSBpcyBpdHMgb3duLCBOT1QgdGhlIG1hcCdzIGBjb250aW51b3VzQ29sb3JtYXBgLiBUaGlzIGlzIGFcbiAqIGRpZmZlcmVudCBxdWFudGl0eSDigJQgYSB6LXNjb3JlZCBtZWFuIHBlciBncm91cCwgbm90IGEgcGVyLWNlbGwgdmFsdWUg4oCUIHNvXG4gKiBzaGFyaW5nIG9uZSBzY2FsZSB3b3VsZCBpbnZpdGUgcmVhZGluZyBhIGhlYXRtYXAgY2VsbCBhcyBpZiBpdCB3ZXJlIGEgbWFya2VyXG4gKiBjb2xvdXIuIERpdmVyZ2luZyBhbmQgY2VudHJlZCBvbiB6ZXJvLCBiZWNhdXNlIGFmdGVyIHotc2NvcmluZyB0aGUgc2lnbiBpc1xuICogdGhlIHJlYWRpbmc6IGFib3ZlIG9yIGJlbG93IHRoaXMgZ2VuZSdzIGF2ZXJhZ2UgYWNyb3NzIHRoZSBncm91cHMuXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBidWlsZEhlYXRtYXBUcmFjZXMoaW5wdXQ6IE9taWNzSGVhdG1hcElucHV0KTogdW5rbm93bltdIHtcbiAgY29uc3QgeyByb3dzLCBjb2xzLCB2YWx1ZXMsIGNvdW50cyB9ID0gaW5wdXQ7XG4gIGlmIChyb3dzLmxlbmd0aCA9PT0gMCB8fCBjb2xzLmxlbmd0aCA9PT0gMCkgcmV0dXJuIFtdO1xuICAvLyBQbG90bHkgd2FudHMgeiBhcyBhbiBhcnJheSBvZiByb3dzLCBib3R0b20tdXA7IE5hTiByZW5kZXJzIGFzIGEgZ2FwLlxuICBjb25zdCB6OiAobnVtYmVyIHwgbnVsbClbXVtdID0gW107XG4gIGZvciAobGV0IHIgPSByb3dzLmxlbmd0aCAtIDE7IHIgPj0gMDsgci0tKSB7XG4gICAgY29uc3QgbGluZTogKG51bWJlciB8IG51bGwpW10gPSBbXTtcbiAgICBmb3IgKGxldCBjID0gMDsgYyA8IGNvbHMubGVuZ3RoOyBjKyspIHtcbiAgICAgIGNvbnN0IHYgPSB2YWx1ZXNbciAqIGNvbHMubGVuZ3RoICsgY107XG4gICAgICBsaW5lLnB1c2goTnVtYmVyLmlzRmluaXRlKHYpID8gdiA6IG51bGwpO1xuICAgIH1cbiAgICB6LnB1c2gobGluZSk7XG4gIH1cbiAgY29uc3QgeSA9IHJvd3Muc2xpY2UoKS5yZXZlcnNlKCk7XG4gIGNvbnN0IHVuaXQgPSBpbnB1dC56U2NvcmVkID8gJ3onIDogJ21lYW4nO1xuICAvLyBTeW1tZXRyaWMgYWJvdXQgemVybyB3aGVuIHotc2NvcmVkLCBzbyB0aGUgc2FtZSBtYWduaXR1ZGUgcmVhZHMgdGhlIHNhbWVcbiAgLy8gd2hpY2hldmVyIHNpZGUgb2YgdGhlIGdlbmUncyBhdmVyYWdlIGl0IGZhbGxzIG9uLlxuICBsZXQgem1pbjogbnVtYmVyIHwgdW5kZWZpbmVkO1xuICBsZXQgem1heDogbnVtYmVyIHwgdW5kZWZpbmVkO1xuICBpZiAoaW5wdXQuelNjb3JlZCkge1xuICAgIGxldCBwZWFrID0gMDtcbiAgICBmb3IgKGxldCBpID0gMDsgaSA8IHZhbHVlcy5sZW5ndGg7IGkrKykge1xuICAgICAgY29uc3QgdiA9IE1hdGguYWJzKHZhbHVlc1tpXSk7XG4gICAgICBpZiAoTnVtYmVyLmlzRmluaXRlKHYpICYmIHYgPiBwZWFrKSBwZWFrID0gdjtcbiAgICB9XG4gICAgem1heCA9IHBlYWsgPiAwID8gcGVhayA6IDE7XG4gICAgem1pbiA9IC16bWF4O1xuICB9XG4gIGNvbnN0IGhvdmVyID0gY291bnRzID8gY29scy5tYXAoKGxhYmVsLCBjKSA9PiBgJHtsYWJlbH0gwrcgJHtjb3VudHNbY119IGNlbGxzYCkgOiBjb2xzO1xuICByZXR1cm4gW1xuICAgIHtcbiAgICAgIHR5cGU6ICdoZWF0bWFwJyxcbiAgICAgIHosXG4gICAgICB4OiBjb2xzLFxuICAgICAgeSxcbiAgICAgIGN1c3RvbWRhdGE6IHoubWFwKCgpID0+IGhvdmVyKSxcbiAgICAgIGNvbG9yc2NhbGU6IGlucHV0LnpTY29yZWQgPyBIRUFUTUFQX0RJVkVSR0lORyA6IEhFQVRNQVBfU0VRVUVOVElBTCxcbiAgICAgIC4uLih6bWluICE9PSB1bmRlZmluZWQgPyB7IHptaW4sIHptYXggfSA6IHt9KSxcbiAgICAgIC8vIEEgZ2FwIGhhcyBubyBjb2xvdXIgcmF0aGVyIHRoYW4gdGhlIHNjYWxlJ3MgYm90dG9tOiBub3RoaW5nIHdhcyBtZWFzdXJlZFxuICAgICAgLy8gdGhlcmUsIHdoaWNoIGlzIG5vdCB0aGUgc2FtZSBhcyBhIGxvdyBtZWFuLlxuICAgICAgaG92ZXJvbmdhcHM6IGZhbHNlLFxuICAgICAgY29sb3JiYXI6IHsgdGl0bGU6IHsgdGV4dDogdW5pdCwgc2lkZTogJ3JpZ2h0JyB9LCB0aGlja25lc3M6IDEwLCBsZW46IDAuOSB9LFxuICAgICAgaG92ZXJ0ZW1wbGF0ZTogYCV7eX08YnI+JXtjdXN0b21kYXRhfTxicj4ke3VuaXR9ICV7ejouMmZ9PGV4dHJhPjwvZXh0cmE+YCxcbiAgICB9LFxuICBdO1xufVxuXG5leHBvcnQgZnVuY3Rpb24gaGVhdG1hcExheW91dChpbnB1dDogT21pY3NIZWF0bWFwSW5wdXQpOiB1bmtub3duIHtcbiAgcmV0dXJuIHtcbiAgICAvLyBMZWZ0IG1hcmdpbiBncm93cyB3aXRoIHRoZSBsb25nZXN0IGdlbmUgbmFtZTsgdGhlIGxhYmVscyBhcmUgdGhlIHBvaW50LlxuICAgIG1hcmdpbjogeyB0OiAxMCwgcjogMTAsIGI6IDkwLCBsOiA4IH0sXG4gICAgYXV0b3NpemU6IHRydWUsXG4gICAgaG92ZXJtb2RlOiAnY2xvc2VzdCcsXG4gICAgeGF4aXM6IHsgYXV0b21hcmdpbjogdHJ1ZSwgdGlja2FuZ2xlOiAtNDUsIHRpY2tmb250OiB7IHNpemU6IDEwIH0sIHRpdGxlOiB7IHRleHQ6IGlucHV0Lmdyb3VwTGFiZWwgPz8gJycgfSB9LFxuICAgIHlheGlzOiB7IGF1dG9tYXJnaW46IHRydWUsIHRpY2tmb250OiB7IHNpemU6IDEwIH0gfSxcbiAgICAvLyBHcm93cyB3aXRoIHRoZSBnZW5lIGNvdW50IHNvIDMgcm93cyBhcmUgbm90IHN0cmV0Y2hlZCB0byAyMCByb3dzJyBoZWlnaHQuXG4gICAgaGVpZ2h0OiBNYXRoLm1heCgxODAsIDI0ICogaW5wdXQucm93cy5sZW5ndGggKyAxMTApLFxuICB9O1xufVxuIl19