@firestitch/report 18.9.0 → 18.10.1
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/anchor-at-point.d.ts +14 -0
- package/app/reports/canvas-landing-page.d.ts +2 -0
- package/app/reports/components/component-chart/component-chart.component.d.ts +18 -2
- package/app/reports/components/component-kpi/component-kpi.component.d.ts +4 -1
- package/app/reports/components/report-canvas/report-canvas.component.d.ts +3 -0
- package/app/reports/components/report-component/report-component.component.d.ts +35 -1
- package/app/reports/components/report-view-picker/report-view-picker.component.d.ts +21 -0
- package/app/reports/data/report.data.d.ts +20 -7
- package/app/reports/dialogs/component-settings/component-settings.component.d.ts +18 -3
- package/app/reports/dialogs/report-settings/report-settings.component.d.ts +45 -8
- package/app/reports/dialogs/report-view/report-view-dialog.component.d.ts +13 -0
- package/app/reports/drill-crumbs.d.ts +12 -0
- package/app/reports/export/report-export-collector.service.d.ts +13 -4
- package/app/reports/export/report-filter-lines.d.ts +18 -0
- package/app/reports/filter-settings-rules.d.ts +37 -0
- package/app/reports/format.d.ts +0 -1
- package/app/reports/interfaces/canvas-landing-input.interface.d.ts +8 -0
- package/app/reports/interfaces/component-data-applied.interface.d.ts +13 -0
- package/app/reports/interfaces/component-data-drill.interface.d.ts +22 -0
- package/app/reports/interfaces/filter-bar-placement.type.d.ts +1 -0
- package/app/reports/interfaces/filter-component-toggle-state.interface.d.ts +4 -0
- package/app/reports/interfaces/filter-settings-option.interface.d.ts +4 -0
- package/app/reports/interfaces/filter-type-select-state.interface.d.ts +5 -0
- package/app/reports/interfaces/report-chart-hit.interface.d.ts +5 -0
- package/app/reports/interfaces/report-chat-viewer-cross-filter-field.interface.d.ts +4 -0
- package/app/reports/interfaces/report-chat-viewer-cross-filter.interface.d.ts +7 -0
- package/app/reports/interfaces/report-chat-viewer-detail.interface.d.ts +4 -0
- package/app/reports/interfaces/report-chat-viewer-drill-step.interface.d.ts +5 -0
- package/app/reports/interfaces/report-chat-viewer-drill.interface.d.ts +5 -0
- package/app/reports/interfaces/report-chat-viewer-filter.interface.d.ts +3 -0
- package/app/reports/interfaces/report-chat-viewer-selection.interface.d.ts +5 -0
- package/app/reports/interfaces/report-chat-viewer-state.interface.d.ts +12 -0
- package/app/reports/interfaces/report-drill-crumb.interface.d.ts +6 -0
- package/app/reports/interfaces/report-drill-refusal.type.d.ts +1 -0
- package/app/reports/interfaces/report-drill-step.interface.d.ts +5 -0
- package/app/reports/interfaces/report-export-line-kind.type.d.ts +1 -0
- package/app/reports/interfaces/report-export-line.interface.d.ts +8 -0
- package/app/reports/interfaces/report-export-lines-input.interface.d.ts +9 -0
- package/app/reports/interfaces/report-export-snapshot.interface.d.ts +15 -0
- package/app/reports/interfaces/report-filter-group-changes.interface.d.ts +7 -0
- package/app/reports/interfaces/report-filter-line-context.interface.d.ts +8 -0
- package/app/reports/interfaces/report-filter-line-form.type.d.ts +1 -0
- package/app/reports/interfaces/report-filter-match.type.d.ts +1 -0
- package/app/reports/interfaces/report-filter-option-pair.interface.d.ts +4 -0
- package/app/reports/interfaces/report-filter-options-ask.interface.d.ts +6 -0
- package/app/reports/interfaces/report-filter-options-list.interface.d.ts +7 -0
- package/app/reports/interfaces/report-filter-options-request.interface.d.ts +6 -0
- package/app/reports/interfaces/report-filter-options-stream.interface.d.ts +11 -0
- package/app/reports/interfaces/report-filter-options.interface.d.ts +7 -0
- package/app/reports/interfaces/report-filter-skip.type.d.ts +1 -0
- package/app/reports/interfaces/report-mark-action.type.d.ts +1 -0
- package/app/reports/interfaces/report-mark-click.interface.d.ts +13 -0
- package/app/reports/interfaces/report-mark-context.interface.d.ts +6 -0
- package/app/reports/interfaces/report-mark-decision.interface.d.ts +6 -0
- package/app/reports/interfaces/report-mark-event.interface.d.ts +11 -0
- package/app/reports/interfaces/report-mark-point.interface.d.ts +8 -0
- package/app/reports/interfaces/report-temporary-state.interface.d.ts +4 -0
- package/app/reports/interfaces/report-tile-state.interface.d.ts +8 -0
- package/app/reports/interfaces/report-view-config.interface.d.ts +11 -0
- package/app/reports/interfaces/report-view-create.interface.d.ts +7 -0
- package/app/reports/interfaces/report-view-deleted.interface.d.ts +4 -0
- package/app/reports/interfaces/report-view-dialog-data.interface.d.ts +7 -0
- package/app/reports/interfaces/report-view-dropped.interface.d.ts +5 -0
- package/app/reports/interfaces/report-view-menu-item.interface.d.ts +10 -0
- package/app/reports/interfaces/report-view-summary.interface.d.ts +11 -0
- package/app/reports/interfaces/report-view.interface.d.ts +7 -0
- package/app/reports/interfaces/report-viewer-feature.type.d.ts +1 -0
- package/app/reports/interfaces/report-views.interface.d.ts +7 -0
- package/app/reports/interfaces/report.interface.d.ts +27 -16
- package/app/reports/interfaces/tile-load-result.interface.d.ts +4 -0
- package/app/reports/mark-click.d.ts +20 -0
- package/app/reports/option-builder.d.ts +12 -1
- package/app/reports/report-chat-viewer-state.d.ts +8 -0
- package/app/reports/report-date-presets.d.ts +2 -0
- package/app/reports/report-filter-items.d.ts +20 -21
- package/app/reports/report-tile.d.ts +2 -0
- package/app/reports/report-view-config.d.ts +34 -0
- package/app/reports/report-view-menu.d.ts +15 -0
- package/app/reports/report-viewer-features.d.ts +5 -0
- package/app/reports/services/report-filter-options.service.d.ts +26 -0
- package/app/reports/services/report-filter-state.service.d.ts +65 -11
- package/app/reports/services/report-view.service.d.ts +39 -0
- package/app/reports/tile-data-state.d.ts +7 -0
- package/app/reports/tile-loads.d.ts +4 -0
- package/app/reports/views/report/fs-ai-report.component.d.ts +10 -8
- package/app/reports/views/report/report.component.d.ts +6 -0
- package/esm2022/app/reports/anchor-at-point.mjs +49 -0
- package/esm2022/app/reports/canvas-landing-page.mjs +26 -0
- package/esm2022/app/reports/components/component-chart/component-chart.component.mjs +97 -5
- package/esm2022/app/reports/components/component-kpi/component-kpi.component.mjs +11 -4
- package/esm2022/app/reports/components/component-list/component-list.component.mjs +11 -5
- package/esm2022/app/reports/components/report-canvas/report-canvas.component.mjs +56 -40
- package/esm2022/app/reports/components/report-component/report-component.component.mjs +261 -65
- package/esm2022/app/reports/components/report-view-picker/report-view-picker.component.mjs +115 -0
- package/esm2022/app/reports/data/report.data.mjs +94 -14
- package/esm2022/app/reports/dialogs/component-settings/component-settings.component.mjs +106 -51
- package/esm2022/app/reports/dialogs/report-settings/report-settings.component.mjs +248 -104
- package/esm2022/app/reports/dialogs/report-view/report-view-dialog.component.mjs +52 -0
- package/esm2022/app/reports/drill-crumbs.mjs +73 -0
- package/esm2022/app/reports/export/report-export-collector.service.mjs +187 -117
- package/esm2022/app/reports/export/report-filter-lines.mjs +235 -0
- package/esm2022/app/reports/export/report-pdf.service.mjs +12 -7
- package/esm2022/app/reports/export/report-pptx.service.mjs +18 -14
- package/esm2022/app/reports/filter-settings-rules.mjs +290 -0
- package/esm2022/app/reports/format.mjs +2 -22
- package/esm2022/app/reports/interfaces/canvas-landing-input.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/component-data-applied.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/component-data-drill.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/filter-bar-placement.type.mjs +2 -0
- package/esm2022/app/reports/interfaces/filter-component-toggle-state.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/filter-settings-option.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/filter-type-select-state.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-chart-hit.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-chat-viewer-cross-filter-field.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-chat-viewer-cross-filter.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-chat-viewer-detail.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-chat-viewer-drill-step.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-chat-viewer-drill.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-chat-viewer-filter.interface.mjs +1 -1
- package/esm2022/app/reports/interfaces/report-chat-viewer-selection.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-chat-viewer-state.interface.mjs +1 -1
- package/esm2022/app/reports/interfaces/report-drill-crumb.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-drill-refusal.type.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-drill-step.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-export-line-kind.type.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-export-line.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-export-lines-input.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-export-snapshot.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-filter-group-changes.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-filter-line-context.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-filter-line-form.type.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-filter-match.type.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-filter-option-pair.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-filter-options-ask.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-filter-options-list.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-filter-options-request.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-filter-options-stream.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-filter-options.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-filter-skip.type.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-mark-action.type.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-mark-click.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-mark-context.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-mark-decision.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-mark-event.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-mark-point.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-temporary-state.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-tile-state.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-view-config.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-view-create.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-view-deleted.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-view-dialog-data.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-view-dropped.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-view-menu-item.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-view-summary.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-view.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-viewer-feature.type.mjs +2 -0
- package/esm2022/app/reports/interfaces/report-views.interface.mjs +2 -0
- package/esm2022/app/reports/interfaces/report.interface.mjs +1 -1
- package/esm2022/app/reports/interfaces/tile-load-result.interface.mjs +2 -0
- package/esm2022/app/reports/mark-click.mjs +193 -0
- package/esm2022/app/reports/option-builder.mjs +159 -15
- package/esm2022/app/reports/report-chat-viewer-state.mjs +34 -0
- package/esm2022/app/reports/report-date-presets.mjs +18 -0
- package/esm2022/app/reports/report-filter-items.mjs +263 -72
- package/esm2022/app/reports/report-tile.mjs +12 -0
- package/esm2022/app/reports/report-view-config.mjs +587 -0
- package/esm2022/app/reports/report-view-menu.mjs +119 -0
- package/esm2022/app/reports/report-viewer-features.mjs +42 -0
- package/esm2022/app/reports/services/report-filter-options.service.mjs +238 -0
- package/esm2022/app/reports/services/report-filter-state.service.mjs +668 -210
- package/esm2022/app/reports/services/report-view.service.mjs +218 -0
- package/esm2022/app/reports/tile-data-state.mjs +127 -0
- package/esm2022/app/reports/tile-loads.mjs +38 -0
- package/esm2022/app/reports/views/report/fs-ai-report.component.mjs +194 -127
- package/esm2022/app/reports/views/report/report.component.mjs +112 -29
- package/esm2022/public_api.mjs +23 -1
- package/fesm2022/{firestitch-report-echarts-DBMOHmBF.mjs → firestitch-report-echarts-DHEH_K_q.mjs} +2 -2
- package/fesm2022/{firestitch-report-echarts-DBMOHmBF.mjs.map → firestitch-report-echarts-DHEH_K_q.mjs.map} +1 -1
- package/fesm2022/{firestitch-report-firestitch-report-CqbXT1gh.mjs → firestitch-report-firestitch-report-ZcHTnNKq.mjs} +8222 -4447
- package/fesm2022/firestitch-report-firestitch-report-ZcHTnNKq.mjs.map +1 -0
- package/fesm2022/firestitch-report.mjs +1 -1
- package/package.json +1 -1
- package/public_api.d.ts +22 -0
- package/app/reports/report-url-state.d.ts +0 -19
- package/esm2022/app/reports/report-url-state.mjs +0 -189
- package/fesm2022/firestitch-report-firestitch-report-CqbXT1gh.mjs.map +0 -1
|
@@ -7,10 +7,12 @@ import { FsMenuModule } from '@firestitch/menu';
|
|
|
7
7
|
import { FsMessage } from '@firestitch/message';
|
|
8
8
|
import { FsPrompt } from '@firestitch/prompt';
|
|
9
9
|
import { FsZoomPanComponent, FsZoomPanModule } from '@firestitch/zoom-pan';
|
|
10
|
-
import { Subject, catchError, debounceTime, map, merge, of, switchMap, tap, } from 'rxjs';
|
|
10
|
+
import { Subject, catchError, debounceTime, filter as rxFilter, map, merge, of, switchMap, tap, } from 'rxjs';
|
|
11
|
+
import { canvasLandingPage } from '../../canvas-landing-page';
|
|
11
12
|
import { ReportData } from '../../data/report.data';
|
|
12
13
|
import { DEFAULT_HEADING_SIZE } from '../../layout';
|
|
13
14
|
import { ReportFilterStateService } from '../../services/report-filter-state.service';
|
|
15
|
+
import { valuesMatchAnyGroupIds } from '../../tile-data-state';
|
|
14
16
|
import { isDrawn, layerValueKeys, sameTextValues, shownValues, textValues, valueKey, valueKeys, } from '../../values';
|
|
15
17
|
import { ReportComponentComponent } from '../report-component/report-component.component';
|
|
16
18
|
import * as i0 from "@angular/core";
|
|
@@ -55,9 +57,10 @@ function sameTokens(a, b) {
|
|
|
55
57
|
export class ReportCanvasComponent {
|
|
56
58
|
report;
|
|
57
59
|
editMode = false;
|
|
58
|
-
// The page the host wants on screen, by page id (a
|
|
59
|
-
//
|
|
60
|
-
//
|
|
60
|
+
// The page the host wants on screen, by page id (a ?page= the report opened
|
|
61
|
+
// with, or an opened view's page). Keyed on id rather than index so it
|
|
62
|
+
// survives pages being reordered or deleted; an id that no longer resolves
|
|
63
|
+
// falls back to the first page.
|
|
61
64
|
pageId = null;
|
|
62
65
|
// A component asked for its settings dialog — the page-level host opens it
|
|
63
66
|
// (it owns MatDialog + the post-save reload).
|
|
@@ -65,8 +68,8 @@ export class ReportCanvasComponent {
|
|
|
65
68
|
// The report's structure changed here (a page was added) — the host re-fetches
|
|
66
69
|
// it (it owns the assembled report + filter state).
|
|
67
70
|
reportChanged = new EventEmitter();
|
|
68
|
-
// The page on screen changed — the host
|
|
69
|
-
//
|
|
71
|
+
// The page on screen changed — the host keeps it in the report's state (a
|
|
72
|
+
// saved view stores it). Carries the page id, never the index.
|
|
70
73
|
pageChanged = new EventEmitter();
|
|
71
74
|
zoomPan;
|
|
72
75
|
// The rendered components of the active page — only the canvas can reach the
|
|
@@ -77,7 +80,7 @@ export class ReportCanvasComponent {
|
|
|
77
80
|
PX = PX_PER_INCH;
|
|
78
81
|
// The report's pages as the canvas draws them. This is the host's own
|
|
79
82
|
// `report.pages` array, patched in place (a rename, a delete, a reorder) so
|
|
80
|
-
// the host's exports
|
|
83
|
+
// the host's exports see the change too. Because the array
|
|
81
84
|
// and its pages keep their identity across a patch, the signal notifies on
|
|
82
85
|
// every set rather than only when the reference changes.
|
|
83
86
|
pages = signal([], { equal: () => false });
|
|
@@ -88,6 +91,10 @@ export class ReportCanvasComponent {
|
|
|
88
91
|
masterMode = signal(false);
|
|
89
92
|
groups = new Map();
|
|
90
93
|
selectedComponentId = signal(null);
|
|
94
|
+
// Moves when a view is opened. Every tile is tracked by it, so each is
|
|
95
|
+
// drawn again from the view's state. A reset to the open view leaves it:
|
|
96
|
+
// the tiles reload in place and keep their data on screen meanwhile.
|
|
97
|
+
appliedVersion = inject(ReportFilterStateService).appliedVersion;
|
|
91
98
|
// The components each layer draws. A value only reads inside text, so one
|
|
92
99
|
// that leaked into a layer's components is still never drawn.
|
|
93
100
|
activePageComponents = computed(() => (this.pages()[this.activePageIndex()]?.components ?? []).filter(isDrawn));
|
|
@@ -125,6 +132,7 @@ export class ReportCanvasComponent {
|
|
|
125
132
|
_destroyRef = inject(DestroyRef);
|
|
126
133
|
_fitted = false;
|
|
127
134
|
_previousPageCount = 0;
|
|
135
|
+
_previousReportId = null;
|
|
128
136
|
// The page id last announced through pageChanged, so a re-render that lands on
|
|
129
137
|
// the same page stays quiet — hosts reload on this and an unchanged page is
|
|
130
138
|
// not news.
|
|
@@ -159,27 +167,19 @@ export class ReportCanvasComponent {
|
|
|
159
167
|
}
|
|
160
168
|
this.groups = new Map((this.report?.filterGroups ?? []).map((group) => [group.id, group]));
|
|
161
169
|
this.pages.set(this.report?.pages ?? []);
|
|
162
|
-
|
|
163
|
-
//
|
|
164
|
-
const
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
const index = this.pages().findIndex((page) => page.id === this.pageId);
|
|
176
|
-
if (index > -1) {
|
|
177
|
-
this.activePageIndex.set(index);
|
|
178
|
-
}
|
|
179
|
-
}
|
|
180
|
-
if (this.activePageIndex() >= pageCount) {
|
|
181
|
-
this.activePageIndex.set(0);
|
|
182
|
-
}
|
|
170
|
+
// A page just added in this tab, else the asked-for page, else the page
|
|
171
|
+
// shown (the first page on another report). See canvasLandingPage.
|
|
172
|
+
const reportId = this.report?.id ?? null;
|
|
173
|
+
this.activePageIndex.set(canvasLandingPage({
|
|
174
|
+
reportId,
|
|
175
|
+
previousReportId: this._previousReportId,
|
|
176
|
+
previousPageCount: this._previousPageCount,
|
|
177
|
+
pageIds: this.pages().map((page) => page.id),
|
|
178
|
+
pageId: this.pageId,
|
|
179
|
+
activePageIndex: this.activePageIndex(),
|
|
180
|
+
}));
|
|
181
|
+
this._previousPageCount = this.pages().length;
|
|
182
|
+
this._previousReportId = reportId;
|
|
183
183
|
// Tell the host which page is open whenever that changes — including the
|
|
184
184
|
// FIRST time the report renders, not only when someone clicks a page.
|
|
185
185
|
// Hosts bind things to the open page (the report chat scopes its
|
|
@@ -376,8 +376,8 @@ export class ReportCanvasComponent {
|
|
|
376
376
|
this.activePageIndex.set(Math.min(index, pages.length - 1));
|
|
377
377
|
this._previousPageCount = pages.length;
|
|
378
378
|
this.selectedComponentId.set(null);
|
|
379
|
-
// The
|
|
380
|
-
//
|
|
379
|
+
// The page on screen just stopped existing — report the neighbour we
|
|
380
|
+
// landed on, so the host's state names a page the report has.
|
|
381
381
|
this.pageChanged.emit(this.activePage?.id ?? null);
|
|
382
382
|
this._message.success('Deleted page');
|
|
383
383
|
});
|
|
@@ -483,9 +483,13 @@ export class ReportCanvasComponent {
|
|
|
483
483
|
};
|
|
484
484
|
}
|
|
485
485
|
// Triggers landing together (a reload that also changes the page) make one
|
|
486
|
-
// request, and a newer request drops the one still in flight.
|
|
486
|
+
// request, and a newer request drops the one still in flight. Any other
|
|
487
|
+
// change of the screen's state (changes) asks again only when it moved
|
|
488
|
+
// the request: a view applied or the bar reset (stateVersion moves on
|
|
489
|
+
// each), the match changed, or, while the groups match 'any', a group the
|
|
490
|
+
// values have no member of took or lost a value.
|
|
487
491
|
_watchValues(layer, onScreen$) {
|
|
488
|
-
merge(layer.reload$, onScreen$, this._filterState.changesForAny(() => layer.source()?.values ?? []).pipe(debounceTime(300)))
|
|
492
|
+
merge(layer.reload$, onScreen$, this._filterState.changesForAny(() => layer.source()?.values ?? []).pipe(debounceTime(300)), this._filterState.changes().pipe(debounceTime(300), rxFilter(() => this._requestMoved(layer))))
|
|
489
493
|
.pipe(debounceTime(0), map(() => this._layerRequest(layer.source())), tap((request) => layer.pending.set(request)), switchMap((request) => this._loadValues(request)), tap((loaded) => {
|
|
490
494
|
layer.results.set(loaded);
|
|
491
495
|
layer.pending.set(null);
|
|
@@ -497,32 +501,44 @@ export class ReportCanvasComponent {
|
|
|
497
501
|
// report and leaves every number as it was. Compared with the request on its
|
|
498
502
|
// way, else the one whose numbers are on screen.
|
|
499
503
|
_reloadIfChanged(layer) {
|
|
500
|
-
|
|
501
|
-
if (this._layerRequest(layer.source()).signature !== last?.signature) {
|
|
504
|
+
if (this._requestMoved(layer)) {
|
|
502
505
|
layer.reload$.next();
|
|
503
506
|
}
|
|
504
507
|
}
|
|
508
|
+
// Whether the layer's request now differs from the one on its way, else
|
|
509
|
+
// the one whose numbers are on screen.
|
|
510
|
+
_requestMoved(layer) {
|
|
511
|
+
const last = layer.pending() ?? layer.results();
|
|
512
|
+
return this._layerRequest(layer.source()).signature !== last?.signature;
|
|
513
|
+
}
|
|
505
514
|
// Read when the request is sent, not when it was asked for: an edit may have
|
|
506
515
|
// just changed which values the layer's text shows. The filter values of
|
|
507
516
|
// every value on the layer go out, shown or not: the server decides which
|
|
508
517
|
// values it reads, and applies to each only the entries naming its own
|
|
509
518
|
// filters, so an operand only a formula reads is filtered as if it were
|
|
510
519
|
// shown. A value's Name is left out of the signature: a rename moves no
|
|
511
|
-
// number.
|
|
520
|
+
// number. While the groups match 'any', the request lists the groups that
|
|
521
|
+
// combine, by the tile rule (valuesMatchAnyGroupIds): a header or footer
|
|
522
|
+
// value's are the page on screen's.
|
|
512
523
|
_layerRequest(layer) {
|
|
513
524
|
const pageId = layer?.id ?? null;
|
|
514
525
|
const values = layer?.values ?? [];
|
|
515
526
|
const shown = this._shownValues(layer);
|
|
516
527
|
const filters = values.flatMap((component) => this._filterState.resolveForComponent(component));
|
|
528
|
+
const matchAnyGroupIds = values.length
|
|
529
|
+
? valuesMatchAnyGroupIds(this.report, pageId, this._filterState.snapshot())
|
|
530
|
+
: [];
|
|
517
531
|
return {
|
|
518
532
|
pageId,
|
|
519
533
|
shown,
|
|
520
534
|
filters,
|
|
535
|
+
matchAnyGroupIds,
|
|
521
536
|
signature: JSON.stringify([
|
|
522
537
|
pageId,
|
|
523
538
|
shown.map((value) => value.id),
|
|
524
539
|
values.map((value) => ({ ...value, title: null })),
|
|
525
540
|
filters,
|
|
541
|
+
matchAnyGroupIds,
|
|
526
542
|
]),
|
|
527
543
|
};
|
|
528
544
|
}
|
|
@@ -536,7 +552,7 @@ export class ReportCanvasComponent {
|
|
|
536
552
|
// One layer's numbers, by value id. A layer whose text shows no value asks
|
|
537
553
|
// for nothing. A failed request reads as no numbers (each value an em dash)
|
|
538
554
|
// rather than an error dialog: the words around them still read.
|
|
539
|
-
_loadValues({ pageId, shown, filters, signature }) {
|
|
555
|
+
_loadValues({ pageId, shown, filters, matchAnyGroupIds, signature, }) {
|
|
540
556
|
const loaded = (rows) => ({
|
|
541
557
|
pageId,
|
|
542
558
|
signature,
|
|
@@ -545,7 +561,7 @@ export class ReportCanvasComponent {
|
|
|
545
561
|
if (pageId === null || !shown.length) {
|
|
546
562
|
return of(loaded([]));
|
|
547
563
|
}
|
|
548
|
-
return this._reportData.pageValues(this.report.id, pageId, filters, false, { handlers: false })
|
|
564
|
+
return this._reportData.pageValues(this.report.id, pageId, filters, false, { handlers: false }, matchAnyGroupIds)
|
|
549
565
|
.pipe(map((rows) => loaded(rows ?? [])), catchError(() => of(loaded([]))));
|
|
550
566
|
}
|
|
551
567
|
// The tokens of one layer's blocks. Numbers read for another page are not
|
|
@@ -734,7 +750,7 @@ export class ReportCanvasComponent {
|
|
|
734
750
|
this._guides?.nativeElement?.replaceChildren();
|
|
735
751
|
}
|
|
736
752
|
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: ReportCanvasComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
737
|
-
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", 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 wheel=\"modifier\"\n [zoomMin]=\"0.1\"\n [zoomMax]=\"3\"\n (zoomed)=\"onZoomed($event)\">\n @if (activePage) {\n <div\n class=\"page\"\n [class.editing]=\"editMode\"\n [class.master-editing]=\"isMasterEditing\"\n [style.width.px]=\"report.pageWidth * PX\"\n [style.height.px]=\"report.pageHeight * PX\"\n [style.--canvas-zoom]=\"zoom()\"\n [style.--report-heading-size.px]=\"headingSizePx\">\n <!-- The header and footer: the master's components, drawn under the\n page's own. -->\n @if (isMasterShown && masterComponents().length) {\n <div\n class=\"master-layer\"\n [class.editable]=\"isMasterEditing\">\n @for (component of masterComponents(); track component.id) {\n <app-report-component\n [reportId]=\"report.id\"\n [component]=\"component\"\n [groups]=\"groups\"\n [editMode]=\"isMasterEditing\"\n [zoom]=\"zoom()\"\n [snapper]=\"snapper\"\n [tokens]=\"masterTokens()\"\n [valueKeysElsewhere]=\"valueKeysElsewhere\"\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 (removed)=\"onComponentRemoved($event)\"\n (openSettings)=\"componentSettings.emit($event)\"\n (valueSettings)=\"openValueSettings(component, $event)\"\n (textSaved)=\"onTextSaved(component, $event)\"\n (valuesRemoved)=\"reportChanged.emit()\">\n </app-report-component>\n }\n </div>\n }\n\n <!-- The header and footer bands, as guides while editing. -->\n @if (editMode) {\n @if (bands.headerHeight) {\n <div\n class=\"band band-header\"\n [style.height.px]=\"bands.headerHeight * PX\">\n @if (isMasterEditing) {\n <span class=\"band-label small\">Header</span>\n }\n </div>\n }\n @if (bands.footerHeight) {\n <div\n class=\"band band-footer\"\n [style.height.px]=\"bands.footerHeight * PX\">\n @if (isMasterEditing) {\n <span class=\"band-label small\">Footer</span>\n }\n </div>\n }\n }\n\n @for (component of activePageComponents(); track component.id) {\n <app-report-component\n [reportId]=\"report.id\"\n [component]=\"component\"\n [groups]=\"groups\"\n [editMode]=\"isPageEditing\"\n [zoom]=\"zoom()\"\n [snapper]=\"snapper\"\n [tokens]=\"pageTokens()\"\n [valueKeysElsewhere]=\"valueKeysElsewhere\"\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 (removed)=\"onComponentRemoved($event)\"\n (openSettings)=\"componentSettings.emit($event)\"\n (valueSettings)=\"openValueSettings(component, $event)\"\n (textSaved)=\"onTextSaved(component, $event)\"\n (valuesRemoved)=\"reportChanged.emit()\">\n </app-report-component>\n }\n\n <div\n #guides\n class=\"guides\">\n </div>\n\n @if (!activePageComponents().length && !masterMode()) {\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 </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 Every page gets a chip, including a lone one: the chip is what tells\n you which page you are on, and a report that hid it left you unable to\n tell page 1 of 1 from a page that failed to load. Deleting the last\n page is refused server-side, so the kebab is safe to expose here. -->\n <div\n class=\"page-tabs\"\n cdkDropList\n cdkDropListOrientation=\"horizontal\"\n (cdkDropListDropped)=\"onPageDropped($event)\">\n @for (page of 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)=\"toggleMasterHidden(page)\">\n {{ page.masterHidden ? 'Show header & footer' : 'Hide header & footer' }}\n </ng-template>\n <ng-template\n fs-menu-item\n (click)=\"deletePage(page)\">\n Delete\n </ng-template>\n </fs-menu>\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 (Ctrl/Cmd + scroll)\"\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 (Ctrl/Cmd + scroll)\"\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%}.page{position:relative;background:#fff;border-radius:2px;box-shadow:0 2px 12px #0f172a1f,0 0 0 1px #0f172a0a;box-sizing:border-box}.page.editing{background-image:radial-gradient(circle,#d8dee6 1px,transparent 1px);background-size:24px 24px}.page.master-editing>app-report-component{opacity:.35;pointer-events:none}.master-layer{position:absolute;inset:0;pointer-events:none}.master-layer.editable{z-index:10}.master-layer.editable app-report-component{pointer-events:auto}.band{position:absolute;left:0;right:0;z-index:5;pointer-events:none;background:#2196f30a;border-color:#2196f373;border-style:dashed;border-width:0}.band.band-header{top:0;border-bottom-width:calc(1px / var(--canvas-zoom, 1))}.band.band-footer{bottom:0;border-top-width:calc(1px / var(--canvas-zoom, 1))}.band .band-label{position:absolute;top:calc(10px / var(--canvas-zoom, 1));left:calc(10px / var(--canvas-zoom, 1));transform:scale(calc(1 / var(--canvas-zoom, 1)));transform-origin:top left;color:#2196f3cc;font-weight:600;text-transform:uppercase;letter-spacing:.06em}.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: 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", "zoomFit", "fitMode", "fitPosition", "fitPadding", "fitMaxScale", "wheel", "top", "left"], outputs: ["moved", "zoomed"] }, { kind: "component", type: ReportComponentComponent, selector: "app-report-component", inputs: ["reportId", "component", "groups", "editMode", "zoom", "snapper", "selected", "tokens", "valueKeysElsewhere"], outputs: ["selectComponent", "positionChanged", "openSettings", "removed", "valueSettings", "textSaved", "valuesRemoved"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
|
|
753
|
+
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", 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 wheel=\"modifier\"\n [zoomMin]=\"0.1\"\n [zoomMax]=\"3\"\n (zoomed)=\"onZoomed($event)\">\n @if (activePage) {\n <div\n class=\"page\"\n [class.editing]=\"editMode\"\n [class.master-editing]=\"isMasterEditing\"\n [style.width.px]=\"report.pageWidth * PX\"\n [style.height.px]=\"report.pageHeight * PX\"\n [style.--canvas-zoom]=\"zoom()\"\n [style.--report-heading-size.px]=\"headingSizePx\">\n <!-- The header and footer: the master's components, drawn under the\n page's own. -->\n @if (isMasterShown && masterComponents().length) {\n <div\n class=\"master-layer\"\n [class.editable]=\"isMasterEditing\">\n @for (component of masterComponents(); track component.id + ':' + appliedVersion()) {\n <app-report-component\n [reportId]=\"report.id\"\n [component]=\"component\"\n [groups]=\"groups\"\n [editMode]=\"isMasterEditing\"\n [zoom]=\"zoom()\"\n [snapper]=\"snapper\"\n [tokens]=\"masterTokens()\"\n [valueKeysElsewhere]=\"valueKeysElsewhere\"\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 (removed)=\"onComponentRemoved($event)\"\n (openSettings)=\"componentSettings.emit($event)\"\n (valueSettings)=\"openValueSettings(component, $event)\"\n (textSaved)=\"onTextSaved(component, $event)\"\n (valuesRemoved)=\"reportChanged.emit()\">\n </app-report-component>\n }\n </div>\n }\n\n <!-- The header and footer bands, as guides while editing. -->\n @if (editMode) {\n @if (bands.headerHeight) {\n <div\n class=\"band band-header\"\n [style.height.px]=\"bands.headerHeight * PX\">\n @if (isMasterEditing) {\n <span class=\"band-label small\">Header</span>\n }\n </div>\n }\n @if (bands.footerHeight) {\n <div\n class=\"band band-footer\"\n [style.height.px]=\"bands.footerHeight * PX\">\n @if (isMasterEditing) {\n <span class=\"band-label small\">Footer</span>\n }\n </div>\n }\n }\n\n @for (component of activePageComponents(); track component.id + ':' + appliedVersion()) {\n <app-report-component\n [reportId]=\"report.id\"\n [component]=\"component\"\n [groups]=\"groups\"\n [editMode]=\"isPageEditing\"\n [zoom]=\"zoom()\"\n [snapper]=\"snapper\"\n [tokens]=\"pageTokens()\"\n [valueKeysElsewhere]=\"valueKeysElsewhere\"\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 (removed)=\"onComponentRemoved($event)\"\n (openSettings)=\"componentSettings.emit($event)\"\n (valueSettings)=\"openValueSettings(component, $event)\"\n (textSaved)=\"onTextSaved(component, $event)\"\n (valuesRemoved)=\"reportChanged.emit()\">\n </app-report-component>\n }\n\n <div\n #guides\n class=\"guides\">\n </div>\n\n @if (!activePageComponents().length && !masterMode()) {\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 </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 Every page gets a chip, including a lone one: the chip is what tells\n you which page you are on, and a report that hid it left you unable to\n tell page 1 of 1 from a page that failed to load. Deleting the last\n page is refused server-side, so the kebab is safe to expose here. -->\n <div\n class=\"page-tabs\"\n cdkDropList\n cdkDropListOrientation=\"horizontal\"\n (cdkDropListDropped)=\"onPageDropped($event)\">\n @for (page of 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)=\"toggleMasterHidden(page)\">\n {{ page.masterHidden ? 'Show header & footer' : 'Hide header & footer' }}\n </ng-template>\n <ng-template\n fs-menu-item\n (click)=\"deletePage(page)\">\n Delete\n </ng-template>\n </fs-menu>\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 (Ctrl/Cmd + scroll)\"\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 (Ctrl/Cmd + scroll)\"\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%}.page{position:relative;background:#fff;border-radius:2px;box-shadow:0 2px 12px #0f172a1f,0 0 0 1px #0f172a0a;box-sizing:border-box}.page.editing{background-image:radial-gradient(circle,#d8dee6 1px,transparent 1px);background-size:24px 24px}.page.master-editing>app-report-component{opacity:.35;pointer-events:none}.master-layer{position:absolute;inset:0;pointer-events:none}.master-layer.editable{z-index:10}.master-layer.editable app-report-component{pointer-events:auto}.band{position:absolute;left:0;right:0;z-index:5;pointer-events:none;background:#2196f30a;border-color:#2196f373;border-style:dashed;border-width:0}.band.band-header{top:0;border-bottom-width:calc(1px / var(--canvas-zoom, 1))}.band.band-footer{bottom:0;border-top-width:calc(1px / var(--canvas-zoom, 1))}.band .band-label{position:absolute;top:calc(10px / var(--canvas-zoom, 1));left:calc(10px / var(--canvas-zoom, 1));transform:scale(calc(1 / var(--canvas-zoom, 1)));transform-origin:top left;color:#2196f3cc;font-weight:600;text-transform:uppercase;letter-spacing:.06em}.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: 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", "zoomFit", "fitMode", "fitPosition", "fitPadding", "fitMaxScale", "wheel", "top", "left"], outputs: ["moved", "zoomed"] }, { kind: "component", type: ReportComponentComponent, selector: "app-report-component", inputs: ["reportId", "component", "groups", "editMode", "zoom", "snapper", "selected", "tokens", "valueKeysElsewhere"], outputs: ["selectComponent", "positionChanged", "openSettings", "removed", "valueSettings", "textSaved", "valuesRemoved"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
|
|
738
754
|
}
|
|
739
755
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: ReportCanvasComponent, decorators: [{
|
|
740
756
|
type: Component,
|
|
@@ -745,7 +761,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImpo
|
|
|
745
761
|
FsMenuModule,
|
|
746
762
|
FsZoomPanModule,
|
|
747
763
|
ReportComponentComponent,
|
|
748
|
-
], template: "<div class=\"canvas\">\n <div\n #viewport\n class=\"page-viewport\"\n (pointerdown)=\"onCanvasPointerDown()\">\n <fs-zoom-pan\n wheel=\"modifier\"\n [zoomMin]=\"0.1\"\n [zoomMax]=\"3\"\n (zoomed)=\"onZoomed($event)\">\n @if (activePage) {\n <div\n class=\"page\"\n [class.editing]=\"editMode\"\n [class.master-editing]=\"isMasterEditing\"\n [style.width.px]=\"report.pageWidth * PX\"\n [style.height.px]=\"report.pageHeight * PX\"\n [style.--canvas-zoom]=\"zoom()\"\n [style.--report-heading-size.px]=\"headingSizePx\">\n <!-- The header and footer: the master's components, drawn under the\n page's own. -->\n @if (isMasterShown && masterComponents().length) {\n <div\n class=\"master-layer\"\n [class.editable]=\"isMasterEditing\">\n @for (component of masterComponents(); track component.id) {\n <app-report-component\n [reportId]=\"report.id\"\n [component]=\"component\"\n [groups]=\"groups\"\n [editMode]=\"isMasterEditing\"\n [zoom]=\"zoom()\"\n [snapper]=\"snapper\"\n [tokens]=\"masterTokens()\"\n [valueKeysElsewhere]=\"valueKeysElsewhere\"\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 (removed)=\"onComponentRemoved($event)\"\n (openSettings)=\"componentSettings.emit($event)\"\n (valueSettings)=\"openValueSettings(component, $event)\"\n (textSaved)=\"onTextSaved(component, $event)\"\n (valuesRemoved)=\"reportChanged.emit()\">\n </app-report-component>\n }\n </div>\n }\n\n <!-- The header and footer bands, as guides while editing. -->\n @if (editMode) {\n @if (bands.headerHeight) {\n <div\n class=\"band band-header\"\n [style.height.px]=\"bands.headerHeight * PX\">\n @if (isMasterEditing) {\n <span class=\"band-label small\">Header</span>\n }\n </div>\n }\n @if (bands.footerHeight) {\n <div\n class=\"band band-footer\"\n [style.height.px]=\"bands.footerHeight * PX\">\n @if (isMasterEditing) {\n <span class=\"band-label small\">Footer</span>\n }\n </div>\n }\n }\n\n @for (component of activePageComponents(); track component.id) {\n <app-report-component\n [reportId]=\"report.id\"\n [component]=\"component\"\n [groups]=\"groups\"\n [editMode]=\"isPageEditing\"\n [zoom]=\"zoom()\"\n [snapper]=\"snapper\"\n [tokens]=\"pageTokens()\"\n [valueKeysElsewhere]=\"valueKeysElsewhere\"\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 (removed)=\"onComponentRemoved($event)\"\n (openSettings)=\"componentSettings.emit($event)\"\n (valueSettings)=\"openValueSettings(component, $event)\"\n (textSaved)=\"onTextSaved(component, $event)\"\n (valuesRemoved)=\"reportChanged.emit()\">\n </app-report-component>\n }\n\n <div\n #guides\n class=\"guides\">\n </div>\n\n @if (!activePageComponents().length && !masterMode()) {\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 </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 Every page gets a chip, including a lone one: the chip is what tells\n you which page you are on, and a report that hid it left you unable to\n tell page 1 of 1 from a page that failed to load. Deleting the last\n page is refused server-side, so the kebab is safe to expose here. -->\n <div\n class=\"page-tabs\"\n cdkDropList\n cdkDropListOrientation=\"horizontal\"\n (cdkDropListDropped)=\"onPageDropped($event)\">\n @for (page of 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)=\"toggleMasterHidden(page)\">\n {{ page.masterHidden ? 'Show header & footer' : 'Hide header & footer' }}\n </ng-template>\n <ng-template\n fs-menu-item\n (click)=\"deletePage(page)\">\n Delete\n </ng-template>\n </fs-menu>\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 (Ctrl/Cmd + scroll)\"\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 (Ctrl/Cmd + scroll)\"\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%}.page{position:relative;background:#fff;border-radius:2px;box-shadow:0 2px 12px #0f172a1f,0 0 0 1px #0f172a0a;box-sizing:border-box}.page.editing{background-image:radial-gradient(circle,#d8dee6 1px,transparent 1px);background-size:24px 24px}.page.master-editing>app-report-component{opacity:.35;pointer-events:none}.master-layer{position:absolute;inset:0;pointer-events:none}.master-layer.editable{z-index:10}.master-layer.editable app-report-component{pointer-events:auto}.band{position:absolute;left:0;right:0;z-index:5;pointer-events:none;background:#2196f30a;border-color:#2196f373;border-style:dashed;border-width:0}.band.band-header{top:0;border-bottom-width:calc(1px / var(--canvas-zoom, 1))}.band.band-footer{bottom:0;border-top-width:calc(1px / var(--canvas-zoom, 1))}.band .band-label{position:absolute;top:calc(10px / var(--canvas-zoom, 1));left:calc(10px / var(--canvas-zoom, 1));transform:scale(calc(1 / var(--canvas-zoom, 1)));transform-origin:top left;color:#2196f3cc;font-weight:600;text-transform:uppercase;letter-spacing:.06em}.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"] }]
|
|
764
|
+
], template: "<div class=\"canvas\">\n <div\n #viewport\n class=\"page-viewport\"\n (pointerdown)=\"onCanvasPointerDown()\">\n <fs-zoom-pan\n wheel=\"modifier\"\n [zoomMin]=\"0.1\"\n [zoomMax]=\"3\"\n (zoomed)=\"onZoomed($event)\">\n @if (activePage) {\n <div\n class=\"page\"\n [class.editing]=\"editMode\"\n [class.master-editing]=\"isMasterEditing\"\n [style.width.px]=\"report.pageWidth * PX\"\n [style.height.px]=\"report.pageHeight * PX\"\n [style.--canvas-zoom]=\"zoom()\"\n [style.--report-heading-size.px]=\"headingSizePx\">\n <!-- The header and footer: the master's components, drawn under the\n page's own. -->\n @if (isMasterShown && masterComponents().length) {\n <div\n class=\"master-layer\"\n [class.editable]=\"isMasterEditing\">\n @for (component of masterComponents(); track component.id + ':' + appliedVersion()) {\n <app-report-component\n [reportId]=\"report.id\"\n [component]=\"component\"\n [groups]=\"groups\"\n [editMode]=\"isMasterEditing\"\n [zoom]=\"zoom()\"\n [snapper]=\"snapper\"\n [tokens]=\"masterTokens()\"\n [valueKeysElsewhere]=\"valueKeysElsewhere\"\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 (removed)=\"onComponentRemoved($event)\"\n (openSettings)=\"componentSettings.emit($event)\"\n (valueSettings)=\"openValueSettings(component, $event)\"\n (textSaved)=\"onTextSaved(component, $event)\"\n (valuesRemoved)=\"reportChanged.emit()\">\n </app-report-component>\n }\n </div>\n }\n\n <!-- The header and footer bands, as guides while editing. -->\n @if (editMode) {\n @if (bands.headerHeight) {\n <div\n class=\"band band-header\"\n [style.height.px]=\"bands.headerHeight * PX\">\n @if (isMasterEditing) {\n <span class=\"band-label small\">Header</span>\n }\n </div>\n }\n @if (bands.footerHeight) {\n <div\n class=\"band band-footer\"\n [style.height.px]=\"bands.footerHeight * PX\">\n @if (isMasterEditing) {\n <span class=\"band-label small\">Footer</span>\n }\n </div>\n }\n }\n\n @for (component of activePageComponents(); track component.id + ':' + appliedVersion()) {\n <app-report-component\n [reportId]=\"report.id\"\n [component]=\"component\"\n [groups]=\"groups\"\n [editMode]=\"isPageEditing\"\n [zoom]=\"zoom()\"\n [snapper]=\"snapper\"\n [tokens]=\"pageTokens()\"\n [valueKeysElsewhere]=\"valueKeysElsewhere\"\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 (removed)=\"onComponentRemoved($event)\"\n (openSettings)=\"componentSettings.emit($event)\"\n (valueSettings)=\"openValueSettings(component, $event)\"\n (textSaved)=\"onTextSaved(component, $event)\"\n (valuesRemoved)=\"reportChanged.emit()\">\n </app-report-component>\n }\n\n <div\n #guides\n class=\"guides\">\n </div>\n\n @if (!activePageComponents().length && !masterMode()) {\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 </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 Every page gets a chip, including a lone one: the chip is what tells\n you which page you are on, and a report that hid it left you unable to\n tell page 1 of 1 from a page that failed to load. Deleting the last\n page is refused server-side, so the kebab is safe to expose here. -->\n <div\n class=\"page-tabs\"\n cdkDropList\n cdkDropListOrientation=\"horizontal\"\n (cdkDropListDropped)=\"onPageDropped($event)\">\n @for (page of 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)=\"toggleMasterHidden(page)\">\n {{ page.masterHidden ? 'Show header & footer' : 'Hide header & footer' }}\n </ng-template>\n <ng-template\n fs-menu-item\n (click)=\"deletePage(page)\">\n Delete\n </ng-template>\n </fs-menu>\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 (Ctrl/Cmd + scroll)\"\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 (Ctrl/Cmd + scroll)\"\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%}.page{position:relative;background:#fff;border-radius:2px;box-shadow:0 2px 12px #0f172a1f,0 0 0 1px #0f172a0a;box-sizing:border-box}.page.editing{background-image:radial-gradient(circle,#d8dee6 1px,transparent 1px);background-size:24px 24px}.page.master-editing>app-report-component{opacity:.35;pointer-events:none}.master-layer{position:absolute;inset:0;pointer-events:none}.master-layer.editable{z-index:10}.master-layer.editable app-report-component{pointer-events:auto}.band{position:absolute;left:0;right:0;z-index:5;pointer-events:none;background:#2196f30a;border-color:#2196f373;border-style:dashed;border-width:0}.band.band-header{top:0;border-bottom-width:calc(1px / var(--canvas-zoom, 1))}.band.band-footer{bottom:0;border-top-width:calc(1px / var(--canvas-zoom, 1))}.band .band-label{position:absolute;top:calc(10px / var(--canvas-zoom, 1));left:calc(10px / var(--canvas-zoom, 1));transform:scale(calc(1 / var(--canvas-zoom, 1)));transform-origin:top left;color:#2196f3cc;font-weight:600;text-transform:uppercase;letter-spacing:.06em}.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"] }]
|
|
749
765
|
}], ctorParameters: () => [], propDecorators: { report: [{
|
|
750
766
|
type: Input
|
|
751
767
|
}], editMode: [{
|
|
@@ -771,4 +787,4 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImpo
|
|
|
771
787
|
type: ViewChild,
|
|
772
788
|
args: ['guides', { static: false }]
|
|
773
789
|
}] } });
|
|
774
|
-
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoicmVwb3J0LWNhbnZhcy5jb21wb25lbnQuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi8uLi8uLi9zcmMvYXBwL3JlcG9ydHMvY29tcG9uZW50cy9yZXBvcnQtY2FudmFzL3JlcG9ydC1jYW52YXMuY29tcG9uZW50LnRzIiwiLi4vLi4vLi4vLi4vLi4vLi4vc3JjL2FwcC9yZXBvcnRzL2NvbXBvbmVudHMvcmVwb3J0LWNhbnZhcy9yZXBvcnQtY2FudmFzLmNvbXBvbmVudC5odG1sIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBLE9BQU8sRUFDVSx1QkFBdUIsRUFBRSxTQUFTLEVBQUUsVUFBVSxFQUM3RCxVQUFVLEVBQUUsWUFBWSxFQUFFLEtBQUssRUFBYSxNQUFNLEVBQUUsU0FBUyxFQUFpQixTQUFTLEVBQUUsWUFBWSxFQUNyRixRQUFRLEVBQUUsTUFBTSxFQUFFLE1BQU0sR0FDekMsTUFBTSxlQUFlLENBQUM7QUFDdkIsT0FBTyxFQUFFLGtCQUFrQixFQUFFLFlBQVksRUFBRSxNQUFNLDRCQUE0QixDQUFDO0FBRTlFLE9BQU8sRUFBZSxjQUFjLEVBQUUsZUFBZSxFQUFFLE1BQU0sd0JBQXdCLENBQUM7QUFDdEYsT0FBTyxFQUFFLE9BQU8sRUFBRSxNQUFNLHdCQUF3QixDQUFDO0FBQ2pELE9BQU8sRUFBRSxVQUFVLEVBQUUsTUFBTSwyQkFBMkIsQ0FBQztBQUV2RCxPQUFPLEVBQUUsWUFBWSxFQUFFLE1BQU0sa0JBQWtCLENBQUM7QUFDaEQsT0FBTyxFQUFFLFNBQVMsRUFBRSxNQUFNLHFCQUFxQixDQUFDO0FBQ2hELE9BQU8sRUFBRSxRQUFRLEVBQUUsTUFBTSxvQkFBb0IsQ0FBQztBQUM5QyxPQUFPLEVBQUUsa0JBQWtCLEVBQUUsZUFBZSxFQUFFLE1BQU0sc0JBQXNCLENBQUM7QUFFM0UsT0FBTyxFQUNPLE9BQU8sRUFBRSxVQUFVLEVBQUUsWUFBWSxFQUFFLEdBQUcsRUFBRSxLQUFLLEVBQUUsRUFBRSxFQUFFLFNBQVMsRUFBRSxHQUFHLEdBQzlFLE1BQU0sTUFBTSxDQUFDO0FBRWQsT0FBTyxFQUFFLFVBQVUsRUFBRSxNQUFNLHdCQUF3QixDQUFDO0FBS3BELE9BQU8sRUFBRSxvQkFBb0IsRUFBRSxNQUFNLGNBQWMsQ0FBQztBQUNwRCxPQUFPLEVBQUUsd0JBQXdCLEVBQUUsTUFBTSw0Q0FBNEMsQ0FBQztBQUV0RixPQUFPLEVBQ0wsT0FBTyxFQUFFLGNBQWMsRUFBRSxjQUFjLEVBQUUsV0FBVyxFQUFFLFVBQVUsRUFBRSxRQUFRLEVBQUUsU0FBUyxHQUN0RixNQUFNLGNBQWMsQ0FBQztBQUN0QixPQUFPLEVBQUUsd0JBQXdCLEVBQUUsTUFBTSxnREFBZ0QsQ0FBQzs7Ozs7QUFHMUYsOEVBQThFO0FBQzlFLDhFQUE4RTtBQUM5RSxNQUFNLENBQUMsTUFBTSxXQUFXLEdBQUcsRUFBRSxDQUFDO0FBb0Q5QiwyRUFBMkU7QUFDM0UsNEVBQTRFO0FBQzVFLFNBQVMsVUFBVSxDQUFDLENBQW1CLEVBQUUsQ0FBbUI7SUFDMUQsT0FBTyxDQUFDLENBQUMsVUFBVSxLQUFLLENBQUMsQ0FBQyxVQUFVO1dBQy9CLENBQUMsQ0FBQyxRQUFRLEtBQUssQ0FBQyxDQUFDLFFBQVE7V0FDekIsQ0FBQyxDQUFDLFVBQVUsS0FBSyxDQUFDLENBQUMsVUFBVTtXQUM3QixDQUFDLENBQUMsV0FBVyxLQUFLLENBQUMsQ0FBQyxXQUFXO1dBQy9CLGNBQWMsQ0FBQyxDQUFDLENBQUMsTUFBTSxFQUFFLENBQUMsQ0FBQyxNQUFNLENBQUMsQ0FBQztBQUMxQyxDQUFDO0FBRUQsOEVBQThFO0FBQzlFLG1FQUFtRTtBQUNuRSwyRUFBMkU7QUFDM0UsOEVBQThFO0FBQzlFLG1EQUFtRDtBQUNuRCxFQUFFO0FBQ0YsNkVBQTZFO0FBQzdFLDREQUE0RDtBQUM1RCxFQUFFO0FBQ0YsOEVBQThFO0FBQzlFLGdGQUFnRjtBQUNoRixnRkFBZ0Y7QUFDaEYsNkVBQTZFO0FBQzdFLDZHQUE2RztBQUM3Ryx3RUFBd0U7QUFDeEUsRUFBRTtBQUNGLDZFQUE2RTtBQUM3RSw0RUFBNEU7QUFDNUUsNkVBQTZFO0FBQzdFLDJFQUEyRTtBQUMzRSx5RUFBeUU7QUFDekUsOEVBQThFO0FBQzlFLCtDQUErQztBQWdCL0MsTUFBTSxPQUFPLHFCQUFxQjtJQUVoQixNQUFNLENBQVM7SUFDZixRQUFRLEdBQUcsS0FBSyxDQUFDO0lBRWpDLDJFQUEyRTtJQUMzRSw0RUFBNEU7SUFDNUUsMkRBQTJEO0lBQzNDLE1BQU0sR0FBa0IsSUFBSSxDQUFDO0lBRTdDLDJFQUEyRTtJQUMzRSw4Q0FBOEM7SUFDN0IsaUJBQWlCLEdBQUcsSUFBSSxZQUFZLEVBQW1CLENBQUM7SUFFekUsK0VBQStFO0lBQy9FLG9EQUFvRDtJQUNuQyxhQUFhLEdBQUcsSUFBSSxZQUFZLEVBQVEsQ0FBQztJQUUxRCw0RUFBNEU7SUFDNUUscUVBQXFFO0lBQ3BELFdBQVcsR0FBRyxJQUFJLFlBQVksRUFBaUIsQ0FBQztJQUcxRCxPQUFPLENBQXFCO0lBRW5DLDZFQUE2RTtJQUM3RSwyQ0FBMkM7SUFFbkMsbUJBQW1CLENBQXNDO0lBR3pELFNBQVMsQ0FBNkI7SUFHdEMsT0FBTyxDQUE2QjtJQUU1QixFQUFFLEdBQUcsV0FBVyxDQUFDO0lBRWpDLHNFQUFzRTtJQUN0RSw0RUFBNEU7SUFDNUUsMEVBQTBFO0lBQzFFLDJFQUEyRTtJQUMzRSx5REFBeUQ7SUFDekMsS0FBSyxHQUFHLE1BQU0sQ0FBZSxFQUFFLEVBQUUsRUFBRSxLQUFLLEVBQUUsR0FBRyxFQUFFLENBQUMsS0FBSyxFQUFFLENBQUMsQ0FBQztJQUN6RCxlQUFlLEdBQUcsTUFBTSxDQUFDLENBQUMsQ0FBQyxDQUFDO0lBQzVCLFlBQVksR0FBRyxRQUFRLENBQUMsR0FBRyxFQUFFLENBQUMsSUFBSSxDQUFDLEtBQUssRUFBRSxDQUFDLElBQUksQ0FBQyxlQUFlLEVBQUUsQ0FBQyxFQUFFLEVBQUUsSUFBSSxJQUFJLENBQUMsQ0FBQztJQUNoRixJQUFJLEdBQUcsTUFBTSxDQUFDLENBQUMsQ0FBQyxDQUFDO0lBRWpDLHlFQUF5RTtJQUN6RCxVQUFVLEdBQUcsTUFBTSxDQUFDLEtBQUssQ0FBQyxDQUFDO0lBQ3BDLE1BQU0sR0FBRyxJQUFJLEdBQUcsRUFBNkIsQ0FBQztJQUNyQyxtQkFBbUIsR0FBRyxNQUFNLENBQWdCLElBQUksQ0FBQyxDQUFDO0lBRWxFLDBFQUEwRTtJQUMxRSw4REFBOEQ7SUFDOUMsb0JBQW9CLEdBQUcsUUFBUSxDQUM3QyxHQUFHLEVBQUUsQ0FBQyxDQUFDLElBQUksQ0FBQyxLQUFLLEVBQUUsQ0FBQyxJQUFJLENBQUMsZUFBZSxFQUFFLENBQUMsRUFBRSxVQUFVLElBQUksRUFBRSxDQUFDLENBQUMsTUFBTSxDQUFDLE9BQU8sQ0FBQyxDQUMvRSxDQUFDO0lBRWMsZ0JBQWdCLEdBQUcsUUFBUSxDQUN6QyxHQUFHLEVBQUUsQ0FBQyxDQUFDLElBQUksQ0FBQyxPQUFPLEVBQUUsRUFBRSxNQUFNLEVBQUUsVUFBVSxJQUFJLEVBQUUsQ0FBQyxDQUFDLE1BQU0sQ0FBQyxPQUFPLENBQUMsQ0FDakUsQ0FBQztJQUVGLCtFQUErRTtJQUMvRSw4RUFBOEU7SUFDOUUsNkVBQTZFO0lBQzdFLDRFQUE0RTtJQUM1RSxxRUFBcUU7SUFDckUsMEVBQTBFO0lBQzFFLCtEQUErRDtJQUMvQyxVQUFVLEdBQUcsUUFBUSxDQUNuQyxHQUFHLEVBQUUsQ0FBQyxJQUFJLENBQUMsYUFBYSxDQUFDLElBQUksQ0FBQyxvQkFBb0IsRUFBRSxFQUFFLElBQUksQ0FBQyxXQUFXLEVBQUUsSUFBSSxDQUFDLFlBQVksRUFBRSxDQUFDLEVBQzVGLEVBQUUsS0FBSyxFQUFFLFVBQVUsRUFBRSxDQUN0QixDQUFDO0lBRWMsWUFBWSxHQUFHLFFBQVEsQ0FDckMsR0FBRyxFQUFFLENBQUMsSUFBSSxDQUFDLGFBQWEsQ0FBQyxJQUFJLENBQUMsc0JBQXNCLEVBQUUsRUFBRSxJQUFJLENBQUMsYUFBYSxFQUFFLElBQUksQ0FBQyxPQUFPLEVBQUUsRUFBRSxNQUFNLEVBQUUsRUFBRSxJQUFJLElBQUksQ0FBQyxFQUMvRyxFQUFFLEtBQUssRUFBRSxVQUFVLEVBQUUsQ0FDdEIsQ0FBQztJQUVGLHNFQUFzRTtJQUN0RCxPQUFPLEdBQWtCO1FBQ3ZDLFFBQVEsRUFBRSxDQUFDLFNBQVMsRUFBRSxDQUFDLEVBQUUsQ0FBQyxFQUFFLEVBQUUsQ0FBQyxJQUFJLENBQUMsU0FBUyxDQUFDLFNBQVMsRUFBRSxDQUFDLEVBQUUsQ0FBQyxDQUFDO1FBQzlELFVBQVUsRUFBRSxDQUFDLFNBQVMsRUFBRSxRQUFRLEVBQUUsTUFBTSxFQUFFLEVBQUUsQ0FBQyxJQUFJLENBQUMsV0FBVyxDQUFDLFNBQVMsRUFBRSxRQUFRLEVBQUUsTUFBTSxDQUFDO1FBQzFGLEtBQUssRUFBRSxHQUFHLEVBQUUsQ0FBQyxJQUFJLENBQUMsWUFBWSxFQUFFO0tBQ2pDLENBQUM7SUFFRiw0RUFBNEU7SUFDNUUsMEVBQTBFO0lBQzFFLHdFQUF3RTtJQUN4RSxxRUFBcUU7SUFDckUsNkJBQTZCO0lBQ2Isa0JBQWtCLEdBQUcsQ0FBQyxJQUFxQixFQUF1QixFQUFFO1FBQ2xGLE1BQU0sS0FBSyxHQUFHLElBQUksQ0FBQyxrQkFBa0IsQ0FBQyxJQUFJLENBQUMsQ0FBQyxDQUFDLENBQUMsSUFBSSxDQUFDLE1BQU0sRUFBRSxNQUFNLENBQUMsQ0FBQyxDQUFDLElBQUksQ0FBQyxVQUFVLENBQUM7UUFFcEYsT0FBTyxJQUFJLEdBQUcsQ0FBQyxDQUFDLEtBQUssRUFBRSxVQUFVLElBQUksRUFBRSxDQUFDO2FBQ3JDLE1BQU0sQ0FBQyxDQUFDLFNBQVMsRUFBRSxFQUFFLENBQUMsU0FBUyxDQUFDLElBQUksS0FBSyxNQUFNLElBQUksU0FBUyxDQUFDLEVBQUUsS0FBSyxJQUFJLENBQUMsRUFBRSxDQUFDO2FBQzVFLE9BQU8sQ0FBQyxDQUFDLFNBQVMsRUFBRSxFQUFFLENBQUMsU0FBUyxDQUFDLFNBQVMsQ0FBQyxNQUFNLEVBQUUsSUFBSSxDQUFDLENBQUMsQ0FBQyxDQUFDO0lBQ2hFLENBQUMsQ0FBQztJQUVNLFdBQVcsR0FBRyxNQUFNLENBQUMsVUFBVSxDQUFDLENBQUM7SUFDakMsWUFBWSxHQUFHLE1BQU0sQ0FBQyx3QkFBd0IsQ0FBQyxDQUFDO0lBQ2hELE9BQU8sR0FBRyxNQUFNLENBQUMsUUFBUSxDQUFDLENBQUM7SUFDM0IsUUFBUSxHQUFHLE1BQU0sQ0FBQyxTQUFTLENBQUMsQ0FBQztJQUM3QixXQUFXLEdBQUcsTUFBTSxDQUFDLFVBQVUsQ0FBQyxDQUFDO0lBQ2pDLE9BQU8sR0FBRyxLQUFLLENBQUM7SUFDaEIsa0JBQWtCLEdBQUcsQ0FBQyxDQUFDO0lBRS9CLCtFQUErRTtJQUMvRSw0RUFBNEU7SUFDNUUsWUFBWTtJQUNKLGNBQWMsR0FBa0IsSUFBSSxDQUFDO0lBRTdDLHdFQUF3RTtJQUN4RSw0RUFBNEU7SUFDNUUsd0VBQXdFO0lBQ3hFLDJDQUEyQztJQUNuQyxPQUFPLEdBQUcsTUFBTSxDQUFnQixJQUFJLEVBQUUsRUFBRSxLQUFLLEVBQUUsR0FBRyxFQUFFLENBQUMsS0FBSyxFQUFFLENBQUMsQ0FBQztJQUV0RSx3REFBd0Q7SUFDaEQsb0JBQW9CLEdBQUcsUUFBUSxDQUFDLEdBQUcsRUFBRSxDQUFDLElBQUksQ0FBQyxLQUFLLEVBQUUsQ0FBQyxJQUFJLENBQUMsZUFBZSxFQUFFLENBQUMsRUFBRSxNQUFNLElBQUksRUFBRSxDQUFDLENBQUM7SUFDMUYsc0JBQXNCLEdBQUcsUUFBUSxDQUFDLEdBQUcsRUFBRSxDQUFDLElBQUksQ0FBQyxPQUFPLEVBQUUsRUFBRSxNQUFNLEVBQUUsTUFBTSxJQUFJLEVBQUUsQ0FBQyxDQUFDO0lBRXRGLHVFQUF1RTtJQUN2RSwwQ0FBMEM7SUFDbEMsYUFBYSxHQUFHLFFBQVEsQ0FBQyxHQUFHLEVBQUUsQ0FBQyxJQUFJLENBQUMsVUFBVSxFQUFFLElBQUksSUFBSSxDQUFDLEtBQUssRUFBRSxDQUFDLElBQUksQ0FBQyxDQUFDLElBQUksRUFBRSxFQUFFLENBQUMsQ0FBQyxJQUFJLENBQUMsWUFBWSxDQUFDLENBQUMsQ0FBQztJQUU3RyxnRUFBZ0U7SUFDeEQsV0FBVyxHQUFHLElBQUksQ0FBQyxXQUFXLENBQUMsR0FBRyxFQUFFLENBQUMsSUFBSSxDQUFDLFVBQVUsQ0FBQyxDQUFDO0lBQ3RELGFBQWEsR0FBRyxJQUFJLENBQUMsV0FBVyxDQUFDLEdBQUcsRUFBRSxDQUFDLENBQUMsSUFBSSxDQUFDLGFBQWEsRUFBRSxDQUFDLENBQUMsQ0FBQyxJQUFJLENBQUMsTUFBTSxFQUFFLE1BQU0sSUFBSSxJQUFJLENBQUMsQ0FBQyxDQUFDLElBQUksQ0FBQyxDQUFDLENBQUM7SUFFNUcsaUVBQWlFO0lBQ3pELGVBQWUsR0FBRyxNQUFNLENBQUMsQ0FBQyxDQUFDLENBQUM7SUFFcEMseUVBQXlFO0lBQ3pFLDZEQUE2RDtJQUNyRCxpQkFBaUIsR0FBRyxJQUFJLEdBQUcsRUFBdUIsQ0FBQztJQUUzRDtRQUNFLElBQUksQ0FBQyxLQUFLLEVBQUUsQ0FBQztJQUNmLENBQUM7SUFFTSxXQUFXLENBQUMsT0FBc0I7UUFDdkMsdUVBQXVFO1FBQ3ZFLHNDQUFzQztRQUN0QyxJQUFJLE9BQU8sQ0FBQyxRQUFRLElBQUksQ0FBQyxJQUFJLENBQUMsUUFBUSxFQUFFLENBQUM7WUFDdkMsSUFBSSxDQUFDLFVBQVUsQ0FBQyxHQUFHLENBQUMsS0FBSyxDQUFDLENBQUM7UUFDN0IsQ0FBQztRQUVELElBQUksQ0FBQyxNQUFNLEdBQUcsSUFBSSxHQUFHLENBQUMsQ0FBQyxJQUFJLENBQUMsTUFBTSxFQUFFLFlBQVksSUFBSSxFQUFFLENBQUMsQ0FBQyxHQUFHLENBQUMsQ0FBQyxLQUFLLEVBQUUsRUFBRSxDQUFDLENBQUMsS0FBSyxDQUFDLEVBQUUsRUFBRSxLQUFLLENBQUMsQ0FBQyxDQUFDLENBQUM7UUFDM0YsSUFBSSxDQUFDLEtBQUssQ0FBQyxHQUFHLENBQUMsSUFBSSxDQUFDLE1BQU0sRUFBRSxLQUFLLElBQUksRUFBRSxDQUFDLENBQUM7UUFFekMsTUFBTSxTQUFTLEdBQUcsSUFBSSxDQUFDLEtBQUssRUFBRSxDQUFDLE1BQU0sQ0FBQztRQUV0Qyx1RUFBdUU7UUFDdkUsTUFBTSxTQUFTLEdBQUcsU0FBUyxHQUFHLElBQUksQ0FBQyxrQkFBa0IsSUFBSSxJQUFJLENBQUMsa0JBQWtCLEdBQUcsQ0FBQyxDQUFDO1FBQ3JGLElBQUksU0FBUyxFQUFFLENBQUM7WUFDZCxJQUFJLENBQUMsZUFBZSxDQUFDLEdBQUcsQ0FBQyxTQUFTLEdBQUcsQ0FBQyxDQUFDLENBQUM7UUFDMUMsQ0FBQztRQUNELElBQUksQ0FBQyxrQkFBa0IsR0FBRyxTQUFTLENBQUM7UUFFcEMsMkVBQTJFO1FBQzNFLDRFQUE0RTtRQUM1RSwwRUFBMEU7UUFDMUUsdUVBQXVFO1FBQ3ZFLGtEQUFrRDtRQUNsRCxJQUFJLENBQUMsU0FBUyxJQUFJLElBQUksQ0FBQyxNQUFNLElBQUksSUFBSSxFQUFFLENBQUM7WUFDdEMsTUFBTSxLQUFLLEdBQUcsSUFBSSxDQUFDLEtBQUssRUFBRSxDQUFDLFNBQVMsQ0FBQyxDQUFDLElBQUksRUFBRSxFQUFFLENBQUMsSUFBSSxDQUFDLEVBQUUsS0FBSyxJQUFJLENBQUMsTUFBTSxDQUFDLENBQUM7WUFFeEUsSUFBSSxLQUFLLEdBQUcsQ0FBQyxDQUFDLEVBQUUsQ0FBQztnQkFDZixJQUFJLENBQUMsZUFBZSxDQUFDLEdBQUcsQ0FBQyxLQUFLLENBQUMsQ0FBQztZQUNsQyxDQUFDO1FBQ0gsQ0FBQztRQUVELElBQUksSUFBSSxDQUFDLGVBQWUsRUFBRSxJQUFJLFNBQVMsRUFBRSxDQUFDO1lBQ3hDLElBQUksQ0FBQyxlQUFlLENBQUMsR0FBRyxDQUFDLENBQUMsQ0FBQyxDQUFDO1FBQzlCLENBQUM7UUFFRCx5RUFBeUU7UUFDekUsc0VBQXNFO1FBQ3RFLGlFQUFpRTtRQUNqRSwwRUFBMEU7UUFDMUUscUNBQXFDO1FBQ3JDLE1BQU0sWUFBWSxHQUFHLElBQUksQ0FBQyxVQUFVLEVBQUUsRUFBRSxJQUFJLElBQUksQ0FBQztRQUNqRCxJQUFJLFlBQVksS0FBSyxJQUFJLENBQUMsY0FBYyxFQUFFLENBQUM7WUFDekMsSUFBSSxDQUFDLGNBQWMsR0FBRyxZQUFZLENBQUM7WUFDbkMsSUFBSSxDQUFDLFdBQVcsQ0FBQyxJQUFJLENBQUMsWUFBWSxDQUFDLENBQUM7UUFDdEMsQ0FBQztRQUVELHVFQUF1RTtRQUN2RSx3RUFBd0U7UUFDeEUsY0FBYztRQUNkLElBQUksT0FBTyxDQUFDLE1BQU0sRUFBRSxDQUFDO1lBQ25CLElBQUksQ0FBQyxPQUFPLENBQUMsR0FBRyxDQUFDLElBQUksQ0FBQyxNQUFNLENBQUMsQ0FBQztZQUM5QixJQUFJLENBQUMsc0JBQXNCLEVBQUUsQ0FBQztZQUM5QixJQUFJLENBQUMsZ0JBQWdCLENBQUMsSUFBSSxDQUFDLFdBQVcsQ0FBQyxDQUFDO1lBQ3hDLElBQUksQ0FBQyxnQkFBZ0IsQ0FBQyxJQUFJLENBQUMsYUFBYSxDQUFDLENBQUM7UUFDNUMsQ0FBQztJQUNILENBQUM7SUFFRCxxRUFBcUU7SUFDckUsNEVBQTRFO0lBQzVFLElBQVcsYUFBYTtRQUN0QixNQUFNLE1BQU0sR0FBRyxJQUFJLENBQUMsTUFBTSxFQUFFLE1BQU0sRUFBRSxNQUFNLEVBQUUsT0FBTyxFQUFFLElBQUksSUFBSSxvQkFBb0IsQ0FBQztRQUVsRixPQUFPLE1BQU0sR0FBRyxDQUFDLFdBQVcsR0FBRyxFQUFFLENBQUMsQ0FBQztJQUNyQyxDQUFDO0lBRU0sZUFBZTtRQUNwQixvRUFBb0U7UUFDcEUsdURBQXVEO1FBQ3ZELFVBQVUsQ0FBQyxHQUFHLEVBQUUsQ0FBQyxJQUFJLENBQUMsT0FBTyxFQUFFLENBQUMsQ0FBQztJQUNuQyxDQUFDO0lBRUQsSUFBVyxVQUFVO1FBQ25CLE9BQU8sSUFBSSxDQUFDLEtBQUssRUFBRSxDQUFDLElBQUksQ0FBQyxlQUFlLEVBQUUsQ0FBQyxJQUFJLElBQUksQ0FBQztJQUN0RCxDQUFDO0lBRUQsb0RBQW9EO0lBQ3BELElBQVcsS0FBSztRQUNkLE9BQU8sSUFBSSxDQUFDLE1BQU0sRUFBRSxNQUFNLEVBQUUsWUFBWSxJQUFJLEVBQUUsWUFBWSxFQUFFLENBQUMsRUFBRSxZQUFZLEVBQUUsQ0FBQyxFQUFFLENBQUM7SUFDbkYsQ0FBQztJQUVELHlFQUF5RTtJQUN6RSw0RUFBNEU7SUFDNUUsSUFBVyxhQUFhO1FBQ3RCLE9BQU8sSUFBSSxDQUFDLFVBQVUsRUFBRSxJQUFJLENBQUMsSUFBSSxDQUFDLFVBQVUsRUFBRSxZQUFZLENBQUM7SUFDN0QsQ0FBQztJQUVELHVDQUF1QztJQUN2QyxJQUFXLGFBQWE7UUFDdEIsT0FBTyxJQUFJLENBQUMsUUFBUSxJQUFJLENBQUMsSUFBSSxDQUFDLFVBQVUsRUFBRSxDQUFDO0lBQzdDLENBQUM7SUFFRCxJQUFXLGVBQWU7UUFDeEIsT0FBTyxJQUFJLENBQUMsUUFBUSxJQUFJLElBQUksQ0FBQyxVQUFVLEVBQUUsQ0FBQztJQUM1QyxDQUFDO0lBRU0sZ0JBQWdCO1FBQ3JCLElBQUksQ0FBQyxVQUFVLENBQUMsTUFBTSxDQUFDLENBQUMsS0FBSyxFQUFFLEVBQUUsQ0FBQyxDQUFDLEtBQUssQ0FBQyxDQUFDO1FBQzFDLElBQUksQ0FBQyxtQkFBbUIsQ0FBQyxHQUFHLENBQUMsSUFBSSxDQUFDLENBQUM7SUFDckMsQ0FBQztJQUVELDZFQUE2RTtJQUM3RSw0RUFBNEU7SUFDNUUsNEVBQTRFO0lBQ3JFLE9BQU87UUFDWixJQUFJLENBQUMsSUFBSSxDQUFDLE1BQU0sRUFBRSxDQUFDO1lBQ2pCLE9BQU87UUFDVCxDQUFDO1FBRUQsTUFBTSxFQUFFLFlBQVksRUFBRSxZQUFZLEVBQUUsR0FBRyxJQUFJLENBQUMsS0FBSyxDQUFDO1FBQ2xELE1BQU0sU0FBUyxHQUFHLElBQUksQ0FBQyxNQUFNLENBQUMsU0FBUyxDQUFDO1FBQ3hDLE1BQU0sVUFBVSxHQUFHLElBQUksQ0FBQyxNQUFNLENBQUMsVUFBVSxDQUFDO1FBQzFDLE1BQU0sUUFBUSxHQUFHLElBQUksQ0FBQyxVQUFVLEVBQUUsQ0FBQztRQUVuQyxJQUFJLFFBQVEsR0FBRyxFQUFFLENBQUMsRUFBRSxHQUFHLEVBQUUsQ0FBQyxFQUFFLFlBQVksR0FBRyxHQUFHLEVBQUUsQ0FBQyxFQUFFLElBQUksQ0FBQyxHQUFHLENBQUMsQ0FBQyxFQUFFLFNBQVMsR0FBRyxDQUFDLENBQUMsRUFBRSxDQUFDLEVBQUUsR0FBRyxFQUFFLENBQUM7UUFDeEYsSUFBSSxRQUFRLEVBQUUsQ0FBQztZQUNiLE1BQU0sVUFBVSxHQUFHLFlBQVksSUFBSSxZQUFZLElBQUksR0FBRyxDQUFDO1lBQ3ZELE1BQU0sQ0FBQyxHQUFHLFlBQVk7Z0JBQ3BCLENBQUMsQ0FBQyxVQUFVLEdBQUcsWUFBWTtnQkFDM0IsQ0FBQyxDQUFDLENBQUMsWUFBWSxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLFVBQVUsR0FBRyxVQUFVLENBQUMsQ0FBQztZQUNqRCxRQUFRLEdBQUcsRUFBRSxDQUFDLEVBQUUsR0FBRyxFQUFFLENBQUMsRUFBRSxDQUFDLEdBQUcsSUFBSSxFQUFFLENBQUMsRUFBRSxJQUFJLENBQUMsR0FBRyxDQUFDLENBQUMsRUFBRSxTQUFTLEdBQUcsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxFQUFFLElBQUksQ0FBQyxHQUFHLENBQUMsR0FBRyxFQUFFLFVBQVUsR0FBRyxHQUFHLENBQUMsRUFBRSxDQUFDO1FBQ3hHLENBQUM7UUFFRCxJQUFJLENBQUMsV0FBVyxDQUFDLE9BQU8sQ0FBQyxJQUFJLENBQUMsTUFBTSxDQUFDLEVBQUUsRUFBRTtZQUN2QyxHQUFHLFFBQVE7WUFDWCxNQUFNLEVBQUUsUUFBUSxDQUFDLENBQUMsQ0FBQyxTQUFTLENBQUMsQ0FBQyxDQUFDLElBQUksQ0FBQyxVQUFVLEVBQUUsRUFBRTtTQUNuRCxDQUFDO2FBQ0MsSUFBSSxDQUFDLGtCQUFrQixDQUFDLElBQUksQ0FBQyxXQUFXLENBQUMsQ0FBQzthQUMxQyxTQUFTLENBQUMsR0FBRyxFQUFFLENBQUMsSUFBSSxDQUFDLGFBQWEsQ0FBQyxJQUFJLEVBQUUsQ0FBQyxDQUFDO0lBQ2hELENBQUM7SUFFRCw2RUFBNkU7SUFDN0UsMEVBQTBFO0lBQzFFLGtFQUFrRTtJQUNsRSw4REFBOEQ7SUFDdkQsa0JBQWtCLENBQUMsV0FBbUI7UUFDM0MsTUFBTSxNQUFNLEdBQUcsQ0FBQyxJQUFJLENBQUMsVUFBVSxFQUFFLFVBQVUsRUFBRSxJQUFJLENBQUMsTUFBTSxFQUFFLE1BQU0sRUFBRSxVQUFVLENBQUMsQ0FBQztRQUM5RSxLQUFLLE1BQU0sVUFBVSxJQUFJLE1BQU0sRUFBRSxDQUFDO1lBQ2hDLE1BQU0sS0FBSyxHQUFHLFVBQVUsRUFBRSxTQUFTLENBQUMsQ0FBQyxTQUFTLEVBQUUsRUFBRSxDQUFDLFNBQVMsQ0FBQyxFQUFFLEtBQUssV0FBVyxDQUFDLElBQUksQ0FBQyxDQUFDLENBQUM7WUFDdkYsSUFBSSxLQUFLLEdBQUcsQ0FBQyxDQUFDLEVBQUUsQ0FBQztnQkFDZixVQUFVLENBQUMsTUFBTSxDQUFDLEtBQUssRUFBRSxDQUFDLENBQUMsQ0FBQztZQUM5QixDQUFDO1FBQ0gsQ0FBQztRQUVELElBQUksQ0FBQyxtQkFBbUIsQ0FBQyxHQUFHLENBQUMsSUFBSSxDQUFDLENBQUM7UUFDbkMsSUFBSSxDQUFDLEtBQUssQ0FBQyxHQUFHLENBQUMsSUFBSSxDQUFDLEtBQUssRUFBRSxDQUFDLENBQUM7UUFDN0IsSUFBSSxDQUFDLE9BQU8sQ0FBQyxHQUFHLENBQUMsSUFBSSxDQUFDLE1BQU0sQ0FBQyxDQUFDO1FBQzlCLElBQUksQ0FBQyxRQUFRLENBQUMsT0FBTyxDQUFDLGNBQWMsQ0FBQyxDQUFDO0lBQ3hDLENBQUM7SUFFRCwwRUFBMEU7SUFDMUUsMkVBQTJFO0lBQzNFLDZFQUE2RTtJQUM3RSw2RUFBNkU7SUFDdEUsV0FBVyxDQUFDLElBQXFCLEVBQUUsSUFBWTtRQUNwRCxNQUFNLFFBQVEsR0FBRyxJQUFJLENBQUMsa0JBQWtCLENBQUMsSUFBSSxDQUFDLENBQUM7UUFDL0MsTUFBTSxLQUFLLEdBQUcsUUFBUSxDQUFDLENBQUMsQ0FBQyxJQUFJLENBQUMsYUFBYSxDQUFDLENBQUMsQ0FBQyxJQUFJLENBQUMsV0FBVyxDQUFDO1FBQy9ELE1BQU0sT0FBTyxHQUFHLFFBQVEsQ0FBQyxDQUFDLENBQUMsQ0FBQyxJQUFJLENBQUMsTUFBTSxFQUFFLE1BQU0sRUFBRSxFQUFFLElBQUksSUFBSSxDQUFDLENBQUMsQ0FBQyxDQUFDLElBQUksQ0FBQyxZQUFZLEVBQUUsQ0FBQztRQUNuRixNQUFNLE9BQU8sR0FBRyxLQUFLLENBQUMsT0FBTyxFQUFFLENBQUM7UUFDaEMsTUFBTSxJQUFJLEdBQUcsT0FBTyxFQUFFLE1BQU0sS0FBSyxPQUFPLENBQUMsQ0FBQyxDQUFDLE9BQU8sQ0FBQyxJQUFJLENBQUMsQ0FBQyxDQUFDLElBQUksQ0FBQztRQUMvRCxNQUFNLE1BQU0sR0FBRyxRQUFRLENBQUMsQ0FBQyxDQUFDLElBQUksQ0FBQyxzQkFBc0IsRUFBRSxDQUFDLENBQUMsQ0FBQyxJQUFJLENBQUMsb0JBQW9CLEVBQUUsQ0FBQztRQUN0RixNQUFNLE1BQU0sR0FBRyxXQUFXLENBQUMsTUFBTSxFQUFFLENBQUMsRUFBRSxHQUFHLElBQUksRUFBRSxNQUFNLEVBQUUsRUFBRSxHQUFHLElBQUksQ0FBQyxNQUFNLEVBQUUsSUFBSSxFQUFFLEVBQUUsQ0FBQyxDQUFDO2FBQ2hGLElBQUksQ0FBQyxDQUFDLEtBQUssRUFBRSxFQUFFLENBQUMsQ0FBQyxJQUFJLEVBQUUsR0FBRyxDQUFDLEtBQUssQ0FBQyxFQUFFLENBQUMsQ0FBQyxDQUFDO1FBRXpDLElBQUksTUFBTSxFQUFFLENBQUM7WUFDWCxLQUFLLENBQUMsT0FBTyxDQUFDLElBQUksRUFBRSxDQUFDO1FBQ3ZCLENBQUM7SUFDSCxDQUFDO0lBRUQsMkVBQTJFO0lBQzNFLGtFQUFrRTtJQUMzRCxpQkFBaUIsQ0FBQyxJQUFxQixFQUFFLEdBQVc7UUFDekQsTUFBTSxNQUFNLEdBQUcsSUFBSSxDQUFDLGtCQUFrQixDQUFDLElBQUksQ0FBQyxDQUFDLENBQUMsQ0FBQyxJQUFJLENBQUMsc0JBQXNCLEVBQUUsQ0FBQyxDQUFDLENBQUMsSUFBSSxDQUFDLG9CQUFvQixFQUFFLENBQUM7UUFDM0csaUVBQWlFO1FBQ2pFLE1BQU0sS0FBSyxHQUFHLE1BQU0sQ0FBQyxNQUFNLENBQUMsQ0FBQyxTQUFTLEVBQUUsRUFBRSxDQUFDLFFBQVEsQ0FBQyxTQUFTLENBQUMsS0FBSyxHQUFHLENBQUMsQ0FBQyxHQUFHLEVBQUUsQ0FBQztRQUU5RSxJQUFJLEtBQUssRUFBRSxDQUFDO1lBQ1YsSUFBSSxDQUFDLGlCQUFpQixDQUFDLElBQUksQ0FBQyxLQUFLLENBQUMsQ0FBQztRQUNyQyxDQUFDO0lBQ0gsQ0FBQztJQUVELHdFQUF3RTtJQUNqRSxrQkFBa0IsQ0FBQyxJQUFnQjtRQUN4QyxNQUFNLFlBQVksR0FBRyxDQUFDLElBQUksQ0FBQyxZQUFZLENBQUM7UUFFeEMsSUFBSSxDQUFDLFdBQVcsQ0FBQyxVQUFVLENBQUMsSUFBSSxDQUFDLE1BQU0sQ0FBQyxFQUFFLEVBQUUsSUFBSSxDQUFDLEVBQUUsRUFBRSxFQUFFLFlBQVksRUFBRSxDQUFDO2FBQ25FLElBQUksQ0FBQyxrQkFBa0IsQ0FBQyxJQUFJLENBQUMsV0FBVyxDQUFDLENBQUM7YUFDMUMsU0FBUyxDQUFDLEdBQUcsRUFBRTtZQUNkLElBQUksQ0FBQyxZQUFZLEdBQUcsWUFBWSxDQUFDO1lBQ2pDLElBQUksQ0FBQyxLQUFLLENBQUMsR0FBRyxDQUFDLElBQUksQ0FBQyxLQUFLLEVBQUUsQ0FBQyxDQUFDO1lBQzdCLElBQUksQ0FBQyxRQUFRLENBQUMsT0FBTyxDQUFDLFlBQVksQ0FBQyxDQUFDLENBQUMscUNBQXFDLENBQUMsQ0FBQyxDQUFDLG9DQUFvQyxDQUFDLENBQUM7UUFDckgsQ0FBQyxDQUFDLENBQUM7SUFDUCxDQUFDO0lBRU0sVUFBVSxDQUFDLEtBQWE7UUFDN0IsSUFBSSxDQUFDLGVBQWUsQ0FBQyxHQUFHLENBQUMsS0FBSyxDQUFDLENBQUM7UUFDaEMsSUFBSSxDQUFDLG1CQUFtQixDQUFDLEdBQUcsQ0FBQyxJQUFJLENBQUMsQ0FBQztRQUVuQywyRUFBMkU7UUFDM0UscUNBQXFDO1FBQ3JDLElBQUksQ0FBQyxjQUFjLEdBQUcsSUFBSSxDQUFDLFVBQVUsRUFBRSxFQUFFLElBQUksSUFBSSxDQUFDO1FBQ2xELElBQUksQ0FBQyxXQUFXLENBQUMsSUFBSSxDQUFDLElBQUksQ0FBQyxjQUFjLENBQUMsQ0FBQztJQUM3QyxDQUFDO0lBRUQsNEVBQTRFO0lBQzVFLG1DQUFtQztJQUM1QixPQUFPO1FBQ1osSUFBSSxDQUFDLElBQUksQ0FBQyxNQUFNLEVBQUUsQ0FBQztZQUNqQixPQUFPO1FBQ1QsQ0FBQztRQUVELElBQUksQ0FBQyxXQUFXLENBQUMsT0FBTyxDQUFDLElBQUksQ0FBQyxNQUFNLENBQUMsRUFBRSxDQUFDO2FBQ3JDLElBQUksQ0FBQyxrQkFBa0IsQ0FBQyxJQUFJLENBQUMsV0FBVyxDQUFDLENBQUM7YUFDMUMsU0FBUyxDQUFDLEdBQUcsRUFBRSxDQUFDLElBQUksQ0FBQyxhQUFhLENBQUMsSUFBSSxFQUFFLENBQUMsQ0FBQztJQUNoRCxDQUFDO0lBRU0sU0FBUyxDQUFDLElBQWdCLEVBQUUsS0FBYTtRQUM5QyxPQUFPLElBQUksQ0FBQyxJQUFJLElBQUksUUFBUSxLQUFLLEdBQUcsQ0FBQyxFQUFFLENBQUM7SUFDMUMsQ0FBQztJQUVELDZFQUE2RTtJQUM3RSx5RUFBeUU7SUFDekUseUVBQXlFO0lBQ3pFLGdCQUFnQjtJQUNULFVBQVUsQ0FBQyxJQUFnQjtRQUNoQyxJQUFJLENBQUMsT0FBTyxDQUFDLEtBQUssQ0FBQztZQUNqQixLQUFLLEVBQUUsZ0JBQWdCO1lBQ3ZCLEtBQUssRUFBRSxNQUFNO1lBQ2IsT0FBTyxFQUFFLElBQUksQ0FBQyxJQUFJLElBQUksRUFBRTtZQUN4QixXQUFXLEVBQUUsTUFBTTtZQUNuQixRQUFRLEVBQUUsSUFBSTtTQUNmLENBQUM7YUFDQyxJQUFJLENBQ0gsU0FBUyxDQUFDLENBQUMsSUFBWSxFQUFFLEVBQUUsQ0FBQyxJQUFJLENBQUMsV0FBVzthQUN6QyxVQUFVLENBQUMsSUFBSSxDQUFDLE1BQU0sQ0FBQyxFQUFFLEVBQUUsSUFBSSxDQUFDLEVBQUUsRUFBRSxFQUFFLElBQUksRUFBRSxDQUFDO2FBQzdDLElBQUksQ0FBQyxHQUFHLENBQUMsR0FBRyxFQUFFLENBQUMsSUFBSSxDQUFDLENBQUMsQ0FBQyxFQUN6QixrQkFBa0IsQ0FBQyxJQUFJLENBQUMsV0FBVyxDQUFDLENBQ3JDO2FBQ0EsU0FBUyxDQUFDLENBQUMsSUFBWSxFQUFFLEVBQUU7WUFDMUIsSUFBSSxDQUFDLElBQUksR0FBRyxJQUFJLENBQUM7WUFDakIsSUFBSSxDQUFDLEtBQUssQ0FBQyxHQUFHLENBQUMsSUFBSSxDQUFDLEtBQUssRUFBRSxDQUFDLENBQUM7WUFDN0IsSUFBSSxDQUFDLFFBQVEsQ0FBQyxPQUFPLENBQUMsaUJBQWlCLENBQUMsQ0FBQztRQUMzQyxDQUFDLENBQUMsQ0FBQztJQUNQLENBQUM7SUFFRCx1RUFBdUU7SUFDdkUsNkVBQTZFO0lBQzdFLDJFQUEyRTtJQUNwRSxVQUFVLENBQUMsSUFBZ0I7UUFDaEMsSUFBSSxDQUFDLE9BQU8sQ0FBQyxPQUFPLENBQUM7WUFDbkIsS0FBSyxFQUFFLFNBQVM7WUFDaEIsUUFBUSxFQUFFLDBDQUEwQyxJQUFJLENBQUMsU0FBUyxDQUFDLElBQUksRUFBRSxJQUFJLENBQUMsS0FBSyxFQUFFLENBQUMsT0FBTyxDQUFDLElBQUksQ0FBQyxDQUFDLHlCQUF5QjtTQUM5SCxDQUFDO2FBQ0MsSUFBSSxDQUNILFNBQVMsQ0FBQyxHQUFHLEVBQUUsQ0FBQyxJQUFJLENBQUMsV0FBVyxDQUFDLFVBQVUsQ0FBQyxJQUFJLENBQUMsTUFBTSxDQUFDLEVBQUUsRUFBRSxJQUFJLENBQUMsRUFBRSxDQUFDLENBQUMsRUFDckUsa0JBQWtCLENBQUMsSUFBSSxDQUFDLFdBQVcsQ0FBQyxDQUNyQzthQUNBLFNBQVMsQ0FBQyxHQUFHLEVBQUU7WUFDZCxNQUFNLEtBQUssR0FBRyxJQUFJLENBQUMsS0FBSyxFQUFFLENBQUM7WUFDM0IsTUFBTSxLQUFLLEdBQUcsS0FBSyxDQUFDLE9BQU8sQ0FBQyxJQUFJLENBQUMsQ0FBQztZQUNsQyxLQUFLLENBQUMsTUFBTSxDQUFDLEtBQUssRUFBRSxDQUFDLENBQUMsQ0FBQztZQUN2QixJQUFJLENBQUMsS0FBSyxDQUFDLEdBQUcsQ0FBQyxLQUFLLENBQUMsQ0FBQztZQUV0QixzRUFBc0U7WUFDdEUsdUVBQXVFO1lBQ3ZFLElBQUksQ0FBQyxlQUFlLENBQUMsR0FBRyxDQUFDLElBQUksQ0FBQyxHQUFHLENBQUMsS0FBSyxFQUFFLEtBQUssQ0FBQyxNQUFNLEdBQUcsQ0FBQyxDQUFDLENBQUMsQ0FBQztZQUM1RCxJQUFJLENBQUMsa0JBQWtCLEdBQUcsS0FBSyxDQUFDLE1BQU0sQ0FBQztZQUN2QyxJQUFJLENBQUMsbUJBQW1CLENBQUMsR0FBRyxDQUFDLElBQUksQ0FBQyxDQUFDO1lBRW5DLGdFQUFnRTtZQUNoRSxzRUFBc0U7WUFDdEUsSUFBSSxDQUFDLFdBQVcsQ0FBQyxJQUFJLENBQUMsSUFBSSxDQUFDLFVBQVUsRUFBRSxFQUFFLElBQUksSUFBSSxDQUFDLENBQUM7WUFFbkQsSUFBSSxDQUFDLFFBQVEsQ0FBQyxPQUFPLENBQUMsY0FBYyxDQUFDLENBQUM7UUFDeEMsQ0FBQyxDQUFDLENBQUM7SUFDUCxDQUFDO0lBRUQsdUVBQXVFO0lBQ3ZFLDZFQUE2RTtJQUM3RSxpQ0FBaUM7SUFDMUIsYUFBYSxDQUFDLEtBQTJCO1FBQzlDLElBQUksS0FBSyxDQUFDLGFBQWEsS0FBSyxLQUFLLENBQUMsWUFBWSxFQUFFLENBQUM7WUFDL0MsT0FBTztRQUNULENBQUM7UUFFRCxNQUFNLFVBQVUsR0FBRyxJQUFJLENBQUMsVUFBVSxDQUFDO1FBQ25DLE1BQU0sS0FBSyxHQUFHLElBQUksQ0FBQyxLQUFLLEVBQUUsQ0FBQztRQUUzQixlQUFlLENBQUMsS0FBSyxFQUFFLEtBQUssQ0FBQyxhQUFhLEVBQUUsS0FBSyxDQUFDLFlBQVksQ0FBQyxDQUFDO1FBQ2hFLElBQUksQ0FBQyxLQUFLLENBQUMsR0FBRyxDQUFDLEtBQUssQ0FBQyxDQUFDO1FBRXRCLE1BQU0sU0FBUyxHQUFHLEtBQUssQ0FBQyxHQUFHLENBQUMsQ0FBQyxJQUFJLEVBQUUsS0FBSyxFQUFFLEVBQUU7WUFDMUMsSUFBSSxDQUFDLEtBQUssR0FBRyxLQUFLLENBQUM7WUFFbkIsT0FBTyxFQUFFLE1BQU0sRUFBRSxJQUFJLENBQUMsRUFBRSxFQUFFLEtBQUssRUFBRSxDQUFDO1FBQ3BDLENBQUMsQ0FBQyxDQUFDO1FBRUgsSUFBSSxVQUFVLEVBQUUsQ0FBQztZQUNmLElBQUksQ0FBQyxlQUFlLENBQUMsR0FBRyxDQUFDLEtBQUssQ0FBQyxPQUFPLENBQUMsVUFBVSxDQUFDLENBQUMsQ0FBQztRQUN0RCxDQUFDO1FBRUQsSUFBSSxDQUFDLFdBQVcsQ0FBQyxpQkFBaUIsQ0FBQyxJQUFJLENBQUMsTUFBTSxDQUFDLEVBQUUsRUFBRSxTQUFTLENBQUM7YUFDMUQsSUFBSSxDQUFDLGtCQUFrQixDQUFDLElBQUksQ0FBQyxXQUFXLENBQUMsQ0FBQzthQUMxQyxTQUFTLEVBQUUsQ0FBQztJQUNqQixDQUFDO0lBRUQsOEVBQThFO0lBQzlFLDBFQUEwRTtJQUMxRSw0RUFBNEU7SUFDNUUsMEVBQTBFO0lBQ25FLHNCQUFzQixDQUFDLFdBQW1CLEVBQUUsUUFBMkI7UUFDNUUsTUFBTSxRQUFRLEdBQUcsSUFBSSxDQUFDLG1CQUFtQjthQUN0QyxJQUFJLENBQUMsQ0FBQyxTQUFTLEVBQUUsRUFBRSxDQUFDLFNBQVMsQ0FBQyxTQUFTLENBQUMsRUFBRSxLQUFLLFdBQVcsQ0FBQyxDQUFDO1FBRS9ELElBQUksUUFBUSxFQUFFLENBQUM7WUFDYixRQUFRLENBQUMsYUFBYSxDQUFDLFFBQVEsQ0FBQyxDQUFDO1lBRWpDLE9BQU87UUFDVCxDQUFDO1FBRUQsTUFBTSxLQUFLLEdBQUcsQ0FBQyxHQUFHLElBQUksQ0FBQyxvQkFBb0IsRUFBRSxFQUFFLEdBQUcsSUFBSSxDQUFDLHNCQUFzQixFQUFFLENBQUM7YUFDN0UsSUFBSSxDQUFDLENBQUMsU0FBUyxFQUFFLEVBQUUsQ0FBQyxTQUFTLENBQUMsRUFBRSxLQUFLLFdBQVcsQ0FBQyxDQUFDO1FBRXJELGlEQUFpRDtRQUNqRCxJQUFJLEtBQUssSUFBSSxRQUFRLENBQUMsS0FBSyxFQUFFLElBQUksRUFBRSxFQUFFLENBQUM7WUFDcEMsS0FBSyxDQUFDLEtBQUssR0FBRyxRQUFRLENBQUMsS0FBSyxDQUFDLElBQUksRUFBRSxDQUFDO1lBQ3BDLElBQUksQ0FBQyxlQUFlLENBQUMsTUFBTSxDQUFDLENBQUMsUUFBUSxFQUFFLEVBQUUsQ0FBQyxRQUFRLEdBQUcsQ0FBQyxDQUFDLENBQUM7UUFDMUQsQ0FBQztJQUNILENBQUM7SUFFTSxlQUFlLENBQUMsV0FBMEI7UUFDL0MsSUFBSSxDQUFDLG1CQUFtQixDQUFDLEdBQUcsQ0FBQyxXQUFXLENBQUMsQ0FBQztJQUM1QyxDQUFDO0lBRU0sbUJBQW1CO1FBQ3hCLDBDQUEwQztRQUMxQyxJQUFJLElBQUksQ0FBQyxtQkFBbUIsRUFBRSxLQUFLLElBQUksRUFBRSxDQUFDO1lBQ3hDLElBQUksQ0FBQyxlQUFlLENBQUMsSUFBSSxDQUFDLENBQUM7UUFDN0IsQ0FBQztJQUNILENBQUM7SUFFRCwrRUFBK0U7SUFFeEUsUUFBUSxDQUFDLEtBQWE7UUFDM0IsSUFBSSxDQUFDLElBQUksQ0FBQyxHQUFHLENBQUMsS0FBSyxDQUFDLENBQUM7SUFDdkIsQ0FBQztJQUVNLE1BQU07UUFDWCxJQUFJLENBQUMsT0FBTyxFQUFFLE1BQU0sRUFBRSxDQUFDO0lBQ3pCLENBQUM7SUFFTSxPQUFPO1FBQ1osSUFBSSxDQUFDLE9BQU8sRUFBRSxPQUFPLEVBQUUsQ0FBQztJQUMxQixDQUFDO0lBRU0sT0FBTztRQUNaLE1BQU0sUUFBUSxHQUFHLElBQUksQ0FBQyxTQUFTLEVBQUUsYUFBYSxDQUFDO1FBQy9DLElBQUksQ0FBQyxRQUFRLElBQUksQ0FBQyxJQUFJLENBQUMsTUFBTSxFQUFFLFNBQVMsSUFBSSxDQUFDLElBQUksQ0FBQyxPQUFPLEVBQUUsQ0FBQztZQUMxRCxPQUFPO1FBQ1QsQ0FBQztRQUVELE1BQU0sR0FBRyxHQUFHLElBQUksQ0FBQyxHQUFHLENBQ2xCLENBQUMsUUFBUSxDQUFDLFdBQVcsR0FBRyxFQUFFLENBQUMsR0FBRyxDQUFDLElBQUksQ0FBQyxNQUFNLENBQUMsU0FBUyxHQUFHLFdBQVcsQ0FBQyxFQUNuRSxDQUFDLFFBQVEsQ0FBQyxZQUFZLEdBQUcsRUFBRSxDQUFDLEdBQUcsQ0FBQyxJQUFJLENBQUMsTUFBTSxDQUFDLFVBQVUsR0FBRyxXQUFXLENBQUMsQ0FDdEUsQ0FBQztRQUVGLElBQUksQ0FBQyxPQUFPLENBQUMsSUFBSSxDQUFDLElBQUksQ0FBQyxHQUFHLENBQUMsR0FBRyxFQUFFLElBQUksQ0FBQyxHQUFHLENBQUMsR0FBRyxFQUFFLEdBQUcsQ0FBQyxDQUFDLENBQUMsQ0FBQztRQUNyRCxJQUFJLENBQUMsT0FBTyxDQUFDLElBQUksQ0FBQyxFQUFFLEVBQUUsRUFBRSxDQUFDLENBQUM7UUFDMUIsSUFBSSxDQUFDLE9BQU8sR0FBRyxJQUFJLENBQUM7SUFDdEIsQ0FBQztJQUVNLFVBQVU7UUFDZixJQUFJLENBQUMsT0FBTyxFQUFFLElBQUksQ0FBQyxDQUFDLENBQUMsQ0FBQztJQUN4QixDQUFDO0lBRUQsK0VBQStFO0lBRS9FLDhDQUE4QztJQUN2QyxpQkFBaUIsQ0FBQyxRQUEwRDtRQUNqRixJQUFJLENBQUMsWUFBWSxFQUFFLENBQUM7UUFDcEIsSUFBSSxDQUFDLFdBQVcsQ0FBQyxhQUFhLENBQUMsSUFBSSxDQUFDLE1BQU0sQ0FBQyxFQUFFLEVBQUUsQ0FBQyxRQUFlLENBQUMsQ0FBQzthQUM5RCxJQUFJLENBQUMsa0JBQWtCLENBQUMsSUFBSSxDQUFDLFdBQVcsQ0FBQyxDQUFDO2FBQzFDLFNBQVMsRUFBRSxDQUFDO0lBQ2pCLENBQUM7SUFFRCwrRUFBK0U7SUFFL0UsdUVBQXVFO0lBQ3ZFLDZFQUE2RTtJQUM3RSxzRUFBc0U7SUFDdEUseUVBQXlFO0lBQ3pFLDZFQUE2RTtJQUM3RSxtREFBbUQ7SUFDM0MsS0FBSztRQUNYLElBQUksQ0FBQyxZQUFZLENBQUMsSUFBSSxDQUFDLFdBQVcsRUFBRSxZQUFZLENBQUMsSUFBSSxDQUFDLFlBQVksQ0FBQyxDQUFDLENBQUM7UUFDckUsSUFBSSxDQUFDLFlBQVksQ0FBQyxJQUFJLENBQUMsYUFBYSxFQUFFLFlBQVksQ0FBQyxJQUFJLENBQUMsYUFBYSxDQUFDLENBQUMsQ0FBQztJQUMxRSxDQUFDO0lBRU8sV0FBVyxDQUFDLE1BQThDO1FBQ2hFLE9BQU87WUFDTCxNQUFNO1lBQ04sT0FBTyxFQUFFLElBQUksT0FBTyxFQUFRO1lBQzVCLE9BQU8sRUFBRSxNQUFNLENBQXFCLElBQUksQ0FBQztZQUN6QyxPQUFPLEVBQUUsTUFBTSxDQUE0QixJQUFJLENBQUM7U0FDakQsQ0FBQztJQUNKLENBQUM7SUFFRCwyRUFBMkU7SUFDM0UsOERBQThEO0lBQ3RELFlBQVksQ0FBQyxLQUFpQixFQUFFLFNBQThCO1FBQ3BFLEtBQUssQ0FDSCxLQUFLLENBQUMsT0FBTyxFQUNiLFNBQVMsRUFDVCxJQUFJLENBQUMsWUFBWSxDQUFDLGFBQWEsQ0FBQyxHQUFHLEVBQUUsQ0FBQyxLQUFLLENBQUMsTUFBTSxFQUFFLEVBQUUsTUFBTSxJQUFJLEVBQUUsQ0FBQyxDQUFDLElBQUksQ0FBQyxZQUFZLENBQUMsR0FBRyxDQUFDLENBQUMsQ0FDNUY7YUFDRSxJQUFJLENBQ0gsWUFBWSxDQUFDLENBQUMsQ0FBQyxFQUNmLEdBQUcsQ0FBQyxHQUFHLEVBQUUsQ0FBQyxJQUFJLENBQUMsYUFBYSxDQUFDLEtBQUssQ0FBQyxNQUFNLEVBQUUsQ0FBQyxDQUFDLEVBQzdDLEdBQUcsQ0FBQyxDQUFDLE9BQU8sRUFBRSxFQUFFLENBQUMsS0FBSyxDQUFDLE9BQU8sQ0FBQyxHQUFHLENBQUMsT0FBTyxDQUFDLENBQUMsRUFDNUMsU0FBUyxDQUFDLENBQUMsT0FBTyxFQUFFLEVBQUUsQ0FBQyxJQUFJLENBQUMsV0FBVyxDQUFDLE9BQU8sQ0FBQyxDQUFDLEVBQ2pELEdBQUcsQ0FBQyxDQUFDLE1BQU0sRUFBRSxFQUFFO1lBQ2IsS0FBSyxDQUFDLE9BQU8sQ0FBQyxHQUFHLENBQUMsTUFBTSxDQUFDLENBQUM7WUFDMUIsS0FBSyxDQUFDLE9BQU8sQ0FBQyxHQUFHLENBQUMsSUFBSSxDQUFDLENBQUM7UUFDMUIsQ0FBQyxDQUFDLEVBQ0Ysa0JBQWtCLENBQUMsSUFBSSxDQUFDLFdBQVcsQ0FBQyxDQUNyQzthQUNBLFNBQVMsRUFBRSxDQUFDO0lBQ2pCLENBQUM7SUFFRCwyRUFBMkU7SUFDM0UseUVBQXlFO0lBQ3pFLDZFQUE2RTtJQUM3RSxpREFBaUQ7SUFDekMsZ0JBQWdCLENBQUMsS0FBaUI7UUFDeEMsTUFBTSxJQUFJLEdBQUcsS0FBSyxDQUFDLE9BQU8sRUFBRSxJQUFJLEtBQUssQ0FBQyxPQUFPLEVBQUUsQ0FBQztRQUVoRCxJQUFJLElBQUksQ0FBQyxhQUFhLENBQUMsS0FBSyxDQUFDLE1BQU0sRUFBRSxDQUFDLENBQUMsU0FBUyxLQUFLLElBQUksRUFBRSxTQUFTLEVBQUUsQ0FBQztZQUNyRSxLQUFLLENBQUMsT0FBTyxDQUFDLElBQUksRUFBRSxDQUFDO1FBQ3ZCLENBQUM7SUFDSCxDQUFDO0lBRUQsNkVBQTZFO0lBQzdFLHlFQUF5RTtJQUN6RSwwRUFBMEU7SUFDMUUsdUVBQXVFO0lBQ3ZFLHdFQUF3RTtJQUN4RSx3RUFBd0U7SUFDeEUsVUFBVTtJQUNGLGFBQWEsQ0FBQyxLQUF1QztRQUMzRCxNQUFNLE1BQU0sR0FBRyxLQUFLLEVBQUUsRUFBRSxJQUFJLElBQUksQ0FBQztRQUNqQyxNQUFNLE1BQU0sR0FBRyxLQUFLLEVBQUUsTUFBTSxJQUFJLEVBQUUsQ0FBQztRQUNuQyxNQUFNLEtBQUssR0FBRyxJQUFJLENBQUMsWUFBWSxDQUFDLEtBQUssQ0FBQyxDQUFDO1FBQ3ZDLE1BQU0sT0FBTyxHQUFHLE1BQU0sQ0FBQyxPQUFPLENBQUMsQ0FBQyxTQUFTLEVBQUUsRUFBRSxDQUFDLElBQUksQ0FBQyxZQUFZLENBQUMsbUJBQW1CLENBQUMsU0FBUyxDQUFDLENBQUMsQ0FBQztRQUVoRyxPQUFPO1lBQ0wsTUFBTTtZQUNOLEtBQUs7WUFDTCxPQUFPO1lBQ1AsU0FBUyxFQUFFLElBQUksQ0FBQyxTQUFTLENBQUM7Z0JBQ3hCLE1BQU07Z0JBQ04sS0FBSyxDQUFDLEdBQUcsQ0FBQyxDQUFDLEtBQUssRUFBRSxFQUFFLENBQUMsS0FBSyxDQUFDLEVBQUUsQ0FBQztnQkFDOUIsTUFBTSxDQUFDLEdBQUcsQ0FBQyxDQUFDLEtBQUssRUFBRSxFQUFFLENBQUMsQ0FBQyxFQUFFLEdBQUcsS0FBSyxFQUFFLEtBQUssRUFBRSxJQUFJLEVBQUUsQ0FBQyxDQUFDO2dCQUNsRCxPQUFPO2FBQ1IsQ0FBQztTQUNILENBQUM7SUFDSixDQUFDO0lBRUQsMEVBQTBFO0lBQzFFLDRFQUE0RTtJQUM1RSwrREFBK0Q7SUFDdkQsWUFBWSxDQUFDLEtBQXVDO1FBQzFELE1BQU0sS0FBSyxHQUFHLENBQUMsS0FBSyxFQUFFLFVBQVUsSUFBSSxFQUFFLENBQUMsQ0FBQyxNQUFNLENBQUMsQ0FBQyxTQUFTLEVBQUUsRUFBRSxDQUFDLFNBQVMsQ0FBQyxJQUFJLEtBQUssTUFBTSxDQUFDLENBQUM7UUFFekYsT0FBTyxXQUFXLENBQUMsS0FBSyxFQUFFLE1BQU0sSUFBSSxFQUFFLEVBQUUsS0FBSyxDQUFDLENBQUM7SUFDakQsQ0FBQztJQUVELDJFQUEyRTtJQUMzRSw0RUFBNEU7SUFDNUUsaUVBQWlFO0lBQ3pELFdBQVcsQ0FBQyxFQUFFLE1BQU0sRUFBRSxLQUFLLEVBQUUsT0FBTyxFQUFFLFNBQVMsRUFBc0I7UUFDM0UsTUFBTSxNQUFNLEdBQUcsQ0FBQyxJQUF1QixFQUFlLEVBQUUsQ0FBQyxDQUFDO1lBQ3hELE1BQU07WUFDTixTQUFTO1lBQ1QsSUFBSSxFQUFFLElBQUksR0FBRyxDQUFDLElBQUksQ0FBQyxHQUFHLENBQUMsQ0FBQyxHQUFHLEVBQUUsRUFBRSxDQUFDLENBQUMsR0FBRyxDQUFDLEVBQUUsRUFBRSxHQUFHLENBQUMsQ0FBQyxDQUFDO1NBQ2hELENBQUMsQ0FBQztRQUVILElBQUksTUFBTSxLQUFLLElBQUksSUFBSSxDQUFDLEtBQUssQ0FBQyxNQUFNLEVBQUUsQ0FBQztZQUNyQyxPQUFPLEVBQUUsQ0FBQyxNQUFNLENBQUMsRUFBRSxDQUFDLENBQUMsQ0FBQztRQUN4QixDQUFDO1FBRUQsT0FBTyxJQUFJLENBQUMsV0FBVyxDQUFDLFVBQVUsQ0FBQyxJQUFJLENBQUMsTUFBTSxDQUFDLEVBQUUsRUFBRSxNQUFNLEVBQUUsT0FBTyxFQUFFLEtBQUssRUFBRSxFQUFFLFFBQVEsRUFBRSxLQUFLLEVBQUUsQ0FBQzthQUM1RixJQUFJLENBQ0gsR0FBRyxDQUFDLENBQUMsSUFBSSxFQUFFLEVBQUUsQ0FBQyxNQUFNLENBQUMsSUFBSSxJQUFJLEVBQUUsQ0FBQyxDQUFDLEVBQ2pDLFVBQVUsQ0FBQyxHQUFHLEVBQUUsQ0FBQyxFQUFFLENBQUMsTUFBTSxDQUFDLEVBQUUsQ0FBQyxDQUFDLENBQUMsQ0FDakMsQ0FBQztJQUNOLENBQUM7SUFFRCwwRUFBMEU7SUFDMUUsNEVBQTRFO0lBQzVFLHlEQUF5RDtJQUNqRCxhQUFhLENBQ25CLE1BQXlCLEVBQ3pCLEtBQWlCLEVBQ2pCLFdBQTBCO1FBRTFCLDJFQUEyRTtRQUMzRSxJQUFJLENBQUMsZUFBZSxFQUFFLENBQUM7UUFFdkIsTUFBTSxLQUFLLEdBQUcsSUFBSSxDQUFDLGVBQWUsRUFBRSxDQUFDO1FBQ3JDLE1BQU0sSUFBSSxHQUFHLElBQUksQ0FBQyxLQUFLLEVBQUUsQ0FBQyxLQUFLLENBQUMsQ0FBQztRQUNqQyxNQUFNLE9BQU8sR0FBRyxLQUFLLENBQUMsT0FBTyxFQUFFLENBQUM7UUFDaEMsTUFBTSxPQUFPLEdBQUcsS0FBSyxDQUFDLE9BQU8sRUFBRSxDQUFDO1FBRWhDLE9BQU87WUFDTCxVQUFVLEVBQUUsS0FBSyxHQUFHLENBQUM7WUFDckIsUUFBUSxFQUFFLElBQUksQ0FBQyxDQUFDLENBQUMsSUFBSSxDQUFDLFNBQVMsQ0FBQyxJQUFJLEVBQUUsS0FBSyxDQUFDLENBQUMsQ0FBQyxDQUFDLEVBQUU7WUFDakQsVUFBVSxFQUFFLElBQUksQ0FBQyxPQUFPLEVBQUUsRUFBRSxJQUFJLElBQUksRUFBRTtZQUN0QyxNQUFNLEVBQUUsVUFBVSxDQUNoQixNQUFNLEVBQ04sT0FBTyxFQUFFLE1BQU0sS0FBSyxXQUFXLENBQUMsQ0FBQyxDQUFDLE9BQU8sQ0FBQyxDQUFDLENBQUMsSUFBSSxFQUNoRCxJQUFJLENBQUMsWUFBWSxDQUFDLGFBQWEsRUFBRSxFQUNqQyxJQUFJLEdBQUcsQ0FBQyxPQUFPLEVBQUUsTUFBTSxLQUFLLFdBQVcsQ0FBQyxDQUFDLENBQUMsT0FBTyxDQUFDLEtBQUssQ0FBQyxHQUFHLENBQUMsQ0FBQyxLQUFLLEVBQUUsRUFBRSxDQUFDLEtBQUssQ0FBQyxFQUFFLENBQUMsQ0FBQyxDQUFDLENBQUMsRUFBRSxDQUFDLENBQ3ZGO1lBQ0QsV0FBVztTQUNaLENBQUM7SUFDSixDQUFDO0lBRUQsd0VBQXdFO0lBQ3hFLDRFQUE0RTtJQUM1RSx3RUFBd0U7SUFDeEUsNkVBQTZFO0lBQzdFLDZFQUE2RTtJQUM3RSxxRUFBcUU7SUFDN0Qsc0JBQXNCO1FBQzVCLE1BQU0sSUFBSSxHQUFHLGNBQWMsQ0FBQyxJQUFJLENBQUMsTUFBTSxDQUFDLENBQUM7UUFDekMsTUFBTSxRQUFRLEdBQUcsSUFBSSxDQUFDLE1BQU0sRUFBRSxNQUFNLEVBQUUsRUFBRSxJQUFJLElBQUksQ0FBQztRQUNqRCxNQUFNLEtBQUssR0FBRyxDQUFDLElBQUksQ0FBQyxtQkFBbUIsRUFBRSxPQUFPLEVBQUUsSUFBSSxFQUFFLENBQUMsQ0FBQyxNQUFNLENBQUMsQ0FBQyxRQUFRLEVBQUUsRUFBRSxDQUFDLFFBQVEsQ0FBQyxNQUFNLENBQUMsQ0FBQztRQUVoRyxJQUFJLENBQUMsaUJBQWlCLENBQUMsT0FBTyxDQUFDLENBQUMsSUFBSSxFQUFFLE9BQU8sRUFBRSxFQUFFO1lBQy9DLE1BQU0sUUFBUSxHQUFHLE9BQU8sS0FBSyxRQUFRLENBQUM7WUFDdEMsSUFBSSxDQUFDLFFBQVEsSUFBSSxPQUFPLEtBQUssSUFBSSxDQUFDLFlBQVksRUFBRSxFQUFFLENBQUM7Z0JBQ2pELE9BQU87WUFDVCxDQUFDO1lBRUQsTUFBTSxPQUFPLEdBQUcsQ0FBQyxHQUFHLElBQUksQ0FBQyxDQUFDLE1BQU0sQ0FBQyxDQUFDLEdBQUcsRUFBRSxFQUFFLENBQUMsQ0FBQyxJQUFJLENBQUMsR0FBRyxDQUFDLE9BQU8sQ0FBQyxFQUFFLEdBQUcsQ0FBQyxHQUFHLENBQUMsQ0FBQyxDQUFDO1lBQ3hFLEtBQUs7aUJBQ0YsTUFBTSxDQUFDLENBQUMsUUFBUSxFQUFFLEVBQUUsQ0FBQyxJQUFJLENBQUMsa0JBQWtCLENBQUMsUUFBUSxDQUFDLFNBQVMsQ0FBQyxLQUFLLFFBQVEsQ0FBQztpQkFDOUUsT0FBTyxDQUFDLENBQUMsUUFBUSxFQUFFLEVBQUUsQ0FBQyxPQUFPLENBQUMsT0FBTyxDQUFDLENBQUMsR0FBRyxFQUFFLEVBQUUsQ0FBQyxRQUFRLENBQUMsV0FBVyxDQUFDLEdBQUcsQ0FBQyxDQUFDLENBQUMsQ0FBQztRQUNoRixDQUFDLENBQUMsQ0FBQztRQUVILElBQUksQ0FBQyxpQkFBaUIsR0FBRyxJQUFJLENBQUM7SUFDaEMsQ0FBQztJQUVELDhFQUE4RTtJQUN0RSxrQkFBa0IsQ0FBQyxTQUEwQjtRQUNuRCxPQUFPLENBQUMsSUFBSSxDQUFDLE1BQU0sRUFBRSxNQUFNLEVBQUUsVUFBVSxJQUFJLEVBQUUsQ0FBQyxDQUFDLElBQUksQ0FBQyxDQUFDLFNBQVMsRUFBRSxFQUFFLENBQUMsU0FBUyxDQUFDLEVBQUUsS0FBSyxTQUFTLENBQUMsRUFBRSxDQUFDLENBQUM7SUFDcEcsQ0FBQztJQUVELCtFQUErRTtJQUUvRSxtRUFBbUU7SUFDbkUsSUFBWSxjQUFjO1FBQ3hCLE9BQU8sQ0FBQyxHQUFHLENBQUMsV0FBVyxHQUFHLElBQUksQ0FBQyxHQUFHLENBQUMsR0FBRyxFQUFFLElBQUksQ0FBQyxJQUFJLEVBQUUsQ0FBQyxDQUFDLENBQUM7SUFDeEQsQ0FBQztJQUVPLFNBQVMsQ0FBQyxTQUEwQixFQUFFLENBQVMsRUFBRSxDQUFTO1FBQ2hFLE1BQU0sRUFBRSxRQUFRLEVBQUUsVUFBVSxFQUFFLEdBQUcsSUFBSSxDQUFDLFdBQVcsQ0FBQyxTQUFTLENBQUMsQ0FBQztRQUM3RCxNQUFNLE1BQU0sR0FBZ0IsRUFBRSxDQUFDO1FBRS9CLE1BQU0sUUFBUSxHQUFHLElBQUksQ0FBQyxTQUFTLENBQzdCO1lBQ0UsRUFBRSxNQUFNLEVBQUUsQ0FBQyxFQUFFLEtBQUssRUFBRSxDQUFDLEVBQUU7WUFDdkIsRUFBRSxNQUFNLEVBQUUsU0FBUyxDQUFDLENBQUMsR0FBRyxDQUFDLEVBQUUsS0FBSyxFQUFFLENBQUMsR0FBRyxTQUFTLENBQUMsQ0FBQyxHQUFHLENBQUMsRUFBRTtZQUN2RCxFQUFFLE1BQU0sRUFBRSxTQUFTLENBQUMsQ0FBQyxFQUFFLEtBQUssRUFBRSxDQUFDLEdBQUcsU0FBUyxDQUFDLENBQUMsRUFBRTtTQUNoRCxFQUNELFFBQVEsQ0FDVCxDQUFDO1FBQ0YsSUFBSSxRQUFRLEtBQUssSUFBSSxFQUFFLENBQUM7WUFDdEIsQ0FBQyxHQUFHLFFBQVEsQ0FBQyxJQUFJLENBQUM7WUFDbEIsTUFBTSxDQUFDLElBQUksQ0FBQyxFQUFFLFdBQVcsRUFBRSxHQUFHLEVBQUUsUUFBUSxFQUFFLFFBQVEsQ0FBQyxLQUFLLEVBQUUsQ0FBQyxDQUFDO1FBQzlELENBQUM7UUFFRCxNQUFNLFFBQVEsR0FBRyxJQUFJLENBQUMsU0FBUyxDQUM3QjtZQUNFLEVBQUUsTUFBTSxFQUFFLENBQUMsRUFBRSxLQUFLLEVBQUUsQ0FBQyxFQUFFO1lBQ3ZCLEVBQUUsTUFBTSxFQUFFLFNBQVMsQ0FBQyxDQUFDLEdBQUcsQ0FBQyxFQUFFLEtBQUssRUFBRSxDQUFDLEdBQUcsU0FBUyxDQUFDLENBQUMsR0FBRyxDQUFDLEVBQUU7WUFDdkQsRUFBRSxNQUFNLEVBQUUsU0FBUyxDQUFDLENBQUMsRUFBRSxLQUFLLEVBQUUsQ0FBQyxHQUFHLFNBQVMsQ0FBQyxDQUFDLEVBQUU7U0FDaEQsRUFDRCxVQUFVLENBQ1gsQ0FBQztRQUNGLElBQUksUUFBUSxLQUFLLElBQUksRUFBRSxDQUFDO1lBQ3RCLENBQUMsR0FBRyxRQUFRLENBQUMsSUFBSSxDQUFDO1lBQ2xCLE1BQU0sQ0FBQyxJQUFJLENBQUMsRUFBRSxXQUFXLEVBQUUsR0FBRyxFQUFFLFFBQVEsRUFBRSxRQUFRLENBQUMsS0FBSyxFQUFFLENBQUMsQ0FBQztRQUM5RCxDQUFDO1FBRUQsSUFBSSxDQUFDLGFBQWEsQ0FBQyxNQUFNLENBQUMsQ0FBQztRQUUzQixPQUFPLEVBQUUsQ0FBQyxFQUFFLENBQUMsRUFBRSxDQUFDO0lBQ2xCLENBQUM7SUFFTyxXQUFXLENBQ2pCLFNBQTBCLEVBQzFCLFFBQXdELEVBQ3hELE1BQWM7UUFFZCxNQUFNLEVBQUUsUUFBUSxFQUFFLFVBQVUsRUFBRSxHQUFHLElBQUksQ0FBQyxXQUFXLENBQUMsU0FBUyxDQUFDLENBQUM7UUFDN0QsTUFBTSxNQUFNLEdBQWdCLEVBQUUsQ0FBQztRQUMvQixNQUFNLE1BQU0sR0FBRyxFQUFFLEdBQUcsUUFBUSxFQUFFLENBQUM7UUFFL0IsMkRBQTJEO1FBQzNELElBQUksTUFBTSxDQUFDLFFBQVEsQ0FBQyxHQUFHLENBQUMsRUFBRSxDQUFDO1lBQ3pCLE1BQU0sT0FBTyxHQUFHLElBQUksQ0FBQyxRQUFRLENBQUMsUUFBUSxDQUFDLENBQUMsR0FBRyxRQUFRLENBQUMsQ0FBQyxFQUFFLFFBQVEsQ0FBQyxDQUFDO1lBQ2pFLElBQUksT0FBTyxLQUFLLElBQUksRUFBRSxDQUFDO2dCQUNyQixNQUFNLENBQUMsQ0FBQyxHQUFHLE9BQU8sR0FBRyxRQUFRLENBQUMsQ0FBQyxDQUFDO2dCQUNoQyxNQUFNLENBQUMsSUFBSSxDQUFDLEVBQUUsV0FBVyxFQUFFLEdBQUcsRUFBRSxRQUFRLEVBQUUsT0FBTyxFQUFFLENBQUMsQ0FBQztZQUN2RCxDQUFDO1FBQ0gsQ0FBQztRQUNELElBQUksTUFBTSxDQUFDLFFBQVEsQ0FBQyxHQUFHLENBQUMsRUFBRSxDQUFDO1lBQ3pCLE1BQU0sT0FBTyxHQUFHLElBQUksQ0FBQyxRQUFRLENBQUMsUUFBUSxDQUFDLENBQUMsRUFBRSxRQUFRLENBQUMsQ0FBQztZQUNwRCxJQUFJLE9BQU8sS0FBSyxJQUFJLEVBQUUsQ0FBQztnQkFDckIsTUFBTSxDQUFDLENBQUMsR0FBRyxRQUFRLENBQUMsQ0FBQyxHQUFHLFFBQVEsQ0FBQyxDQUFDLEdBQUcsT0FBTyxDQUFDO2dCQUM3QyxNQUFNLENBQUMsQ0FBQyxHQUFHLE9BQU8sQ0FBQztnQkFDbkIsTUFBTSxDQUFDLElBQUksQ0FBQyxFQUFFLFdBQVcsRUFBRSxHQUFHLEVBQUUsUUFBUSxFQUFFLE9BQU8sRUFBRSxDQUFDLENBQUM7WUFDdkQsQ0FBQztRQUNILENBQUM7UUFDRCxJQUFJLE1BQU0sQ0FBQyxRQUFRLENBQUMsR0FBRyxDQUFDLEVBQUUsQ0FBQztZQUN6QixNQUFNLE9BQU8sR0FBRyxJQUFJLENBQUMsUUFBUSxDQUFDLFFBQVEsQ0FBQyxDQUFDLEdBQUcsUUFBUSxDQUFDLENBQUMsRUFBRSxVQUFVLENBQUMsQ0FBQztZQUNuRSxJQUFJLE9BQU8sS0FBSyxJQUFJLEVBQUUsQ0FBQztnQkFDckIsTUFBTSxDQUFDLENBQUMsR0FBRyxPQUFPLEdBQUcsUUFBUSxDQUFDLENBQUMsQ0FBQztnQkFDaEMsTUFBTSxDQUFDLElBQUksQ0FBQyxFQUFFLFdBQVcsRUFBRSxHQUFHLEVBQUUsUUFBUSxFQUFFLE9BQU8sRUFBRSxDQUFDLENBQUM7WUFDdkQsQ0FBQztRQUNILENBQUM7UUFDRCxJQUFJLE1BQU0sQ0FBQyxRQUFRLENBQUMsR0FBRyxDQUFDLEVBQUUsQ0FBQztZQUN6QixNQUFNLE9BQU8sR0FBRyxJQUFJLENBQUMsUUFBUSxDQUFDLFFBQVEsQ0FBQyxDQUFDLEVBQUUsVUFBVSxDQUFDLENBQUM7WUFDdEQsSUFBSSxPQUFPLEtBQUssSUFBSSxFQUFFLENBQUM7Z0JBQ3JCLE1BQU0sQ0FBQyxDQUFDLEdBQUcsUUFBUSxDQUFDLENBQUMsR0FBRyxRQUFRLENBQUMsQ0FBQyxHQUFHLE9BQU8sQ0FBQztnQkFDN0MsTUFBTSxDQUFDLENBQUMsR0FBRyxPQUFPLENBQUM7Z0JBQ25CLE1BQU0sQ0FBQyxJQUFJLENBQUMsRUFBRSxXQUFXLEVBQUUsR0FBRyxFQUFFLFFBQVEsRUFBRSxPQUFPLEVBQUUsQ0FBQyxDQUFDO1lBQ3ZELENBQUM7UUFDSCxDQUFDO1FBRUQsSUFBSSxDQUFDLGFBQWEsQ0FBQyxNQUFNLENBQUMsQ0FBQztRQUUzQixPQUFPLE1BQU0sQ0FBQztJQUNoQixDQUFDO0lBRUQsMEVBQTBFO0lBQzFFLDJFQUEyRTtJQUMzRSwwRUFBMEU7SUFDMUUsVUFBVTtJQUNGLFdBQVcsQ0FBQyxNQUF1QjtRQUN6QyxNQUFNLFFBQVEsR0FBRyxDQUFDLENBQUMsRUFBRSxJQUFJLENBQUMsTUFBTSxDQUFDLFNBQVMsR0FBRyxDQUFDLEVBQUUsSUFBSSxDQUFDLE1BQU0sQ0FBQyxTQUFTLENBQUMsQ0FBQztRQUN2RSxNQUFNLFVBQVUsR0FBRyxDQUFDLENBQUMsRUFBRSxJQUFJLENBQUMsTUFBTSxDQUFDLFVBQVUsR0FBRyxDQUFDLEVBQUUsSUFBSSxDQUFDLE1BQU0sQ0FBQyxVQUFVLENBQUMsQ0FBQztRQUUzRSxNQUFNLEVBQUUsWUFBWSxFQUFFLFlBQVksRUFBRSxHQUFHLElBQUksQ0FBQyxLQUFLLENBQUM7UUFDbEQsSUFBSSxZQUFZLEVBQUUsQ0FBQztZQUNqQixVQUFVLENBQUMsSUFBSSxDQUFDLFlBQVksQ0FBQyxDQUFDO1FBQ2hDLENBQUM7UUFDRCxJQUFJLFlBQVksRUFBRSxDQUFDO1lBQ2pCLFVBQVUsQ0FBQyxJQUFJLENBQUMsSUFBSSxDQUFDLE1BQU0sQ0FBQyxVQUFVLEdBQUcsWUFBWSxDQUFDLENBQUM7UUFDekQsQ0FBQztRQUVELE1BQU0sUUFBUSxHQUFHLElBQUksQ0FBQyxrQkFBa0IsQ0FBQyxNQUFNLENBQUMsQ0FBQztRQUNqRCxNQUFNLFFBQVEsR0FBRyxRQUFRLENBQUMsQ0FBQyxDQUFDLElBQUksQ0FBQyxnQkFBZ0IsRUFBRSxDQUFDLENBQUMsQ0FBQyxJQUFJLENBQUMsb0JBQW9CLEVBQUUsQ0FBQztRQUVsRixLQUFLLE1BQU0sU0FBUyxJQUFJLFFBQVEsRUFBRSxDQUFDO1lBQ2pDLElBQUksU0FBUyxDQUFDLEVBQUUsS0FBSyxNQUFNLENBQUMsRUFBRSxFQUFFLENBQUM7Z0JBQy9CLFNBQVM7WUFDWCxDQUFDO1lBRUQsUUFBUSxDQUFDLElBQUksQ0FBQyxTQUFTLENBQUMsQ0FBQyxFQUFFLFNBQVMsQ0FBQyxDQUFDLEdBQUcsU0FBUyxDQUFDLENBQUMsR0FBRyxDQUFDLEVBQUUsU0FBUyxDQUFDLENBQUMsR0FBRyxTQUFTLENBQUMsQ0FBQyxDQUFDLENBQUM7WUFDckYsVUFBVSxDQUFDLElBQUksQ0FBQyxTQUFTLENBQUMsQ0FBQyxFQUFFLFNBQVMsQ0FBQyxDQUFDLEdBQUcsU0FBUyxDQUFDLENBQUMsR0FBRyxDQUFDLEVBQUUsU0FBUyxDQUFDLENBQUMsR0FBRyxTQUFTLENBQUMsQ0FBQyxDQUFDLENBQUM7UUFDekYsQ0FBQztRQUVELE9BQU8sRUFBRSxRQUFRLEVBQUUsVUFBVSxFQUFFLENBQUM7SUFDbEMsQ0FBQztJQUVELDBFQUEwRTtJQUMxRSxzRUFBc0U7SUFDdEUscUNBQXFDO0lBQzdCLFNBQVMsQ0FDZixLQUEwQyxFQUMxQyxVQUFvQjtRQUVwQixJQUFJLElBQUksR0FBNkQsSUFBSSxDQUFDO1FBRTFFLEtBQUssTUFBTSxJQUFJLElBQUksS0FBSyxFQUFFLENBQUM7WUFDekIsS0FBSyxNQUFNLFNBQVMsSUFBSSxVQUFVLEVBQUUsQ0FBQztnQkFDbkMsTUFBTSxRQUFRLEdBQUcsSUFBSSxDQUFDLEdBQUcsQ0FBQyxTQUFTLEdBQUcsSUFBSSxDQUFDLEtBQUssQ0FBQyxDQUFDO2dCQUNsRCxJQUFJLFFBQVEsSUFBSSxJQUFJLENBQUMsY0FBYyxJQUFJLENBQUMsQ0FBQyxJQUFJLElBQUksUUFBUSxHQUFHLElBQUksQ0FBQyxRQUFRLENBQUMsRUFBRSxDQUFDO29CQUMzRSxJQUFJLEdBQUcsRUFBRSxJQUFJLEVBQUUsU0FBUyxHQUFHLElBQUksQ0FBQyxNQUFNLEVBQUUsS0FBSyxFQUFFLFNBQVMsRUFBRSxRQUFRLEVBQUUsQ0FBQztnQkFDdkUsQ0FBQztZQUNILENBQUM7UUFDSCxDQUFDO1FBRUQsT0FBTyxJQUFJLENBQUMsQ0FBQyxDQUFDLEVBQUUsSUFBSSxFQUFFLElBQUksQ0FBQyxJQUFJLEVBQUUsS0FBSyxFQUFFLElBQUksQ0FBQyxLQUFLLEVBQUUsQ0FBQyxDQUFDLENBQUMsSUFBSSxDQUFDO0lBQzlELENBQUM7SUFFTyxRQUFRLENBQUMsS0FBYSxFQUFFLFVBQW9CO1FBQ2xELElBQUksSUFBSSxHQUFrQixJQUFJLENBQUM7UUFDL0IsSUFBSSxZQUFZLEdBQUcsSUFBSSxDQUFDLGNBQWMsQ0FBQztRQUV2QyxLQUFLLE1BQU0sU0FBUyxJQUFJLFVBQVUsRUFBRSxDQUFDO1lBQ25DLE1BQU0sUUFBUSxHQUFHLElBQUksQ0FBQyxHQUFHLENBQUMsU0FBUyxHQUFHLEtBQUssQ0FBQyxDQUFDO1lBQzdDLElBQUksUUFBUSxJQUFJLFlBQVksRUFBRSxDQUFDO2dCQUM3QixJQUFJLEdBQUcsU0FBUyxDQUFDO2dCQUNqQixZQUFZLEdBQUcsUUFBUSxDQUFDO1lBQzFCLENBQUM7UUFDSCxDQUFDO1FBRUQsT0FBTyxJQUFJLENBQUM7SUFDZCxDQUFDO0lBRUQsd0VBQXdFO0lBQ3hFLDZDQUE2QztJQUNyQyxhQUFhLENBQUMsTUFBbUI7UUFDdkMsTUFBTSxJQUFJLEdBQUcsSUFBSSxDQUFDLE9BQU8sRUFBRSxhQUFhLENBQUM7UUFDekMsSUFBSSxDQUFDLElBQUksRUFBRSxDQUFDO1lBQ1YsT0FBTztRQUNULENBQUM7UUFFRCxJQUFJLENBQUMsZUFBZSxDQUFDLEdBQUcsTUFBTSxDQUFDLEdBQUcsQ0FBQyxDQUFDLEtBQUssRUFBRSxFQUFFO1lBQzNDLE1BQU0sSUFBSSxHQUFHLFFBQVEsQ0FBQyxhQUFhLENBQUMsS0FBSyxDQUFDLENBQUM7WUFDM0MsSUFBSSxDQUFDLFNBQVMsR0FBRyxlQUFlLEtBQUssQ0FBQyxXQUFXLEVBQUUsQ0FBQztZQUNwRCxJQUFJLEtBQUssQ0FBQyxXQUFXLEtBQUssR0FBRyxFQUFFLENBQUM7Z0JBQzlCLElBQUksQ0FBQyxLQUFLLENBQUMsSUFBSSxHQUFHLEdBQUcsS0FBSyxDQUFDLFFBQVEsR0FBRyxXQUFXLElBQUksQ0FBQztZQUN4RCxDQUFDO2lCQUFNLENBQUM7Z0JBQ04sSUFBSSxDQUFDLEtBQUssQ0FBQyxHQUFHLEdBQUcsR0FBRyxLQUFLLENBQUMsUUFBUSxHQUFHLFdBQVcsSUFBSSxDQUFDO1lBQ3ZELENBQUM7WUFFRCxPQUFPLElBQUksQ0FBQztRQUNkLENBQUMsQ0FBQyxDQUFDLENBQUM7SUFDTixDQUFDO0lBRU8sWUFBWTtRQUNsQixJQUFJLENBQUMsT0FBTyxFQUFFLGFBQWEsRUFBRSxlQUFlLEVBQUUsQ0FBQztJQUNqRCxDQUFDO3dHQTkyQlUscUJBQXFCOzRGQUFyQixxQkFBcUIsNlNBc0JyQixrQkFBa0IsbVFBS2Ysd0JBQXdCLHFFQ25LeEMsMnFRQW9OQSxnbEtEcEZJLGNBQWMsNi9CQUNkLE9BQU8sMklBQ1AsVUFBVSxnUkFDVixZQUFZLHVaQUNaLGVBQWUsOFNBQ2Ysd0JBQXdCOzs0RkFHZixxQkFBcUI7a0JBZmpDLFNBQVM7K0JBQ0UsbUJBQW1CLG1CQUdaLHVCQUF1QixDQUFDLE1BQU0sY0FDbkMsSUFBSSxXQUNQO3dCQUNQLGNBQWM7d0JBQ2QsT0FBTzt3QkFDUCxVQUFVO3dCQUNWLFlBQVk7d0JBQ1osZUFBZTt3QkFDZix3QkFBd0I7cUJBQ3pCO3dEQUllLE1BQU07c0JBQXJCLEtBQUs7Z0JBQ1UsUUFBUTtzQkFBdkIsS0FBSztnQkFLVSxNQUFNO3NCQUFyQixLQUFLO2dCQUlXLGlCQUFpQjtzQkFBakMsTUFBTTtnQkFJVSxhQUFhO3NCQUE3QixNQUFNO2dCQUlVLFdBQVc7c0JBQTNCLE1BQU07Z0JBR0EsT0FBTztzQkFEYixTQUFTO3VCQUFDLGtCQUFrQjtnQkFNckIsbUJBQW1CO3NCQUQxQixZQUFZO3VCQUFDLHdCQUF3QjtnQkFJOUIsU0FBUztzQkFEaEIsU0FBUzt1QkFBQyxVQUFVLEVBQUUsRUFBRSxNQUFNLEVBQUUsSUFBSSxFQUFFO2dCQUkvQixPQUFPO3NCQURkLFNBQVM7dUJBQUMsUUFBUSxFQUFFLEVBQUUsTUFBTSxFQUFFLEtBQUssRUFBRSIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7XG4gIEFmdGVyVmlld0luaXQsIENoYW5nZURldGVjdGlvblN0cmF0ZWd5LCBDb21wb25lbnQsIERlc3Ryb3lSZWYsXG4gIEVsZW1lbnRSZWYsIEV2ZW50RW1pdHRlciwgSW5wdXQsIE9uQ2hhbmdlcywgT3V0cHV0LCBRdWVyeUxpc3QsIFNpbXBsZUNoYW5nZXMsIFZpZXdDaGlsZCwgVmlld0NoaWxkcmVuLFxuICBXcml0YWJsZVNpZ25hbCwgY29tcHV0ZWQsIGluamVjdCwgc2lnbmFsLFxufSBmcm9tICdAYW5ndWxhci9jb3JlJztcbmltcG9ydCB7IHRha2VVbnRpbERlc3Ryb3llZCwgdG9PYnNlcnZhYmxlIH0gZnJvbSAnQGFuZ3VsYXIvY29yZS9yeGpzLWludGVyb3AnO1xuXG5pbXBvcnQgeyBDZGtEcmFnRHJvcCwgRHJhZ0Ryb3BNb2R1bGUsIG1vdmVJdGVtSW5BcnJheSB9IGZyb20gJ0Bhbmd1bGFyL2Nkay9kcmFnLWRyb3AnO1xuaW1wb3J0IHsgTWF0SWNvbiB9IGZyb20gJ0Bhbmd1bGFyL21hdGVyaWFsL2ljb24nO1xuaW1wb3J0IHsgTWF0VG9vbHRpcCB9IGZyb20gJ0Bhbmd1bGFyL21hdGVyaWFsL3Rvb2x0aXAnO1xuXG5pbXBvcnQgeyBGc01lbnVNb2R1bGUgfSBmcm9tICdAZmlyZXN0aXRjaC9tZW51JztcbmltcG9ydCB7IEZzTWVzc2FnZSB9IGZyb20gJ0BmaXJlc3RpdGNoL21lc3NhZ2UnO1xuaW1wb3J0IHsgRnNQcm9tcHQgfSBmcm9tICdAZmlyZXN0aXRjaC9wcm9tcHQnO1xuaW1wb3J0IHsgRnNab29tUGFuQ29tcG9uZW50LCBGc1pvb21QYW5Nb2R1bGUgfSBmcm9tICdAZmlyZXN0aXRjaC96b29tLXBhbic7XG5cbmltcG9ydCB7XG4gIE9ic2VydmFibGUsIFN1YmplY3QsIGNhdGNoRXJyb3IsIGRlYm91bmNlVGltZSwgbWFwLCBtZXJnZSwgb2YsIHN3aXRjaE1hcCwgdGFwLFxufSBmcm9tICdyeGpzJztcblxuaW1wb3J0IHsgUmVwb3J0RGF0YSB9IGZyb20gJy4uLy4uL2RhdGEvcmVwb3J0LmRhdGEnO1xuaW1wb3J0IHtcbiAgQ29tcG9uZW50U2V0dGluZ3MsIFJlcG9ydCwgUmVwb3J0Q29tcG9uZW50LCBSZXBvcnRGaWx0ZXJHcm91cCwgUmVwb3J0SGVhZGVyRm9vdGVyLCBSZXBvcnRNYXN0ZXIsIFJlcG9ydFBhZ2UsXG4gIFJlcG9ydFBhZ2VWYWx1ZSwgUmVzb2x2ZWRGaWx0ZXJWYWx1ZSxcbn0gZnJvbSAnLi4vLi4vaW50ZXJmYWNlcy9yZXBvcnQuaW50ZXJmYWNlJztcbmltcG9ydCB7IERFRkFVTFRfSEVBRElOR19TSVpFIH0gZnJvbSAnLi4vLi4vbGF5b3V0JztcbmltcG9ydCB7IFJlcG9ydEZpbHRlclN0YXRlU2VydmljZSB9IGZyb20gJy4uLy4uL3NlcnZpY2VzL3JlcG9ydC1maWx0ZXItc3RhdGUuc2VydmljZSc7XG5pbXBvcnQgeyBUZXh0VG9rZW5Db250ZXh0IH0gZnJvbSAnLi4vLi4vdGV4dCc7XG5pbXBvcnQge1xuICBpc0RyYXduLCBsYXllclZhbHVlS2V5cywgc2FtZVRleHRWYWx1ZXMsIHNob3duVmFsdWVzLCB0ZXh0VmFsdWVzLCB2YWx1ZUtleSwgdmFsdWVLZXlzLFxufSBmcm9tICcuLi8uLi92YWx1ZXMnO1xuaW1wb3J0IHsgUmVwb3J0Q29tcG9uZW50Q29tcG9uZW50IH0gZnJvbSAnLi4vcmVwb3J0LWNvbXBvbmVudC9yZXBvcnQtY29tcG9uZW50LmNvbXBvbmVudCc7XG5cblxuLy8gU2NyZWVuIGRlbnNpdHkgb2YgdGhlIGNhbnZhczogOTYgQ1NTIHB4IHBlciBpbmNoICh0aGUgQ1NTIHJlZmVyZW5jZSBwaXhlbCksXG4vLyBiZWZvcmUgem9vbS4gQWxsIGdlb21ldHJ5IHN0YXlzIGluIGluY2hlczsgb25seSByZW5kZXJpbmcgbXVsdGlwbGllcyBieSBpdC5cbmV4cG9ydCBjb25zdCBQWF9QRVJfSU5DSCA9IDk2O1xuXG4vLyBPbmUgc21hcnQgZ3VpZGUgbGluZSwgaW4gcGFnZSBpbmNoZXMuXG5leHBvcnQgaW50ZXJmYWNlIEd1aWRlTGluZSB7XG4gIG9yaWVudGF0aW9uOiAndicgfCAnaCc7XG4gIHBvc2l0aW9uOiBudW1iZXI7XG59XG5cbi8vIFRoZSBzbmFwcGluZyBjb250cmFjdCBoYW5kZWQgdG8gZWFjaCBjb21wb25lbnQncyBkcmFnIGxvb3AuIEltcGxlbWVudGVkIGJ5XG4vLyB0aGUgY2FudmFzIGJlY2F1c2Ugb25seSBpdCBzZWVzIGV2ZXJ5IGNvbXBvbmVudCAoYWxpZ25tZW50IGNhbmRpZGF0ZXMpIGFuZFxuLy8gb3ducyB0aGUgZ3VpZGVzIG92ZXJsYXkuXG5leHBvcnQgaW50ZXJmYWNlIENhbnZhc1NuYXBwZXIge1xuICBzbmFwTW92ZShjb21wb25lbnQ6IFJlcG9ydENvbXBvbmVudCwgeDogbnVtYmVyLCB5OiBudW1iZXIpOiB7IHg6IG51bWJlcjsgeTogbnVtYmVyIH07XG4gIHNuYXBSZXNpemUoY29tcG9uZW50OiBSZXBvcnRDb21wb25lbnQsIGdlb21ldHJ5OiB7IHg6IG51bWJlcjsgeTogbnVtYmVyOyB3OiBudW1iZXI7IGg6IG51bWJlciB9LCBoYW5kbGU6IHN0cmluZyk6IHsgeDogbnVtYmVyOyB5OiBudW1iZXI7IHc6IG51bWJlcjsgaDogbnVtYmVyIH07XG4gIGNsZWFyKCk6IHZvaWQ7XG59XG5cbi8vIE9uZSBsYXllcidzIHZhbHVlcyByZXF1ZXN0IChhIHBhZ2UsIG9yIHRoZSBtYXN0ZXIpLCByZWFkIHdoZW4gaXQgaXMgc2VudDpcbi8vIHRoZSBsYXllciwgdGhlIHZhbHVlcyBpdHMgdGV4dCBzaG93cyBhdCB0aGF0IG1vbWVudCAod2hhdCByZWFkcyBhcyBsb2FkaW5nXG4vLyB1bnRpbCBpdCBsYW5kcykgYW5kIHRoZSBmaWx0ZXIgdmFsdWVzIG9mIGV2ZXJ5IHZhbHVlIG9uIHRoZSBsYXllci5cbmludGVyZmFjZSBMYXllclZhbHVlc1JlcXVlc3Qge1xuICBwYWdlSWQ6IG51bWJlciB8IG51bGw7XG4gIHNob3duOiBSZXBvcnRDb21wb25lbnRbXTtcbiAgZmlsdGVyczogUmVzb2x2ZWRGaWx0ZXJWYWx1ZVtdO1xuICAvLyBFdmVyeXRoaW5nIHRoZSBsYXllcidzIG51bWJlcnMgZGVwZW5kIG9uOiB0aGUgcmVxdWVzdCwgYW5kIGhvdyBlYWNoIHZhbHVlXG4gIC8vIGl0IHJlYWRzIGlzIGRlZmluZWQuIEEgcmVsb2FkIG9mIHRoZSByZXBvcnQgdGhhdCBsZWF2ZXMgaXQgYXMgaXQgd2FzIGFza3NcbiAgLy8gZm9yIG5vdGhpbmcuXG4gIHNpZ25hdHVyZTogc3RyaW5nO1xufVxuXG4vLyBPbmUgbGF5ZXIncyBudW1iZXJzIGFzIHRoZXkgbGFzdCBhcnJpdmVkLCBieSB2YWx1ZSBpZCwgYW5kIHRoZSByZXF1ZXN0IHRoZXlcbi8vIGFuc3dlciDigJQgcmVzdWx0cyBmb3IgYW5vdGhlciBwYWdlIGFyZSBub3QgdGhpcyBwYWdlJ3MuXG5pbnRlcmZhY2UgTGF5ZXJWYWx1ZXMge1xuICBwYWdlSWQ6IG51bWJlciB8IG51bGw7XG4gIHNpZ25hdHVyZTogc3RyaW5nO1xuICByb3dzOiBSZWFkb25seU1hcDxudW1iZXIsIFJlcG9ydFBhZ2VWYWx1ZT47XG59XG5cbi8vIEEgbGF5ZXIgd2hvc2UgdmFsdWVzIHRoZSBjYW52YXMgcmVhZHM6IHRoZSBhY3RpdmUgcGFnZSwgb3IgdGhlIG1hc3Rlci5cbmludGVyZmFjZSBWYWx1ZUxheWVyIHtcbiAgLy8gVGhlIGxheWVyIGFzIGl0IHN0YW5kcywgb3IgbnVsbCB3aGVuIG5vbmUgb2YgaXRzIG51bWJlcnMgYXJlIG5lZWRlZC5cbiAgc291cmNlOiAoKSA9PiBSZXBvcnRQYWdlIHwgUmVwb3J0TWFzdGVyIHwgbnVsbDtcbiAgLy8gQXNrcyBmb3IgaXRzIG51bWJlcnMgYWdhaW4uXG4gIHJlbG9hZCQ6IFN1YmplY3Q8dm9pZD47XG4gIC8vIEl0cyBudW1iZXJzIGFzIHRoZXkgbGFzdCBhcnJpdmVkLlxuICByZXN1bHRzOiBXcml0YWJsZVNpZ25hbDxMYXllclZhbHVlcyB8IG51bGw+O1xuICAvLyBUaGUgcmVxdWVzdCBvbiBpdHMgd2F5LCBudWxsIG9uY2UgaXQgaGFzIGxhbmRlZC4gQSB2YWx1ZSBpdCBhc2tzIGZvclxuICAvLyByZWFkcyBhcyBsb2FkaW5nIHVudGlsIHRoZW4sIHNvIGEgbnVtYmVyIG9uIHNjcmVlbiBpcyBuZXZlciBvbmUgcmVhZCBmb3JcbiAgLy8gYW4gZWFybGllciByZXF1ZXN0IChhbm90aGVyIGZpbHRlciwgdGhlIHZhbHVlIGFzIGl0IHdhcykuXG4gIHBlbmRpbmc6IFdyaXRhYmxlU2lnbmFsPExheWVyVmFsdWVzUmVxdWVzdCB8IG51bGw+O1xufVxuXG4vLyBXaGV0aGVyIHR3byB0b2tlbiBjb250ZXh0cyBmaWxsIGV2ZXJ5IHRva2VuIHRoZSBzYW1lLCBzbyByZWNvbXB1dGluZyBvbmVcbi8vIHRoYXQgY2hhbmdlZCBub3RoaW5nIGEgdG9rZW4gc2hvd3MgaGFuZHMgYmFjayB0aGUgb2JqZWN0IHRoZSBibG9ja3MgaGF2ZS5cbmZ1bmN0aW9uIHNhbWVUb2tlbnMoYTogVGV4dFRva2VuQ29udGV4dCwgYjogVGV4dFRva2VuQ29udGV4dCk6IGJvb2xlYW4ge1xuICByZXR1cm4gYS5wYWdlTnVtYmVyID09PSBiLnBhZ2VOdW1iZXJcbiAgICAmJiBhLnBhZ2VOYW1lID09PSBiLnBhZ2VOYW1lXG4gICAgJiYgYS5yZXBvcnROYW1lID09PSBiLnJlcG9ydE5hbWVcbiAgICAmJiBhLnZhbHVlUGFnZUlkID09PSBiLnZhbHVlUGFnZUlkXG4gICAgJiYgc2FtZVRleHRWYWx1ZXMoYS52YWx1ZXMsIGIudmFsdWVzKTtcbn1cblxuLy8gVGhlIGZpeGVkLXNpemUgcGFnZSBjYW52YXMg4oCUIHRoZSBQb3dlclBvaW50IG1vZGVsLiBQYWdlcyBhcmUgdGFicyAob25seSB0aGVcbi8vIEFDVElWRSBwYWdlJ3MgY29tcG9uZW50cyBleGlzdCDihpIgb25seSB0aGV5IGZldGNoKTsgdGhlIHBhZ2UgaXMgYVxuLy8gcGFnZVdpZHRow5dwYWdlSGVpZ2h0IElOQ0hFUyBzaGVldCByZW5kZXJlZCBhdCA5NnB4L2luIGluc2lkZSBmcy16b29tLXBhblxuLy8gKEN0cmwvQ21kICsgd2hlZWwgb3IgcGluY2ggdG8gem9vbSwgYmFja2dyb3VuZCBkcmFnIHBhbiwgdG9vbGJhciBidXR0b25zOyBhXG4vLyBwbGFpbiB3aGVlbCBzY3JvbGxzIHRoZSBsaXN0IHVuZGVyIHRoZSBwb2ludGVyKS5cbi8vXG4vLyBDb21wb25lbnRzIGFyZSBhYnNvbHV0ZWx5IHBvc2l0aW9uZWQ7IGRyYWdnaW5nIGdldHMgc21hcnQgYWxpZ25tZW50IGd1aWRlc1xuLy8gKGVkZ2VzICsgY2VudGVycyBvZiBzaWJsaW5ncyBhbmQgdGhlIHBhZ2UpIHdpdGggc25hcHBpbmcuXG4vL1xuLy8gSGVhZGVyIGFuZCBmb290ZXI6IHRoZSByZXBvcnQncyBtYXN0ZXIgY29tcG9uZW50cyAocmVwb3J0Lm1hc3RlcikgYXJlIGRyYXduXG4vLyBvbiBhIGxheWVyIFVOREVSIGV2ZXJ5IHBhZ2UncyBvd24gY29tcG9uZW50cywgbGlrZSBhIFBvd2VyUG9pbnQgc2xpZGUgbWFzdGVyLFxuLy8gdW5sZXNzIHRoZSBwYWdlIGhpZGVzIHRoZW0uIEluIGVkaXQgbW9kZSB0aGUgaG9zdCB0b29sYmFyJ3MgXCJIZWFkZXIgJiBmb290ZXJcIlxuLy8gKHRvZ2dsZU1hc3Rlck1vZGUpIHN3aXRjaGVzIHdoaWNoIGxheWVyIGlzIGxpdmU6IHRoZSBwYWdlJ3MgY29tcG9uZW50cyBkaW1cbi8vIGFuZCB0aGUgbWFzdGVyJ3MgYmVjb21lIHRoZSBvbmVzIHRoYXQgZHJhZywgcmVzaXplIGFuZCBzbmFwLiBUaGUgaGVhZGVyL2Zvb3RlciBiYW5kcyAoY29uZmlnLmhlYWRlckZvb3Rlcilcbi8vIGFyZSBkcmF3biBhcyBndWlkZXMgd2hpbGUgZWRpdGluZyBhbmQgYXJlIHNuYXAgbGluZXMgZm9yIGJvdGggbGF5ZXJzLlxuLy9cbi8vIExpdmUgdmFsdWVzOiBhIHRleHQgYmxvY2sgc2hvd3MgbnVtYmVycyBpbmxpbmUgKHt7dmFsdWUua2V5fX0pLiBBIHZhbHVlIGlzXG4vLyBuZXZlciBkcmF3bjsgaXQgYmVsb25ncyB0byB0aGUgcGFnZSB3aG9zZSB0ZXh0IHNob3dzIGl0ICh0aGUgbWFzdGVyIGZvciBhXG4vLyBoZWFkZXIgb3IgZm9vdGVyKSBhbmQgaXMgbGlzdGVkIGluIHRoYXQgbGF5ZXIncyBgdmFsdWVzYC4gVGhlIGNhbnZhcyByZWFkc1xuLy8gdGhlIG51bWJlcnMgb25lIHJlcXVlc3QgcGVyIGxheWVyIOKAlCB0aGUgYWN0aXZlIHBhZ2UncyBhbmQgdGhlIG1hc3RlcidzIOKAlFxuLy8gYW5kIGhhbmRzIHRoZW0gdG8gZXZlcnkgYmxvY2sgb2YgdGhlIGxheWVyIHdpdGggdGhlIHBhZ2UgdG9rZW5zLiBXaGljaFxuLy8gdmFsdWVzIGEgcmVxdWVzdCByZWFkcyBpcyB0aGUgc2VydmVyJ3MgY2FsbCBhbG9uZTogdGhlIG9uZXMgdGhlIHRleHQgc2hvd3MsXG4vLyBhbmQgdGhlIG9wZXJhbmRzIG9mIHRoZSBmb3JtdWxhcyBhbW9uZyB0aGVtLlxuQENvbXBvbmVudCh7XG4gIHNlbGVjdG9yOiAnYXBwLXJlcG9ydC1jYW52YXMnLFxuICB0ZW1wbGF0ZVVybDogJy4vcmVwb3J0LWNhbnZhcy5jb21wb25lbnQuaHRtbCcsXG4gIHN0eWxlVXJsczogWycuL3JlcG9ydC1jYW52YXMuY29tcG9uZW50LnNjc3MnXSxcbiAgY2hhbmdlRGV0ZWN0aW9uOiBDaGFuZ2VEZXRlY3Rpb25TdHJhdGVneS5PblB1c2gsXG4gIHN0YW5kYWxvbmU6IHRydWUsXG4gIGltcG9ydHM6IFtcbiAgICBEcmFnRHJvcE1vZHVsZSxcbiAgICBNYXRJY29uLFxuICAgIE1hdFRvb2x0aXAsXG4gICAgRnNNZW51TW9kdWxlLFxuICAgIEZzWm9vbVBhbk1vZHVsZSxcbiAgICBSZXBvcnRDb21wb25lbnRDb21wb25lbnQsXG4gIF0sXG59KVxuZXhwb3J0IGNsYXNzIFJlcG9ydENhbnZhc0NvbXBvbmVudCBpbXBsZW1lbnRzIE9uQ2hhbmdlcywgQWZ0ZXJWaWV3SW5pdCB7XG5cbiAgQElucHV0KCkgcHVibGljIHJlcG9ydDogUmVwb3J0O1xuICBASW5wdXQoKSBwdWJsaWMgZWRpdE1vZGUgPSBmYWxzZTtcblxuICAvLyBUaGUgcGFnZSB0aGUgaG9zdCB3YW50cyBvbiBzY3JlZW4sIGJ5IHBhZ2UgaWQgKGEgZGVlcCBsaW5rKS4gS2V5ZWQgb24gaWRcbiAgLy8gcmF0aGVyIHRoYW4gaW5kZXggc28gYSBsaW5rIHN1cnZpdmVzIHBhZ2VzIGJlaW5nIHJlb3JkZXJlZCBvciBkZWxldGVkOyBhblxuICAvLyBpZCB0aGF0IG5vIGxvbmdlciByZXNvbHZlcyBmYWxscyBiYWNrIHRvIHRoZSBmaXJzdCBwYWdlLlxuICBASW5wdXQoKSBwdWJsaWMgcGFnZUlkOiBudW1iZXIgfCBudWxsID0gbnVsbDtcblxuICAvLyBBIGNvbXBvbmVudCBhc2tlZCBmb3IgaXRzIHNldHRpbmdzIGRpYWxvZyDigJQgdGhlIHBhZ2UtbGV2ZWwgaG9zdCBvcGVucyBpdFxuICAvLyAoaXQgb3ducyBNYXREaWFsb2cgKyB0aGUgcG9zdC1zYXZlIHJlbG9hZCkuXG4gIEBPdXRwdXQoKSBwdWJsaWMgY29tcG9uZW50U2V0dGluZ3MgPSBuZXcgRXZlbnRFbWl0dGVyPFJlcG9ydENvbXBvbmVudD4oKTtcblxuICAvLyBUaGUgcmVwb3J0J3Mgc3RydWN0dXJlIGNoYW5nZWQgaGVyZSAoYSBwYWdlIHdhcyBhZGRlZCkg4oCUIHRoZSBob3N0IHJlLWZldGNoZXNcbiAgLy8gaXQgKGl0IG93bnMgdGhlIGFzc2VtYmxlZCByZXBvcnQgKyBmaWx0ZXIgc3RhdGUpLlxuICBAT3V0cHV0KCkgcHVibGljIHJlcG9ydENoYW5nZWQgPSBuZXcgRXZlbnRFbWl0dGVyPHZvaWQ+KCk7XG5cbiAgLy8gVGhlIHBhZ2Ugb24gc2NyZWVuIGNoYW5nZWQg4oCUIHRoZSBob3N0IHJlZmxlY3RzIGl0IGluIHRoZSBVUkwgc28gYSByZWZyZXNoXG4gIC8vIGNvbWVzIGJhY2sgdG8gdGhlIHNhbWUgcGFnZS4gQ2FycmllcyB0aGUgcGFnZSBpZCwgbmV2ZXIgdGhlIGluZGV4LlxuICBAT3V0cHV0KCkgcHVibGljIHBhZ2VDaGFuZ2VkID0gbmV3IEV2ZW50RW1pdHRlcjxudW1iZXIgfCBudWxsPigpO1xuXG4gIEBWaWV3Q2hpbGQoRnNab29tUGFuQ29tcG9uZW50KVxuICBwdWJsaWMgem9vbVBhbjogRnNab29tUGFuQ29tcG9uZW50O1xuXG4gIC8vIFRoZSByZW5kZXJlZCBjb21wb25lbnRzIG9mIHRoZSBhY3RpdmUgcGFnZSDigJQgb25seSB0aGUgY2FudmFzIGNhbiByZWFjaCB0aGVcbiAgLy8gb25lIGluc3RhbmNlIGEgc2V0dGluZ3Mgc2F2ZSBhcHBsaWVzIHRvLlxuICBAVmlld0NoaWxkcmVuKFJlcG9ydENvbXBvbmVudENvbXBvbmVudClcbiAgcHJpdmF0ZSBfcmVuZGVyZWRDb21wb25lbnRzOiBRdWVyeUxpc3Q8UmVwb3J0Q29tcG9uZW50Q29tcG9uZW50PjtcblxuICBAVmlld0NoaWxkKCd2aWV3cG9ydCcsIHsgc3RhdGljOiB0cnVlIH0pXG4gIHByaXZhdGUgX3ZpZXdwb3J0OiBFbGVtZW50UmVmPEhUTUxEaXZFbGVtZW50PjtcblxuICBAVmlld0NoaWxkKCdndWlkZXMnLCB7IHN0YXRpYzogZmFsc2UgfSlcbiAgcHJpdmF0ZSBfZ3VpZGVzOiBFbGVtZW50UmVmPEhUTUxEaXZFbGVtZW50PjtcblxuICBwdWJsaWMgcmVhZG9ubHkgUFggPSBQWF9QRVJfSU5DSDtcblxuICAvLyBUaGUgcmVwb3J0J3MgcGFnZXMgYXMgdGhlIGNhbnZhcyBkcmF3cyB0aGVtLiBUaGlzIGlzIHRoZSBob3N0J3Mgb3duXG4gIC8vIGByZXBvcnQucGFnZXNgIGFycmF5LCBwYXRjaGVkIGluIHBsYWNlIChhIHJlbmFtZSwgYSBkZWxldGUsIGEgcmVvcmRlcikgc29cbiAgLy8gdGhlIGhvc3QncyBleHBvcnRzIGFuZCBwYWdlIGxpbmtzIHNlZSB0aGUgY2hhbmdlIHRvby4gQmVjYXVzZSB0aGUgYXJyYXlcbiAgLy8gYW5kIGl0cyBwYWdlcyBrZWVwIHRoZWlyIGlkZW50aXR5IGFjcm9zcyBhIHBhdGNoLCB0aGUgc2lnbmFsIG5vdGlmaWVzIG9uXG4gIC8vIGV2ZXJ5IHNldCByYXRoZXIgdGhhbiBvbmx5IHdoZW4gdGhlIHJlZmVyZW5jZSBjaGFuZ2VzLlxuICBwdWJsaWMgcmVhZG9ubHkgcGFnZXMgPSBzaWduYWw8UmVwb3J0UGFnZVtdPihbXSwgeyBlcXVhbDogKCkgPT4gZmFsc2UgfSk7XG4gIHB1YmxpYyByZWFkb25seSBhY3RpdmVQYWdlSW5kZXggPSBzaWduYWwoMCk7XG4gIHB1YmxpYyByZWFkb25seSBhY3RpdmVQYWdlSWQgPSBjb21wdXRlZCgoKSA9PiB0aGlzLnBhZ2VzKClbdGhpcy5hY3RpdmVQYWdlSW5kZXgoKV0/LmlkID8/IG51bGwpO1xuICBwdWJsaWMgcmVhZG9ubHkgem9vbSA9IHNpZ25hbCgxKTtcblxuICAvLyBFZGl0aW5nIHRoZSBoZWFkZXIgYW5kIGZvb3RlciAodGhlIG1hc3RlciBsYXllcikgcmF0aGVyIHRoYW4gdGhlIHBhZ2UuXG4gIHB1YmxpYyByZWFkb25seSBtYXN0ZXJNb2RlID0gc2lnbmFsKGZhbHNlKTtcbiAgcHVibGljIGdyb3VwcyA9IG5ldyBNYXA8bnVtYmVyLCBSZXBvcnRGaWx0ZXJHcm91cD4oKTtcbiAgcHVibGljIHJlYWRvbmx5IHNlbGVjdGVkQ29tcG9uZW50SWQgPSBzaWduYWw8bnVtYmVyIHwgbnVsbD4obnVsbCk7XG5cbiAgLy8gVGhlIGNvbXBvbmVudHMgZWFjaCBsYXllciBkcmF3cy4gQSB2YWx1ZSBvbmx5IHJlYWRzIGluc2lkZSB0ZXh0LCBzbyBvbmVcbiAgLy8gdGhhdCBsZWFrZWQgaW50byBhIGxheWVyJ3MgY29tcG9uZW50cyBpcyBzdGlsbCBuZXZlciBkcmF3bi5cbiAgcHVibGljIHJlYWRvbmx5IGFjdGl2ZVBhZ2VDb21wb25lbnRzID0gY29tcHV0ZWQoXG4gICAgKCkgPT4gKHRoaXMucGFnZXMoKVt0aGlzLmFjdGl2ZVBhZ2VJbmRleCgpXT8uY29tcG9uZW50cyA/PyBbXSkuZmlsdGVyKGlzRHJhd24pLFxuICApO1xuXG4gIHB1YmxpYyByZWFkb25seSBtYXN0ZXJDb21wb25lbnRzID0gY29tcHV0ZWQoXG4gICAgKCkgPT4gKHRoaXMuX3JlcG9ydCgpPy5tYXN0ZXI/LmNvbXBvbmVudHMgPz8gW10pLmZpbHRlcihpc0RyYXduKSxcbiAgKTtcblxuICAvLyBXaGF0IGEgdGV4dCBibG9jaydzIHRva2VucyBmaWxsIHdpdGggb24gdGhlIHBhZ2Ugb24gc2NyZWVuOiB7e3BhZ2UubnVtYmVyfX0sXG4gIC8vIHt7cGFnZS5uYW1lfX0gYW5kIHt7cmVwb3J0Lm5hbWV9fSAodGhlIG1hc3RlcidzIGZvb3RlciBudW1iZXJzIGVhY2ggcGFnZSBieVxuICAvLyBpdHMgcG9zaXRpb24pLCBhbmQgdGhlIHZhbHVlcyBvZiB0aGUgYmxvY2sncyBsYXllciDigJQgdGhlIGFjdGl2ZSBwYWdlJ3MgZm9yXG4gIC8vIGEgcGFnZSBibG9jaywgdGhlIG1hc3RlcidzIGZvciBhIGhlYWRlciBvciBmb290ZXIgYmxvY2ssIHdob3NlIGlkIGlzIGFsc29cbiAgLy8gdGhlIGVkaXRvcidzIGNsaXBib2FyZCBzY29wZS4gVGhlIHNhbWUgb2JqZWN0IGlzIGhhbmRlZCBiYWNrIHVudGlsXG4gIC8vIHNvbWV0aGluZyBhIHRva2VuIHNob3dzIGNoYW5nZXM6IGV2ZXJ5IHRleHQgYmxvY2sgdGFrZXMgaXQgYXMgYW4gaW5wdXQsXG4gIC8vIGFuZCBhIGZyZXNoIG9iamVjdCB3b3VsZCBtYWtlIGVhY2ggb2YgdGhlbSByZXBhaW50IGl0cyBodG1sLlxuICBwdWJsaWMgcmVhZG9ubHkgcGFnZVRva2VucyA9IGNvbXB1dGVkKFxuICAgICgpID0+IHRoaXMuX3Rva2VuQ29udGV4dCh0aGlzLl9wYWdlVmFsdWVDb21wb25lbnRzKCksIHRoaXMuX3BhZ2VWYWx1ZXMsIHRoaXMuYWN0aXZlUGFnZUlkKCkpLFxuICAgIHsgZXF1YWw6IHNhbWVUb2tlbnMgfSxcbiAgKTtcblxuICBwdWJsaWMgcmVhZG9ubHkgbWFzdGVyVG9rZW5zID0gY29tcHV0ZWQoXG4gICAgKCkgPT4gdGhpcy5fdG9rZW5Db250ZXh0KHRoaXMuX21hc3RlclZhbHVlQ29tcG9uZW50cygpLCB0aGlzLl9tYXN0ZXJWYWx1ZXMsIHRoaXMuX3JlcG9ydCgpPy5tYXN0ZXI/LmlkID8/IG51bGwpLFxuICAgIHsgZXF1YWw6IHNhbWVUb2tlbnMgfSxcbiAgKTtcblxuICAvLyBUaGUgc25hcHBlciBoYW5kZWQgdG8gZXZlcnkgY29tcG9uZW50IChzdGFibGUgaWRlbnRpdHkgZm9yIE9uUHVzaCkuXG4gIHB1YmxpYyByZWFkb25seSBzbmFwcGVyOiBDYW52YXNTbmFwcGVyID0ge1xuICAgIHNuYXBNb3ZlOiAoY29tcG9uZW50LCB4LCB5KSA9PiB0aGlzLl9zbmFwTW92ZShjb21wb25lbnQsIHgsIHkpLFxuICAgIHNuYXBSZXNpemU6IChjb21wb25lbnQsIGdlb21ldHJ5LCBoYW5kbGUpID0+IHRoaXMuX3NuYXBSZXNpemUoY29tcG9uZW50LCBnZW9tZXRyeSwgaGFuZGxlKSxcbiAgICBjbGVhcjogKCkgPT4gdGhpcy5fY2xlYXJHdWlkZXMoKSxcbiAgfTtcblxuICAvLyBUaGUgdmFsdWUga2V5cyB0aGUgb3RoZXIgdGV4dCBibG9ja3Mgb2YgYSB0ZXh0J3MgbGF5ZXIgc2hvdyAodGhlIG1hc3RlcidzXG4gIC8vIGZvciBhIGhlYWRlciBvciBmb290ZXIgYmxvY2spLCBmb3IgaXRzIGVkaXRvcidzIG5vdGljZTogYSB2YWx1ZSBhbm90aGVyXG4gIC8vIGJsb2NrIHN0aWxsIHNob3dzIGlzIG5vdCBsZWZ0IHVudXNlZC4gUmVhZCB3aGVuIGFza2VkOiBzYXZpbmcgYSBibG9ja1xuICAvLyB3cml0ZXMgaXRzIGh0bWwgaW50byBpdHMgY29tcG9uZW50IGluIHBsYWNlLCB3aGljaCBubyBzaWduYWwgc2Vlcy5cbiAgLy8gU3RhYmxlLCBhcyB0aGUgc25hcHBlciBpcy5cbiAgcHVibGljIHJlYWRvbmx5IHZhbHVlS2V5c0Vsc2V3aGVyZSA9ICh0ZXh0OiBSZXBvcnRDb21wb25lbnQpOiBSZWFkb25seVNldDxzdHJpbmc+ID0+IHtcbiAgICBjb25zdCBsYXllciA9IHRoaXMuX2lzTWFzdGVyQ29tcG9uZW50KHRleHQpID8gdGhpcy5yZXBvcnQ/Lm1hc3RlciA6IHRoaXMuYWN0aXZlUGFnZTtcblxuICAgIHJldHVybiBuZXcgU2V0KChsYXllcj8uY29tcG9uZW50cyA/PyBbXSlcbiAgICAgIC5maWx0ZXIoKGNvbXBvbmVudCkgPT4gY29tcG9uZW50LnR5cGUgPT09ICd0ZXh0JyAmJiBjb21wb25lbnQuaWQgIT09IHRleHQuaWQpXG4gICAgICAuZmxhdE1hcCgoY29tcG9uZW50KSA9PiB2YWx1ZUtleXMoY29tcG9uZW50LmNvbmZpZz8uaHRtbCkpKTtcbiAgfTtcblxuICBwcml2YXRlIF9yZXBvcnREYXRhID0gaW5qZWN0KFJlcG9ydERhdGEpO1xuICBwcml2YXRlIF9maWx0ZXJTdGF0ZSA9IGluamVjdChSZXBvcnRGaWx0ZXJTdGF0ZVNlcnZpY2UpO1xuICBwcml2YXRlIF9wcm9tcHQgPSBpbmplY3QoRnNQcm9tcHQpO1xuICBwcml2YXRlIF9tZXNzYWdlID0gaW5qZWN0KEZzTWVzc2FnZSk7XG4gIHByaXZhdGUgX2Rlc3Ryb3lSZWYgPSBpbmplY3QoRGVzdHJveVJlZik7XG4gIHByaXZhdGUgX2ZpdHRlZCA9IGZhbHNlO1xuICBwcml2YXRlIF9wcmV2aW91c1BhZ2VDb3VudCA9IDA7XG5cbiAgLy8gVGhlIHBhZ2UgaWQgbGFzdCBhbm5vdW5jZWQgdGhyb3VnaCBwYWdlQ2hhbmdlZCwgc28gYSByZS1yZW5kZXIgdGhhdCBsYW5kcyBvblxuICAvLyB0aGUgc2FtZSBwYWdlIHN0YXlzIHF1aWV0IOKAlCBob3N0cyByZWxvYWQgb24gdGhpcyBhbmQgYW4gdW5jaGFuZ2VkIHBhZ2UgaXNcbiAgLy8gbm90IG5ld3MuXG4gIHByaXZhdGUgX2VtaXR0ZWRQYWdlSWQ6IG51bWJlciB8IG51bGwgPSBudWxsO1xuXG4gIC8vIFRoZSByZXBvcnQgaW5wdXQgYXMgYSBzaWduYWwsIGZvciB0aGUgdG9rZW4gY29udGV4dHMgYW5kIHRoZSBtYXN0ZXInc1xuICAvLyBkcmF3biBjb21wb25lbnRzLiBOb3RpZmllcyBvbiBldmVyeSBzZXQ6IGEgcmVsb2FkIGhhbmRzIG92ZXIgYSBuZXcgcmVwb3J0XG4gIC8vIGV2ZW4gd2hlbiBub3RoaW5nIGEgdG9rZW4gc2hvd3MgbW92ZWQsIGFuZCBhIGRlbGV0ZWQgaGVhZGVyIG9yIGZvb3RlclxuICAvLyBibG9jayBpcyBzcGxpY2VkIG91dCBvZiB0aGUgc2FtZSByZXBvcnQuXG4gIHByaXZhdGUgX3JlcG9ydCA9IHNpZ25hbDxSZXBvcnQgfCBudWxsPihudWxsLCB7IGVxdWFsOiAoKSA9PiBmYWxzZSB9KTtcblxuICAvLyBUaGUgdmFsdWVzIGVhY2ggbGF5ZXIncyB0ZXh0IGNhbiBzaG93IChzaG93biBvciBub3QpLlxuICBwcml2YXRlIF9wYWdlVmFsdWVDb21wb25lbnRzID0gY29tcHV0ZWQoKCkgPT4gdGhpcy5wYWdlcygpW3RoaXMuYWN0aXZlUGFnZUluZGV4KCldPy52YWx1ZXMgPz8gW10pO1xuICBwcml2YXRlIF9tYXN0ZXJWYWx1ZUNvbXBvbmVudHMgPSBjb21wdXRlZCgoKSA9PiB0aGlzLl9yZXBvcnQoKT8ubWFzdGVyPy52YWx1ZXMgPz8gW10pO1xuXG4gIC8vIFRoZSBtYXN0ZXIncyBudW1iZXJzIGFyZSBuZWVkZWQgd2hpbGUgc29tZSBwYWdlIHNob3dzIHRoZSBoZWFkZXIgYW5kXG4gIC8vIGZvb3Rlciwgb3Igd2hpbGUgdGhleSBhcmUgYmVpbmcgZWRpdGVkLlxuICBwcml2YXRlIF9tYXN0ZXJOZWVkZWQgPSBjb21wdXRlZCgoKSA9PiB0aGlzLm1hc3Rlck1vZGUoKSB8fCB0aGlzLnBhZ2VzKCkuc29tZSgocGFnZSkgPT4gIXBhZ2UubWFzdGVySGlkZGVuKSk7XG5cbiAgLy8gVGhlIHR3byBsYXllcnMgd2hvc2UgdmFsdWVzIGFyZSByZWFkLCBlYWNoIG9uIGl0cyBvd24gc3RyZWFtLlxuICBwcml2YXRlIF9wYWdlVmFsdWVzID0gdGhpcy5fdmFsdWVMYXllcigoKSA9PiB0aGlzLmFjdGl2ZVBhZ2UpO1xuICBwcml2YXRlIF9tYXN0ZXJWYWx1ZXMgPSB0aGlzLl92YWx1ZUxheWVyKCgpID0+ICh0aGlzLl9tYXN0ZXJOZWVkZWQoKSA/IHRoaXMucmVwb3J0Py5tYXN0ZXIgPz8gbnVsbCA6IG51bGwpKTtcblxuICAvLyBCdW1wZWQgd2hlbiBhIHZhbHVlIGlzIHJlbmFtZWQgaW4gcGxhY2UsIHdoaWNoIG5vIHNpZ25hbCBzZWVzLlxuICBwcml2YXRlIF92YWx1ZXNSZXZpc2lvbiA9IHNpZ25hbCgwKTtcblxuICAvLyBUaGUgdmFsdWUga2V5cyBlYWNoIGxheWVyIGhlbGQgYXQgdGhlIGxhc3QgcmVwb3J0IGxvYWQsIGJ5IHBhZ2UgaWQgYW5kXG4gIC8vIG1hc3RlciBpZCwgc28gYSByZWxvYWQgY2FuIHRlbGwgd2hpY2ggdmFsdWVzIHdlcmUgZGVsZXRlZC5cbiAgcHJpdmF0ZSBfdmFsdWVLZXlzQnlMYXllciA9IG5ldyBNYXA8bnVtYmVyLCBTZXQ8c3RyaW5nPj4oKTtcblxuICBjb25zdHJ1Y3RvcigpIHtcbiAgICB0aGlzLl9pbml0KCk7XG4gIH1cblxuICBwdWJsaWMgbmdPbkNoYW5nZXMoY2hhbmdlczogU2ltcGxlQ2hhbmdlcyk6IHZvaWQge1xuICAgIC8vIExlYXZpbmcgZWRpdCBtb2RlIGFsd2F5cyByZXR1cm5zIHRvIHRoZSBwYWdlIGxheWVyLCBzbyB0aGUgbmV4dCBlZGl0XG4gICAgLy8gc2Vzc2lvbiBzdGFydHMgd2hlcmUgcGVvcGxlIGV4cGVjdC5cbiAgICBpZiAoY2hhbmdlcy5lZGl0TW9kZSAmJiAhdGhpcy5lZGl0TW9kZSkge1xuICAgICAgdGhpcy5tYXN0ZXJNb2RlLnNldChmYWxzZSk7XG4gICAgfVxuXG4gICAgdGhpcy5ncm91cHMgPSBuZXcgTWFwKCh0aGlzLnJlcG9ydD8uZmlsdGVyR3JvdXBzID8/IFtdKS5tYXAoKGdyb3VwKSA9PiBbZ3JvdXAuaWQsIGdyb3VwXSkpO1xuICAgIHRoaXMucGFnZXMuc2V0KHRoaXMucmVwb3J0Py5wYWdlcyA/PyBbXSk7XG5cbiAgICBjb25zdCBwYWdlQ291bnQgPSB0aGlzLnBhZ2VzKCkubGVuZ3RoO1xuXG4gICAgLy8gQSBwYWdlIHdhcyBqdXN0IGFkZGVkICh0aGUgaG9zdCByZS1mZXRjaGVkIHRoZSByZXBvcnQpIOKAlCBsYW5kIG9uIGl0LlxuICAgIGNvbnN0IHBhZ2VBZGRlZCA9IHBhZ2VDb3VudCA+IHRoaXMuX3ByZXZpb3VzUGFnZUNvdW50ICYmIHRoaXMuX3ByZXZpb3VzUGFnZUNvdW50ID4gMDtcbiAgICBpZiAocGFnZUFkZGVkKSB7XG4gICAgICB0aGlzLmFjdGl2ZVBhZ2VJbmRleC5zZXQocGFnZUNvdW50IC0gMSk7XG4gICAgfVxuICAgIHRoaXMuX3ByZXZpb3VzUGFnZUNvdW50ID0gcGFnZUNvdW50O1xuXG4gICAgLy8gSG9ub3VyIGFuIGluY29taW5nIGRlZXAgbGluaywgYnV0IG5ldmVyIG92ZXIgYSBqdXN0LWFkZGVkIHBhZ2U6IGFkZGluZyBhXG4gICAgLy8gcGFnZSBpcyBhIGRlbGliZXJhdGUgYWN0IGluIHRoaXMgdGFiLCB3aGlsZSBwYWdlSWQgaXMgdGhlIHN0YWxlIHZhbHVlIHRoZVxuICAgIC8vIGhvc3QgaXMgc3RpbGwgaG9sZGluZyBmcm9tIHRoZSBVUkwuIEFuIGlkIHRoYXQgZG9lcyBub3QgcmVzb2x2ZSBpcyBsZWZ0XG4gICAgLy8gYWxvbmUgcmF0aGVyIHRoYW4gZm9yY2VkIHRvIHRoZSBmaXJzdCBwYWdlIOKAlCB0aGUgcmVwb3J0IG1heSBzdGlsbCBiZVxuICAgIC8vIGxvYWRpbmcsIGFuZCB0aGUgY2xhbXAgYmVsb3cgaXMgdGhlIHJlYWwgZ3VhcmQuXG4gICAgaWYgKCFwYWdlQWRkZWQgJiYgdGhpcy5wYWdlSWQgIT0gbnVsbCkge1xuICAgICAgY29uc3QgaW5kZXggPSB0aGlzLnBhZ2VzKCkuZmluZEluZGV4KChwYWdlKSA9PiBwYWdlLmlkID09PSB0aGlzLnBhZ2VJZCk7XG5cbiAgICAgIGlmIChpbmRleCA+IC0xKSB7XG4gICAgICAgIHRoaXMuYWN0aXZlUGFnZUluZGV4LnNldChpbmRleCk7XG4gICAgICB9XG4gICAgfVxuXG4gICAgaWYgKHRoaXMuYWN0aXZlUGFnZUluZGV4KCkgPj0gcGFnZUNvdW50KSB7XG4gICAgICB0aGlzLmFjdGl2ZVBhZ2VJbmRleC5zZXQoMCk7XG4gICAgfVxuXG4gICAgLy8gVGVsbCB0aGUgaG9zdCB3aGljaCBwYWdlIGlzIG9wZW4gd2hlbmV2ZXIgdGhhdCBjaGFuZ2VzIOKAlCBpbmNsdWRpbmcgdGhlXG4gICAgLy8gRklSU1QgdGltZSB0aGUgcmVwb3J0IHJlbmRlcnMsIG5vdCBvbmx5IHdoZW4gc29tZW9uZSBjbGlja3MgYSBwYWdlLlxuICAgIC8vIEhvc3RzIGJpbmQgdGhpbmdzIHRvIHRoZSBvcGVuIHBhZ2UgKHRoZSByZXBvcnQgY2hhdCBzY29wZXMgaXRzXG4gICAgLy8gY29udmVyc2F0aW9ucyB0byBpdCksIGFuZCB3aXRob3V0IHRoaXMgdGhleSB3b3VsZCBzaXQgb24gbm8gcGFnZSBhdCBhbGxcbiAgICAvLyB1bnRpbCB0aGUgZmlyc3QgbWFudWFsIHBhZ2UgY2xpY2suXG4gICAgY29uc3QgYWN0aXZlUGFnZUlkID0gdGhpcy5hY3RpdmVQYWdlPy5pZCA/PyBudWxsO1xuICAgIGlmIChhY3RpdmVQYWdlSWQgIT09IHRoaXMuX2VtaXR0ZWRQYWdlSWQpIHtcbiAgICAgIHRoaXMuX2VtaXR0ZWRQYWdlSWQgPSBhY3RpdmVQYWdlSWQ7XG4gICAgICB0aGlzLnBhZ2VDaGFuZ2VkLmVtaXQoYWN0aXZlUGFnZUlkKTtcbiAgICB9XG5cbiAgICAvLyBBIChyZSlsb2FkZWQgcmVwb3J0IG1heSBoYXZlIGdhaW5lZCwgbG9zdCBvciBjaGFuZ2VkIHZhbHVlcywgYW5kIGFueVxuICAgIC8vIHRleHQgbWF5IG5vdyBzaG93IGRpZmZlcmVudCBvbmVzOiByZWFkIGFnYWluIGVhY2ggbGF5ZXIgd2hvc2UgbnVtYmVyc1xuICAgIC8vIHRoYXQgbW92ZXMuXG4gICAgaWYgKGNoYW5nZXMucmVwb3J0KSB7XG4gICAgICB0aGlzLl9yZXBvcnQuc2V0KHRoaXMucmVwb3J0KTtcbiAgICAgIHRoaXMuX2Ryb3BSZW1vdmVkVmFsdWVDaGlwcygpO1xuICAgICAgdGhpcy5fcmVsb2FkSWZDaGFuZ2VkKHRoaXMuX3BhZ2VWYWx1ZXMpO1xuICAgICAgdGhpcy5fcmVsb2FkSWZDaGFuZ2VkKHRoaXMuX21hc3RlclZhbHVlcyk7XG4gICAgfVxuICB9XG5cbiAgLy8gUmVwb3J0IGhlYWRpbmcgc2l6ZSBpbiBweCAoY29uZmlnIGlzIHBvaW50czsgdGhlIGNhbnZhcyByZW5kZXJzIGF0XG4gIC8vIDk2cHgvaW4sIHNvIHBvaW50cyDDlyA5Ni83MikuIEluaGVyaXRlZCBieSBjb21wb25lbnQgdGl0bGVzIHZpYSBhIENTUyB2YXIuXG4gIHB1YmxpYyBnZXQgaGVhZGluZ1NpemVQeCgpOiBudW1iZXIge1xuICAgIGNvbnN0IHBvaW50cyA9IHRoaXMucmVwb3J0Py5jb25maWc/LnN0eWxlcz8uaGVhZGluZz8uc2l6ZSA/PyBERUZBVUxUX0hFQURJTkdfU0laRTtcblxuICAgIHJldHVybiBwb2ludHMgKiAoUFhfUEVSX0lOQ0ggLyA3Mik7XG4gIH1cblxuICBwdWJsaWMgbmdBZnRlclZpZXdJbml0KCk6IHZvaWQge1xuICAgIC8vIEZpdCB0aGUgcGFnZSB0byB0aGUgdmlld3BvcnQgb25jZSBvbiBmaXJzdCByZW5kZXI7IGFmdGVyIHRoYXQgdGhlXG4gICAgLy8gdmlld2VyJ3Mgem9vbSBjaG9pY2UgaXMgcmVzcGVjdGVkIGFjcm9zcyByZS1yZW5kZXJzLlxuICAgIHNldFRpbWVvdXQoKCkgPT4gdGhpcy56b29tRml0KCkpO1xuICB9XG5cbiAgcHVibGljIGdldCBhY3RpdmVQYWdlKCk6IFJlcG9ydFBhZ2UgfCBudWxsIHtcbiAgICByZXR1cm4gdGhpcy5wYWdlcygpW3RoaXMuYWN0aXZlUGFnZUluZGV4KCldID8/IG51bGw7XG4gIH1cblxuICAvLyBUaGUgaGVhZGVyL2Zvb3RlciBiYW5kcywgaW4gaW5jaGVzICgwID0gbm8gYmFuZCkuXG4gIHB1YmxpYyBnZXQgYmFuZHMoKTogUmVwb3J0SGVhZGVyRm9vdGVyIHtcbiAgICByZXR1cm4gdGhpcy5yZXBvcnQ/LmNvbmZpZz8uaGVhZGVyRm9vdGVyID8/IHsgaGVhZGVySGVpZ2h0OiAwLCBmb290ZXJIZWlnaHQ6IDAgfTtcbiAgfVxuXG4gIC8vIFRoZSBtYXN0ZXIgZHJhd3MgdW5sZXNzIHRoZSBwYWdlIGhpZGVzIGl0IOKAlCBhbmQgYWx3YXlzIHdoaWxlIGl0IGlzIHRoZVxuICAvLyBsYXllciBiZWluZyBlZGl0ZWQsIHNvIGEgcGFnZSB0aGF0IGhpZGVzIGl0IGNhbiBzdGlsbCBiZSB1c2VkIHRvIGVkaXQgaXQuXG4gIHB1YmxpYyBnZXQgaXNNYXN0ZXJTaG93bigpOiBib29sZWFuIHtcbiAgICByZXR1cm4gdGhpcy5tYXN0ZXJNb2RlKCkgfHwgIXRoaXMuYWN0aXZlUGFnZT8ubWFzdGVySGlkZGVuO1xuICB9XG5cbiAgLy8gV2hpY2ggbGF5ZXIgdGhlIGVkaXQgZ2VzdHVyZXMgcmVhY2guXG4gIHB1YmxpYyBnZXQgaXNQYWdlRWRpdGluZygpOiBib29sZWFuIHtcbiAgICByZXR1cm4gdGhpcy5lZGl0TW9kZSAmJiAhdGhpcy5tYXN0ZXJNb2RlKCk7XG4gIH1cblxuICBwdWJsaWMgZ2V0IGlzTWFzdGVyRWRpdGluZygpOiBib29sZWFuIHtcbiAgICByZXR1cm4gdGhpcy5lZGl0TW9kZSAmJiB0aGlzLm1hc3Rlck1vZGUoKTtcbiAgfVxuXG4gIHB1YmxpYyB0b2dnbGVNYXN0ZXJNb2RlKCk6IHZvaWQge1xuICAgIHRoaXMubWFzdGVyTW9kZS51cGRhdGUoKHZhbHVlKSA9PiAhdmFsdWUpO1xuICAgIHRoaXMuc2VsZWN0ZWRDb21wb25lbnRJZC5zZXQobnVsbCk7XG4gIH1cblxuICAvLyBEcm9wIGEgdGV4dCBibG9jayB3aGVyZSBpdCB3aWxsIGJlIGZvdW5kOiBpbnRvIHRoZSBmb290ZXIgKG9yIGhlYWRlcikgYmFuZFxuICAvLyB3aGlsZSBlZGl0aW5nIHRoZSBoZWFkZXIgYW5kIGZvb3RlciwgYmVsb3cgdGhlIGhlYWRlciBiYW5kIG9uIGEgcGFnZS4gVGhlXG4gIC8vIGhvc3QgcmUtZmV0Y2hlcyB0aGUgcmVwb3J0IGFuZCBpdCBhcHBlYXJzOyBkb3VibGUtcHJlc3Mgb3BlbnMgaXRzIGVkaXRvci5cbiAgcHVibGljIGFkZFRleHQoKTogdm9pZCB7XG4gICAgaWYgKCF0aGlzLnJlcG9ydCkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIGNvbnN0IHsgaGVhZGVySGVpZ2h0LCBmb290ZXJIZWlnaHQgfSA9IHRoaXMuYmFuZHM7XG4gICAgY29uc3QgcGFnZVdpZHRoID0gdGhpcy5yZXBvcnQucGFnZVdpZHRoO1xuICAgIGNvbnN0IHBhZ2VIZWlnaHQgPSB0aGlzLnJlcG9ydC5wYWdlSGVpZ2h0O1xuICAgIGNvbnN0IGlzTWFzdGVyID0gdGhpcy5tYXN0ZXJNb2RlKCk7XG5cbiAgICBsZXQgZ2VvbWV0cnkgPSB7IHg6IDAuNSwgeTogaGVhZGVySGVpZ2h0ICsgMC41LCB3OiBNYXRoLm1pbig1LCBwYWdlV2lkdGggLSAxKSwgaDogMC44IH07XG4gICAgaWYgKGlzTWFzdGVyKSB7XG4gICAgICBjb25zdCBiYW5kSGVpZ2h0ID0gZm9vdGVySGVpZ2h0IHx8IGhlYWRlckhlaWdodCB8fCAwLjU7XG4gICAgICBjb25zdCB5ID0gZm9vdGVySGVpZ2h0XG4gICAgICAgID8gcGFnZUhlaWdodCAtIGZvb3RlckhlaWdodFxuICAgICAgICA6IChoZWFkZXJIZWlnaHQgPyAwIDogcGFnZUhlaWdodCAtIGJhbmRIZWlnaHQpO1xuICAgICAgZ2VvbWV0cnkgPSB7IHg6IDAuNSwgeTogeSArIDAuMDUsIHc6IE1hdGgubWluKDQsIHBhZ2VXaWR0aCAtIDEpLCBoOiBNYXRoLm1heCgwLjMsIGJhbmRIZWlnaHQgLSAwLjEpIH07XG4gICAgfVxuXG4gICAgdGhpcy5fcmVwb3J0RGF0YS5hZGRUZXh0KHRoaXMucmVwb3J0LmlkLCB7XG4gICAgICAuLi5nZW9tZXRyeSxcbiAgICAgIHBhZ2VJZDogaXNNYXN0ZXIgPyB1bmRlZmluZWQgOiB0aGlzLmFjdGl2ZVBhZ2U/LmlkLFxuICAgIH0pXG4gICAgICAucGlwZSh0YWtlVW50aWxEZXN0cm95ZWQodGhpcy5fZGVzdHJveVJlZikpXG4gICAgICAuc3Vic2NyaWJlKCgpID0+IHRoaXMucmVwb3J0Q2hhbmdlZC5lbWl0KCkpO1xuICB9XG5cbiAgLy8gQSB0ZXh0IGJsb2NrIGRlbGV0ZWQgaXRzZWxmIGZyb20gaXRzIG1lbnU6IGRyb3AgaXQgZnJvbSB3aGljaGV2ZXIgbGF5ZXIgaXRcbiAgLy8gd2FzIG9uIHdpdGhvdXQgcmUtZmV0Y2hpbmcgdGhlIHJlcG9ydC4gVGhhdCBjb3ZlcnMgdGhlIGJsb2NrIGFsb25lOiB0aGVcbiAgLy8gZGVsZXRlIGFsc28gdGFrZXMgdGhlIHZhbHVlcyBvbmx5IGl0IHNob3dlZCwgd2hpY2ggY29tZSBiYWNrIGFzXG4gIC8vIHZhbHVlc1JlbW92ZWQsIGFuZCB0aGF0IGFza3MgdGhlIGhvc3QgdG8gcmVsb2FkIHRoZSByZXBvcnQuXG4gIHB1YmxpYyBvbkNvbXBvbmVudFJlbW92ZWQoY29tcG9uZW50SWQ6IG51bWJlcik6IHZvaWQge1xuICAgIGNvbnN0IGxheWVycyA9IFt0aGlzLmFjdGl2ZVBhZ2U/LmNvbXBvbmVudHMsIHRoaXMucmVwb3J0Py5tYXN0ZXI/LmNvbXBvbmVudHNdO1xuICAgIGZvciAoY29uc3QgY29tcG9uZW50cyBvZiBsYXllcnMpIHtcbiAgICAgIGNvbnN0IGluZGV4ID0gY29tcG9uZW50cz8uZmluZEluZGV4KChjb21wb25lbnQpID0+IGNvbXBvbmVudC5pZCA9PT0gY29tcG9uZW50SWQpID8/IC0xO1xuICAgICAgaWYgKGluZGV4ID4gLTEpIHtcbiAgICAgICAgY29tcG9uZW50cy5zcGxpY2UoaW5kZXgsIDEpO1xuICAgICAgfVxuICAgIH1cblxuICAgIHRoaXMuc2VsZWN0ZWRDb21wb25lbnRJZC5zZXQobnVsbCk7XG4gICAgdGhpcy5wYWdlcy5zZXQodGhpcy5wYWdlcygpKTtcbiAgICB0aGlzLl9yZXBvcnQuc2V0KHRoaXMucmVwb3J0KTtcbiAgICB0aGlzLl9tZXNzYWdlLnN1Y2Nlc3MoJ0RlbGV0ZWQgdGV4dCcpO1xuICB9XG5cbiAgLy8gQSB0ZXh0IGJsb2NrJ3MgaHRtbCB3YXMgc2F2ZWQuIFNhdmluZyBuZXZlciBkZWxldGVzIGEgdmFsdWUsIGJ1dCBpdCBjYW5cbiAgLy8gc2hvdyBvbmUgdGhlIGxheWVyIGhhcyBubyBudW1iZXIgZm9yOiBhIGNoaXAgcGFzdGVkIGJhY2sgZnJvbSBhIHZhbHVlIG5vXG4gIC8vIHRleHQgc2hvd2VkLCB3aGljaCB0aGUgc2VydmVyIGRpZCBub3QgcmVhZC4gSXRzIGxheWVyIGlzIHJlYWQgYWdhaW4gc28gdGhlXG4gIC8vIG51bWJlciBjb21lcyBpbjsgYW4gZWRpdCB0aGF0IHNob3dzIG9ubHkgdmFsdWVzIGFscmVhZHkgcmVhZCBhc2tzIG5vdGhpbmcuXG4gIHB1YmxpYyBvblRleHRTYXZlZCh0ZXh0OiBSZXBvcnRDb21wb25lbnQsIGh0bWw6IHN0cmluZyk6IHZvaWQge1xuICAgIGNvbnN0IGlzTWFzdGVyID0gdGhpcy5faXNNYXN0ZXJDb21wb25lbnQodGV4dCk7XG4gICAgY29uc3QgbGF5ZXIgPSBpc01hc3RlciA/IHRoaXMuX21hc3RlclZhbHVlcyA6IHRoaXMuX3BhZ2VWYWx1ZXM7XG4gICAgY29uc3QgbGF5ZXJJZCA9IGlzTWFzdGVyID8gKHRoaXMucmVwb3J0Py5tYXN0ZXI/LmlkID8/IG51bGwpIDogdGhpcy5hY3RpdmVQYWdlSWQoKTtcbiAgICBjb25zdCByZXN1bHRzID0gbGF5ZXIucmVzdWx0cygpO1xuICAgIGNvbnN0IHJvd3MgPSByZXN1bHRzPy5wYWdlSWQgPT09IGxheWVySWQgPyByZXN1bHRzLnJvd3MgOiBudWxsO1xuICAgIGNvbnN0IHZhbHVlcyA9IGlzTWFzdGVyID8gdGhpcy5fbWFzdGVyVmFsdWVDb21wb25lbnRzKCkgOiB0aGlzLl9wYWdlVmFsdWVDb21wb25lbnRzKCk7XG4gICAgY29uc3QgdW5yZWFkID0gc2hvd25WYWx1ZXModmFsdWVzLCBbeyAuLi50ZXh0LCBjb25maWc6IHsgLi4udGV4dC5jb25maWcsIGh0bWwgfSB9XSlcbiAgICAgIC5zb21lKCh2YWx1ZSkgPT4gIXJvd3M/Lmhhcyh2YWx1ZS5pZCkpO1xuXG4gICAgaWYgKHVucmVhZCkge1xuICAgICAgbGF5ZXIucmVsb2FkJC5uZXh0KCk7XG4gICAgfVxuICB9XG5cbiAgLy8gQSBjaGlwJ3MgZ2Vhcjogb3BlbiB0aGUgc2V0dGluZ3Mgb2YgdGhlIHZhbHVlIGl0IG5hbWVzLCBmcm9tIHRoZSBibG9jaydzXG4gIC8vIG93biBsYXllciwgdGhyb3VnaCB0aGUgc2FtZSBvdXRwdXQgYXMgYW55IGNvbXBvbmVudCdzIHNldHRpbmdzLlxuICBwdWJsaWMgb3BlblZhbHVlU2V0dGluZ3ModGV4dDogUmVwb3J0Q29tcG9uZW50LCBrZXk6IHN0cmluZyk6IHZvaWQge1xuICAgIGNvbnN0IHZhbHVlcyA9IHRoaXMuX2lzTWFzdGVyQ29tcG9uZW50KHRleHQpID8gdGhpcy5fbWFzdGVyVmFsdWVDb21wb25lbnRzKCkgOiB0aGlzLl9wYWdlVmFsdWVDb21wb25lbnRzKCk7XG4gICAgLy8gVGhlIG5ld2VzdCB2YWx1ZSBob2xkcyBhIGtleSwgYXMgaXQgZG9lcyBpbiB0aGUgdGV4dCdzIHRva2Vucy5cbiAgICBjb25zdCB2YWx1ZSA9IHZhbHVlcy5maWx0ZXIoKGNhbmRpZGF0ZSkgPT4gdmFsdWVLZXkoY2FuZGlkYXRlKSA9PT0ga2V5KS5wb3AoKTtcblxuICAgIGlmICh2YWx1ZSkge1xuICAgICAgdGhpcy5jb21wb25lbnRTZXR0aW5ncy5lbWl0KHZhbHVlKTtcbiAgICB9XG4gIH1cblxuICAvLyBTaG93IG9yIGhpZGUgdGhlIGhlYWRlciBhbmQgZm9vdGVyIG9uIG9uZSBwYWdlLCBmcm9tIGl0cyB0YWIncyBrZWJhYi5cbiAgcHVibGljIHRvZ2dsZU1hc3RlckhpZGRlbihwYWdlOiBSZXBvcnRQYWdlKTogdm9pZCB7XG4gICAgY29uc3QgbWFzdGVySGlkZGVuID0gIXBhZ2UubWFzdGVySGlkZGVuO1xuXG4gICAgdGhpcy5fcmVwb3J0RGF0YS51cGRhdGVQYWdlKHRoaXMucmVwb3J0LmlkLCBwYWdlLmlkLCB7IG1hc3RlckhpZGRlbiB9KVxuICAgICAgLnBpcGUodGFrZVVudGlsRGVzdHJveWVkKHRoaXMuX2Rlc3Ryb3lSZWYpKVxuICAgICAgLnN1YnNjcmliZSgoKSA9PiB7XG4gICAgICAgIHBhZ2UubWFzdGVySGlkZGVuID0gbWFzdGVySGlkZGVuO1xuICAgICAgICB0aGlzLnBhZ2VzLnNldCh0aGlzLnBhZ2VzKCkpO1xuICAgICAgICB0aGlzLl9tZXNzYWdlLnN1Y2Nlc3MobWFzdGVySGlkZGVuID8gJ0hlYWRlciAmIGZvb3RlciBoaWRkZW4gb24gdGhpcyBwYWdlJyA6ICdIZWFkZXIgJiBmb290ZXIgc2hvd24gb24gdGhpcyBwYWdlJyk7XG4gICAgICB9KTtcbiAgfVxuXG4gIHB1YmxpYyBzZWxlY3RQYWdlKGluZGV4OiBudW1iZXIpOiB2b2lkIHtcbiAgICB0aGlzLmFjdGl2ZVBhZ2VJbmRleC5zZXQoaW5kZXgpO1xuICAgIHRoaXMuc2VsZWN0ZWRDb21wb25lbnRJZC5zZXQobnVsbCk7XG5cbiAgICAvLyBLZXB0IGluIHN0ZXAgd2l0aCB0aGUgbmdPbkNoYW5nZXMgYW5ub3VuY2VtZW50IHNvIHRoZSB0d28gY2FuJ3QgZGlzYWdyZWVcbiAgICAvLyBhYm91dCB3aGF0IHRoZSBob3N0IHdhcyBsYXN0IHRvbGQuXG4gICAgdGhpcy5fZW1pdHRlZFBhZ2VJZCA9IHRoaXMuYWN0aXZlUGFnZT8uaWQgPz8gbnVsbDtcbiAgICB0aGlzLnBhZ2VDaGFuZ2VkLmVtaXQodGhpcy5fZW1pdHRlZFBhZ2VJZCk7XG4gIH1cblxuICAvLyBBcHBlbmQgYSBibGFuayBwYWdlOyB0aGUgaG9zdCByZS1mZXRjaGVzIHRoZSByZXBvcnQgYW5kIG5nT25DaGFuZ2VzIGxhbmRzXG4gIC8vIHRoZSB2aWV3IG9uIHRoZSBuZXcgKGxhc3QpIHBhZ2UuXG4gIHB1YmxpYyBhZGRQYWdlKCk6IHZvaWQge1xuICAgIGlmICghdGhpcy5yZXBvcnQpIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICB0aGlzLl9yZXBvcnREYXRhLmFkZFBhZ2UodGhpcy5yZXBvcnQuaWQpXG4gICAgICAucGlwZSh0YWtlVW50aWxEZXN0cm95ZWQodGhpcy5fZGVzdHJveVJlZikpXG4gICAgICAuc3Vic2NyaWJlKCgpID0+IHRoaXMucmVwb3J0Q2hhbmdlZC5lbWl0KCkpO1xuICB9XG5cbiAgcHVibGljIHBhZ2VMYWJlbChwYWdlOiBSZXBvcnRQYWdlLCBpbmRleDogbnVtYmVyKTogc3RyaW5nIHtcbiAgICByZXR1cm4gcGFnZS5uYW1lIHx8IGBQYWdlICR7aW5kZXggKyAxfWA7XG4gIH1cblxuICAvLyBSZW5hbWUgZnJvbSB0aGUgdGFiJ3Mga2ViYWIuIFRoZSBwYWdlIGxpc3QgaXMgcGF0Y2hlZCBpbiBwbGFjZSByYXRoZXIgdGhhblxuICAvLyByZS1mZXRjaGluZyB0aGUgcmVwb3J0OiBub3RoaW5nIGVsc2Ugb24gdGhlIGNhbnZhcyBkZXBlbmRzIG9uIGEgcGFnZSdzXG4gIC8vIG5hbWUsIGFuZCBhIHJlLWZldGNoIHdvdWxkIHJlLXJ1biBldmVyeSBjb21wb25lbnQncyBxdWVyeSB0byByZXBhaW50IGFcbiAgLy8gY2hpcCdzIGxhYmVsLlxuICBwdWJsaWMgcmVuYW1lUGFnZShwYWdlOiBSZXBvcnRQYWdlKTogdm9pZCB7XG4gICAgdGhpcy5fcHJvbXB0LmlucHV0KHtcbiAgICAgIHRpdGxlOiAnRWRpdCBQYWdlIE5hbWUnLFxuICAgICAgbGFiZWw6ICdOYW1lJyxcbiAgICAgIGRlZmF1bHQ6IHBhZ2UubmFtZSA/PyAnJyxcbiAgICAgIGNvbW1pdExhYmVsOiAnU2F2ZScsXG4gICAgICByZXF1aXJlZDogdHJ1ZSxcbiAgICB9KVxuICAgICAgLnBpcGUoXG4gICAgICAgIHN3aXRjaE1hcCgobmFtZTogc3RyaW5nKSA9PiB0aGlzLl9yZXBvcnREYXRhXG4gICAgICAgICAgLnVwZGF0ZVBhZ2UodGhpcy5yZXBvcnQuaWQsIHBhZ2UuaWQsIHsgbmFtZSB9KVxuICAgICAgICAgIC5waXBlKG1hcCgoKSA9PiBuYW1lKSkpLFxuICAgICAgICB0YWtlVW50aWxEZXN0cm95ZWQodGhpcy5fZGVzdHJveVJlZiksXG4gICAgICApXG4gICAgICAuc3Vic2NyaWJlKChuYW1lOiBzdHJpbmcpID0+IHtcbiAgICAgICAgcGFnZS5uYW1lID0gbmFtZTtcbiAgICAgICAgdGhpcy5wYWdlcy5zZXQodGhpcy5wYWdlcygpKTtcbiAgICAgICAgdGhpcy5fbWVzc2FnZS5zdWNjZXNzKCdTYXZlZCBwYWdlIG5hbWUnKTtcbiAgICAgIH0pO1xuICB9XG5cbiAgLy8gRGVsZXRlIGZyb20gdGhlIHRhYidzIGtlYmFiLiBUaGUgY29uZmlybSBuYW1lcyB0aGUgcGFnZSBhbmQgc2F5cyB0aGVcbiAgLy8gY29tcG9uZW50cyBnbyB3aXRoIGl0IOKAlCB0aGUgc2VydmVyIHJlZnVzZXMgdGhlIGxhc3QgcGFnZSwgYW5kIHRoYXQgcmVmdXNhbFxuICAvLyBzdXJmYWNlcyBhcyB0aGUgQVBJIGVycm9yIG1lc3NhZ2UgcmF0aGVyIHRoYW4gYmVpbmcgc2Vjb25kLWd1ZXNzZWQgaGVyZS5cbiAgcHVibGljIGRlbGV0ZVBhZ2UocGFnZTogUmVwb3J0UGFnZSk6IHZvaWQge1xuICAgIHRoaXMuX3Byb21wdC5jb25maXJtKHtcbiAgICAgIHRpdGxlOiAnQ29uZmlybScsXG4gICAgICB0ZW1wbGF0ZTogYEFyZSB5b3Ugc3VyZSB5b3Ugd291bGQgbGlrZSB0byBkZWxldGUgXCIke3RoaXMucGFnZUxhYmVsKHBhZ2UsIHRoaXMucGFnZXMoKS5pbmRleE9mKHBhZ2UpKX1cIiBhbmQgZXZlcnl0aGluZyBvbiBpdD9gLFxuICAgIH0pXG4gICAgICAucGlwZShcbiAgICAgICAgc3dpdGNoTWFwKCgpID0+IHRoaXMuX3JlcG9ydERhdGEuZGVsZXRlUGFnZSh0aGlzLnJlcG9ydC5pZCwgcGFnZS5pZCkpLFxuICAgICAgICB0YWtlVW50aWxEZXN0cm95ZWQodGhpcy5fZGVzdHJveVJlZiksXG4gICAgICApXG4gICAgICAuc3Vic2NyaWJlKCgpID0+IHtcbiAgICAgICAgY29uc3QgcGFnZXMgPSB0aGlzLnBhZ2VzKCk7XG4gICAgICAgIGNvbnN0IGluZGV4ID0gcGFnZXMuaW5kZXhPZihwYWdlKTtcbiAgICAgICAgcGFnZXMuc3BsaWNlKGluZGV4LCAxKTtcbiAgICAgICAgdGhpcy5wYWdlcy5zZXQocGFnZXMpO1xuXG4gICAgICAgIC8vIExhbmQgb24gdGhlIG5laWdoYm91ciByYXRoZXIgdGhhbiBzbmFwcGluZyBiYWNrIHRvIHRoZSBmaXJzdCBwYWdlIOKAlFxuICAgICAgICAvLyBkZWxldGluZyBwYWdlIDQgb2YgNiBzaG91bGQgbGVhdmUgeW91IGxvb2tpbmcgYXQgd2hhdCBpcyBub3cgcGFnZSA0LlxuICAgICAgICB0aGlzLmFjdGl2ZVBhZ2VJbmRleC5zZXQoTWF0aC5taW4oaW5kZXgsIHBhZ2VzLmxlbmd0aCAtIDEpKTtcbiAgICAgICAgdGhpcy5fcHJldmlvdXNQYWdlQ291bnQgPSBwYWdlcy5sZW5ndGg7XG4gICAgICAgIHRoaXMuc2VsZWN0ZWRDb21wb25lbnRJZC5zZXQobnVsbCk7XG5cbiAgICAgICAgLy8gVGhlIGlkIGluIHRoZSBVUkwganVzdCBzdG9wcGVkIGV4aXN0aW5nIOKAlCByZXBsYWNlIGl0IHdpdGggdGhlXG4gICAgICAgIC8vIG5laWdoYm91ciB3ZSBsYW5kZWQgb24sIG9yIGEgcmVmcmVzaCB3b3VsZCA0MDQgaXRzIHdheSB0byBwYWdlIG9uZS5cbiAgICAgICAgdGhpcy5wYWdlQ2hhbmdlZC5lbWl0KHRoaXMuYWN0aXZlUGFnZT8uaWQgPz8gbnVsbCk7XG5cbiAgICAgICAgdGhpcy5fbWVzc2FnZS5zdWNjZXNzKCdEZWxldGVkIHBhZ2UnKTtcbiAgICAgIH0pO1xuICB9XG5cbiAgLy8gQSB0YWIgd2FzIGRyYWdnZWQgdG8gYSBuZXcgc2xvdDogcmVvcmRlciBsb2NhbGx5IHNvIHRoZSBjaGlwcyBzZXR0bGVcbiAgLy8gaW1tZWRpYXRlbHksIGtlZXAgdGhlIHZpZXdlciBvbiB0aGUgcGFnZSB0aGV5IHdlcmUgbG9va2luZyBhdCwgYW5kIHBlcnNpc3RcbiAgLy8gdGhlIHdob2xlIHNlcXVlbmNlIGluIG9uZSBQVVQuXG4gIHB1YmxpYyBvblBhZ2VEcm9wcGVkKGV2ZW50OiBDZGtEcmFnRHJvcDx1bmtub3duPik6IHZvaWQge1xuICAgIGlmIChldmVudC5wcmV2aW91c0luZGV4ID09PSBldmVudC5jdXJyZW50SW5kZXgpIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICBjb25zdCBhY3RpdmVQYWdlID0gdGhpcy5hY3RpdmVQYWdlO1xuICAgIGNvbnN0IHBhZ2VzID0gdGhpcy5wYWdlcygpO1xuXG4gICAgbW92ZUl0ZW1JbkFycmF5KHBhZ2VzLCBldmVudC5wcmV2aW91c0luZGV4LCBldmVudC5jdXJyZW50SW5kZXgpO1xuICAgIHRoaXMucGFnZXMuc2V0KHBhZ2VzKTtcblxuICAgIGNvbnN0IHBvc2l0aW9ucyA9IHBhZ2VzLm1hcCgocGFnZSwgb3JkZXIpID0+IHtcbiAgICAgIHBhZ2Uub3JkZXIgPSBvcmRlcjtcblxuICAgICAgcmV0dXJuIHsgcGFnZUlkOiBwYWdlLmlkLCBvcmRlciB9O1xuICAgIH0pO1xuXG4gICAgaWYgKGFjdGl2ZVBhZ2UpIHtcbiAgICAgIHRoaXMuYWN0aXZlUGFnZUluZGV4LnNldChwYWdlcy5pbmRleE9mKGFjdGl2ZVBhZ2UpKTtcbiAgICB9XG5cbiAgICB0aGlzLl9yZXBvcnREYXRhLnNhdmVQYWdlUG9zaXRpb25zKHRoaXMucmVwb3J0LmlkLCBwb3NpdGlvbnMpXG4gICAgICAucGlwZSh0YWtlVW50aWxEZXN0cm95ZWQodGhpcy5fZGVzdHJveVJlZikpXG4gICAgICAuc3Vic2NyaWJlKCk7XG4gIH1cblxuICAvLyBIYW5kIHByZXNlbnRhdGlvbiBzZXR0aW5ncyAodGl0bGUsIHBhZGRpbmcpIHNhdmVkIGluIHRoZSBzZXR0aW5ncyBkaWFsb2cgdG9cbiAgLy8gdGhlIG9uZSBjb21wb25lbnQgdGhleSBiZWxvbmcgdG8uIE5vdGhpbmcgaGVyZSBmZWVkcyB0aGUgcXVlcnksIHNvIHRoYXRcbiAgLy8gY29tcG9uZW50IHJlcGFpbnRzIGFuZCBldmVyeSBvdGhlciBvbmUgb24gdGhlIHBhZ2UgaXMgbGVmdCBhbG9uZS4gQSB2YWx1ZVxuICAvLyBpcyBuZXZlciBkcmF3bjogaXRzIHRpdGxlIGlzIGl0cyBOYW1lLCB3aGljaCBpdHMgY2hpcHMgYW5kIHRva2VucyByZWFkLlxuICBwdWJsaWMgYXBwbHlDb21wb25lbnRTZXR0aW5ncyhjb21wb25lbnRJZDogbnVtYmVyLCBzZXR0aW5nczogQ29tcG9uZW50U2V0dGluZ3MpOiB2b2lkIHtcbiAgICBjb25zdCByZW5kZXJlZCA9IHRoaXMuX3JlbmRlcmVkQ29tcG9uZW50c1xuICAgICAgLmZpbmQoKGNhbmRpZGF0ZSkgPT4gY2FuZGlkYXRlLmNvbXBvbmVudC5pZCA9PT0gY29tcG9uZW50SWQpO1xuXG4gICAgaWYgKHJlbmRlcmVkKSB7XG4gICAgICByZW5kZXJlZC5hcHBseVNldHRpbmdzKHNldHRpbmdzKTtcblxuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIGNvbnN0IHZhbHVlID0gWy4uLnRoaXMuX3BhZ2VWYWx1ZUNvbXBvbmVudHMoKSwgLi4udGhpcy5fbWFzdGVyVmFsdWVDb21wb25lbnRzKCldXG4gICAgICAuZmluZCgoY2FuZGlkYXRlKSA9PiBjYW5kaWRhdGUuaWQgPT09IGNvbXBvbmVudElkKTtcblxuICAgIC8vIFRoZSBzZXJ2ZXIga2VlcHMgdGhlIG9sZCBOYW1lIGZvciBhIGJsYW5rIG9uZS5cbiAgICBpZiAodmFsdWUgJiYgc2V0dGluZ3MudGl0bGU/LnRyaW0oKSkge1xuICAgICAgdmFsdWUudGl0bGUgPSBzZXR0aW5ncy50aXRsZS50cmltKCk7XG4gICAgICB0aGlzLl92YWx1ZXNSZXZpc2lvbi51cGRhdGUoKHJldmlzaW9uKSA9PiByZXZpc2lvbiArIDEpO1xuICAgIH1cbiAgfVxuXG4gIHB1YmxpYyBzZWxlY3RDb21wb25lbnQoY29tcG9uZW50SWQ6IG51bWJlciB8IG51bGwpOiB2b2lkIHtcbiAgICB0aGlzLnNlbGVjdGVkQ29tcG9uZW50SWQuc2V0KGNvbXBvbmVudElkKTtcbiAgfVxuXG4gIHB1YmxpYyBvbkNhbnZhc1BvaW50ZXJEb3duKCk6IHZvaWQge1xuICAgIC8vIEJhY2tncm91bmQgY2xpY2sgKHBhbiBzdGFydCkgZGVzZWxlY3RzLlxuICAgIGlmICh0aGlzLnNlbGVjdGVkQ29tcG9uZW50SWQoKSAhPT0gbnVsbCkge1xuICAgICAgdGhpcy5zZWxlY3RDb21wb25lbnQobnVsbCk7XG4gICAgfVxuICB9XG5cbiAgLy8gLS0tLS0gem9vbSB0b29sYmFyIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLVxuXG4gIHB1YmxpYyBvblpvb21lZChzY2FsZTogbnVtYmVyKTogdm9pZCB7XG4gICAgdGhpcy56b29tLnNldChzY2FsZSk7XG4gIH1cblxuICBwdWJsaWMgem9vbUluKCk6IHZvaWQge1xuICAgIHRoaXMuem9vbVBhbj8uem9vbUluKCk7XG4gIH1cblxuICBwdWJsaWMgem9vbU91dCgpOiB2b2lkIHtcbiAgICB0aGlzLnpvb21QYW4/Lnpvb21PdXQoKTtcbiAgfVxuXG4gIHB1YmxpYyB6b29tRml0KCk6IHZvaWQge1xuICAgIGNvbnN0IHZpZXdwb3J0ID0gdGhpcy5fdmlld3BvcnQ/Lm5hdGl2ZUVsZW1lbnQ7XG4gICAgaWYgKCF2aWV3cG9ydCB8fCAhdGhpcy5yZXBvcnQ/LnBhZ2VXaWR0aCB8fCAhdGhpcy56b29tUGFuKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgY29uc3QgZml0ID0gTWF0aC5taW4oXG4gICAgICAodmlld3BvcnQuY2xpZW50V2lkdGggLSAzMikgLyAodGhpcy5yZXBvcnQucGFnZVdpZHRoICogUFhfUEVSX0lOQ0gpLFxuICAgICAgKHZpZXdwb3J0LmNsaWVudEhlaWdodCAtIDMyKSAvICh0aGlzLnJlcG9ydC5wYWdlSGVpZ2h0ICogUFhfUEVSX0lOQ0gpLFxuICAgICk7XG5cbiAgICB0aGlzLnpvb21QYW4uem9vbShNYXRoLm1pbigxLjUsIE1hdGgubWF4KDAuMSwgZml0KSkpO1xuICAgIHRoaXMuem9vbVBhbi5tb3ZlKDE2LCAxNik7XG4gICAgdGhpcy5fZml0dGVkID0gdHJ1ZTtcbiAgfVxuXG4gIHB1YmxpYyB6b29tQWN0dWFsKCk6IHZvaWQge1xuICAgIHRoaXMuem9vbVBhbj8uem9vbSgxKTtcbiAgfVxuXG4gIC8vIC0tLS0tIHBlcnNpc3RlbmNlIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cblxuICAvLyBBIGRyYWcvcmVzaXplIGxhbmRlZCDigJQgb25lIFBVVCBwZXIgZ2VzdHVyZS5cbiAgcHVibGljIG9uUG9zaXRpb25DaGFuZ2VkKHBvc2l0aW9uOiB7IGNvbXBvbmVudElkOiBudW1iZXIgfSAmIFJlY29yZDxzdHJpbmcsIG51bWJlcj4pOiB2b2lkIHtcbiAgICB0aGlzLl9jbGVhckd1aWRlcygpO1xuICAgIHRoaXMuX3JlcG9ydERhdGEuc2F2ZVBvc2l0aW9ucyh0aGlzLnJlcG9ydC5pZCwgW3Bvc2l0aW9uIGFzIGFueV0pXG4gICAgICAucGlwZSh0YWtlVW50aWxEZXN0cm95ZWQodGhpcy5fZGVzdHJveVJlZikpXG4gICAgICAuc3Vic2NyaWJlKCk7XG4gIH1cblxuICAvLyAtLS0tLSB2YWx1ZXMgLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG5cbiAgLy8gRWFjaCBsYXllciByZWFkcyBpdHMgdmFsdWVzJyBudW1iZXJzIG9uIGl0cyBvd24gc3RyZWFtOiBhZ2FpbiB3aGVuIGFcbiAgLy8gcmVwb3J0IHJlbG9hZCBjaGFuZ2VzIHdoYXQgdGhleSBkZXBlbmQgb24gKG5nT25DaGFuZ2VzKSwgd2hlbiBhIHNhdmVkIHRleHRcbiAgLy8gc2hvd3MgYSB2YWx1ZSBpdCBoYXMgbm8gbnVtYmVyIGZvciwgd2hlbiBhIGZpbHRlciBhbnkgb2YgaXRzIHZhbHVlc1xuICAvLyBmb2xsb3dzIGNoYW5nZXMgKGFuIG9wZXJhbmQgbm8gdGV4dCBzaG93cyBtb3ZlcyB0aGUgZm9ybXVsYSB0aGF0IHJlYWRzXG4gIC8vIGl0KSwgYW5kIHdoZW4gaXQgY29tZXMgb24gc2NyZWVuIOKAlCB0aGUgYWN0aXZlIHBhZ2Ugd2hlbiBhbm90aGVyIHBhZ2UgZG9lcyxcbiAgLy8gdGhlIG1hc3RlciB3aGVuIGEgcGFnZSBzaG93cyBpdCBvciBpdCBpcyBlZGl0ZWQuXG4gIHByaXZhdGUgX2luaXQoKTogdm9pZCB7XG4gICAgdGhpcy5fd2F0Y2hWYWx1ZXModGhpcy5fcGFnZVZhbHVlcywgdG9PYnNlcnZhYmxlKHRoaXMuYWN0aXZlUGFnZUlkKSk7XG4gICAgdGhpcy5fd2F0Y2hWYWx1ZXModGhpcy5fbWFzdGVyVmFsdWVzLCB0b09ic2VydmFibGUodGhpcy5fbWFzdGVyTmVlZGVkKSk7XG4gIH1cblxuICBwcml2YXRlIF92YWx1ZUxheWVyKHNvdXJjZTogKCkgPT4gUmVwb3J0UGFnZSB8IFJlcG9ydE1hc3RlciB8IG51bGwpOiBWYWx1ZUxheWVyIHtcbiAgICByZXR1cm4ge1xuICAgICAgc291cmNlLFxuICAgICAgcmVsb2FkJDogbmV3IFN1YmplY3Q8dm9pZD4oKSxcbiAgICAgIHJlc3VsdHM6IHNpZ25hbDxMYXllclZhbHVlcyB8IG51bGw+KG51bGwpLFxuICAgICAgcGVuZGluZzogc2lnbmFsPExheWVyVmFsdWVzUmVxdWVzdCB8IG51bGw+KG51bGwpLFxuICAgIH07XG4gIH1cblxuICAvLyBUcmlnZ2VycyBsYW5kaW5nIHRvZ2V0aGVyIChhIHJlbG9hZCB0aGF0IGFsc28gY2hhbmdlcyB0aGUgcGFnZSkgbWFrZSBvbmVcbiAgLy8gcmVxdWVzdCwgYW5kIGEgbmV3ZXIgcmVxdWVzdCBkcm9wcyB0aGUgb25lIHN0aWxsIGluIGZsaWdodC5cbiAgcHJpdmF0ZSBfd2F0Y2hWYWx1ZXMobGF5ZXI6IFZhbHVlTGF5ZXIsIG9uU2NyZWVuJDogT2JzZXJ2YWJsZTx1bmtub3duPik6IHZvaWQge1xuICAgIG1lcmdlKFxuICAgICAgbGF5ZXIucmVsb2FkJCxcbiAgICAgIG9uU2NyZWVuJCxcbiAgICAgIHRoaXMuX2ZpbHRlclN0YXRlLmNoYW5nZXNGb3JBbnkoKCkgPT4gbGF5ZXIuc291cmNlKCk/LnZhbHVlcyA/PyBbXSkucGlwZShkZWJvdW5jZVRpbWUoMzAwKSksXG4gICAgKVxuICAgICAgLnBpcGUoXG4gICAgICAgIGRlYm91bmNlVGltZSgwKSxcbiAgICAgICAgbWFwKCgpID0+IHRoaXMuX2xheWVyUmVxdWVzdChsYXllci5zb3VyY2UoKSkpLFxuICAgICAgICB0YXAoKHJlcXVlc3QpID0+IGxheWVyLnBlbmRpbmcuc2V0KHJlcXVlc3QpKSxcbiAgICAgICAgc3dpdGNoTWFwKChyZXF1ZXN0KSA9PiB0aGlzLl9sb2FkVmFsdWVzKHJlcXVlc3QpKSxcbiAgICAgICAgdGFwKChsb2FkZWQpID0+IHtcbiAgICAgICAgICBsYXllci5yZXN1bHRzLnNldChsb2FkZWQpO1xuICAgICAgICAgIGxheWVyLnBlbmRpbmcuc2V0KG51bGwpO1xuICAgICAgICB9KSxcbiAgICAgICAgdGFrZVVudGlsRGVzdHJveWVkKHRoaXMuX2Rlc3Ryb3lSZWYpLFxuICAgICAgKVxuICAgICAgLnN1YnNjcmliZSgpO1xuICB9XG5cbiAgLy8gQSByZWxvYWQgb2YgdGhlIHJlcG9ydCByZWFkcyBhIGxheWVyJ3MgbnVtYmVycyBhZ2FpbiBvbmx5IHdoZW4gc29tZXRoaW5nXG4gIC8vIHRoZXkgZGVwZW5kIG9uIG1vdmVkOiBhIHJlbmFtZSwgb3IgYW4gZWRpdCB0byBhIHRpbGUsIGhhbmRzIG92ZXIgYSBuZXdcbiAgLy8gcmVwb3J0IGFuZCBsZWF2ZXMgZXZlcnkgbnVtYmVyIGFzIGl0IHdhcy4gQ29tcGFyZWQgd2l0aCB0aGUgcmVxdWVzdCBvbiBpdHNcbiAgLy8gd2F5LCBlbHNlIHRoZSBvbmUgd2hvc2UgbnVtYmVycyBhcmUgb24gc2NyZWVuLlxuICBwcml2YXRlIF9yZWxvYWRJZkNoYW5nZWQobGF5ZXI6IFZhbHVlTGF5ZXIpOiB2b2lkIHtcbiAgICBjb25zdCBsYXN0ID0gbGF5ZXIucGVuZGluZygpID8/IGxheWVyLnJlc3VsdHMoKTtcblxuICAgIGlmICh0aGlzLl9sYXllclJlcXVlc3QobGF5ZXIuc291cmNlKCkpLnNpZ25hdHVyZSAhPT0gbGFzdD8uc2lnbmF0dXJlKSB7XG4gICAgICBsYXllci5yZWxvYWQkLm5leHQoKTtcbiAgICB9XG4gIH1cblxuICAvLyBSZWFkIHdoZW4gdGhlIHJlcXVlc3QgaXMgc2VudCwgbm90IHdoZW4gaXQgd2FzIGFza2VkIGZvcjogYW4gZWRpdCBtYXkgaGF2ZVxuICAvLyBqdXN0IGNoYW5nZWQgd2hpY2ggdmFsdWVzIHRoZSBsYXllcidzIHRleHQgc2hvd3MuIFRoZSBmaWx0ZXIgdmFsdWVzIG9mXG4gIC8vIGV2ZXJ5IHZhbHVlIG9uIHRoZSBsYXllciBnbyBvdXQsIHNob3duIG9yIG5vdDogdGhlIHNlcnZlciBkZWNpZGVzIHdoaWNoXG4gIC8vIHZhbHVlcyBpdCByZWFkcywgYW5kIGFwcGxpZXMgdG8gZWFjaCBvbmx5IHRoZSBlbnRyaWVzIG5hbWluZyBpdHMgb3duXG4gIC8vIGZpbHRlcnMsIHNvIGFuIG9wZXJhbmQgb25seSBhIGZvcm11bGEgcmVhZHMgaXMgZmlsdGVyZWQgYXMgaWYgaXQgd2VyZVxuICAvLyBzaG93bi4gQSB2YWx1ZSdzIE5hbWUgaXMgbGVmdCBvdXQgb2YgdGhlIHNpZ25hdHVyZTogYSByZW5hbWUgbW92ZXMgbm9cbiAgLy8gbnVtYmVyLlxuICBwcml2YXRlIF9sYXllclJlcXVlc3QobGF5ZXI6IFJlcG9ydFBhZ2UgfCBSZXBvcnRNYXN0ZXIgfCBudWxsKTogTGF5ZXJWYWx1ZXNSZXF1ZXN0IHtcbiAgICBjb25zdCBwYWdlSWQgPSBsYXllcj8uaWQgPz8gbnVsbDtcbiAgICBjb25zdCB2YWx1ZXMgPSBsYXllcj8udmFsdWVzID8/IFtdO1xuICAgIGNvbnN0IHNob3duID0gdGhpcy5fc2hvd25WYWx1ZXMobGF5ZXIpO1xuICAgIGNvbnN0IGZpbHRlcnMgPSB2YWx1ZXMuZmxhdE1hcCgoY29tcG9uZW50KSA9PiB0aGlzLl9maWx0ZXJTdGF0ZS5yZXNvbHZlRm9yQ29tcG9uZW50KGNvbXBvbmVudCkpO1xuXG4gICAgcmV0dXJuIHtcbiAgICAgIHBhZ2VJZCxcbiAgICAgIHNob3duLFxuICAgICAgZmlsdGVycyxcbiAgICAgIHNpZ25hdHVyZTogSlNPTi5zdHJpbmdpZnkoW1xuICAgICAgICBwYWdlSWQsXG4gICAgICAgIHNob3duLm1hcCgodmFsdWUpID0+IHZhbHVlLmlkKSxcbiAgICAgICAgdmFsdWVzLm1hcCgodmFsdWUpID0+ICh7IC4uLnZhbHVlLCB0aXRsZTogbnVsbCB9KSksXG4gICAgICAgIGZpbHRlcnMsXG4gICAgICBdKSxcbiAgICB9O1xuICB9XG5cbiAgLy8gVGhlIHZhbHVlcyBhIGxheWVyJ3MgdGV4dCBzaG93cy4gSXRzIHJlcXVlc3QgYWxzbyByZWFkcyB0aGUgb3BlcmFuZHMgb2ZcbiAgLy8gdGhlIGZvcm11bGFzIGFtb25nIHRoZW0sIGJ1dCBvbmx5IHRoZSBzaG93biBvbmVzIHJlYWQgYXMgbG9hZGluZyB3aGlsZSBpdFxuICAvLyBpcyBvbiBpdHMgd2F5LCBhbmQgYSBsYXllciB0aGF0IHNob3dzIG5vbmUgYXNrcyBmb3Igbm90aGluZy5cbiAgcHJpdmF0ZSBfc2hvd25WYWx1ZXMobGF5ZXI6IFJlcG9ydFBhZ2UgfCBSZXBvcnRNYXN0ZXIgfCBudWxsKTogUmVwb3J0Q29tcG9uZW50W10ge1xuICAgIGNvbnN0IHRleHRzID0gKGxheWVyPy5jb21wb25lbnRzID8/IFtdKS5maWx0ZXIoKGNvbXBvbmVudCkgPT4gY29tcG9uZW50LnR5cGUgPT09ICd0ZXh0Jyk7XG5cbiAgICByZXR1cm4gc2hvd25WYWx1ZXMobGF5ZXI/LnZhbHVlcyA/PyBbXSwgdGV4dHMpO1xuICB9XG5cbiAgLy8gT25lIGxheWVyJ3MgbnVtYmVycywgYnkgdmFsdWUgaWQuIEEgbGF5ZXIgd2hvc2UgdGV4dCBzaG93cyBubyB2YWx1ZSBhc2tzXG4gIC8vIGZvciBub3RoaW5nLiBBIGZhaWxlZCByZXF1ZXN0IHJlYWRzIGFzIG5vIG51bWJlcnMgKGVhY2ggdmFsdWUgYW4gZW0gZGFzaClcbiAgLy8gcmF0aGVyIHRoYW4gYW4gZXJyb3IgZGlhbG9nOiB0aGUgd29yZHMgYXJvdW5kIHRoZW0gc3RpbGwgcmVhZC5cbiAgcHJpdmF0ZSBfbG9hZFZhbHVlcyh7IHBhZ2VJZCwgc2hvd24sIGZpbHRlcnMsIHNpZ25hdHVyZSB9OiBMYXllclZhbHVlc1JlcXVlc3QpOiBPYnNlcnZhYmxlPExheWVyVmFsdWVzPiB7XG4gICAgY29uc3QgbG9hZGVkID0gKHJvd3M6IFJlcG9ydFBhZ2VWYWx1ZVtdKTogTGF5ZXJWYWx1ZXMgPT4gKHtcbiAgICAgIHBhZ2VJZCxcbiAgICAgIHNpZ25hdHVyZSxcbiAgICAgIHJvd3M6IG5ldyBNYXAocm93cy5tYXAoKHJvdykgPT4gW3Jvdy5pZCwgcm93XSkpLFxuICAgIH0pO1xuXG4gICAgaWYgKHBhZ2VJZCA9PT0gbnVsbCB8fCAhc2hvd24ubGVuZ3RoKSB7XG4gICAgICByZXR1cm4gb2YobG9hZGVkKFtdKSk7XG4gICAgfVxuXG4gICAgcmV0dXJuIHRoaXMuX3JlcG9ydERhdGEucGFnZVZhbHVlcyh0aGlzLnJlcG9ydC5pZCwgcGFnZUlkLCBmaWx0ZXJzLCBmYWxzZSwgeyBoYW5kbGVyczogZmFsc2UgfSlcbiAgICAgIC5waXBlKFxuICAgICAgICBtYXAoKHJvd3MpID0+IGxvYWRlZChyb3dzID8/IFtdKSksXG4gICAgICAgIGNhdGNoRXJyb3IoKCkgPT4gb2YobG9hZGVkKFtdKSkpLFxuICAgICAgKTtcbiAgfVxuXG4gIC8vIFRoZSB0b2tlbnMgb2Ygb25lIGxheWVyJ3MgYmxvY2tzLiBOdW1iZXJzIHJlYWQgZm9yIGFub3RoZXIgcGFnZSBhcmUgbm90XG4gIC8vIHRoaXMgb25lJ3MsIHNvIHVudGlsIGl0cyBvd24gYXJyaXZlIGl0cyB2YWx1ZXMgcmVhZCBhcyBsb2FkaW5nOyBzbyBkb2VzIGFcbiAgLy8gdmFsdWUgdGhlIHJlcXVlc3Qgb24gaXRzIHdheSBhc2tzIGZvciwgdW50aWwgaXQgbGFuZHMuXG4gIHByaXZhdGUgX3Rva2VuQ29udGV4dChcbiAgICB2YWx1ZXM6IFJlcG9ydENvbXBvbmVudFtdLFxuICAgIGxheWVyOiBWYWx1ZUxheWVyLFxuICAgIHZhbHVlUGFnZUlkOiBudW1iZXIgfCBudWxsLFxuICApOiBUZXh0VG9rZW5Db250ZXh0IHtcbiAgICAvLyBSZWFkIHNvIGEgcmVuYW1lLCBwYXRjaGVkIGludG8gdGhlIHZhbHVlIGluIHBsYWNlLCByZWNvbXB1dGVzIHRoZSBuYW1lcy5cbiAgICB0aGlzLl92YWx1ZXNSZXZpc2lvbigpO1xuXG4gICAgY29uc3QgaW5kZXggPSB0aGlzLmFjdGl2ZVBhZ2VJbmRleCgpO1xuICAgIGNvbnN0IHBhZ2UgPSB0aGlzLnBhZ2VzKClbaW5kZXhdO1xuICAgIGNvbnN0IHJlc3VsdHMgPSBsYXllci5yZXN1bHRzKCk7XG4gICAgY29uc3QgcGVuZGluZyA9IGxheWVyLnBlbmRpbmcoKTtcblxuICAgIHJldHVybiB7XG4gICAgICBwYWdlTnVtYmVyOiBpbmRleCArIDEsXG4gICAgICBwYWdlTmFtZTogcGFnZSA/IHRoaXMucGFnZUxhYmVsKHBhZ2UsIGluZGV4KSA6ICcnLFxuICAgICAgcmVwb3J0TmFtZTogdGhpcy5fcmVwb3J0KCk/Lm5hbWUgPz8gJycsXG4gICAgICB2YWx1ZXM6IHRleHRWYWx1ZXMoXG4gICAgICAgIHZhbHVlcyxcbiAgICAgICAgcmVzdWx0cz8ucGFnZUlkID09PSB2YWx1ZVBhZ2VJZCA/IHJlc3VsdHMgOiBudWxsLFxuICAgICAgICB0aGlzLl9maWx0ZXJTdGF0ZS5mb3JtYXRDb250ZXh0KCksXG4gICAgICAgIG5ldyBTZXQocGVuZGluZz8ucGFnZUlkID09PSB2YWx1ZVBhZ2VJZCA/IHBlbmRpbmcuc2hvd24ubWFwKCh2YWx1ZSkgPT4gdmFsdWUuaWQpIDogW10pLFxuICAgICAgKSxcbiAgICAgIHZhbHVlUGFnZUlkLFxuICAgIH07XG4gIH1cblxuICAvLyBUYWtlIGEgZGVsZXRlZCB2YWx1ZSdzIGNoaXBzIG91dCBvZiBhbiBvcGVuIGVkaXRvci4gU2F2aW5nIGh0bWwgbmV2ZXJcbiAgLy8gZGVsZXRlcyBhIHZhbHVlLCBzbyBhIGtleSBsZWF2ZXMgaXRzIGxheWVyIG9ubHkgd2hlbiB0aGUgdmFsdWUgaXMgZGVsZXRlZFxuICAvLyAoaXRzIGRpYWxvZywgdGhlIGFzc2lzdGFudCksIHdoZW4gYSB0ZXh0IGRlbGV0ZSBvciBhbiBhc3Npc3RhbnQgd3JpdGVcbiAgLy8gc3dlZXBzIHRoZSBwYWdlJ3MgdW51c2VkIHZhbHVlcywgb3Igd2l0aCBpdHMgcGFnZS4gSG9zdHMgcmVsb2FkIHRoZSByZXBvcnRcbiAgLy8gYWZ0ZXIgZWFjaCwgYW5kIHRoaXMgaXMgd2hhdCBmb2xsb3dzIHRoYXQgcmVsb2FkIGludG8gdGhlIGVkaXRvci4gT25seSB0aGVcbiAgLy8gbGF5ZXJzIG9uIHNjcmVlbiBoYXZlIHJlbmRlcmVkIGJsb2Nrczsgb3RoZXIgcGFnZXMgYXJlIGxlZnQgYWxvbmUuXG4gIHByaXZhdGUgX2Ryb3BSZW1vdmVkVmFsdWVDaGlwcygpOiB2b2lkIHtcbiAgICBjb25zdCBuZXh0ID0gbGF5ZXJWYWx1ZUtleXModGhpcy5yZXBvcnQpO1xuICAgIGNvbnN0IG1hc3RlcklkID0gdGhpcy5yZXBvcnQ/Lm1hc3Rlcj8uaWQgPz8gbnVsbDtcbiAgICBjb25zdCB0ZXh0cyA9ICh0aGlzLl9yZW5kZXJlZENvbXBvbmVudHM/LnRvQXJyYXkoKSA/PyBbXSkuZmlsdGVyKChyZW5kZXJlZCkgPT4gcmVuZGVyZWQuaXNUZXh0KTtcblxuICAgIHRoaXMuX3ZhbHVlS2V5c0J5TGF5ZXIuZm9yRWFjaCgoa2V5cywgbGF5ZXJJZCkgPT4ge1xuICAgICAgY29uc3QgaXNNYXN0ZXIgPSBsYXllcklkID09PSBtYXN0ZXJJZDtcbiAgICAgIGlmICghaXNNYXN0ZXIgJiYgbGF5ZXJJZCAhPT0gdGhpcy5hY3RpdmVQYWdlSWQoKSkge1xuICAgICAgICByZXR1cm47XG4gICAgICB9XG5cbiAgICAgIGNvbnN0IHJlbW92ZWQgPSBbLi4ua2V5c10uZmlsdGVyKChrZXkpID0+ICFuZXh0LmdldChsYXllcklkKT8uaGFzKGtleSkpO1xuICAgICAgdGV4dHNcbiAgICAgICAgLmZpbHRlcigocmVuZGVyZWQpID0+IHRoaXMuX2lzTWFzdGVyQ29tcG9uZW50KHJlbmRlcmVkLmNvbXBvbmVudCkgPT09IGlzTWFzdGVyKVxuICAgICAgICAuZm9yRWFjaCgocmVuZGVyZWQpID0+IHJlbW92ZWQuZm9yRWFjaCgoa2V5KSA9PiByZW5kZXJlZC5yZW1vdmVWYWx1ZShrZXkpKSk7XG4gICAgfSk7XG5cbiAgICB0aGlzLl92YWx1ZUtleXNCeUxheWVyID0gbmV4dDtcbiAgfVxuXG4gIC8vIEhlYWRlciBhbmQgZm9vdGVyIGJsb2NrcyBhcmUgdGhlIG1hc3RlcidzOyBldmVyeSBvdGhlciBibG9jayBpcyB0aGUgcGFnZSdzLlxuICBwcml2YXRlIF9pc01hc3RlckNvbXBvbmVudChjb21wb25lbnQ6IFJlcG9ydENvbXBvbmVudCk6IGJvb2xlYW4ge1xuICAgIHJldHVybiAodGhpcy5yZXBvcnQ/Lm1hc3Rlcj8uY29tcG9uZW50cyA/PyBbXSkuc29tZSgoY2FuZGlkYXRlKSA9PiBjYW5kaWRhdGUuaWQgPT09IGNvbXBvbmVudC5pZCk7XG4gIH1cblxuICAvLyAtLS0tLSBzbWFydCBndWlkZXMgLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG5cbiAgLy8gUGl4ZWwgZmVlbCBvZiB0aGUgc25hcCwgY29udmVydGVkIHRvIGluY2hlcyBhdCB0aGUgY3VycmVudCB6b29tLlxuICBwcml2YXRlIGdldCBfc25hcFRocmVzaG9sZCgpOiBudW1iZXIge1xuICAgIHJldHVybiA4IC8gKFBYX1BFUl9JTkNIICogTWF0aC5tYXgoMC4xLCB0aGlzLnpvb20oKSkpO1xuICB9XG5cbiAgcHJpdmF0ZSBfc25hcE1vdmUoY29tcG9uZW50OiBSZXBvcnRDb21wb25lbnQsIHg6IG51bWJlciwgeTogbnVtYmVyKTogeyB4OiBudW1iZXI7IHk6IG51bWJlciB9IHtcbiAgICBjb25zdCB7IHZlcnRpY2FsLCBob3Jpem9udGFsIH0gPSB0aGlzLl9jYW5kaWRhdGVzKGNvbXBvbmVudCk7XG4gICAgY29uc3QgZ3VpZGVzOiBHdWlkZUxpbmVbXSA9IFtdO1xuXG4gICAgY29uc3Qgc25hcHBlZFggPSB0aGlzLl9zbmFwQXhpcyhcbiAgICAgIFtcbiAgICAgICAgeyBvZmZzZXQ6IDAsIHZhbHVlOiB4IH0sXG4gICAgICAgIHsgb2Zmc2V0OiBjb21wb25lbnQudyAvIDIsIHZhbHVlOiB4ICsgY29tcG9uZW50LncgLyAyIH0sXG4gICAgICAgIHsgb2Zmc2V0OiBjb21wb25lbnQudywgdmFsdWU6IHggKyBjb21wb25lbnQudyB9LFxuICAgICAgXSxcbiAgICAgIHZlcnRpY2FsLFxuICAgICk7XG4gICAgaWYgKHNuYXBwZWRYICE9PSBudWxsKSB7XG4gICAgICB4ID0gc25hcHBlZFguYmFzZTtcbiAgICAgIGd1aWRlcy5wdXNoKHsgb3JpZW50YXRpb246ICd2JywgcG9zaXRpb246IHNuYXBwZWRYLmd1aWRlIH0pO1xuICAgIH1cblxuICAgIGNvbnN0IHNuYXBwZWRZID0gdGhpcy5fc25hcEF4aXMoXG4gICAgICBbXG4gICAgICAgIHsgb2Zmc2V0OiAwLCB2YWx1ZTogeSB9LFxuICAgICAgICB7IG9mZnNldDogY29tcG9uZW50LmggLyAyLCB2YWx1ZTogeSArIGNvbXBvbmVudC5oIC8gMiB9LFxuICAgICAgICB7IG9mZnNldDogY29tcG9uZW50LmgsIHZhbHVlOiB5ICsgY29tcG9uZW50LmggfSxcbiAgICAgIF0sXG4gICAgICBob3Jpem9udGFsLFxuICAgICk7XG4gICAgaWYgKHNuYXBwZWRZICE9PSBudWxsKSB7XG4gICAgICB5ID0gc25hcHBlZFkuYmFzZTtcbiAgICAgIGd1aWRlcy5wdXNoKHsgb3JpZW50YXRpb246ICdoJywgcG9zaXRpb246IHNuYXBwZWRZLmd1aWRlIH0pO1xuICAgIH1cblxuICAgIHRoaXMuX3JlbmRlckd1aWRlcyhndWlkZXMpO1xuXG4gICAgcmV0dXJuIHsgeCwgeSB9O1xuICB9XG5cbiAgcHJpdmF0ZSBfc25hcFJlc2l6ZShcbiAgICBjb21wb25lbnQ6IFJlcG9ydENvbXBvbmVudCxcbiAgICBnZW9tZXRyeTogeyB4OiBudW1iZXI7IHk6IG51bWJlcjsgdzogbnVtYmVyOyBoOiBudW1iZXIgfSxcbiAgICBoYW5kbGU6IHN0cmluZyxcbiAgKTogeyB4OiBudW1iZXI7IHk6IG51bWJlcjsgdzogbnVtYmVyOyBoOiBudW1iZXIgfSB7XG4gICAgY29uc3QgeyB2ZXJ0aWNhbCwgaG9yaXpvbnRhbCB9ID0gdGhpcy5fY2FuZGlkYXRlcyhjb21wb25lbnQpO1xuICAgIGNvbnN0IGd1aWRlczogR3VpZGVMaW5lW10gPSBbXTtcbiAgICBjb25zdCByZXN1bHQgPSB7IC4uLmdlb21ldHJ5IH07XG5cbiAgICAvLyBPbmx5IHRoZSBlZGdlcyB0aGUgaGFuZGxlIG1vdmVzIHBhcnRpY2lwYXRlIGluIHNuYXBwaW5nLlxuICAgIGlmIChoYW5kbGUuaW5jbHVkZXMoJ2UnKSkge1xuICAgICAgY29uc3Qgc25hcHBlZCA9IHRoaXMuX25lYXJlc3QoZ2VvbWV0cnkueCArIGdlb21ldHJ5LncsIHZlcnRpY2FsKTtcbiAgICAgIGlmIChzbmFwcGVkICE9PSBudWxsKSB7XG4gICAgICAgIHJlc3VsdC53ID0gc25hcHBlZCAtIGdlb21ldHJ5Lng7XG4gICAgICAgIGd1aWRlcy5wdXNoKHsgb3JpZW50YXRpb246ICd2JywgcG9zaXRpb246IHNuYXBwZWQgfSk7XG4gICAgICB9XG4gICAgfVxuICAgIGlmIChoYW5kbGUuaW5jbHVkZXMoJ3cnKSkge1xuICAgICAgY29uc3Qgc25hcHBlZCA9IHRoaXMuX25lYXJlc3QoZ2VvbWV0cnkueCwgdmVydGljYWwpO1xuICAgICAgaWYgKHNuYXBwZWQgIT09IG51bGwpIHtcbiAgICAgICAgcmVzdWx0LncgPSBnZW9tZXRyeS54ICsgZ2VvbWV0cnkudyAtIHNuYXBwZWQ7XG4gICAgICAgIHJlc3VsdC54ID0gc25hcHBlZDtcbiAgICAgICAgZ3VpZGVzLnB1c2goeyBvcmllbnRhdGlvbjogJ3YnLCBwb3NpdGlvbjogc25hcHBlZCB9KTtcbiAgICAgIH1cbiAgICB9XG4gICAgaWYgKGhhbmRsZS5pbmNsdWRlcygncycpKSB7XG4gICAgICBjb25zdCBzbmFwcGVkID0gdGhpcy5fbmVhcmVzdChnZW9tZXRyeS55ICsgZ2VvbWV0cnkuaCwgaG9yaXpvbnRhbCk7XG4gICAgICBpZiAoc25hcHBlZCAhPT0gbnVsbCkge1xuICAgICAgICByZXN1bHQuaCA9IHNuYXBwZWQgLSBnZW9tZXRyeS55O1xuICAgICAgICBndWlkZXMucHVzaCh7IG9yaWVudGF0aW9uOiAnaCcsIHBvc2l0aW9uOiBzbmFwcGVkIH0pO1xuICAgICAgfVxuICAgIH1cbiAgICBpZiAoaGFuZGxlLmluY2x1ZGVzKCduJykpIHtcbiAgICAgIGNvbnN0IHNuYXBwZWQgPSB0aGlzLl9uZWFyZXN0KGdlb21ldHJ5LnksIGhvcml6b250YWwpO1xuICAgICAgaWYgKHNuYXBwZWQgIT09IG51bGwpIHtcbiAgICAgICAgcmVzdWx0LmggPSBnZW9tZXRyeS55ICsgZ2VvbWV0cnkuaCAtIHNuYXBwZWQ7XG4gICAgICAgIHJlc3VsdC55ID0gc25hcHBlZDtcbiAgICAgICAgZ3VpZGVzLnB1c2goeyBvcmllbnRhdGlvbjogJ2gnLCBwb3NpdGlvbjogc25hcHBlZCB9KTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICB0aGlzLl9yZW5kZXJHdWlkZXMoZ3VpZGVzKTtcblxuICAgIHJldHVybiByZXN1bHQ7XG4gIH1cblxuICAvLyBBbGlnbm1lbnQgY2FuZGlkYXRlczogdGhlIHBhZ2UncyBlZGdlcyArIGNlbnRlciwgdGhlIGhlYWRlci9mb290ZXIgYmFuZFxuICAvLyBsaW5lcywgYW5kIGV2ZXJ5IHNpYmxpbmcncyBlZGdlcyArIGNlbnRlcnMg4oCUIHNpYmxpbmdzIG9uIHRoZSBTQU1FIGxheWVyLFxuICAvLyBzaW5jZSBhIHBhZ2UgY29tcG9uZW50IGFsaWducyB3aXRoIHRoZSBwYWdlIGFuZCBhIGhlYWRlciBibG9jayB3aXRoIHRoZVxuICAvLyBoZWFkZXIuXG4gIHByaXZhdGUgX2NhbmRpZGF0ZXMobW92aW5nOiBSZXBvcnRDb21wb25lbnQpOiB7IHZlcnRpY2FsOiBudW1iZXJbXTsgaG9yaXpvbnRhbDogbnVtYmVyW10gfSB7XG4gICAgY29uc3QgdmVydGljYWwgPSBbMCwgdGhpcy5yZXBvcnQucGFnZVdpZHRoIC8gMiwgdGhpcy5yZXBvcnQucGFnZVdpZHRoXTtcbiAgICBjb25zdCBob3Jpem9udGFsID0gWzAsIHRoaXMucmVwb3J0LnBhZ2VIZWlnaHQgLyAyLCB0aGlzLnJlcG9ydC5wYWdlSGVpZ2h0XTtcblxuICAgIGNvbnN0IHsgaGVhZGVySGVpZ2h0LCBmb290ZXJIZWlnaHQgfSA9IHRoaXMuYmFuZHM7XG4gICAgaWYgKGhlYWRlckhlaWdodCkge1xuICAgICAgaG9yaXpvbnRhbC5wdXNoKGhlYWRlckhlaWdodCk7XG4gICAgfVxuICAgIGlmIChmb290ZXJIZWlnaHQpIHtcbiAgICAgIGhvcml6b250YWwucHVzaCh0aGlzLnJlcG9ydC5wYWdlSGVpZ2h0IC0gZm9vdGVySGVpZ2h0KTtcbiAgICB9XG5cbiAgICBjb25zdCBpc01hc3RlciA9IHRoaXMuX2lzTWFzdGVyQ29tcG9uZW50KG1vdmluZyk7XG4gICAgY29uc3Qgc2libGluZ3MgPSBpc01hc3RlciA/IHRoaXMubWFzdGVyQ29tcG9uZW50cygpIDogdGhpcy5hY3RpdmVQYWdlQ29tcG9uZW50cygpO1xuXG4gICAgZm9yIChjb25zdCBjb21wb25lbnQgb2Ygc2libGluZ3MpIHtcbiAgICAgIGlmIChjb21wb25lbnQuaWQgPT09IG1vdmluZy5pZCkge1xuICAgICAgICBjb250aW51ZTtcbiAgICAgIH1cblxuICAgICAgdmVydGljYWwucHVzaChjb21wb25lbnQueCwgY29tcG9uZW50LnggKyBjb21wb25lbnQudyAvIDIsIGNvbXBvbmVudC54ICsgY29tcG9uZW50LncpO1xuICAgICAgaG9yaXpvbnRhbC5wdXNoKGNvbXBvbmVudC55LCBjb21wb25lbnQueSArIGNvbXBvbmVudC5oIC8gMiwgY29tcG9uZW50LnkgKyBjb21wb25lbnQuaCk7XG4gICAgfVxuXG4gICAgcmV0dXJuIHsgdmVydGljYWwsIGhvcml6b250YWwgfTtcbiAgfVxuXG4gIC8vIFNuYXAgb25lIGF4aXM6IG9mIHRoZSBtb3ZpbmcgYm94J3MgdGhyZWUgbGluZXMgKGVkZ2UvY2VudGVyL2VkZ2UpLCBmaW5kXG4gIC8vIHRoZSBjbG9zZXN0IGNhbmRpZGF0ZSB3aXRoaW4gdGhyZXNob2xkIGFuZCByZXR1cm4gdGhlIGFkanVzdGVkIGJhc2VcbiAgLy8gY29vcmRpbmF0ZSBwbHVzIHRoZSBndWlkZSB0byBkcmF3LlxuICBwcml2YXRlIF9zbmFwQXhpcyhcbiAgICBsaW5lczogeyBvZmZzZXQ6IG51bWJlcjsgdmFsdWU6IG51bWJlciB9W10sXG4gICAgY2FuZGlkYXRlczogbnVtYmVyW10sXG4gICk6IHsgYmFzZTogbnVtYmVyOyBndWlkZTogbnVtYmVyIH0gfCBudWxsIHtcbiAgICBsZXQgYmVzdDogeyBiYXNlOiBudW1iZXI7IGd1aWRlOiBudW1iZXI7IGRpc3RhbmNlOiBudW1iZXIgfSB8IG51bGwgPSBudWxsO1xuXG4gICAgZm9yIChjb25zdCBsaW5lIG9mIGxpbmVzKSB7XG4gICAgICBmb3IgKGNvbnN0IGNhbmRpZGF0ZSBvZiBjYW5kaWRhdGVzKSB7XG4gICAgICAgIGNvbnN0IGRpc3RhbmNlID0gTWF0aC5hYnMoY2FuZGlkYXRlIC0gbGluZS52YWx1ZSk7XG4gICAgICAgIGlmIChkaXN0YW5jZSA8PSB0aGlzLl9zbmFwVGhyZXNob2xkICYmICghYmVzdCB8fCBkaXN0YW5jZSA8IGJlc3QuZGlzdGFuY2UpKSB7XG4gICAgICAgICAgYmVzdCA9IHsgYmFzZTogY2FuZGlkYXRlIC0gbGluZS5vZmZzZXQsIGd1aWRlOiBjYW5kaWRhdGUsIGRpc3RhbmNlIH07XG4gICAgICAgIH1cbiAgICAgIH1cbiAgICB9XG5cbiAgICByZXR1cm4gYmVzdCA/IHsgYmFzZTogYmVzdC5iYXNlLCBndWlkZTogYmVzdC5ndWlkZSB9IDogbnVsbDtcbiAgfVxuXG4gIHByaXZhdGUgX25lYXJlc3QodmFsdWU6IG51bWJlciwgY2FuZGlkYXRlczogbnVtYmVyW10pOiBudW1iZXIgfCBudWxsIHtcbiAgICBsZXQgYmVzdDogbnVtYmVyIHwgbnVsbCA9IG51bGw7XG4gICAgbGV0IGJlc3REaXN0YW5jZSA9IHRoaXMuX3NuYXBUaHJlc2hvbGQ7XG5cbiAgICBmb3IgKGNvbnN0IGNhbmRpZGF0ZSBvZiBjYW5kaWRhdGVzKSB7XG4gICAgICBjb25zdCBkaXN0YW5jZSA9IE1hdGguYWJzKGNhbmRpZGF0ZSAtIHZhbHVlKTtcbiAgICAgIGlmIChkaXN0YW5jZSA8PSBiZXN0RGlzdGFuY2UpIHtcbiAgICAgICAgYmVzdCA9IGNhbmRpZGF0ZTtcbiAgICAgICAgYmVzdERpc3RhbmNlID0gZGlzdGFuY2U7XG4gICAgICB9XG4gICAgfVxuXG4gICAgcmV0dXJuIGJlc3Q7XG4gIH1cblxuICAvLyBUaGUgZ3VpZGVzIG92ZXJsYXkgaXMgZHJhd24gaW1wZXJhdGl2ZWx5IOKAlCB0aGUgZHJhZyBsb29wIHJ1bnMgb3V0c2lkZVxuICAvLyBBbmd1bGFyIGFuZCByZXBhaW50cyBvbiBldmVyeSBwb2ludGVybW92ZS5cbiAgcHJpdmF0ZSBfcmVuZGVyR3VpZGVzKGd1aWRlczogR3VpZGVMaW5lW10pOiB2b2lkIHtcbiAgICBjb25zdCBob3N0ID0gdGhpcy5fZ3VpZGVzPy5uYXRpdmVFbGVtZW50O1xuICAgIGlmICghaG9zdCkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIGhvc3QucmVwbGFjZUNoaWxkcmVuKC4uLmd1aWRlcy5tYXAoKGd1aWRlKSA9PiB7XG4gICAgICBjb25zdCBsaW5lID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnZGl2Jyk7XG4gICAgICBsaW5lLmNsYXNzTmFtZSA9IGBndWlkZSBndWlkZS0ke2d1aWRlLm9yaWVudGF0aW9ufWA7XG4gICAgICBpZiAoZ3VpZGUub3JpZW50YXRpb24gPT09ICd2Jykge1xuICAgICAgICBsaW5lLnN0eWxlLmxlZnQgPSBgJHtndWlkZS5wb3NpdGlvbiAqIFBYX1BFUl9JTkNIfXB4YDtcbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIGxpbmUuc3R5bGUudG9wID0gYCR7Z3VpZGUucG9zaXRpb24gKiBQWF9QRVJfSU5DSH1weGA7XG4gICAgICB9XG5cbiAgICAgIHJldHVybiBsaW5lO1xuICAgIH0pKTtcbiAgfVxuXG4gIHByaXZhdGUgX2NsZWFyR3VpZGVzKCk6IHZvaWQge1xuICAgIHRoaXMuX2d1aWRlcz8ubmF0aXZlRWxlbWVudD8ucmVwbGFjZUNoaWxkcmVuKCk7XG4gIH1cbn1cbiIsIjxkaXYgY2xhc3M9XCJjYW52YXNcIj5cbiAgPGRpdlxuICAgICN2aWV3cG9ydFxuICAgIGNsYXNzPVwicGFnZS12aWV3cG9ydFwiXG4gICAgKHBvaW50ZXJkb3duKT1cIm9uQ2FudmFzUG9pbnRlckRvd24oKVwiPlxuICAgIDxmcy16b29tLXBhblxuICAgICAgd2hlZWw9XCJtb2RpZmllclwiXG4gICAgICBbem9vbU1pbl09XCIwLjFcIlxuICAgICAgW3pvb21NYXhdPVwiM1wiXG4gICAgICAoem9vbWVkKT1cIm9uWm9vbWVkKCRldmVudClcIj5cbiAgICAgIEBpZiAoYWN0aXZlUGFnZSkge1xuICAgICAgICA8ZGl2XG4gICAgICAgICAgY2xhc3M9XCJwYWdlXCJcbiAgICAgICAgICBbY2xhc3MuZWRpdGluZ109XCJlZGl0TW9kZVwiXG4gICAgICAgICAgW2NsYXNzLm1hc3Rlci1lZGl0aW5nXT1cImlzTWFzdGVyRWRpdGluZ1wiXG4gICAgICAgICAgW3N0eWxlLndpZHRoLnB4XT1cInJlcG9ydC5wYWdlV2lkdGggKiBQWFwiXG4gICAgICAgICAgW3N0eWxlLmhlaWdodC5weF09XCJyZXBvcnQucGFnZUhlaWdodCAqIFBYXCJcbiAgICAgICAgICBbc3R5bGUuLS1jYW52YXMtem9vbV09XCJ6b29tKClcIlxuICAgICAgICAgIFtzdHlsZS4tLXJlcG9ydC1oZWFkaW5nLXNpemUucHhdPVwiaGVhZGluZ1NpemVQeFwiPlxuICAgICAgICAgIDwhLS0gVGhlIGhlYWRlciBhbmQgZm9vdGVyOiB0aGUgbWFzdGVyJ3MgY29tcG9uZW50cywgZHJhd24gdW5kZXIgdGhlXG4gICAgICAgICAgICAgICBwYWdlJ3Mgb3duLiAtLT5cbiAgICAgICAgICBAaWYgKGlzTWFzdGVyU2hvd24gJiYgbWFzdGVyQ29tcG9uZW50cygpLmxlbmd0aCkge1xuICAgICAgICAgICAgPGRpdlxuICAgICAgICAgICAgICBjbGFzcz1cIm1hc3Rlci1sYXllclwiXG4gICAgICAgICAgICAgIFtjbGFzcy5lZGl0YWJsZV09XCJpc01hc3RlckVkaXRpbmdcIj5cbiAgICAgICAgICAgICAgQGZvciAoY29tcG9uZW50IG9mIG1hc3RlckNvbXBvbmVudHMoKTsgdHJhY2sgY29tcG9uZW50LmlkKSB7XG4gICAgICAgICAgICAgICAgPGFwcC1yZXBvcnQtY29tcG9uZW50XG4gICAgICAgICAgICAgICAgICBbcmVwb3J0SWRdPVwicmVwb3J0LmlkXCJcbiAgICAgICAgICAgICAgICAgIFtjb21wb25lbnRdPVwiY29tcG9uZW50XCJcbiAgICAgICAgICAgICAgICAgIFtncm91cHNdPVwiZ3JvdXBzXCJcbiAgICAgICAgICAgICAgICAgIFtlZGl0TW9kZV09XCJpc01hc3RlckVkaXRpbmdcIlxuICAgICAgICAgICAgICAgICAgW3pvb21dPVwiem9vbSgpXCJcbiAgICAgICAgICAgICAgICAgIFtzbmFwcGVyXT1cInNuYXBwZXJcIlxuICAgICAgICAgICAgICAgICAgW3Rva2Vuc109XCJtYXN0ZXJUb2tlbnMoKVwiXG4gICAgICAgICAgICAgICAgICBbdmFsdWVLZXlzRWxzZXdoZXJlXT1cInZhbHVlS2V5c0Vsc2V3aGVyZVwiXG4gICAgICAgICAgICAgICAgICBbc2VsZWN0ZWRdPVwiY29tcG9uZW50LmlkID09PSBzZWxlY3RlZENvbXBvbmVudElkKClcIlxuICAgICAgICAgICAgICAgICAgW3N0eWxlLmxlZnQucHhdPVwiY29tcG9uZW50LnggKiBQWFwiXG4gICAgICAgICAgICAgICAgICBbc3R5bGUudG9wLnB4XT1cImNvbXBvbmVudC55ICogUFhcIlxuICAgICAgICAgICAgICAgICAgW3N0eWxlLndpZHRoLnB4XT1cImNvbXBvbmVudC53ICogUFhcIlxuICAgICAgICAgICAgICAgICAgW3N0eWxlLmhlaWdodC5weF09XCJjb21wb25lbnQuYXV0b0hlaWdodCA/IG51bGwgOiBjb21wb25lbnQuaCAqIFBYXCJcbiAgICAgICAgICAgICAgICAgIChzZWxlY3RDb21wb25lbnQpPVwic2VsZWN0Q29tcG9uZW50KCRldmVudClcIlxuICAgICAgICAgICAgICAgICAgKHBvc2l0aW9uQ2hhbmdlZCk9XCJvblBvc2l0aW9uQ2hhbmdlZCgkZXZlbnQpXCJcbiAgICAgICAgICAgICAgICAgIChyZW1vdmVkKT1cIm9uQ29tcG9uZW50UmVtb3ZlZCgkZXZlbnQpXCJcbiAgICAgICAgICAgICAgICAgIChvcGVuU2V0dGluZ3MpPVwiY29tcG9uZW50U2V0dGluZ3MuZW1pdCgkZXZlbnQpXCJcbiAgICAgICAgICAgICAgICAgICh2YWx1ZVNldHRpbmdzKT1cIm9wZW5WYWx1ZVNldHRpbmdzKGNvbXBvbmVudCwgJGV2ZW50KVwiXG4gICAgICAgICAgICAgICAgICAodGV4dFNhdmVkKT1cIm9uVGV4dFNhdmVkKGNvbXBvbmVudCwgJGV2ZW50KVwiXG4gICAgICAgICAgICAgICAgICAodmFsdWVzUmVtb3ZlZCk9XCJyZXBvcnRDaGFuZ2VkLmVtaXQoKVwiPlxuICAgICAgICAgICAgICAgIDwvYXBwLXJlcG9ydC1jb21wb25lbnQ+XG4gICAgICAgICAgICAgIH1cbiAgICAgICAgICAgIDwvZGl2PlxuICAgICAgICAgIH1cblxuICAgICAgICAgIDwhLS0gVGhlIGhlYWRlciBhbmQgZm9vdGVyIGJhbmRzLCBhcyBndWlkZXMgd2hpbGUgZWRpdGluZy4gLS0+XG4gICAgICAgICAgQGlmIChlZGl0TW9kZSkge1xuICAgICAgICAgICAgQGlmIChiYW5kcy5oZWFkZXJIZWlnaHQpIHtcbiAgICAgICAgICAgICAgPGRpdlxuICAgICAgICAgICAgICAgIGNsYXNzPVwiYmFuZCBiYW5kLWhlYWRlclwiXG4gICAgICAgICAgICAgICAgW3N0eWxlLmhlaWdodC5weF09XCJiYW5kcy5oZWFkZXJIZWlnaHQgKiBQWFwiPlxuICAgICAgICAgICAgICAgIEBpZiAoaXNNYXN0ZXJFZGl0aW5nKSB7XG4gICAgICAgICAgICAgICAgICA8c3BhbiBjbGFzcz1cImJhbmQtbGFiZWwgc21hbGxcIj5IZWFkZXI8L3NwYW4+XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICA8L2Rpdj5cbiAgICAgICAgICAgIH1cbiAgICAgICAgICAgIEBpZiAoYmFuZHMuZm9vdGVySGVpZ2h0KSB7XG4gICAgICAgICAgICAgIDxkaXZcbiAgICAgICAgICAgICAgICBjbGFzcz1cImJhbmQgYmFuZC1mb290ZXJcIlxuICAgICAgICAgICAgICAgIFtzdHlsZS5oZWlnaHQucHhdPVwiYmFuZHMuZm9vdGVySGVpZ2h0ICogUFhcIj5cbiAgICAgICAgICAgICAgICBAaWYgKGlzTWFzdGVyRWRpdGluZykge1xuICAgICAgICAgICAgICAgICAgPHNwYW4gY2xhc3M9XCJiYW5kLWxhYmVsIHNtYWxsXCI+Rm9vdGVyPC9zcGFuPlxuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgPC9kaXY+XG4gICAgICAgICAgICB9XG4gICAgICAgICAgfVxuXG4gICAgICAgICAgQGZvciAoY29tcG9uZW50IG9mIGFjdGl2ZVBhZ2VDb21wb25lbnRzKCk7IHRyYWNrIGNvbXBvbmVudC5pZCkge1xuICAgICAgICAgICAgPGFwcC1yZXBvcnQtY29tcG9uZW50XG4gICAgICAgICAgICAgIFtyZXBvcnRJZF09XCJyZXBvcnQuaWRcIlxuICAgICAgICAgICAgICBbY29tcG9uZW50XT1cImNvbXBvbmVudFwiXG4gICAgICAgICAgICAgIFtncm91cHNdPVwiZ3JvdXBzXCJcbiAgICAgICAgICAgICAgW2VkaXRNb2RlXT1cImlzUGFnZUVkaXRpbmdcIlxuICAgICAgICAgICAgICBbem9vbV09XCJ6b29tKClcIlxuICAgICAgICAgICAgICBbc25hcHBlcl09XCJzbmFwcGVyXCJcbiAgICAgICAgICAgICAgW3Rva2Vuc109XCJwYWdlVG9rZW5zKClcIlxuICAgICAgICAgICAgICBbdmFsdWVLZXlzRWxzZXdoZXJlXT1cInZhbHVlS2V5c0Vsc2V3aGVyZVwiXG4gICAgICAgICAgICAgIFtzZWxlY3RlZF09XCJjb21wb25lbnQuaWQgPT09IHNlbGVjdGVkQ29tcG9uZW50SWQoKVwiXG4gICAgICAgICAgICAgIFtzdHlsZS5sZWZ0LnB4XT1cImNvbXBvbmVudC54ICogUFhcIlxuICAgICAgICAgICAgICBbc3R5bGUudG9wLnB4XT1cImNvbXBvbmVudC55ICogUFhcIlxuICAgICAgICAgICAgICBbc3R5bGUud2lkdGgucHhdPVwiY29tcG9uZW50LncgKiBQWFwiXG4gICAgICAgICAgICAgIFtzdHlsZS5oZWlnaHQucHhdPVwiY29tcG9uZW50LmF1dG9IZWlnaHQgPyBudWxsIDogY29tcG9uZW50LmggKiBQWFwiXG4gICAgICAgICAgICAgIChzZWxlY3RDb21wb25lbnQpPVwic2VsZWN0Q29tcG9uZW50KCRldmVudClcIlxuICAgICAgICAgICAgICAocG9zaXRpb25DaGFuZ2VkKT1cIm9uUG9zaXRpb25DaGFuZ2VkKCRldmVudClcIlxuICAgICAgICAgICAgICAocmVtb3ZlZCk9XCJvbkNvbXBvbmVudFJlbW92ZWQoJGV2ZW50KVwiXG4gICAgICAgICAgICAgIChvcGVuU2V0dGluZ3MpPVwiY29tcG9uZW50U2V0dGluZ3MuZW1pdCgkZXZlbnQpXCJcbiAgICAgICAgICAgICAgKHZhbHVlU2V0dGluZ3MpPVwib3BlblZhbHVlU2V0dGluZ3MoY29tcG9uZW50LCAkZXZlbnQpXCJcbiAgICAgICAgICAgICAgKHRleHRTYXZlZCk9XCJvblRleHRTYXZlZChjb21wb25lbnQsICRldmVudClcIlxuICAgICAgICAgICAgICAodmFsdWVzUmVtb3ZlZCk9XCJyZXBvcnRDaGFuZ2VkLmVtaXQoKVwiPlxuICAgICAgICAgICAgPC9hcHAtcmVwb3J0LWNvbXBvbmVudD5cbiAgICAgICAgICB9XG5cbiAgICAgICAgICA8ZGl2XG4gICAgICAgICAgICAjZ3VpZGVzXG4gICAgICAgICAgICBjbGFzcz1cImd1aWRlc1wiPlxuICAgICAgICAgIDwvZGl2PlxuXG4gICAgICAgICAgQGlmICghYWN0aXZlUGFnZUNvbXBvbmVudHMoKS5sZW5ndGggJiYgIW1hc3Rlck1vZGUoKSkge1xuICAgICAgICAgICAgPGRpdiBjbGFzcz1cInBhZ2UtZW1wdHlcIj5cbiAgICAgICAgICAgICAgQXNrIHRoZSBhc3Npc3RhbnQgdG8gYWRkIGEgY2hhcnQsIGxpc3Qgb3IgS1BJIHRvIHRoaXMgcGFnZS5cbiAgICAgICAgICAgIDwvZGl2PlxuICAgICAgICAgIH1cbiAgICAgICAgPC9kaXY+XG4gICAgICB9XG4gICAgPC9mcy16b29tLXBhbj5cbiAgPC9kaXY+XG5cbiAgPGRpdiBjbGFzcz1cImNhbnZhcy10b29sYmFyXCI+XG4gICAgPCEtLSBUYWJzIGFyZSBvbmUgaG9yaXpvbnRhbCBkcm9wIGxpc3Q6IGRyYWdnaW5nIGEgY2hpcCByZW9yZGVycyB0aGUgcGFnZXMuXG4gICAgICAgICBUaGUgZHJvcCBJTkRFWCBpcyBjb21wdXRlZCBhbG9uZyBYIChvcmllbnRhdGlvbiksIGJ1dCB0aGUgcHJldmlldyBpc1xuICAgICAgICAgZGVsaWJlcmF0ZWx5IGxlZnQgdW5ib3VuZGVkIG9uIGJvdGggYXhlcyDigJQgcGlubmluZyBpdCB0byB0aGUgcm93IHdpdGhcbiAgICAgICAgIGNka0RyYWdCb3VuZGFyeSBtZWFucyB0aGUgY2hpcCB5b3UgYXJlIGRyYWdnaW5nIGNvdmVycyB0aGUgY2hpcHMgeW91XG4gICAgICAgICBhcmUgZHJhZ2dpbmcgaXQgcGFzdCwgYW5kIHlvdSBjYW5ub3Qgc2VlIHdoZXJlIGl0IGlzIGdvaW5nIHRvIGxhbmQuXG4gICAgICAgICBFdmVyeSBwYWdlIGdldHMgYSBjaGlwLCBpbmNsdWRpbmcgYSBsb25lIG9uZTogdGhlIGNoaXAgaXMgd2hhdCB0ZWxsc1xuICAgICAgICAgeW91IHdoaWNoIHBhZ2UgeW91IGFyZSBvbiwgYW5kIGEgcmVwb3J0IHRoYXQgaGlkIGl0IGxlZnQgeW91IHVuYWJsZSB0b1xuICAgICAgICAgdGVsbCBwYWdlIDEgb2YgMSBmcm9tIGEgcGFnZSB0aGF0IGZhaWxlZCB0byBsb2FkLiBEZWxldGluZyB0aGUgbGFzdFxuICAgICAgICAgcGFnZSBpcyByZWZ1c2VkIHNlcnZlci1zaWRlLCBzbyB0aGUga2ViYWIgaXMgc2FmZSB0byBleHBvc2UgaGVyZS4gLS0+XG4gICAgPGRpdlxuICAgICAgY2xhc3M9XCJwYWdlLXRhYnNcIlxuICAgICAgY2RrRHJvcExpc3RcbiAgICAgIGNka0Ryb3BMaXN0T3JpZW50YXRpb249XCJob3Jpem9udGFsXCJcbiAgICAgIChjZGtEcm9wTGlzdERyb3BwZWQpPVwib25QYWdlRHJvcHBlZCgkZXZlbnQpXCI+XG4gICAgICBAZm9yIChwYWdlIG9mIHBhZ2VzKCk7IHRyYWNrIHBhZ2UuaWQ7IGxldCBpbmRleCA9ICRpbmRleCkge1xuICAgICAgICA8IS0tIFRoZSBjaGlwIGlzIHRoZSBkcmFnIGhhbmRsZSBBTkQgdGhlIHRhYjogY2xpY2tpbmcgc2VsZWN0cyxcbiAgICAgICAgICAgICBkcmFnZ2luZyByZW9yZGVycy4gVGhlIGtlYmFiIGxpdmVzIGluc2lkZSBpdCwgc28gdGhlIHdob2xlXG4gICAgICAgICAgICAgY29udHJvbCBzdGF5cyBvbmUgY2hpcCBpbnN0ZWFkIG9mIGdyb3dpbmcgYSBzZWNvbmQgYnV0dG9uLiAtLT5cbiAgICAgICAgPGRpdlxuICAgICAgICAgIGNka0RyYWdcbiAgICAgICAgICBjbGFzcz1cInBhZ2UtdGFiXCJcbiAgICAgICAgICBbY2xhc3MuYWN0aXZlXT1cImluZGV4ID09PSBhY3RpdmVQYWdlSW5kZXgoKVwiXG4gICAgICAgICAgKGNsaWNrKT1cInNlbGVjdFBhZ2UoaW5kZXgpXCI+XG4gICAgICAgICAgPHNwYW4gY2xhc3M9XCJwYWdlLXRhYi1sYWJlbFwiPnt7IHBhZ2VMYWJlbChwYWdlLCBpbmRleCkgfX08L3NwYW4+XG4gICAgICAgICAgPCEtLSBUaGUga2ViYWIgb3BlbnMgdGhlIG1lbnUgcmF0aGVyIHRoYW4gc3RhcnRpbmcgYSBkcmFnIG9yXG4gICAgICAgICAgICAgICBzd2l0Y2hpbmcgcGFnZXMsIHNvIGl0IHN3YWxsb3dzIGl0cyBvd24gY2xpY2suIC0tPlxuICAgICAgICAgIDxzcGFuXG4gICAgICAgICAgICBjbGFzcz1cInBhZ2UtdGFiLW1lbnVcIlxuICAgICAgICAgICAgW2ZzTWVudVRyaWdnZXJGb3JdPVwicGFnZU1lbnVcIlxuICAgICAgICAgICAgKGNsaWNrKT1cIiRldmVudC5zdG9wUHJvcGFnYXRpb24oKVwiXG4gICAgICAgICAgICAobW91c2Vkb3duKT1cIiRldmVudC5zdG9wUHJvcGFnYXRpb24oKVwiPlxuICAgICAgICAgICAgPG1hdC1pY29uPm1vcmVfdmVydDwvbWF0LWljb24+XG4gICAgICAgICAgPC9zcGFuPlxuICAgICAgICA8L2Rpdj5cbiAgICAgICAgPCEtLSBPdXRzaWRlIHRoZSBjaGlwOiBjZGtEcmFnIGNsb25lcyBpdHMgaG9zdCBpbnRvIHRoZSBkcmFnIHByZXZpZXcsXG4gICAgICAgICAgICAgYW5kIGEgbWVudSBvdmVybGF5IGFuY2hvcmVkIHRvIGEgY2xvbmVkIHRyaWdnZXIgb3BlbnMgZGV0YWNoZWRcbiAgICAgICAgICAgICBmcm9tIHRoZSByZWFsIHRhYi4gLS0+XG4gICAgICAgIDxmcy1tZW51ICNwYWdlTWVudT5cbiAgICAgICAgICA8bmctdGVtcGxhdGVcbiAgICAgICAgICAgIGZzLW1lbnUtaXRlbVxuICAgICAgICAgICAgKGNsaWNrKT1cInJlbmFtZVBhZ2UocGFnZSlcIj5cbiAgICAgICAgICAgIEVkaXQgbmFtZVxuICAgICAgICAgIDwvbmctdGVtcGxhdGU+XG4gICAgICAgICAgPG5nLXRlbXBsYXRlXG4gICAgICAgICAgICBmcy1tZW51LWl0ZW1cbiAgICAgICAgICAgIChjbGljayk9XCJ0b2dnbGVNYXN0ZXJIaWRkZW4ocGFnZSlcIj5cbiAgICAgICAgICAgIHt7IHBhZ2UubWFzdGVySGlkZGVuID8gJ1Nob3cgaGVhZGVyICYgZm9vdGVyJyA6ICdIaWRlIGhlYWRlciAmIGZvb3RlcicgfX1cbiAgICAgICAgICA8L25nLXRlbXBsYXRlPlxuICAgICAgICAgIDxuZy10ZW1wbGF0ZVxuICAgICAgICAgICAgZnMtbWVudS1pdGVtXG4gICAgICAgICAgICAoY2xpY2spPVwiZGVsZXRlUGFnZShwYWdlKVwiPlxuICAgICAgICAgICAgRGVsZXRlXG4gICAgICAgICAgPC9uZy10ZW1wbGF0ZT5cbiAgICAgICAgPC9mcy1tZW51PlxuICAgICAgfVxuICAgICAgPGJ1dHRvblxuICAgICAgICB0eXBlPVwiYnV0dG9uXCJcbiAgICAgICAgY2xhc3M9XCJwYWdlLXRhYiBhZGQtcGFnZVwiXG4gICAgICAgIG1hdFRvb2x0aXA9XCJBZGQgcGFnZVwiXG4gICAgICAgIChjbGljayk9XCJhZGRQYWdlKClcIj5cbiAgICAgICAgPG1hdC1pY29uPmFkZDwvbWF0LWljb24+XG4gICAgICAgIFBhZ2VcbiAgICAgIDwvYnV0dG9uPlxuICAgIDwvZGl2PlxuXG4gICAgPGRpdiBjbGFzcz1cInpvb20tY29udHJvbHNcIj5cbiAgICAgIDxidXR0b25cbiAgICAgICAgdHlwZT1cImJ1dHRvblwiXG4gICAgICAgIGNsYXNzPVwiem9vbS1idXR0b25cIlxuICAgICAgICBtYXRUb29sdGlwPVwiWm9vbSBvdXQgKEN0cmwvQ21kICsgc2Nyb2xsKVwiXG4gICAgICAgIChjbGljayk9XCJ6b29tT3V0KClcIj5cbiAgICAgICAgPG1hdC1pY29uPnJlbW92ZTwvbWF0LWljb24+XG4gICAgICA8L2J1dHRvbj5cbiAgICAgIDxidXR0b25cbiAgICAgICAgdHlwZT1cImJ1dHRvblwiXG4gICAgICAgIGNsYXNzPVwiem9vbS1sYWJlbFwiXG4gICAgICAgIG1hdFRvb2x0aXA9XCJab29tIHRvIDEwMCVcIlxuICAgICAgICAoY2xpY2spPVwiem9vbUFjdHVhbCgpXCI+XG4gICAgICAgIHt7ICh6b29tKCkgKiAxMDApLnRvRml4ZWQoMCkgfX0lXG4gICAgICA8L2J1dHRvbj5cbiAgICAgIDxidXR0b25cbiAgICAgICAgdHlwZT1cImJ1dHRvblwiXG4gICAgICAgIGNsYXNzPVwiem9vbS1idXR0b25cIlxuICAgICAgICBtYXRUb29sdGlwPVwiWm9vbSBpbiAoQ3RybC9DbWQgKyBzY3JvbGwpXCJcbiAgICAgICAgKGNsaWNrKT1cInpvb21JbigpXCI+XG4gICAgICAgIDxtYXQtaWNvbj5hZGQ8L21hdC1pY29uPlxuICAgICAgPC9idXR0b24+XG4gICAgICA8YnV0dG9uXG4gICAgICAgIHR5cGU9XCJidXR0b25cIlxuICAgICAgICBjbGFzcz1cInpvb20tYnV0dG9uXCJcbiAgICAgICAgbWF0VG9vbHRpcD1cIkZpdCBwYWdlXCJcbiAgICAgICAgKGNsaWNrKT1cInpvb21GaXQoKVwiPlxuICAgICAgICA8bWF0LWljb24+Zml0X3NjcmVlbjwvbWF0LWljb24+XG4gICAgICA8L2J1dHRvbj5cbiAgICA8L2Rpdj5cbiAgPC9kaXY+XG48L2Rpdj5cbiJdfQ==
|
|
790
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoicmVwb3J0LWNhbnZhcy5jb21wb25lbnQuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi8uLi8uLi9zcmMvYXBwL3JlcG9ydHMvY29tcG9uZW50cy9yZXBvcnQtY2FudmFzL3JlcG9ydC1jYW52YXMuY29tcG9uZW50LnRzIiwiLi4vLi4vLi4vLi4vLi4vLi4vc3JjL2FwcC9yZXBvcnRzL2NvbXBvbmVudHMvcmVwb3J0LWNhbnZhcy9yZXBvcnQtY2FudmFzLmNvbXBvbmVudC5odG1sIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBLE9BQU8sRUFDVSx1QkFBdUIsRUFBRSxTQUFTLEVBQUUsVUFBVSxFQUM3RCxVQUFVLEVBQUUsWUFBWSxFQUFFLEtBQUssRUFBYSxNQUFNLEVBQUUsU0FBUyxFQUFpQixTQUFTLEVBQUUsWUFBWSxFQUNyRixRQUFRLEVBQUUsTUFBTSxFQUFFLE1BQU0sR0FDekMsTUFBTSxlQUFlLENBQUM7QUFDdkIsT0FBTyxFQUFFLGtCQUFrQixFQUFFLFlBQVksRUFBRSxNQUFNLDRCQUE0QixDQUFDO0FBRTlFLE9BQU8sRUFBZSxjQUFjLEVBQUUsZUFBZSxFQUFFLE1BQU0sd0JBQXdCLENBQUM7QUFDdEYsT0FBTyxFQUFFLE9BQU8sRUFBRSxNQUFNLHdCQUF3QixDQUFDO0FBQ2pELE9BQU8sRUFBRSxVQUFVLEVBQUUsTUFBTSwyQkFBMkIsQ0FBQztBQUV2RCxPQUFPLEVBQUUsWUFBWSxFQUFFLE1BQU0sa0JBQWtCLENBQUM7QUFDaEQsT0FBTyxFQUFFLFNBQVMsRUFBRSxNQUFNLHFCQUFxQixDQUFDO0FBQ2hELE9BQU8sRUFBRSxRQUFRLEVBQUUsTUFBTSxvQkFBb0IsQ0FBQztBQUM5QyxPQUFPLEVBQUUsa0JBQWtCLEVBQUUsZUFBZSxFQUFFLE1BQU0sc0JBQXNCLENBQUM7QUFFM0UsT0FBTyxFQUNPLE9BQU8sRUFBRSxVQUFVLEVBQUUsWUFBWSxFQUFFLE1BQU0sSUFBSSxRQUFRLEVBQUUsR0FBRyxFQUFFLEtB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LGFBQWE7c0JBQTdCLE1BQU07Z0JBSVUsV0FBVztzQkFBM0IsTUFBTTtnQkFHQSxPQUFPO3NCQURiLFNBQVM7dUJBQUMsa0JBQWtCO2dCQU1yQixtQkFBbUI7c0JBRDFCLFlBQVk7dUJBQUMsd0JBQXdCO2dCQUk5QixTQUFTO3NCQURoQixTQUFTO3VCQUFDLFVBQVUsRUFBRSxFQUFFLE1BQU0sRUFBRSxJQUFJLEVBQUU7Z0JBSS9CLE9BQU87c0JBRGQsU0FBUzt1QkFBQyxRQUFRLEVBQUUsRUFBRSxNQUFNLEVBQUUsS0FBSyxFQUFFIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHtcbiAgQWZ0ZXJWaWV3SW5pdCwgQ2hhbmdlRGV0ZWN0aW9uU3RyYXRlZ3ksIENvbXBvbmVudCwgRGVzdHJveVJlZixcbiAgRWxlbWVudFJlZiwgRXZlbnRFbWl0dGVyLCBJbnB1dCwgT25DaGFuZ2VzLCBPdXRwdXQsIFF1ZXJ5TGlzdCwgU2ltcGxlQ2hhbmdlcywgVmlld0NoaWxkLCBWaWV3Q2hpbGRyZW4sXG4gIFdyaXRhYmxlU2lnbmFsLCBjb21wdXRlZCwgaW5qZWN0LCBzaWduYWwsXG59IGZyb20gJ0Bhbmd1bGFyL2NvcmUnO1xuaW1wb3J0IHsgdGFrZVVudGlsRGVzdHJveWVkLCB0b09ic2VydmFibGUgfSBmcm9tICdAYW5ndWxhci9jb3JlL3J4anMtaW50ZXJvcCc7XG5cbmltcG9ydCB7IENka0RyYWdEcm9wLCBEcmFnRHJvcE1vZHVsZSwgbW92ZUl0ZW1JbkFycmF5IH0gZnJvbSAnQGFuZ3VsYXIvY2RrL2RyYWctZHJvcCc7XG5pbXBvcnQgeyBNYXRJY29uIH0gZnJvbSAnQGFuZ3VsYXIvbWF0ZXJpYWwvaWNvbic7XG5pbXBvcnQgeyBNYXRUb29sdGlwIH0gZnJvbSAnQGFuZ3VsYXIvbWF0ZXJpYWwvdG9vbHRpcCc7XG5cbmltcG9ydCB7IEZzTWVudU1vZHVsZSB9IGZyb20gJ0BmaXJlc3RpdGNoL21lbnUnO1xuaW1wb3J0IHsgRnNNZXNzYWdlIH0gZnJvbSAnQGZpcmVzdGl0Y2gvbWVzc2FnZSc7XG5pbXBvcnQgeyBGc1Byb21wdCB9IGZyb20gJ0BmaXJlc3RpdGNoL3Byb21wdCc7XG5pbXBvcnQgeyBGc1pvb21QYW5Db21wb25lbnQsIEZzWm9vbVBhbk1vZHVsZSB9IGZyb20gJ0BmaXJlc3RpdGNoL3pvb20tcGFuJztcblxuaW1wb3J0IHtcbiAgT2JzZXJ2YWJsZSwgU3ViamVjdCwgY2F0Y2hFcnJvciwgZGVib3VuY2VUaW1lLCBmaWx0ZXIgYXMgcnhGaWx0ZXIsIG1hcCwgbWVyZ2UsIG9mLCBzd2l0Y2hNYXAsIHRhcCxcbn0gZnJvbSAncnhqcyc7XG5cbmltcG9ydCB7IGNhbnZhc0xhbmRpbmdQYWdlIH0gZnJvbSAnLi4vLi4vY2FudmFzLWxhbmRpbmctcGFnZSc7XG5pbXBvcnQgeyBSZXBvcnREYXRhIH0gZnJvbSAnLi4vLi4vZGF0YS9yZXBvcnQuZGF0YSc7XG5pbXBvcnQge1xuICBDb21wb25lbnRTZXR0aW5ncywgUmVwb3J0LCBSZXBvcnRDb21wb25lbnQsIFJlcG9ydEZpbHRlckdyb3VwLCBSZXBvcnRIZWFkZXJGb290ZXIsIFJlcG9ydE1hc3RlciwgUmVwb3J0UGFnZSxcbiAgUmVwb3J0UGFnZVZhbHVlLCBSZXNvbHZlZEZpbHRlclZhbHVlLFxufSBmcm9tICcuLi8uLi9pbnRlcmZhY2VzL3JlcG9ydC5pbnRlcmZhY2UnO1xuaW1wb3J0IHsgREVGQVVMVF9IRUFESU5HX1NJWkUgfSBmcm9tICcuLi8uLi9sYXlvdXQnO1xuaW1wb3J0IHsgUmVwb3J0RmlsdGVyU3RhdGVTZXJ2aWNlIH0gZnJvbSAnLi4vLi4vc2VydmljZXMvcmVwb3J0LWZpbHRlci1zdGF0ZS5zZXJ2aWNlJztcbmltcG9ydCB7IFRleHRUb2tlbkNvbnRleHQgfSBmcm9tICcuLi8uLi90ZXh0JztcbmltcG9ydCB7IHZhbHVlc01hdGNoQW55R3JvdXBJZHMgfSBmcm9tICcuLi8uLi90aWxlLWRhdGEtc3RhdGUnO1xuaW1wb3J0IHtcbiAgaXNEcmF3biwgbGF5ZXJWYWx1ZUtleXMsIHNhbWVUZXh0VmFsdWVzLCBzaG93blZhbHVlcywgdGV4dFZhbHVlcywgdmFsdWVLZXksIHZhbHVlS2V5cyxcbn0gZnJvbSAnLi4vLi4vdmFsdWVzJztcbmltcG9ydCB7IFJlcG9ydENvbXBvbmVudENvbXBvbmVudCB9IGZyb20gJy4uL3JlcG9ydC1jb21wb25lbnQvcmVwb3J0LWNvbXBvbmVudC5jb21wb25lbnQnO1xuXG5cbi8vIFNjcmVlbiBkZW5zaXR5IG9mIHRoZSBjYW52YXM6IDk2IENTUyBweCBwZXIgaW5jaCAodGhlIENTUyByZWZlcmVuY2UgcGl4ZWwpLFxuLy8gYmVmb3JlIHpvb20uIEFsbCBnZW9tZXRyeSBzdGF5cyBpbiBpbmNoZXM7IG9ubHkgcmVuZGVyaW5nIG11bHRpcGxpZXMgYnkgaXQuXG5leHBvcnQgY29uc3QgUFhfUEVSX0lOQ0ggPSA5NjtcblxuLy8gT25lIHNtYXJ0IGd1aWRlIGxpbmUsIGluIHBhZ2UgaW5jaGVzLlxuZXhwb3J0IGludGVyZmFjZSBHdWlkZUxpbmUge1xuICBvcmllbnRhdGlvbjogJ3YnIHwgJ2gnO1xuICBwb3NpdGlvbjogbnVtYmVyO1xufVxuXG4vLyBUaGUgc25hcHBpbmcgY29udHJhY3QgaGFuZGVkIHRvIGVhY2ggY29tcG9uZW50J3MgZHJhZyBsb29wLiBJbXBsZW1lbnRlZCBieVxuLy8gdGhlIGNhbnZhcyBiZWNhdXNlIG9ubHkgaXQgc2VlcyBldmVyeSBjb21wb25lbnQgKGFsaWdubWVudCBjYW5kaWRhdGVzKSBhbmRcbi8vIG93bnMgdGhlIGd1aWRlcyBvdmVybGF5LlxuZXhwb3J0IGludGVyZmFjZSBDYW52YXNTbmFwcGVyIHtcbiAgc25hcE1vdmUoY29tcG9uZW50OiBSZXBvcnRDb21wb25lbnQsIHg6IG51bWJlciwgeTogbnVtYmVyKTogeyB4OiBudW1iZXI7IHk6IG51bWJlciB9O1xuICBzbmFwUmVzaXplKGNvbXBvbmVudDogUmVwb3J0Q29tcG9uZW50LCBnZW9tZXRyeTogeyB4OiBudW1iZXI7IHk6IG51bWJlcjsgdzogbnVtYmVyOyBoOiBudW1iZXIgfSwgaGFuZGxlOiBzdHJpbmcpOiB7IHg6IG51bWJlcjsgeTogbnVtYmVyOyB3OiBudW1iZXI7IGg6IG51bWJlciB9O1xuICBjbGVhcigpOiB2b2lkO1xufVxuXG4vLyBPbmUgbGF5ZXIncyB2YWx1ZXMgcmVxdWVzdCAoYSBwYWdlLCBvciB0aGUgbWFzdGVyKSwgcmVhZCB3aGVuIGl0IGlzIHNlbnQ6XG4vLyB0aGUgbGF5ZXIsIHRoZSB2YWx1ZXMgaXRzIHRleHQgc2hvd3MgYXQgdGhhdCBtb21lbnQgKHdoYXQgcmVhZHMgYXMgbG9hZGluZ1xuLy8gdW50aWwgaXQgbGFuZHMpIGFuZCB0aGUgZmlsdGVyIHZhbHVlcyBvZiBldmVyeSB2YWx1ZSBvbiB0aGUgbGF5ZXIuXG5pbnRlcmZhY2UgTGF5ZXJWYWx1ZXNSZXF1ZXN0IHtcbiAgcGFnZUlkOiBudW1iZXIgfCBudWxsO1xuICBzaG93bjogUmVwb3J0Q29tcG9uZW50W107XG4gIGZpbHRlcnM6IFJlc29sdmVkRmlsdGVyVmFsdWVbXTtcbiAgLy8gV2hpbGUgdGhlIGdyb3VwcyBtYXRjaCAnYW55JywgdGhlIGdyb3VwcyB0aGF0IGNvbWJpbmVcbiAgLy8gKHZhbHVlc01hdGNoQW55R3JvdXBJZHMpOyBlbXB0eSBvdGhlcndpc2UuXG4gIG1hdGNoQW55R3JvdXBJZHM6IG51bWJlcltdO1xuICAvLyBFdmVyeXRoaW5nIHRoZSBsYXllcidzIG51bWJlcnMgZGVwZW5kIG9uOiB0aGUgcmVxdWVzdCwgYW5kIGhvdyBlYWNoIHZhbHVlXG4gIC8vIGl0IHJlYWRzIGlzIGRlZmluZWQuIEEgcmVsb2FkIG9mIHRoZSByZXBvcnQgdGhhdCBsZWF2ZXMgaXQgYXMgaXQgd2FzIGFza3NcbiAgLy8gZm9yIG5vdGhpbmcuXG4gIHNpZ25hdHVyZTogc3RyaW5nO1xufVxuXG4vLyBPbmUgbGF5ZXIncyBudW1iZXJzIGFzIHRoZXkgbGFzdCBhcnJpdmVkLCBieSB2YWx1ZSBpZCwgYW5kIHRoZSByZXF1ZXN0IHRoZXlcbi8vIGFuc3dlciDigJQgcmVzdWx0cyBmb3IgYW5vdGhlciBwYWdlIGFyZSBub3QgdGhpcyBwYWdlJ3MuXG5pbnRlcmZhY2UgTGF5ZXJWYWx1ZXMge1xuICBwYWdlSWQ6IG51bWJlciB8IG51bGw7XG4gIHNpZ25hdHVyZTogc3RyaW5nO1xuICByb3dzOiBSZWFkb25seU1hcDxudW1iZXIsIFJlcG9ydFBhZ2VWYWx1ZT47XG59XG5cbi8vIEEgbGF5ZXIgd2hvc2UgdmFsdWVzIHRoZSBjYW52YXMgcmVhZHM6IHRoZSBhY3RpdmUgcGFnZSwgb3IgdGhlIG1hc3Rlci5cbmludGVyZmFjZSBWYWx1ZUxheWVyIHtcbiAgLy8gVGhlIGxheWVyIGFzIGl0IHN0YW5kcywgb3IgbnVsbCB3aGVuIG5vbmUgb2YgaXRzIG51bWJlcnMgYXJlIG5lZWRlZC5cbiAgc291cmNlOiAoKSA9PiBSZXBvcnRQYWdlIHwgUmVwb3J0TWFzdGVyIHwgbnVsbDtcbiAgLy8gQXNrcyBmb3IgaXRzIG51bWJlcnMgYWdhaW4uXG4gIHJlbG9hZCQ6IFN1YmplY3Q8dm9pZD47XG4gIC8vIEl0cyBudW1iZXJzIGFzIHRoZXkgbGFzdCBhcnJpdmVkLlxuICByZXN1bHRzOiBXcml0YWJsZVNpZ25hbDxMYXllclZhbHVlcyB8IG51bGw+O1xuICAvLyBUaGUgcmVxdWVzdCBvbiBpdHMgd2F5LCBudWxsIG9uY2UgaXQgaGFzIGxhbmRlZC4gQSB2YWx1ZSBpdCBhc2tzIGZvclxuICAvLyByZWFkcyBhcyBsb2FkaW5nIHVudGlsIHRoZW4sIHNvIGEgbnVtYmVyIG9uIHNjcmVlbiBpcyBuZXZlciBvbmUgcmVhZCBmb3JcbiAgLy8gYW4gZWFybGllciByZXF1ZXN0IChhbm90aGVyIGZpbHRlciwgdGhlIHZhbHVlIGFzIGl0IHdhcykuXG4gIHBlbmRpbmc6IFdyaXRhYmxlU2lnbmFsPExheWVyVmFsdWVzUmVxdWVzdCB8IG51bGw+O1xufVxuXG4vLyBXaGV0aGVyIHR3byB0b2tlbiBjb250ZXh0cyBmaWxsIGV2ZXJ5IHRva2VuIHRoZSBzYW1lLCBzbyByZWNvbXB1dGluZyBvbmVcbi8vIHRoYXQgY2hhbmdlZCBub3RoaW5nIGEgdG9rZW4gc2hvd3MgaGFuZHMgYmFjayB0aGUgb2JqZWN0IHRoZSBibG9ja3MgaGF2ZS5cbmZ1bmN0aW9uIHNhbWVUb2tlbnMoYTogVGV4dFRva2VuQ29udGV4dCwgYjogVGV4dFRva2VuQ29udGV4dCk6IGJvb2xlYW4ge1xuICByZXR1cm4gYS5wYWdlTnVtYmVyID09PSBiLnBhZ2VOdW1iZXJcbiAgICAmJiBhLnBhZ2VOYW1lID09PSBiLnBhZ2VOYW1lXG4gICAgJiYgYS5yZXBvcnROYW1lID09PSBiLnJlcG9ydE5hbWVcbiAgICAmJiBhLnZhbHVlUGFnZUlkID09PSBiLnZhbHVlUGFnZUlkXG4gICAgJiYgc2FtZVRleHRWYWx1ZXMoYS52YWx1ZXMsIGIudmFsdWVzKTtcbn1cblxuLy8gVGhlIGZpeGVkLXNpemUgcGFnZSBjYW52YXMg4oCUIHRoZSBQb3dlclBvaW50IG1vZGVsLiBQYWdlcyBhcmUgdGFicyAob25seSB0aGVcbi8vIEFDVElWRSBwYWdlJ3MgY29tcG9uZW50cyBleGlzdCDihpIgb25seSB0aGV5IGZldGNoKTsgdGhlIHBhZ2UgaXMgYVxuLy8gcGFnZVdpZHRow5dwYWdlSGVpZ2h0IElOQ0hFUyBzaGVldCByZW5kZXJlZCBhdCA5NnB4L2luIGluc2lkZSBmcy16b29tLXBhblxuLy8gKEN0cmwvQ21kICsgd2hlZWwgb3IgcGluY2ggdG8gem9vbSwgYmFja2dyb3VuZCBkcmFnIHBhbiwgdG9vbGJhciBidXR0b25zOyBhXG4vLyBwbGFpbiB3aGVlbCBzY3JvbGxzIHRoZSBsaXN0IHVuZGVyIHRoZSBwb2ludGVyKS5cbi8vXG4vLyBDb21wb25lbnRzIGFyZSBhYnNvbHV0ZWx5IHBvc2l0aW9uZWQ7IGRyYWdnaW5nIGdldHMgc21hcnQgYWxpZ25tZW50IGd1aWRlc1xuLy8gKGVkZ2VzICsgY2VudGVycyBvZiBzaWJsaW5ncyBhbmQgdGhlIHBhZ2UpIHdpdGggc25hcHBpbmcuXG4vL1xuLy8gSGVhZGVyIGFuZCBmb290ZXI6IHRoZSByZXBvcnQncyBtYXN0ZXIgY29tcG9uZW50cyAocmVwb3J0Lm1hc3RlcikgYXJlIGRyYXduXG4vLyBvbiBhIGxheWVyIFVOREVSIGV2ZXJ5IHBhZ2UncyBvd24gY29tcG9uZW50cywgbGlrZSBhIFBvd2VyUG9pbnQgc2xpZGUgbWFzdGVyLFxuLy8gdW5sZXNzIHRoZSBwYWdlIGhpZGVzIHRoZW0uIEluIGVkaXQgbW9kZSB0aGUgaG9zdCB0b29sYmFyJ3MgXCJIZWFkZXIgJiBmb290ZXJcIlxuLy8gKHRvZ2dsZU1hc3Rlck1vZGUpIHN3aXRjaGVzIHdoaWNoIGxheWVyIGlzIGxpdmU6IHRoZSBwYWdlJ3MgY29tcG9uZW50cyBkaW1cbi8vIGFuZCB0aGUgbWFzdGVyJ3MgYmVjb21lIHRoZSBvbmVzIHRoYXQgZHJhZywgcmVzaXplIGFuZCBzbmFwLiBUaGUgaGVhZGVyL2Zvb3RlciBiYW5kcyAoY29uZmlnLmhlYWRlckZvb3Rlcilcbi8vIGFyZSBkcmF3biBhcyBndWlkZXMgd2hpbGUgZWRpdGluZyBhbmQgYXJlIHNuYXAgbGluZXMgZm9yIGJvdGggbGF5ZXJzLlxuLy9cbi8vIExpdmUgdmFsdWVzOiBhIHRleHQgYmxvY2sgc2hvd3MgbnVtYmVycyBpbmxpbmUgKHt7dmFsdWUua2V5fX0pLiBBIHZhbHVlIGlzXG4vLyBuZXZlciBkcmF3bjsgaXQgYmVsb25ncyB0byB0aGUgcGFnZSB3aG9zZSB0ZXh0IHNob3dzIGl0ICh0aGUgbWFzdGVyIGZvciBhXG4vLyBoZWFkZXIgb3IgZm9vdGVyKSBhbmQgaXMgbGlzdGVkIGluIHRoYXQgbGF5ZXIncyBgdmFsdWVzYC4gVGhlIGNhbnZhcyByZWFkc1xuLy8gdGhlIG51bWJlcnMgb25lIHJlcXVlc3QgcGVyIGxheWVyIOKAlCB0aGUgYWN0aXZlIHBhZ2UncyBhbmQgdGhlIG1hc3RlcidzIOKAlFxuLy8gYW5kIGhhbmRzIHRoZW0gdG8gZXZlcnkgYmxvY2sgb2YgdGhlIGxheWVyIHdpdGggdGhlIHBhZ2UgdG9rZW5zLiBXaGljaFxuLy8gdmFsdWVzIGEgcmVxdWVzdCByZWFkcyBpcyB0aGUgc2VydmVyJ3MgY2FsbCBhbG9uZTogdGhlIG9uZXMgdGhlIHRleHQgc2hvd3MsXG4vLyBhbmQgdGhlIG9wZXJhbmRzIG9mIHRoZSBmb3JtdWxhcyBhbW9uZyB0aGVtLlxuQENvbXBvbmVudCh7XG4gIHNlbGVjdG9yOiAnYXBwLXJlcG9ydC1jYW52YXMnLFxuICB0ZW1wbGF0ZVVybDogJy4vcmVwb3J0LWNhbnZhcy5jb21wb25lbnQuaHRtbCcsXG4gIHN0eWxlVXJsczogWycuL3JlcG9ydC1jYW52YXMuY29tcG9uZW50LnNjc3MnXSxcbiAgY2hhbmdlRGV0ZWN0aW9uOiBDaGFuZ2VEZXRlY3Rpb25TdHJhdGVneS5PblB1c2gsXG4gIHN0YW5kYWxvbmU6IHRydWUsXG4gIGltcG9ydHM6IFtcbiAgICBEcmFnRHJvcE1vZHVsZSxcbiAgICBNYXRJY29uLFxuICAgIE1hdFRvb2x0aXAsXG4gICAgRnNNZW51TW9kdWxlLFxuICAgIEZzWm9vbVBhbk1vZHVsZSxcbiAgICBSZXBvcnRDb21wb25lbnRDb21wb25lbnQsXG4gIF0sXG59KVxuZXhwb3J0IGNsYXNzIFJlcG9ydENhbnZhc0NvbXBvbmVudCBpbXBsZW1lbnRzIE9uQ2hhbmdlcywgQWZ0ZXJWaWV3SW5pdCB7XG5cbiAgQElucHV0KCkgcHVibGljIHJlcG9ydDogUmVwb3J0O1xuICBASW5wdXQoKSBwdWJsaWMgZWRpdE1vZGUgPSBmYWxzZTtcblxuICAvLyBUaGUgcGFnZSB0aGUgaG9zdCB3YW50cyBvbiBzY3JlZW4sIGJ5IHBhZ2UgaWQgKGEgP3BhZ2U9IHRoZSByZXBvcnQgb3BlbmVkXG4gIC8vIHdpdGgsIG9yIGFuIG9wZW5lZCB2aWV3J3MgcGFnZSkuIEtleWVkIG9uIGlkIHJhdGhlciB0aGFuIGluZGV4IHNvIGl0XG4gIC8vIHN1cnZpdmVzIHBhZ2VzIGJlaW5nIHJlb3JkZXJlZCBvciBkZWxldGVkOyBhbiBpZCB0aGF0IG5vIGxvbmdlciByZXNvbHZlc1xuICAvLyBmYWxscyBiYWNrIHRvIHRoZSBmaXJzdCBwYWdlLlxuICBASW5wdXQoKSBwdWJsaWMgcGFnZUlkOiBudW1iZXIgfCBudWxsID0gbnVsbDtcblxuICAvLyBBIGNvbXBvbmVudCBhc2tlZCBmb3IgaXRzIHNldHRpbmdzIGRpYWxvZyDigJQgdGhlIHBhZ2UtbGV2ZWwgaG9zdCBvcGVucyBpdFxuICAvLyAoaXQgb3ducyBNYXREaWFsb2cgKyB0aGUgcG9zdC1zYXZlIHJlbG9hZCkuXG4gIEBPdXRwdXQoKSBwdWJsaWMgY29tcG9uZW50U2V0dGluZ3MgPSBuZXcgRXZlbnRFbWl0dGVyPFJlcG9ydENvbXBvbmVudD4oKTtcblxuICAvLyBUaGUgcmVwb3J0J3Mgc3RydWN0dXJlIGNoYW5nZWQgaGVyZSAoYSBwYWdlIHdhcyBhZGRlZCkg4oCUIHRoZSBob3N0IHJlLWZldGNoZXNcbiAgLy8gaXQgKGl0IG93bnMgdGhlIGFzc2VtYmxlZCByZXBvcnQgKyBmaWx0ZXIgc3RhdGUpLlxuICBAT3V0cHV0KCkgcHVibGljIHJlcG9ydENoYW5nZWQgPSBuZXcgRXZlbnRFbWl0dGVyPHZvaWQ+KCk7XG5cbiAgLy8gVGhlIHBhZ2Ugb24gc2NyZWVuIGNoYW5nZWQg4oCUIHRoZSBob3N0IGtlZXBzIGl0IGluIHRoZSByZXBvcnQncyBzdGF0ZSAoYVxuICAvLyBzYXZlZCB2aWV3IHN0b3JlcyBpdCkuIENhcnJpZXMgdGhlIHBhZ2UgaWQsIG5ldmVyIHRoZSBpbmRleC5cbiAgQE91dHB1dCgpIHB1YmxpYyBwYWdlQ2hhbmdlZCA9IG5ldyBFdmVudEVtaXR0ZXI8bnVtYmVyIHwgbnVsbD4oKTtcblxuICBAVmlld0NoaWxkKEZzWm9vbVBhbkNvbXBvbmVudClcbiAgcHVibGljIHpvb21QYW46IEZzWm9vbVBhbkNvbXBvbmVudDtcblxuICAvLyBUaGUgcmVuZGVyZWQgY29tcG9uZW50cyBvZiB0aGUgYWN0aXZlIHBhZ2Ug4oCUIG9ubHkgdGhlIGNhbnZhcyBjYW4gcmVhY2ggdGhlXG4gIC8vIG9uZSBpbnN0YW5jZSBhIHNldHRpbmdzIHNhdmUgYXBwbGllcyB0by5cbiAgQFZpZXdDaGlsZHJlbihSZXBvcnRDb21wb25lbnRDb21wb25lbnQpXG4gIHByaXZhdGUgX3JlbmRlcmVkQ29tcG9uZW50czogUXVlcnlMaXN0PFJlcG9ydENvbXBvbmVudENvbXBvbmVudD47XG5cbiAgQFZpZXdDaGlsZCgndmlld3BvcnQnLCB7IHN0YXRpYzogdHJ1ZSB9KVxuICBwcml2YXRlIF92aWV3cG9ydDogRWxlbWVudFJlZjxIVE1MRGl2RWxlbWVudD47XG5cbiAgQFZpZXdDaGlsZCgnZ3VpZGVzJywgeyBzdGF0aWM6IGZhbHNlIH0pXG4gIHByaXZhdGUgX2d1aWRlczogRWxlbWVudFJlZjxIVE1MRGl2RWxlbWVudD47XG5cbiAgcHVibGljIHJlYWRvbmx5IFBYID0gUFhfUEVSX0lOQ0g7XG5cbiAgLy8gVGhlIHJlcG9ydCdzIHBhZ2VzIGFzIHRoZSBjYW52YXMgZHJhd3MgdGhlbS4gVGhpcyBpcyB0aGUgaG9zdCdzIG93blxuICAvLyBgcmVwb3J0LnBhZ2VzYCBhcnJheSwgcGF0Y2hlZCBpbiBwbGFjZSAoYSByZW5hbWUsIGEgZGVsZXRlLCBhIHJlb3JkZXIpIHNvXG4gIC8vIHRoZSBob3N0J3MgZXhwb3J0cyBzZWUgdGhlIGNoYW5nZSB0b28uIEJlY2F1c2UgdGhlIGFycmF5XG4gIC8vIGFuZCBpdHMgcGFnZXMga2VlcCB0aGVpciBpZGVudGl0eSBhY3Jvc3MgYSBwYXRjaCwgdGhlIHNpZ25hbCBub3RpZmllcyBvblxuICAvLyBldmVyeSBzZXQgcmF0aGVyIHRoYW4gb25seSB3aGVuIHRoZSByZWZlcmVuY2UgY2hhbmdlcy5cbiAgcHVibGljIHJlYWRvbmx5IHBhZ2VzID0gc2lnbmFsPFJlcG9ydFBhZ2VbXT4oW10sIHsgZXF1YWw6ICgpID0+IGZhbHNlIH0pO1xuICBwdWJsaWMgcmVhZG9ubHkgYWN0aXZlUGFnZUluZGV4ID0gc2lnbmFsKDApO1xuICBwdWJsaWMgcmVhZG9ubHkgYWN0aXZlUGFnZUlkID0gY29tcHV0ZWQoKCkgPT4gdGhpcy5wYWdlcygpW3RoaXMuYWN0aXZlUGFnZUluZGV4KCldPy5pZCA/PyBudWxsKTtcbiAgcHVibGljIHJlYWRvbmx5IHpvb20gPSBzaWduYWwoMSk7XG5cbiAgLy8gRWRpdGluZyB0aGUgaGVhZGVyIGFuZCBmb290ZXIgKHRoZSBtYXN0ZXIgbGF5ZXIpIHJhdGhlciB0aGFuIHRoZSBwYWdlLlxuICBwdWJsaWMgcmVhZG9ubHkgbWFzdGVyTW9kZSA9IHNpZ25hbChmYWxzZSk7XG4gIHB1YmxpYyBncm91cHMgPSBuZXcgTWFwPG51bWJlciwgUmVwb3J0RmlsdGVyR3JvdXA+KCk7XG4gIHB1YmxpYyByZWFkb25seSBzZWxlY3RlZENvbXBvbmVudElkID0gc2lnbmFsPG51bWJlciB8IG51bGw+KG51bGwpO1xuICAvLyBNb3ZlcyB3aGVuIGEgdmlldyBpcyBvcGVuZWQuIEV2ZXJ5IHRpbGUgaXMgdHJhY2tlZCBieSBpdCwgc28gZWFjaCBpc1xuICAvLyBkcmF3biBhZ2FpbiBmcm9tIHRoZSB2aWV3J3Mgc3RhdGUuIEEgcmVzZXQgdG8gdGhlIG9wZW4gdmlldyBsZWF2ZXMgaXQ6XG4gIC8vIHRoZSB0aWxlcyByZWxvYWQgaW4gcGxhY2UgYW5kIGtlZXAgdGhlaXIgZGF0YSBvbiBzY3JlZW4gbWVhbndoaWxlLlxuICBwdWJsaWMgcmVhZG9ubHkgYXBwbGllZFZlcnNpb24gPSBpbmplY3QoUmVwb3J0RmlsdGVyU3RhdGVTZXJ2aWNlKS5hcHBsaWVkVmVyc2lvbjtcblxuICAvLyBUaGUgY29tcG9uZW50cyBlYWNoIGxheWVyIGRyYXdzLiBBIHZhbHVlIG9ubHkgcmVhZHMgaW5zaWRlIHRleHQsIHNvIG9uZVxuICAvLyB0aGF0IGxlYWtlZCBpbnRvIGEgbGF5ZXIncyBjb21wb25lbnRzIGlzIHN0aWxsIG5ldmVyIGRyYXduLlxuICBwdWJsaWMgcmVhZG9ubHkgYWN0aXZlUGFnZUNvbXBvbmVudHMgPSBjb21wdXRlZChcbiAgICAoKSA9PiAodGhpcy5wYWdlcygpW3RoaXMuYWN0aXZlUGFnZUluZGV4KCldPy5jb21wb25lbnRzID8/IFtdKS5maWx0ZXIoaXNEcmF3biksXG4gICk7XG5cbiAgcHVibGljIHJlYWRvbmx5IG1hc3RlckNvbXBvbmVudHMgPSBjb21wdXRlZChcbiAgICAoKSA9PiAodGhpcy5fcmVwb3J0KCk/Lm1hc3Rlcj8uY29tcG9uZW50cyA/PyBbXSkuZmlsdGVyKGlzRHJhd24pLFxuICApO1xuXG4gIC8vIFdoYXQgYSB0ZXh0IGJsb2NrJ3MgdG9rZW5zIGZpbGwgd2l0aCBvbiB0aGUgcGFnZSBvbiBzY3JlZW46IHt7cGFnZS5udW1iZXJ9fSxcbiAgLy8ge3twYWdlLm5hbWV9fSBhbmQge3tyZXBvcnQubmFtZX19ICh0aGUgbWFzdGVyJ3MgZm9vdGVyIG51bWJlcnMgZWFjaCBwYWdlIGJ5XG4gIC8vIGl0cyBwb3NpdGlvbiksIGFuZCB0aGUgdmFsdWVzIG9mIHRoZSBibG9jaydzIGxheWVyIOKAlCB0aGUgYWN0aXZlIHBhZ2UncyBmb3JcbiAgLy8gYSBwYWdlIGJsb2NrLCB0aGUgbWFzdGVyJ3MgZm9yIGEgaGVhZGVyIG9yIGZvb3RlciBibG9jaywgd2hvc2UgaWQgaXMgYWxzb1xuICAvLyB0aGUgZWRpdG9yJ3MgY2xpcGJvYXJkIHNjb3BlLiBUaGUgc2FtZSBvYmplY3QgaXMgaGFuZGVkIGJhY2sgdW50aWxcbiAgLy8gc29tZXRoaW5nIGEgdG9rZW4gc2hvd3MgY2hhbmdlczogZXZlcnkgdGV4dCBibG9jayB0YWtlcyBpdCBhcyBhbiBpbnB1dCxcbiAgLy8gYW5kIGEgZnJlc2ggb2JqZWN0IHdvdWxkIG1ha2UgZWFjaCBvZiB0aGVtIHJlcGFpbnQgaXRzIGh0bWwuXG4gIHB1YmxpYyByZWFkb25seSBwYWdlVG9rZW5zID0gY29tcHV0ZWQoXG4gICAgKCkgPT4gdGhpcy5fdG9rZW5Db250ZXh0KHRoaXMuX3BhZ2VWYWx1ZUNvbXBvbmVudHMoKSwgdGhpcy5fcGFnZVZhbHVlcywgdGhpcy5hY3RpdmVQYWdlSWQoKSksXG4gICAgeyBlcXVhbDogc2FtZVRva2VucyB9LFxuICApO1xuXG4gIHB1YmxpYyByZWFkb25seSBtYXN0ZXJUb2tlbnMgPSBjb21wdXRlZChcbiAgICAoKSA9PiB0aGlzLl90b2tlbkNvbnRleHQodGhpcy5fbWFzdGVyVmFsdWVDb21wb25lbnRzKCksIHRoaXMuX21hc3RlclZhbHVlcywgdGhpcy5fcmVwb3J0KCk/Lm1hc3Rlcj8uaWQgPz8gbnVsbCksXG4gICAgeyBlcXVhbDogc2FtZVRva2VucyB9LFxuICApO1xuXG4gIC8vIFRoZSBzbmFwcGVyIGhhbmRlZCB0byBldmVyeSBjb21wb25lbnQgKHN0YWJsZSBpZGVudGl0eSBmb3IgT25QdXNoKS5cbiAgcHVibGljIHJlYWRvbmx5IHNuYXBwZXI6IENhbnZhc1NuYXBwZXIgPSB7XG4gICAgc25hcE1vdmU6IChjb21wb25lbnQsIHgsIHkpID0+IHRoaXMuX3NuYXBNb3ZlKGNvbXBvbmVudCwgeCwgeSksXG4gICAgc25hcFJlc2l6ZTogKGNvbXBvbmVudCwgZ2VvbWV0cnksIGhhbmRsZSkgPT4gdGhpcy5fc25hcFJlc2l6ZShjb21wb25lbnQsIGdlb21ldHJ5LCBoYW5kbGUpLFxuICAgIGNsZWFyOiAoKSA9PiB0aGlzLl9jbGVhckd1aWRlcygpLFxuICB9O1xuXG4gIC8vIFRoZSB2YWx1ZSBrZXlzIHRoZSBvdGhlciB0ZXh0IGJsb2NrcyBvZiBhIHRleHQncyBsYXllciBzaG93ICh0aGUgbWFzdGVyJ3NcbiAgLy8gZm9yIGEgaGVhZGVyIG9yIGZvb3RlciBibG9jayksIGZvciBpdHMgZWRpdG9yJ3Mgbm90aWNlOiBhIHZhbHVlIGFub3RoZXJcbiAgLy8gYmxvY2sgc3RpbGwgc2hvd3MgaXMgbm90IGxlZnQgdW51c2VkLiBSZWFkIHdoZW4gYXNrZWQ6IHNhdmluZyBhIGJsb2NrXG4gIC8vIHdyaXRlcyBpdHMgaHRtbCBpbnRvIGl0cyBjb21wb25lbnQgaW4gcGxhY2UsIHdoaWNoIG5vIHNpZ25hbCBzZWVzLlxuICAvLyBTdGFibGUsIGFzIHRoZSBzbmFwcGVyIGlzLlxuICBwdWJsaWMgcmVhZG9ubHkgdmFsdWVLZXlzRWxzZXdoZXJlID0gKHRleHQ6IFJlcG9ydENvbXBvbmVudCk6IFJlYWRvbmx5U2V0PHN0cmluZz4gPT4ge1xuICAgIGNvbnN0IGxheWVyID0gdGhpcy5faXNNYXN0ZXJDb21wb25lbnQodGV4dCkgPyB0aGlzLnJlcG9ydD8ubWFzdGVyIDogdGhpcy5hY3RpdmVQYWdlO1xuXG4gICAgcmV0dXJuIG5ldyBTZXQoKGxheWVyPy5jb21wb25lbnRzID8/IFtdKVxuICAgICAgLmZpbHRlcigoY29tcG9uZW50KSA9PiBjb21wb25lbnQudHlwZSA9PT0gJ3RleHQnICYmIGNvbXBvbmVudC5pZCAhPT0gdGV4dC5pZClcbiAgICAgIC5mbGF0TWFwKChjb21wb25lbnQpID0+IHZhbHVlS2V5cyhjb21wb25lbnQuY29uZmlnPy5odG1sKSkpO1xuICB9O1xuXG4gIHByaXZhdGUgX3JlcG9ydERhdGEgPSBpbmplY3QoUmVwb3J0RGF0YSk7XG4gIHByaXZhdGUgX2ZpbHRlclN0YXRlID0gaW5qZWN0KFJlcG9ydEZpbHRlclN0YXRlU2VydmljZSk7XG4gIHByaXZhdGUgX3Byb21wdCA9IGluamVjdChGc1Byb21wdCk7XG4gIHByaXZhdGUgX21lc3NhZ2UgPSBpbmplY3QoRnNNZXNzYWdlKTtcbiAgcHJpdmF0ZSBfZGVzdHJveVJlZiA9IGluamVjdChEZXN0cm95UmVmKTtcbiAgcHJpdmF0ZSBfZml0dGVkID0gZmFsc2U7XG4gIHByaXZhdGUgX3ByZXZpb3VzUGFnZUNvdW50ID0gMDtcbiAgcHJpdmF0ZSBfcHJldmlvdXNSZXBvcnRJZDogbnVtYmVyIHwgbnVsbCA9IG51bGw7XG5cbiAgLy8gVGhlIHBhZ2UgaWQgbGFzdCBhbm5vdW5jZWQgdGhyb3VnaCBwYWdlQ2hhbmdlZCwgc28gYSByZS1yZW5kZXIgdGhhdCBsYW5kcyBvblxuICAvLyB0aGUgc2FtZSBwYWdlIHN0YXlzIHF1aWV0IOKAlCBob3N0cyByZWxvYWQgb24gdGhpcyBhbmQgYW4gdW5jaGFuZ2VkIHBhZ2UgaXNcbiAgLy8gbm90IG5ld3MuXG4gIHByaXZhdGUgX2VtaXR0ZWRQYWdlSWQ6IG51bWJlciB8IG51bGwgPSBudWxsO1xuXG4gIC8vIFRoZSByZXBvcnQgaW5wdXQgYXMgYSBzaWduYWwsIGZvciB0aGUgdG9rZW4gY29udGV4dHMgYW5kIHRoZSBtYXN0ZXInc1xuICAvLyBkcmF3biBjb21wb25lbnRzLiBOb3RpZmllcyBvbiBldmVyeSBzZXQ6IGEgcmVsb2FkIGhhbmRzIG92ZXIgYSBuZXcgcmVwb3J0XG4gIC8vIGV2ZW4gd2hlbiBub3RoaW5nIGEgdG9rZW4gc2hvd3MgbW92ZWQsIGFuZCBhIGRlbGV0ZWQgaGVhZGVyIG9yIGZvb3RlclxuICAvLyBibG9jayBpcyBzcGxpY2VkIG91dCBvZiB0aGUgc2FtZSByZXBvcnQuXG4gIHByaXZhdGUgX3JlcG9ydCA9IHNpZ25hbDxSZXBvcnQgfCBudWxsPihudWxsLCB7IGVxdWFsOiAoKSA9PiBmYWxzZSB9KTtcblxuICAvLyBUaGUgdmFsdWVzIGVhY2ggbGF5ZXIncyB0ZXh0IGNhbiBzaG93IChzaG93biBvciBub3QpLlxuICBwcml2YXRlIF9wYWdlVmFsdWVDb21wb25lbnRzID0gY29tcHV0ZWQoKCkgPT4gdGhpcy5wYWdlcygpW3RoaXMuYWN0aXZlUGFnZUluZGV4KCldPy52YWx1ZXMgPz8gW10pO1xuICBwcml2YXRlIF9tYXN0ZXJWYWx1ZUNvbXBvbmVudHMgPSBjb21wdXRlZCgoKSA9PiB0aGlzLl9yZXBvcnQoKT8ubWFzdGVyPy52YWx1ZXMgPz8gW10pO1xuXG4gIC8vIFRoZSBtYXN0ZXIncyBudW1iZXJzIGFyZSBuZWVkZWQgd2hpbGUgc29tZSBwYWdlIHNob3dzIHRoZSBoZWFkZXIgYW5kXG4gIC8vIGZvb3Rlciwgb3Igd2hpbGUgdGhleSBhcmUgYmVpbmcgZWRpdGVkLlxuICBwcml2YXRlIF9tYXN0ZXJOZWVkZWQgPSBjb21wdXRlZCgoKSA9PiB0aGlzLm1hc3Rlck1vZGUoKSB8fCB0aGlzLnBhZ2VzKCkuc29tZSgocGFnZSkgPT4gIXBhZ2UubWFzdGVySGlkZGVuKSk7XG5cbiAgLy8gVGhlIHR3byBsYXllcnMgd2hvc2UgdmFsdWVzIGFyZSByZWFkLCBlYWNoIG9uIGl0cyBvd24gc3RyZWFtLlxuICBwcml2YXRlIF9wYWdlVmFsdWVzID0gdGhpcy5fdmFsdWVMYXllcigoKSA9PiB0aGlzLmFjdGl2ZVBhZ2UpO1xuICBwcml2YXRlIF9tYXN0ZXJWYWx1ZXMgPSB0aGlzLl92YWx1ZUxheWVyKCgpID0+ICh0aGlzLl9tYXN0ZXJOZWVkZWQoKSA/IHRoaXMucmVwb3J0Py5tYXN0ZXIgPz8gbnVsbCA6IG51bGwpKTtcblxuICAvLyBCdW1wZWQgd2hlbiBhIHZhbHVlIGlzIHJlbmFtZWQgaW4gcGxhY2UsIHdoaWNoIG5vIHNpZ25hbCBzZWVzLlxuICBwcml2YXRlIF92YWx1ZXNSZXZpc2lvbiA9IHNpZ25hbCgwKTtcblxuICAvLyBUaGUgdmFsdWUga2V5cyBlYWNoIGxheWVyIGhlbGQgYXQgdGhlIGxhc3QgcmVwb3J0IGxvYWQsIGJ5IHBhZ2UgaWQgYW5kXG4gIC8vIG1hc3RlciBpZCwgc28gYSByZWxvYWQgY2FuIHRlbGwgd2hpY2ggdmFsdWVzIHdlcmUgZGVsZXRlZC5cbiAgcHJpdmF0ZSBfdmFsdWVLZXlzQnlMYXllciA9IG5ldyBNYXA8bnVtYmVyLCBTZXQ8c3RyaW5nPj4oKTtcblxuICBjb25zdHJ1Y3RvcigpIHtcbiAgICB0aGlzLl9pbml0KCk7XG4gIH1cblxuICBwdWJsaWMgbmdPbkNoYW5nZXMoY2hhbmdlczogU2ltcGxlQ2hhbmdlcyk6IHZvaWQge1xuICAgIC8vIExlYXZpbmcgZWRpdCBtb2RlIGFsd2F5cyByZXR1cm5zIHRvIHRoZSBwYWdlIGxheWVyLCBzbyB0aGUgbmV4dCBlZGl0XG4gICAgLy8gc2Vzc2lvbiBzdGFydHMgd2hlcmUgcGVvcGxlIGV4cGVjdC5cbiAgICBpZiAoY2hhbmdlcy5lZGl0TW9kZSAmJiAhdGhpcy5lZGl0TW9kZSkge1xuICAgICAgdGhpcy5tYXN0ZXJNb2RlLnNldChmYWxzZSk7XG4gICAgfVxuXG4gICAgdGhpcy5ncm91cHMgPSBuZXcgTWFwKCh0aGlzLnJlcG9ydD8uZmlsdGVyR3JvdXBzID8/IFtdKS5tYXAoKGdyb3VwKSA9PiBbZ3JvdXAuaWQsIGdyb3VwXSkpO1xuICAgIHRoaXMucGFnZXMuc2V0KHRoaXMucmVwb3J0Py5wYWdlcyA/PyBbXSk7XG5cbiAgICAvLyBBIHBhZ2UganVzdCBhZGRlZCBpbiB0aGlzIHRhYiwgZWxzZSB0aGUgYXNrZWQtZm9yIHBhZ2UsIGVsc2UgdGhlIHBhZ2VcbiAgICAvLyBzaG93biAodGhlIGZpcnN0IHBhZ2Ugb24gYW5vdGhlciByZXBvcnQpLiBTZWUgY2FudmFzTGFuZGluZ1BhZ2UuXG4gICAgY29uc3QgcmVwb3J0SWQgPSB0aGlzLnJlcG9ydD8uaWQgPz8gbnVsbDtcbiAgICB0aGlzLmFjdGl2ZVBhZ2VJbmRleC5zZXQoY2FudmFzTGFuZGluZ1BhZ2Uoe1xuICAgICAgcmVwb3J0SWQsXG4gICAgICBwcmV2aW91c1JlcG9ydElkOiB0aGlzLl9wcmV2aW91c1JlcG9ydElkLFxuICAgICAgcHJldmlvdXNQYWdlQ291bnQ6IHRoaXMuX3ByZXZpb3VzUGFnZUNvdW50LFxuICAgICAgcGFnZUlkczogdGhpcy5wYWdlcygpLm1hcCgocGFnZSkgPT4gcGFnZS5pZCksXG4gICAgICBwYWdlSWQ6IHRoaXMucGFnZUlkLFxuICAgICAgYWN0aXZlUGFnZUluZGV4OiB0aGlzLmFjdGl2ZVBhZ2VJbmRleCgpLFxuICAgIH0pKTtcbiAgICB0aGlzLl9wcmV2aW91c1BhZ2VDb3VudCA9IHRoaXMucGFnZXMoKS5sZW5ndGg7XG4gICAgdGhpcy5fcHJldmlvdXNSZXBvcnRJZCA9IHJlcG9ydElkO1xuXG4gICAgLy8gVGVsbCB0aGUgaG9zdCB3aGljaCBwYWdlIGlzIG9wZW4gd2hlbmV2ZXIgdGhhdCBjaGFuZ2VzIOKAlCBpbmNsdWRpbmcgdGhlXG4gICAgLy8gRklSU1QgdGltZSB0aGUgcmVwb3J0IHJlbmRlcnMsIG5vdCBvbmx5IHdoZW4gc29tZW9uZSBjbGlja3MgYSBwYWdlLlxuICAgIC8vIEhvc3RzIGJpbmQgdGhpbmdzIHRvIHRoZSBvcGVuIHBhZ2UgKHRoZSByZXBvcnQgY2hhdCBzY29wZXMgaXRzXG4gICAgLy8gY29udmVyc2F0aW9ucyB0byBpdCksIGFuZCB3aXRob3V0IHRoaXMgdGhleSB3b3VsZCBzaXQgb24gbm8gcGFnZSBhdCBhbGxcbiAgICAvLyB1bnRpbCB0aGUgZmlyc3QgbWFudWFsIHBhZ2UgY2xpY2suXG4gICAgY29uc3QgYWN0aXZlUGFnZUlkID0gdGhpcy5hY3RpdmVQYWdlPy5pZCA/PyBudWxsO1xuICAgIGlmIChhY3RpdmVQYWdlSWQgIT09IHRoaXMuX2VtaXR0ZWRQYWdlSWQpIHtcbiAgICAgIHRoaXMuX2VtaXR0ZWRQYWdlSWQgPSBhY3RpdmVQYWdlSWQ7XG4gICAgICB0aGlzLnBhZ2VDaGFuZ2VkLmVtaXQoYWN0aXZlUGFnZUlkKTtcbiAgICB9XG5cbiAgICAvLyBBIChyZSlsb2FkZWQgcmVwb3J0IG1heSBoYXZlIGdhaW5lZCwgbG9zdCBvciBjaGFuZ2VkIHZhbHVlcywgYW5kIGFueVxuICAgIC8vIHRleHQgbWF5IG5vdyBzaG93IGRpZmZlcmVudCBvbmVzOiByZWFkIGFnYWluIGVhY2ggbGF5ZXIgd2hvc2UgbnVtYmVyc1xuICAgIC8vIHRoYXQgbW92ZXMuXG4gICAgaWYgKGNoYW5nZXMucmVwb3J0KSB7XG4gICAgICB0aGlzLl9yZXBvcnQuc2V0KHRoaXMucmVwb3J0KTtcbiAgICAgIHRoaXMuX2Ryb3BSZW1vdmVkVmFsdWVDaGlwcygpO1xuICAgICAgdGhpcy5fcmVsb2FkSWZDaGFuZ2VkKHRoaXMuX3BhZ2VWYWx1ZXMpO1xuICAgICAgdGhpcy5fcmVsb2FkSWZDaGFuZ2VkKHRoaXMuX21hc3RlclZhbHVlcyk7XG4gICAgfVxuICB9XG5cbiAgLy8gUmVwb3J0IGhlYWRpbmcgc2l6ZSBpbiBweCAoY29uZmlnIGlzIHBvaW50czsgdGhlIGNhbnZhcyByZW5kZXJzIGF0XG4gIC8vIDk2cHgvaW4sIHNvIHBvaW50cyDDlyA5Ni83MikuIEluaGVyaXRlZCBieSBjb21wb25lbnQgdGl0bGVzIHZpYSBhIENTUyB2YXIuXG4gIHB1YmxpYyBnZXQgaGVhZGluZ1NpemVQeCgpOiBudW1iZXIge1xuICAgIGNvbnN0IHBvaW50cyA9IHRoaXMucmVwb3J0Py5jb25maWc/LnN0eWxlcz8uaGVhZGluZz8uc2l6ZSA/PyBERUZBVUxUX0hFQURJTkdfU0laRTtcblxuICAgIHJldHVybiBwb2ludHMgKiAoUFhfUEVSX0lOQ0ggLyA3Mik7XG4gIH1cblxuICBwdWJsaWMgbmdBZnRlclZpZXdJbml0KCk6IHZvaWQge1xuICAgIC8vIEZpdCB0aGUgcGFnZSB0byB0aGUgdmlld3BvcnQgb25jZSBvbiBmaXJzdCByZW5kZXI7IGFmdGVyIHRoYXQgdGhlXG4gICAgLy8gdmlld2VyJ3Mgem9vbSBjaG9pY2UgaXMgcmVzcGVjdGVkIGFjcm9zcyByZS1yZW5kZXJzLlxuICAgIHNldFRpbWVvdXQoKCkgPT4gdGhpcy56b29tRml0KCkpO1xuICB9XG5cbiAgcHVibGljIGdldCBhY3RpdmVQYWdlKCk6IFJlcG9ydFBhZ2UgfCBudWxsIHtcbiAgICByZXR1cm4gdGhpcy5wYWdlcygpW3RoaXMuYWN0aXZlUGFnZUluZGV4KCldID8/IG51bGw7XG4gIH1cblxuICAvLyBUaGUgaGVhZGVyL2Zvb3RlciBiYW5kcywgaW4gaW5jaGVzICgwID0gbm8gYmFuZCkuXG4gIHB1YmxpYyBnZXQgYmFuZHMoKTogUmVwb3J0SGVhZGVyRm9vdGVyIHtcbiAgICByZXR1cm4gdGhpcy5yZXBvcnQ/LmNvbmZpZz8uaGVhZGVyRm9vdGVyID8/IHsgaGVhZGVySGVpZ2h0OiAwLCBmb290ZXJIZWlnaHQ6IDAgfTtcbiAgfVxuXG4gIC8vIFRoZSBtYXN0ZXIgZHJhd3MgdW5sZXNzIHRoZSBwYWdlIGhpZGVzIGl0IOKAlCBhbmQgYWx3YXlzIHdoaWxlIGl0IGlzIHRoZVxuICAvLyBsYXllciBiZWluZyBlZGl0ZWQsIHNvIGEgcGFnZSB0aGF0IGhpZGVzIGl0IGNhbiBzdGlsbCBiZSB1c2VkIHRvIGVkaXQgaXQuXG4gIHB1YmxpYyBnZXQgaXNNYXN0ZXJTaG93bigpOiBib29sZWFuIHtcbiAgICByZXR1cm4gdGhpcy5tYXN0ZXJNb2RlKCkgfHwgIXRoaXMuYWN0aXZlUGFnZT8ubWFzdGVySGlkZGVuO1xuICB9XG5cbiAgLy8gV2hpY2ggbGF5ZXIgdGhlIGVkaXQgZ2VzdHVyZXMgcmVhY2guXG4gIHB1YmxpYyBnZXQgaXNQYWdlRWRpdGluZygpOiBib29sZWFuIHtcbiAgICByZXR1cm4gdGhpcy5lZGl0TW9kZSAmJiAhdGhpcy5tYXN0ZXJNb2RlKCk7XG4gIH1cblxuICBwdWJsaWMgZ2V0IGlzTWFzdGVyRWRpdGluZygpOiBib29sZWFuIHtcbiAgICByZXR1cm4gdGhpcy5lZGl0TW9kZSAmJiB0aGlzLm1hc3Rlck1vZGUoKTtcbiAgfVxuXG4gIHB1YmxpYyB0b2dnbGVNYXN0ZXJNb2RlKCk6IHZvaWQge1xuICAgIHRoaXMubWFzdGVyTW9kZS51cGRhdGUoKHZhbHVlKSA9PiAhdmFsdWUpO1xuICAgIHRoaXMuc2VsZWN0ZWRDb21wb25lbnRJZC5zZXQobnVsbCk7XG4gIH1cblxuICAvLyBEcm9wIGEgdGV4dCBibG9jayB3aGVyZSBpdCB3aWxsIGJlIGZvdW5kOiBpbnRvIHRoZSBmb290ZXIgKG9yIGhlYWRlcikgYmFuZFxuICAvLyB3aGlsZSBlZGl0aW5nIHRoZSBoZWFkZXIgYW5kIGZvb3RlciwgYmVsb3cgdGhlIGhlYWRlciBiYW5kIG9uIGEgcGFnZS4gVGhlXG4gIC8vIGhvc3QgcmUtZmV0Y2hlcyB0aGUgcmVwb3J0IGFuZCBpdCBhcHBlYXJzOyBkb3VibGUtcHJlc3Mgb3BlbnMgaXRzIGVkaXRvci5cbiAgcHVibGljIGFkZFRleHQoKTogdm9pZCB7XG4gICAgaWYgKCF0aGlzLnJlcG9ydCkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIGNvbnN0IHsgaGVhZGVySGVpZ2h0LCBmb290ZXJIZWlnaHQgfSA9IHRoaXMuYmFuZHM7XG4gICAgY29uc3QgcGFnZVdpZHRoID0gdGhpcy5yZXBvcnQucGFnZVdpZHRoO1xuICAgIGNvbnN0IHBhZ2VIZWlnaHQgPSB0aGlzLnJlcG9ydC5wYWdlSGVpZ2h0O1xuICAgIGNvbnN0IGlzTWFzdGVyID0gdGhpcy5tYXN0ZXJNb2RlKCk7XG5cbiAgICBsZXQgZ2VvbWV0cnkgPSB7IHg6IDAuNSwgeTogaGVhZGVySGVpZ2h0ICsgMC41LCB3OiBNYXRoLm1pbig1LCBwYWdlV2lkdGggLSAxKSwgaDogMC44IH07XG4gICAgaWYgKGlzTWFzdGVyKSB7XG4gICAgICBjb25zdCBiYW5kSGVpZ2h0ID0gZm9vdGVySGVpZ2h0IHx8IGhlYWRlckhlaWdodCB8fCAwLjU7XG4gICAgICBjb25zdCB5ID0gZm9vdGVySGVpZ2h0XG4gICAgICAgID8gcGFnZUhlaWdodCAtIGZvb3RlckhlaWdodFxuICAgICAgICA6IChoZWFkZXJIZWlnaHQgPyAwIDogcGFnZUhlaWdodCAtIGJhbmRIZWlnaHQpO1xuICAgICAgZ2VvbWV0cnkgPSB7IHg6IDAuNSwgeTogeSArIDAuMDUsIHc6IE1hdGgubWluKDQsIHBhZ2VXaWR0aCAtIDEpLCBoOiBNYXRoLm1heCgwLjMsIGJhbmRIZWlnaHQgLSAwLjEpIH07XG4gICAgfVxuXG4gICAgdGhpcy5fcmVwb3J0RGF0YS5hZGRUZXh0KHRoaXMucmVwb3J0LmlkLCB7XG4gICAgICAuLi5nZW9tZXRyeSxcbiAgICAgIHBhZ2VJZDogaXNNYXN0ZXIgPyB1bmRlZmluZWQgOiB0aGlzLmFjdGl2ZVBhZ2U/LmlkLFxuICAgIH0pXG4gICAgICAucGlwZSh0YWtlVW50aWxEZXN0cm95ZWQodGhpcy5fZGVzdHJveVJlZikpXG4gICAgICAuc3Vic2NyaWJlKCgpID0+IHRoaXMucmVwb3J0Q2hhbmdlZC5lbWl0KCkpO1xuICB9XG5cbiAgLy8gQSB0ZXh0IGJsb2NrIGRlbGV0ZWQgaXRzZWxmIGZyb20gaXRzIG1lbnU6IGRyb3AgaXQgZnJvbSB3aGljaGV2ZXIgbGF5ZXIgaXRcbiAgLy8gd2FzIG9uIHdpdGhvdXQgcmUtZmV0Y2hpbmcgdGhlIHJlcG9ydC4gVGhhdCBjb3ZlcnMgdGhlIGJsb2NrIGFsb25lOiB0aGVcbiAgLy8gZGVsZXRlIGFsc28gdGFrZXMgdGhlIHZhbHVlcyBvbmx5IGl0IHNob3dlZCwgd2hpY2ggY29tZSBiYWNrIGFzXG4gIC8vIHZhbHVlc1JlbW92ZWQsIGFuZCB0aGF0IGFza3MgdGhlIGhvc3QgdG8gcmVsb2FkIHRoZSByZXBvcnQuXG4gIHB1YmxpYyBvbkNvbXBvbmVudFJlbW92ZWQoY29tcG9uZW50SWQ6IG51bWJlcik6IHZvaWQge1xuICAgIGNvbnN0IGxheWVycyA9IFt0aGlzLmFjdGl2ZVBhZ2U/LmNvbXBvbmVudHMsIHRoaXMucmVwb3J0Py5tYXN0ZXI/LmNvbXBvbmVudHNdO1xuICAgIGZvciAoY29uc3QgY29tcG9uZW50cyBvZiBsYXllcnMpIHtcbiAgICAgIGNvbnN0IGluZGV4ID0gY29tcG9uZW50cz8uZmluZEluZGV4KChjb21wb25lbnQpID0+IGNvbXBvbmVudC5pZCA9PT0gY29tcG9uZW50SWQpID8/IC0xO1xuICAgICAgaWYgKGluZGV4ID4gLTEpIHtcbiAgICAgICAgY29tcG9uZW50cy5zcGxpY2UoaW5kZXgsIDEpO1xuICAgICAgfVxuICAgIH1cblxuICAgIHRoaXMuc2VsZWN0ZWRDb21wb25lbnRJZC5zZXQobnVsbCk7XG4gICAgdGhpcy5wYWdlcy5zZXQodGhpcy5wYWdlcygpKTtcbiAgICB0aGlzLl9yZXBvcnQuc2V0KHRoaXMucmVwb3J0KTtcbiAgICB0aGlzLl9tZXNzYWdlLnN1Y2Nlc3MoJ0RlbGV0ZWQgdGV4dCcpO1xuICB9XG5cbiAgLy8gQSB0ZXh0IGJsb2NrJ3MgaHRtbCB3YXMgc2F2ZWQuIFNhdmluZyBuZXZlciBkZWxldGVzIGEgdmFsdWUsIGJ1dCBpdCBjYW5cbiAgLy8gc2hvdyBvbmUgdGhlIGxheWVyIGhhcyBubyBudW1iZXIgZm9yOiBhIGNoaXAgcGFzdGVkIGJhY2sgZnJvbSBhIHZhbHVlIG5vXG4gIC8vIHRleHQgc2hvd2VkLCB3aGljaCB0aGUgc2VydmVyIGRpZCBub3QgcmVhZC4gSXRzIGxheWVyIGlzIHJlYWQgYWdhaW4gc28gdGhlXG4gIC8vIG51bWJlciBjb21lcyBpbjsgYW4gZWRpdCB0aGF0IHNob3dzIG9ubHkgdmFsdWVzIGFscmVhZHkgcmVhZCBhc2tzIG5vdGhpbmcuXG4gIHB1YmxpYyBvblRleHRTYXZlZCh0ZXh0OiBSZXBvcnRDb21wb25lbnQsIGh0bWw6IHN0cmluZyk6IHZvaWQge1xuICAgIGNvbnN0IGlzTWFzdGVyID0gdGhpcy5faXNNYXN0ZXJDb21wb25lbnQodGV4dCk7XG4gICAgY29uc3QgbGF5ZXIgPSBpc01hc3RlciA/IHRoaXMuX21hc3RlclZhbHVlcyA6IHRoaXMuX3BhZ2VWYWx1ZXM7XG4gICAgY29uc3QgbGF5ZXJJZCA9IGlzTWFzdGVyID8gKHRoaXMucmVwb3J0Py5tYXN0ZXI/LmlkID8/IG51bGwpIDogdGhpcy5hY3RpdmVQYWdlSWQoKTtcbiAgICBjb25zdCByZXN1bHRzID0gbGF5ZXIucmVzdWx0cygpO1xuICAgIGNvbnN0IHJvd3MgPSByZXN1bHRzPy5wYWdlSWQgPT09IGxheWVySWQgPyByZXN1bHRzLnJvd3MgOiBudWxsO1xuICAgIGNvbnN0IHZhbHVlcyA9IGlzTWFzdGVyID8gdGhpcy5fbWFzdGVyVmFsdWVDb21wb25lbnRzKCkgOiB0aGlzLl9wYWdlVmFsdWVDb21wb25lbnRzKCk7XG4gICAgY29uc3QgdW5yZWFkID0gc2hvd25WYWx1ZXModmFsdWVzLCBbeyAuLi50ZXh0LCBjb25maWc6IHsgLi4udGV4dC5jb25maWcsIGh0bWwgfSB9XSlcbiAgICAgIC5zb21lKCh2YWx1ZSkgPT4gIXJvd3M/Lmhhcyh2YWx1ZS5pZCkpO1xuXG4gICAgaWYgKHVucmVhZCkge1xuICAgICAgbGF5ZXIucmVsb2FkJC5uZXh0KCk7XG4gICAgfVxuICB9XG5cbiAgLy8gQSBjaGlwJ3MgZ2Vhcjogb3BlbiB0aGUgc2V0dGluZ3Mgb2YgdGhlIHZhbHVlIGl0IG5hbWVzLCBmcm9tIHRoZSBibG9jaydzXG4gIC8vIG93biBsYXllciwgdGhyb3VnaCB0aGUgc2FtZSBvdXRwdXQgYXMgYW55IGNvbXBvbmVudCdzIHNldHRpbmdzLlxuICBwdWJsaWMgb3BlblZhbHVlU2V0dGluZ3ModGV4dDogUmVwb3J0Q29tcG9uZW50LCBrZXk6IHN0cmluZyk6IHZvaWQge1xuICAgIGNvbnN0IHZhbHVlcyA9IHRoaXMuX2lzTWFzdGVyQ29tcG9uZW50KHRleHQpID8gdGhpcy5fbWFzdGVyVmFsdWVDb21wb25lbnRzKCkgOiB0aGlzLl9wYWdlVmFsdWVDb21wb25lbnRzKCk7XG4gICAgLy8gVGhlIG5ld2VzdCB2YWx1ZSBob2xkcyBhIGtleSwgYXMgaXQgZG9lcyBpbiB0aGUgdGV4dCdzIHRva2Vucy5cbiAgICBjb25zdCB2YWx1ZSA9IHZhbHVlcy5maWx0ZXIoKGNhbmRpZGF0ZSkgPT4gdmFsdWVLZXkoY2FuZGlkYXRlKSA9PT0ga2V5KS5wb3AoKTtcblxuICAgIGlmICh2YWx1ZSkge1xuICAgICAgdGhpcy5jb21wb25lbnRTZXR0aW5ncy5lbWl0KHZhbHVlKTtcbiAgICB9XG4gIH1cblxuICAvLyBTaG93IG9yIGhpZGUgdGhlIGhlYWRlciBhbmQgZm9vdGVyIG9uIG9uZSBwYWdlLCBmcm9tIGl0cyB0YWIncyBrZWJhYi5cbiAgcHVibGljIHRvZ2dsZU1hc3RlckhpZGRlbihwYWdlOiBSZXBvcnRQYWdlKTogdm9pZCB7XG4gICAgY29uc3QgbWFzdGVySGlkZGVuID0gIXBhZ2UubWFzdGVySGlkZGVuO1xuXG4gICAgdGhpcy5fcmVwb3J0RGF0YS51cGRhdGVQYWdlKHRoaXMucmVwb3J0LmlkLCBwYWdlLmlkLCB7IG1hc3RlckhpZGRlbiB9KVxuICAgICAgLnBpcGUodGFrZVVudGlsRGVzdHJveWVkKHRoaXMuX2Rlc3Ryb3lSZWYpKVxuICAgICAgLnN1YnNjcmliZSgoKSA9PiB7XG4gICAgICAgIHBhZ2UubWFzdGVySGlkZGVuID0gbWFzdGVySGlkZGVuO1xuICAgICAgICB0aGlzLnBhZ2VzLnNldCh0aGlzLnBhZ2VzKCkpO1xuICAgICAgICB0aGlzLl9tZXNzYWdlLnN1Y2Nlc3MobWFzdGVySGlkZGVuID8gJ0hlYWRlciAmIGZvb3RlciBoaWRkZW4gb24gdGhpcyBwYWdlJyA6ICdIZWFkZXIgJiBmb290ZXIgc2hvd24gb24gdGhpcyBwYWdlJyk7XG4gICAgICB9KTtcbiAgfVxuXG4gIHB1YmxpYyBzZWxlY3RQYWdlKGluZGV4OiBudW1iZXIpOiB2b2lkIHtcbiAgICB0aGlzLmFjdGl2ZVBhZ2VJbmRleC5zZXQoaW5kZXgpO1xuICAgIHRoaXMuc2VsZWN0ZWRDb21wb25lbnRJZC5zZXQobnVsbCk7XG5cbiAgICAvLyBLZXB0IGluIHN0ZXAgd2l0aCB0aGUgbmdPbkNoYW5nZXMgYW5ub3VuY2VtZW50IHNvIHRoZSB0d28gY2FuJ3QgZGlzYWdyZWVcbiAgICAvLyBhYm91dCB3aGF0IHRoZSBob3N0IHdhcyBsYXN0IHRvbGQuXG4gICAgdGhpcy5fZW1pdHRlZFBhZ2VJZCA9IHRoaXMuYWN0aXZlUGFnZT8uaWQgPz8gbnVsbDtcbiAgICB0aGlzLnBhZ2VDaGFuZ2VkLmVtaXQodGhpcy5fZW1pdHRlZFBhZ2VJZCk7XG4gIH1cblxuICAvLyBBcHBlbmQgYSBibGFuayBwYWdlOyB0aGUgaG9zdCByZS1mZXRjaGVzIHRoZSByZXBvcnQgYW5kIG5nT25DaGFuZ2VzIGxhbmRzXG4gIC8vIHRoZSB2aWV3IG9uIHRoZSBuZXcgKGxhc3QpIHBhZ2UuXG4gIHB1YmxpYyBhZGRQYWdlKCk6IHZvaWQge1xuICAgIGlmICghdGhpcy5yZXBvcnQpIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICB0aGlzLl9yZXBvcnREYXRhLmFkZFBhZ2UodGhpcy5yZXBvcnQuaWQpXG4gICAgICAucGlwZSh0YWtlVW50aWxEZXN0cm95ZWQodGhpcy5fZGVzdHJveVJlZikpXG4gICAgICAuc3Vic2NyaWJlKCgpID0+IHRoaXMucmVwb3J0Q2hhbmdlZC5lbWl0KCkpO1xuICB9XG5cbiAgcHVibGljIHBhZ2VMYWJlbChwYWdlOiBSZXBvcnRQYWdlLCBpbmRleDogbnVtYmVyKTogc3RyaW5nIHtcbiAgICByZXR1cm4gcGFnZS5uYW1lIHx8IGBQYWdlICR7aW5kZXggKyAxfWA7XG4gIH1cblxuICAvLyBSZW5hbWUgZnJvbSB0aGUgdGFiJ3Mga2ViYWIuIFRoZSBwYWdlIGxpc3QgaXMgcGF0Y2hlZCBpbiBwbGFjZSByYXRoZXIgdGhhblxuICAvLyByZS1mZXRjaGluZyB0aGUgcmVwb3J0OiBub3RoaW5nIGVsc2Ugb24gdGhlIGNhbnZhcyBkZXBlbmRzIG9uIGEgcGFnZSdzXG4gIC8vIG5hbWUsIGFuZCBhIHJlLWZldGNoIHdvdWxkIHJlLXJ1biBldmVyeSBjb21wb25lbnQncyBxdWVyeSB0byByZXBhaW50IGFcbiAgLy8gY2hpcCdzIGxhYmVsLlxuICBwdWJsaWMgcmVuYW1lUGFnZShwYWdlOiBSZXBvcnRQYWdlKTogdm9pZCB7XG4gICAgdGhpcy5fcHJvbXB0LmlucHV0KHtcbiAgICAgIHRpdGxlOiAnRWRpdCBQYWdlIE5hbWUnLFxuICAgICAgbGFiZWw6ICdOYW1lJyxcbiAgICAgIGRlZmF1bHQ6IHBhZ2UubmFtZSA/PyAnJyxcbiAgICAgIGNvbW1pdExhYmVsOiAnU2F2ZScsXG4gICAgICByZXF1aXJlZDogdHJ1ZSxcbiAgICB9KVxuICAgICAgLnBpcGUoXG4gICAgICAgIHN3aXRjaE1hcCgobmFtZTogc3RyaW5nKSA9PiB0aGlzLl9yZXBvcnREYXRhXG4gICAgICAgICAgLnVwZGF0ZVBhZ2UodGhpcy5yZXBvcnQuaWQsIHBhZ2UuaWQsIHsgbmFtZSB9KVxuICAgICAgICAgIC5waXBlKG1hcCgoKSA9PiBuYW1lKSkpLFxuICAgICAgICB0YWtlVW50aWxEZXN0cm95ZWQodGhpcy5fZGVzdHJveVJlZiksXG4gICAgICApXG4gICAgICAuc3Vic2NyaWJlKChuYW1lOiBzdHJpbmcpID0+IHtcbiAgICAgICAgcGFnZS5uYW1lID0gbmFtZTtcbiAgICAgICAgdGhpcy5wYWdlcy5zZXQodGhpcy5wYWdlcygpKTtcbiAgICAgICAgdGhpcy5fbWVzc2FnZS5zdWNjZXNzKCdTYXZlZCBwYWdlIG5hbWUnKTtcbiAgICAgIH0pO1xuICB9XG5cbiAgLy8gRGVsZXRlIGZyb20gdGhlIHRhYidzIGtlYmFiLiBUaGUgY29uZmlybSBuYW1lcyB0aGUgcGFnZSBhbmQgc2F5cyB0aGVcbiAgLy8gY29tcG9uZW50cyBnbyB3aXRoIGl0IOKAlCB0aGUgc2VydmVyIHJlZnVzZXMgdGhlIGxhc3QgcGFnZSwgYW5kIHRoYXQgcmVmdXNhbFxuICAvLyBzdXJmYWNlcyBhcyB0aGUgQVBJIGVycm9yIG1lc3NhZ2UgcmF0aGVyIHRoYW4gYmVpbmcgc2Vjb25kLWd1ZXNzZWQgaGVyZS5cbiAgcHVibGljIGRlbGV0ZVBhZ2UocGFnZTogUmVwb3J0UGFnZSk6IHZvaWQge1xuICAgIHRoaXMuX3Byb21wdC5jb25maXJtKHtcbiAgICAgIHRpdGxlOiAnQ29uZmlybScsXG4gICAgICB0ZW1wbGF0ZTogYEFyZSB5b3Ugc3VyZSB5b3Ugd291bGQgbGlrZSB0byBkZWxldGUgXCIke3RoaXMucGFnZUxhYmVsKHBhZ2UsIHRoaXMucGFnZXMoKS5pbmRleE9mKHBhZ2UpKX1cIiBhbmQgZXZlcnl0aGluZyBvbiBpdD9gLFxuICAgIH0pXG4gICAgICAucGlwZShcbiAgICAgICAgc3dpdGNoTWFwKCgpID0+IHRoaXMuX3JlcG9ydERhdGEuZGVsZXRlUGFnZSh0aGlzLnJlcG9ydC5pZCwgcGFnZS5pZCkpLFxuICAgICAgICB0YWtlVW50aWxEZXN0cm95ZWQodGhpcy5fZGVzdHJveVJlZiksXG4gICAgICApXG4gICAgICAuc3Vic2NyaWJlKCgpID0+IHtcbiAgICAgICAgY29uc3QgcGFnZXMgPSB0aGlzLnBhZ2VzKCk7XG4gICAgICAgIGNvbnN0IGluZGV4ID0gcGFnZXMuaW5kZXhPZihwYWdlKTtcbiAgICAgICAgcGFnZXMuc3BsaWNlKGluZGV4LCAxKTtcbiAgICAgICAgdGhpcy5wYWdlcy5zZXQocGFnZXMpO1xuXG4gICAgICAgIC8vIExhbmQgb24gdGhlIG5laWdoYm91ciByYXRoZXIgdGhhbiBzbmFwcGluZyBiYWNrIHRvIHRoZSBmaXJzdCBwYWdlIOKAlFxuICAgICAgICAvLyBkZWxldGluZyBwYWdlIDQgb2YgNiBzaG91bGQgbGVhdmUgeW91IGxvb2tpbmcgYXQgd2hhdCBpcyBub3cgcGFnZSA0LlxuICAgICAgICB0aGlzLmFjdGl2ZVBhZ2VJbmRleC5zZXQoTWF0aC5taW4oaW5kZXgsIHBhZ2VzLmxlbmd0aCAtIDEpKTtcbiAgICAgICAgdGhpcy5fcHJldmlvdXNQYWdlQ291bnQgPSBwYWdlcy5sZW5ndGg7XG4gICAgICAgIHRoaXMuc2VsZWN0ZWRDb21wb25lbnRJZC5zZXQobnVsbCk7XG5cbiAgICAgICAgLy8gVGhlIHBhZ2Ugb24gc2NyZWVuIGp1c3Qgc3RvcHBlZCBleGlzdGluZyDigJQgcmVwb3J0IHRoZSBuZWlnaGJvdXIgd2VcbiAgICAgICAgLy8gbGFuZGVkIG9uLCBzbyB0aGUgaG9zdCdzIHN0YXRlIG5hbWVzIGEgcGFnZSB0aGUgcmVwb3J0IGhhcy5cbiAgICAgICAgdGhpcy5wYWdlQ2hhbmdlZC5lbWl0KHRoaXMuYWN0aXZlUGFnZT8uaWQgPz8gbnVsbCk7XG5cbiAgICAgICAgdGhpcy5fbWVzc2FnZS5zdWNjZXNzKCdEZWxldGVkIHBhZ2UnKTtcbiAgICAgIH0pO1xuICB9XG5cbiAgLy8gQSB0YWIgd2FzIGRyYWdnZWQgdG8gYSBuZXcgc2xvdDogcmVvcmRlciBsb2NhbGx5IHNvIHRoZSBjaGlwcyBzZXR0bGVcbiAgLy8gaW1tZWRpYXRlbHksIGtlZXAgdGhlIHZpZXdlciBvbiB0aGUgcGFnZSB0aGV5IHdlcmUgbG9va2luZyBhdCwgYW5kIHBlcnNpc3RcbiAgLy8gdGhlIHdob2xlIHNlcXVlbmNlIGluIG9uZSBQVVQuXG4gIHB1YmxpYyBvblBhZ2VEcm9wcGVkKGV2ZW50OiBDZGtEcmFnRHJvcDx1bmtub3duPik6IHZvaWQge1xuICAgIGlmIChldmVudC5wcmV2aW91c0luZGV4ID09PSBldmVudC5jdXJyZW50SW5kZXgpIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICBjb25zdCBhY3RpdmVQYWdlID0gdGhpcy5hY3RpdmVQYWdlO1xuICAgIGNvbnN0IHBhZ2VzID0gdGhpcy5wYWdlcygpO1xuXG4gICAgbW92ZUl0ZW1JbkFycmF5KHBhZ2VzLCBldmVudC5wcmV2aW91c0luZGV4LCBldmVudC5jdXJyZW50SW5kZXgpO1xuICAgIHRoaXMucGFnZXMuc2V0KHBhZ2VzKTtcblxuICAgIGNvbnN0IHBvc2l0aW9ucyA9IHBhZ2VzLm1hcCgocGFnZSwgb3JkZXIpID0+IHtcbiAgICAgIHBhZ2Uub3JkZXIgPSBvcmRlcjtcblxuICAgICAgcmV0dXJuIHsgcGFnZUlkOiBwYWdlLmlkLCBvcmRlciB9O1xuICAgIH0pO1xuXG4gICAgaWYgKGFjdGl2ZVBhZ2UpIHtcbiAgICAgIHRoaXMuYWN0aXZlUGFnZUluZGV4LnNldChwYWdlcy5pbmRleE9mKGFjdGl2ZVBhZ2UpKTtcbiAgICB9XG5cbiAgICB0aGlzLl9yZXBvcnREYXRhLnNhdmVQYWdlUG9zaXRpb25zKHRoaXMucmVwb3J0LmlkLCBwb3NpdGlvbnMpXG4gICAgICAucGlwZSh0YWtlVW50aWxEZXN0cm95ZWQodGhpcy5fZGVzdHJveVJlZikpXG4gICAgICAuc3Vic2NyaWJlKCk7XG4gIH1cblxuICAvLyBIYW5kIHByZXNlbnRhdGlvbiBzZXR0aW5ncyAodGl0bGUsIHBhZGRpbmcpIHNhdmVkIGluIHRoZSBzZXR0aW5ncyBkaWFsb2cgdG9cbiAgLy8gdGhlIG9uZSBjb21wb25lbnQgdGhleSBiZWxvbmcgdG8uIE5vdGhpbmcgaGVyZSBmZWVkcyB0aGUgcXVlcnksIHNvIHRoYXRcbiAgLy8gY29tcG9uZW50IHJlcGFpbnRzIGFuZCBldmVyeSBvdGhlciBvbmUgb24gdGhlIHBhZ2UgaXMgbGVmdCBhbG9uZS4gQSB2YWx1ZVxuICAvLyBpcyBuZXZlciBkcmF3bjogaXRzIHRpdGxlIGlzIGl0cyBOYW1lLCB3aGljaCBpdHMgY2hpcHMgYW5kIHRva2VucyByZWFkLlxuICBwdWJsaWMgYXBwbHlDb21wb25lbnRTZXR0aW5ncyhjb21wb25lbnRJZDogbnVtYmVyLCBzZXR0aW5nczogQ29tcG9uZW50U2V0dGluZ3MpOiB2b2lkIHtcbiAgICBjb25zdCByZW5kZXJlZCA9IHRoaXMuX3JlbmRlcmVkQ29tcG9uZW50c1xuICAgICAgLmZpbmQoKGNhbmRpZGF0ZSkgPT4gY2FuZGlkYXRlLmNvbXBvbmVudC5pZCA9PT0gY29tcG9uZW50SWQpO1xuXG4gICAgaWYgKHJlbmRlcmVkKSB7XG4gICAgICByZW5kZXJlZC5hcHBseVNldHRpbmdzKHNldHRpbmdzKTtcblxuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIGNvbnN0IHZhbHVlID0gWy4uLnRoaXMuX3BhZ2VWYWx1ZUNvbXBvbmVudHMoKSwgLi4udGhpcy5fbWFzdGVyVmFsdWVDb21wb25lbnRzKCldXG4gICAgICAuZmluZCgoY2FuZGlkYXRlKSA9PiBjYW5kaWRhdGUuaWQgPT09IGNvbXBvbmVudElkKTtcblxuICAgIC8vIFRoZSBzZXJ2ZXIga2VlcHMgdGhlIG9sZCBOYW1lIGZvciBhIGJsYW5rIG9uZS5cbiAgICBpZiAodmFsdWUgJiYgc2V0dGluZ3MudGl0bGU/LnRyaW0oKSkge1xuICAgICAgdmFsdWUudGl0bGUgPSBzZXR0aW5ncy50aXRsZS50cmltKCk7XG4gICAgICB0aGlzLl92YWx1ZXNSZXZpc2lvbi51cGRhdGUoKHJldmlzaW9uKSA9PiByZXZpc2lvbiArIDEpO1xuICAgIH1cbiAgfVxuXG4gIHB1YmxpYyBzZWxlY3RDb21wb25lbnQoY29tcG9uZW50SWQ6IG51bWJlciB8IG51bGwpOiB2b2lkIHtcbiAgICB0aGlzLnNlbGVjdGVkQ29tcG9uZW50SWQuc2V0KGNvbXBvbmVudElkKTtcbiAgfVxuXG4gIHB1YmxpYyBvbkNhbnZhc1BvaW50ZXJEb3duKCk6IHZvaWQge1xuICAgIC8vIEJhY2tncm91bmQgY2xpY2sgKHBhbiBzdGFydCkgZGVzZWxlY3RzLlxuICAgIGlmICh0aGlzLnNlbGVjdGVkQ29tcG9uZW50SWQoKSAhPT0gbnVsbCkge1xuICAgICAgdGhpcy5zZWxlY3RDb21wb25lbnQobnVsbCk7XG4gICAgfVxuICB9XG5cbiAgLy8gLS0tLS0gem9vbSB0b29sYmFyIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLVxuXG4gIHB1YmxpYyBvblpvb21lZChzY2FsZTogbnVtYmVyKTogdm9pZCB7XG4gICAgdGhpcy56b29tLnNldChzY2FsZSk7XG4gIH1cblxuICBwdWJsaWMgem9vbUluKCk6IHZvaWQge1xuICAgIHRoaXMuem9vbVBhbj8uem9vbUluKCk7XG4gIH1cblxuICBwdWJsaWMgem9vbU91dCgpOiB2b2lkIHtcbiAgICB0aGlzLnpvb21QYW4/Lnpvb21PdXQoKTtcbiAgfVxuXG4gIHB1YmxpYyB6b29tRml0KCk6IHZvaWQge1xuICAgIGNvbnN0IHZpZXdwb3J0ID0gdGhpcy5fdmlld3BvcnQ/Lm5hdGl2ZUVsZW1lbnQ7XG4gICAgaWYgKCF2aWV3cG9ydCB8fCAhdGhpcy5yZXBvcnQ/LnBhZ2VXaWR0aCB8fCAhdGhpcy56b29tUGFuKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgY29uc3QgZml0ID0gTWF0aC5taW4oXG4gICAgICAodmlld3BvcnQuY2xpZW50V2lkdGggLSAzMikgLyAodGhpcy5yZXBvcnQucGFnZVdpZHRoICogUFhfUEVSX0lOQ0gpLFxuICAgICAgKHZpZXdwb3J0LmNsaWVudEhlaWdodCAtIDMyKSAvICh0aGlzLnJlcG9ydC5wYWdlSGVpZ2h0ICogUFhfUEVSX0lOQ0gpLFxuICAgICk7XG5cbiAgICB0aGlzLnpvb21QYW4uem9vbShNYXRoLm1pbigxLjUsIE1hdGgubWF4KDAuMSwgZml0KSkpO1xuICAgIHRoaXMuem9vbVBhbi5tb3ZlKDE2LCAxNik7XG4gICAgdGhpcy5fZml0dGVkID0gdHJ1ZTtcbiAgfVxuXG4gIHB1YmxpYyB6b29tQWN0dWFsKCk6IHZvaWQge1xuICAgIHRoaXMuem9vbVBhbj8uem9vbSgxKTtcbiAgfVxuXG4gIC8vIC0tLS0tIHBlcnNpc3RlbmNlIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cblxuICAvLyBBIGRyYWcvcmVzaXplIGxhbmRlZCDigJQgb25lIFBVVCBwZXIgZ2VzdHVyZS5cbiAgcHVibGljIG9uUG9zaXRpb25DaGFuZ2VkKHBvc2l0aW9uOiB7IGNvbXBvbmVudElkOiBudW1iZXIgfSAmIFJlY29yZDxzdHJpbmcsIG51bWJlcj4pOiB2b2lkIHtcbiAgICB0aGlzLl9jbGVhckd1aWRlcygpO1xuICAgIHRoaXMuX3JlcG9ydERhdGEuc2F2ZVBvc2l0aW9ucyh0aGlzLnJlcG9ydC5pZCwgW3Bvc2l0aW9uIGFzIGFueV0pXG4gICAgICAucGlwZSh0YWtlVW50aWxEZXN0cm95ZWQodGhpcy5fZGVzdHJveVJlZikpXG4gICAgICAuc3Vic2NyaWJlKCk7XG4gIH1cblxuICAvLyAtLS0tLSB2YWx1ZXMgLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG5cbiAgLy8gRWFjaCBsYXllciByZWFkcyBpdHMgdmFsdWVzJyBudW1iZXJzIG9uIGl0cyBvd24gc3RyZWFtOiBhZ2FpbiB3aGVuIGFcbiAgLy8gcmVwb3J0IHJlbG9hZCBjaGFuZ2VzIHdoYXQgdGhleSBkZXBlbmQgb24gKG5nT25DaGFuZ2VzKSwgd2hlbiBhIHNhdmVkIHRleHRcbiAgLy8gc2hvd3MgYSB2YWx1ZSBpdCBoYXMgbm8gbnVtYmVyIGZvciwgd2hlbiBhIGZpbHRlciBhbnkgb2YgaXRzIHZhbHVlc1xuICAvLyBmb2xsb3dzIGNoYW5nZXMgKGFuIG9wZXJhbmQgbm8gdGV4dCBzaG93cyBtb3ZlcyB0aGUgZm9ybXVsYSB0aGF0IHJlYWRzXG4gIC8vIGl0KSwgYW5kIHdoZW4gaXQgY29tZXMgb24gc2NyZWVuIOKAlCB0aGUgYWN0aXZlIHBhZ2Ugd2hlbiBhbm90aGVyIHBhZ2UgZG9lcyxcbiAgLy8gdGhlIG1hc3RlciB3aGVuIGEgcGFnZSBzaG93cyBpdCBvciBpdCBpcyBlZGl0ZWQuXG4gIHByaXZhdGUgX2luaXQoKTogdm9pZCB7XG4gICAgdGhpcy5fd2F0Y2hWYWx1ZXModGhpcy5fcGFnZVZhbHVlcywgdG9PYnNlcnZhYmxlKHRoaXMuYWN0aXZlUGFnZUlkKSk7XG4gICAgdGhpcy5fd2F0Y2hWYWx1ZXModGhpcy5fbWFzdGVyVmFsdWVzLCB0b09ic2VydmFibGUodGhpcy5fbWFzdGVyTmVlZGVkKSk7XG4gIH1cblxuICBwcml2YXRlIF92YWx1ZUxheWVyKHNvdXJjZTogKCkgPT4gUmVwb3J0UGFnZSB8IFJlcG9ydE1hc3RlciB8IG51bGwpOiBWYWx1ZUxheWVyIHtcbiAgICByZXR1cm4ge1xuICAgICAgc291cmNlLFxuICAgICAgcmVsb2FkJDogbmV3IFN1YmplY3Q8dm9pZD4oKSxcbiAgICAgIHJlc3VsdHM6IHNpZ25hbDxMYXllclZhbHVlcyB8IG51bGw+KG51bGwpLFxuICAgICAgcGVuZGluZzogc2lnbmFsPExheWVyVmFsdWVzUmVxdWVzdCB8IG51bGw+KG51bGwpLFxuICAgIH07XG4gIH1cblxuICAvLyBUcmlnZ2VycyBsYW5kaW5nIHRvZ2V0aGVyIChhIHJlbG9hZCB0aGF0IGFsc28gY2hhbmdlcyB0aGUgcGFnZSkgbWFrZSBvbmVcbiAgLy8gcmVxdWVzdCwgYW5kIGEgbmV3ZXIgcmVxdWVzdCBkcm9wcyB0aGUgb25lIHN0aWxsIGluIGZsaWdodC4gQW55IG90aGVyXG4gIC8vIGNoYW5nZSBvZiB0aGUgc2NyZWVuJ3Mgc3RhdGUgKGNoYW5nZXMpIGFza3MgYWdhaW4gb25seSB3aGVuIGl0IG1vdmVkXG4gIC8vIHRoZSByZXF1ZXN0OiBhIHZpZXcgYXBwbGllZCBvciB0aGUgYmFyIHJlc2V0IChzdGF0ZVZlcnNpb24gbW92ZXMgb25cbiAgLy8gZWFjaCksIHRoZSBtYXRjaCBjaGFuZ2VkLCBvciwgd2hpbGUgdGhlIGdyb3VwcyBtYXRjaCAnYW55JywgYSBncm91cCB0aGVcbiAgLy8gdmFsdWVzIGhhdmUgbm8gbWVtYmVyIG9mIHRvb2sgb3IgbG9zdCBhIHZhbHVlLlxuICBwcml2YXRlIF93YXRjaFZhbHVlcyhsYXllcjogVmFsdWVMYXllciwgb25TY3JlZW4kOiBPYnNlcnZhYmxlPHVua25vd24+KTogdm9pZCB7XG4gICAgbWVyZ2UoXG4gICAgICBsYXllci5yZWxvYWQkLFxuICAgICAgb25TY3JlZW4kLFxuICAgICAgdGhpcy5fZmlsdGVyU3RhdGUuY2hhbmdlc0ZvckFueSgoKSA9PiBsYXllci5zb3VyY2UoKT8udmFsdWVzID8/IFtdKS5waXBlKGRlYm91bmNlVGltZSgzMDApKSxcbiAgICAgIHRoaXMuX2ZpbHRlclN0YXRlLmNoYW5nZXMoKS5waXBlKFxuICAgICAgICBkZWJvdW5jZVRpbWUoMzAwKSxcbiAgICAgICAgcnhGaWx0ZXIoKCkgPT4gdGhpcy5fcmVxdWVzdE1vdmVkKGxheWVyKSksXG4gICAgICApLFxuICAgIClcbiAgICAgIC5waXBlKFxuICAgICAgICBkZWJvdW5jZVRpbWUoMCksXG4gICAgICAgIG1hcCgoKSA9PiB0aGlzLl9sYXllclJlcXVlc3QobGF5ZXIuc291cmNlKCkpKSxcbiAgICAgICAgdGFwKChyZXF1ZXN0KSA9PiBsYXllci5wZW5kaW5nLnNldChyZXF1ZXN0KSksXG4gICAgICAgIHN3aXRjaE1hcCgocmVxdWVzdCkgPT4gdGhpcy5fbG9hZFZhbHVlcyhyZXF1ZXN0KSksXG4gICAgICAgIHRhcCgobG9hZGVkKSA9PiB7XG4gICAgICAgICAgbGF5ZXIucmVzdWx0cy5zZXQobG9hZGVkKTtcbiAgICAgICAgICBsYXllci5wZW5kaW5nLnNldChudWxsKTtcbiAgICAgICAgfSksXG4gICAgICAgIHRha2VVbnRpbERlc3Ryb3llZCh0aGlzLl9kZXN0cm95UmVmKSxcbiAgICAgIClcbiAgICAgIC5zdWJzY3JpYmUoKTtcbiAgfVxuXG4gIC8vIEEgcmVsb2FkIG9mIHRoZSByZXBvcnQgcmVhZHMgYSBsYXllcidzIG51bWJlcnMgYWdhaW4gb25seSB3aGVuIHNvbWV0aGluZ1xuICAvLyB0aGV5IGRlcGVuZCBvbiBtb3ZlZDogYSByZW5hbWUsIG9yIGFuIGVkaXQgdG8gYSB0aWxlLCBoYW5kcyBvdmVyIGEgbmV3XG4gIC8vIHJlcG9ydCBhbmQgbGVhdmVzIGV2ZXJ5IG51bWJlciBhcyBpdCB3YXMuIENvbXBhcmVkIHdpdGggdGhlIHJlcXVlc3Qgb24gaXRzXG4gIC8vIHdheSwgZWxzZSB0aGUgb25lIHdob3NlIG51bWJlcnMgYXJlIG9uIHNjcmVlbi5cbiAgcHJpdmF0ZSBfcmVsb2FkSWZDaGFuZ2VkKGxheWVyOiBWYWx1ZUxheWVyKTogdm9pZCB7XG4gICAgaWYgKHRoaXMuX3JlcXVlc3RNb3ZlZChsYXllcikpIHtcbiAgICAgIGxheWVyLnJlbG9hZCQubmV4dCgpO1xuICAgIH1cbiAgfVxuXG4gIC8vIFdoZXRoZXIgdGhlIGxheWVyJ3MgcmVxdWVzdCBub3cgZGlmZmVycyBmcm9tIHRoZSBvbmUgb24gaXRzIHdheSwgZWxzZVxuICAvLyB0aGUgb25lIHdob3NlIG51bWJlcnMgYXJlIG9uIHNjcmVlbi5cbiAgcHJpdmF0ZSBfcmVxdWVzdE1vdmVkKGxheWVyOiBWYWx1ZUxheWVyKTogYm9vbGVhbiB7XG4gICAgY29uc3QgbGFzdCA9IGxheWVyLnBlbmRpbmcoKSA/PyBsYXllci5yZXN1bHRzKCk7XG5cbiAgICByZXR1cm4gdGhpcy5fbGF5ZXJSZXF1ZXN0KGxheWVyLnNvdXJjZSgpKS5zaWduYXR1cmUgIT09IGxhc3Q/LnNpZ25hdHVyZTtcbiAgfVxuXG4gIC8vIFJlYWQgd2hlbiB0aGUgcmVxdWVzdCBpcyBzZW50LCBub3Qgd2hlbiBpdCB3YXMgYXNrZWQgZm9yOiBhbiBlZGl0IG1heSBoYXZlXG4gIC8vIGp1c3QgY2hhbmdlZCB3aGljaCB2YWx1ZXMgdGhlIGxheWVyJ3MgdGV4dCBzaG93cy4gVGhlIGZpbHRlciB2YWx1ZXMgb2ZcbiAgLy8gZXZlcnkgdmFsdWUgb24gdGhlIGxheWVyIGdvIG91dCwgc2hvd24gb3Igbm90OiB0aGUgc2VydmVyIGRlY2lkZXMgd2hpY2hcbiAgLy8gdmFsdWVzIGl0IHJlYWRzLCBhbmQgYXBwbGllcyB0byBlYWNoIG9ubHkgdGhlIGVudHJpZXMgbmFtaW5nIGl0cyBvd25cbiAgLy8gZmlsdGVycywgc28gYW4gb3BlcmFuZCBvbmx5IGEgZm9ybXVsYSByZWFkcyBpcyBmaWx0ZXJlZCBhcyBpZiBpdCB3ZXJlXG4gIC8vIHNob3duLiBBIHZhbHVlJ3MgTmFtZSBpcyBsZWZ0IG91dCBvZiB0aGUgc2lnbmF0dXJlOiBhIHJlbmFtZSBtb3ZlcyBub1xuICAvLyBudW1iZXIuIFdoaWxlIHRoZSBncm91cHMgbWF0Y2ggJ2FueScsIHRoZSByZXF1ZXN0IGxpc3RzIHRoZSBncm91cHMgdGhhdFxuICAvLyBjb21iaW5lLCBieSB0aGUgdGlsZSBydWxlICh2YWx1ZXNNYXRjaEFueUdyb3VwSWRzKTogYSBoZWFkZXIgb3IgZm9vdGVyXG4gIC8vIHZhbHVlJ3MgYXJlIHRoZSBwYWdlIG9uIHNjcmVlbidzLlxuICBwcml2YXRlIF9sYXllclJlcXVlc3QobGF5ZXI6IFJlcG9ydFBhZ2UgfCBSZXBvcnRNYXN0ZXIgfCBudWxsKTogTGF5ZXJWYWx1ZXNSZXF1ZXN0IHtcbiAgICBjb25zdCBwYWdlSWQgPSBsYXllcj8uaWQgPz8gbnVsbDtcbiAgICBjb25zdCB2YWx1ZXMgPSBsYXllcj8udmFsdWVzID8/IFtdO1xuICAgIGNvbnN0IHNob3duID0gdGhpcy5fc2hvd25WYWx1ZXMobGF5ZXIpO1xuICAgIGNvbnN0IGZpbHRlcnMgPSB2YWx1ZXMuZmxhdE1hcCgoY29tcG9uZW50KSA9PiB0aGlzLl9maWx0ZXJTdGF0ZS5yZXNvbHZlRm9yQ29tcG9uZW50KGNvbXBvbmVudCkpO1xuICAgIGNvbnN0IG1hdGNoQW55R3JvdXBJZHMgPSB2YWx1ZXMubGVuZ3RoXG4gICAgICA/IHZhbHVlc01hdGNoQW55R3JvdXBJZHModGhpcy5yZXBvcnQsIHBhZ2VJZCwgdGhpcy5fZmlsdGVyU3RhdGUuc25hcHNob3QoKSlcbiAgICAgIDogW107XG5cbiAgICByZXR1cm4ge1xuICAgICAgcGFnZUlkLFxuICAgICAgc2hvd24sXG4gICAgICBmaWx0ZXJzLFxuICAgICAgbWF0Y2hBbnlHcm91cElkcyxcbiAgICAgIHNpZ25hdHVyZTogSlNPTi5zdHJpbmdpZnkoW1xuICAgICAgICBwYWdlSWQsXG4gICAgICAgIHNob3duLm1hcCgodmFsdWUpID0+IHZhbHVlLmlkKSxcbiAgICAgICAgdmFsdWVzLm1hcCgodmFsdWUpID0+ICh7IC4uLnZhbHVlLCB0aXRsZTogbnVsbCB9KSksXG4gICAgICAgIGZpbHRlcnMsXG4gICAgICAgIG1hdGNoQW55R3JvdXBJZHMsXG4gICAgICBdKSxcbiAgICB9O1xuICB9XG5cbiAgLy8gVGhlIHZhbHVlcyBhIGxheWVyJ3MgdGV4dCBzaG93cy4gSXRzIHJlcXVlc3QgYWxzbyByZWFkcyB0aGUgb3BlcmFuZHMgb2ZcbiAgLy8gdGhlIGZvcm11bGFzIGFtb25nIHRoZW0sIGJ1dCBvbmx5IHRoZSBzaG93biBvbmVzIHJlYWQgYXMgbG9hZGluZyB3aGlsZSBpdFxuICAvLyBpcyBvbiBpdHMgd2F5LCBhbmQgYSBsYXllciB0aGF0IHNob3dzIG5vbmUgYXNrcyBmb3Igbm90aGluZy5cbiAgcHJpdmF0ZSBfc2hvd25WYWx1ZXMobGF5ZXI6IFJlcG9ydFBhZ2UgfCBSZXBvcnRNYXN0ZXIgfCBudWxsKTogUmVwb3J0Q29tcG9uZW50W10ge1xuICAgIGNvbnN0IHRleHRzID0gKGxheWVyPy5jb21wb25lbnRzID8/IFtdKS5maWx0ZXIoKGNvbXBvbmVudCkgPT4gY29tcG9uZW50LnR5cGUgPT09ICd0ZXh0Jyk7XG5cbiAgICByZXR1cm4gc2hvd25WYWx1ZXMobGF5ZXI/LnZhbHVlcyA/PyBbXSwgdGV4dHMpO1xuICB9XG5cbiAgLy8gT25lIGxheWVyJ3MgbnVtYmVycywgYnkgdmFsdWUgaWQuIEEgbGF5ZXIgd2hvc2UgdGV4dCBzaG93cyBubyB2YWx1ZSBhc2tzXG4gIC8vIGZvciBub3RoaW5nLiBBIGZhaWxlZCByZXF1ZXN0IHJlYWRzIGFzIG5vIG51bWJlcnMgKGVhY2ggdmFsdWUgYW4gZW0gZGFzaClcbiAgLy8gcmF0aGVyIHRoYW4gYW4gZXJyb3IgZGlhbG9nOiB0aGUgd29yZHMgYXJvdW5kIHRoZW0gc3RpbGwgcmVhZC5cbiAgcHJpdmF0ZSBfbG9hZFZhbHVlcyh7XG4gICAgcGFnZUlkLCBzaG93biwgZmlsdGVycywgbWF0Y2hBbnlHcm91cElkcywgc2lnbmF0dXJlLFxuICB9OiBMYXllclZhbHVlc1JlcXVlc3QpOiBPYnNlcnZhYmxlPExheWVyVmFsdWVzPiB7XG4gICAgY29uc3QgbG9hZGVkID0gKHJvd3M6IFJlcG9ydFBhZ2VWYWx1ZVtdKTogTGF5ZXJWYWx1ZXMgPT4gKHtcbiAgICAgIHBhZ2VJZCxcbiAgICAgIHNpZ25hdHVyZSxcbiAgICAgIHJvd3M6IG5ldyBNYXAocm93cy5tYXAoKHJvdykgPT4gW3Jvdy5pZCwgcm93XSkpLFxuICAgIH0pO1xuXG4gICAgaWYgKHBhZ2VJZCA9PT0gbnVsbCB8fCAhc2hvd24ubGVuZ3RoKSB7XG4gICAgICByZXR1cm4gb2YobG9hZGVkKFtdKSk7XG4gICAgfVxuXG4gICAgcmV0dXJuIHRoaXMuX3JlcG9ydERhdGEucGFnZVZhbHVlcyh0aGlzLnJlcG9ydC5pZCwgcGFnZUlkLCBmaWx0ZXJzLCBmYWxzZSwgeyBoYW5kbGVyczogZmFsc2UgfSwgbWF0Y2hBbnlHcm91cElkcylcbiAgICAgIC5waXBlKFxuICAgICAgICBtYXAoKHJvd3MpID0+IGxvYWRlZChyb3dzID8/IFtdKSksXG4gICAgICAgIGNhdGNoRXJyb3IoKCkgPT4gb2YobG9hZGVkKFtdKSkpLFxuICAgICAgKTtcbiAgfVxuXG4gIC8vIFRoZSB0b2tlbnMgb2Ygb25lIGxheWVyJ3MgYmxvY2tzLiBOdW1iZXJzIHJlYWQgZm9yIGFub3RoZXIgcGFnZSBhcmUgbm90XG4gIC8vIHRoaXMgb25lJ3MsIHNvIHVudGlsIGl0cyBvd24gYXJyaXZlIGl0cyB2YWx1ZXMgcmVhZCBhcyBsb2FkaW5nOyBzbyBkb2VzIGFcbiAgLy8gdmFsdWUgdGhlIHJlcXVlc3Qgb24gaXRzIHdheSBhc2tzIGZvciwgdW50aWwgaXQgbGFuZHMuXG4gIHByaXZhdGUgX3Rva2VuQ29udGV4dChcbiAgICB2YWx1ZXM6IFJlcG9ydENvbXBvbmVudFtdLFxuICAgIGxheWVyOiBWYWx1ZUxheWVyLFxuICAgIHZhbHVlUGFnZUlkOiBudW1iZXIgfCBudWxsLFxuICApOiBUZXh0VG9rZW5Db250ZXh0IHtcbiAgICAvLyBSZWFkIHNvIGEgcmVuYW1lLCBwYXRjaGVkIGludG8gdGhlIHZhbHVlIGluIHBsYWNlLCByZWNvbXB1dGVzIHRoZSBuYW1lcy5cbiAgICB0aGlzLl92YWx1ZXNSZXZpc2lvbigpO1xuXG4gICAgY29uc3QgaW5kZXggPSB0aGlzLmFjdGl2ZVBhZ2VJbmRleCgpO1xuICAgIGNvbnN0IHBhZ2UgPSB0aGlzLnBhZ2VzKClbaW5kZXhdO1xuICAgIGNvbnN0IHJlc3VsdHMgPSBsYXllci5yZXN1bHRzKCk7XG4gICAgY29uc3QgcGVuZGluZyA9IGxheWVyLnBlbmRpbmcoKTtcblxuICAgIHJldHVybiB7XG4gICAgICBwYWdlTnVtYmVyOiBpbmRleCArIDEsXG4gICAgICBwYWdlTmFtZTogcGFnZSA/IHRoaXMucGFnZUxhYmVsKHBhZ2UsIGluZGV4KSA6ICcnLFxuICAgICAgcmVwb3J0TmFtZTogdGhpcy5fcmVwb3J0KCk/Lm5hbWUgPz8gJycsXG4gICAgICB2YWx1ZXM6IHRleHRWYWx1ZXMoXG4gICAgICAgIHZhbHVlcyxcbiAgICAgICAgcmVzdWx0cz8ucGFnZUlkID09PSB2YWx1ZVBhZ2VJZCA/IHJlc3VsdHMgOiBudWxsLFxuICAgICAgICB0aGlzLl9maWx0ZXJTdGF0ZS5mb3JtYXRDb250ZXh0KCksXG4gICAgICAgIG5ldyBTZXQocGVuZGluZz8ucGFnZUlkID09PSB2YWx1ZVBhZ2VJZCA/IHBlbmRpbmcuc2hvd24ubWFwKCh2YWx1ZSkgPT4gdmFsdWUuaWQpIDogW10pLFxuICAgICAgKSxcbiAgICAgIHZhbHVlUGFnZUlkLFxuICAgIH07XG4gIH1cblxuICAvLyBUYWtlIGEgZGVsZXRlZCB2YWx1ZSdzIGNoaXBzIG91dCBvZiBhbiBvcGVuIGVkaXRvci4gU2F2aW5nIGh0bWwgbmV2ZXJcbiAgLy8gZGVsZXRlcyBhIHZhbHVlLCBzbyBhIGtleSBsZWF2ZXMgaXRzIGxheWVyIG9ubHkgd2hlbiB0aGUgdmFsdWUgaXMgZGVsZXRlZFxuICAvLyAoaXRzIGRpYWxvZywgdGhlIGFzc2lzdGFudCksIHdoZW4gYSB0ZXh0IGRlbGV0ZSBvciBhbiBhc3Npc3RhbnQgd3JpdGVcbiAgLy8gc3dlZXBzIHRoZSBwYWdlJ3MgdW51c2VkIHZhbHVlcywgb3Igd2l0aCBpdHMgcGFnZS4gSG9zdHMgcmVsb2FkIHRoZSByZXBvcnRcbiAgLy8gYWZ0ZXIgZWFjaCwgYW5kIHRoaXMgaXMgd2hhdCBmb2xsb3dzIHRoYXQgcmVsb2FkIGludG8gdGhlIGVkaXRvci4gT25seSB0aGVcbiAgLy8gbGF5ZXJzIG9uIHNjcmVlbiBoYXZlIHJlbmRlcmVkIGJsb2Nrczsgb3RoZXIgcGFnZXMgYXJlIGxlZnQgYWxvbmUuXG4gIHByaXZhdGUgX2Ryb3BSZW1vdmVkVmFsdWVDaGlwcygpOiB2b2lkIHtcbiAgICBjb25zdCBuZXh0ID0gbGF5ZXJWYWx1ZUtleXModGhpcy5yZXBvcnQpO1xuICAgIGNvbnN0IG1hc3RlcklkID0gdGhpcy5yZXBvcnQ/Lm1hc3Rlcj8uaWQgPz8gbnVsbDtcbiAgICBjb25zdCB0ZXh0cyA9ICh0aGlzLl9yZW5kZXJlZENvbXBvbmVudHM/LnRvQXJyYXkoKSA/PyBbXSkuZmlsdGVyKChyZW5kZXJlZCkgPT4gcmVuZGVyZWQuaXNUZXh0KTtcblxuICAgIHRoaXMuX3ZhbHVlS2V5c0J5TGF5ZXIuZm9yRWFjaCgoa2V5cywgbGF5ZXJJZCkgPT4ge1xuICAgICAgY29uc3QgaXNNYXN0ZXIgPSBsYXllcklkID09PSBtYXN0ZXJJZDtcbiAgICAgIGlmICghaXNNYXN0ZXIgJiYgbGF5ZXJJZCAhPT0gdGhpcy5hY3RpdmVQYWdlSWQoKSkge1xuICAgICAgICByZXR1cm47XG4gICAgICB9XG5cbiAgICAgIGNvbnN0IHJlbW92ZWQgPSBbLi4ua2V5c10uZmlsdGVyKChrZXkpID0+ICFuZXh0LmdldChsYXllcklkKT8uaGFzKGtleSkpO1xuICAgICAgdGV4dHNcbiAgICAgICAgLmZpbHRlcigocmVuZGVyZWQpID0+IHRoaXMuX2lzTWFzdGVyQ29tcG9uZW50KHJlbmRlcmVkLmNvbXBvbmVudCkgPT09IGlzTWFzdGVyKVxuICAgICAgICAuZm9yRWFjaCgocmVuZGVyZWQpID0+IHJlbW92ZWQuZm9yRWFjaCgoa2V5KSA9PiByZW5kZXJlZC5yZW1vdmVWYWx1ZShrZXkpKSk7XG4gICAgfSk7XG5cbiAgICB0aGlzLl92YWx1ZUtleXNCeUxheWVyID0gbmV4dDtcbiAgfVxuXG4gIC8vIEhlYWRlciBhbmQgZm9vdGVyIGJsb2NrcyBhcmUgdGhlIG1hc3RlcidzOyBldmVyeSBvdGhlciBibG9jayBpcyB0aGUgcGFnZSdzLlxuICBwcml2YXRlIF9pc01hc3RlckNvbXBvbmVudChjb21wb25lbnQ6IFJlcG9ydENvbXBvbmVudCk6IGJvb2xlYW4ge1xuICAgIHJldHVybiAodGhpcy5yZXBvcnQ/Lm1hc3Rlcj8uY29tcG9uZW50cyA/PyBbXSkuc29tZSgoY2FuZGlkYXRlKSA9PiBjYW5kaWRhdGUuaWQgPT09IGNvbXBvbmVudC5pZCk7XG4gIH1cblxuICAvLyAtLS0tLSBzbWFydCBndWlkZXMgLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG5cbiAgLy8gUGl4ZWwgZmVlbCBvZiB0aGUgc25hcCwgY29udmVydGVkIHRvIGluY2hlcyBhdCB0aGUgY3VycmVudCB6b29tLlxuICBwcml2YXRlIGdldCBfc25hcFRocmVzaG9sZCgpOiBudW1iZXIge1xuICAgIHJldHVybiA4IC8gKFBYX1BFUl9JTkNIICogTWF0aC5tYXgoMC4xLCB0aGlzLnpvb20oKSkpO1xuICB9XG5cbiAgcHJpdmF0ZSBfc25hcE1vdmUoY29tcG9uZW50OiBSZXBvcnRDb21wb25lbnQsIHg6IG51bWJlciwgeTogbnVtYmVyKTogeyB4OiBudW1iZXI7IHk6IG51bWJlciB9IHtcbiAgICBjb25zdCB7IHZlcnRpY2FsLCBob3Jpem9udGFsIH0gPSB0aGlzLl9jYW5kaWRhdGVzKGNvbXBvbmVudCk7XG4gICAgY29uc3QgZ3VpZGVzOiBHdWlkZUxpbmVbXSA9IFtdO1xuXG4gICAgY29uc3Qgc25hcHBlZFggPSB0aGlzLl9zbmFwQXhpcyhcbiAgICAgIFtcbiAgICAgICAgeyBvZmZzZXQ6IDAsIHZhbHVlOiB4IH0sXG4gICAgICAgIHsgb2Zmc2V0OiBjb21wb25lbnQudyAvIDIsIHZhbHVlOiB4ICsgY29tcG9uZW50LncgLyAyIH0sXG4gICAgICAgIHsgb2Zmc2V0OiBjb21wb25lbnQudywgdmFsdWU6IHggKyBjb21wb25lbnQudyB9LFxuICAgICAgXSxcbiAgICAgIHZlcnRpY2FsLFxuICAgICk7XG4gICAgaWYgKHNuYXBwZWRYICE9PSBudWxsKSB7XG4gICAgICB4ID0gc25hcHBlZFguYmFzZTtcbiAgICAgIGd1aWRlcy5wdXNoKHsgb3JpZW50YXRpb246ICd2JywgcG9zaXRpb246IHNuYXBwZWRYLmd1aWRlIH0pO1xuICAgIH1cblxuICAgIGNvbnN0IHNuYXBwZWRZID0gdGhpcy5fc25hcEF4aXMoXG4gICAgICBbXG4gICAgICAgIHsgb2Zmc2V0OiAwLCB2YWx1ZTogeSB9LFxuICAgICAgICB7IG9mZnNldDogY29tcG9uZW50LmggLyAyLCB2YWx1ZTogeSArIGNvbXBvbmVudC5oIC8gMiB9LFxuICAgICAgICB7IG9mZnNldDogY29tcG9uZW50LmgsIHZhbHVlOiB5ICsgY29tcG9uZW50LmggfSxcbiAgICAgIF0sXG4gICAgICBob3Jpem9udGFsLFxuICAgICk7XG4gICAgaWYgKHNuYXBwZWRZICE9PSBudWxsKSB7XG4gICAgICB5ID0gc25hcHBlZFkuYmFzZTtcbiAgICAgIGd1aWRlcy5wdXNoKHsgb3JpZW50YXRpb246ICdoJywgcG9zaXRpb246IHNuYXBwZWRZLmd1aWRlIH0pO1xuICAgIH1cblxuICAgIHRoaXMuX3JlbmRlckd1aWRlcyhndWlkZXMpO1xuXG4gICAgcmV0dXJuIHsgeCwgeSB9O1xuICB9XG5cbiAgcHJpdmF0ZSBfc25hcFJlc2l6ZShcbiAgICBjb21wb25lbnQ6IFJlcG9ydENvbXBvbmVudCxcbiAgICBnZW9tZXRyeTogeyB4OiBudW1iZXI7IHk6IG51bWJlcjsgdzogbnVtYmVyOyBoOiBudW1iZXIgfSxcbiAgICBoYW5kbGU6IHN0cmluZyxcbiAgKTogeyB4OiBudW1iZXI7IHk6IG51bWJlcjsgdzogbnVtYmVyOyBoOiBudW1iZXIgfSB7XG4gICAgY29uc3QgeyB2ZXJ0aWNhbCwgaG9yaXpvbnRhbCB9ID0gdGhpcy5fY2FuZGlkYXRlcyhjb21wb25lbnQpO1xuICAgIGNvbnN0IGd1aWRlczogR3VpZGVMaW5lW10gPSBbXTtcbiAgICBjb25zdCByZXN1bHQgPSB7IC4uLmdlb21ldHJ5IH07XG5cbiAgICAvLyBPbmx5IHRoZSBlZGdlcyB0aGUgaGFuZGxlIG1vdmVzIHBhcnRpY2lwYXRlIGluIHNuYXBwaW5nLlxuICAgIGlmIChoYW5kbGUuaW5jbHVkZXMoJ2UnKSkge1xuICAgICAgY29uc3Qgc25hcHBlZCA9IHRoaXMuX25lYXJlc3QoZ2VvbWV0cnkueCArIGdlb21ldHJ5LncsIHZlcnRpY2FsKTtcbiAgICAgIGlmIChzbmFwcGVkICE9PSBudWxsKSB7XG4gICAgICAgIHJlc3VsdC53ID0gc25hcHBlZCAtIGdlb21ldHJ5Lng7XG4gICAgICAgIGd1aWRlcy5wdXNoKHsgb3JpZW50YXRpb246ICd2JywgcG9zaXRpb246IHNuYXBwZWQgfSk7XG4gICAgICB9XG4gICAgfVxuICAgIGlmIChoYW5kbGUuaW5jbHVkZXMoJ3cnKSkge1xuICAgICAgY29uc3Qgc25hcHBlZCA9IHRoaXMuX25lYXJlc3QoZ2VvbWV0cnkueCwgdmVydGljYWwpO1xuICAgICAgaWYgKHNuYXBwZWQgIT09IG51bGwpIHtcbiAgICAgICAgcmVzdWx0LncgPSBnZW9tZXRyeS54ICsgZ2VvbWV0cnkudyAtIHNuYXBwZWQ7XG4gICAgICAgIHJlc3VsdC54ID0gc25hcHBlZDtcbiAgICAgICAgZ3VpZGVzLnB1c2goeyBvcmllbnRhdGlvbjogJ3YnLCBwb3NpdGlvbjogc25hcHBlZCB9KTtcbiAgICAgIH1cbiAgICB9XG4gICAgaWYgKGhhbmRsZS5pbmNsdWRlcygncycpKSB7XG4gICAgICBjb25zdCBzbmFwcGVkID0gdGhpcy5fbmVhcmVzdChnZW9tZXRyeS55ICsgZ2VvbWV0cnkuaCwgaG9yaXpvbnRhbCk7XG4gICAgICBpZiAoc25hcHBlZCAhPT0gbnVsbCkge1xuICAgICAgICByZXN1bHQuaCA9IHNuYXBwZWQgLSBnZW9tZXRyeS55O1xuICAgICAgICBndWlkZXMucHVzaCh7IG9yaWVudGF0aW9uOiAnaCcsIHBvc2l0aW9uOiBzbmFwcGVkIH0pO1xuICAgICAgfVxuICAgIH1cbiAgICBpZiAoaGFuZGxlLmluY2x1ZGVzKCduJykpIHtcbiAgICAgIGNvbnN0IHNuYXBwZWQgPSB0aGlzLl9uZWFyZXN0KGdlb21ldHJ5LnksIGhvcml6b250YWwpO1xuICAgICAgaWYgKHNuYXBwZWQgIT09IG51bGwpIHtcbiAgICAgICAgcmVzdWx0LmggPSBnZW9tZXRyeS55ICsgZ2VvbWV0cnkuaCAtIHNuYXBwZWQ7XG4gICAgICAgIHJlc3VsdC55ID0gc25hcHBlZDtcbiAgICAgICAgZ3VpZGVzLnB1c2goeyBvcmllbnRhdGlvbjogJ2gnLCBwb3NpdGlvbjogc25hcHBlZCB9KTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICB0aGlzLl9yZW5kZXJHdWlkZXMoZ3VpZGVzKTtcblxuICAgIHJldHVybiByZXN1bHQ7XG4gIH1cblxuICAvLyBBbGlnbm1lbnQgY2FuZGlkYXRlczogdGhlIHBhZ2UncyBlZGdlcyArIGNlbnRlciwgdGhlIGhlYWRlci9mb290ZXIgYmFuZFxuICAvLyBsaW5lcywgYW5kIGV2ZXJ5IHNpYmxpbmcncyBlZGdlcyArIGNlbnRlcnMg4oCUIHNpYmxpbmdzIG9uIHRoZSBTQU1FIGxheWVyLFxuICAvLyBzaW5jZSBhIHBhZ2UgY29tcG9uZW50IGFsaWducyB3aXRoIHRoZSBwYWdlIGFuZCBhIGhlYWRlciBibG9jayB3aXRoIHRoZVxuICAvLyBoZWFkZXIuXG4gIHByaXZhdGUgX2NhbmRpZGF0ZXMobW92aW5nOiBSZXBvcnRDb21wb25lbnQpOiB7IHZlcnRpY2FsOiBudW1iZXJbXTsgaG9yaXpvbnRhbDogbnVtYmVyW10gfSB7XG4gICAgY29uc3QgdmVydGljYWwgPSBbMCwgdGhpcy5yZXBvcnQucGFnZVdpZHRoIC8gMiwgdGhpcy5yZXBvcnQucGFnZVdpZHRoXTtcbiAgICBjb25zdCBob3Jpem9udGFsID0gWzAsIHRoaXMucmVwb3J0LnBhZ2VIZWlnaHQgLyAyLCB0aGlzLnJlcG9ydC5wYWdlSGVpZ2h0XTtcblxuICAgIGNvbnN0IHsgaGVhZGVySGVpZ2h0LCBmb290ZXJIZWlnaHQgfSA9IHRoaXMuYmFuZHM7XG4gICAgaWYgKGhlYWRlckhlaWdodCkge1xuICAgICAgaG9yaXpvbnRhbC5wdXNoKGhlYWRlckhlaWdodCk7XG4gICAgfVxuICAgIGlmIChmb290ZXJIZWlnaHQpIHtcbiAgICAgIGhvcml6b250YWwucHVzaCh0aGlzLnJlcG9ydC5wYWdlSGVpZ2h0IC0gZm9vdGVySGVpZ2h0KTtcbiAgICB9XG5cbiAgICBjb25zdCBpc01hc3RlciA9IHRoaXMuX2lzTWFzdGVyQ29tcG9uZW50KG1vdmluZyk7XG4gICAgY29uc3Qgc2libGluZ3MgPSBpc01hc3RlciA/IHRoaXMubWFzdGVyQ29tcG9uZW50cygpIDogdGhpcy5hY3RpdmVQYWdlQ29tcG9uZW50cygpO1xuXG4gICAgZm9yIChjb25zdCBjb21wb25lbnQgb2Ygc2libGluZ3MpIHtcbiAgICAgIGlmIChjb21wb25lbnQuaWQgPT09IG1vdmluZy5pZCkge1xuICAgICAgICBjb250aW51ZTtcbiAgICAgIH1cblxuICAgICAgdmVydGljYWwucHVzaChjb21wb25lbnQueCwgY29tcG9uZW50LnggKyBjb21wb25lbnQudyAvIDIsIGNvbXBvbmVudC54ICsgY29tcG9uZW50LncpO1xuICAgICAgaG9yaXpvbnRhbC5wdXNoKGNvbXBvbmVudC55LCBjb21wb25lbnQueSArIGNvbXBvbmVudC5oIC8gMiwgY29tcG9uZW50LnkgKyBjb21wb25lbnQuaCk7XG4gICAgfVxuXG4gICAgcmV0dXJuIHsgdmVydGljYWwsIGhvcml6b250YWwgfTtcbiAgfVxuXG4gIC8vIFNuYXAgb25lIGF4aXM6IG9mIHRoZSBtb3ZpbmcgYm94J3MgdGhyZWUgbGluZXMgKGVkZ2UvY2VudGVyL2VkZ2UpLCBmaW5kXG4gIC8vIHRoZSBjbG9zZXN0IGNhbmRpZGF0ZSB3aXRoaW4gdGhyZXNob2xkIGFuZCByZXR1cm4gdGhlIGFkanVzdGVkIGJhc2VcbiAgLy8gY29vcmRpbmF0ZSBwbHVzIHRoZSBndWlkZSB0byBkcmF3LlxuICBwcml2YXRlIF9zbmFwQXhpcyhcbiAgICBsaW5lczogeyBvZmZzZXQ6IG51bWJlcjsgdmFsdWU6IG51bWJlciB9W10sXG4gICAgY2FuZGlkYXRlczogbnVtYmVyW10sXG4gICk6IHsgYmFzZTogbnVtYmVyOyBndWlkZTogbnVtYmVyIH0gfCBudWxsIHtcbiAgICBsZXQgYmVzdDogeyBiYXNlOiBudW1iZXI7IGd1aWRlOiBudW1iZXI7IGRpc3RhbmNlOiBudW1iZXIgfSB8IG51bGwgPSBudWxsO1xuXG4gICAgZm9yIChjb25zdCBsaW5lIG9mIGxpbmVzKSB7XG4gICAgICBmb3IgKGNvbnN0IGNhbmRpZGF0ZSBvZiBjYW5kaWRhdGVzKSB7XG4gICAgICAgIGNvbnN0IGRpc3RhbmNlID0gTWF0aC5hYnMoY2FuZGlkYXRlIC0gbGluZS52YWx1ZSk7XG4gICAgICAgIGlmIChkaXN0YW5jZSA8PSB0aGlzLl9zbmFwVGhyZXNob2xkICYmICghYmVzdCB8fCBkaXN0YW5jZSA8IGJlc3QuZGlzdGFuY2UpKSB7XG4gICAgICAgICAgYmVzdCA9IHsgYmFzZTogY2FuZGlkYXRlIC0gbGluZS5vZmZzZXQsIGd1aWRlOiBjYW5kaWRhdGUsIGRpc3RhbmNlIH07XG4gICAgICAgIH1cbiAgICAgIH1cbiAgICB9XG5cbiAgICByZXR1cm4gYmVzdCA/IHsgYmFzZTogYmVzdC5iYXNlLCBndWlkZTogYmVzdC5ndWlkZSB9IDogbnVsbDtcbiAgfVxuXG4gIHByaXZhdGUgX25lYXJlc3QodmFsdWU6IG51bWJlciwgY2FuZGlkYXRlczogbnVtYmVyW10pOiBudW1iZXIgfCBudWxsIHtcbiAgICBsZXQgYmVzdDogbnVtYmVyIHwgbnVsbCA9IG51bGw7XG4gICAgbGV0IGJlc3REaXN0YW5jZSA9IHRoaXMuX3NuYXBUaHJlc2hvbGQ7XG5cbiAgICBmb3IgKGNvbnN0IGNhbmRpZGF0ZSBvZiBjYW5kaWRhdGVzKSB7XG4gICAgICBjb25zdCBkaXN0YW5jZSA9IE1hdGguYWJzKGNhbmRpZGF0ZSAtIHZhbHVlKTtcbiAgICAgIGlmIChkaXN0YW5jZSA8PSBiZXN0RGlzdGFuY2UpIHtcbiAgICAgICAgYmVzdCA9IGNhbmRpZGF0ZTtcbiAgICAgICAgYmVzdERpc3RhbmNlID0gZGlzdGFuY2U7XG4gICAgICB9XG4gICAgfVxuXG4gICAgcmV0dXJuIGJlc3Q7XG4gIH1cblxuICAvLyBUaGUgZ3VpZGVzIG92ZXJsYXkgaXMgZHJhd24gaW1wZXJhdGl2ZWx5IOKAlCB0aGUgZHJhZyBsb29wIHJ1bnMgb3V0c2lkZVxuICAvLyBBbmd1bGFyIGFuZCByZXBhaW50cyBvbiBldmVyeSBwb2ludGVybW92ZS5cbiAgcHJpdmF0ZSBfcmVuZGVyR3VpZGVzKGd1aWRlczogR3VpZGVMaW5lW10pOiB2b2lkIHtcbiAgICBjb25zdCBob3N0ID0gdGhpcy5fZ3VpZGVzPy5uYXRpdmVFbGVtZW50O1xuICAgIGlmICghaG9zdCkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIGhvc3QucmVwbGFjZUNoaWxkcmVuKC4uLmd1aWRlcy5tYXAoKGd1aWRlKSA9PiB7XG4gICAgICBjb25zdCBsaW5lID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnZGl2Jyk7XG4gICAgICBsaW5lLmNsYXNzTmFtZSA9IGBndWlkZSBndWlkZS0ke2d1aWRlLm9yaWVudGF0aW9ufWA7XG4gICAgICBpZiAoZ3VpZGUub3JpZW50YXRpb24gPT09ICd2Jykge1xuICAgICAgICBsaW5lLnN0eWxlLmxlZnQgPSBgJHtndWlkZS5wb3NpdGlvbiAqIFBYX1BFUl9JTkNIfXB4YDtcbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIGxpbmUuc3R5bGUudG9wID0gYCR7Z3VpZGUucG9zaXRpb24gKiBQWF9QRVJfSU5DSH1weGA7XG4gICAgICB9XG5cbiAgICAgIHJldHVybiBsaW5lO1xuICAgIH0pKTtcbiAgfVxuXG4gIHByaXZhdGUgX2NsZWFyR3VpZGVzKCk6IHZvaWQge1xuICAgIHRoaXMuX2d1aWRlcz8ubmF0aXZlRWxlbWVudD8ucmVwbGFjZUNoaWxkcmVuKCk7XG4gIH1cbn1cbiIsIjxkaXYgY2xhc3M9XCJjYW52YXNcIj5cbiAgPGRpdlxuICAgICN2aWV3cG9ydFxuICAgIGNsYXNzPVwicGFnZS12aWV3cG9ydFwiXG4gICAgKHBvaW50ZXJkb3duKT1cIm9uQ2FudmFzUG9pbnRlckRvd24oKVwiPlxuICAgIDxmcy16b29tLXBhblxuICAgICAgd2hlZWw9XCJtb2RpZmllclwiXG4gICAgICBbem9vbU1pbl09XCIwLjFcIlxuICAgICAgW3pvb21NYXhdPVwiM1wiXG4gICAgICAoem9vbWVkKT1cIm9uWm9vbWVkKCRldmVudClcIj5cbiAgICAgIEBpZiAoYWN0aXZlUGFnZSkge1xuICAgICAgICA8ZGl2XG4gICAgICAgICAgY2xhc3M9XCJwYWdlXCJcbiAgICAgICAgICBbY2xhc3MuZWRpdGluZ109XCJlZGl0TW9kZVwiXG4gICAgICAgICAgW2NsYXNzLm1hc3Rlci1lZGl0aW5nXT1cImlzTWFzdGVyRWRpdGluZ1wiXG4gICAgICAgICAgW3N0eWxlLndpZHRoLnB4XT1cInJlcG9ydC5wYWdlV2lkdGggKiBQWFwiXG4gICAgICAgICAgW3N0eWxlLmhlaWdodC5weF09XCJyZXBvcnQucGFnZUhlaWdodCAqIFBYXCJcbiAgICAgICAgICBbc3R5bGUuLS1jYW52YXMtem9vbV09XCJ6b29tKClcIlxuICAgICAgICAgIFtzdHlsZS4tLXJlcG9ydC1oZWFkaW5nLXNpemUucHhdPVwiaGVhZGluZ1NpemVQeFwiPlxuICAgICAgICAgIDwhLS0gVGhlIGhlYWRlciBhbmQgZm9vdGVyOiB0aGUgbWFzdGVyJ3MgY29tcG9uZW50cywgZHJhd24gdW5kZXIgdGhlXG4gICAgICAgICAgICAgICBwYWdlJ3Mgb3duLiAtLT5cbiAgICAgICAgICBAaWYgKGlzTWFzdGVyU2hvd24gJiYgbWFzdGVyQ29tcG9uZW50cygpLmxlbmd0aCkge1xuICAgICAgICAgICAgPGRpdlxuICAgICAgICAgICAgICBjbGFzcz1cIm1hc3Rlci1sYXllclwiXG4gICAgICAgICAgICAgIFtjbGFzcy5lZGl0YWJsZV09XCJpc01hc3RlckVkaXRpbmdcIj5cbiAgICAgICAgICAgICAgQGZvciAoY29tcG9uZW50IG9mIG1hc3RlckNvbXBvbmVudHMoKTsgdHJhY2sgY29tcG9uZW50LmlkICsgJzonICsgYXBwbGllZFZlcnNpb24oKSkge1xuICAgICAgICAgICAgICAgIDxhcHAtcmVwb3J0LWNvbXBvbmVudFxuICAgICAgICAgICAgICAgICAgW3JlcG9ydElkXT1cInJlcG9ydC5pZFwiXG4gICAgICAgICAgICAgICAgICBbY29tcG9uZW50XT1cImNvbXBvbmVudFwiXG4gICAgICAgICAgICAgICAgICBbZ3JvdXBzXT1cImdyb3Vwc1wiXG4gICAgICAgICAgICAgICAgICBbZWRpdE1vZGVdPVwiaXNNYXN0ZXJFZGl0aW5nXCJcbiAgICAgICAgICAgICAgICAgIFt6b29tXT1cInpvb20oKVwiXG4gICAgICAgICAgICAgICAgICBbc25hcHBlcl09XCJzbmFwcGVyXCJcbiAgICAgICAgICAgICAgICAgIFt0b2tlbnNdPVwibWFzdGVyVG9rZW5zKClcIlxuICAgICAgICAgICAgICAgICAgW3ZhbHVlS2V5c0Vsc2V3aGVyZV09XCJ2YWx1ZUtleXNFbHNld2hlcmVcIlxuICAgICAgICAgICAgICAgICAgW3NlbGVjdGVkXT1cImNvbXBvbmVudC5pZCA9PT0gc2VsZWN0ZWRDb21wb25lbnRJZCgpXCJcbiAgICAgICAgICAgICAgICAgIFtzdHlsZS5sZWZ0LnB4XT1cImNvbXBvbmVudC54ICogUFhcIlxuICAgICAgICAgICAgICAgICAgW3N0eWxlLnRvcC5weF09XCJjb21wb25lbnQueSAqIFBYXCJcbiAgICAgICAgICAgICAgICAgIFtzdHlsZS53aWR0aC5weF09XCJjb21wb25lbnQudyAqIFBYXCJcbiAgICAgICAgICAgICAgICAgIFtzdHlsZS5oZWlnaHQucHhdPVwiY29tcG9uZW50LmF1dG9IZWlnaHQgPyBudWxsIDogY29tcG9uZW50LmggKiBQWFwiXG4gICAgICAgICAgICAgICAgICAoc2VsZWN0Q29tcG9uZW50KT1cInNlbGVjdENvbXBvbmVudCgkZXZlbnQpXCJcbiAgICAgICAgICAgICAgICAgIChwb3NpdGlvbkNoYW5nZWQpPVwib25Qb3NpdGlvbkNoYW5nZWQoJGV2ZW50KVwiXG4gICAgICAgICAgICAgICAgICAocmVtb3ZlZCk9XCJvbkNvbXBvbmVudFJlbW92ZWQoJGV2ZW50KVwiXG4gICAgICAgICAgICAgICAgICAob3BlblNldHRpbmdzKT1cImNvbXBvbmVudFNldHRpbmdzLmVtaXQoJGV2ZW50KVwiXG4gICAgICAgICAgICAgICAgICAodmFsdWVTZXR0aW5ncyk9XCJvcGVuVmFsdWVTZXR0aW5ncyhjb21wb25lbnQsICRldmVudClcIlxuICAgICAgICAgICAgICAgICAgKHRleHRTYXZlZCk9XCJvblRleHRTYXZlZChjb21wb25lbnQsICRldmVudClcIlxuICAgICAgICAgICAgICAgICAgKHZhbHVlc1JlbW92ZWQpPVwicmVwb3J0Q2hhbmdlZC5lbWl0KClcIj5cbiAgICAgICAgICAgICAgICA8L2FwcC1yZXBvcnQtY29tcG9uZW50PlxuICAgICAgICAgICAgICB9XG4gICAgICAgICAgICA8L2Rpdj5cbiAgICAgICAgICB9XG5cbiAgICAgICAgICA8IS0tIFRoZSBoZWFkZXIgYW5kIGZvb3RlciBiYW5kcywgYXMgZ3VpZGVzIHdoaWxlIGVkaXRpbmcuIC0tPlxuICAgICAgICAgIEBpZiAoZWRpdE1vZGUpIHtcbiAgICAgICAgICAgIEBpZiAoYmFuZHMuaGVhZGVySGVpZ2h0KSB7XG4gICAgICAgICAgICAgIDxkaXZcbiAgICAgICAgICAgICAgICBjbGFzcz1cImJhbmQgYmFuZC1oZWFkZXJcIlxuICAgICAgICAgICAgICAgIFtzdHlsZS5oZWlnaHQucHhdPVwiYmFuZHMuaGVhZGVySGVpZ2h0ICogUFhcIj5cbiAgICAgICAgICAgICAgICBAaWYgKGlzTWFzdGVyRWRpdGluZykge1xuICAgICAgICAgICAgICAgICAgPHNwYW4gY2xhc3M9XCJiYW5kLWxhYmVsIHNtYWxsXCI+SGVhZGVyPC9zcGFuPlxuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgPC9kaXY+XG4gICAgICAgICAgICB9XG4gICAgICAgICAgICBAaWYgKGJhbmRzLmZvb3RlckhlaWdodCkge1xuICAgICAgICAgICAgICA8ZGl2XG4gICAgICAgICAgICAgICAgY2xhc3M9XCJiYW5kIGJhbmQtZm9vdGVyXCJcbiAgICAgICAgICAgICAgICBbc3R5bGUuaGVpZ2h0LnB4XT1cImJhbmRzLmZvb3RlckhlaWdodCAqIFBYXCI+XG4gICAgICAgICAgICAgICAgQGlmIChpc01hc3RlckVkaXRpbmcpIHtcbiAgICAgICAgICAgICAgICAgIDxzcGFuIGNsYXNzPVwiYmFuZC1sYWJlbCBzbWFsbFwiPkZvb3Rlcjwvc3Bhbj5cbiAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgIDwvZGl2PlxuICAgICAgICAgICAgfVxuICAgICAgICAgIH1cblxuICAgICAgICAgIEBmb3IgKGNvbXBvbmVudCBvZiBhY3RpdmVQYWdlQ29tcG9uZW50cygpOyB0cmFjayBjb21wb25lbnQuaWQgKyAnOicgKyBhcHBsaWVkVmVyc2lvbigpKSB7XG4gICAgICAgICAgICA8YXBwLXJlcG9ydC1jb21wb25lbnRcbiAgICAgICAgICAgICAgW3JlcG9ydElkXT1cInJlcG9ydC5pZFwiXG4gICAgICAgICAgICAgIFtjb21wb25lbnRdPVwiY29tcG9uZW50XCJcbiAgICAgICAgICAgICAgW2dyb3Vwc109XCJncm91cHNcIlxuICAgICAgICAgICAgICBbZWRpdE1vZGVdPVwiaXNQYWdlRWRpdGluZ1wiXG4gICAgICAgICAgICAgIFt6b29tXT1cInpvb20oKVwiXG4gICAgICAgICAgICAgIFtzbmFwcGVyXT1cInNuYXBwZXJcIlxuICAgICAgICAgICAgICBbdG9rZW5zXT1cInBhZ2VUb2tlbnMoKVwiXG4gICAgICAgICAgICAgIFt2YWx1ZUtleXNFbHNld2hlcmVdPVwidmFsdWVLZXlzRWxzZXdoZXJlXCJcbiAgICAgICAgICAgICAgW3NlbGVjdGVkXT1cImNvbXBvbmVudC5pZCA9PT0gc2VsZWN0ZWRDb21wb25lbnRJZCgpXCJcbiAgICAgICAgICAgICAgW3N0eWxlLmxlZnQucHhdPVwiY29tcG9uZW50LnggKiBQWFwiXG4gICAgICAgICAgICAgIFtzdHlsZS50b3AucHhdPVwiY29tcG9uZW50LnkgKiBQWFwiXG4gICAgICAgICAgICAgIFtzdHlsZS53aWR0aC5weF09XCJjb21wb25lbnQudyAqIFBYXCJcbiAgICAgICAgICAgICAgW3N0eWxlLmhlaWdodC5weF09XCJjb21wb25lbnQuYXV0b0hlaWdodCA/IG51bGwgOiBjb21wb25lbnQuaCAqIFBYXCJcbiAgICAgICAgICAgICAgKHNlbGVjdENvbXBvbmVudCk9XCJzZWxlY3RDb21wb25lbnQoJGV2ZW50KVwiXG4gICAgICAgICAgICAgIChwb3NpdGlvbkNoYW5nZWQpPVwib25Qb3NpdGlvbkNoYW5nZWQoJGV2ZW50KVwiXG4gICAgICAgICAgICAgIChyZW1vdmVkKT1cIm9uQ29tcG9uZW50UmVtb3ZlZCgkZXZlbnQpXCJcbiAgICAgICAgICAgICAgKG9wZW5TZXR0aW5ncyk9XCJjb21wb25lbnRTZXR0aW5ncy5lbWl0KCRldmVudClcIlxuICAgICAgICAgICAgICAodmFsdWVTZXR0aW5ncyk9XCJvcGVuVmFsdWVTZXR0aW5ncyhjb21wb25lbnQsICRldmVudClcIlxuICAgICAgICAgICAgICAodGV4dFNhdmVkKT1cIm9uVGV4dFNhdmVkKGNvbXBvbmVudCwgJGV2ZW50KVwiXG4gICAgICAgICAgICAgICh2YWx1ZXNSZW1vdmVkKT1cInJlcG9ydENoYW5nZWQuZW1pdCgpXCI+XG4gICAgICAgICAgICA8L2FwcC1yZXBvcnQtY29tcG9uZW50PlxuICAgICAgICAgIH1cblxuICAgICAgICAgIDxkaXZcbiAgICAgICAgICAgICNndWlkZXNcbiAgICAgICAgICAgIGNsYXNzPVwiZ3VpZGVzXCI+XG4gICAgICAgICAgPC9kaXY+XG5cbiAgICAgICAgICBAaWYgKCFhY3RpdmVQYWdlQ29tcG9uZW50cygpLmxlbmd0aCAmJiAhbWFzdGVyTW9kZSgpKSB7XG4gICAgICAgICAgICA8ZGl2IGNsYXNzPVwicGFnZS1lbXB0eVwiPlxuICAgICAgICAgICAgICBBc2sgdGhlIGFzc2lzdGFudCB0byBhZGQgYSBjaGFydCwgbGlzdCBvciBLUEkgdG8gdGhpcyBwYWdlLlxuICAgICAgICAgICAgPC9kaXY+XG4gICAgICAgICAgfVxuICAgICAgICA8L2Rpdj5cbiAgICAgIH1cbiAgICA8L2ZzLXpvb20tcGFuPlxuICA8L2Rpdj5cblxuICA8ZGl2IGNsYXNzPVwiY2FudmFzLXRvb2xiYXJcIj5cbiAgICA8IS0tIFRhYnMgYXJlIG9uZSBob3Jpem9udGFsIGRyb3AgbGlzdDogZHJhZ2dpbmcgYSBjaGlwIHJlb3JkZXJzIHRoZSBwYWdlcy5cbiAgICAgICAgIFRoZSBkcm9wIElOREVYIGlzIGNvbXB1dGVkIGFsb25nIFggKG9yaWVudGF0aW9uKSwgYnV0IHRoZSBwcmV2aWV3IGlzXG4gICAgICAgICBkZWxpYmVyYXRlbHkgbGVmdCB1bmJvdW5kZWQgb24gYm90aCBheGVzIOKAlCBwaW5uaW5nIGl0IHRvIHRoZSByb3cgd2l0aFxuICAgICAgICAgY2RrRHJhZ0JvdW5kYXJ5IG1lYW5zIHRoZSBjaGlwIHlvdSBhcmUgZHJhZ2dpbmcgY292ZXJzIHRoZSBjaGlwcyB5b3VcbiAgICAgICAgIGFyZSBkcmFnZ2luZyBpdCBwYXN0LCBhbmQgeW91IGNhbm5vdCBzZWUgd2hlcmUgaXQgaXMgZ29pbmcgdG8gbGFuZC5cbiAgICAgICAgIEV2ZXJ5IHBhZ2UgZ2V0cyBhIGNoaXAsIGluY2x1ZGluZyBhIGxvbmUgb25lOiB0aGUgY2hpcCBpcyB3aGF0IHRlbGxzXG4gICAgICAgICB5b3Ugd2hpY2ggcGFnZSB5b3UgYXJlIG9uLCBhbmQgYSByZXBvcnQgdGhhdCBoaWQgaXQgbGVmdCB5b3UgdW5hYmxlIHRvXG4gICAgICAgICB0ZWxsIHBhZ2UgMSBvZiAxIGZyb20gYSBwYWdlIHRoYXQgZmFpbGVkIHRvIGxvYWQuIERlbGV0aW5nIHRoZSBsYXN0XG4gICAgICAgICBwYWdlIGlzIHJlZnVzZWQgc2VydmVyLXNpZGUsIHNvIHRoZSBrZWJhYiBpcyBzYWZlIHRvIGV4cG9zZSBoZXJlLiAtLT5cbiAgICA8ZGl2XG4gICAgICBjbGFzcz1cInBhZ2UtdGFic1wiXG4gICAgICBjZGtEcm9wTGlzdFxuICAgICAgY2RrRHJvcExpc3RPcmllbnRhdGlvbj1cImhvcml6b250YWxcIlxuICAgICAgKGNka0Ryb3BMaXN0RHJvcHBlZCk9XCJvblBhZ2VEcm9wcGVkKCRldmVudClcIj5cbiAgICAgIEBmb3IgKHBhZ2Ugb2YgcGFnZXMoKTsgdHJhY2sgcGFnZS5pZDsgbGV0IGluZGV4ID0gJGluZGV4KSB7XG4gICAgICAgIDwhLS0gVGhlIGNoaXAgaXMgdGhlIGRyYWcgaGFuZGxlIEFORCB0aGUgdGFiOiBjbGlja2luZyBzZWxlY3RzLFxuICAgICAgICAgICAgIGRyYWdnaW5nIHJlb3JkZXJzLiBUaGUga2ViYWIgbGl2ZXMgaW5zaWRlIGl0LCBzbyB0aGUgd2hvbGVcbiAgICAgICAgICAgICBjb250cm9sIHN0YXlzIG9uZSBjaGlwIGluc3RlYWQgb2YgZ3Jvd2luZyBhIHNlY29uZCBidXR0b24uIC0tPlxuICAgICAgICA8ZGl2XG4gICAgICAgICAgY2RrRHJhZ1xuICAgICAgICAgIGNsYXNzPVwicGFnZS10YWJcIlxuICAgICAgICAgIFtjbGFzcy5hY3RpdmVdPVwiaW5kZXggPT09IGFjdGl2ZVBhZ2VJbmRleCgpXCJcbiAgICAgICAgICAoY2xpY2spPVwic2VsZWN0UGFnZShpbmRleClcIj5cbiAgICAgICAgICA8c3BhbiBjbGFzcz1cInBhZ2UtdGFiLWxhYmVsXCI+e3sgcGFnZUxhYmVsKHBhZ2UsIGluZGV4KSB9fTwvc3Bhbj5cbiAgICAgICAgICA8IS0tIFRoZSBrZWJhYiBvcGVucyB0aGUgbWVudSByYXRoZXIgdGhhbiBzdGFydGluZyBhIGRyYWcgb3JcbiAgICAgICAgICAgICAgIHN3aXRjaGluZyBwYWdlcywgc28gaXQgc3dhbGxvd3MgaXRzIG93biBjbGljay4gLS0+XG4gICAgICAgICAgPHNwYW5cbiAgICAgICAgICAgIGNsYXNzPVwicGFnZS10YWItbWVudVwiXG4gICAgICAgICAgICBbZnNNZW51VHJpZ2dlckZvcl09XCJwYWdlTWVudVwiXG4gICAgICAgICAgICAoY2xpY2spPVwiJGV2ZW50LnN0b3BQcm9wYWdhdGlvbigpXCJcbiAgICAgICAgICAgIChtb3VzZWRvd24pPVwiJGV2ZW50LnN0b3BQcm9wYWdhdGlvbigpXCI+XG4gICAgICAgICAgICA8bWF0LWljb24+bW9yZV92ZXJ0PC9tYXQtaWNvbj5cbiAgICAgICAgICA8L3NwYW4+XG4gICAgICAgIDwvZGl2PlxuICAgICAgICA8IS0tIE91dHNpZGUgdGhlIGNoaXA6IGNka0RyYWcgY2xvbmVzIGl0cyBob3N0IGludG8gdGhlIGRyYWcgcHJldmlldyxcbiAgICAgICAgICAgICBhbmQgYSBtZW51IG92ZXJsYXkgYW5jaG9yZWQgdG8gYSBjbG9uZWQgdHJpZ2dlciBvcGVucyBkZXRhY2hlZFxuICAgICAgICAgICAgIGZyb20gdGhlIHJlYWwgdGFiLiAtLT5cbiAgICAgICAgPGZzLW1lbnUgI3BhZ2VNZW51PlxuICAgICAgICAgIDxuZy10ZW1wbGF0ZVxuICAgICAgICAgICAgZnMtbWVudS1pdGVtXG4gICAgICAgICAgICAoY2xpY2spPVwicmVuYW1lUGFnZShwYWdlKVwiPlxuICAgICAgICAgICAgRWRpdCBuYW1lXG4gICAgICAgICAgPC9uZy10ZW1wbGF0ZT5cbiAgICAgICAgICA8bmctdGVtcGxhdGVcbiAgICAgICAgICAgIGZzLW1lbnUtaXRlbVxuICAgICAgICAgICAgKGNsaWNrKT1cInRvZ2dsZU1hc3RlckhpZGRlbihwYWdlKVwiPlxuICAgICAgICAgICAge3sgcGFnZS5tYXN0ZXJIaWRkZW4gPyAnU2hvdyBoZWFkZXIgJiBmb290ZXInIDogJ0hpZGUgaGVhZGVyICYgZm9vdGVyJyB9fVxuICAgICAgICAgIDwvbmctdGVtcGxhdGU+XG4gICAgICAgICAgPG5nLXRlbXBsYXRlXG4gICAgICAgICAgICBmcy1tZW51LWl0ZW1cbiAgICAgICAgICAgIChjbGljayk9XCJkZWxldGVQYWdlKHBhZ2UpXCI+XG4gICAgICAgICAgICBEZWxldGVcbiAgICAgICAgICA8L25nLXRlbXBsYXRlPlxuICAgICAgICA8L2ZzLW1lbnU+XG4gICAgICB9XG4gICAgICA8YnV0dG9uXG4gICAgICAgIHR5cGU9XCJidXR0b25cIlxuICAgICAgICBjbGFzcz1cInBhZ2UtdGFiIGFkZC1wYWdlXCJcbiAgICAgICAgbWF0VG9vbHRpcD1cIkFkZCBwYWdlXCJcbiAgICAgICAgKGNsaWNrKT1cImFkZFBhZ2UoKVwiPlxuICAgICAgICA8bWF0LWljb24+YWRkPC9tYXQtaWNvbj5cbiAgICAgICAgUGFnZVxuICAgICAgPC9idXR0b24+XG4gICAgPC9kaXY+XG5cbiAgICA8ZGl2IGNsYXNzPVwiem9vbS1jb250cm9sc1wiPlxuICAgICAgPGJ1dHRvblxuICAgICAgICB0eXBlPVwiYnV0dG9uXCJcbiAgICAgICAgY2xhc3M9XCJ6b29tLWJ1dHRvblwiXG4gICAgICAgIG1hdFRvb2x0aXA9XCJab29tIG91dCAoQ3RybC9DbWQgKyBzY3JvbGwpXCJcbiAgICAgICAgKGNsaWNrKT1cInpvb21PdXQoKVwiPlxuICAgICAgICA8bWF0LWljb24+cmVtb3ZlPC9tYXQtaWNvbj5cbiAgICAgIDwvYnV0dG9uPlxuICAgICAgPGJ1dHRvblxuICAgICAgICB0eXBlPVwiYnV0dG9uXCJcbiAgICAgICAgY2xhc3M9XCJ6b29tLWxhYmVsXCJcbiAgICAgICAgbWF0VG9vbHRpcD1cIlpvb20gdG8gMTAwJVwiXG4gICAgICAgIChjbGljayk9XCJ6b29tQWN0dWFsKClcIj5cbiAgICAgICAge3sgKHpvb20oKSAqIDEwMCkudG9GaXhlZCgwKSB9fSVcbiAgICAgIDwvYnV0dG9uPlxuICAgICAgPGJ1dHRvblxuICAgICAgICB0eXBlPVwiYnV0dG9uXCJcbiAgICAgICAgY2xhc3M9XCJ6b29tLWJ1dHRvblwiXG4gICAgICAgIG1hdFRvb2x0aXA9XCJab29tIGluIChDdHJsL0NtZCArIHNjcm9sbClcIlxuICAgICAgICAoY2xpY2spPVwiem9vbUluKClcIj5cbiAgICAgICAgPG1hdC1pY29uPmFkZDwvbWF0LWljb24+XG4gICAgICA8L2J1dHRvbj5cbiAgICAgIDxidXR0b25cbiAgICAgICAgdHlwZT1cImJ1dHRvblwiXG4gICAgICAgIGNsYXNzPVwiem9vbS1idXR0b25cIlxuICAgICAgICBtYXRUb29sdGlwPVwiRml0IHBhZ2VcIlxuICAgICAgICAoY2xpY2spPVwiem9vbUZpdCgpXCI+XG4gICAgICAgIDxtYXQtaWNvbj5maXRfc2NyZWVuPC9tYXQtaWNvbj5cbiAgICAgIDwvYnV0dG9uPlxuICAgIDwvZGl2PlxuICA8L2Rpdj5cbjwvZGl2PlxuIl19
|