@firestitch/report 18.0.30 → 18.1.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.
- package/app/reports/components/report-canvas/report-canvas.component.d.ts +9 -1
- package/app/reports/data/report.data.d.ts +8 -1
- package/app/reports/dialogs/component-settings/component-settings.component.d.ts +9 -4
- package/app/reports/dialogs/global-settings/components/semantic-database/semantic-database.component.d.ts +2 -0
- package/app/reports/dialogs/report-settings/report-settings.component.d.ts +3 -2
- package/app/reports/interfaces/report.interface.d.ts +8 -0
- package/app/reports/views/report/fs-ai-report.component.d.ts +8 -1
- package/esm2022/app/reports/components/report-canvas/report-canvas.component.mjs +105 -5
- package/esm2022/app/reports/data/report.data.mjs +42 -1
- package/esm2022/app/reports/dialogs/component-settings/component-settings.component.mjs +59 -10
- package/esm2022/app/reports/dialogs/global-settings/components/semantic-database/semantic-database.component.mjs +20 -3
- package/esm2022/app/reports/dialogs/report-settings/report-settings.component.mjs +27 -11
- package/esm2022/app/reports/interfaces/report.interface.mjs +1 -1
- package/esm2022/app/reports/views/report/fs-ai-report.component.mjs +50 -4
- package/esm2022/app/reports/views/report/report.component.mjs +1 -1
- package/fesm2022/{firestitch-report-echarts-CvuyZRgq.mjs → firestitch-report-echarts-DPeQc3Lq.mjs} +2 -2
- package/fesm2022/{firestitch-report-echarts-CvuyZRgq.mjs.map → firestitch-report-echarts-DPeQc3Lq.mjs.map} +1 -1
- package/fesm2022/{firestitch-report-firestitch-report-C00Q9Orr.mjs → firestitch-report-firestitch-report-BSGrWdzK.mjs} +319 -58
- package/fesm2022/firestitch-report-firestitch-report-BSGrWdzK.mjs.map +1 -0
- package/fesm2022/firestitch-report.mjs +1 -1
- package/package.json +1 -1
- package/fesm2022/firestitch-report-firestitch-report-C00Q9Orr.mjs.map +0 -1
|
@@ -1,14 +1,21 @@
|
|
|
1
1
|
import { ChangeDetectionStrategy, ChangeDetectorRef, Component, DestroyRef, ElementRef, EventEmitter, Input, Output, QueryList, ViewChild, ViewChildren, inject, } from '@angular/core';
|
|
2
2
|
import { takeUntilDestroyed } from '@angular/core/rxjs-interop';
|
|
3
|
+
import { DragDropModule, moveItemInArray } from '@angular/cdk/drag-drop';
|
|
3
4
|
import { MatButton } from '@angular/material/button';
|
|
4
5
|
import { MatIcon } from '@angular/material/icon';
|
|
5
6
|
import { MatTooltip } from '@angular/material/tooltip';
|
|
7
|
+
import { FsMenuModule } from '@firestitch/menu';
|
|
8
|
+
import { FsMessage } from '@firestitch/message';
|
|
9
|
+
import { FsPrompt } from '@firestitch/prompt';
|
|
6
10
|
import { FsZoomPanComponent, FsZoomPanModule } from '@firestitch/zoom-pan';
|
|
11
|
+
import { map, switchMap } from 'rxjs';
|
|
7
12
|
import { ReportData } from '../../data/report.data';
|
|
8
13
|
import { DEFAULT_HEADING_SIZE, FLOW_PADDING } from '../../layout';
|
|
9
14
|
import { ReportComponentComponent } from '../report-component/report-component.component';
|
|
10
15
|
import * as i0 from "@angular/core";
|
|
11
|
-
import * as i1 from "@
|
|
16
|
+
import * as i1 from "@angular/cdk/drag-drop";
|
|
17
|
+
import * as i2 from "@firestitch/menu";
|
|
18
|
+
import * as i3 from "@firestitch/zoom-pan";
|
|
12
19
|
// Screen density of the canvas: 96 CSS px per inch (the CSS reference pixel),
|
|
13
20
|
// before zoom. All geometry stays in inches; only rendering multiplies by it.
|
|
14
21
|
export const PX_PER_INCH = 96;
|
|
@@ -24,6 +31,10 @@ export const PX_PER_INCH = 96;
|
|
|
24
31
|
export class ReportCanvasComponent {
|
|
25
32
|
report;
|
|
26
33
|
editMode = false;
|
|
34
|
+
// The page the host wants on screen, by page id (a deep link). Keyed on id
|
|
35
|
+
// rather than index so a link survives pages being reordered or deleted; an
|
|
36
|
+
// id that no longer resolves falls back to the first page.
|
|
37
|
+
pageId = null;
|
|
27
38
|
// A component asked for its settings dialog — the page-level host opens it
|
|
28
39
|
// (it owns MatDialog + the post-save reload).
|
|
29
40
|
componentSettings = new EventEmitter();
|
|
@@ -33,6 +44,9 @@ export class ReportCanvasComponent {
|
|
|
33
44
|
// The viewer dismissed edit mode from the on-canvas badge — the host owns the
|
|
34
45
|
// editMode flag, so it flips it off (mirrors the menu's "Done editing layout").
|
|
35
46
|
editDone = new EventEmitter();
|
|
47
|
+
// The page on screen changed — the host reflects it in the URL so a refresh
|
|
48
|
+
// comes back to the same page. Carries the page id, never the index.
|
|
49
|
+
pageChanged = new EventEmitter();
|
|
36
50
|
zoomPan;
|
|
37
51
|
// The rendered components of the active page — only the canvas can reach the
|
|
38
52
|
// one instance a settings save applies to.
|
|
@@ -52,6 +66,8 @@ export class ReportCanvasComponent {
|
|
|
52
66
|
clear: () => this._clearGuides(),
|
|
53
67
|
};
|
|
54
68
|
_reportData = inject(ReportData);
|
|
69
|
+
_prompt = inject(FsPrompt);
|
|
70
|
+
_message = inject(FsMessage);
|
|
55
71
|
_cdRef = inject(ChangeDetectorRef);
|
|
56
72
|
_destroyRef = inject(DestroyRef);
|
|
57
73
|
_fitted = false;
|
|
@@ -60,10 +76,22 @@ export class ReportCanvasComponent {
|
|
|
60
76
|
this.groups = new Map((this.report?.filterGroups ?? []).map((group) => [group.id, group]));
|
|
61
77
|
const pageCount = this.report?.pages?.length ?? 0;
|
|
62
78
|
// A page was just added (the host re-fetched the report) — land on it.
|
|
63
|
-
|
|
79
|
+
const pageAdded = pageCount > this._previousPageCount && this._previousPageCount > 0;
|
|
80
|
+
if (pageAdded) {
|
|
64
81
|
this.activePageIndex = pageCount - 1;
|
|
65
82
|
}
|
|
66
83
|
this._previousPageCount = pageCount;
|
|
84
|
+
// Honour an incoming deep link, but never over a just-added page: adding a
|
|
85
|
+
// page is a deliberate act in this tab, while pageId is the stale value the
|
|
86
|
+
// host is still holding from the URL. An id that does not resolve is left
|
|
87
|
+
// alone rather than forced to the first page — the report may still be
|
|
88
|
+
// loading, and the clamp below is the real guard.
|
|
89
|
+
if (!pageAdded && this.pageId != null) {
|
|
90
|
+
const index = this.report?.pages?.findIndex((page) => page.id === this.pageId) ?? -1;
|
|
91
|
+
if (index > -1) {
|
|
92
|
+
this.activePageIndex = index;
|
|
93
|
+
}
|
|
94
|
+
}
|
|
67
95
|
if (this.activePageIndex >= pageCount) {
|
|
68
96
|
this.activePageIndex = 0;
|
|
69
97
|
}
|
|
@@ -93,6 +121,7 @@ export class ReportCanvasComponent {
|
|
|
93
121
|
selectPage(index) {
|
|
94
122
|
this.activePageIndex = index;
|
|
95
123
|
this.selectedComponentId = null;
|
|
124
|
+
this.pageChanged.emit(this.activePage?.id ?? null);
|
|
96
125
|
}
|
|
97
126
|
// Append a blank page; the host re-fetches the report and ngOnChanges lands
|
|
98
127
|
// the view on the new (last) page.
|
|
@@ -107,6 +136,71 @@ export class ReportCanvasComponent {
|
|
|
107
136
|
pageLabel(page, index) {
|
|
108
137
|
return page.name || `Page ${index + 1}`;
|
|
109
138
|
}
|
|
139
|
+
// Rename from the tab's kebab. The page list is patched in place rather than
|
|
140
|
+
// re-fetching the report: nothing else on the canvas depends on a page's
|
|
141
|
+
// name, and a re-fetch would re-run every component's query to repaint a
|
|
142
|
+
// chip's label.
|
|
143
|
+
renamePage(page) {
|
|
144
|
+
this._prompt.input({
|
|
145
|
+
title: 'Edit Page Name',
|
|
146
|
+
label: 'Name',
|
|
147
|
+
default: page.name ?? '',
|
|
148
|
+
commitLabel: 'Save',
|
|
149
|
+
required: true,
|
|
150
|
+
})
|
|
151
|
+
.pipe(switchMap((name) => this._reportData
|
|
152
|
+
.updatePage(this.report.id, page.id, name)
|
|
153
|
+
.pipe(map(() => name))), takeUntilDestroyed(this._destroyRef))
|
|
154
|
+
.subscribe((name) => {
|
|
155
|
+
page.name = name;
|
|
156
|
+
this._message.success('Saved page name');
|
|
157
|
+
this._cdRef.markForCheck();
|
|
158
|
+
});
|
|
159
|
+
}
|
|
160
|
+
// Delete from the tab's kebab. The confirm names the page and says the
|
|
161
|
+
// components go with it — the server refuses the last page, and that refusal
|
|
162
|
+
// surfaces as the API error message rather than being second-guessed here.
|
|
163
|
+
deletePage(page) {
|
|
164
|
+
this._prompt.confirm({
|
|
165
|
+
title: 'Confirm',
|
|
166
|
+
template: `Are you sure you would like to delete "${this.pageLabel(page, this.report.pages.indexOf(page))}" and everything on it?`,
|
|
167
|
+
})
|
|
168
|
+
.pipe(switchMap(() => this._reportData.deletePage(this.report.id, page.id)), takeUntilDestroyed(this._destroyRef))
|
|
169
|
+
.subscribe(() => {
|
|
170
|
+
const index = this.report.pages.indexOf(page);
|
|
171
|
+
this.report.pages.splice(index, 1);
|
|
172
|
+
// Land on the neighbour rather than snapping back to the first page —
|
|
173
|
+
// deleting page 4 of 6 should leave you looking at what is now page 4.
|
|
174
|
+
this.activePageIndex = Math.min(index, this.report.pages.length - 1);
|
|
175
|
+
this._previousPageCount = this.report.pages.length;
|
|
176
|
+
this.selectedComponentId = null;
|
|
177
|
+
// The id in the URL just stopped existing — replace it with the
|
|
178
|
+
// neighbour we landed on, or a refresh would 404 its way to page one.
|
|
179
|
+
this.pageChanged.emit(this.activePage?.id ?? null);
|
|
180
|
+
this._message.success('Deleted page');
|
|
181
|
+
this._cdRef.markForCheck();
|
|
182
|
+
});
|
|
183
|
+
}
|
|
184
|
+
// A tab was dragged to a new slot: reorder locally so the chips settle
|
|
185
|
+
// immediately, keep the viewer on the page they were looking at, and persist
|
|
186
|
+
// the whole sequence in one PUT.
|
|
187
|
+
onPageDropped(event) {
|
|
188
|
+
if (event.previousIndex === event.currentIndex) {
|
|
189
|
+
return;
|
|
190
|
+
}
|
|
191
|
+
const activePage = this.activePage;
|
|
192
|
+
moveItemInArray(this.report.pages, event.previousIndex, event.currentIndex);
|
|
193
|
+
const positions = this.report.pages.map((page, order) => {
|
|
194
|
+
page.order = order;
|
|
195
|
+
return { pageId: page.id, order };
|
|
196
|
+
});
|
|
197
|
+
this.activePageIndex = activePage
|
|
198
|
+
? this.report.pages.indexOf(activePage)
|
|
199
|
+
: this.activePageIndex;
|
|
200
|
+
this._reportData.savePagePositions(this.report.id, positions)
|
|
201
|
+
.pipe(takeUntilDestroyed(this._destroyRef))
|
|
202
|
+
.subscribe();
|
|
203
|
+
}
|
|
110
204
|
// Hand presentation settings (title, padding) saved in the settings dialog to
|
|
111
205
|
// the one component they belong to. Nothing here feeds the query, so that
|
|
112
206
|
// component repaints and every other one on the page is left alone.
|
|
@@ -324,27 +418,33 @@ export class ReportCanvasComponent {
|
|
|
324
418
|
this._guides?.nativeElement?.replaceChildren();
|
|
325
419
|
}
|
|
326
420
|
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: ReportCanvasComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
327
|
-
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "18.2.14", type: ReportCanvasComponent, isStandalone: true, selector: "app-report-canvas", inputs: { report: "report", editMode: "editMode" }, outputs: { componentSettings: "componentSettings", reportChanged: "reportChanged", editDone: "editDone" }, viewQueries: [{ propertyName: "zoomPan", first: true, predicate: FsZoomPanComponent, descendants: true }, { propertyName: "_viewport", first: true, predicate: ["viewport"], descendants: true, static: true }, { propertyName: "_guides", first: true, predicate: ["guides"], descendants: true }, { propertyName: "_renderedComponents", predicate: ReportComponentComponent, descendants: true }], usesOnChanges: true, ngImport: i0, template: "<div class=\"canvas\">\n <div\n #viewport\n class=\"page-viewport\"\n (pointerdown)=\"onCanvasPointerDown()\">\n <fs-zoom-pan\n [zoomMin]=\"0.1\"\n [zoomMax]=\"3\"\n (zoomed)=\"onZoomed($event)\">\n @if (activePage; as page) {\n <div\n class=\"page\"\n [class.flow]=\"isFlow\"\n [class.editing]=\"editMode\"\n [style.width.px]=\"report.pageWidth * PX\"\n [style.height.px]=\"report.pageHeight * PX\"\n [style.padding.px]=\"isFlow ? flowPadding * PX : 0\"\n [style.--canvas-zoom]=\"zoom\"\n [style.--report-heading-size.px]=\"headingSizePx\">\n @if (isFlow) {\n @for (component of flowComponents; track component.id) {\n <app-report-component\n class=\"flow-item\"\n [reportId]=\"report.id\"\n [component]=\"component\"\n [groups]=\"groups\"\n [editMode]=\"editMode\"\n [layout]=\"'flow'\"\n [zoom]=\"zoom\"\n [snapper]=\"snapper\"\n [selected]=\"component.id === selectedComponentId\"\n [style.width.%]=\"component.flowWidth\"\n [style.height.px]=\"component.autoHeight ? null : component.h * PX\"\n (selectComponent)=\"selectComponent($event)\"\n (positionChanged)=\"onPositionChanged($event)\"\n (flowReorder)=\"onFlowReorder($event)\"\n (openSettings)=\"componentSettings.emit($event)\">\n </app-report-component>\n }\n } @else {\n @for (component of page.components; track component.id) {\n <app-report-component\n [reportId]=\"report.id\"\n [component]=\"component\"\n [groups]=\"groups\"\n [editMode]=\"editMode\"\n [layout]=\"'freeform'\"\n [zoom]=\"zoom\"\n [snapper]=\"snapper\"\n [selected]=\"component.id === selectedComponentId\"\n [style.left.px]=\"component.x * PX\"\n [style.top.px]=\"component.y * PX\"\n [style.width.px]=\"component.w * PX\"\n [style.height.px]=\"component.autoHeight ? null : component.h * PX\"\n (selectComponent)=\"selectComponent($event)\"\n (positionChanged)=\"onPositionChanged($event)\"\n (openSettings)=\"componentSettings.emit($event)\">\n </app-report-component>\n }\n }\n\n <div\n #guides\n class=\"guides\">\n </div>\n\n @if (!page.components.length) {\n <div class=\"page-empty\">\n Ask the assistant to add a chart, list or KPI to this page.\n </div>\n }\n </div>\n }\n </fs-zoom-pan>\n\n @if (editMode) {\n <button\n mat-flat-button\n type=\"button\"\n color=\"primary\"\n class=\"edit-done\"\n matTooltip=\"Exit layout editing\"\n (click)=\"editDone.emit()\">\n <mat-icon>check</mat-icon>\n Done editing\n </button>\n }\n </div>\n\n <div class=\"canvas-toolbar\">\n <div class=\"page-tabs\">\n @if ((report?.pages?.length ?? 0) > 1) {\n @for (page of report.pages; track page.id; let index = $index) {\n <button\n type=\"button\"\n class=\"page-tab\"\n [class.active]=\"index === activePageIndex\"\n (click)=\"selectPage(index)\">\n {{ pageLabel(page, index) }}\n </button>\n }\n }\n <button\n type=\"button\"\n class=\"page-tab add-page\"\n matTooltip=\"Add page\"\n (click)=\"addPage()\">\n <mat-icon>add</mat-icon>\n Page\n </button>\n </div>\n\n <div class=\"zoom-controls\">\n <button\n type=\"button\"\n class=\"zoom-button\"\n matTooltip=\"Zoom out\"\n (click)=\"zoomOut()\">\n <mat-icon>remove</mat-icon>\n </button>\n <button\n type=\"button\"\n class=\"zoom-label\"\n matTooltip=\"Zoom to 100%\"\n (click)=\"zoomActual()\">\n {{ (zoom * 100).toFixed(0) }}%\n </button>\n <button\n type=\"button\"\n class=\"zoom-button\"\n matTooltip=\"Zoom in\"\n (click)=\"zoomIn()\">\n <mat-icon>add</mat-icon>\n </button>\n <button\n type=\"button\"\n class=\"zoom-button\"\n matTooltip=\"Fit page\"\n (click)=\"zoomFit()\">\n <mat-icon>fit_screen</mat-icon>\n </button>\n </div>\n </div>\n</div>\n", styles: [":host{display:flex;flex-direction:column;min-width:0;min-height:0;flex:1;margin-top:10px}.canvas{display:flex;flex-direction:column;gap:8px;flex:1;min-height:0}.canvas-toolbar{display:flex;align-items:center;justify-content:space-between;gap:8px}.canvas-toolbar .page-tabs{display:flex;gap:4px;flex-wrap:wrap}.canvas-toolbar .page-tabs .page-tab{border:1px solid #e4e7eb;border-radius:16px;background:#fff;padding:4px 14px;font-size:12px;color:#52606d;cursor:pointer}.canvas-toolbar .page-tabs .page-tab.active{background:var(--brand-primary-color, #3b82f6);border-color:var(--brand-primary-color, #3b82f6);color:#fff}.canvas-toolbar .page-tabs .page-tab.add-page{display:inline-flex;align-items:center;gap:2px;padding-left:8px;border-style:dashed;color:#52606d}.canvas-toolbar .page-tabs .page-tab.add-page mat-icon{font-size:16px;width:16px;height:16px}.canvas-toolbar .zoom-controls{display:flex;align-items:center;gap:2px;margin-left:auto;border:1px solid #e4e7eb;border-radius:18px;background:#fff;padding:2px 6px}.canvas-toolbar .zoom-controls .zoom-button{display:flex;align-items:center;justify-content:center;border:none;border-radius:50%;background:transparent;color:#52606d;cursor:pointer}.canvas-toolbar .zoom-controls .zoom-button:hover{background:#f0f4f8}.canvas-toolbar .zoom-controls .zoom-button mat-icon{font-size:18px;width:18px;height:18px}.canvas-toolbar .zoom-controls .zoom-label{border:none;background:transparent;font-size:12px;color:#52606d;min-width:44px;cursor:pointer}.canvas-toolbar .zoom-controls .zoom-label:hover{color:#1f2933}.page-viewport{position:relative;flex:1;min-height:420px;border:1px solid #e4e7eb;border-radius:8px;background:#eef1f5;overflow:hidden}.page-viewport fs-zoom-pan{width:100%;height:100%}.edit-done{position:absolute;top:12px;right:12px;z-index:40;border-radius:999px;box-shadow:0 2px 10px #0f172a2e}.page{position:relative;background:#fff;border-radius:2px;box-shadow:0 2px 12px #0f172a1f,0 0 0 1px #0f172a0a;box-sizing:border-box}.page.flow{display:flex;flex-wrap:wrap;align-content:flex-start;align-items:flex-start}.page.editing{background-image:radial-gradient(circle,#d8dee6 1px,transparent 1px);background-size:24px 24px}.guides{position:absolute;inset:0;pointer-events:none;z-index:30}.guides ::ng-deep .guide{position:absolute;background:#2196f3}.guides ::ng-deep .guide.guide-v{top:0;bottom:0;width:calc(1.25px / var(--canvas-zoom, 1))}.guides ::ng-deep .guide.guide-h{left:0;right:0;height:calc(1.25px / var(--canvas-zoom, 1))}.page-empty{position:absolute;inset:0;display:flex;align-items:center;justify-content:center;color:#9aa5b1;font-size:14px;pointer-events:none}\n"], dependencies: [{ kind: "component", type: MatButton, selector: " button[mat-button], button[mat-raised-button], button[mat-flat-button], button[mat-stroked-button] ", exportAs: ["matButton"] }, { kind: "component", type: MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }, { kind: "directive", type: MatTooltip, selector: "[matTooltip]", inputs: ["matTooltipPosition", "matTooltipPositionAtOrigin", "matTooltipDisabled", "matTooltipShowDelay", "matTooltipHideDelay", "matTooltipTouchGestures", "matTooltip", "matTooltipClass"], exportAs: ["matTooltip"] }, { kind: "ngmodule", type: FsZoomPanModule }, { kind: "component", type: i1.FsZoomPanComponent, selector: "fs-zoom-pan", inputs: ["zoomMax", "zoomMin", "zoomScale", "zoomDefault", "zoomFactor", "top", "left"], outputs: ["moved", "zoomed"] }, { kind: "component", type: ReportComponentComponent, selector: "app-report-component", inputs: ["reportId", "component", "groups", "editMode", "layout", "zoom", "snapper", "selected"], outputs: ["selectComponent", "positionChanged", "flowReorder", "openSettings"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
|
|
421
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "18.2.14", type: ReportCanvasComponent, isStandalone: true, selector: "app-report-canvas", inputs: { report: "report", editMode: "editMode", pageId: "pageId" }, outputs: { componentSettings: "componentSettings", reportChanged: "reportChanged", editDone: "editDone", pageChanged: "pageChanged" }, viewQueries: [{ propertyName: "zoomPan", first: true, predicate: FsZoomPanComponent, descendants: true }, { propertyName: "_viewport", first: true, predicate: ["viewport"], descendants: true, static: true }, { propertyName: "_guides", first: true, predicate: ["guides"], descendants: true }, { propertyName: "_renderedComponents", predicate: ReportComponentComponent, descendants: true }], usesOnChanges: true, ngImport: i0, template: "<div class=\"canvas\">\n <div\n #viewport\n class=\"page-viewport\"\n (pointerdown)=\"onCanvasPointerDown()\">\n <fs-zoom-pan\n [zoomMin]=\"0.1\"\n [zoomMax]=\"3\"\n (zoomed)=\"onZoomed($event)\">\n @if (activePage; as page) {\n <div\n class=\"page\"\n [class.flow]=\"isFlow\"\n [class.editing]=\"editMode\"\n [style.width.px]=\"report.pageWidth * PX\"\n [style.height.px]=\"report.pageHeight * PX\"\n [style.padding.px]=\"isFlow ? flowPadding * PX : 0\"\n [style.--canvas-zoom]=\"zoom\"\n [style.--report-heading-size.px]=\"headingSizePx\">\n @if (isFlow) {\n @for (component of flowComponents; track component.id) {\n <app-report-component\n class=\"flow-item\"\n [reportId]=\"report.id\"\n [component]=\"component\"\n [groups]=\"groups\"\n [editMode]=\"editMode\"\n [layout]=\"'flow'\"\n [zoom]=\"zoom\"\n [snapper]=\"snapper\"\n [selected]=\"component.id === selectedComponentId\"\n [style.width.%]=\"component.flowWidth\"\n [style.height.px]=\"component.autoHeight ? null : component.h * PX\"\n (selectComponent)=\"selectComponent($event)\"\n (positionChanged)=\"onPositionChanged($event)\"\n (flowReorder)=\"onFlowReorder($event)\"\n (openSettings)=\"componentSettings.emit($event)\">\n </app-report-component>\n }\n } @else {\n @for (component of page.components; track component.id) {\n <app-report-component\n [reportId]=\"report.id\"\n [component]=\"component\"\n [groups]=\"groups\"\n [editMode]=\"editMode\"\n [layout]=\"'freeform'\"\n [zoom]=\"zoom\"\n [snapper]=\"snapper\"\n [selected]=\"component.id === selectedComponentId\"\n [style.left.px]=\"component.x * PX\"\n [style.top.px]=\"component.y * PX\"\n [style.width.px]=\"component.w * PX\"\n [style.height.px]=\"component.autoHeight ? null : component.h * PX\"\n (selectComponent)=\"selectComponent($event)\"\n (positionChanged)=\"onPositionChanged($event)\"\n (openSettings)=\"componentSettings.emit($event)\">\n </app-report-component>\n }\n }\n\n <div\n #guides\n class=\"guides\">\n </div>\n\n @if (!page.components.length) {\n <div class=\"page-empty\">\n Ask the assistant to add a chart, list or KPI to this page.\n </div>\n }\n </div>\n }\n </fs-zoom-pan>\n\n @if (editMode) {\n <button\n mat-flat-button\n type=\"button\"\n color=\"primary\"\n class=\"edit-done\"\n matTooltip=\"Exit layout editing\"\n (click)=\"editDone.emit()\">\n <mat-icon>check</mat-icon>\n Done editing\n </button>\n }\n </div>\n\n <div class=\"canvas-toolbar\">\n <!-- Tabs are one horizontal drop list: dragging a chip reorders the pages.\n The drop INDEX is computed along X (orientation), but the preview is\n deliberately left unbounded on both axes \u2014 pinning it to the row with\n cdkDragBoundary means the chip you are dragging covers the chips you\n are dragging it past, and you cannot see where it is going to land. -->\n <div\n class=\"page-tabs\"\n cdkDropList\n cdkDropListOrientation=\"horizontal\"\n (cdkDropListDropped)=\"onPageDropped($event)\">\n @if ((report?.pages?.length ?? 0) > 1) {\n @for (page of report.pages; track page.id; let index = $index) {\n <!-- The chip is the drag handle AND the tab: clicking selects,\n dragging reorders. The kebab lives inside it, so the whole\n control stays one chip instead of growing a second button. -->\n <div\n cdkDrag\n class=\"page-tab\"\n [class.active]=\"index === activePageIndex\"\n (click)=\"selectPage(index)\">\n <span class=\"page-tab-label\">{{ pageLabel(page, index) }}</span>\n <!-- The kebab opens the menu rather than starting a drag or\n switching pages, so it swallows its own click. -->\n <span\n class=\"page-tab-menu\"\n [fsMenuTriggerFor]=\"pageMenu\"\n (click)=\"$event.stopPropagation()\"\n (mousedown)=\"$event.stopPropagation()\">\n <mat-icon>more_vert</mat-icon>\n </span>\n </div>\n <!-- Outside the chip: cdkDrag clones its host into the drag preview,\n and a menu overlay anchored to a cloned trigger opens detached\n from the real tab. -->\n <fs-menu #pageMenu>\n <ng-template\n fs-menu-item\n (click)=\"renamePage(page)\">\n Edit name\n </ng-template>\n <ng-template\n fs-menu-item\n (click)=\"deletePage(page)\">\n Delete\n </ng-template>\n </fs-menu>\n }\n }\n <button\n type=\"button\"\n class=\"page-tab add-page\"\n matTooltip=\"Add page\"\n (click)=\"addPage()\">\n <mat-icon>add</mat-icon>\n Page\n </button>\n </div>\n\n <div class=\"zoom-controls\">\n <button\n type=\"button\"\n class=\"zoom-button\"\n matTooltip=\"Zoom out\"\n (click)=\"zoomOut()\">\n <mat-icon>remove</mat-icon>\n </button>\n <button\n type=\"button\"\n class=\"zoom-label\"\n matTooltip=\"Zoom to 100%\"\n (click)=\"zoomActual()\">\n {{ (zoom * 100).toFixed(0) }}%\n </button>\n <button\n type=\"button\"\n class=\"zoom-button\"\n matTooltip=\"Zoom in\"\n (click)=\"zoomIn()\">\n <mat-icon>add</mat-icon>\n </button>\n <button\n type=\"button\"\n class=\"zoom-button\"\n matTooltip=\"Fit page\"\n (click)=\"zoomFit()\">\n <mat-icon>fit_screen</mat-icon>\n </button>\n </div>\n </div>\n</div>\n", styles: [":host{display:flex;flex-direction:column;min-width:0;min-height:0;flex:1;margin-top:10px}.canvas{display:flex;flex-direction:column;gap:8px;flex:1;min-height:0}.canvas-toolbar{display:flex;align-items:center;justify-content:space-between;gap:8px}.canvas-toolbar .page-tabs{display:flex;align-items:center;gap:4px;flex-wrap:wrap}.canvas-toolbar .page-tabs fs-menu{display:none}.canvas-toolbar .page-tabs .page-tab{display:inline-flex;align-items:center;box-sizing:border-box;border:1px solid #e4e7eb;border-radius:16px;background:#fff;padding:4px 6px 4px 14px;font-size:12px;line-height:16px;color:#52606d;cursor:pointer}.canvas-toolbar .page-tabs .page-tab.active{background:var(--brand-primary-color, #3b82f6);border-color:var(--brand-primary-color, #3b82f6);color:#fff}.canvas-toolbar .page-tabs .page-tab .page-tab-label{white-space:nowrap}.canvas-toolbar .page-tabs .page-tab .page-tab-menu{display:inline-flex;align-items:center;justify-content:center;flex:0 0 auto;width:16px;height:16px;margin-left:2px;border-radius:50%;opacity:.75}.canvas-toolbar .page-tabs .page-tab .page-tab-menu mat-icon{font-size:14px;width:14px;height:14px;line-height:14px}.canvas-toolbar .page-tabs .page-tab .page-tab-menu:hover{background:#0f172a14;opacity:1}.canvas-toolbar .page-tabs .page-tab.active .page-tab-menu:hover{background:#ffffff38}.canvas-toolbar .page-tabs .page-tab.add-page{gap:2px;padding:4px 14px 4px 8px;border-style:dashed;color:#52606d}.canvas-toolbar .page-tabs .page-tab.add-page mat-icon{font-size:16px;width:16px;height:16px}.canvas-toolbar .page-tabs .page-tab.cdk-drag-placeholder{background:transparent;border-style:dashed;border-color:#cbd2d9}.canvas-toolbar .page-tabs .page-tab.cdk-drag-placeholder .page-tab-label,.canvas-toolbar .page-tabs .page-tab.cdk-drag-placeholder .page-tab-menu{visibility:hidden}.canvas-toolbar .page-tabs .cdk-drag-animating,.canvas-toolbar .page-tabs.cdk-drop-list-dragging .page-tab:not(.cdk-drag-placeholder){transition:transform .18s cubic-bezier(0,0,.2,1)}.canvas-toolbar .zoom-controls{display:flex;align-items:center;gap:2px;margin-left:auto;border:1px solid #e4e7eb;border-radius:18px;background:#fff;padding:2px 6px}.canvas-toolbar .zoom-controls .zoom-button{display:flex;align-items:center;justify-content:center;border:none;border-radius:50%;background:transparent;color:#52606d;cursor:pointer}.canvas-toolbar .zoom-controls .zoom-button:hover{background:#f0f4f8}.canvas-toolbar .zoom-controls .zoom-button mat-icon{font-size:18px;width:18px;height:18px}.canvas-toolbar .zoom-controls .zoom-label{border:none;background:transparent;font-size:12px;color:#52606d;min-width:44px;cursor:pointer}.canvas-toolbar .zoom-controls .zoom-label:hover{color:#1f2933}.page-tab.cdk-drag-preview{display:inline-flex;align-items:center;box-sizing:border-box;border:1px solid #e4e7eb;border-radius:16px;background:#fff;padding:4px 6px 4px 14px;font-size:12px;line-height:16px;color:#52606d;box-shadow:0 3px 10px #0f172a3d}.page-tab.cdk-drag-preview.active{background:var(--brand-primary-color, #3b82f6);border-color:var(--brand-primary-color, #3b82f6);color:#fff}.page-tab.cdk-drag-preview .page-tab-label{white-space:nowrap}.page-tab.cdk-drag-preview .page-tab-menu{display:inline-flex;align-items:center;justify-content:center;flex:0 0 auto;width:16px;height:16px;margin-left:2px;border-radius:50%;opacity:.75}.page-tab.cdk-drag-preview .page-tab-menu mat-icon{font-size:14px;width:14px;height:14px;line-height:14px}.page-viewport{position:relative;flex:1;min-height:420px;border:1px solid #e4e7eb;border-radius:8px;background:#eef1f5;overflow:hidden}.page-viewport fs-zoom-pan{width:100%;height:100%}.edit-done{position:absolute;top:12px;right:12px;z-index:40;border-radius:999px;box-shadow:0 2px 10px #0f172a2e}.page{position:relative;background:#fff;border-radius:2px;box-shadow:0 2px 12px #0f172a1f,0 0 0 1px #0f172a0a;box-sizing:border-box}.page.flow{display:flex;flex-wrap:wrap;align-content:flex-start;align-items:flex-start}.page.editing{background-image:radial-gradient(circle,#d8dee6 1px,transparent 1px);background-size:24px 24px}.guides{position:absolute;inset:0;pointer-events:none;z-index:30}.guides ::ng-deep .guide{position:absolute;background:#2196f3}.guides ::ng-deep .guide.guide-v{top:0;bottom:0;width:calc(1.25px / var(--canvas-zoom, 1))}.guides ::ng-deep .guide.guide-h{left:0;right:0;height:calc(1.25px / var(--canvas-zoom, 1))}.page-empty{position:absolute;inset:0;display:flex;align-items:center;justify-content:center;color:#9aa5b1;font-size:14px;pointer-events:none}\n"], dependencies: [{ kind: "ngmodule", type: DragDropModule }, { kind: "directive", type: i1.CdkDropList, selector: "[cdkDropList], cdk-drop-list", inputs: ["cdkDropListConnectedTo", "cdkDropListData", "cdkDropListOrientation", "id", "cdkDropListLockAxis", "cdkDropListDisabled", "cdkDropListSortingDisabled", "cdkDropListEnterPredicate", "cdkDropListSortPredicate", "cdkDropListAutoScrollDisabled", "cdkDropListAutoScrollStep", "cdkDropListElementContainer"], outputs: ["cdkDropListDropped", "cdkDropListEntered", "cdkDropListExited", "cdkDropListSorted"], exportAs: ["cdkDropList"] }, { kind: "directive", type: i1.CdkDrag, selector: "[cdkDrag]", inputs: ["cdkDragData", "cdkDragLockAxis", "cdkDragRootElement", "cdkDragBoundary", "cdkDragStartDelay", "cdkDragFreeDragPosition", "cdkDragDisabled", "cdkDragConstrainPosition", "cdkDragPreviewClass", "cdkDragPreviewContainer", "cdkDragScale"], outputs: ["cdkDragStarted", "cdkDragReleased", "cdkDragEnded", "cdkDragEntered", "cdkDragExited", "cdkDragDropped", "cdkDragMoved"], exportAs: ["cdkDrag"] }, { kind: "component", type: MatButton, selector: " button[mat-button], button[mat-raised-button], button[mat-flat-button], button[mat-stroked-button] ", exportAs: ["matButton"] }, { kind: "component", type: MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }, { kind: "directive", type: MatTooltip, selector: "[matTooltip]", inputs: ["matTooltipPosition", "matTooltipPositionAtOrigin", "matTooltipDisabled", "matTooltipShowDelay", "matTooltipHideDelay", "matTooltipTouchGestures", "matTooltip", "matTooltipClass"], exportAs: ["matTooltip"] }, { kind: "ngmodule", type: FsMenuModule }, { kind: "component", type: i2.FsMenuComponent, selector: "fs-menu", inputs: ["class", "buttonClass", "buttonType", "buttonColor"], outputs: ["opened", "closed"] }, { kind: "directive", type: i2.FsMenuItemDirective, selector: "fs-menu-group,[fs-menu-item]" }, { kind: "directive", type: i2.FsMenuTriggerDirective, selector: "[fsMenuTriggerFor]", inputs: ["fsMenuTriggerFor"] }, { kind: "ngmodule", type: FsZoomPanModule }, { kind: "component", type: i3.FsZoomPanComponent, selector: "fs-zoom-pan", inputs: ["zoomMax", "zoomMin", "zoomScale", "zoomDefault", "zoomFactor", "top", "left"], outputs: ["moved", "zoomed"] }, { kind: "component", type: ReportComponentComponent, selector: "app-report-component", inputs: ["reportId", "component", "groups", "editMode", "layout", "zoom", "snapper", "selected"], outputs: ["selectComponent", "positionChanged", "flowReorder", "openSettings"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
|
|
328
422
|
}
|
|
329
423
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: ReportCanvasComponent, decorators: [{
|
|
330
424
|
type: Component,
|
|
331
425
|
args: [{ selector: 'app-report-canvas', changeDetection: ChangeDetectionStrategy.OnPush, standalone: true, imports: [
|
|
426
|
+
DragDropModule,
|
|
332
427
|
MatButton,
|
|
333
428
|
MatIcon,
|
|
334
429
|
MatTooltip,
|
|
430
|
+
FsMenuModule,
|
|
335
431
|
FsZoomPanModule,
|
|
336
432
|
ReportComponentComponent,
|
|
337
|
-
], template: "<div class=\"canvas\">\n <div\n #viewport\n class=\"page-viewport\"\n (pointerdown)=\"onCanvasPointerDown()\">\n <fs-zoom-pan\n [zoomMin]=\"0.1\"\n [zoomMax]=\"3\"\n (zoomed)=\"onZoomed($event)\">\n @if (activePage; as page) {\n <div\n class=\"page\"\n [class.flow]=\"isFlow\"\n [class.editing]=\"editMode\"\n [style.width.px]=\"report.pageWidth * PX\"\n [style.height.px]=\"report.pageHeight * PX\"\n [style.padding.px]=\"isFlow ? flowPadding * PX : 0\"\n [style.--canvas-zoom]=\"zoom\"\n [style.--report-heading-size.px]=\"headingSizePx\">\n @if (isFlow) {\n @for (component of flowComponents; track component.id) {\n <app-report-component\n class=\"flow-item\"\n [reportId]=\"report.id\"\n [component]=\"component\"\n [groups]=\"groups\"\n [editMode]=\"editMode\"\n [layout]=\"'flow'\"\n [zoom]=\"zoom\"\n [snapper]=\"snapper\"\n [selected]=\"component.id === selectedComponentId\"\n [style.width.%]=\"component.flowWidth\"\n [style.height.px]=\"component.autoHeight ? null : component.h * PX\"\n (selectComponent)=\"selectComponent($event)\"\n (positionChanged)=\"onPositionChanged($event)\"\n (flowReorder)=\"onFlowReorder($event)\"\n (openSettings)=\"componentSettings.emit($event)\">\n </app-report-component>\n }\n } @else {\n @for (component of page.components; track component.id) {\n <app-report-component\n [reportId]=\"report.id\"\n [component]=\"component\"\n [groups]=\"groups\"\n [editMode]=\"editMode\"\n [layout]=\"'freeform'\"\n [zoom]=\"zoom\"\n [snapper]=\"snapper\"\n [selected]=\"component.id === selectedComponentId\"\n [style.left.px]=\"component.x * PX\"\n [style.top.px]=\"component.y * PX\"\n [style.width.px]=\"component.w * PX\"\n [style.height.px]=\"component.autoHeight ? null : component.h * PX\"\n (selectComponent)=\"selectComponent($event)\"\n (positionChanged)=\"onPositionChanged($event)\"\n (openSettings)=\"componentSettings.emit($event)\">\n </app-report-component>\n }\n }\n\n <div\n #guides\n class=\"guides\">\n </div>\n\n @if (!page.components.length) {\n <div class=\"page-empty\">\n Ask the assistant to add a chart, list or KPI to this page.\n </div>\n }\n </div>\n }\n </fs-zoom-pan>\n\n @if (editMode) {\n <button\n mat-flat-button\n type=\"button\"\n color=\"primary\"\n class=\"edit-done\"\n matTooltip=\"Exit layout editing\"\n (click)=\"editDone.emit()\">\n <mat-icon>check</mat-icon>\n Done editing\n </button>\n }\n </div>\n\n <div class=\"canvas-toolbar\">\n <div class=\"page-tabs\">\n @if ((report?.pages?.length ?? 0) > 1) {\n @for (page of report.pages; track page.id; let index = $index) {\n <button\n type=\"button\"\n class=\"page-tab\"\n [class.active]=\"index === activePageIndex\"\n (click)=\"selectPage(index)\">\n {{ pageLabel(page, index) }}\n </button>\n }\n }\n <button\n type=\"button\"\n class=\"page-tab add-page\"\n matTooltip=\"Add page\"\n (click)=\"addPage()\">\n <mat-icon>add</mat-icon>\n Page\n </button>\n </div>\n\n <div class=\"zoom-controls\">\n <button\n type=\"button\"\n class=\"zoom-button\"\n matTooltip=\"Zoom out\"\n (click)=\"zoomOut()\">\n <mat-icon>remove</mat-icon>\n </button>\n <button\n type=\"button\"\n class=\"zoom-label\"\n matTooltip=\"Zoom to 100%\"\n (click)=\"zoomActual()\">\n {{ (zoom * 100).toFixed(0) }}%\n </button>\n <button\n type=\"button\"\n class=\"zoom-button\"\n matTooltip=\"Zoom in\"\n (click)=\"zoomIn()\">\n <mat-icon>add</mat-icon>\n </button>\n <button\n type=\"button\"\n class=\"zoom-button\"\n matTooltip=\"Fit page\"\n (click)=\"zoomFit()\">\n <mat-icon>fit_screen</mat-icon>\n </button>\n </div>\n </div>\n</div>\n", styles: [":host{display:flex;flex-direction:column;min-width:0;min-height:0;flex:1;margin-top:10px}.canvas{display:flex;flex-direction:column;gap:8px;flex:1;min-height:0}.canvas-toolbar{display:flex;align-items:center;justify-content:space-between;gap:8px}.canvas-toolbar .page-tabs{display:flex;gap:4px;flex-wrap:wrap}.canvas-toolbar .page-tabs .page-tab{border:1px solid #e4e7eb;border-radius:16px;background:#fff;padding:4px 14px;font-size:12px;color:#52606d;cursor:pointer}.canvas-toolbar .page-tabs .page-tab.active{background:var(--brand-primary-color, #3b82f6);border-color:var(--brand-primary-color, #3b82f6);color:#fff}.canvas-toolbar .page-tabs .page-tab.add-page{display:inline-flex;align-items:center;gap:2px;padding-left:8px;border-style:dashed;color:#52606d}.canvas-toolbar .page-tabs .page-tab.add-page mat-icon{font-size:16px;width:16px;height:16px}.canvas-toolbar .zoom-controls{display:flex;align-items:center;gap:2px;margin-left:auto;border:1px solid #e4e7eb;border-radius:18px;background:#fff;padding:2px 6px}.canvas-toolbar .zoom-controls .zoom-button{display:flex;align-items:center;justify-content:center;border:none;border-radius:50%;background:transparent;color:#52606d;cursor:pointer}.canvas-toolbar .zoom-controls .zoom-button:hover{background:#f0f4f8}.canvas-toolbar .zoom-controls .zoom-button mat-icon{font-size:18px;width:18px;height:18px}.canvas-toolbar .zoom-controls .zoom-label{border:none;background:transparent;font-size:12px;color:#52606d;min-width:44px;cursor:pointer}.canvas-toolbar .zoom-controls .zoom-label:hover{color:#1f2933}.page-viewport{position:relative;flex:1;min-height:420px;border:1px solid #e4e7eb;border-radius:8px;background:#eef1f5;overflow:hidden}.page-viewport fs-zoom-pan{width:100%;height:100%}.edit-done{position:absolute;top:12px;right:12px;z-index:40;border-radius:999px;box-shadow:0 2px 10px #0f172a2e}.page{position:relative;background:#fff;border-radius:2px;box-shadow:0 2px 12px #0f172a1f,0 0 0 1px #0f172a0a;box-sizing:border-box}.page.flow{display:flex;flex-wrap:wrap;align-content:flex-start;align-items:flex-start}.page.editing{background-image:radial-gradient(circle,#d8dee6 1px,transparent 1px);background-size:24px 24px}.guides{position:absolute;inset:0;pointer-events:none;z-index:30}.guides ::ng-deep .guide{position:absolute;background:#2196f3}.guides ::ng-deep .guide.guide-v{top:0;bottom:0;width:calc(1.25px / var(--canvas-zoom, 1))}.guides ::ng-deep .guide.guide-h{left:0;right:0;height:calc(1.25px / var(--canvas-zoom, 1))}.page-empty{position:absolute;inset:0;display:flex;align-items:center;justify-content:center;color:#9aa5b1;font-size:14px;pointer-events:none}\n"] }]
|
|
433
|
+
], template: "<div class=\"canvas\">\n <div\n #viewport\n class=\"page-viewport\"\n (pointerdown)=\"onCanvasPointerDown()\">\n <fs-zoom-pan\n [zoomMin]=\"0.1\"\n [zoomMax]=\"3\"\n (zoomed)=\"onZoomed($event)\">\n @if (activePage; as page) {\n <div\n class=\"page\"\n [class.flow]=\"isFlow\"\n [class.editing]=\"editMode\"\n [style.width.px]=\"report.pageWidth * PX\"\n [style.height.px]=\"report.pageHeight * PX\"\n [style.padding.px]=\"isFlow ? flowPadding * PX : 0\"\n [style.--canvas-zoom]=\"zoom\"\n [style.--report-heading-size.px]=\"headingSizePx\">\n @if (isFlow) {\n @for (component of flowComponents; track component.id) {\n <app-report-component\n class=\"flow-item\"\n [reportId]=\"report.id\"\n [component]=\"component\"\n [groups]=\"groups\"\n [editMode]=\"editMode\"\n [layout]=\"'flow'\"\n [zoom]=\"zoom\"\n [snapper]=\"snapper\"\n [selected]=\"component.id === selectedComponentId\"\n [style.width.%]=\"component.flowWidth\"\n [style.height.px]=\"component.autoHeight ? null : component.h * PX\"\n (selectComponent)=\"selectComponent($event)\"\n (positionChanged)=\"onPositionChanged($event)\"\n (flowReorder)=\"onFlowReorder($event)\"\n (openSettings)=\"componentSettings.emit($event)\">\n </app-report-component>\n }\n } @else {\n @for (component of page.components; track component.id) {\n <app-report-component\n [reportId]=\"report.id\"\n [component]=\"component\"\n [groups]=\"groups\"\n [editMode]=\"editMode\"\n [layout]=\"'freeform'\"\n [zoom]=\"zoom\"\n [snapper]=\"snapper\"\n [selected]=\"component.id === selectedComponentId\"\n [style.left.px]=\"component.x * PX\"\n [style.top.px]=\"component.y * PX\"\n [style.width.px]=\"component.w * PX\"\n [style.height.px]=\"component.autoHeight ? null : component.h * PX\"\n (selectComponent)=\"selectComponent($event)\"\n (positionChanged)=\"onPositionChanged($event)\"\n (openSettings)=\"componentSettings.emit($event)\">\n </app-report-component>\n }\n }\n\n <div\n #guides\n class=\"guides\">\n </div>\n\n @if (!page.components.length) {\n <div class=\"page-empty\">\n Ask the assistant to add a chart, list or KPI to this page.\n </div>\n }\n </div>\n }\n </fs-zoom-pan>\n\n @if (editMode) {\n <button\n mat-flat-button\n type=\"button\"\n color=\"primary\"\n class=\"edit-done\"\n matTooltip=\"Exit layout editing\"\n (click)=\"editDone.emit()\">\n <mat-icon>check</mat-icon>\n Done editing\n </button>\n }\n </div>\n\n <div class=\"canvas-toolbar\">\n <!-- Tabs are one horizontal drop list: dragging a chip reorders the pages.\n The drop INDEX is computed along X (orientation), but the preview is\n deliberately left unbounded on both axes \u2014 pinning it to the row with\n cdkDragBoundary means the chip you are dragging covers the chips you\n are dragging it past, and you cannot see where it is going to land. -->\n <div\n class=\"page-tabs\"\n cdkDropList\n cdkDropListOrientation=\"horizontal\"\n (cdkDropListDropped)=\"onPageDropped($event)\">\n @if ((report?.pages?.length ?? 0) > 1) {\n @for (page of report.pages; track page.id; let index = $index) {\n <!-- The chip is the drag handle AND the tab: clicking selects,\n dragging reorders. The kebab lives inside it, so the whole\n control stays one chip instead of growing a second button. -->\n <div\n cdkDrag\n class=\"page-tab\"\n [class.active]=\"index === activePageIndex\"\n (click)=\"selectPage(index)\">\n <span class=\"page-tab-label\">{{ pageLabel(page, index) }}</span>\n <!-- The kebab opens the menu rather than starting a drag or\n switching pages, so it swallows its own click. -->\n <span\n class=\"page-tab-menu\"\n [fsMenuTriggerFor]=\"pageMenu\"\n (click)=\"$event.stopPropagation()\"\n (mousedown)=\"$event.stopPropagation()\">\n <mat-icon>more_vert</mat-icon>\n </span>\n </div>\n <!-- Outside the chip: cdkDrag clones its host into the drag preview,\n and a menu overlay anchored to a cloned trigger opens detached\n from the real tab. -->\n <fs-menu #pageMenu>\n <ng-template\n fs-menu-item\n (click)=\"renamePage(page)\">\n Edit name\n </ng-template>\n <ng-template\n fs-menu-item\n (click)=\"deletePage(page)\">\n Delete\n </ng-template>\n </fs-menu>\n }\n }\n <button\n type=\"button\"\n class=\"page-tab add-page\"\n matTooltip=\"Add page\"\n (click)=\"addPage()\">\n <mat-icon>add</mat-icon>\n Page\n </button>\n </div>\n\n <div class=\"zoom-controls\">\n <button\n type=\"button\"\n class=\"zoom-button\"\n matTooltip=\"Zoom out\"\n (click)=\"zoomOut()\">\n <mat-icon>remove</mat-icon>\n </button>\n <button\n type=\"button\"\n class=\"zoom-label\"\n matTooltip=\"Zoom to 100%\"\n (click)=\"zoomActual()\">\n {{ (zoom * 100).toFixed(0) }}%\n </button>\n <button\n type=\"button\"\n class=\"zoom-button\"\n matTooltip=\"Zoom in\"\n (click)=\"zoomIn()\">\n <mat-icon>add</mat-icon>\n </button>\n <button\n type=\"button\"\n class=\"zoom-button\"\n matTooltip=\"Fit page\"\n (click)=\"zoomFit()\">\n <mat-icon>fit_screen</mat-icon>\n </button>\n </div>\n </div>\n</div>\n", styles: [":host{display:flex;flex-direction:column;min-width:0;min-height:0;flex:1;margin-top:10px}.canvas{display:flex;flex-direction:column;gap:8px;flex:1;min-height:0}.canvas-toolbar{display:flex;align-items:center;justify-content:space-between;gap:8px}.canvas-toolbar .page-tabs{display:flex;align-items:center;gap:4px;flex-wrap:wrap}.canvas-toolbar .page-tabs fs-menu{display:none}.canvas-toolbar .page-tabs .page-tab{display:inline-flex;align-items:center;box-sizing:border-box;border:1px solid #e4e7eb;border-radius:16px;background:#fff;padding:4px 6px 4px 14px;font-size:12px;line-height:16px;color:#52606d;cursor:pointer}.canvas-toolbar .page-tabs .page-tab.active{background:var(--brand-primary-color, #3b82f6);border-color:var(--brand-primary-color, #3b82f6);color:#fff}.canvas-toolbar .page-tabs .page-tab .page-tab-label{white-space:nowrap}.canvas-toolbar .page-tabs .page-tab .page-tab-menu{display:inline-flex;align-items:center;justify-content:center;flex:0 0 auto;width:16px;height:16px;margin-left:2px;border-radius:50%;opacity:.75}.canvas-toolbar .page-tabs .page-tab .page-tab-menu mat-icon{font-size:14px;width:14px;height:14px;line-height:14px}.canvas-toolbar .page-tabs .page-tab .page-tab-menu:hover{background:#0f172a14;opacity:1}.canvas-toolbar .page-tabs .page-tab.active .page-tab-menu:hover{background:#ffffff38}.canvas-toolbar .page-tabs .page-tab.add-page{gap:2px;padding:4px 14px 4px 8px;border-style:dashed;color:#52606d}.canvas-toolbar .page-tabs .page-tab.add-page mat-icon{font-size:16px;width:16px;height:16px}.canvas-toolbar .page-tabs .page-tab.cdk-drag-placeholder{background:transparent;border-style:dashed;border-color:#cbd2d9}.canvas-toolbar .page-tabs .page-tab.cdk-drag-placeholder .page-tab-label,.canvas-toolbar .page-tabs .page-tab.cdk-drag-placeholder .page-tab-menu{visibility:hidden}.canvas-toolbar .page-tabs .cdk-drag-animating,.canvas-toolbar .page-tabs.cdk-drop-list-dragging .page-tab:not(.cdk-drag-placeholder){transition:transform .18s cubic-bezier(0,0,.2,1)}.canvas-toolbar .zoom-controls{display:flex;align-items:center;gap:2px;margin-left:auto;border:1px solid #e4e7eb;border-radius:18px;background:#fff;padding:2px 6px}.canvas-toolbar .zoom-controls .zoom-button{display:flex;align-items:center;justify-content:center;border:none;border-radius:50%;background:transparent;color:#52606d;cursor:pointer}.canvas-toolbar .zoom-controls .zoom-button:hover{background:#f0f4f8}.canvas-toolbar .zoom-controls .zoom-button mat-icon{font-size:18px;width:18px;height:18px}.canvas-toolbar .zoom-controls .zoom-label{border:none;background:transparent;font-size:12px;color:#52606d;min-width:44px;cursor:pointer}.canvas-toolbar .zoom-controls .zoom-label:hover{color:#1f2933}.page-tab.cdk-drag-preview{display:inline-flex;align-items:center;box-sizing:border-box;border:1px solid #e4e7eb;border-radius:16px;background:#fff;padding:4px 6px 4px 14px;font-size:12px;line-height:16px;color:#52606d;box-shadow:0 3px 10px #0f172a3d}.page-tab.cdk-drag-preview.active{background:var(--brand-primary-color, #3b82f6);border-color:var(--brand-primary-color, #3b82f6);color:#fff}.page-tab.cdk-drag-preview .page-tab-label{white-space:nowrap}.page-tab.cdk-drag-preview .page-tab-menu{display:inline-flex;align-items:center;justify-content:center;flex:0 0 auto;width:16px;height:16px;margin-left:2px;border-radius:50%;opacity:.75}.page-tab.cdk-drag-preview .page-tab-menu mat-icon{font-size:14px;width:14px;height:14px;line-height:14px}.page-viewport{position:relative;flex:1;min-height:420px;border:1px solid #e4e7eb;border-radius:8px;background:#eef1f5;overflow:hidden}.page-viewport fs-zoom-pan{width:100%;height:100%}.edit-done{position:absolute;top:12px;right:12px;z-index:40;border-radius:999px;box-shadow:0 2px 10px #0f172a2e}.page{position:relative;background:#fff;border-radius:2px;box-shadow:0 2px 12px #0f172a1f,0 0 0 1px #0f172a0a;box-sizing:border-box}.page.flow{display:flex;flex-wrap:wrap;align-content:flex-start;align-items:flex-start}.page.editing{background-image:radial-gradient(circle,#d8dee6 1px,transparent 1px);background-size:24px 24px}.guides{position:absolute;inset:0;pointer-events:none;z-index:30}.guides ::ng-deep .guide{position:absolute;background:#2196f3}.guides ::ng-deep .guide.guide-v{top:0;bottom:0;width:calc(1.25px / var(--canvas-zoom, 1))}.guides ::ng-deep .guide.guide-h{left:0;right:0;height:calc(1.25px / var(--canvas-zoom, 1))}.page-empty{position:absolute;inset:0;display:flex;align-items:center;justify-content:center;color:#9aa5b1;font-size:14px;pointer-events:none}\n"] }]
|
|
338
434
|
}], propDecorators: { report: [{
|
|
339
435
|
type: Input
|
|
340
436
|
}], editMode: [{
|
|
341
437
|
type: Input
|
|
438
|
+
}], pageId: [{
|
|
439
|
+
type: Input
|
|
342
440
|
}], componentSettings: [{
|
|
343
441
|
type: Output
|
|
344
442
|
}], reportChanged: [{
|
|
345
443
|
type: Output
|
|
346
444
|
}], editDone: [{
|
|
347
445
|
type: Output
|
|
446
|
+
}], pageChanged: [{
|
|
447
|
+
type: Output
|
|
348
448
|
}], zoomPan: [{
|
|
349
449
|
type: ViewChild,
|
|
350
450
|
args: [FsZoomPanComponent]
|
|
@@ -358,4 +458,4 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImpo
|
|
|
358
458
|
type: ViewChild,
|
|
359
459
|
args: ['guides', { static: false }]
|
|
360
460
|
}] } });
|
|
361
|
-
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoicmVwb3J0LWNhbnZhcy5jb21wb25lbnQuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi8uLi8uLi9zcmMvYXBwL3JlcG9ydHMvY29tcG9uZW50cy9yZXBvcnQtY2FudmFzL3JlcG9ydC1jYW52YXMuY29tcG9uZW50LnRzIiwiLi4vLi4vLi4vLi4vLi4vLi4vc3JjL2FwcC9yZXBvcnRzL2NvbXBvbmVudHMvcmVwb3J0LWNhbnZhcy9yZXBvcnQtY2FudmFzLmNvbXBvbmVudC5odG1sIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBLE9BQU8sRUFDVSx1QkFBdUIsRUFBRSxpQkFBaUIsRUFBRSxTQUFTLEVBQUUsVUFBVSxFQUNoRixVQUFVLEVBQUUsWUFBWSxFQUFFLEtBQUssRUFBYSxNQUFNLEVBQUUsU0FBUyxFQUFFLFNBQVMsRUFBRSxZQUFZLEVBQUUsTUFBTSxHQUMvRixNQUFNLGVBQWUsQ0FBQztBQUN2QixPQUFPLEVBQUUsa0JBQWtCLEVBQUUsTUFBTSw0QkFBNEIsQ0FBQztBQUVoRSxPQUFPLEVBQUUsU0FBUyxFQUFFLE1BQU0sMEJBQTBCLENBQUM7QUFDckQsT0FBTyxFQUFFLE9BQU8sRUFBRSxNQUFNLHdCQUF3QixDQUFDO0FBQ2pELE9BQU8sRUFBRSxVQUFVLEVBQUUsTUFBTSwyQkFBMkIsQ0FBQztBQUV2RCxPQUFPLEVBQUUsa0JBQWtCLEVBQUUsZUFBZSxFQUFFLE1BQU0sc0JBQXNCLENBQUM7QUFFM0UsT0FBTyxFQUFFLFVBQVUsRUFBRSxNQUFNLHdCQUF3QixDQUFDO0FBSXBELE9BQU8sRUFBRSxvQkFBb0IsRUFBRSxZQUFZLEVBQUUsTUFBTSxjQUFjLENBQUM7QUFDbEUsT0FBTyxFQUFFLHdCQUF3QixFQUFFLE1BQU0sZ0RBQWdELENBQUM7OztBQUcxRiw4RUFBOEU7QUFDOUUsOEVBQThFO0FBQzlFLE1BQU0sQ0FBQyxNQUFNLFdBQVcsR0FBRyxFQUFFLENBQUM7QUFpQjlCLDhFQUE4RTtBQUM5RSxtRUFBbUU7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OzRGQUFyQixxQkFBcUIscVJBaUJyQixrQkFBa0IsbVFBS2Ysd0JBQXdCLHFFQ3BGeEMsb3BKQWdKQSx5b0ZEekZJLFNBQVMsaUxBQ1QsT0FBTywySUFDUCxVQUFVLGdSQUNWLGVBQWUsbU9BQ2Ysd0JBQXdCOzs0RkFHZixxQkFBcUI7a0JBZGpDLFNBQVM7K0JBQ0UsbUJBQW1CLG1CQUdaLHVCQUF1QixDQUFDLE1BQU0sY0FDbkMsSUFBSSxXQUNQO3dCQUNQLFNBQVM7d0JBQ1QsT0FBTzt3QkFDUCxVQUFVO3dCQUNWLGVBQWU7d0JBQ2Ysd0JBQXdCO3FCQUN6Qjs4QkFJZSxNQUFNO3NCQUFyQixLQUFLO2dCQUNVLFFBQVE7c0JBQXZCLEtBQUs7Z0JBSVcsaUJBQWlCO3NCQUFqQyxNQUFNO2dCQUlVLGFBQWE7c0JBQTdCLE1BQU07Z0JBSVUsUUFBUTtzQkFBeEIsTUFBTTtnQkFHQSxPQUFPO3NCQURiLFNBQVM7dUJBQUMsa0JBQWtCO2dCQU1yQixtQkFBbUI7c0JBRDFCLFlBQVk7dUJBQUMsd0JBQXdCO2dCQUk5QixTQUFTO3NCQURoQixTQUFTO3VCQUFDLFVBQVUsRUFBRSxFQUFFLE1BQU0sRUFBRSxJQUFJLEVBQUU7Z0JBSS9CLE9BQU87c0JBRGQsU0FBUzt1QkFBQyxRQUFRLEVBQUUsRUFBRSxNQUFNLEVBQUUsS0FBSyxFQUFFIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHtcbiAgQWZ0ZXJWaWV3SW5pdCwgQ2hhbmdlRGV0ZWN0aW9uU3RyYXRlZ3ksIENoYW5nZURldGVjdG9yUmVmLCBDb21wb25lbnQsIERlc3Ryb3lSZWYsXG4gIEVsZW1lbnRSZWYsIEV2ZW50RW1pdHRlciwgSW5wdXQsIE9uQ2hhbmdlcywgT3V0cHV0LCBRdWVyeUxpc3QsIFZpZXdDaGlsZCwgVmlld0NoaWxkcmVuLCBpbmplY3QsXG59IGZyb20gJ0Bhbmd1bGFyL2NvcmUnO1xuaW1wb3J0IHsgdGFrZVVudGlsRGVzdHJveWVkIH0gZnJvbSAnQGFuZ3VsYXIvY29yZS9yeGpzLWludGVyb3AnO1xuXG5pbXBvcnQgeyBNYXRCdXR0b24gfSBmcm9tICdAYW5ndWxhci9tYXRlcmlhbC9idXR0b24nO1xuaW1wb3J0IHsgTWF0SWNvbiB9IGZyb20gJ0Bhbmd1bGFyL21hdGVyaWFsL2ljb24nO1xuaW1wb3J0IHsgTWF0VG9vbHRpcCB9IGZyb20gJ0Bhbmd1bGFyL21hdGVyaWFsL3Rvb2x0aXAnO1xuXG5pbXBvcnQgeyBGc1pvb21QYW5Db21wb25lbnQsIEZzWm9vbVBhbk1vZHVsZSB9IGZyb20gJ0BmaXJlc3RpdGNoL3pvb20tcGFuJztcblxuaW1wb3J0IHsgUmVwb3J0RGF0YSB9IGZyb20gJy4uLy4uL2RhdGEvcmVwb3J0LmRhdGEnO1xuaW1wb3J0IHtcbiAgQ29tcG9uZW50U2V0dGluZ3MsIFJlcG9ydCwgUmVwb3J0Q29tcG9uZW50LCBSZXBvcnRGaWx0ZXJHcm91cCwgUmVwb3J0UGFnZSxcbn0gZnJvbSAnLi4vLi4vaW50ZXJmYWNlcy9yZXBvcnQuaW50ZXJmYWNlJztcbmltcG9ydCB7IERFRkFVTFRfSEVBRElOR19TSVpFLCBGTE9XX1BBRERJTkcgfSBmcm9tICcuLi8uLi9sYXlvdXQnO1xuaW1wb3J0IHsgUmVwb3J0Q29tcG9uZW50Q29tcG9uZW50IH0gZnJvbSAnLi4vcmVwb3J0LWNvbXBvbmVudC9yZXBvcnQtY29tcG9uZW50LmNvbXBvbmVudCc7XG5cblxuLy8gU2NyZWVuIGRlbnNpdHkgb2YgdGhlIGNhbnZhczogOTYgQ1NTIHB4IHBlciBpbmNoICh0aGUgQ1NTIHJlZmVyZW5jZSBwaXhlbCksXG4vLyBiZWZvcmUgem9vbS4gQWxsIGdlb21ldHJ5IHN0YXlzIGluIGluY2hlczsgb25seSByZW5kZXJpbmcgbXVsdGlwbGllcyBieSBpdC5cbmV4cG9ydCBjb25zdCBQWF9QRVJfSU5DSCA9IDk2O1xuXG4vLyBPbmUgc21hcnQgZ3VpZGUgbGluZSwgaW4gcGFnZSBpbmNoZXMuXG5leHBvcnQgaW50ZXJmYWNlIEd1aWRlTGluZSB7XG4gIG9yaWVudGF0aW9uOiAndicgfCAnaCc7XG4gIHBvc2l0aW9uOiBudW1iZXI7XG59XG5cbi8vIFRoZSBzbmFwcGluZyBjb250cmFjdCBoYW5kZWQgdG8gZWFjaCBjb21wb25lbnQncyBkcmFnIGxvb3AuIEltcGxlbWVudGVkIGJ5XG4vLyB0aGUgY2FudmFzIGJlY2F1c2Ugb25seSBpdCBzZWVzIGV2ZXJ5IGNvbXBvbmVudCAoYWxpZ25tZW50IGNhbmRpZGF0ZXMpIGFuZFxuLy8gb3ducyB0aGUgZ3VpZGVzIG92ZXJsYXkuXG5leHBvcnQgaW50ZXJmYWNlIENhbnZhc1NuYXBwZXIge1xuICBzbmFwTW92ZShjb21wb25lbnQ6IFJlcG9ydENvbXBvbmVudCwgeDogbnVtYmVyLCB5OiBudW1iZXIpOiB7IHg6IG51bWJlcjsgeTogbnVtYmVyIH07XG4gIHNuYXBSZXNpemUoY29tcG9uZW50OiBSZXBvcnRDb21wb25lbnQsIGdlb21ldHJ5OiB7IHg6IG51bWJlcjsgeTogbnVtYmVyOyB3OiBudW1iZXI7IGg6IG51bWJlciB9LCBoYW5kbGU6IHN0cmluZyk6IHsgeDogbnVtYmVyOyB5OiBudW1iZXI7IHc6IG51bWJlcjsgaDogbnVtYmVyIH07XG4gIGNsZWFyKCk6IHZvaWQ7XG59XG5cbi8vIFRoZSBmaXhlZC1zaXplIHBhZ2UgY2FudmFzIOKAlCB0aGUgUG93ZXJQb2ludCBtb2RlbC4gUGFnZXMgYXJlIHRhYnMgKG9ubHkgdGhlXG4vLyBBQ1RJVkUgcGFnZSdzIGNvbXBvbmVudHMgZXhpc3Qg4oaSIG9ubHkgdGhleSBmZXRjaCk7IHRoZSBwYWdlIGlzIGFcbi8vIHBhZ2VXaWR0aMOXcGFnZUhlaWdodCBJTkNIRVMgc2hlZXQgcmVuZGVyZWQgYXQgOTZweC9pbiBpbnNpZGUgZnMtem9vbS1wYW5cbi8vICh3aGVlbCB6b29tLCBiYWNrZ3JvdW5kIGRyYWcgcGFuLCB0b29sYmFyIGJ1dHRvbnMpLlxuLy9cbi8vIEZyZWVmb3JtIGxheW91dDogY29tcG9uZW50cyBhcmUgYWJzb2x1dGVseSBwb3NpdGlvbmVkOyBkcmFnZ2luZyBnZXRzIHNtYXJ0XG4vLyBhbGlnbm1lbnQgZ3VpZGVzIChlZGdlcyArIGNlbnRlcnMgb2Ygc2libGluZ3MgYW5kIHRoZSBwYWdlKSB3aXRoIHNuYXBwaW5nLlxuLy8gRmxvdyBsYXlvdXQ6IGNvbXBvbmVudHMgZmxvdyBpbnRvIHJvd3MgKGZsb3dXaWR0aCAlIG9mIHRoZSBjb250ZW50IHdpZHRoKSxcbi8vIGRyYWcgcmVvcmRlcnMsIGVhc3Qvc291dGggaGFuZGxlcyByZXNpemUgd2lkdGglL2hlaWdodC5cbkBDb21wb25lbnQoe1xuICBzZWxlY3RvcjogJ2FwcC1yZXBvcnQtY2FudmFzJyxcbiAgdGVtcGxhdGVVcmw6ICcuL3JlcG9ydC1jYW52YXMuY29tcG9uZW50Lmh0bWwnLFxuICBzdHlsZVVybHM6IFsnLi9yZXBvcnQtY2FudmFzLmNvbXBvbmVudC5zY3NzJ10sXG4gIGNoYW5nZURldGVjdGlvbjogQ2hhbmdlRGV0ZWN0aW9uU3RyYXRlZ3kuT25QdXNoLFxuICBzdGFuZGFsb25lOiB0cnVlLFxuICBpbXBvcnRzOiBbXG4gICAgTWF0QnV0dG9uLFxuICAgIE1hdEljb24sXG4gICAgTWF0VG9vbHRpcCxcbiAgICBGc1pvb21QYW5Nb2R1bGUsXG4gICAgUmVwb3J0Q29tcG9uZW50Q29tcG9uZW50LFxuICBdLFxufSlcbmV4cG9ydCBjbGFzcyBSZXBvcnRDYW52YXNDb21wb25lbnQgaW1wbGVtZW50cyBPbkNoYW5nZXMsIEFmdGVyVmlld0luaXQge1xuXG4gIEBJbnB1dCgpIHB1YmxpYyByZXBvcnQ6IFJlcG9ydDtcbiAgQElucHV0KCkgcHVibGljIGVkaXRNb2RlID0gZmFsc2U7XG5cbiAgLy8gQSBjb21wb25lbnQgYXNrZWQgZm9yIGl0cyBzZXR0aW5ncyBkaWFsb2cg4oCUIHRoZSBwYWdlLWxldmVsIGhvc3Qgb3BlbnMgaXRcbiAgLy8gKGl0IG93bnMgTWF0RGlhbG9nICsgdGhlIHBvc3Qtc2F2ZSByZWxvYWQpLlxuICBAT3V0cHV0KCkgcHVibGljIGNvbXBvbmVudFNldHRpbmdzID0gbmV3IEV2ZW50RW1pdHRlcjxSZXBvcnRDb21wb25lbnQ+KCk7XG5cbiAgLy8gVGhlIHJlcG9ydCdzIHN0cnVjdHVyZSBjaGFuZ2VkIGhlcmUgKGEgcGFnZSB3YXMgYWRkZWQpIOKAlCB0aGUgaG9zdCByZS1mZXRjaGVzXG4gIC8vIGl0IChpdCBvd25zIHRoZSBhc3NlbWJsZWQgcmVwb3J0ICsgZmlsdGVyIHN0YXRlKS5cbiAgQE91dHB1dCgpIHB1YmxpYyByZXBvcnRDaGFuZ2VkID0gbmV3IEV2ZW50RW1pdHRlcjx2b2lkPigpO1xuXG4gIC8vIFRoZSB2aWV3ZXIgZGlzbWlzc2VkIGVkaXQgbW9kZSBmcm9tIHRoZSBvbi1jYW52YXMgYmFkZ2Ug4oCUIHRoZSBob3N0IG93bnMgdGhlXG4gIC8vIGVkaXRNb2RlIGZsYWcsIHNvIGl0IGZsaXBzIGl0IG9mZiAobWlycm9ycyB0aGUgbWVudSdzIFwiRG9uZSBlZGl0aW5nIGxheW91dFwiKS5cbiAgQE91dHB1dCgpIHB1YmxpYyBlZGl0RG9uZSA9IG5ldyBFdmVudEVtaXR0ZXI8dm9pZD4oKTtcblxuICBAVmlld0NoaWxkKEZzWm9vbVBhbkNvbXBvbmVudClcbiAgcHVibGljIHpvb21QYW46IEZzWm9vbVBhbkNvbXBvbmVudDtcblxuICAvLyBUaGUgcmVuZGVyZWQgY29tcG9uZW50cyBvZiB0aGUgYWN0aXZlIHBhZ2Ug4oCUIG9ubHkgdGhlIGNhbnZhcyBjYW4gcmVhY2ggdGhlXG4gIC8vIG9uZSBpbnN0YW5jZSBhIHNldHRpbmdzIHNhdmUgYXBwbGllcyB0by5cbiAgQFZpZXdDaGlsZHJlbihSZXBvcnRDb21wb25lbnRDb21wb25lbnQpXG4gIHByaXZhdGUgX3JlbmRlcmVkQ29tcG9uZW50czogUXVlcnlMaXN0PFJlcG9ydENvbXBvbmVudENvbXBvbmVudD47XG5cbiAgQFZpZXdDaGlsZCgndmlld3BvcnQnLCB7IHN0YXRpYzogdHJ1ZSB9KVxuICBwcml2YXRlIF92aWV3cG9ydDogRWxlbWVudFJlZjxIVE1MRGl2RWxlbWVudD47XG5cbiAgQFZpZXdDaGlsZCgnZ3VpZGVzJywgeyBzdGF0aWM6IGZhbHNlIH0pXG4gIHByaXZhdGUgX2d1aWRlczogRWxlbWVudFJlZjxIVE1MRGl2RWxlbWVudD47XG5cbiAgcHVibGljIHJlYWRvbmx5IFBYID0gUFhfUEVSX0lOQ0g7XG4gIHB1YmxpYyByZWFkb25seSBmbG93UGFkZGluZyA9IEZMT1dfUEFERElORztcblxuICBwdWJsaWMgYWN0aXZlUGFnZUluZGV4ID0gMDtcbiAgcHVibGljIHpvb20gPSAxO1xuICBwdWJsaWMgZ3JvdXBzID0gbmV3IE1hcDxudW1iZXIsIFJlcG9ydEZpbHRlckdyb3VwPigpO1xuICBwdWJsaWMgc2VsZWN0ZWRDb21wb25lbnRJZDogbnVtYmVyIHwgbnVsbCA9IG51bGw7XG5cbiAgLy8gVGhlIHNuYXBwZXIgaGFuZGVkIHRvIGV2ZXJ5IGNvbXBvbmVudCAoc3RhYmxlIGlkZW50aXR5IGZvciBPblB1c2gpLlxuICBwdWJsaWMgcmVhZG9ubHkgc25hcHBlcjogQ2FudmFzU25hcHBlciA9IHtcbiAgICBzbmFwTW92ZTogKGNvbXBvbmVudCwgeCwgeSkgPT4gdGhpcy5fc25hcE1vdmUoY29tcG9uZW50LCB4LCB5KSxcbiAgICBzbmFwUmVzaXplOiAoY29tcG9uZW50LCBnZW9tZXRyeSwgaGFuZGxlKSA9PiB0aGlzLl9zbmFwUmVzaXplKGNvbXBvbmVudCwgZ2VvbWV0cnksIGhhbmRsZSksXG4gICAgY2xlYXI6ICgpID0+IHRoaXMuX2NsZWFyR3VpZGVzKCksXG4gIH07XG5cbiAgcHJpdmF0ZSBfcmVwb3J0RGF0YSA9IGluamVjdChSZXBvcnREYXRhKTtcbiAgcHJpdmF0ZSBfY2RSZWYgPSBpbmplY3QoQ2hhbmdlRGV0ZWN0b3JSZWYpO1xuICBwcml2YXRlIF9kZXN0cm95UmVmID0gaW5qZWN0KERlc3Ryb3lSZWYpO1xuICBwcml2YXRlIF9maXR0ZWQgPSBmYWxzZTtcbiAgcHJpdmF0ZSBfcHJldmlvdXNQYWdlQ291bnQgPSAwO1xuXG4gIHB1YmxpYyBuZ09uQ2hhbmdlcygpOiB2b2lkIHtcbiAgICB0aGlzLmdyb3VwcyA9IG5ldyBNYXAoKHRoaXMucmVwb3J0Py5maWx0ZXJHcm91cHMgPz8gW10pLm1hcCgoZ3JvdXApID0+IFtncm91cC5pZCwgZ3JvdXBdKSk7XG5cbiAgICBjb25zdCBwYWdlQ291bnQgPSB0aGlzLnJlcG9ydD8ucGFnZXM/Lmxlbmd0aCA/PyAwO1xuXG4gICAgLy8gQSBwYWdlIHdhcyBqdXN0IGFkZGVkICh0aGUgaG9zdCByZS1mZXRjaGVkIHRoZSByZXBvcnQpIOKAlCBsYW5kIG9uIGl0LlxuICAgIGlmIChwYWdlQ291bnQgPiB0aGlzLl9wcmV2aW91c1BhZ2VDb3VudCAmJiB0aGlzLl9wcmV2aW91c1BhZ2VDb3VudCA+IDApIHtcbiAgICAgIHRoaXMuYWN0aXZlUGFnZUluZGV4ID0gcGFnZUNvdW50IC0gMTtcbiAgICB9XG4gICAgdGhpcy5fcHJldmlvdXNQYWdlQ291bnQgPSBwYWdlQ291bnQ7XG5cbiAgICBpZiAodGhpcy5hY3RpdmVQYWdlSW5kZXggPj0gcGFnZUNvdW50KSB7XG4gICAgICB0aGlzLmFjdGl2ZVBhZ2VJbmRleCA9IDA7XG4gICAgfVxuICB9XG5cbiAgLy8gUmVwb3J0IGhlYWRpbmcgc2l6ZSBpbiBweCAoY29uZmlnIGlzIHBvaW50czsgdGhlIGNhbnZhcyByZW5kZXJzIGF0XG4gIC8vIDk2cHgvaW4sIHNvIHBvaW50cyDDlyA5Ni83MikuIEluaGVyaXRlZCBieSBjb21wb25lbnQgdGl0bGVzIHZpYSBhIENTUyB2YXIuXG4gIHB1YmxpYyBnZXQgaGVhZGluZ1NpemVQeCgpOiBudW1iZXIge1xuICAgIGNvbnN0IHBvaW50cyA9IHRoaXMucmVwb3J0Py5jb25maWc/LnN0eWxlcz8uaGVhZGluZz8uc2l6ZSA/PyBERUZBVUxUX0hFQURJTkdfU0laRTtcblxuICAgIHJldHVybiBwb2ludHMgKiAoUFhfUEVSX0lOQ0ggLyA3Mik7XG4gIH1cblxuICBwdWJsaWMgbmdBZnRlclZpZXdJbml0KCk6IHZvaWQge1xuICAgIC8vIEZpdCB0aGUgcGFnZSB0byB0aGUgdmlld3BvcnQgb25jZSBvbiBmaXJzdCByZW5kZXI7IGFmdGVyIHRoYXQgdGhlXG4gICAgLy8gdmlld2VyJ3Mgem9vbSBjaG9pY2UgaXMgcmVzcGVjdGVkIGFjcm9zcyByZS1yZW5kZXJzLlxuICAgIHNldFRpbWVvdXQoKCkgPT4gdGhpcy56b29tRml0KCkpO1xuICB9XG5cbiAgcHVibGljIGdldCBpc0Zsb3coKTogYm9vbGVhbiB7XG4gICAgcmV0dXJuIHRoaXMucmVwb3J0Py5sYXlvdXQgPT09ICdmbG93JztcbiAgfVxuXG4gIHB1YmxpYyBnZXQgYWN0aXZlUGFnZSgpOiBSZXBvcnRQYWdlIHwgbnVsbCB7XG4gICAgcmV0dXJuIHRoaXMucmVwb3J0Py5wYWdlcz8uW3RoaXMuYWN0aXZlUGFnZUluZGV4XSA/PyBudWxsO1xuICB9XG5cbiAgLy8gRmxvdyByZW5kZXIgb3JkZXIgKHRoZSBhc3NlbWJsZXIgYWxyZWFkeSBzb3J0cywgYnV0IGEgbG9jYWwgcmVvcmRlclxuICAvLyBtaWQtc2Vzc2lvbiBtdXN0IGhvbGQgd2l0aG91dCBhIHJlLWZldGNoKS5cbiAgcHVibGljIGdldCBmbG93Q29tcG9uZW50cygpOiBSZXBvcnRDb21wb25lbnRbXSB7XG4gICAgcmV0dXJuIFsuLi4odGhpcy5hY3RpdmVQYWdlPy5jb21wb25lbnRzID8/IFtdKV0uc29ydCgoYSwgYikgPT4gYS5vcmRlciAtIGIub3JkZXIpO1xuICB9XG5cbiAgcHVibGljIHNlbGVjdFBhZ2UoaW5kZXg6IG51bWJlcik6IHZvaWQge1xuICAgIHRoaXMuYWN0aXZlUGFnZUluZGV4ID0gaW5kZXg7XG4gICAgdGhpcy5zZWxlY3RlZENvbXBvbmVudElkID0gbnVsbDtcbiAgfVxuXG4gIC8vIEFwcGVuZCBhIGJsYW5rIHBhZ2U7IHRoZSBob3N0IHJlLWZldGNoZXMgdGhlIHJlcG9ydCBhbmQgbmdPbkNoYW5nZXMgbGFuZHNcbiAgLy8gdGhlIHZpZXcgb24gdGhlIG5ldyAobGFzdCkgcGFnZS5cbiAgcHVibGljIGFkZFBhZ2UoKTogdm9pZCB7XG4gICAgaWYgKCF0aGlzLnJlcG9ydCkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIHRoaXMuX3JlcG9ydERhdGEuYWRkUGFnZSh0aGlzLnJlcG9ydC5pZClcbiAgICAgIC5waXBlKHRha2VVbnRpbERlc3Ryb3llZCh0aGlzLl9kZXN0cm95UmVmKSlcbiAgICAgIC5zdWJzY3JpYmUoKCkgPT4gdGhpcy5yZXBvcnRDaGFuZ2VkLmVtaXQoKSk7XG4gIH1cblxuICBwdWJsaWMgcGFnZUxhYmVsKHBhZ2U6IFJlcG9ydFBhZ2UsIGluZGV4OiBudW1iZXIpOiBzdHJpbmcge1xuICAgIHJldHVybiBwYWdlLm5hbWUgfHwgYFBhZ2UgJHtpbmRleCArIDF9YDtcbiAgfVxuXG4gIC8vIEhhbmQgcHJlc2VudGF0aW9uIHNldHRpbmdzICh0aXRsZSwgcGFkZGluZykgc2F2ZWQgaW4gdGhlIHNldHRpbmdzIGRpYWxvZyB0b1xuICAvLyB0aGUgb25lIGNvbXBvbmVudCB0aGV5IGJlbG9uZyB0by4gTm90aGluZyBoZXJlIGZlZWRzIHRoZSBxdWVyeSwgc28gdGhhdFxuICAvLyBjb21wb25lbnQgcmVwYWludHMgYW5kIGV2ZXJ5IG90aGVyIG9uZSBvbiB0aGUgcGFnZSBpcyBsZWZ0IGFsb25lLlxuICBwdWJsaWMgYXBwbHlDb21wb25lbnRTZXR0aW5ncyhjb21wb25lbnRJZDogbnVtYmVyLCBzZXR0aW5nczogQ29tcG9uZW50U2V0dGluZ3MpOiB2b2lkIHtcbiAgICB0aGlzLl9yZW5kZXJlZENvbXBvbmVudHNcbiAgICAgIC5maW5kKChyZW5kZXJlZCkgPT4gcmVuZGVyZWQuY29tcG9uZW50LmlkID09PSBjb21wb25lbnRJZClcbiAgICAgID8uYXBwbHlTZXR0aW5ncyhzZXR0aW5ncyk7XG4gIH1cblxuICBwdWJsaWMgc2VsZWN0Q29tcG9uZW50KGNvbXBvbmVudElkOiBudW1iZXIgfCBudWxsKTogdm9pZCB7XG4gICAgdGhpcy5zZWxlY3RlZENvbXBvbmVudElkID0gY29tcG9uZW50SWQ7XG4gICAgdGhpcy5fY2RSZWYubWFya0ZvckNoZWNrKCk7XG4gIH1cblxuICBwdWJsaWMgb25DYW52YXNQb2ludGVyRG93bigpOiB2b2lkIHtcbiAgICAvLyBCYWNrZ3JvdW5kIGNsaWNrIChwYW4gc3RhcnQpIGRlc2VsZWN0cy5cbiAgICBpZiAodGhpcy5zZWxlY3RlZENvbXBvbmVudElkICE9PSBudWxsKSB7XG4gICAgICB0aGlzLnNlbGVjdENvbXBvbmVudChudWxsKTtcbiAgICB9XG4gIH1cblxuICAvLyAtLS0tLSB6b29tIHRvb2xiYXIgLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG5cbiAgcHVibGljIG9uWm9vbWVkKHNjYWxlOiBudW1iZXIpOiB2b2lkIHtcbiAgICB0aGlzLnpvb20gPSBzY2FsZTtcbiAgICB0aGlzLl9jZFJlZi5tYXJrRm9yQ2hlY2soKTtcbiAgfVxuXG4gIHB1YmxpYyB6b29tSW4oKTogdm9pZCB7XG4gICAgdGhpcy56b29tUGFuPy56b29tSW4oKTtcbiAgfVxuXG4gIHB1YmxpYyB6b29tT3V0KCk6IHZvaWQge1xuICAgIHRoaXMuem9vbVBhbj8uem9vbU91dCgpO1xuICB9XG5cbiAgcHVibGljIHpvb21GaXQoKTogdm9pZCB7XG4gICAgY29uc3Qgdmlld3BvcnQgPSB0aGlzLl92aWV3cG9ydD8ubmF0aXZlRWxlbWVudDtcbiAgICBpZiAoIXZpZXdwb3J0IHx8ICF0aGlzLnJlcG9ydD8ucGFnZVdpZHRoIHx8ICF0aGlzLnpvb21QYW4pIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICBjb25zdCBmaXQgPSBNYXRoLm1pbihcbiAgICAgICh2aWV3cG9ydC5jbGllbnRXaWR0aCAtIDMyKSAvICh0aGlzLnJlcG9ydC5wYWdlV2lkdGggKiBQWF9QRVJfSU5DSCksXG4gICAgICAodmlld3BvcnQuY2xpZW50SGVpZ2h0IC0gMzIpIC8gKHRoaXMucmVwb3J0LnBhZ2VIZWlnaHQgKiBQWF9QRVJfSU5DSCksXG4gICAgKTtcblxuICAgIHRoaXMuem9vbVBhbi56b29tKE1hdGgubWluKDEuNSwgTWF0aC5tYXgoMC4xLCBmaXQpKSk7XG4gICAgdGhpcy56b29tUGFuLm1vdmUoMTYsIDE2KTtcbiAgICB0aGlzLl9maXR0ZWQgPSB0cnVlO1xuICB9XG5cbiAgcHVibGljIHpvb21BY3R1YWwoKTogdm9pZCB7XG4gICAgdGhpcy56b29tUGFuPy56b29tKDEpO1xuICB9XG5cbiAgLy8gLS0tLS0gcGVyc2lzdGVuY2UgLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLVxuXG4gIC8vIEEgZnJlZWZvcm0gZHJhZy9yZXNpemUgb3IgYSBmbG93IHdpZHRoIHJlc2l6ZSBsYW5kZWQg4oCUIG9uZSBQVVQgcGVyIGdlc3R1cmUuXG4gIHB1YmxpYyBvblBvc2l0aW9uQ2hhbmdlZChwb3NpdGlvbjogeyBjb21wb25lbnRJZDogbnVtYmVyIH0gJiBSZWNvcmQ8c3RyaW5nLCBudW1iZXI+KTogdm9pZCB7XG4gICAgdGhpcy5fY2xlYXJHdWlkZXMoKTtcbiAgICB0aGlzLl9yZXBvcnREYXRhLnNhdmVQb3NpdGlvbnModGhpcy5yZXBvcnQuaWQsIFtwb3NpdGlvbiBhcyBhbnldKVxuICAgICAgLnBpcGUodGFrZVVudGlsRGVzdHJveWVkKHRoaXMuX2Rlc3Ryb3lSZWYpKVxuICAgICAgLnN1YnNjcmliZSgpO1xuICB9XG5cbiAgLy8gQSBmbG93IGRyYWcgZHJvcHBlZDogcmVvcmRlciB0aGUgcGFnZSdzIGNvbXBvbmVudHMgYXJvdW5kIHRoZSBtb3ZlZCBvbmVcbiAgLy8gYW5kIHBlcnNpc3QgZXZlcnkgb3JkZXIgaW4gb25lIFBVVC5cbiAgcHVibGljIG9uRmxvd1Jlb3JkZXIoZXZlbnQ6IHsgY29tcG9uZW50SWQ6IG51bWJlcjsgY2xpZW50WDogbnVtYmVyOyBjbGllbnRZOiBudW1iZXIgfSk6IHZvaWQge1xuICAgIGNvbnN0IHBhZ2UgPSB0aGlzLmFjdGl2ZVBhZ2U7XG4gICAgaWYgKCFwYWdlKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgY29uc3Qgb3JkZXJlZCA9IHRoaXMuZmxvd0NvbXBvbmVudHMuZmlsdGVyKChjb21wb25lbnQpID0+IGNvbXBvbmVudC5pZCAhPT0gZXZlbnQuY29tcG9uZW50SWQpO1xuICAgIGNvbnN0IG1vdmVkID0gcGFnZS5jb21wb25lbnRzLmZpbmQoKGNvbXBvbmVudCkgPT4gY29tcG9uZW50LmlkID09PSBldmVudC5jb21wb25lbnRJZCk7XG4gICAgaWYgKCFtb3ZlZCkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIGNvbnN0IGluZGV4ID0gdGhpcy5fZmxvd0Ryb3BJbmRleChvcmRlcmVkLCBldmVudC5jbGllbnRYLCBldmVudC5jbGllbnRZKTtcbiAgICBvcmRlcmVkLnNwbGljZShpbmRleCwgMCwgbW92ZWQpO1xuXG4gICAgY29uc3QgcG9zaXRpb25zID0gb3JkZXJlZC5tYXAoKGNvbXBvbmVudCwgb3JkZXIpID0+IHtcbiAgICAgIGNvbXBvbmVudC5vcmRlciA9IG9yZGVyO1xuXG4gICAgICByZXR1cm4geyBjb21wb25lbnRJZDogY29tcG9uZW50LmlkLCBvcmRlciB9O1xuICAgIH0pO1xuXG4gICAgdGhpcy5fY2RSZWYubWFya0ZvckNoZWNrKCk7XG4gICAgdGhpcy5fcmVwb3J0RGF0YS5zYXZlUG9zaXRpb25zKHRoaXMucmVwb3J0LmlkLCBwb3NpdGlvbnMpXG4gICAgICAucGlwZSh0YWtlVW50aWxEZXN0cm95ZWQodGhpcy5fZGVzdHJveVJlZikpXG4gICAgICAuc3Vic2NyaWJlKCk7XG4gIH1cblxuICAvLyBXaGVyZSB0aGUgcG9pbnRlciBsYW5kZWQgYW1vbmcgdGhlIGZsb3dlZCBjb21wb25lbnRzOiBiZWZvcmUgdGhlIGZpcnN0XG4gIC8vIGNvbXBvbmVudCB3aG9zZSBjZW50ZXIgdGhlIHBvaW50ZXIgaXMgYWJvdmUvbGVmdCBvZi5cbiAgcHJpdmF0ZSBfZmxvd0Ryb3BJbmRleChvcmRlcmVkOiBSZXBvcnRDb21wb25lbnRbXSwgY2xpZW50WDogbnVtYmVyLCBjbGllbnRZOiBudW1iZXIpOiBudW1iZXIge1xuICAgIGNvbnN0IGhvc3RzID0gQXJyYXkuZnJvbShcbiAgICAgIHRoaXMuX3ZpZXdwb3J0Lm5hdGl2ZUVsZW1lbnQucXVlcnlTZWxlY3RvckFsbDxIVE1MRWxlbWVudD4oJ2FwcC1yZXBvcnQtY29tcG9uZW50JyksXG4gICAgKS5maWx0ZXIoKGhvc3QpID0+ICFob3N0LmNsYXNzTGlzdC5jb250YWlucygnZmxvdy1kcmFnZ2luZycpKTtcblxuICAgIGZvciAobGV0IGluZGV4ID0gMDsgaW5kZXggPCBob3N0cy5sZW5ndGggJiYgaW5kZXggPCBvcmRlcmVkLmxlbmd0aDsgaW5kZXgrKykge1xuICAgICAgY29uc3QgcmVjdCA9IGhvc3RzW2luZGV4XS5nZXRCb3VuZGluZ0NsaWVudFJlY3QoKTtcbiAgICAgIGlmIChjbGllbnRZIDwgcmVjdC50b3AgKyByZWN0LmhlaWdodCAvIDJcbiAgICAgICAgfHwgKGNsaWVudFkgPCByZWN0LmJvdHRvbSAmJiBjbGllbnRYIDwgcmVjdC5sZWZ0ICsgcmVjdC53aWR0aCAvIDIpKSB7XG4gICAgICAgIHJldHVybiBpbmRleDtcbiAgICAgIH1cbiAgICB9XG5cbiAgICByZXR1cm4gb3JkZXJlZC5sZW5ndGg7XG4gIH1cblxuICAvLyAtLS0tLSBzbWFydCBndWlkZXMgLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG5cbiAgLy8gUGl4ZWwgZmVlbCBvZiB0aGUgc25hcCwgY29udmVydGVkIHRvIGluY2hlcyBhdCB0aGUgY3VycmVudCB6b29tLlxuICBwcml2YXRlIGdldCBfc25hcFRocmVzaG9sZCgpOiBudW1iZXIge1xuICAgIHJldHVybiA4IC8gKFBYX1BFUl9JTkNIICogTWF0aC5tYXgoMC4xLCB0aGlzLnpvb20pKTtcbiAgfVxuXG4gIHByaXZhdGUgX3NuYXBNb3ZlKGNvbXBvbmVudDogUmVwb3J0Q29tcG9uZW50LCB4OiBudW1iZXIsIHk6IG51bWJlcik6IHsgeDogbnVtYmVyOyB5OiBudW1iZXIgfSB7XG4gICAgY29uc3QgeyB2ZXJ0aWNhbCwgaG9yaXpvbnRhbCB9ID0gdGhpcy5fY2FuZGlkYXRlcyhjb21wb25lbnQpO1xuICAgIGNvbnN0IGd1aWRlczogR3VpZGVMaW5lW10gPSBbXTtcblxuICAgIGNvbnN0IHNuYXBwZWRYID0gdGhpcy5fc25hcEF4aXMoXG4gICAgICBbXG4gICAgICAgIHsgb2Zmc2V0OiAwLCB2YWx1ZTogeCB9LFxuICAgICAgICB7IG9mZnNldDogY29tcG9uZW50LncgLyAyLCB2YWx1ZTogeCArIGNvbXBvbmVudC53IC8gMiB9LFxuICAgICAgICB7IG9mZnNldDogY29tcG9uZW50LncsIHZhbHVlOiB4ICsgY29tcG9uZW50LncgfSxcbiAgICAgIF0sXG4gICAgICB2ZXJ0aWNhbCxcbiAgICApO1xuICAgIGlmIChzbmFwcGVkWCAhPT0gbnVsbCkge1xuICAgICAgeCA9IHNuYXBwZWRYLmJhc2U7XG4gICAgICBndWlkZXMucHVzaCh7IG9yaWVudGF0aW9uOiAndicsIHBvc2l0aW9uOiBzbmFwcGVkWC5ndWlkZSB9KTtcbiAgICB9XG5cbiAgICBjb25zdCBzbmFwcGVkWSA9IHRoaXMuX3NuYXBBeGlzKFxuICAgICAgW1xuICAgICAgICB7IG9mZnNldDogMCwgdmFsdWU6IHkgfSxcbiAgICAgICAgeyBvZmZzZXQ6IGNvbXBvbmVudC5oIC8gMiwgdmFsdWU6IHkgKyBjb21wb25lbnQuaCAvIDIgfSxcbiAgICAgICAgeyBvZmZzZXQ6IGNvbXBvbmVudC5oLCB2YWx1ZTogeSArIGNvbXBvbmVudC5oIH0sXG4gICAgICBdLFxuICAgICAgaG9yaXpvbnRhbCxcbiAgICApO1xuICAgIGlmIChzbmFwcGVkWSAhPT0gbnVsbCkge1xuICAgICAgeSA9IHNuYXBwZWRZLmJhc2U7XG4gICAgICBndWlkZXMucHVzaCh7IG9yaWVudGF0aW9uOiAnaCcsIHBvc2l0aW9uOiBzbmFwcGVkWS5ndWlkZSB9KTtcbiAgICB9XG5cbiAgICB0aGlzLl9yZW5kZXJHdWlkZXMoZ3VpZGVzKTtcblxuICAgIHJldHVybiB7IHgsIHkgfTtcbiAgfVxuXG4gIHByaXZhdGUgX3NuYXBSZXNpemUoXG4gICAgY29tcG9uZW50OiBSZXBvcnRDb21wb25lbnQsXG4gICAgZ2VvbWV0cnk6IHsgeDogbnVtYmVyOyB5OiBudW1iZXI7IHc6IG51bWJlcjsgaDogbnVtYmVyIH0sXG4gICAgaGFuZGxlOiBzdHJpbmcsXG4gICk6IHsgeDogbnVtYmVyOyB5OiBudW1iZXI7IHc6IG51bWJlcjsgaDogbnVtYmVyIH0ge1xuICAgIGNvbnN0IHsgdmVydGljYWwsIGhvcml6b250YWwgfSA9IHRoaXMuX2NhbmRpZGF0ZXMoY29tcG9uZW50KTtcbiAgICBjb25zdCBndWlkZXM6IEd1aWRlTGluZVtdID0gW107XG4gICAgY29uc3QgcmVzdWx0ID0geyAuLi5nZW9tZXRyeSB9O1xuXG4gICAgLy8gT25seSB0aGUgZWRnZXMgdGhlIGhhbmRsZSBtb3ZlcyBwYXJ0aWNpcGF0ZSBpbiBzbmFwcGluZy5cbiAgICBpZiAoaGFuZGxlLmluY2x1ZGVzKCdlJykpIHtcbiAgICAgIGNvbnN0IHNuYXBwZWQgPSB0aGlzLl9uZWFyZXN0KGdlb21ldHJ5LnggKyBnZW9tZXRyeS53LCB2ZXJ0aWNhbCk7XG4gICAgICBpZiAoc25hcHBlZCAhPT0gbnVsbCkge1xuICAgICAgICByZXN1bHQudyA9IHNuYXBwZWQgLSBnZW9tZXRyeS54O1xuICAgICAgICBndWlkZXMucHVzaCh7IG9yaWVudGF0aW9uOiAndicsIHBvc2l0aW9uOiBzbmFwcGVkIH0pO1xuICAgICAgfVxuICAgIH1cbiAgICBpZiAoaGFuZGxlLmluY2x1ZGVzKCd3JykpIHtcbiAgICAgIGNvbnN0IHNuYXBwZWQgPSB0aGlzLl9uZWFyZXN0KGdlb21ldHJ5LngsIHZlcnRpY2FsKTtcbiAgICAgIGlmIChzbmFwcGVkICE9PSBudWxsKSB7XG4gICAgICAgIHJlc3VsdC53ID0gZ2VvbWV0cnkueCArIGdlb21ldHJ5LncgLSBzbmFwcGVkO1xuICAgICAgICByZXN1bHQueCA9IHNuYXBwZWQ7XG4gICAgICAgIGd1aWRlcy5wdXNoKHsgb3JpZW50YXRpb246ICd2JywgcG9zaXRpb246IHNuYXBwZWQgfSk7XG4gICAgICB9XG4gICAgfVxuICAgIGlmIChoYW5kbGUuaW5jbHVkZXMoJ3MnKSkge1xuICAgICAgY29uc3Qgc25hcHBlZCA9IHRoaXMuX25lYXJlc3QoZ2VvbWV0cnkueSArIGdlb21ldHJ5LmgsIGhvcml6b250YWwpO1xuICAgICAgaWYgKHNuYXBwZWQgIT09IG51bGwpIHtcbiAgICAgICAgcmVzdWx0LmggPSBzbmFwcGVkIC0gZ2VvbWV0cnkueTtcbiAgICAgICAgZ3VpZGVzLnB1c2goeyBvcmllbnRhdGlvbjogJ2gnLCBwb3NpdGlvbjogc25hcHBlZCB9KTtcbiAgICAgIH1cbiAgICB9XG4gICAgaWYgKGhhbmRsZS5pbmNsdWRlcygnbicpKSB7XG4gICAgICBjb25zdCBzbmFwcGVkID0gdGhpcy5fbmVhcmVzdChnZW9tZXRyeS55LCBob3Jpem9udGFsKTtcbiAgICAgIGlmIChzbmFwcGVkICE9PSBudWxsKSB7XG4gICAgICAgIHJlc3VsdC5oID0gZ2VvbWV0cnkueSArIGdlb21ldHJ5LmggLSBzbmFwcGVkO1xuICAgICAgICByZXN1bHQueSA9IHNuYXBwZWQ7XG4gICAgICAgIGd1aWRlcy5wdXNoKHsgb3JpZW50YXRpb246ICdoJywgcG9zaXRpb246IHNuYXBwZWQgfSk7XG4gICAgICB9XG4gICAgfVxuXG4gICAgdGhpcy5fcmVuZGVyR3VpZGVzKGd1aWRlcyk7XG5cbiAgICByZXR1cm4gcmVzdWx0O1xuICB9XG5cbiAgLy8gQWxpZ25tZW50IGNhbmRpZGF0ZXM6IHRoZSBwYWdlJ3MgZWRnZXMgKyBjZW50ZXIsIGFuZCBldmVyeSBzaWJsaW5nJ3NcbiAgLy8gZWRnZXMgKyBjZW50ZXJzLlxuICBwcml2YXRlIF9jYW5kaWRhdGVzKG1vdmluZzogUmVwb3J0Q29tcG9uZW50KTogeyB2ZXJ0aWNhbDogbnVtYmVyW107IGhvcml6b250YWw6IG51bWJlcltdIH0ge1xuICAgIGNvbnN0IHZlcnRpY2FsID0gWzAsIHRoaXMucmVwb3J0LnBhZ2VXaWR0aCAvIDIsIHRoaXMucmVwb3J0LnBhZ2VXaWR0aF07XG4gICAgY29uc3QgaG9yaXpvbnRhbCA9IFswLCB0aGlzLnJlcG9ydC5wYWdlSGVpZ2h0IC8gMiwgdGhpcy5yZXBvcnQucGFnZUhlaWdodF07XG5cbiAgICBmb3IgKGNvbnN0IGNvbXBvbmVudCBvZiB0aGlzLmFjdGl2ZVBhZ2U/LmNvbXBvbmVudHMgPz8gW10pIHtcbiAgICAgIGlmIChjb21wb25lbnQuaWQgPT09IG1vdmluZy5pZCkge1xuICAgICAgICBjb250aW51ZTtcbiAgICAgIH1cblxuICAgICAgdmVydGljYWwucHVzaChjb21wb25lbnQueCwgY29tcG9uZW50LnggKyBjb21wb25lbnQudyAvIDIsIGNvbXBvbmVudC54ICsgY29tcG9uZW50LncpO1xuICAgICAgaG9yaXpvbnRhbC5wdXNoKGNvbXBvbmVudC55LCBjb21wb25lbnQueSArIGNvbXBvbmVudC5oIC8gMiwgY29tcG9uZW50LnkgKyBjb21wb25lbnQuaCk7XG4gICAgfVxuXG4gICAgcmV0dXJuIHsgdmVydGljYWwsIGhvcml6b250YWwgfTtcbiAgfVxuXG4gIC8vIFNuYXAgb25lIGF4aXM6IG9mIHRoZSBtb3ZpbmcgYm94J3MgdGhyZWUgbGluZXMgKGVkZ2UvY2VudGVyL2VkZ2UpLCBmaW5kXG4gIC8vIHRoZSBjbG9zZXN0IGNhbmRpZGF0ZSB3aXRoaW4gdGhyZXNob2xkIGFuZCByZXR1cm4gdGhlIGFkanVzdGVkIGJhc2VcbiAgLy8gY29vcmRpbmF0ZSBwbHVzIHRoZSBndWlkZSB0byBkcmF3LlxuICBwcml2YXRlIF9zbmFwQXhpcyhcbiAgICBsaW5lczogeyBvZmZzZXQ6IG51bWJlcjsgdmFsdWU6IG51bWJlciB9W10sXG4gICAgY2FuZGlkYXRlczogbnVtYmVyW10sXG4gICk6IHsgYmFzZTogbnVtYmVyOyBndWlkZTogbnVtYmVyIH0gfCBudWxsIHtcbiAgICBsZXQgYmVzdDogeyBiYXNlOiBudW1iZXI7IGd1aWRlOiBudW1iZXI7IGRpc3RhbmNlOiBudW1iZXIgfSB8IG51bGwgPSBudWxsO1xuXG4gICAgZm9yIChjb25zdCBsaW5lIG9mIGxpbmVzKSB7XG4gICAgICBmb3IgKGNvbnN0IGNhbmRpZGF0ZSBvZiBjYW5kaWRhdGVzKSB7XG4gICAgICAgIGNvbnN0IGRpc3RhbmNlID0gTWF0aC5hYnMoY2FuZGlkYXRlIC0gbGluZS52YWx1ZSk7XG4gICAgICAgIGlmIChkaXN0YW5jZSA8PSB0aGlzLl9zbmFwVGhyZXNob2xkICYmICghYmVzdCB8fCBkaXN0YW5jZSA8IGJlc3QuZGlzdGFuY2UpKSB7XG4gICAgICAgICAgYmVzdCA9IHsgYmFzZTogY2FuZGlkYXRlIC0gbGluZS5vZmZzZXQsIGd1aWRlOiBjYW5kaWRhdGUsIGRpc3RhbmNlIH07XG4gICAgICAgIH1cbiAgICAgIH1cbiAgICB9XG5cbiAgICByZXR1cm4gYmVzdCA/IHsgYmFzZTogYmVzdC5iYXNlLCBndWlkZTogYmVzdC5ndWlkZSB9IDogbnVsbDtcbiAgfVxuXG4gIHByaXZhdGUgX25lYXJlc3QodmFsdWU6IG51bWJlciwgY2FuZGlkYXRlczogbnVtYmVyW10pOiBudW1iZXIgfCBudWxsIHtcbiAgICBsZXQgYmVzdDogbnVtYmVyIHwgbnVsbCA9IG51bGw7XG4gICAgbGV0IGJlc3REaXN0YW5jZSA9IHRoaXMuX3NuYXBUaHJlc2hvbGQ7XG5cbiAgICBmb3IgKGNvbnN0IGNhbmRpZGF0ZSBvZiBjYW5kaWRhdGVzKSB7XG4gICAgICBjb25zdCBkaXN0YW5jZSA9IE1hdGguYWJzKGNhbmRpZGF0ZSAtIHZhbHVlKTtcbiAgICAgIGlmIChkaXN0YW5jZSA8PSBiZXN0RGlzdGFuY2UpIHtcbiAgICAgICAgYmVzdCA9IGNhbmRpZGF0ZTtcbiAgICAgICAgYmVzdERpc3RhbmNlID0gZGlzdGFuY2U7XG4gICAgICB9XG4gICAgfVxuXG4gICAgcmV0dXJuIGJlc3Q7XG4gIH1cblxuICAvLyBUaGUgZ3VpZGVzIG92ZXJsYXkgaXMgZHJhd24gaW1wZXJhdGl2ZWx5IOKAlCB0aGUgZHJhZyBsb29wIHJ1bnMgb3V0c2lkZVxuICAvLyBBbmd1bGFyIGFuZCByZXBhaW50cyBvbiBldmVyeSBwb2ludGVybW92ZS5cbiAgcHJpdmF0ZSBfcmVuZGVyR3VpZGVzKGd1aWRlczogR3VpZGVMaW5lW10pOiB2b2lkIHtcbiAgICBjb25zdCBob3N0ID0gdGhpcy5fZ3VpZGVzPy5uYXRpdmVFbGVtZW50O1xuICAgIGlmICghaG9zdCkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIGhvc3QucmVwbGFjZUNoaWxkcmVuKC4uLmd1aWRlcy5tYXAoKGd1aWRlKSA9PiB7XG4gICAgICBjb25zdCBsaW5lID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnZGl2Jyk7XG4gICAgICBsaW5lLmNsYXNzTmFtZSA9IGBndWlkZSBndWlkZS0ke2d1aWRlLm9yaWVudGF0aW9ufWA7XG4gICAgICBpZiAoZ3VpZGUub3JpZW50YXRpb24gPT09ICd2Jykge1xuICAgICAgICBsaW5lLnN0eWxlLmxlZnQgPSBgJHtndWlkZS5wb3NpdGlvbiAqIFBYX1BFUl9JTkNIfXB4YDtcbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIGxpbmUuc3R5bGUudG9wID0gYCR7Z3VpZGUucG9zaXRpb24gKiBQWF9QRVJfSU5DSH1weGA7XG4gICAgICB9XG5cbiAgICAgIHJldHVybiBsaW5lO1xuICAgIH0pKTtcbiAgfVxuXG4gIHByaXZhdGUgX2NsZWFyR3VpZGVzKCk6IHZvaWQge1xuICAgIHRoaXMuX2d1aWRlcz8ubmF0aXZlRWxlbWVudD8ucmVwbGFjZUNoaWxkcmVuKCk7XG4gIH1cbn1cbiIsIjxkaXYgY2xhc3M9XCJjYW52YXNcIj5cbiAgPGRpdlxuICAgICN2aWV3cG9ydFxuICAgIGNsYXNzPVwicGFnZS12aWV3cG9ydFwiXG4gICAgKHBvaW50ZXJkb3duKT1cIm9uQ2FudmFzUG9pbnRlckRvd24oKVwiPlxuICAgIDxmcy16b29tLXBhblxuICAgICAgW3pvb21NaW5dPVwiMC4xXCJcbiAgICAgIFt6b29tTWF4XT1cIjNcIlxuICAgICAgKHpvb21lZCk9XCJvblpvb21lZCgkZXZlbnQpXCI+XG4gICAgICBAaWYgKGFjdGl2ZVBhZ2U7IGFzIHBhZ2UpIHtcbiAgICAgICAgPGRpdlxuICAgICAgICAgIGNsYXNzPVwicGFnZVwiXG4gICAgICAgICAgW2NsYXNzLmZsb3ddPVwiaXNGbG93XCJcbiAgICAgICAgICBbY2xhc3MuZWRpdGluZ109XCJlZGl0TW9kZVwiXG4gICAgICAgICAgW3N0eWxlLndpZHRoLnB4XT1cInJlcG9ydC5wYWdlV2lkdGggKiBQWFwiXG4gICAgICAgICAgW3N0eWxlLmhlaWdodC5weF09XCJyZXBvcnQucGFnZUhlaWdodCAqIFBYXCJcbiAgICAgICAgICBbc3R5bGUucGFkZGluZy5weF09XCJpc0Zsb3cgPyBmbG93UGFkZGluZyAqIFBYIDogMFwiXG4gICAgICAgICAgW3N0eWxlLi0tY2FudmFzLXpvb21dPVwiem9vbVwiXG4gICAgICAgICAgW3N0eWxlLi0tcmVwb3J0LWhlYWRpbmctc2l6ZS5weF09XCJoZWFkaW5nU2l6ZVB4XCI+XG4gICAgICAgICAgQGlmIChpc0Zsb3cpIHtcbiAgICAgICAgICAgIEBmb3IgKGNvbXBvbmVudCBvZiBmbG93Q29tcG9uZW50czsgdHJhY2sgY29tcG9uZW50LmlkKSB7XG4gICAgICAgICAgICAgIDxhcHAtcmVwb3J0LWNvbXBvbmVudFxuICAgICAgICAgICAgICAgIGNsYXNzPVwiZmxvdy1pdGVtXCJcbiAgICAgICAgICAgICAgICBbcmVwb3J0SWRdPVwicmVwb3J0LmlkXCJcbiAgICAgICAgICAgICAgICBbY29tcG9uZW50XT1cImNvbXBvbmVudFwiXG4gICAgICAgICAgICAgICAgW2dyb3Vwc109XCJncm91cHNcIlxuICAgICAgICAgICAgICAgIFtlZGl0TW9kZV09XCJlZGl0TW9kZVwiXG4gICAgICAgICAgICAgICAgW2xheW91dF09XCInZmxvdydcIlxuICAgICAgICAgICAgICAgIFt6b29tXT1cInpvb21cIlxuICAgICAgICAgICAgICAgIFtzbmFwcGVyXT1cInNuYXBwZXJcIlxuICAgICAgICAgICAgICAgIFtzZWxlY3RlZF09XCJjb21wb25lbnQuaWQgPT09IHNlbGVjdGVkQ29tcG9uZW50SWRcIlxuICAgICAgICAgICAgICAgIFtzdHlsZS53aWR0aC4lXT1cImNvbXBvbmVudC5mbG93V2lkdGhcIlxuICAgICAgICAgICAgICAgIFtzdHlsZS5oZWlnaHQucHhdPVwiY29tcG9uZW50LmF1dG9IZWlnaHQgPyBudWxsIDogY29tcG9uZW50LmggKiBQWFwiXG4gICAgICAgICAgICAgICAgKHNlbGVjdENvbXBvbmVudCk9XCJzZWxlY3RDb21wb25lbnQoJGV2ZW50KVwiXG4gICAgICAgICAgICAgICAgKHBvc2l0aW9uQ2hhbmdlZCk9XCJvblBvc2l0aW9uQ2hhbmdlZCgkZXZlbnQpXCJcbiAgICAgICAgICAgICAgICAoZmxvd1Jlb3JkZXIpPVwib25GbG93UmVvcmRlcigkZXZlbnQpXCJcbiAgICAgICAgICAgICAgICAob3BlblNldHRpbmdzKT1cImNvbXBvbmVudFNldHRpbmdzLmVtaXQoJGV2ZW50KVwiPlxuICAgICAgICAgICAgICA8L2FwcC1yZXBvcnQtY29tcG9uZW50PlxuICAgICAgICAgICAgfVxuICAgICAgICAgIH0gQGVsc2Uge1xuICAgICAgICAgICAgQGZvciAoY29tcG9uZW50IG9mIHBhZ2UuY29tcG9uZW50czsgdHJhY2sgY29tcG9uZW50LmlkKSB7XG4gICAgICAgICAgICAgIDxhcHAtcmVwb3J0LWNvbXBvbmVudFxuICAgICAgICAgICAgICAgIFtyZXBvcnRJZF09XCJyZXBvcnQuaWRcIlxuICAgICAgICAgICAgICAgIFtjb21wb25lbnRdPVwiY29tcG9uZW50XCJcbiAgICAgICAgICAgICAgICBbZ3JvdXBzXT1cImdyb3Vwc1wiXG4gICAgICAgICAgICAgICAgW2VkaXRNb2RlXT1cImVkaXRNb2RlXCJcbiAgICAgICAgICAgICAgICBbbGF5b3V0XT1cIidmcmVlZm9ybSdcIlxuICAgICAgICAgICAgICAgIFt6b29tXT1cInpvb21cIlxuICAgICAgICAgICAgICAgIFtzbmFwcGVyXT1cInNuYXBwZXJcIlxuICAgICAgICAgICAgICAgIFtzZWxlY3RlZF09XCJjb21wb25lbnQuaWQgPT09IHNlbGVjdGVkQ29tcG9uZW50SWRcIlxuICAgICAgICAgICAgICAgIFtzdHlsZS5sZWZ0LnB4XT1cImNvbXBvbmVudC54ICogUFhcIlxuICAgICAgICAgICAgICAgIFtzdHlsZS50b3AucHhdPVwiY29tcG9uZW50LnkgKiBQWFwiXG4gICAgICAgICAgICAgICAgW3N0eWxlLndpZHRoLnB4XT1cImNvbXBvbmVudC53ICogUFhcIlxuICAgICAgICAgICAgICAgIFtzdHlsZS5oZWlnaHQucHhdPVwiY29tcG9uZW50LmF1dG9IZWlnaHQgPyBudWxsIDogY29tcG9uZW50LmggKiBQWFwiXG4gICAgICAgICAgICAgICAgKHNlbGVjdENvbXBvbmVudCk9XCJzZWxlY3RDb21wb25lbnQoJGV2ZW50KVwiXG4gICAgICAgICAgICAgICAgKHBvc2l0aW9uQ2hhbmdlZCk9XCJvblBvc2l0aW9uQ2hhbmdlZCgkZXZlbnQpXCJcbiAgICAgICAgICAgICAgICAob3BlblNldHRpbmdzKT1cImNvbXBvbmVudFNldHRpbmdzLmVtaXQoJGV2ZW50KVwiPlxuICAgICAgICAgICAgICA8L2FwcC1yZXBvcnQtY29tcG9uZW50PlxuICAgICAgICAgICAgfVxuICAgICAgICAgIH1cblxuICAgICAgICAgIDxkaXZcbiAgICAgICAgICAgICNndWlkZXNcbiAgICAgICAgICAgIGNsYXNzPVwiZ3VpZGVzXCI+XG4gICAgICAgICAgPC9kaXY+XG5cbiAgICAgICAgICBAaWYgKCFwYWdlLmNvbXBvbmVudHMubGVuZ3RoKSB7XG4gICAgICAgICAgICA8ZGl2IGNsYXNzPVwicGFnZS1lbXB0eVwiPlxuICAgICAgICAgICAgICBBc2sgdGhlIGFzc2lzdGFudCB0byBhZGQgYSBjaGFydCwgbGlzdCBvciBLUEkgdG8gdGhpcyBwYWdlLlxuICAgICAgICAgICAgPC9kaXY+XG4gICAgICAgICAgfVxuICAgICAgICA8L2Rpdj5cbiAgICAgIH1cbiAgICA8L2ZzLXpvb20tcGFuPlxuXG4gICAgQGlmIChlZGl0TW9kZSkge1xuICAgICAgPGJ1dHRvblxuICAgICAgICBtYXQtZmxhdC1idXR0b25cbiAgICAgICAgdHlwZT1cImJ1dHRvblwiXG4gICAgICAgIGNvbG9yPVwicHJpbWFyeVwiXG4gICAgICAgIGNsYXNzPVwiZWRpdC1kb25lXCJcbiAgICAgICAgbWF0VG9vbHRpcD1cIkV4aXQgbGF5b3V0IGVkaXRpbmdcIlxuICAgICAgICAoY2xpY2spPVwiZWRpdERvbmUuZW1pdCgpXCI+XG4gICAgICAgIDxtYXQtaWNvbj5jaGVjazwvbWF0LWljb24+XG4gICAgICAgIERvbmUgZWRpdGluZ1xuICAgICAgPC9idXR0b24+XG4gICAgfVxuICA8L2Rpdj5cblxuICA8ZGl2IGNsYXNzPVwiY2FudmFzLXRvb2xiYXJcIj5cbiAgICA8ZGl2IGNsYXNzPVwicGFnZS10YWJzXCI+XG4gICAgICBAaWYgKChyZXBvcnQ/LnBhZ2VzPy5sZW5ndGggPz8gMCkgPiAxKSB7XG4gICAgICAgIEBmb3IgKHBhZ2Ugb2YgcmVwb3J0LnBhZ2VzOyB0cmFjayBwYWdlLmlkOyBsZXQgaW5kZXggPSAkaW5kZXgpIHtcbiAgICAgICAgICA8YnV0dG9uXG4gICAgICAgICAgICB0eXBlPVwiYnV0dG9uXCJcbiAgICAgICAgICAgIGNsYXNzPVwicGFnZS10YWJcIlxuICAgICAgICAgICAgW2NsYXNzLmFjdGl2ZV09XCJpbmRleCA9PT0gYWN0aXZlUGFnZUluZGV4XCJcbiAgICAgICAgICAgIChjbGljayk9XCJzZWxlY3RQYWdlKGluZGV4KVwiPlxuICAgICAgICAgICAge3sgcGFnZUxhYmVsKHBhZ2UsIGluZGV4KSB9fVxuICAgICAgICAgIDwvYnV0dG9uPlxuICAgICAgICB9XG4gICAgICB9XG4gICAgICA8YnV0dG9uXG4gICAgICAgIHR5cGU9XCJidXR0b25cIlxuICAgICAgICBjbGFzcz1cInBhZ2UtdGFiIGFkZC1wYWdlXCJcbiAgICAgICAgbWF0VG9vbHRpcD1cIkFkZCBwYWdlXCJcbiAgICAgICAgKGNsaWNrKT1cImFkZFBhZ2UoKVwiPlxuICAgICAgICA8bWF0LWljb24+YWRkPC9tYXQtaWNvbj5cbiAgICAgICAgUGFnZVxuICAgICAgPC9idXR0b24+XG4gICAgPC9kaXY+XG5cbiAgICA8ZGl2IGNsYXNzPVwiem9vbS1jb250cm9sc1wiPlxuICAgICAgPGJ1dHRvblxuICAgICAgICB0eXBlPVwiYnV0dG9uXCJcbiAgICAgICAgY2xhc3M9XCJ6b29tLWJ1dHRvblwiXG4gICAgICAgIG1hdFRvb2x0aXA9XCJab29tIG91dFwiXG4gICAgICAgIChjbGljayk9XCJ6b29tT3V0KClcIj5cbiAgICAgICAgPG1hdC1pY29uPnJlbW92ZTwvbWF0LWljb24+XG4gICAgICA8L2J1dHRvbj5cbiAgICAgIDxidXR0b25cbiAgICAgICAgdHlwZT1cImJ1dHRvblwiXG4gICAgICAgIGNsYXNzPVwiem9vbS1sYWJlbFwiXG4gICAgICAgIG1hdFRvb2x0aXA9XCJab29tIHRvIDEwMCVcIlxuICAgICAgICAoY2xpY2spPVwiem9vbUFjdHVhbCgpXCI+XG4gICAgICAgIHt7ICh6b29tICogMTAwKS50b0ZpeGVkKDApIH19JVxuICAgICAgPC9idXR0b24+XG4gICAgICA8YnV0dG9uXG4gICAgICAgIHR5cGU9XCJidXR0b25cIlxuICAgICAgICBjbGFzcz1cInpvb20tYnV0dG9uXCJcbiAgICAgICAgbWF0VG9vbHRpcD1cIlpvb20gaW5cIlxuICAgICAgICAoY2xpY2spPVwiem9vbUluKClcIj5cbiAgICAgICAgPG1hdC1pY29uPmFkZDwvbWF0LWljb24+XG4gICAgICA8L2J1dHRvbj5cbiAgICAgIDxidXR0b25cbiAgICAgICAgdHlwZT1cImJ1dHRvblwiXG4gICAgICAgIGNsYXNzPVwiem9vbS1idXR0b25cIlxuICAgICAgICBtYXRUb29sdGlwPVwiRml0IHBhZ2VcIlxuICAgICAgICAoY2xpY2spPVwiem9vbUZpdCgpXCI+XG4gICAgICAgIDxtYXQtaWNvbj5maXRfc2NyZWVuPC9tYXQtaWNvbj5cbiAgICAgIDwvYnV0dG9uPlxuICAgIDwvZGl2PlxuICA8L2Rpdj5cbjwvZGl2PlxuIl19
|
|
461
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoicmVwb3J0LWNhbnZhcy5jb21wb25lbnQuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi8uLi8uLi9zcmMvYXBwL3JlcG9ydHMvY29tcG9uZW50cy9yZXBvcnQtY2FudmFzL3JlcG9ydC1jYW52YXMuY29tcG9uZW50LnRzIiwiLi4vLi4vLi4vLi4vLi4vLi4vc3JjL2FwcC9yZXBvcnRzL2NvbXBvbmVudHMvcmVwb3J0LWNhbnZhcy9yZXBvcnQtY2FudmFzLmNvbXBvbmVudC5odG1sIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBLE9BQU8sRUFDVSx1QkFBdUIsRUFBRSxpQkFBaUIsRUFBRSxTQUFTLEVBQUUsVUFBVSxFQUNoRixVQUFVLEVBQUUsWUFBWSxFQUFFLEtBQUssRUFBYSxNQUFNLEVBQUUsU0FBUyxFQUFFLFNBQVMsRUFBRSxZQUFZLEVBQUUsTUFBTSxHQUMvRixNQUFNLGVBQWUsQ0FBQztBQUN2QixPQUFPLEVBQUUsa0JBQWtCLEVBQUUsTUFBTSw0QkFBNEIsQ0FBQztBQUVoRSxPQUFPLEVBQWUsY0FBYyxFQUFFLGVBQWUsRUFBRSxNQUFNLHdCQUF3QixDQUFDO0FBQ3RGLE9BQU8sRUFBRSxTQUFTLEVBQUUsTUFBTSwwQkFBMEIsQ0FBQztBQUNyRCxPQUFPLEVBQUUsT0FBTyxFQUFFLE1BQU0sd0JBQXdCLENBQUM7QUFDakQsT0FBTyxFQUFFLFVBQVUsRUFBRSxNQUFNLDJCQUEyQixDQUFDO0FBRXZELE9BQU8sRUFBRSxZQUFZLEVBQUUsTUFBTSxrQkFBa0IsQ0FBQztBQUNoRCxPQUFPLEVBQUUsU0FBUyxFQUFFLE1BQU0scUJBQXFCLENBQUM7QUFDaEQsT0FBTyxFQUFFLFFBQVEsRUFBRSxNQUFNLG9CQUFvQixDQUFDO0FBQzlDLE9BQU8sRUFBRSxrQkFBa0IsRUFBRSxlQUFlLEVBQUUsTUFBTSxzQkFBc0IsQ0FBQztBQUUzRSxPQUFPLEVBQUUsR0FBRyxFQUFFLFNBQVMsRUFBRSxNQUFNLE1BQU0sQ0FBQztBQUV0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QmpDLFNBQVM7K0JBQ0UsbUJBQW1CLG1CQUdaLHVCQUF1QixDQUFDLE1BQU0sY0FDbkMsSUFBSSxXQUNQO3dCQUNQLGNBQWM7d0JBQ2QsU0FBUzt3QkFDVCxPQUFPO3dCQUNQLFVBQVU7d0JBQ1YsWUFBWTt3QkFDWixlQUFlO3dCQUNmLHdCQUF3QjtxQkFDekI7OEJBSWUsTUFBTTtzQkFBckIsS0FBSztnQkFDVSxRQUFRO3NCQUF2QixLQUFLO2dCQUtVLE1BQU07c0JBQXJCLEtBQUs7Z0JBSVcsaUJBQWlCO3NCQUFqQyxNQUFNO2dCQUlVLGFBQWE7c0JBQTdCLE1BQU07Z0JBSVUsUUFBUTtzQkFBeEIsTUFBTTtnQkFJVSxXQUFXO3NCQUEzQixNQUFNO2dCQUdBLE9BQU87c0JBRGIsU0FBUzt1QkFBQyxrQkFBa0I7Z0JBTXJCLG1CQUFtQjtzQkFEMUIsWUFBWTt1QkFBQyx3QkFBd0I7Z0JBSTlCLFNBQVM7c0JBRGhCLFNBQVM7dUJBQUMsVUFBVSxFQUFFLEVBQUUsTUFBTSxFQUFFLElBQUksRUFBRTtnQkFJL0IsT0FBTztzQkFEZCxTQUFTO3VCQUFDLFFBQVEsRUFBRSxFQUFFLE1BQU0sRUFBRSxLQUFLLEVBQUUiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQge1xuICBBZnRlclZpZXdJbml0LCBDaGFuZ2VEZXRlY3Rpb25TdHJhdGVneSwgQ2hhbmdlRGV0ZWN0b3JSZWYsIENvbXBvbmVudCwgRGVzdHJveVJlZixcbiAgRWxlbWVudFJlZiwgRXZlbnRFbWl0dGVyLCBJbnB1dCwgT25DaGFuZ2VzLCBPdXRwdXQsIFF1ZXJ5TGlzdCwgVmlld0NoaWxkLCBWaWV3Q2hpbGRyZW4sIGluamVjdCxcbn0gZnJvbSAnQGFuZ3VsYXIvY29yZSc7XG5pbXBvcnQgeyB0YWtlVW50aWxEZXN0cm95ZWQgfSBmcm9tICdAYW5ndWxhci9jb3JlL3J4anMtaW50ZXJvcCc7XG5cbmltcG9ydCB7IENka0RyYWdEcm9wLCBEcmFnRHJvcE1vZHVsZSwgbW92ZUl0ZW1JbkFycmF5IH0gZnJvbSAnQGFuZ3VsYXIvY2RrL2RyYWctZHJvcCc7XG5pbXBvcnQgeyBNYXRCdXR0b24gfSBmcm9tICdAYW5ndWxhci9tYXRlcmlhbC9idXR0b24nO1xuaW1wb3J0IHsgTWF0SWNvbiB9IGZyb20gJ0Bhbmd1bGFyL21hdGVyaWFsL2ljb24nO1xuaW1wb3J0IHsgTWF0VG9vbHRpcCB9IGZyb20gJ0Bhbmd1bGFyL21hdGVyaWFsL3Rvb2x0aXAnO1xuXG5pbXBvcnQgeyBGc01lbnVNb2R1bGUgfSBmcm9tICdAZmlyZXN0aXRjaC9tZW51JztcbmltcG9ydCB7IEZzTWVzc2FnZSB9IGZyb20gJ0BmaXJlc3RpdGNoL21lc3NhZ2UnO1xuaW1wb3J0IHsgRnNQcm9tcHQgfSBmcm9tICdAZmlyZXN0aXRjaC9wcm9tcHQnO1xuaW1wb3J0IHsgRnNab29tUGFuQ29tcG9uZW50LCBGc1pvb21QYW5Nb2R1bGUgfSBmcm9tICdAZmlyZXN0aXRjaC96b29tLXBhbic7XG5cbmltcG9ydCB7IG1hcCwgc3dpdGNoTWFwIH0gZnJvbSAncnhqcyc7XG5cbmltcG9ydCB7IFJlcG9ydERhdGEgfSBmcm9tICcuLi8uLi9kYXRhL3JlcG9ydC5kYXRhJztcbmltcG9ydCB7XG4gIENvbXBvbmVudFNldHRpbmdzLCBSZXBvcnQsIFJlcG9ydENvbXBvbmVudCwgUmVwb3J0RmlsdGVyR3JvdXAsIFJlcG9ydFBhZ2UsXG59IGZyb20gJy4uLy4uL2ludGVyZmFjZXMvcmVwb3J0LmludGVyZmFjZSc7XG5pbXBvcnQgeyBERUZBVUxUX0hFQURJTkdfU0laRSwgRkxPV19QQURESU5HIH0gZnJvbSAnLi4vLi4vbGF5b3V0JztcbmltcG9ydCB7IFJlcG9ydENvbXBvbmVudENvbXBvbmVudCB9IGZyb20gJy4uL3JlcG9ydC1jb21wb25lbnQvcmVwb3J0LWNvbXBvbmVudC5jb21wb25lbnQnO1xuXG5cbi8vIFNjcmVlbiBkZW5zaXR5IG9mIHRoZSBjYW52YXM6IDk2IENTUyBweCBwZXIgaW5jaCAodGhlIENTUyByZWZlcmVuY2UgcGl4ZWwpLFxuLy8gYmVmb3JlIHpvb20uIEFsbCBnZW9tZXRyeSBzdGF5cyBpbiBpbmNoZXM7IG9ubHkgcmVuZGVyaW5nIG11bHRpcGxpZXMgYnkgaXQuXG5leHBvcnQgY29uc3QgUFhfUEVSX0lOQ0ggPSA5NjtcblxuLy8gT25lIHNtYXJ0IGd1aWRlIGxpbmUsIGluIHBhZ2UgaW5jaGVzLlxuZXhwb3J0IGludGVyZmFjZSBHdWlkZUxpbmUge1xuICBvcmllbnRhdGlvbjogJ3YnIHwgJ2gnO1xuICBwb3NpdGlvbjogbnVtYmVyO1xufVxuXG4vLyBUaGUgc25hcHBpbmcgY29udHJhY3QgaGFuZGVkIHRvIGVhY2ggY29tcG9uZW50J3MgZHJhZyBsb29wLiBJbXBsZW1lbnRlZCBieVxuLy8gdGhlIGNhbnZhcyBiZWNhdXNlIG9ubHkgaXQgc2VlcyBldmVyeSBjb21wb25lbnQgKGFsaWdubWVudCBjYW5kaWRhdGVzKSBhbmRcbi8vIG93bnMgdGhlIGd1aWRlcyBvdmVybGF5LlxuZXhwb3J0IGludGVyZmFjZSBDYW52YXNTbmFwcGVyIHtcbiAgc25hcE1vdmUoY29tcG9uZW50OiBSZXBvcnRDb21wb25lbnQsIHg6IG51bWJlciwgeTogbnVtYmVyKTogeyB4OiBudW1iZXI7IHk6IG51bWJlciB9O1xuICBzbmFwUmVzaXplKGNvbXBvbmVudDogUmVwb3J0Q29tcG9uZW50LCBnZW9tZXRyeTogeyB4OiBudW1iZXI7IHk6IG51bWJlcjsgdzogbnVtYmVyOyBoOiBudW1iZXIgfSwgaGFuZGxlOiBzdHJpbmcpOiB7IHg6IG51bWJlcjsgeTogbnVtYmVyOyB3OiBudW1iZXI7IGg6IG51bWJlciB9O1xuICBjbGVhcigpOiB2b2lkO1xufVxuXG4vLyBUaGUgZml4ZWQtc2l6ZSBwYWdlIGNhbnZhcyDigJQgdGhlIFBvd2VyUG9pbnQgbW9kZWwuIFBhZ2VzIGFyZSB0YWJzIChvbmx5IHRoZVxuLy8gQUNUSVZFIHBhZ2UncyBjb21wb25lbnRzIGV4aXN0IOKGkiBvbmx5IHRoZXkgZmV0Y2gpOyB0aGUgcGFnZSBpcyBhXG4vLyBwYWdlV2lkdGjDl3BhZ2VIZWlnaHQgSU5DSEVTIHNoZWV0IHJlbmRlcmVkIGF0IDk2cHgvaW4gaW5zaWRlIGZzLXpvb20tcGFuXG4vLyAod2hlZWwgem9vbSwgYmFja2dyb3VuZCBkcmFnIHBhbiwgdG9vbGJhciBidXR0b25zKS5cbi8vXG4vLyBGcmVlZm9ybSBsYXlvdXQ6IGNvbXBvbmVudHMgYXJlIGFic29sdXRlbHkgcG9zaXRpb25lZDsgZHJhZ2dpbmcgZ2V0cyBzbWFydFxuLy8gYWxpZ25tZW50IGd1aWRlcyAoZWRnZXMgKyBjZW50ZXJzIG9mIHNpYmxpbmdzIGFuZCB0aGUgcGFnZSkgd2l0aCBzbmFwcGluZy5cbi8vIEZsb3cgbGF5b3V0OiBjb21wb25lbnRzIGZsb3cgaW50byByb3dzIChmbG93V2lkdGggJSBvZiB0aGUgY29udGVudCB3aWR0aCksXG4vLyBkcmFnIHJlb3JkZXJzLCBlYXN0L3NvdXRoIGhhbmRsZXMgcmVzaXplIHdpZHRoJS9oZWlnaHQuXG5AQ29tcG9uZW50KHtcbiAgc2VsZWN0b3I6ICdhcHAtcmVwb3J0LWNhbnZhcycsXG4gIHRlbXBsYXRlVXJsOiAnLi9yZXBvcnQtY2FudmFzLmNvbXBvbmVudC5odG1sJyxcbiAgc3R5bGVVcmxzOiBbJy4vcmVwb3J0LWNhbnZhcy5jb21wb25lbnQuc2NzcyddLFxuICBjaGFuZ2VEZXRlY3Rpb246IENoYW5nZURldGVjdGlvblN0cmF0ZWd5Lk9uUHVzaCxcbiAgc3RhbmRhbG9uZTogdHJ1ZSxcbiAgaW1wb3J0czogW1xuICAgIERyYWdEcm9wTW9kdWxlLFxuICAgIE1hdEJ1dHRvbixcbiAgICBNYXRJY29uLFxuICAgIE1hdFRvb2x0aXAsXG4gICAgRnNNZW51TW9kdWxlLFxuICAgIEZzWm9vbVBhbk1vZHVsZSxcbiAgICBSZXBvcnRDb21wb25lbnRDb21wb25lbnQsXG4gIF0sXG59KVxuZXhwb3J0IGNsYXNzIFJlcG9ydENhbnZhc0NvbXBvbmVudCBpbXBsZW1lbnRzIE9uQ2hhbmdlcywgQWZ0ZXJWaWV3SW5pdCB7XG5cbiAgQElucHV0KCkgcHVibGljIHJlcG9ydDogUmVwb3J0O1xuICBASW5wdXQoKSBwdWJsaWMgZWRpdE1vZGUgPSBmYWxzZTtcblxuICAvLyBUaGUgcGFnZSB0aGUgaG9zdCB3YW50cyBvbiBzY3JlZW4sIGJ5IHBhZ2UgaWQgKGEgZGVlcCBsaW5rKS4gS2V5ZWQgb24gaWRcbiAgLy8gcmF0aGVyIHRoYW4gaW5kZXggc28gYSBsaW5rIHN1cnZpdmVzIHBhZ2VzIGJlaW5nIHJlb3JkZXJlZCBvciBkZWxldGVkOyBhblxuICAvLyBpZCB0aGF0IG5vIGxvbmdlciByZXNvbHZlcyBmYWxscyBiYWNrIHRvIHRoZSBmaXJzdCBwYWdlLlxuICBASW5wdXQoKSBwdWJsaWMgcGFnZUlkOiBudW1iZXIgfCBudWxsID0gbnVsbDtcblxuICAvLyBBIGNvbXBvbmVudCBhc2tlZCBmb3IgaXRzIHNldHRpbmdzIGRpYWxvZyDigJQgdGhlIHBhZ2UtbGV2ZWwgaG9zdCBvcGVucyBpdFxuICAvLyAoaXQgb3ducyBNYXREaWFsb2cgKyB0aGUgcG9zdC1zYXZlIHJlbG9hZCkuXG4gIEBPdXRwdXQoKSBwdWJsaWMgY29tcG9uZW50U2V0dGluZ3MgPSBuZXcgRXZlbnRFbWl0dGVyPFJlcG9ydENvbXBvbmVudD4oKTtcblxuICAvLyBUaGUgcmVwb3J0J3Mgc3RydWN0dXJlIGNoYW5nZWQgaGVyZSAoYSBwYWdlIHdhcyBhZGRlZCkg4oCUIHRoZSBob3N0IHJlLWZldGNoZXNcbiAgLy8gaXQgKGl0IG93bnMgdGhlIGFzc2VtYmxlZCByZXBvcnQgKyBmaWx0ZXIgc3RhdGUpLlxuICBAT3V0cHV0KCkgcHVibGljIHJlcG9ydENoYW5nZWQgPSBuZXcgRXZlbnRFbWl0dGVyPHZvaWQ+KCk7XG5cbiAgLy8gVGhlIHZpZXdlciBkaXNtaXNzZWQgZWRpdCBtb2RlIGZyb20gdGhlIG9uLWNhbnZhcyBiYWRnZSDigJQgdGhlIGhvc3Qgb3ducyB0aGVcbiAgLy8gZWRpdE1vZGUgZmxhZywgc28gaXQgZmxpcHMgaXQgb2ZmIChtaXJyb3JzIHRoZSBtZW51J3MgXCJEb25lIGVkaXRpbmcgbGF5b3V0XCIpLlxuICBAT3V0cHV0KCkgcHVibGljIGVkaXREb25lID0gbmV3IEV2ZW50RW1pdHRlcjx2b2lkPigpO1xuXG4gIC8vIFRoZSBwYWdlIG9uIHNjcmVlbiBjaGFuZ2VkIOKAlCB0aGUgaG9zdCByZWZsZWN0cyBpdCBpbiB0aGUgVVJMIHNvIGEgcmVmcmVzaFxuICAvLyBjb21lcyBiYWNrIHRvIHRoZSBzYW1lIHBhZ2UuIENhcnJpZXMgdGhlIHBhZ2UgaWQsIG5ldmVyIHRoZSBpbmRleC5cbiAgQE91dHB1dCgpIHB1YmxpYyBwYWdlQ2hhbmdlZCA9IG5ldyBFdmVudEVtaXR0ZXI8bnVtYmVyIHwgbnVsbD4oKTtcblxuICBAVmlld0NoaWxkKEZzWm9vbVBhbkNvbXBvbmVudClcbiAgcHVibGljIHpvb21QYW46IEZzWm9vbVBhbkNvbXBvbmVudDtcblxuICAvLyBUaGUgcmVuZGVyZWQgY29tcG9uZW50cyBvZiB0aGUgYWN0aXZlIHBhZ2Ug4oCUIG9ubHkgdGhlIGNhbnZhcyBjYW4gcmVhY2ggdGhlXG4gIC8vIG9uZSBpbnN0YW5jZSBhIHNldHRpbmdzIHNhdmUgYXBwbGllcyB0by5cbiAgQFZpZXdDaGlsZHJlbihSZXBvcnRDb21wb25lbnRDb21wb25lbnQpXG4gIHByaXZhdGUgX3JlbmRlcmVkQ29tcG9uZW50czogUXVlcnlMaXN0PFJlcG9ydENvbXBvbmVudENvbXBvbmVudD47XG5cbiAgQFZpZXdDaGlsZCgndmlld3BvcnQnLCB7IHN0YXRpYzogdHJ1ZSB9KVxuICBwcml2YXRlIF92aWV3cG9ydDogRWxlbWVudFJlZjxIVE1MRGl2RWxlbWVudD47XG5cbiAgQFZpZXdDaGlsZCgnZ3VpZGVzJywgeyBzdGF0aWM6IGZhbHNlIH0pXG4gIHByaXZhdGUgX2d1aWRlczogRWxlbWVudFJlZjxIVE1MRGl2RWxlbWVudD47XG5cbiAgcHVibGljIHJlYWRvbmx5IFBYID0gUFhfUEVSX0lOQ0g7XG4gIHB1YmxpYyByZWFkb25seSBmbG93UGFkZGluZyA9IEZMT1dfUEFERElORztcblxuICBwdWJsaWMgYWN0aXZlUGFnZUluZGV4ID0gMDtcbiAgcHVibGljIHpvb20gPSAxO1xuICBwdWJsaWMgZ3JvdXBzID0gbmV3IE1hcDxudW1iZXIsIFJlcG9ydEZpbHRlckdyb3VwPigpO1xuICBwdWJsaWMgc2VsZWN0ZWRDb21wb25lbnRJZDogbnVtYmVyIHwgbnVsbCA9IG51bGw7XG5cbiAgLy8gVGhlIHNuYXBwZXIgaGFuZGVkIHRvIGV2ZXJ5IGNvbXBvbmVudCAoc3RhYmxlIGlkZW50aXR5IGZvciBPblB1c2gpLlxuICBwdWJsaWMgcmVhZG9ubHkgc25hcHBlcjogQ2FudmFzU25hcHBlciA9IHtcbiAgICBzbmFwTW92ZTogKGNvbXBvbmVudCwgeCwgeSkgPT4gdGhpcy5fc25hcE1vdmUoY29tcG9uZW50LCB4LCB5KSxcbiAgICBzbmFwUmVzaXplOiAoY29tcG9uZW50LCBnZW9tZXRyeSwgaGFuZGxlKSA9PiB0aGlzLl9zbmFwUmVzaXplKGNvbXBvbmVudCwgZ2VvbWV0cnksIGhhbmRsZSksXG4gICAgY2xlYXI6ICgpID0+IHRoaXMuX2NsZWFyR3VpZGVzKCksXG4gIH07XG5cbiAgcHJpdmF0ZSBfcmVwb3J0RGF0YSA9IGluamVjdChSZXBvcnREYXRhKTtcbiAgcHJpdmF0ZSBfcHJvbXB0ID0gaW5qZWN0KEZzUHJvbXB0KTtcbiAgcHJpdmF0ZSBfbWVzc2FnZSA9IGluamVjdChGc01lc3NhZ2UpO1xuICBwcml2YXRlIF9jZFJlZiA9IGluamVjdChDaGFuZ2VEZXRlY3RvclJlZik7XG4gIHByaXZhdGUgX2Rlc3Ryb3lSZWYgPSBpbmplY3QoRGVzdHJveVJlZik7XG4gIHByaXZhdGUgX2ZpdHRlZCA9IGZhbHNlO1xuICBwcml2YXRlIF9wcmV2aW91c1BhZ2VDb3VudCA9IDA7XG5cbiAgcHVibGljIG5nT25DaGFuZ2VzKCk6IHZvaWQge1xuICAgIHRoaXMuZ3JvdXBzID0gbmV3IE1hcCgodGhpcy5yZXBvcnQ/LmZpbHRlckdyb3VwcyA/PyBbXSkubWFwKChncm91cCkgPT4gW2dyb3VwLmlkLCBncm91cF0pKTtcblxuICAgIGNvbnN0IHBhZ2VDb3VudCA9IHRoaXMucmVwb3J0Py5wYWdlcz8ubGVuZ3RoID8/IDA7XG5cbiAgICAvLyBBIHBhZ2Ugd2FzIGp1c3QgYWRkZWQgKHRoZSBob3N0IHJlLWZldGNoZWQgdGhlIHJlcG9ydCkg4oCUIGxhbmQgb24gaXQuXG4gICAgY29uc3QgcGFnZUFkZGVkID0gcGFnZUNvdW50ID4gdGhpcy5fcHJldmlvdXNQYWdlQ291bnQgJiYgdGhpcy5fcHJldmlvdXNQYWdlQ291bnQgPiAwO1xuICAgIGlmIChwYWdlQWRkZWQpIHtcbiAgICAgIHRoaXMuYWN0aXZlUGFnZUluZGV4ID0gcGFnZUNvdW50IC0gMTtcbiAgICB9XG4gICAgdGhpcy5fcHJldmlvdXNQYWdlQ291bnQgPSBwYWdlQ291bnQ7XG5cbiAgICAvLyBIb25vdXIgYW4gaW5jb21pbmcgZGVlcCBsaW5rLCBidXQgbmV2ZXIgb3ZlciBhIGp1c3QtYWRkZWQgcGFnZTogYWRkaW5nIGFcbiAgICAvLyBwYWdlIGlzIGEgZGVsaWJlcmF0ZSBhY3QgaW4gdGhpcyB0YWIsIHdoaWxlIHBhZ2VJZCBpcyB0aGUgc3RhbGUgdmFsdWUgdGhlXG4gICAgLy8gaG9zdCBpcyBzdGlsbCBob2xkaW5nIGZyb20gdGhlIFVSTC4gQW4gaWQgdGhhdCBkb2VzIG5vdCByZXNvbHZlIGlzIGxlZnRcbiAgICAvLyBhbG9uZSByYXRoZXIgdGhhbiBmb3JjZWQgdG8gdGhlIGZpcnN0IHBhZ2Ug4oCUIHRoZSByZXBvcnQgbWF5IHN0aWxsIGJlXG4gICAgLy8gbG9hZGluZywgYW5kIHRoZSBjbGFtcCBiZWxvdyBpcyB0aGUgcmVhbCBndWFyZC5cbiAgICBpZiAoIXBhZ2VBZGRlZCAmJiB0aGlzLnBhZ2VJZCAhPSBudWxsKSB7XG4gICAgICBjb25zdCBpbmRleCA9IHRoaXMucmVwb3J0Py5wYWdlcz8uZmluZEluZGV4KChwYWdlKSA9PiBwYWdlLmlkID09PSB0aGlzLnBhZ2VJZCkgPz8gLTE7XG5cbiAgICAgIGlmIChpbmRleCA+IC0xKSB7XG4gICAgICAgIHRoaXMuYWN0aXZlUGFnZUluZGV4ID0gaW5kZXg7XG4gICAgICB9XG4gICAgfVxuXG4gICAgaWYgKHRoaXMuYWN0aXZlUGFnZUluZGV4ID49IHBhZ2VDb3VudCkge1xuICAgICAgdGhpcy5hY3RpdmVQYWdlSW5kZXggPSAwO1xuICAgIH1cbiAgfVxuXG4gIC8vIFJlcG9ydCBoZWFkaW5nIHNpemUgaW4gcHggKGNvbmZpZyBpcyBwb2ludHM7IHRoZSBjYW52YXMgcmVuZGVycyBhdFxuICAvLyA5NnB4L2luLCBzbyBwb2ludHMgw5cgOTYvNzIpLiBJbmhlcml0ZWQgYnkgY29tcG9uZW50IHRpdGxlcyB2aWEgYSBDU1MgdmFyLlxuICBwdWJsaWMgZ2V0IGhlYWRpbmdTaXplUHgoKTogbnVtYmVyIHtcbiAgICBjb25zdCBwb2ludHMgPSB0aGlzLnJlcG9ydD8uY29uZmlnPy5zdHlsZXM/LmhlYWRpbmc/LnNpemUgPz8gREVGQVVMVF9IRUFESU5HX1NJWkU7XG5cbiAgICByZXR1cm4gcG9pbnRzICogKFBYX1BFUl9JTkNIIC8gNzIpO1xuICB9XG5cbiAgcHVibGljIG5nQWZ0ZXJWaWV3SW5pdCgpOiB2b2lkIHtcbiAgICAvLyBGaXQgdGhlIHBhZ2UgdG8gdGhlIHZpZXdwb3J0IG9uY2Ugb24gZmlyc3QgcmVuZGVyOyBhZnRlciB0aGF0IHRoZVxuICAgIC8vIHZpZXdlcidzIHpvb20gY2hvaWNlIGlzIHJlc3BlY3RlZCBhY3Jvc3MgcmUtcmVuZGVycy5cbiAgICBzZXRUaW1lb3V0KCgpID0+IHRoaXMuem9vbUZpdCgpKTtcbiAgfVxuXG4gIHB1YmxpYyBnZXQgaXNGbG93KCk6IGJvb2xlYW4ge1xuICAgIHJldHVybiB0aGlzLnJlcG9ydD8ubGF5b3V0ID09PSAnZmxvdyc7XG4gIH1cblxuICBwdWJsaWMgZ2V0IGFjdGl2ZVBhZ2UoKTogUmVwb3J0UGFnZSB8IG51bGwge1xuICAgIHJldHVybiB0aGlzLnJlcG9ydD8ucGFnZXM/Llt0aGlzLmFjdGl2ZVBhZ2VJbmRleF0gPz8gbnVsbDtcbiAgfVxuXG4gIC8vIEZsb3cgcmVuZGVyIG9yZGVyICh0aGUgYXNzZW1ibGVyIGFscmVhZHkgc29ydHMsIGJ1dCBhIGxvY2FsIHJlb3JkZXJcbiAgLy8gbWlkLXNlc3Npb24gbXVzdCBob2xkIHdpdGhvdXQgYSByZS1mZXRjaCkuXG4gIHB1YmxpYyBnZXQgZmxvd0NvbXBvbmVudHMoKTogUmVwb3J0Q29tcG9uZW50W10ge1xuICAgIHJldHVybiBbLi4uKHRoaXMuYWN0aXZlUGFnZT8uY29tcG9uZW50cyA/PyBbXSldLnNvcnQoKGEsIGIpID0+IGEub3JkZXIgLSBiLm9yZGVyKTtcbiAgfVxuXG4gIHB1YmxpYyBzZWxlY3RQYWdlKGluZGV4OiBudW1iZXIpOiB2b2lkIHtcbiAgICB0aGlzLmFjdGl2ZVBhZ2VJbmRleCA9IGluZGV4O1xuICAgIHRoaXMuc2VsZWN0ZWRDb21wb25lbnRJZCA9IG51bGw7XG4gICAgdGhpcy5wYWdlQ2hhbmdlZC5lbWl0KHRoaXMuYWN0aXZlUGFnZT8uaWQgPz8gbnVsbCk7XG4gIH1cblxuICAvLyBBcHBlbmQgYSBibGFuayBwYWdlOyB0aGUgaG9zdCByZS1mZXRjaGVzIHRoZSByZXBvcnQgYW5kIG5nT25DaGFuZ2VzIGxhbmRzXG4gIC8vIHRoZSB2aWV3IG9uIHRoZSBuZXcgKGxhc3QpIHBhZ2UuXG4gIHB1YmxpYyBhZGRQYWdlKCk6IHZvaWQge1xuICAgIGlmICghdGhpcy5yZXBvcnQpIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICB0aGlzLl9yZXBvcnREYXRhLmFkZFBhZ2UodGhpcy5yZXBvcnQuaWQpXG4gICAgICAucGlwZSh0YWtlVW50aWxEZXN0cm95ZWQodGhpcy5fZGVzdHJveVJlZikpXG4gICAgICAuc3Vic2NyaWJlKCgpID0+IHRoaXMucmVwb3J0Q2hhbmdlZC5lbWl0KCkpO1xuICB9XG5cbiAgcHVibGljIHBhZ2VMYWJlbChwYWdlOiBSZXBvcnRQYWdlLCBpbmRleDogbnVtYmVyKTogc3RyaW5nIHtcbiAgICByZXR1cm4gcGFnZS5uYW1lIHx8IGBQYWdlICR7aW5kZXggKyAxfWA7XG4gIH1cblxuICAvLyBSZW5hbWUgZnJvbSB0aGUgdGFiJ3Mga2ViYWIuIFRoZSBwYWdlIGxpc3QgaXMgcGF0Y2hlZCBpbiBwbGFjZSByYXRoZXIgdGhhblxuICAvLyByZS1mZXRjaGluZyB0aGUgcmVwb3J0OiBub3RoaW5nIGVsc2Ugb24gdGhlIGNhbnZhcyBkZXBlbmRzIG9uIGEgcGFnZSdzXG4gIC8vIG5hbWUsIGFuZCBhIHJlLWZldGNoIHdvdWxkIHJlLXJ1biBldmVyeSBjb21wb25lbnQncyBxdWVyeSB0byByZXBhaW50IGFcbiAgLy8gY2hpcCdzIGxhYmVsLlxuICBwdWJsaWMgcmVuYW1lUGFnZShwYWdlOiBSZXBvcnRQYWdlKTogdm9pZCB7XG4gICAgdGhpcy5fcHJvbXB0LmlucHV0KHtcbiAgICAgIHRpdGxlOiAnRWRpdCBQYWdlIE5hbWUnLFxuICAgICAgbGFiZWw6ICdOYW1lJyxcbiAgICAgIGRlZmF1bHQ6IHBhZ2UubmFtZSA/PyAnJyxcbiAgICAgIGNvbW1pdExhYmVsOiAnU2F2ZScsXG4gICAgICByZXF1aXJlZDogdHJ1ZSxcbiAgICB9KVxuICAgICAgLnBpcGUoXG4gICAgICAgIHN3aXRjaE1hcCgobmFtZTogc3RyaW5nKSA9PiB0aGlzLl9yZXBvcnREYXRhXG4gICAgICAgICAgLnVwZGF0ZVBhZ2UodGhpcy5yZXBvcnQuaWQsIHBhZ2UuaWQsIG5hbWUpXG4gICAgICAgICAgLnBpcGUobWFwKCgpID0+IG5hbWUpKSksXG4gICAgICAgIHRha2VVbnRpbERlc3Ryb3llZCh0aGlzLl9kZXN0cm95UmVmKSxcbiAgICAgIClcbiAgICAgIC5zdWJzY3JpYmUoKG5hbWU6IHN0cmluZykgPT4ge1xuICAgICAgICBwYWdlLm5hbWUgPSBuYW1lO1xuICAgICAgICB0aGlzLl9tZXNzYWdlLnN1Y2Nlc3MoJ1NhdmVkIHBhZ2UgbmFtZScpO1xuICAgICAgICB0aGlzLl9jZFJlZi5tYXJrRm9yQ2hlY2soKTtcbiAgICAgIH0pO1xuICB9XG5cbiAgLy8gRGVsZXRlIGZyb20gdGhlIHRhYidzIGtlYmFiLiBUaGUgY29uZmlybSBuYW1lcyB0aGUgcGFnZSBhbmQgc2F5cyB0aGVcbiAgLy8gY29tcG9uZW50cyBnbyB3aXRoIGl0IOKAlCB0aGUgc2VydmVyIHJlZnVzZXMgdGhlIGxhc3QgcGFnZSwgYW5kIHRoYXQgcmVmdXNhbFxuICAvLyBzdXJmYWNlcyBhcyB0aGUgQVBJIGVycm9yIG1lc3NhZ2UgcmF0aGVyIHRoYW4gYmVpbmcgc2Vjb25kLWd1ZXNzZWQgaGVyZS5cbiAgcHVibGljIGRlbGV0ZVBhZ2UocGFnZTogUmVwb3J0UGFnZSk6IHZvaWQge1xuICAgIHRoaXMuX3Byb21wdC5jb25maXJtKHtcbiAgICAgIHRpdGxlOiAnQ29uZmlybScsXG4gICAgICB0ZW1wbGF0ZTogYEFyZSB5b3Ugc3VyZSB5b3Ugd291bGQgbGlrZSB0byBkZWxldGUgXCIke3RoaXMucGFnZUxhYmVsKHBhZ2UsIHRoaXMucmVwb3J0LnBhZ2VzLmluZGV4T2YocGFnZSkpfVwiIGFuZCBldmVyeXRoaW5nIG9uIGl0P2AsXG4gICAgfSlcbiAgICAgIC5waXBlKFxuICAgICAgICBzd2l0Y2hNYXAoKCkgPT4gdGhpcy5fcmVwb3J0RGF0YS5kZWxldGVQYWdlKHRoaXMucmVwb3J0LmlkLCBwYWdlLmlkKSksXG4gICAgICAgIHRha2VVbnRpbERlc3Ryb3llZCh0aGlzLl9kZXN0cm95UmVmKSxcbiAgICAgIClcbiAgICAgIC5zdWJzY3JpYmUoKCkgPT4ge1xuICAgICAgICBjb25zdCBpbmRleCA9IHRoaXMucmVwb3J0LnBhZ2VzLmluZGV4T2YocGFnZSk7XG4gICAgICAgIHRoaXMucmVwb3J0LnBhZ2VzLnNwbGljZShpbmRleCwgMSk7XG5cbiAgICAgICAgLy8gTGFuZCBvbiB0aGUgbmVpZ2hib3VyIHJhdGhlciB0aGFuIHNuYXBwaW5nIGJhY2sgdG8gdGhlIGZpcnN0IHBhZ2Ug4oCUXG4gICAgICAgIC8vIGRlbGV0aW5nIHBhZ2UgNCBvZiA2IHNob3VsZCBsZWF2ZSB5b3UgbG9va2luZyBhdCB3aGF0IGlzIG5vdyBwYWdlIDQuXG4gICAgICAgIHRoaXMuYWN0aXZlUGFnZUluZGV4ID0gTWF0aC5taW4oaW5kZXgsIHRoaXMucmVwb3J0LnBhZ2VzLmxlbmd0aCAtIDEpO1xuICAgICAgICB0aGlzLl9wcmV2aW91c1BhZ2VDb3VudCA9IHRoaXMucmVwb3J0LnBhZ2VzLmxlbmd0aDtcbiAgICAgICAgdGhpcy5zZWxlY3RlZENvbXBvbmVudElkID0gbnVsbDtcblxuICAgICAgICAvLyBUaGUgaWQgaW4gdGhlIFVSTCBqdXN0IHN0b3BwZWQgZXhpc3Rpbmcg4oCUIHJlcGxhY2UgaXQgd2l0aCB0aGVcbiAgICAgICAgLy8gbmVpZ2hib3VyIHdlIGxhbmRlZCBvbiwgb3IgYSByZWZyZXNoIHdvdWxkIDQwNCBpdHMgd2F5IHRvIHBhZ2Ugb25lLlxuICAgICAgICB0aGlzLnBhZ2VDaGFuZ2VkLmVtaXQodGhpcy5hY3RpdmVQYWdlPy5pZCA/PyBudWxsKTtcblxuICAgICAgICB0aGlzLl9tZXNzYWdlLnN1Y2Nlc3MoJ0RlbGV0ZWQgcGFnZScpO1xuICAgICAgICB0aGlzLl9jZFJlZi5tYXJrRm9yQ2hlY2soKTtcbiAgICAgIH0pO1xuICB9XG5cbiAgLy8gQSB0YWIgd2FzIGRyYWdnZWQgdG8gYSBuZXcgc2xvdDogcmVvcmRlciBsb2NhbGx5IHNvIHRoZSBjaGlwcyBzZXR0bGVcbiAgLy8gaW1tZWRpYXRlbHksIGtlZXAgdGhlIHZpZXdlciBvbiB0aGUgcGFnZSB0aGV5IHdlcmUgbG9va2luZyBhdCwgYW5kIHBlcnNpc3RcbiAgLy8gdGhlIHdob2xlIHNlcXVlbmNlIGluIG9uZSBQVVQuXG4gIHB1YmxpYyBvblBhZ2VEcm9wcGVkKGV2ZW50OiBDZGtEcmFnRHJvcDx1bmtub3duPik6IHZvaWQge1xuICAgIGlmIChldmVudC5wcmV2aW91c0luZGV4ID09PSBldmVudC5jdXJyZW50SW5kZXgpIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICBjb25zdCBhY3RpdmVQYWdlID0gdGhpcy5hY3RpdmVQYWdlO1xuXG4gICAgbW92ZUl0ZW1JbkFycmF5KHRoaXMucmVwb3J0LnBhZ2VzLCBldmVudC5wcmV2aW91c0luZGV4LCBldmVudC5jdXJyZW50SW5kZXgpO1xuXG4gICAgY29uc3QgcG9zaXRpb25zID0gdGhpcy5yZXBvcnQucGFnZXMubWFwKChwYWdlLCBvcmRlcikgPT4ge1xuICAgICAgcGFnZS5vcmRlciA9IG9yZGVyO1xuXG4gICAgICByZXR1cm4geyBwYWdlSWQ6IHBhZ2UuaWQsIG9yZGVyIH07XG4gICAgfSk7XG5cbiAgICB0aGlzLmFjdGl2ZVBhZ2VJbmRleCA9IGFjdGl2ZVBhZ2VcbiAgICAgID8gdGhpcy5yZXBvcnQucGFnZXMuaW5kZXhPZihhY3RpdmVQYWdlKVxuICAgICAgOiB0aGlzLmFjdGl2ZVBhZ2VJbmRleDtcblxuICAgIHRoaXMuX3JlcG9ydERhdGEuc2F2ZVBhZ2VQb3NpdGlvbnModGhpcy5yZXBvcnQuaWQsIHBvc2l0aW9ucylcbiAgICAgIC5waXBlKHRha2VVbnRpbERlc3Ryb3llZCh0aGlzLl9kZXN0cm95UmVmKSlcbiAgICAgIC5zdWJzY3JpYmUoKTtcbiAgfVxuXG4gIC8vIEhhbmQgcHJlc2VudGF0aW9uIHNldHRpbmdzICh0aXRsZSwgcGFkZGluZykgc2F2ZWQgaW4gdGhlIHNldHRpbmdzIGRpYWxvZyB0b1xuICAvLyB0aGUgb25lIGNvbXBvbmVudCB0aGV5IGJlbG9uZyB0by4gTm90aGluZyBoZXJlIGZlZWRzIHRoZSBxdWVyeSwgc28gdGhhdFxuICAvLyBjb21wb25lbnQgcmVwYWludHMgYW5kIGV2ZXJ5IG90aGVyIG9uZSBvbiB0aGUgcGFnZSBpcyBsZWZ0IGFsb25lLlxuICBwdWJsaWMgYXBwbHlDb21wb25lbnRTZXR0aW5ncyhjb21wb25lbnRJZDogbnVtYmVyLCBzZXR0aW5nczogQ29tcG9uZW50U2V0dGluZ3MpOiB2b2lkIHtcbiAgICB0aGlzLl9yZW5kZXJlZENvbXBvbmVudHNcbiAgICAgIC5maW5kKChyZW5kZXJlZCkgPT4gcmVuZGVyZWQuY29tcG9uZW50LmlkID09PSBjb21wb25lbnRJZClcbiAgICAgID8uYXBwbHlTZXR0aW5ncyhzZXR0aW5ncyk7XG4gIH1cblxuICBwdWJsaWMgc2VsZWN0Q29tcG9uZW50KGNvbXBvbmVudElkOiBudW1iZXIgfCBudWxsKTogdm9pZCB7XG4gICAgdGhpcy5zZWxlY3RlZENvbXBvbmVudElkID0gY29tcG9uZW50SWQ7XG4gICAgdGhpcy5fY2RSZWYubWFya0ZvckNoZWNrKCk7XG4gIH1cblxuICBwdWJsaWMgb25DYW52YXNQb2ludGVyRG93bigpOiB2b2lkIHtcbiAgICAvLyBCYWNrZ3JvdW5kIGNsaWNrIChwYW4gc3RhcnQpIGRlc2VsZWN0cy5cbiAgICBpZiAodGhpcy5zZWxlY3RlZENvbXBvbmVudElkICE9PSBudWxsKSB7XG4gICAgICB0aGlzLnNlbGVjdENvbXBvbmVudChudWxsKTtcbiAgICB9XG4gIH1cblxuICAvLyAtLS0tLSB6b29tIHRvb2xiYXIgLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG5cbiAgcHVibGljIG9uWm9vbWVkKHNjYWxlOiBudW1iZXIpOiB2b2lkIHtcbiAgICB0aGlzLnpvb20gPSBzY2FsZTtcbiAgICB0aGlzLl9jZFJlZi5tYXJrRm9yQ2hlY2soKTtcbiAgfVxuXG4gIHB1YmxpYyB6b29tSW4oKTogdm9pZCB7XG4gICAgdGhpcy56b29tUGFuPy56b29tSW4oKTtcbiAgfVxuXG4gIHB1YmxpYyB6b29tT3V0KCk6IHZvaWQge1xuICAgIHRoaXMuem9vbVBhbj8uem9vbU91dCgpO1xuICB9XG5cbiAgcHVibGljIHpvb21GaXQoKTogdm9pZCB7XG4gICAgY29uc3Qgdmlld3BvcnQgPSB0aGlzLl92aWV3cG9ydD8ubmF0aXZlRWxlbWVudDtcbiAgICBpZiAoIXZpZXdwb3J0IHx8ICF0aGlzLnJlcG9ydD8ucGFnZVdpZHRoIHx8ICF0aGlzLnpvb21QYW4pIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICBjb25zdCBmaXQgPSBNYXRoLm1pbihcbiAgICAgICh2aWV3cG9ydC5jbGllbnRXaWR0aCAtIDMyKSAvICh0aGlzLnJlcG9ydC5wYWdlV2lkdGggKiBQWF9QRVJfSU5DSCksXG4gICAgICAodmlld3BvcnQuY2xpZW50SGVpZ2h0IC0gMzIpIC8gKHRoaXMucmVwb3J0LnBhZ2VIZWlnaHQgKiBQWF9QRVJfSU5DSCksXG4gICAgKTtcblxuICAgIHRoaXMuem9vbVBhbi56b29tKE1hdGgubWluKDEuNSwgTWF0aC5tYXgoMC4xLCBmaXQpKSk7XG4gICAgdGhpcy56b29tUGFuLm1vdmUoMTYsIDE2KTtcbiAgICB0aGlzLl9maXR0ZWQgPSB0cnVlO1xuICB9XG5cbiAgcHVibGljIHpvb21BY3R1YWwoKTogdm9pZCB7XG4gICAgdGhpcy56b29tUGFuPy56b29tKDEpO1xuICB9XG5cbiAgLy8gLS0tLS0gcGVyc2lzdGVuY2UgLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLVxuXG4gIC8vIEEgZnJlZWZvcm0gZHJhZy9yZXNpemUgb3IgYSBmbG93IHdpZHRoIHJlc2l6ZSBsYW5kZWQg4oCUIG9uZSBQVVQgcGVyIGdlc3R1cmUuXG4gIHB1YmxpYyBvblBvc2l0aW9uQ2hhbmdlZChwb3NpdGlvbjogeyBjb21wb25lbnRJZDogbnVtYmVyIH0gJiBSZWNvcmQ8c3RyaW5nLCBudW1iZXI+KTogdm9pZCB7XG4gICAgdGhpcy5fY2xlYXJHdWlkZXMoKTtcbiAgICB0aGlzLl9yZXBvcnREYXRhLnNhdmVQb3NpdGlvbnModGhpcy5yZXBvcnQuaWQsIFtwb3NpdGlvbiBhcyBhbnldKVxuICAgICAgLnBpcGUodGFrZVVudGlsRGVzdHJveWVkKHRoaXMuX2Rlc3Ryb3lSZWYpKVxuICAgICAgLnN1YnNjcmliZSgpO1xuICB9XG5cbiAgLy8gQSBmbG93IGRyYWcgZHJvcHBlZDogcmVvcmRlciB0aGUgcGFnZSdzIGNvbXBvbmVudHMgYXJvdW5kIHRoZSBtb3ZlZCBvbmVcbiAgLy8gYW5kIHBlcnNpc3QgZXZlcnkgb3JkZXIgaW4gb25lIFBVVC5cbiAgcHVibGljIG9uRmxvd1Jlb3JkZXIoZXZlbnQ6IHsgY29tcG9uZW50SWQ6IG51bWJlcjsgY2xpZW50WDogbnVtYmVyOyBjbGllbnRZOiBudW1iZXIgfSk6IHZvaWQge1xuICAgIGNvbnN0IHBhZ2UgPSB0aGlzLmFjdGl2ZVBhZ2U7XG4gICAgaWYgKCFwYWdlKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgY29uc3Qgb3JkZXJlZCA9IHRoaXMuZmxvd0NvbXBvbmVudHMuZmlsdGVyKChjb21wb25lbnQpID0+IGNvbXBvbmVudC5pZCAhPT0gZXZlbnQuY29tcG9uZW50SWQpO1xuICAgIGNvbnN0IG1vdmVkID0gcGFnZS5jb21wb25lbnRzLmZpbmQoKGNvbXBvbmVudCkgPT4gY29tcG9uZW50LmlkID09PSBldmVudC5jb21wb25lbnRJZCk7XG4gICAgaWYgKCFtb3ZlZCkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIGNvbnN0IGluZGV4ID0gdGhpcy5fZmxvd0Ryb3BJbmRleChvcmRlcmVkLCBldmVudC5jbGllbnRYLCBldmVudC5jbGllbnRZKTtcbiAgICBvcmRlcmVkLnNwbGljZShpbmRleCwgMCwgbW92ZWQpO1xuXG4gICAgY29uc3QgcG9zaXRpb25zID0gb3JkZXJlZC5tYXAoKGNvbXBvbmVudCwgb3JkZXIpID0+IHtcbiAgICAgIGNvbXBvbmVudC5vcmRlciA9IG9yZGVyO1xuXG4gICAgICByZXR1cm4geyBjb21wb25lbnRJZDogY29tcG9uZW50LmlkLCBvcmRlciB9O1xuICAgIH0pO1xuXG4gICAgdGhpcy5fY2RSZWYubWFya0ZvckNoZWNrKCk7XG4gICAgdGhpcy5fcmVwb3J0RGF0YS5zYXZlUG9zaXRpb25zKHRoaXMucmVwb3J0LmlkLCBwb3NpdGlvbnMpXG4gICAgICAucGlwZSh0YWtlVW50aWxEZXN0cm95ZWQodGhpcy5fZGVzdHJveVJlZikpXG4gICAgICAuc3Vic2NyaWJlKCk7XG4gIH1cblxuICAvLyBXaGVyZSB0aGUgcG9pbnRlciBsYW5kZWQgYW1vbmcgdGhlIGZsb3dlZCBjb21wb25lbnRzOiBiZWZvcmUgdGhlIGZpcnN0XG4gIC8vIGNvbXBvbmVudCB3aG9zZSBjZW50ZXIgdGhlIHBvaW50ZXIgaXMgYWJvdmUvbGVmdCBvZi5cbiAgcHJpdmF0ZSBfZmxvd0Ryb3BJbmRleChvcmRlcmVkOiBSZXBvcnRDb21wb25lbnRbXSwgY2xpZW50WDogbnVtYmVyLCBjbGllbnRZOiBudW1iZXIpOiBudW1iZXIge1xuICAgIGNvbnN0IGhvc3RzID0gQXJyYXkuZnJvbShcbiAgICAgIHRoaXMuX3ZpZXdwb3J0Lm5hdGl2ZUVsZW1lbnQucXVlcnlTZWxlY3RvckFsbDxIVE1MRWxlbWVudD4oJ2FwcC1yZXBvcnQtY29tcG9uZW50JyksXG4gICAgKS5maWx0ZXIoKGhvc3QpID0+ICFob3N0LmNsYXNzTGlzdC5jb250YWlucygnZmxvdy1kcmFnZ2luZycpKTtcblxuICAgIGZvciAobGV0IGluZGV4ID0gMDsgaW5kZXggPCBob3N0cy5sZW5ndGggJiYgaW5kZXggPCBvcmRlcmVkLmxlbmd0aDsgaW5kZXgrKykge1xuICAgICAgY29uc3QgcmVjdCA9IGhvc3RzW2luZGV4XS5nZXRCb3VuZGluZ0NsaWVudFJlY3QoKTtcbiAgICAgIGlmIChjbGllbnRZIDwgcmVjdC50b3AgKyByZWN0LmhlaWdodCAvIDJcbiAgICAgICAgfHwgKGNsaWVudFkgPCByZWN0LmJvdHRvbSAmJiBjbGllbnRYIDwgcmVjdC5sZWZ0ICsgcmVjdC53aWR0aCAvIDIpKSB7XG4gICAgICAgIHJldHVybiBpbmRleDtcbiAgICAgIH1cbiAgICB9XG5cbiAgICByZXR1cm4gb3JkZXJlZC5sZW5ndGg7XG4gIH1cblxuICAvLyAtLS0tLSBzbWFydCBndWlkZXMgLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG5cbiAgLy8gUGl4ZWwgZmVlbCBvZiB0aGUgc25hcCwgY29udmVydGVkIHRvIGluY2hlcyBhdCB0aGUgY3VycmVudCB6b29tLlxuICBwcml2YXRlIGdldCBfc25hcFRocmVzaG9sZCgpOiBudW1iZXIge1xuICAgIHJldHVybiA4IC8gKFBYX1BFUl9JTkNIICogTWF0aC5tYXgoMC4xLCB0aGlzLnpvb20pKTtcbiAgfVxuXG4gIHByaXZhdGUgX3NuYXBNb3ZlKGNvbXBvbmVudDogUmVwb3J0Q29tcG9uZW50LCB4OiBudW1iZXIsIHk6IG51bWJlcik6IHsgeDogbnVtYmVyOyB5OiBudW1iZXIgfSB7XG4gICAgY29uc3QgeyB2ZXJ0aWNhbCwgaG9yaXpvbnRhbCB9ID0gdGhpcy5fY2FuZGlkYXRlcyhjb21wb25lbnQpO1xuICAgIGNvbnN0IGd1aWRlczogR3VpZGVMaW5lW10gPSBbXTtcblxuICAgIGNvbnN0IHNuYXBwZWRYID0gdGhpcy5fc25hcEF4aXMoXG4gICAgICBbXG4gICAgICAgIHsgb2Zmc2V0OiAwLCB2YWx1ZTogeCB9LFxuICAgICAgICB7IG9mZnNldDogY29tcG9uZW50LncgLyAyLCB2YWx1ZTogeCArIGNvbXBvbmVudC53IC8gMiB9LFxuICAgICAgICB7IG9mZnNldDogY29tcG9uZW50LncsIHZhbHVlOiB4ICsgY29tcG9uZW50LncgfSxcbiAgICAgIF0sXG4gICAgICB2ZXJ0aWNhbCxcbiAgICApO1xuICAgIGlmIChzbmFwcGVkWCAhPT0gbnVsbCkge1xuICAgICAgeCA9IHNuYXBwZWRYLmJhc2U7XG4gICAgICBndWlkZXMucHVzaCh7IG9yaWVudGF0aW9uOiAndicsIHBvc2l0aW9uOiBzbmFwcGVkWC5ndWlkZSB9KTtcbiAgICB9XG5cbiAgICBjb25zdCBzbmFwcGVkWSA9IHRoaXMuX3NuYXBBeGlzKFxuICAgICAgW1xuICAgICAgICB7IG9mZnNldDogMCwgdmFsdWU6IHkgfSxcbiAgICAgICAgeyBvZmZzZXQ6IGNvbXBvbmVudC5oIC8gMiwgdmFsdWU6IHkgKyBjb21wb25lbnQuaCAvIDIgfSxcbiAgICAgICAgeyBvZmZzZXQ6IGNvbXBvbmVudC5oLCB2YWx1ZTogeSArIGNvbXBvbmVudC5oIH0sXG4gICAgICBdLFxuICAgICAgaG9yaXpvbnRhbCxcbiAgICApO1xuICAgIGlmIChzbmFwcGVkWSAhPT0gbnVsbCkge1xuICAgICAgeSA9IHNuYXBwZWRZLmJhc2U7XG4gICAgICBndWlkZXMucHVzaCh7IG9yaWVudGF0aW9uOiAnaCcsIHBvc2l0aW9uOiBzbmFwcGVkWS5ndWlkZSB9KTtcbiAgICB9XG5cbiAgICB0aGlzLl9yZW5kZXJHdWlkZXMoZ3VpZGVzKTtcblxuICAgIHJldHVybiB7IHgsIHkgfTtcbiAgfVxuXG4gIHByaXZhdGUgX3NuYXBSZXNpemUoXG4gICAgY29tcG9uZW50OiBSZXBvcnRDb21wb25lbnQsXG4gICAgZ2VvbWV0cnk6IHsgeDogbnVtYmVyOyB5OiBudW1iZXI7IHc6IG51bWJlcjsgaDogbnVtYmVyIH0sXG4gICAgaGFuZGxlOiBzdHJpbmcsXG4gICk6IHsgeDogbnVtYmVyOyB5OiBudW1iZXI7IHc6IG51bWJlcjsgaDogbnVtYmVyIH0ge1xuICAgIGNvbnN0IHsgdmVydGljYWwsIGhvcml6b250YWwgfSA9IHRoaXMuX2NhbmRpZGF0ZXMoY29tcG9uZW50KTtcbiAgICBjb25zdCBndWlkZXM6IEd1aWRlTGluZVtdID0gW107XG4gICAgY29uc3QgcmVzdWx0ID0geyAuLi5nZW9tZXRyeSB9O1xuXG4gICAgLy8gT25seSB0aGUgZWRnZXMgdGhlIGhhbmRsZSBtb3ZlcyBwYXJ0aWNpcGF0ZSBpbiBzbmFwcGluZy5cbiAgICBpZiAoaGFuZGxlLmluY2x1ZGVzKCdlJykpIHtcbiAgICAgIGNvbnN0IHNuYXBwZWQgPSB0aGlzLl9uZWFyZXN0KGdlb21ldHJ5LnggKyBnZW9tZXRyeS53LCB2ZXJ0aWNhbCk7XG4gICAgICBpZiAoc25hcHBlZCAhPT0gbnVsbCkge1xuICAgICAgICByZXN1bHQudyA9IHNuYXBwZWQgLSBnZW9tZXRyeS54O1xuICAgICAgICBndWlkZXMucHVzaCh7IG9yaWVudGF0aW9uOiAndicsIHBvc2l0aW9uOiBzbmFwcGVkIH0pO1xuICAgICAgfVxuICAgIH1cbiAgICBpZiAoaGFuZGxlLmluY2x1ZGVzKCd3JykpIHtcbiAgICAgIGNvbnN0IHNuYXBwZWQgPSB0aGlzLl9uZWFyZXN0KGdlb21ldHJ5LngsIHZlcnRpY2FsKTtcbiAgICAgIGlmIChzbmFwcGVkICE9PSBudWxsKSB7XG4gICAgICAgIHJlc3VsdC53ID0gZ2VvbWV0cnkueCArIGdlb21ldHJ5LncgLSBzbmFwcGVkO1xuICAgICAgICByZXN1bHQueCA9IHNuYXBwZWQ7XG4gICAgICAgIGd1aWRlcy5wdXNoKHsgb3JpZW50YXRpb246ICd2JywgcG9zaXRpb246IHNuYXBwZWQgfSk7XG4gICAgICB9XG4gICAgfVxuICAgIGlmIChoYW5kbGUuaW5jbHVkZXMoJ3MnKSkge1xuICAgICAgY29uc3Qgc25hcHBlZCA9IHRoaXMuX25lYXJlc3QoZ2VvbWV0cnkueSArIGdlb21ldHJ5LmgsIGhvcml6b250YWwpO1xuICAgICAgaWYgKHNuYXBwZWQgIT09IG51bGwpIHtcbiAgICAgICAgcmVzdWx0LmggPSBzbmFwcGVkIC0gZ2VvbWV0cnkueTtcbiAgICAgICAgZ3VpZGVzLnB1c2goeyBvcmllbnRhdGlvbjogJ2gnLCBwb3NpdGlvbjogc25hcHBlZCB9KTtcbiAgICAgIH1cbiAgICB9XG4gICAgaWYgKGhhbmRsZS5pbmNsdWRlcygnbicpKSB7XG4gICAgICBjb25zdCBzbmFwcGVkID0gdGhpcy5fbmVhcmVzdChnZW9tZXRyeS55LCBob3Jpem9udGFsKTtcbiAgICAgIGlmIChzbmFwcGVkICE9PSBudWxsKSB7XG4gICAgICAgIHJlc3VsdC5oID0gZ2VvbWV0cnkueSArIGdlb21ldHJ5LmggLSBzbmFwcGVkO1xuICAgICAgICByZXN1bHQueSA9IHNuYXBwZWQ7XG4gICAgICAgIGd1aWRlcy5wdXNoKHsgb3JpZW50YXRpb246ICdoJywgcG9zaXRpb246IHNuYXBwZWQgfSk7XG4gICAgICB9XG4gICAgfVxuXG4gICAgdGhpcy5fcmVuZGVyR3VpZGVzKGd1aWRlcyk7XG5cbiAgICByZXR1cm4gcmVzdWx0O1xuICB9XG5cbiAgLy8gQWxpZ25tZW50IGNhbmRpZGF0ZXM6IHRoZSBwYWdlJ3MgZWRnZXMgKyBjZW50ZXIsIGFuZCBldmVyeSBzaWJsaW5nJ3NcbiAgLy8gZWRnZXMgKyBjZW50ZXJzLlxuICBwcml2YXRlIF9jYW5kaWRhdGVzKG1vdmluZzogUmVwb3J0Q29tcG9uZW50KTogeyB2ZXJ0aWNhbDogbnVtYmVyW107IGhvcml6b250YWw6IG51bWJlcltdIH0ge1xuICAgIGNvbnN0IHZlcnRpY2FsID0gWzAsIHRoaXMucmVwb3J0LnBhZ2VXaWR0aCAvIDIsIHRoaXMucmVwb3J0LnBhZ2VXaWR0aF07XG4gICAgY29uc3QgaG9yaXpvbnRhbCA9IFswLCB0aGlzLnJlcG9ydC5wYWdlSGVpZ2h0IC8gMiwgdGhpcy5yZXBvcnQucGFnZUhlaWdodF07XG5cbiAgICBmb3IgKGNvbnN0IGNvbXBvbmVudCBvZiB0aGlzLmFjdGl2ZVBhZ2U/LmNvbXBvbmVudHMgPz8gW10pIHtcbiAgICAgIGlmIChjb21wb25lbnQuaWQgPT09IG1vdmluZy5pZCkge1xuICAgICAgICBjb250aW51ZTtcbiAgICAgIH1cblxuICAgICAgdmVydGljYWwucHVzaChjb21wb25lbnQueCwgY29tcG9uZW50LnggKyBjb21wb25lbnQudyAvIDIsIGNvbXBvbmVudC54ICsgY29tcG9uZW50LncpO1xuICAgICAgaG9yaXpvbnRhbC5wdXNoKGNvbXBvbmVudC55LCBjb21wb25lbnQueSArIGNvbXBvbmVudC5oIC8gMiwgY29tcG9uZW50LnkgKyBjb21wb25lbnQuaCk7XG4gICAgfVxuXG4gICAgcmV0dXJuIHsgdmVydGljYWwsIGhvcml6b250YWwgfTtcbiAgfVxuXG4gIC8vIFNuYXAgb25lIGF4aXM6IG9mIHRoZSBtb3ZpbmcgYm94J3MgdGhyZWUgbGluZXMgKGVkZ2UvY2VudGVyL2VkZ2UpLCBmaW5kXG4gIC8vIHRoZSBjbG9zZXN0IGNhbmRpZGF0ZSB3aXRoaW4gdGhyZXNob2xkIGFuZCByZXR1cm4gdGhlIGFkanVzdGVkIGJhc2VcbiAgLy8gY29vcmRpbmF0ZSBwbHVzIHRoZSBndWlkZSB0byBkcmF3LlxuICBwcml2YXRlIF9zbmFwQXhpcyhcbiAgICBsaW5lczogeyBvZmZzZXQ6IG51bWJlcjsgdmFsdWU6IG51bWJlciB9W10sXG4gICAgY2FuZGlkYXRlczogbnVtYmVyW10sXG4gICk6IHsgYmFzZTogbnVtYmVyOyBndWlkZTogbnVtYmVyIH0gfCBudWxsIHtcbiAgICBsZXQgYmVzdDogeyBiYXNlOiBudW1iZXI7IGd1aWRlOiBudW1iZXI7IGRpc3RhbmNlOiBudW1iZXIgfSB8IG51bGwgPSBudWxsO1xuXG4gICAgZm9yIChjb25zdCBsaW5lIG9mIGxpbmVzKSB7XG4gICAgICBmb3IgKGNvbnN0IGNhbmRpZGF0ZSBvZiBjYW5kaWRhdGVzKSB7XG4gICAgICAgIGNvbnN0IGRpc3RhbmNlID0gTWF0aC5hYnMoY2FuZGlkYXRlIC0gbGluZS52YWx1ZSk7XG4gICAgICAgIGlmIChkaXN0YW5jZSA8PSB0aGlzLl9zbmFwVGhyZXNob2xkICYmICghYmVzdCB8fCBkaXN0YW5jZSA8IGJlc3QuZGlzdGFuY2UpKSB7XG4gICAgICAgICAgYmVzdCA9IHsgYmFzZTogY2FuZGlkYXRlIC0gbGluZS5vZmZzZXQsIGd1aWRlOiBjYW5kaWRhdGUsIGRpc3RhbmNlIH07XG4gICAgICAgIH1cbiAgICAgIH1cbiAgICB9XG5cbiAgICByZXR1cm4gYmVzdCA/IHsgYmFzZTogYmVzdC5iYXNlLCBndWlkZTogYmVzdC5ndWlkZSB9IDogbnVsbDtcbiAgfVxuXG4gIHByaXZhdGUgX25lYXJlc3QodmFsdWU6IG51bWJlciwgY2FuZGlkYXRlczogbnVtYmVyW10pOiBudW1iZXIgfCBudWxsIHtcbiAgICBsZXQgYmVzdDogbnVtYmVyIHwgbnVsbCA9IG51bGw7XG4gICAgbGV0IGJlc3REaXN0YW5jZSA9IHRoaXMuX3NuYXBUaHJlc2hvbGQ7XG5cbiAgICBmb3IgKGNvbnN0IGNhbmRpZGF0ZSBvZiBjYW5kaWRhdGVzKSB7XG4gICAgICBjb25zdCBkaXN0YW5jZSA9IE1hdGguYWJzKGNhbmRpZGF0ZSAtIHZhbHVlKTtcbiAgICAgIGlmIChkaXN0YW5jZSA8PSBiZXN0RGlzdGFuY2UpIHtcbiAgICAgICAgYmVzdCA9IGNhbmRpZGF0ZTtcbiAgICAgICAgYmVzdERpc3RhbmNlID0gZGlzdGFuY2U7XG4gICAgICB9XG4gICAgfVxuXG4gICAgcmV0dXJuIGJlc3Q7XG4gIH1cblxuICAvLyBUaGUgZ3VpZGVzIG92ZXJsYXkgaXMgZHJhd24gaW1wZXJhdGl2ZWx5IOKAlCB0aGUgZHJhZyBsb29wIHJ1bnMgb3V0c2lkZVxuICAvLyBBbmd1bGFyIGFuZCByZXBhaW50cyBvbiBldmVyeSBwb2ludGVybW92ZS5cbiAgcHJpdmF0ZSBfcmVuZGVyR3VpZGVzKGd1aWRlczogR3VpZGVMaW5lW10pOiB2b2lkIHtcbiAgICBjb25zdCBob3N0ID0gdGhpcy5fZ3VpZGVzPy5uYXRpdmVFbGVtZW50O1xuICAgIGlmICghaG9zdCkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIGhvc3QucmVwbGFjZUNoaWxkcmVuKC4uLmd1aWRlcy5tYXAoKGd1aWRlKSA9PiB7XG4gICAgICBjb25zdCBsaW5lID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnZGl2Jyk7XG4gICAgICBsaW5lLmNsYXNzTmFtZSA9IGBndWlkZSBndWlkZS0ke2d1aWRlLm9yaWVudGF0aW9ufWA7XG4gICAgICBpZiAoZ3VpZGUub3JpZW50YXRpb24gPT09ICd2Jykge1xuICAgICAgICBsaW5lLnN0eWxlLmxlZnQgPSBgJHtndWlkZS5wb3NpdGlvbiAqIFBYX1BFUl9JTkNIfXB4YDtcbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIGxpbmUuc3R5bGUudG9wID0gYCR7Z3VpZGUucG9zaXRpb24gKiBQWF9QRVJfSU5DSH1weGA7XG4gICAgICB9XG5cbiAgICAgIHJldHVybiBsaW5lO1xuICAgIH0pKTtcbiAgfVxuXG4gIHByaXZhdGUgX2NsZWFyR3VpZGVzKCk6IHZvaWQge1xuICAgIHRoaXMuX2d1aWRlcz8ubmF0aXZlRWxlbWVudD8ucmVwbGFjZUNoaWxkcmVuKCk7XG4gIH1cbn1cbiIsIjxkaXYgY2xhc3M9XCJjYW52YXNcIj5cbiAgPGRpdlxuICAgICN2aWV3cG9ydFxuICAgIGNsYXNzPVwicGFnZS12aWV3cG9ydFwiXG4gICAgKHBvaW50ZXJkb3duKT1cIm9uQ2FudmFzUG9pbnRlckRvd24oKVwiPlxuICAgIDxmcy16b29tLXBhblxuICAgICAgW3pvb21NaW5dPVwiMC4xXCJcbiAgICAgIFt6b29tTWF4XT1cIjNcIlxuICAgICAgKHpvb21lZCk9XCJvblpvb21lZCgkZXZlbnQpXCI+XG4gICAgICBAaWYgKGFjdGl2ZVBhZ2U7IGFzIHBhZ2UpIHtcbiAgICAgICAgPGRpdlxuICAgICAgICAgIGNsYXNzPVwicGFnZVwiXG4gICAgICAgICAgW2NsYXNzLmZsb3ddPVwiaXNGbG93XCJcbiAgICAgICAgICBbY2xhc3MuZWRpdGluZ109XCJlZGl0TW9kZVwiXG4gICAgICAgICAgW3N0eWxlLndpZHRoLnB4XT1cInJlcG9ydC5wYWdlV2lkdGggKiBQWFwiXG4gICAgICAgICAgW3N0eWxlLmhlaWdodC5weF09XCJyZXBvcnQucGFnZUhlaWdodCAqIFBYXCJcbiAgICAgICAgICBbc3R5bGUucGFkZGluZy5weF09XCJpc0Zsb3cgPyBmbG93UGFkZGluZyAqIFBYIDogMFwiXG4gICAgICAgICAgW3N0eWxlLi0tY2FudmFzLXpvb21dPVwiem9vbVwiXG4gICAgICAgICAgW3N0eWxlLi0tcmVwb3J0LWhlYWRpbmctc2l6ZS5weF09XCJoZWFkaW5nU2l6ZVB4XCI+XG4gICAgICAgICAgQGlmIChpc0Zsb3cpIHtcbiAgICAgICAgICAgIEBmb3IgKGNvbXBvbmVudCBvZiBmbG93Q29tcG9uZW50czsgdHJhY2sgY29tcG9uZW50LmlkKSB7XG4gICAgICAgICAgICAgIDxhcHAtcmVwb3J0LWNvbXBvbmVudFxuICAgICAgICAgICAgICAgIGNsYXNzPVwiZmxvdy1pdGVtXCJcbiAgICAgICAgICAgICAgICBbcmVwb3J0SWRdPVwicmVwb3J0LmlkXCJcbiAgICAgICAgICAgICAgICBbY29tcG9uZW50XT1cImNvbXBvbmVudFwiXG4gICAgICAgICAgICAgICAgW2dyb3Vwc109XCJncm91cHNcIlxuICAgICAgICAgICAgICAgIFtlZGl0TW9kZV09XCJlZGl0TW9kZVwiXG4gICAgICAgICAgICAgICAgW2xheW91dF09XCInZmxvdydcIlxuICAgICAgICAgICAgICAgIFt6b29tXT1cInpvb21cIlxuICAgICAgICAgICAgICAgIFtzbmFwcGVyXT1cInNuYXBwZXJcIlxuICAgICAgICAgICAgICAgIFtzZWxlY3RlZF09XCJjb21wb25lbnQuaWQgPT09IHNlbGVjdGVkQ29tcG9uZW50SWRcIlxuICAgICAgICAgICAgICAgIFtzdHlsZS53aWR0aC4lXT1cImNvbXBvbmVudC5mbG93V2lkdGhcIlxuICAgICAgICAgICAgICAgIFtzdHlsZS5oZWlnaHQucHhdPVwiY29tcG9uZW50LmF1dG9IZWlnaHQgPyBudWxsIDogY29tcG9uZW50LmggKiBQWFwiXG4gICAgICAgICAgICAgICAgKHNlbGVjdENvbXBvbmVudCk9XCJzZWxlY3RDb21wb25lbnQoJGV2ZW50KVwiXG4gICAgICAgICAgICAgICAgKHBvc2l0aW9uQ2hhbmdlZCk9XCJvblBvc2l0aW9uQ2hhbmdlZCgkZXZlbnQpXCJcbiAgICAgICAgICAgICAgICAoZmxvd1Jlb3JkZXIpPVwib25GbG93UmVvcmRlcigkZXZlbnQpXCJcbiAgICAgICAgICAgICAgICAob3BlblNldHRpbmdzKT1cImNvbXBvbmVudFNldHRpbmdzLmVtaXQoJGV2ZW50KVwiPlxuICAgICAgICAgICAgICA8L2FwcC1yZXBvcnQtY29tcG9uZW50PlxuICAgICAgICAgICAgfVxuICAgICAgICAgIH0gQGVsc2Uge1xuICAgICAgICAgICAgQGZvciAoY29tcG9uZW50IG9mIHBhZ2UuY29tcG9uZW50czsgdHJhY2sgY29tcG9uZW50LmlkKSB7XG4gICAgICAgICAgICAgIDxhcHAtcmVwb3J0LWNvbXBvbmVudFxuICAgICAgICAgICAgICAgIFtyZXBvcnRJZF09XCJyZXBvcnQuaWRcIlxuICAgICAgICAgICAgICAgIFtjb21wb25lbnRdPVwiY29tcG9uZW50XCJcbiAgICAgICAgICAgICAgICBbZ3JvdXBzXT1cImdyb3Vwc1wiXG4gICAgICAgICAgICAgICAgW2VkaXRNb2RlXT1cImVkaXRNb2RlXCJcbiAgICAgICAgICAgICAgICBbbGF5b3V0XT1cIidmcmVlZm9ybSdcIlxuICAgICAgICAgICAgICAgIFt6b29tXT1cInpvb21cIlxuICAgICAgICAgICAgICAgIFtzbmFwcGVyXT1cInNuYXBwZXJcIlxuICAgICAgICAgICAgICAgIFtzZWxlY3RlZF09XCJjb21wb25lbnQuaWQgPT09IHNlbGVjdGVkQ29tcG9uZW50SWRcIlxuICAgICAgICAgICAgICAgIFtzdHlsZS5sZWZ0LnB4XT1cImNvbXBvbmVudC54ICogUFhcIlxuICAgICAgICAgICAgICAgIFtzdHlsZS50b3AucHhdPVwiY29tcG9uZW50LnkgKiBQWFwiXG4gICAgICAgICAgICAgICAgW3N0eWxlLndpZHRoLnB4XT1cImNvbXBvbmVudC53ICogUFhcIlxuICAgICAgICAgICAgICAgIFtzdHlsZS5oZWlnaHQucHhdPVwiY29tcG9uZW50LmF1dG9IZWlnaHQgPyBudWxsIDogY29tcG9uZW50LmggKiBQWFwiXG4gICAgICAgICAgICAgICAgKHNlbGVjdENvbXBvbmVudCk9XCJzZWxlY3RDb21wb25lbnQoJGV2ZW50KVwiXG4gICAgICAgICAgICAgICAgKHBvc2l0aW9uQ2hhbmdlZCk9XCJvblBvc2l0aW9uQ2hhbmdlZCgkZXZlbnQpXCJcbiAgICAgICAgICAgICAgICAob3BlblNldHRpbmdzKT1cImNvbXBvbmVudFNldHRpbmdzLmVtaXQoJGV2ZW50KVwiPlxuICAgICAgICAgICAgICA8L2FwcC1yZXBvcnQtY29tcG9uZW50PlxuICAgICAgICAgICAgfVxuICAgICAgICAgIH1cblxuICAgICAgICAgIDxkaXZcbiAgICAgICAgICAgICNndWlkZXNcbiAgICAgICAgICAgIGNsYXNzPVwiZ3VpZGVzXCI+XG4gICAgICAgICAgPC9kaXY+XG5cbiAgICAgICAgICBAaWYgKCFwYWdlLmNvbXBvbmVudHMubGVuZ3RoKSB7XG4gICAgICAgICAgICA8ZGl2IGNsYXNzPVwicGFnZS1lbXB0eVwiPlxuICAgICAgICAgICAgICBBc2sgdGhlIGFzc2lzdGFudCB0byBhZGQgYSBjaGFydCwgbGlzdCBvciBLUEkgdG8gdGhpcyBwYWdlLlxuICAgICAgICAgICAgPC9kaXY+XG4gICAgICAgICAgfVxuICAgICAgICA8L2Rpdj5cbiAgICAgIH1cbiAgICA8L2ZzLXpvb20tcGFuPlxuXG4gICAgQGlmIChlZGl0TW9kZSkge1xuICAgICAgPGJ1dHRvblxuICAgICAgICBtYXQtZmxhdC1idXR0b25cbiAgICAgICAgdHlwZT1cImJ1dHRvblwiXG4gICAgICAgIGNvbG9yPVwicHJpbWFyeVwiXG4gICAgICAgIGNsYXNzPVwiZWRpdC1kb25lXCJcbiAgICAgICAgbWF0VG9vbHRpcD1cIkV4aXQgbGF5b3V0IGVkaXRpbmdcIlxuICAgICAgICAoY2xpY2spPVwiZWRpdERvbmUuZW1pdCgpXCI+XG4gICAgICAgIDxtYXQtaWNvbj5jaGVjazwvbWF0LWljb24+XG4gICAgICAgIERvbmUgZWRpdGluZ1xuICAgICAgPC9idXR0b24+XG4gICAgfVxuICA8L2Rpdj5cblxuICA8ZGl2IGNsYXNzPVwiY2FudmFzLXRvb2xiYXJcIj5cbiAgICA8IS0tIFRhYnMgYXJlIG9uZSBob3Jpem9udGFsIGRyb3AgbGlzdDogZHJhZ2dpbmcgYSBjaGlwIHJlb3JkZXJzIHRoZSBwYWdlcy5cbiAgICAgICAgIFRoZSBkcm9wIElOREVYIGlzIGNvbXB1dGVkIGFsb25nIFggKG9yaWVudGF0aW9uKSwgYnV0IHRoZSBwcmV2aWV3IGlzXG4gICAgICAgICBkZWxpYmVyYXRlbHkgbGVmdCB1bmJvdW5kZWQgb24gYm90aCBheGVzIOKAlCBwaW5uaW5nIGl0IHRvIHRoZSByb3cgd2l0aFxuICAgICAgICAgY2RrRHJhZ0JvdW5kYXJ5IG1lYW5zIHRoZSBjaGlwIHlvdSBhcmUgZHJhZ2dpbmcgY292ZXJzIHRoZSBjaGlwcyB5b3VcbiAgICAgICAgIGFyZSBkcmFnZ2luZyBpdCBwYXN0LCBhbmQgeW91IGNhbm5vdCBzZWUgd2hlcmUgaXQgaXMgZ29pbmcgdG8gbGFuZC4gLS0+XG4gICAgPGRpdlxuICAgICAgY2xhc3M9XCJwYWdlLXRhYnNcIlxuICAgICAgY2RrRHJvcExpc3RcbiAgICAgIGNka0Ryb3BMaXN0T3JpZW50YXRpb249XCJob3Jpem9udGFsXCJcbiAgICAgIChjZGtEcm9wTGlzdERyb3BwZWQpPVwib25QYWdlRHJvcHBlZCgkZXZlbnQpXCI+XG4gICAgICBAaWYgKChyZXBvcnQ/LnBhZ2VzPy5sZW5ndGggPz8gMCkgPiAxKSB7XG4gICAgICAgIEBmb3IgKHBhZ2Ugb2YgcmVwb3J0LnBhZ2VzOyB0cmFjayBwYWdlLmlkOyBsZXQgaW5kZXggPSAkaW5kZXgpIHtcbiAgICAgICAgICA8IS0tIFRoZSBjaGlwIGlzIHRoZSBkcmFnIGhhbmRsZSBBTkQgdGhlIHRhYjogY2xpY2tpbmcgc2VsZWN0cyxcbiAgICAgICAgICAgICAgIGRyYWdnaW5nIHJlb3JkZXJzLiBUaGUga2ViYWIgbGl2ZXMgaW5zaWRlIGl0LCBzbyB0aGUgd2hvbGVcbiAgICAgICAgICAgICAgIGNvbnRyb2wgc3RheXMgb25lIGNoaXAgaW5zdGVhZCBvZiBncm93aW5nIGEgc2Vjb25kIGJ1dHRvbi4gLS0+XG4gICAgICAgICAgPGRpdlxuICAgICAgICAgICAgY2RrRHJhZ1xuICAgICAgICAgICAgY2xhc3M9XCJwYWdlLXRhYlwiXG4gICAgICAgICAgICBbY2xhc3MuYWN0aXZlXT1cImluZGV4ID09PSBhY3RpdmVQYWdlSW5kZXhcIlxuICAgICAgICAgICAgKGNsaWNrKT1cInNlbGVjdFBhZ2UoaW5kZXgpXCI+XG4gICAgICAgICAgICA8c3BhbiBjbGFzcz1cInBhZ2UtdGFiLWxhYmVsXCI+e3sgcGFnZUxhYmVsKHBhZ2UsIGluZGV4KSB9fTwvc3Bhbj5cbiAgICAgICAgICAgIDwhLS0gVGhlIGtlYmFiIG9wZW5zIHRoZSBtZW51IHJhdGhlciB0aGFuIHN0YXJ0aW5nIGEgZHJhZyBvclxuICAgICAgICAgICAgICAgICBzd2l0Y2hpbmcgcGFnZXMsIHNvIGl0IHN3YWxsb3dzIGl0cyBvd24gY2xpY2suIC0tPlxuICAgICAgICAgICAgPHNwYW5cbiAgICAgICAgICAgICAgY2xhc3M9XCJwYWdlLXRhYi1tZW51XCJcbiAgICAgICAgICAgICAgW2ZzTWVudVRyaWdnZXJGb3JdPVwicGFnZU1lbnVcIlxuICAgICAgICAgICAgICAoY2xpY2spPVwiJGV2ZW50LnN0b3BQcm9wYWdhdGlvbigpXCJcbiAgICAgICAgICAgICAgKG1vdXNlZG93bik9XCIkZXZlbnQuc3RvcFByb3BhZ2F0aW9uKClcIj5cbiAgICAgICAgICAgICAgPG1hdC1pY29uPm1vcmVfdmVydDwvbWF0LWljb24+XG4gICAgICAgICAgICA8L3NwYW4+XG4gICAgICAgICAgPC9kaXY+XG4gICAgICAgICAgPCEtLSBPdXRzaWRlIHRoZSBjaGlwOiBjZGtEcmFnIGNsb25lcyBpdHMgaG9zdCBpbnRvIHRoZSBkcmFnIHByZXZpZXcsXG4gICAgICAgICAgICAgICBhbmQgYSBtZW51IG92ZXJsYXkgYW5jaG9yZWQgdG8gYSBjbG9uZWQgdHJpZ2dlciBvcGVucyBkZXRhY2hlZFxuICAgICAgICAgICAgICAgZnJvbSB0aGUgcmVhbCB0YWIuIC0tPlxuICAgICAgICAgIDxmcy1tZW51ICNwYWdlTWVudT5cbiAgICAgICAgICAgIDxuZy10ZW1wbGF0ZVxuICAgICAgICAgICAgICBmcy1tZW51LWl0ZW1cbiAgICAgICAgICAgICAgKGNsaWNrKT1cInJlbmFtZVBhZ2UocGFnZSlcIj5cbiAgICAgICAgICAgICAgRWRpdCBuYW1lXG4gICAgICAgICAgICA8L25nLXRlbXBsYXRlPlxuICAgICAgICAgICAgPG5nLXRlbXBsYXRlXG4gICAgICAgICAgICAgIGZzLW1lbnUtaXRlbVxuICAgICAgICAgICAgICAoY2xpY2spPVwiZGVsZXRlUGFnZShwYWdlKVwiPlxuICAgICAgICAgICAgICBEZWxldGVcbiAgICAgICAgICAgIDwvbmctdGVtcGxhdGU+XG4gICAgICAgICAgPC9mcy1tZW51PlxuICAgICAgICB9XG4gICAgICB9XG4gICAgICA8YnV0dG9uXG4gICAgICAgIHR5cGU9XCJidXR0b25cIlxuICAgICAgICBjbGFzcz1cInBhZ2UtdGFiIGFkZC1wYWdlXCJcbiAgICAgICAgbWF0VG9vbHRpcD1cIkFkZCBwYWdlXCJcbiAgICAgICAgKGNsaWNrKT1cImFkZFBhZ2UoKVwiPlxuICAgICAgICA8bWF0LWljb24+YWRkPC9tYXQtaWNvbj5cbiAgICAgICAgUGFnZVxuICAgICAgPC9idXR0b24+XG4gICAgPC9kaXY+XG5cbiAgICA8ZGl2IGNsYXNzPVwiem9vbS1jb250cm9sc1wiPlxuICAgICAgPGJ1dHRvblxuICAgICAgICB0eXBlPVwiYnV0dG9uXCJcbiAgICAgICAgY2xhc3M9XCJ6b29tLWJ1dHRvblwiXG4gICAgICAgIG1hdFRvb2x0aXA9XCJab29tIG91dFwiXG4gICAgICAgIChjbGljayk9XCJ6b29tT3V0KClcIj5cbiAgICAgICAgPG1hdC1pY29uPnJlbW92ZTwvbWF0LWljb24+XG4gICAgICA8L2J1dHRvbj5cbiAgICAgIDxidXR0b25cbiAgICAgICAgdHlwZT1cImJ1dHRvblwiXG4gICAgICAgIGNsYXNzPVwiem9vbS1sYWJlbFwiXG4gICAgICAgIG1hdFRvb2x0aXA9XCJab29tIHRvIDEwMCVcIlxuICAgICAgICAoY2xpY2spPVwiem9vbUFjdHVhbCgpXCI+XG4gICAgICAgIHt7ICh6b29tICogMTAwKS50b0ZpeGVkKDApIH19JVxuICAgICAgPC9idXR0b24+XG4gICAgICA8YnV0dG9uXG4gICAgICAgIHR5cGU9XCJidXR0b25cIlxuICAgICAgICBjbGFzcz1cInpvb20tYnV0dG9uXCJcbiAgICAgICAgbWF0VG9vbHRpcD1cIlpvb20gaW5cIlxuICAgICAgICAoY2xpY2spPVwiem9vbUluKClcIj5cbiAgICAgICAgPG1hdC1pY29uPmFkZDwvbWF0LWljb24+XG4gICAgICA8L2J1dHRvbj5cbiAgICAgIDxidXR0b25cbiAgICAgICAgdHlwZT1cImJ1dHRvblwiXG4gICAgICAgIGNsYXNzPVwiem9vbS1idXR0b25cIlxuICAgICAgICBtYXRUb29sdGlwPVwiRml0IHBhZ2VcIlxuICAgICAgICAoY2xpY2spPVwiem9vbUZpdCgpXCI+XG4gICAgICAgIDxtYXQtaWNvbj5maXRfc2NyZWVuPC9tYXQtaWNvbj5cbiAgICAgIDwvYnV0dG9uPlxuICAgIDwvZGl2PlxuICA8L2Rpdj5cbjwvZGl2PlxuIl19
|