@firestitch/report 18.7.0 → 18.8.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/app/reports/components/component-kpi/component-kpi.component.d.ts +12 -3
- package/app/reports/components/component-kpi/components/sparkline/sparkline.component.d.ts +8 -0
- package/app/reports/components/component-list/component-list.component.d.ts +7 -1
- package/app/reports/components/component-note/component-note.component.d.ts +12 -0
- package/app/reports/components/report-canvas/report-canvas.component.d.ts +0 -9
- package/app/reports/components/report-component/report-component.component.d.ts +2 -11
- package/app/reports/data/report.data.d.ts +0 -2
- package/app/reports/dialogs/component-settings/component-settings.component.d.ts +34 -2
- package/app/reports/dialogs/report-settings/report-settings.component.d.ts +0 -1
- package/app/reports/enums/report-change-polarity.enum.d.ts +5 -0
- package/app/reports/enums/report-kpi-trend.enum.d.ts +5 -0
- package/app/reports/export/report-export-collector.service.d.ts +27 -1
- package/app/reports/export/report-pdf.service.d.ts +5 -0
- package/app/reports/export/report-pptx.service.d.ts +7 -0
- package/app/reports/format.d.ts +27 -1
- package/app/reports/interfaces/report-chat-viewer-filter.interface.d.ts +2 -0
- package/app/reports/interfaces/report.interface.d.ts +124 -4
- package/app/reports/kpi-card.d.ts +48 -0
- package/app/reports/layout.d.ts +0 -9
- package/app/reports/list-config.d.ts +8 -1
- package/app/reports/option-builder.d.ts +7 -0
- package/app/reports/output-notes.d.ts +14 -0
- package/app/reports/pipes/report-output.pipe.d.ts +10 -0
- package/app/reports/services/report-filter-state.service.d.ts +1 -0
- package/app/reports/theme/palette.d.ts +3 -0
- package/app/reports/theme/typography.d.ts +1 -0
- package/esm2022/app/reports/components/component-chart/component-chart.component.mjs +8 -4
- package/esm2022/app/reports/components/component-kpi/component-kpi.component.mjs +50 -17
- package/esm2022/app/reports/components/component-kpi/components/sparkline/sparkline.component.mjs +19 -0
- package/esm2022/app/reports/components/component-list/component-list.component.mjs +66 -6
- package/esm2022/app/reports/components/component-note/component-note.component.mjs +30 -0
- package/esm2022/app/reports/components/report-canvas/report-canvas.component.mjs +7 -56
- package/esm2022/app/reports/components/report-component/report-component.component.mjs +21 -82
- package/esm2022/app/reports/data/report.data.mjs +5 -5
- package/esm2022/app/reports/dialogs/component-settings/component-settings.component.mjs +133 -13
- package/esm2022/app/reports/dialogs/report-settings/report-settings.component.mjs +4 -8
- package/esm2022/app/reports/enums/report-change-polarity.enum.mjs +11 -0
- package/esm2022/app/reports/enums/report-kpi-trend.enum.mjs +10 -0
- package/esm2022/app/reports/export/report-export-collector.service.mjs +101 -10
- package/esm2022/app/reports/export/report-pdf.service.mjs +249 -40
- package/esm2022/app/reports/export/report-pptx.service.mjs +312 -49
- package/esm2022/app/reports/format.mjs +423 -2
- package/esm2022/app/reports/interfaces/report-chat-viewer-filter.interface.mjs +1 -1
- package/esm2022/app/reports/interfaces/report.interface.mjs +1 -1
- package/esm2022/app/reports/kpi-card.mjs +174 -0
- package/esm2022/app/reports/layout.mjs +1 -46
- package/esm2022/app/reports/list-config.mjs +33 -1
- package/esm2022/app/reports/option-builder.mjs +624 -54
- package/esm2022/app/reports/output-notes.mjs +158 -0
- package/esm2022/app/reports/pipes/report-output.pipe.mjs +28 -0
- package/esm2022/app/reports/services/report-filter-state.service.mjs +40 -3
- package/esm2022/app/reports/theme/palette.mjs +17 -1
- package/esm2022/app/reports/theme/typography.mjs +5 -1
- package/esm2022/app/reports/views/report/fs-ai-report.component.mjs +2 -2
- package/esm2022/app/reports/views/report/report.component.mjs +3 -4
- package/esm2022/public_api.mjs +2 -1
- package/fesm2022/{firestitch-report-echarts-u5ImuZT5.mjs → firestitch-report-echarts-qCBE3LqM.mjs} +2 -2
- package/fesm2022/{firestitch-report-echarts-u5ImuZT5.mjs.map → firestitch-report-echarts-qCBE3LqM.mjs.map} +1 -1
- package/fesm2022/{firestitch-report-firestitch-report-Cz-kA_id.mjs → firestitch-report-firestitch-report-DbsWbE-j.mjs} +2574 -487
- package/fesm2022/firestitch-report-firestitch-report-DbsWbE-j.mjs.map +1 -0
- package/fesm2022/firestitch-report.mjs +1 -1
- package/package.json +1 -1
- package/public_api.d.ts +1 -0
- package/fesm2022/firestitch-report-firestitch-report-Cz-kA_id.mjs.map +0 -1
|
@@ -12,6 +12,7 @@ import { Subject, debounceTime, map, switchMap, tap } from 'rxjs';
|
|
|
12
12
|
import { takeUntilDestroyed } from '@angular/core/rxjs-interop';
|
|
13
13
|
import { ReportData } from '../../data/report.data';
|
|
14
14
|
import { ListColumnsComponent } from '../../dialogs/list-columns/list-columns.component';
|
|
15
|
+
import { kpiCardSettings, sameKpiCardSettings } from '../../kpi-card';
|
|
15
16
|
import { DEFAULT_COMPONENT_PADDING } from '../../layout';
|
|
16
17
|
import { listHideableColumns } from '../../list-config';
|
|
17
18
|
import { LIST_SEARCH_ITEM, filterItemForGroup, groupValuesFromQuery, listSearchItem, } from '../../report-filter-items';
|
|
@@ -24,10 +25,8 @@ import { PX_PER_INCH } from '../report-canvas/report-canvas.component';
|
|
|
24
25
|
import * as i0 from "@angular/core";
|
|
25
26
|
import * as i1 from "@firestitch/filter";
|
|
26
27
|
import * as i2 from "@firestitch/menu";
|
|
27
|
-
//
|
|
28
|
+
// Resize handles, named by compass direction.
|
|
28
29
|
const HANDLES = ['nw', 'n', 'ne', 'e', 'se', 's', 'sw', 'w'];
|
|
29
|
-
// Flow width snaps to the useful fractions of a page row.
|
|
30
|
-
const FLOW_WIDTH_STOPS = [25, 33.33, 50, 66.67, 75, 100];
|
|
31
30
|
const MIN_W = 0.6; // inches
|
|
32
31
|
const MIN_H = 0.4; // inches
|
|
33
32
|
// Two presses on a text block this close together open its editor. Detected
|
|
@@ -37,15 +36,9 @@ const MIN_H = 0.4; // inches
|
|
|
37
36
|
const DOUBLE_PRESS_MS = 400;
|
|
38
37
|
// One component on the page: title bar, the type-specific body (chart | list
|
|
39
38
|
// | kpi), a menu (settings, filter toggles, export) — and the editing
|
|
40
|
-
// interactions:
|
|
41
|
-
//
|
|
42
|
-
//
|
|
43
|
-
// dragging the body moves with smart alignment guides (via the canvas
|
|
44
|
-
// snapper); everything works at any zoom (pixel deltas ÷ zoom·96 → inches).
|
|
45
|
-
//
|
|
46
|
-
// Flow: dragging reorders (drop position decided by the canvas); the E
|
|
47
|
-
// handle resizes flowWidth % (snapping to 25/33/50/66/75/100), the S handle
|
|
48
|
-
// resizes height in inches.
|
|
39
|
+
// interactions: click selects; the selection frame shows 8 resize handles;
|
|
40
|
+
// dragging the body moves with smart alignment guides (via the canvas
|
|
41
|
+
// snapper); everything works at any zoom (pixel deltas ÷ zoom·96 → inches).
|
|
49
42
|
//
|
|
50
43
|
// Charts and KPIs fetch their own data here; lists fetch inside
|
|
51
44
|
// ComponentListComponent through FsList paging.
|
|
@@ -54,14 +47,12 @@ export class ReportComponentComponent {
|
|
|
54
47
|
component;
|
|
55
48
|
groups;
|
|
56
49
|
editMode = false;
|
|
57
|
-
layout = 'freeform';
|
|
58
50
|
// The canvas zoom — converts on-screen pixel deltas back to inches.
|
|
59
51
|
zoom = 1;
|
|
60
52
|
snapper = null;
|
|
61
53
|
selected = false;
|
|
62
54
|
selectComponent = new EventEmitter();
|
|
63
55
|
positionChanged = new EventEmitter();
|
|
64
|
-
flowReorder = new EventEmitter();
|
|
65
56
|
openSettings = new EventEmitter();
|
|
66
57
|
// What a text block's {{tokens}} fill with on the page it is drawn on.
|
|
67
58
|
tokens = input({ pageNumber: 1, pageName: '', reportName: '' });
|
|
@@ -72,7 +63,7 @@ export class ReportComponentComponent {
|
|
|
72
63
|
// which saves.
|
|
73
64
|
textEditing = signal(false);
|
|
74
65
|
chartComponent;
|
|
75
|
-
//
|
|
66
|
+
// Resize handles by type: a fixed-height component (chart/list)
|
|
76
67
|
// gets all eight (resize width AND height); an auto-height one (kpi) gets
|
|
77
68
|
// only the side handles since its height fits its content and can't be set.
|
|
78
69
|
get resizeHandles() {
|
|
@@ -241,11 +232,19 @@ export class ReportComponentComponent {
|
|
|
241
232
|
// repaints. The header config is rebuilt because `filterKey` changes with the
|
|
242
233
|
// title and recreates the fs-filter block around it; setting the config signal
|
|
243
234
|
// is also what repaints the new padding. The chart follows its box on its own
|
|
244
|
-
// (ngx-echarts observes the host), so nothing is told to resize.
|
|
235
|
+
// (ngx-echarts observes the host), so nothing is told to resize. A KPI's card
|
|
236
|
+
// keys are different: settings.kpi carries the keys the server saved (never
|
|
237
|
+
// the ones the dialog sent), and the server sends the target's progress and
|
|
238
|
+
// the sparkline's points with the data, so a change to them reloads it.
|
|
245
239
|
applySettings(settings) {
|
|
240
|
+
const cardChanged = !!settings.kpi
|
|
241
|
+
&& !sameKpiCardSettings(settings.kpi, kpiCardSettings(this.component.config));
|
|
246
242
|
this.component.title = settings.title;
|
|
247
|
-
this.component.config = { ...this.component.config, padding: settings.padding };
|
|
243
|
+
this.component.config = { ...this.component.config, padding: settings.padding, ...(settings.kpi ?? {}) };
|
|
248
244
|
this._buildFilterConfig();
|
|
245
|
+
if (cardChanged) {
|
|
246
|
+
this._refresh$.next();
|
|
247
|
+
}
|
|
249
248
|
}
|
|
250
249
|
// The CSV is what the screen shows, so it carries the same interaction state
|
|
251
250
|
// the screen fetched with: the group-by grain for a time-series chart, and the
|
|
@@ -308,10 +307,6 @@ export class ReportComponentComponent {
|
|
|
308
307
|
}
|
|
309
308
|
}
|
|
310
309
|
this.selectComponent.emit(this.component.id);
|
|
311
|
-
if (this.layout === 'flow') {
|
|
312
|
-
this._flowDrag(event);
|
|
313
|
-
return;
|
|
314
|
-
}
|
|
315
310
|
this._track(event, (deltaX, deltaY) => {
|
|
316
311
|
let x = Math.max(0, this._origin.x + this._inches(deltaX));
|
|
317
312
|
let y = Math.max(0, this._origin.y + this._inches(deltaY));
|
|
@@ -328,10 +323,6 @@ export class ReportComponentComponent {
|
|
|
328
323
|
return;
|
|
329
324
|
}
|
|
330
325
|
this.selectComponent.emit(this.component.id);
|
|
331
|
-
if (this.layout === 'flow') {
|
|
332
|
-
this._flowResize(event, handle);
|
|
333
|
-
return;
|
|
334
|
-
}
|
|
335
326
|
this._track(event, (deltaX, deltaY) => {
|
|
336
327
|
const dx = this._inches(deltaX);
|
|
337
328
|
const dy = this._inches(deltaY);
|
|
@@ -404,46 +395,7 @@ export class ReportComponentComponent {
|
|
|
404
395
|
},
|
|
405
396
|
});
|
|
406
397
|
}
|
|
407
|
-
|
|
408
|
-
// (the box fits its content), so there's no south handle here.
|
|
409
|
-
_flowResize(event, handle) {
|
|
410
|
-
const pageWidth = this._host.nativeElement.parentElement?.clientWidth || 1;
|
|
411
|
-
this._track(event, (deltaX) => {
|
|
412
|
-
if (handle.includes('e')) {
|
|
413
|
-
const deltaPercent = (deltaX / this.zoom / pageWidth) * 100;
|
|
414
|
-
const raw = Math.min(100, Math.max(10, this._origin.flowWidth + deltaPercent));
|
|
415
|
-
this.component.flowWidth = this._snapFlowWidth(raw);
|
|
416
|
-
this._host.nativeElement.style.width = `${this.component.flowWidth}%`;
|
|
417
|
-
}
|
|
418
|
-
}, () => {
|
|
419
|
-
this.positionChanged.emit({
|
|
420
|
-
componentId: this.component.id,
|
|
421
|
-
flowWidth: this.component.flowWidth,
|
|
422
|
-
});
|
|
423
|
-
});
|
|
424
|
-
}
|
|
425
|
-
// Flow: drag lifts the component (ghost) and the canvas decides the drop
|
|
426
|
-
// index from the pointer position.
|
|
427
|
-
_flowDrag(event) {
|
|
428
|
-
const host = this._host.nativeElement;
|
|
429
|
-
let lastClientX = event.clientX;
|
|
430
|
-
let lastClientY = event.clientY;
|
|
431
|
-
host.classList.add('flow-dragging');
|
|
432
|
-
this._track(event, (deltaX, deltaY, e) => {
|
|
433
|
-
lastClientX = e.clientX;
|
|
434
|
-
lastClientY = e.clientY;
|
|
435
|
-
host.style.transform = `translate(${deltaX / this.zoom}px, ${deltaY / this.zoom}px)`;
|
|
436
|
-
}, () => {
|
|
437
|
-
host.classList.remove('flow-dragging');
|
|
438
|
-
host.style.transform = '';
|
|
439
|
-
this.flowReorder.emit({
|
|
440
|
-
componentId: this.component.id,
|
|
441
|
-
clientX: lastClientX,
|
|
442
|
-
clientY: lastClientY,
|
|
443
|
-
});
|
|
444
|
-
});
|
|
445
|
-
}
|
|
446
|
-
_origin = { x: 0, y: 0, w: 0, h: 0, flowWidth: 50 };
|
|
398
|
+
_origin = { x: 0, y: 0, w: 0, h: 0 };
|
|
447
399
|
// Pointer-capture gesture loop: runs outside Angular, repaints imperatively,
|
|
448
400
|
// and finishes back inside Angular (selection/persistence).
|
|
449
401
|
_track(event, onMove, onEnd) {
|
|
@@ -456,12 +408,11 @@ export class ReportComponentComponent {
|
|
|
456
408
|
y: this.component.y,
|
|
457
409
|
w: this.component.w,
|
|
458
410
|
h: this.component.h,
|
|
459
|
-
flowWidth: this.component.flowWidth ?? 50,
|
|
460
411
|
};
|
|
461
412
|
const startX = event.clientX;
|
|
462
413
|
const startY = event.clientY;
|
|
463
414
|
this._zone.runOutsideAngular(() => {
|
|
464
|
-
const move = (e) => onMove(e.clientX - startX, e.clientY - startY
|
|
415
|
+
const move = (e) => onMove(e.clientX - startX, e.clientY - startY);
|
|
465
416
|
const end = () => {
|
|
466
417
|
handle.releasePointerCapture(event.pointerId);
|
|
467
418
|
handle.removeEventListener('pointermove', move);
|
|
@@ -517,14 +468,6 @@ export class ReportComponentComponent {
|
|
|
517
468
|
_round(value) {
|
|
518
469
|
return Math.round(value * 100) / 100;
|
|
519
470
|
}
|
|
520
|
-
_snapFlowWidth(value) {
|
|
521
|
-
for (const stop of FLOW_WIDTH_STOPS) {
|
|
522
|
-
if (Math.abs(value - stop) < 3) {
|
|
523
|
-
return stop;
|
|
524
|
-
}
|
|
525
|
-
}
|
|
526
|
-
return Math.round(value * 10) / 10;
|
|
527
|
-
}
|
|
528
471
|
// The canvas positions the host via [style]; mid-gesture we set it directly
|
|
529
472
|
// so OnPush never re-renders in the move loop.
|
|
530
473
|
_applyGeometry() {
|
|
@@ -566,7 +509,7 @@ export class ReportComponentComponent {
|
|
|
566
509
|
});
|
|
567
510
|
}
|
|
568
511
|
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: ReportComponentComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
569
|
-
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "18.2.14", type: ReportComponentComponent, isStandalone: true, selector: "app-report-component", inputs: { reportId: { classPropertyName: "reportId", publicName: "reportId", isSignal: false, isRequired: false, transformFunction: null }, component: { classPropertyName: "component", publicName: "component", isSignal: false, isRequired: false, transformFunction: null }, groups: { classPropertyName: "groups", publicName: "groups", isSignal: false, isRequired: false, transformFunction: null }, editMode: { classPropertyName: "editMode", publicName: "editMode", isSignal: false, isRequired: false, transformFunction: null }, layout: { classPropertyName: "layout", publicName: "layout", isSignal: false, isRequired: false, transformFunction: null }, zoom: { classPropertyName: "zoom", publicName: "zoom", isSignal: false, isRequired: false, transformFunction: null }, snapper: { classPropertyName: "snapper", publicName: "snapper", isSignal: false, isRequired: false, transformFunction: null }, selected: { classPropertyName: "selected", publicName: "selected", isSignal: false, isRequired: false, transformFunction: null }, tokens: { classPropertyName: "tokens", publicName: "tokens", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { selectComponent: "selectComponent", positionChanged: "positionChanged", flowReorder: "flowReorder", openSettings: "openSettings", removed: "removed" }, host: { properties: { "class.height-auto": "this.heightAuto" } }, viewQueries: [{ propertyName: "chartComponent", first: true, predicate: ComponentChartComponent, descendants: true }], usesOnChanges: true, ngImport: i0, template: "<div\n class=\"component-box\"\n [class.editing]=\"editMode\"\n [class.text]=\"isText\"\n [class.selected]=\"selected\"\n [style.padding]=\"bodyPadding\"\n (pointerdown)=\"onComponentPointerDown($event)\"\n (mousedown)=\"stopCanvasPan($event)\"\n (touchstart)=\"stopCanvasPan($event)\">\n <!-- The header is an fs-filter: heading template = title (and the edit-mode\n drag handle), actions = the menu, items = component-level filter groups,\n the same strip for every type (lists included). fs-filter reads its\n config once, so the block is keyed on the component-filter set to be\n recreated when it changes. -->\n <!-- A text block has no title bar \u2014 it IS its words, like a text box on a\n slide \u2014 so it gets neither the header nor the data actions. -->\n @for (key of isText ? [] : [filterKey]; track key) {\n <fs-filter\n class=\"component-filter\"\n [config]=\"filterConfig()\">\n <ng-template fsFilterHeading>\n <div\n class=\"component-title\"\n (pointerdown)=\"onDragStart($event)\">\n {{ component.title }}\n @if (truncated) {\n <mat-icon\n class=\"truncated-icon\"\n matTooltip=\"Showing a truncated result \u2014 refine the filters to see everything.\">\n warning_amber\n </mat-icon>\n }\n </div>\n </ng-template>\n </fs-filter>\n }\n <!-- The actions menu is floated top-right (absolute) rather than living in\n fs-filter's actions slot, so its ~40px button height no longer drives the\n header row's height. It overlays the box corner; the heading reserves\n right padding so a long title ellipsises before it. -->\n @if (!isText || (editMode && !textEditing())) {\n <button\n mat-icon-button\n class=\"component-menu\"\n [fsMenuTriggerFor]=\"menu\"\n (pointerdown)=\"$event.stopPropagation()\"\n (mousedown)=\"stopCanvasPan($event)\">\n <mat-icon>more_vert</mat-icon>\n </button>\n <!-- Beside its trigger, inside the same block: an fs-menu that finds no\n trigger of its own draws one. -->\n <fs-menu #menu>\n <ng-template\n fs-menu-item\n [hidden]=\"!isText\"\n (click)=\"editText()\">\n <mat-icon>edit</mat-icon>\n <span>Edit text</span>\n </ng-template>\n <ng-template\n fs-menu-item\n [hidden]=\"!isText\"\n (click)=\"deleteText()\">\n <mat-icon>delete</mat-icon>\n <span>Delete</span>\n </ng-template>\n <ng-template\n fs-menu-item\n [hidden]=\"isText\"\n (click)=\"settings()\">\n <mat-icon>tune</mat-icon>\n <span>Settings</span>\n </ng-template>\n <ng-template\n fs-menu-item\n [hidden]=\"isText\"\n (click)=\"exportCsv()\">\n <mat-icon>download</mat-icon>\n <span>Export CSV</span>\n </ng-template>\n <ng-template\n fs-menu-item\n [hidden]=\"!hidesColumns\"\n (click)=\"chooseColumns()\">\n <mat-icon>view_column</mat-icon>\n <span>Columns</span>\n </ng-template>\n </fs-menu>\n }\n <div class=\"component-body\">\n @if (isText) {\n <app-report-component-text\n [html]=\"component.config?.html ?? ''\"\n [tokens]=\"tokens()\"\n [editing]=\"textEditing()\"\n (saved)=\"onTextSaved($event)\"\n (editEnded)=\"textEditing.set(false)\">\n </app-report-component-text>\n } @else if (component.type === 'list') {\n <app-report-component-list\n [reportId]=\"reportId\"\n [component]=\"component\">\n </app-report-component-list>\n } @else if (loading()) {\n <div class=\"component-state\">\n <div class=\"loading-shimmer\"></div>\n </div>\n } @else if (error()) {\n <div class=\"component-state error\">\n {{ error() }}\n </div>\n } @else if (!data()?.rows?.length) {\n <div class=\"component-state\">\n No data\n </div>\n } @else if (component.type === 'kpi') {\n <app-report-component-kpi\n [component]=\"component\"\n [data]=\"data()\">\n </app-report-component-kpi>\n } @else {\n <app-report-component-chart\n [component]=\"component\"\n [data]=\"data()\">\n </app-report-component-chart>\n }\n <!-- In edit mode a transparent veil over the body makes the WHOLE\n component draggable (industry standard: you grab the object, not just\n its title bar) and keeps inner widgets from swallowing the gesture. -->\n @if (editMode && !textEditing()) {\n <div\n class=\"drag-veil\"\n (pointerdown)=\"onDragStart($event)\">\n </div>\n }\n </div>\n</div>\n<!-- Handles live OUTSIDE the clipped box so they straddle its edges. -->\n@if (editMode && selected) {\n @if (layout === 'freeform') {\n @for (handle of resizeHandles; track handle) {\n <div\n class=\"handle handle-{{ handle }}\"\n (mousedown)=\"stopCanvasPan($event)\"\n (pointerdown)=\"onResizeStart($event, handle)\">\n </div>\n }\n } @else {\n <!-- Flow height is always auto (the box fits its content), so only the\n east handle (width %) is offered here. -->\n <div\n class=\"handle handle-e\"\n matTooltip=\"Width (% of page)\"\n (mousedown)=\"stopCanvasPan($event)\"\n (pointerdown)=\"onResizeStart($event, 'e')\">\n </div>\n }\n}", styles: [":host{position:absolute;display:flex;flex-direction:column;font-size:10px;--mdc-outlined-button-container-height: 30px;--mdc-outlined-button-label-text-size: 10px;--mat-outlined-button-horizontal-padding: 15px;--mdc-text-button-container-height: 30px;--mdc-text-button-label-text-size: 10px;--mat-text-button-horizontal-padding: 15px;--mat-button-outlined-container-height: 30px;--mat-button-outlined-label-text-size: 10px;--mat-button-outlined-horizontal-padding: 15px;--mat-button-text-container-height: 30px;--mat-button-text-label-text-size: 10px;--mat-button-text-horizontal-padding: 15px}:host.flow-item{position:relative;left:auto;top:auto}:host.flow-dragging{z-index:40;opacity:.7;pointer-events:none}.component-box{position:relative;width:100%;flex:1 1 auto;min-height:0;box-sizing:border-box;display:flex;flex-direction:column;background:#fff;border:1px solid #e4e7eb;border-radius:6px;overflow:hidden;transition:box-shadow .12s ease,border-color .12s ease;cursor:default}.component-box.editing .component-title{cursor:grab}.component-box.editing .component-title:active{cursor:grabbing}.component-box.editing:hover{border-color:#9db3c8;box-shadow:0 2px 8px #0f172a14}.component-box.selected{border-color:var(--brand-primary-color);box-shadow:0 0 0 1px var(--brand-primary-color),0 4px 14px #2196f32e}.component-box.text{background:transparent;border-color:transparent;border-radius:0;overflow:visible}.component-box.text.editing{border-style:dashed;border-color:#cbd2d9}.component-box.text.editing:hover{box-shadow:none}.component-box.text.selected{border-style:solid;border-color:var(--brand-primary-color);box-shadow:0 0 0 1px var(--brand-primary-color)}:host ::ng-deep .component-filter .filter-bar-container{align-items:center!important}.component-filter{flex:0 0 auto;display:block;padding:0 0 4px}.component-filter .component-title{display:flex;align-items:center;gap:4px;-webkit-user-select:none;user-select:none;padding-right:40px;font-size:var(--report-heading-size);font-weight:600;color:#1f2933;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.component-filter .component-title .truncated-icon{font-size:16px;width:16px;height:16px;color:#f59e0b}.component-menu{position:absolute;top:2px;right:2px;z-index:30}.component-body{flex:1 1 auto;min-height:0;position:relative}:host(.height-auto) .component-state{min-height:120px}.drag-veil{position:absolute;inset:0;cursor:grab;touch-action:none}.drag-veil:active{cursor:grabbing}.component-state{width:100%;height:100%;display:flex;align-items:center;justify-content:center;font-size:12px;color:#7b8794;padding:8px;text-align:center}.component-state.error{color:#e15759}.loading-shimmer{width:70%;height:60%;border-radius:6px;background:linear-gradient(100deg,#f0f4f8 40%,#e4ebf2,#f0f4f8 60%);background-size:200% 100%;animation:shimmer 1.2s infinite linear}@keyframes shimmer{to{background-position-x:-200%}}.handle{position:absolute;width:14px;height:14px;display:flex;align-items:center;justify-content:center;touch-action:none;z-index:20;transform:scale(calc(1 / var(--canvas-zoom, 1)))}.handle:before{content:\"\";width:8px;height:8px;background:#fff;border:1.5px solid var(--brand-primary-color);border-radius:2px;box-shadow:0 1px 2px #0f172a33}.handle-nw{left:-7px;top:-7px;cursor:nwse-resize}.handle-n{left:calc(50% - 7px);top:-7px;cursor:ns-resize}.handle-ne{right:-7px;top:-7px;cursor:nesw-resize}.handle-e{right:-7px;top:calc(50% - 7px);cursor:ew-resize}.handle-se{right:-7px;bottom:-7px;cursor:nwse-resize}.handle-s{left:calc(50% - 7px);bottom:-7px;cursor:ns-resize}.handle-sw{left:-7px;bottom:-7px;cursor:nesw-resize}.handle-w{left:-7px;top:calc(50% - 7px);cursor:ew-resize}\n"], dependencies: [{ kind: "component", type: MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }, { kind: "component", type: MatIconButton, selector: "button[mat-icon-button]", exportAs: ["matButton"] }, { kind: "directive", type: MatTooltip, selector: "[matTooltip]", inputs: ["matTooltipPosition", "matTooltipPositionAtOrigin", "matTooltipDisabled", "matTooltipShowDelay", "matTooltipHideDelay", "matTooltipTouchGestures", "matTooltip", "matTooltipClass"], exportAs: ["matTooltip"] }, { kind: "ngmodule", type: FsFilterModule }, { kind: "component", type: i1.FilterComponent, selector: "fs-filter", inputs: ["config"], outputs: ["closed", "opened", "ready"] }, { kind: "directive", type: i1.FilterHeadingDirective, selector: "[fsFilterHeading]" }, { 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: "component", type: ComponentChartComponent, selector: "app-report-component-chart", inputs: ["component", "data"] }, { kind: "component", type: ComponentKpiComponent, selector: "app-report-component-kpi", inputs: ["component", "data"] }, { kind: "component", type: ComponentListComponent, selector: "app-report-component-list", inputs: ["reportId", "component"] }, { kind: "component", type: ComponentTextComponent, selector: "app-report-component-text", inputs: ["html", "tokens", "editing"], outputs: ["saved", "editEnded"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
|
|
512
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "18.2.14", type: ReportComponentComponent, isStandalone: true, selector: "app-report-component", inputs: { reportId: { classPropertyName: "reportId", publicName: "reportId", isSignal: false, isRequired: false, transformFunction: null }, component: { classPropertyName: "component", publicName: "component", isSignal: false, isRequired: false, transformFunction: null }, groups: { classPropertyName: "groups", publicName: "groups", isSignal: false, isRequired: false, transformFunction: null }, editMode: { classPropertyName: "editMode", publicName: "editMode", isSignal: false, isRequired: false, transformFunction: null }, zoom: { classPropertyName: "zoom", publicName: "zoom", isSignal: false, isRequired: false, transformFunction: null }, snapper: { classPropertyName: "snapper", publicName: "snapper", isSignal: false, isRequired: false, transformFunction: null }, selected: { classPropertyName: "selected", publicName: "selected", isSignal: false, isRequired: false, transformFunction: null }, tokens: { classPropertyName: "tokens", publicName: "tokens", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { selectComponent: "selectComponent", positionChanged: "positionChanged", openSettings: "openSettings", removed: "removed" }, host: { properties: { "class.height-auto": "this.heightAuto" } }, viewQueries: [{ propertyName: "chartComponent", first: true, predicate: ComponentChartComponent, descendants: true }], usesOnChanges: true, ngImport: i0, template: "<div\n class=\"component-box\"\n [class.editing]=\"editMode\"\n [class.text]=\"isText\"\n [class.selected]=\"selected\"\n [style.padding]=\"bodyPadding\"\n (pointerdown)=\"onComponentPointerDown($event)\"\n (mousedown)=\"stopCanvasPan($event)\"\n (touchstart)=\"stopCanvasPan($event)\">\n <!-- The header is an fs-filter: heading template = title (and the edit-mode\n drag handle), actions = the menu, items = component-level filter groups,\n the same strip for every type (lists included). fs-filter reads its\n config once, so the block is keyed on the component-filter set to be\n recreated when it changes. -->\n <!-- A text block has no title bar \u2014 it IS its words, like a text box on a\n slide \u2014 so it gets neither the header nor the data actions. -->\n @for (key of isText ? [] : [filterKey]; track key) {\n <fs-filter\n class=\"component-filter\"\n [config]=\"filterConfig()\">\n <ng-template fsFilterHeading>\n <div\n class=\"component-title\"\n (pointerdown)=\"onDragStart($event)\">\n {{ component.title }}\n @if (truncated) {\n <mat-icon\n class=\"truncated-icon\"\n matTooltip=\"Showing a truncated result \u2014 refine the filters to see everything.\">\n warning_amber\n </mat-icon>\n }\n </div>\n </ng-template>\n </fs-filter>\n }\n <!-- The actions menu is floated top-right (absolute) rather than living in\n fs-filter's actions slot, so its ~40px button height no longer drives the\n header row's height. It overlays the box corner; the heading reserves\n right padding so a long title ellipsises before it. -->\n @if (!isText || (editMode && !textEditing())) {\n <button\n mat-icon-button\n class=\"component-menu\"\n [fsMenuTriggerFor]=\"menu\"\n (pointerdown)=\"$event.stopPropagation()\"\n (mousedown)=\"stopCanvasPan($event)\">\n <mat-icon>more_vert</mat-icon>\n </button>\n <!-- Beside its trigger, inside the same block: an fs-menu that finds no\n trigger of its own draws one. -->\n <fs-menu #menu>\n <ng-template\n fs-menu-item\n [hidden]=\"!isText\"\n (click)=\"editText()\">\n <mat-icon>edit</mat-icon>\n <span>Edit text</span>\n </ng-template>\n <ng-template\n fs-menu-item\n [hidden]=\"!isText\"\n (click)=\"deleteText()\">\n <mat-icon>delete</mat-icon>\n <span>Delete</span>\n </ng-template>\n <ng-template\n fs-menu-item\n [hidden]=\"isText\"\n (click)=\"settings()\">\n <mat-icon>tune</mat-icon>\n <span>Settings</span>\n </ng-template>\n <ng-template\n fs-menu-item\n [hidden]=\"isText\"\n (click)=\"exportCsv()\">\n <mat-icon>download</mat-icon>\n <span>Export CSV</span>\n </ng-template>\n <ng-template\n fs-menu-item\n [hidden]=\"!hidesColumns\"\n (click)=\"chooseColumns()\">\n <mat-icon>view_column</mat-icon>\n <span>Columns</span>\n </ng-template>\n </fs-menu>\n }\n <div class=\"component-body\">\n @if (isText) {\n <app-report-component-text\n [html]=\"component.config?.html ?? ''\"\n [tokens]=\"tokens()\"\n [editing]=\"textEditing()\"\n (saved)=\"onTextSaved($event)\"\n (editEnded)=\"textEditing.set(false)\">\n </app-report-component-text>\n } @else if (component.type === 'list') {\n <app-report-component-list\n [reportId]=\"reportId\"\n [component]=\"component\">\n </app-report-component-list>\n } @else if (loading()) {\n <div class=\"component-state\">\n <div class=\"loading-shimmer\"></div>\n </div>\n } @else if (error()) {\n <div class=\"component-state error\">\n {{ error() }}\n </div>\n } @else if (!data()?.rows?.length) {\n <div class=\"component-state\">\n No data\n </div>\n } @else if (component.type === 'kpi') {\n <app-report-component-kpi\n [component]=\"component\"\n [data]=\"data()\">\n </app-report-component-kpi>\n } @else {\n <app-report-component-chart\n [component]=\"component\"\n [data]=\"data()\">\n </app-report-component-chart>\n }\n <!-- In edit mode a transparent veil over the body makes the WHOLE\n component draggable (industry standard: you grab the object, not just\n its title bar) and keeps inner widgets from swallowing the gesture. -->\n @if (editMode && !textEditing()) {\n <div\n class=\"drag-veil\"\n (pointerdown)=\"onDragStart($event)\">\n </div>\n }\n </div>\n</div>\n<!-- Handles live OUTSIDE the clipped box so they straddle its edges. -->\n@if (editMode && selected) {\n @for (handle of resizeHandles; track handle) {\n <div\n class=\"handle handle-{{ handle }}\"\n (mousedown)=\"stopCanvasPan($event)\"\n (pointerdown)=\"onResizeStart($event, handle)\">\n </div>\n }\n}", styles: [":host{position:absolute;display:flex;flex-direction:column;font-size:10px;--mdc-outlined-button-container-height: 30px;--mdc-outlined-button-label-text-size: 10px;--mat-outlined-button-horizontal-padding: 15px;--mdc-text-button-container-height: 30px;--mdc-text-button-label-text-size: 10px;--mat-text-button-horizontal-padding: 15px;--mat-button-outlined-container-height: 30px;--mat-button-outlined-label-text-size: 10px;--mat-button-outlined-horizontal-padding: 15px;--mat-button-text-container-height: 30px;--mat-button-text-label-text-size: 10px;--mat-button-text-horizontal-padding: 15px}.component-box{position:relative;width:100%;flex:1 1 auto;min-height:0;box-sizing:border-box;display:flex;flex-direction:column;background:#fff;border:1px solid #e4e7eb;border-radius:6px;overflow:hidden;transition:box-shadow .12s ease,border-color .12s ease;cursor:default}.component-box.editing .component-title{cursor:grab}.component-box.editing .component-title:active{cursor:grabbing}.component-box.editing:hover{border-color:#9db3c8;box-shadow:0 2px 8px #0f172a14}.component-box.selected{border-color:var(--brand-primary-color);box-shadow:0 0 0 1px var(--brand-primary-color),0 4px 14px #2196f32e}.component-box.text{background:transparent;border-color:transparent;border-radius:0;overflow:visible}.component-box.text.editing{border-style:dashed;border-color:#cbd2d9}.component-box.text.editing:hover{box-shadow:none}.component-box.text.selected{border-style:solid;border-color:var(--brand-primary-color);box-shadow:0 0 0 1px var(--brand-primary-color)}:host ::ng-deep .component-filter .filter-bar-container{align-items:center!important}.component-filter{flex:0 0 auto;display:block;padding:0 0 4px}.component-filter .component-title{display:flex;align-items:center;gap:4px;-webkit-user-select:none;user-select:none;padding-right:40px;font-size:var(--report-heading-size);font-weight:600;color:#1f2933;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.component-filter .component-title .truncated-icon{font-size:16px;width:16px;height:16px;color:#f59e0b}.component-menu{position:absolute;top:2px;right:2px;z-index:30}.component-body{flex:1 1 auto;min-height:0;position:relative}:host(.height-auto) .component-state{min-height:120px}.drag-veil{position:absolute;inset:0;cursor:grab;touch-action:none}.drag-veil:active{cursor:grabbing}.component-state{width:100%;height:100%;display:flex;align-items:center;justify-content:center;font-size:12px;color:#7b8794;padding:8px;text-align:center}.component-state.error{color:#e15759}.loading-shimmer{width:70%;height:60%;border-radius:6px;background:linear-gradient(100deg,#f0f4f8 40%,#e4ebf2,#f0f4f8 60%);background-size:200% 100%;animation:shimmer 1.2s infinite linear}@keyframes shimmer{to{background-position-x:-200%}}.handle{position:absolute;width:14px;height:14px;display:flex;align-items:center;justify-content:center;touch-action:none;z-index:20;transform:scale(calc(1 / var(--canvas-zoom, 1)))}.handle:before{content:\"\";width:8px;height:8px;background:#fff;border:1.5px solid var(--brand-primary-color);border-radius:2px;box-shadow:0 1px 2px #0f172a33}.handle-nw{left:-7px;top:-7px;cursor:nwse-resize}.handle-n{left:calc(50% - 7px);top:-7px;cursor:ns-resize}.handle-ne{right:-7px;top:-7px;cursor:nesw-resize}.handle-e{right:-7px;top:calc(50% - 7px);cursor:ew-resize}.handle-se{right:-7px;bottom:-7px;cursor:nwse-resize}.handle-s{left:calc(50% - 7px);bottom:-7px;cursor:ns-resize}.handle-sw{left:-7px;bottom:-7px;cursor:nesw-resize}.handle-w{left:-7px;top:calc(50% - 7px);cursor:ew-resize}\n"], dependencies: [{ kind: "component", type: MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }, { kind: "component", type: MatIconButton, selector: "button[mat-icon-button]", exportAs: ["matButton"] }, { kind: "directive", type: MatTooltip, selector: "[matTooltip]", inputs: ["matTooltipPosition", "matTooltipPositionAtOrigin", "matTooltipDisabled", "matTooltipShowDelay", "matTooltipHideDelay", "matTooltipTouchGestures", "matTooltip", "matTooltipClass"], exportAs: ["matTooltip"] }, { kind: "ngmodule", type: FsFilterModule }, { kind: "component", type: i1.FilterComponent, selector: "fs-filter", inputs: ["config"], outputs: ["closed", "opened", "ready"] }, { kind: "directive", type: i1.FilterHeadingDirective, selector: "[fsFilterHeading]" }, { 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: "component", type: ComponentChartComponent, selector: "app-report-component-chart", inputs: ["component", "data"] }, { kind: "component", type: ComponentKpiComponent, selector: "app-report-component-kpi", inputs: ["component", "data"] }, { kind: "component", type: ComponentListComponent, selector: "app-report-component-list", inputs: ["reportId", "component"] }, { kind: "component", type: ComponentTextComponent, selector: "app-report-component-text", inputs: ["html", "tokens", "editing"], outputs: ["saved", "editEnded"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
|
|
570
513
|
}
|
|
571
514
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: ReportComponentComponent, decorators: [{
|
|
572
515
|
type: Component,
|
|
@@ -580,7 +523,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImpo
|
|
|
580
523
|
ComponentKpiComponent,
|
|
581
524
|
ComponentListComponent,
|
|
582
525
|
ComponentTextComponent,
|
|
583
|
-
], template: "<div\n class=\"component-box\"\n [class.editing]=\"editMode\"\n [class.text]=\"isText\"\n [class.selected]=\"selected\"\n [style.padding]=\"bodyPadding\"\n (pointerdown)=\"onComponentPointerDown($event)\"\n (mousedown)=\"stopCanvasPan($event)\"\n (touchstart)=\"stopCanvasPan($event)\">\n <!-- The header is an fs-filter: heading template = title (and the edit-mode\n drag handle), actions = the menu, items = component-level filter groups,\n the same strip for every type (lists included). fs-filter reads its\n config once, so the block is keyed on the component-filter set to be\n recreated when it changes. -->\n <!-- A text block has no title bar \u2014 it IS its words, like a text box on a\n slide \u2014 so it gets neither the header nor the data actions. -->\n @for (key of isText ? [] : [filterKey]; track key) {\n <fs-filter\n class=\"component-filter\"\n [config]=\"filterConfig()\">\n <ng-template fsFilterHeading>\n <div\n class=\"component-title\"\n (pointerdown)=\"onDragStart($event)\">\n {{ component.title }}\n @if (truncated) {\n <mat-icon\n class=\"truncated-icon\"\n matTooltip=\"Showing a truncated result \u2014 refine the filters to see everything.\">\n warning_amber\n </mat-icon>\n }\n </div>\n </ng-template>\n </fs-filter>\n }\n <!-- The actions menu is floated top-right (absolute) rather than living in\n fs-filter's actions slot, so its ~40px button height no longer drives the\n header row's height. It overlays the box corner; the heading reserves\n right padding so a long title ellipsises before it. -->\n @if (!isText || (editMode && !textEditing())) {\n <button\n mat-icon-button\n class=\"component-menu\"\n [fsMenuTriggerFor]=\"menu\"\n (pointerdown)=\"$event.stopPropagation()\"\n (mousedown)=\"stopCanvasPan($event)\">\n <mat-icon>more_vert</mat-icon>\n </button>\n <!-- Beside its trigger, inside the same block: an fs-menu that finds no\n trigger of its own draws one. -->\n <fs-menu #menu>\n <ng-template\n fs-menu-item\n [hidden]=\"!isText\"\n (click)=\"editText()\">\n <mat-icon>edit</mat-icon>\n <span>Edit text</span>\n </ng-template>\n <ng-template\n fs-menu-item\n [hidden]=\"!isText\"\n (click)=\"deleteText()\">\n <mat-icon>delete</mat-icon>\n <span>Delete</span>\n </ng-template>\n <ng-template\n fs-menu-item\n [hidden]=\"isText\"\n (click)=\"settings()\">\n <mat-icon>tune</mat-icon>\n <span>Settings</span>\n </ng-template>\n <ng-template\n fs-menu-item\n [hidden]=\"isText\"\n (click)=\"exportCsv()\">\n <mat-icon>download</mat-icon>\n <span>Export CSV</span>\n </ng-template>\n <ng-template\n fs-menu-item\n [hidden]=\"!hidesColumns\"\n (click)=\"chooseColumns()\">\n <mat-icon>view_column</mat-icon>\n <span>Columns</span>\n </ng-template>\n </fs-menu>\n }\n <div class=\"component-body\">\n @if (isText) {\n <app-report-component-text\n [html]=\"component.config?.html ?? ''\"\n [tokens]=\"tokens()\"\n [editing]=\"textEditing()\"\n (saved)=\"onTextSaved($event)\"\n (editEnded)=\"textEditing.set(false)\">\n </app-report-component-text>\n } @else if (component.type === 'list') {\n <app-report-component-list\n [reportId]=\"reportId\"\n [component]=\"component\">\n </app-report-component-list>\n } @else if (loading()) {\n <div class=\"component-state\">\n <div class=\"loading-shimmer\"></div>\n </div>\n } @else if (error()) {\n <div class=\"component-state error\">\n {{ error() }}\n </div>\n } @else if (!data()?.rows?.length) {\n <div class=\"component-state\">\n No data\n </div>\n } @else if (component.type === 'kpi') {\n <app-report-component-kpi\n [component]=\"component\"\n [data]=\"data()\">\n </app-report-component-kpi>\n } @else {\n <app-report-component-chart\n [component]=\"component\"\n [data]=\"data()\">\n </app-report-component-chart>\n }\n <!-- In edit mode a transparent veil over the body makes the WHOLE\n component draggable (industry standard: you grab the object, not just\n its title bar) and keeps inner widgets from swallowing the gesture. -->\n @if (editMode && !textEditing()) {\n <div\n class=\"drag-veil\"\n (pointerdown)=\"onDragStart($event)\">\n </div>\n }\n </div>\n</div>\n<!-- Handles live OUTSIDE the clipped box so they straddle its edges. -->\n@if (editMode && selected) {\n @
|
|
526
|
+
], template: "<div\n class=\"component-box\"\n [class.editing]=\"editMode\"\n [class.text]=\"isText\"\n [class.selected]=\"selected\"\n [style.padding]=\"bodyPadding\"\n (pointerdown)=\"onComponentPointerDown($event)\"\n (mousedown)=\"stopCanvasPan($event)\"\n (touchstart)=\"stopCanvasPan($event)\">\n <!-- The header is an fs-filter: heading template = title (and the edit-mode\n drag handle), actions = the menu, items = component-level filter groups,\n the same strip for every type (lists included). fs-filter reads its\n config once, so the block is keyed on the component-filter set to be\n recreated when it changes. -->\n <!-- A text block has no title bar \u2014 it IS its words, like a text box on a\n slide \u2014 so it gets neither the header nor the data actions. -->\n @for (key of isText ? [] : [filterKey]; track key) {\n <fs-filter\n class=\"component-filter\"\n [config]=\"filterConfig()\">\n <ng-template fsFilterHeading>\n <div\n class=\"component-title\"\n (pointerdown)=\"onDragStart($event)\">\n {{ component.title }}\n @if (truncated) {\n <mat-icon\n class=\"truncated-icon\"\n matTooltip=\"Showing a truncated result \u2014 refine the filters to see everything.\">\n warning_amber\n </mat-icon>\n }\n </div>\n </ng-template>\n </fs-filter>\n }\n <!-- The actions menu is floated top-right (absolute) rather than living in\n fs-filter's actions slot, so its ~40px button height no longer drives the\n header row's height. It overlays the box corner; the heading reserves\n right padding so a long title ellipsises before it. -->\n @if (!isText || (editMode && !textEditing())) {\n <button\n mat-icon-button\n class=\"component-menu\"\n [fsMenuTriggerFor]=\"menu\"\n (pointerdown)=\"$event.stopPropagation()\"\n (mousedown)=\"stopCanvasPan($event)\">\n <mat-icon>more_vert</mat-icon>\n </button>\n <!-- Beside its trigger, inside the same block: an fs-menu that finds no\n trigger of its own draws one. -->\n <fs-menu #menu>\n <ng-template\n fs-menu-item\n [hidden]=\"!isText\"\n (click)=\"editText()\">\n <mat-icon>edit</mat-icon>\n <span>Edit text</span>\n </ng-template>\n <ng-template\n fs-menu-item\n [hidden]=\"!isText\"\n (click)=\"deleteText()\">\n <mat-icon>delete</mat-icon>\n <span>Delete</span>\n </ng-template>\n <ng-template\n fs-menu-item\n [hidden]=\"isText\"\n (click)=\"settings()\">\n <mat-icon>tune</mat-icon>\n <span>Settings</span>\n </ng-template>\n <ng-template\n fs-menu-item\n [hidden]=\"isText\"\n (click)=\"exportCsv()\">\n <mat-icon>download</mat-icon>\n <span>Export CSV</span>\n </ng-template>\n <ng-template\n fs-menu-item\n [hidden]=\"!hidesColumns\"\n (click)=\"chooseColumns()\">\n <mat-icon>view_column</mat-icon>\n <span>Columns</span>\n </ng-template>\n </fs-menu>\n }\n <div class=\"component-body\">\n @if (isText) {\n <app-report-component-text\n [html]=\"component.config?.html ?? ''\"\n [tokens]=\"tokens()\"\n [editing]=\"textEditing()\"\n (saved)=\"onTextSaved($event)\"\n (editEnded)=\"textEditing.set(false)\">\n </app-report-component-text>\n } @else if (component.type === 'list') {\n <app-report-component-list\n [reportId]=\"reportId\"\n [component]=\"component\">\n </app-report-component-list>\n } @else if (loading()) {\n <div class=\"component-state\">\n <div class=\"loading-shimmer\"></div>\n </div>\n } @else if (error()) {\n <div class=\"component-state error\">\n {{ error() }}\n </div>\n } @else if (!data()?.rows?.length) {\n <div class=\"component-state\">\n No data\n </div>\n } @else if (component.type === 'kpi') {\n <app-report-component-kpi\n [component]=\"component\"\n [data]=\"data()\">\n </app-report-component-kpi>\n } @else {\n <app-report-component-chart\n [component]=\"component\"\n [data]=\"data()\">\n </app-report-component-chart>\n }\n <!-- In edit mode a transparent veil over the body makes the WHOLE\n component draggable (industry standard: you grab the object, not just\n its title bar) and keeps inner widgets from swallowing the gesture. -->\n @if (editMode && !textEditing()) {\n <div\n class=\"drag-veil\"\n (pointerdown)=\"onDragStart($event)\">\n </div>\n }\n </div>\n</div>\n<!-- Handles live OUTSIDE the clipped box so they straddle its edges. -->\n@if (editMode && selected) {\n @for (handle of resizeHandles; track handle) {\n <div\n class=\"handle handle-{{ handle }}\"\n (mousedown)=\"stopCanvasPan($event)\"\n (pointerdown)=\"onResizeStart($event, handle)\">\n </div>\n }\n}", styles: [":host{position:absolute;display:flex;flex-direction:column;font-size:10px;--mdc-outlined-button-container-height: 30px;--mdc-outlined-button-label-text-size: 10px;--mat-outlined-button-horizontal-padding: 15px;--mdc-text-button-container-height: 30px;--mdc-text-button-label-text-size: 10px;--mat-text-button-horizontal-padding: 15px;--mat-button-outlined-container-height: 30px;--mat-button-outlined-label-text-size: 10px;--mat-button-outlined-horizontal-padding: 15px;--mat-button-text-container-height: 30px;--mat-button-text-label-text-size: 10px;--mat-button-text-horizontal-padding: 15px}.component-box{position:relative;width:100%;flex:1 1 auto;min-height:0;box-sizing:border-box;display:flex;flex-direction:column;background:#fff;border:1px solid #e4e7eb;border-radius:6px;overflow:hidden;transition:box-shadow .12s ease,border-color .12s ease;cursor:default}.component-box.editing .component-title{cursor:grab}.component-box.editing .component-title:active{cursor:grabbing}.component-box.editing:hover{border-color:#9db3c8;box-shadow:0 2px 8px #0f172a14}.component-box.selected{border-color:var(--brand-primary-color);box-shadow:0 0 0 1px var(--brand-primary-color),0 4px 14px #2196f32e}.component-box.text{background:transparent;border-color:transparent;border-radius:0;overflow:visible}.component-box.text.editing{border-style:dashed;border-color:#cbd2d9}.component-box.text.editing:hover{box-shadow:none}.component-box.text.selected{border-style:solid;border-color:var(--brand-primary-color);box-shadow:0 0 0 1px var(--brand-primary-color)}:host ::ng-deep .component-filter .filter-bar-container{align-items:center!important}.component-filter{flex:0 0 auto;display:block;padding:0 0 4px}.component-filter .component-title{display:flex;align-items:center;gap:4px;-webkit-user-select:none;user-select:none;padding-right:40px;font-size:var(--report-heading-size);font-weight:600;color:#1f2933;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.component-filter .component-title .truncated-icon{font-size:16px;width:16px;height:16px;color:#f59e0b}.component-menu{position:absolute;top:2px;right:2px;z-index:30}.component-body{flex:1 1 auto;min-height:0;position:relative}:host(.height-auto) .component-state{min-height:120px}.drag-veil{position:absolute;inset:0;cursor:grab;touch-action:none}.drag-veil:active{cursor:grabbing}.component-state{width:100%;height:100%;display:flex;align-items:center;justify-content:center;font-size:12px;color:#7b8794;padding:8px;text-align:center}.component-state.error{color:#e15759}.loading-shimmer{width:70%;height:60%;border-radius:6px;background:linear-gradient(100deg,#f0f4f8 40%,#e4ebf2,#f0f4f8 60%);background-size:200% 100%;animation:shimmer 1.2s infinite linear}@keyframes shimmer{to{background-position-x:-200%}}.handle{position:absolute;width:14px;height:14px;display:flex;align-items:center;justify-content:center;touch-action:none;z-index:20;transform:scale(calc(1 / var(--canvas-zoom, 1)))}.handle:before{content:\"\";width:8px;height:8px;background:#fff;border:1.5px solid var(--brand-primary-color);border-radius:2px;box-shadow:0 1px 2px #0f172a33}.handle-nw{left:-7px;top:-7px;cursor:nwse-resize}.handle-n{left:calc(50% - 7px);top:-7px;cursor:ns-resize}.handle-ne{right:-7px;top:-7px;cursor:nesw-resize}.handle-e{right:-7px;top:calc(50% - 7px);cursor:ew-resize}.handle-se{right:-7px;bottom:-7px;cursor:nwse-resize}.handle-s{left:calc(50% - 7px);bottom:-7px;cursor:ns-resize}.handle-sw{left:-7px;bottom:-7px;cursor:nesw-resize}.handle-w{left:-7px;top:calc(50% - 7px);cursor:ew-resize}\n"] }]
|
|
584
527
|
}], propDecorators: { reportId: [{
|
|
585
528
|
type: Input
|
|
586
529
|
}], component: [{
|
|
@@ -589,8 +532,6 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImpo
|
|
|
589
532
|
type: Input
|
|
590
533
|
}], editMode: [{
|
|
591
534
|
type: Input
|
|
592
|
-
}], layout: [{
|
|
593
|
-
type: Input
|
|
594
535
|
}], zoom: [{
|
|
595
536
|
type: Input
|
|
596
537
|
}], snapper: [{
|
|
@@ -601,8 +542,6 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImpo
|
|
|
601
542
|
type: Output
|
|
602
543
|
}], positionChanged: [{
|
|
603
544
|
type: Output
|
|
604
|
-
}], flowReorder: [{
|
|
605
|
-
type: Output
|
|
606
545
|
}], openSettings: [{
|
|
607
546
|
type: Output
|
|
608
547
|
}], chartComponent: [{
|
|
@@ -612,4 +551,4 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImpo
|
|
|
612
551
|
type: HostBinding,
|
|
613
552
|
args: ['class.height-auto']
|
|
614
553
|
}] } });
|
|
615
|
-
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoicmVwb3J0LWNvbXBvbmVudC5jb21wb25lbnQuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi8uLi8uLi9zcmMvYXBwL3JlcG9ydHMvY29tcG9uZW50cy9yZXBvcnQtY29tcG9uZW50L3JlcG9ydC1jb21wb25lbnQuY29tcG9uZW50LnRzIiwiLi4vLi4vLi4vLi4vLi4vLi4vc3JjL2FwcC9yZXBvcnRzL2NvbXBvbmVudHMvcmVwb3J0LWNvbXBvbmVudC9yZXBvcnQtY29tcG9uZW50LmNvbXBvbmVudC5odG1sIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBLE9BQU8sRUFDTCx1QkFBdUIsRUFBRSxTQUFTLEVBQUUsVUFBVSxFQUFFLFVBQVUsRUFDMUQsWUFBWSxFQUFFLFdBQVcsRUFBRSxLQUFLLEVBQUUsTUFBTSxFQUFxQixNQUFNLEVBQWlCLFNBQVMsRUFBRSxNQUFNLEVBQ3JHLEtBQUssRUFBRSxNQUFNLEVBQUUsTUFBTSxHQUN0QixNQUFNLGVBQWUsQ0FBQztBQUd2QixPQUFPLEVBQUUsYUFBYSxFQUFFLE1BQU0sMEJBQTBCLENBQUM7QUFDekQsT0FBTyxFQUFFLFNBQVMsRUFBRSxNQUFNLDBCQUEwQixDQUFDO0FBQ3JELE9BQU8sRUFBRSxPQUFPLEVBQUUsTUFBTSx3QkFBd0IsQ0FBQztBQUNqRCxPQUFPLEVBQUUsVUFBVSxFQUFFLE1BQU0sMkJBQTJCLENBQUM7QUFFdkQsT0FBTyxFQUFnQixjQUFjLEVBQUUsTUFBTSxvQkFBb0IsQ0FBQztBQUNsRSxPQUFPLEVBQUUsWUFBWSxFQUFFLE1BQU0sa0JBQWtCLENBQUM7QUFDaEQsT0FBTyxFQUFFLFNBQVMsRUFBRSxNQUFNLHFCQUFxQixDQUFDO0FBQ2hELE9BQU8sRUFBRSxTQUFTLEVBQUUsTUFBTSxxQkFBcUIsQ0FBQztBQUNoRCxPQUFPLEVBQUUsUUFBUSxFQUFFLE1BQU0sb0JBQW9CLENBQUM7QUFFOUMsT0FBTyxFQUFFLE9BQU8sRUFBRSxZQUFZLEVBQUUsR0FBRyxF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d0JBQ2IsVUFBVTt3QkFDVixjQUFjO3dCQUNkLFlBQVk7d0JBQ1osdUJBQXVCO3dCQUN2QixxQkFBcUI7d0JBQ3JCLHNCQUFzQjt3QkFDdEIsc0JBQXNCO3FCQUN2Qjs4QkFJZSxRQUFRO3NCQUF2QixLQUFLO2dCQUNVLFNBQVM7c0JBQXhCLEtBQUs7Z0JBQ1UsTUFBTTtzQkFBckIsS0FBSztnQkFDVSxRQUFRO3NCQUF2QixLQUFLO2dCQUNVLE1BQU07c0JBQXJCLEtBQUs7Z0JBRVUsSUFBSTtzQkFBbkIsS0FBSztnQkFDVSxPQUFPO3NCQUF0QixLQUFLO2dCQUNVLFFBQVE7c0JBQXZCLEtBQUs7Z0JBRVcsZUFBZTtzQkFBL0IsTUFBTTtnQkFDVSxlQUFlO3NCQUEvQixNQUFNO2dCQUNVLFdBQVc7c0JBQTNCLE1BQU07Z0JBQ1UsWUFBWTtzQkFBNUIsTUFBTTtnQkFjQSxjQUFjO3NCQURwQixTQUFTO3VCQUFDLHVCQUF1QjtnQkFvaEJ2QixVQUFVO3NCQURwQixXQUFXO3VCQUFDLG1CQUFtQiIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7XG4gIENoYW5nZURldGVjdGlvblN0cmF0ZWd5LCBDb21wb25lbnQsIERlc3Ryb3lSZWYsIEVsZW1lbnRSZWYsXG4gIEV2ZW50RW1pdHRlciwgSG9zdEJpbmRpbmcsIElucHV0LCBOZ1pvbmUsIE9uQ2hhbmdlcywgT25Jbml0LCBPdXRwdXQsIFNpbXBsZUNoYW5nZXMsIFZpZXdDaGlsZCwgaW5qZWN0LFxuICBpbnB1dCwgb3V0cHV0LCBzaWduYWwsXG59IGZyb20gJ0Bhbmd1bGFyL2NvcmUnO1xuXG5cbmltcG9ydCB7IE1hdEljb25CdXR0b24gfSBmcm9tICdAYW5ndWxhci9tYXRlcmlhbC9idXR0b24nO1xuaW1wb3J0IHsgTWF0RGlhbG9nIH0gZnJvbSAnQGFuZ3VsYXIvbWF0ZXJpYWwvZGlhbG9nJztcbmltcG9ydCB7IE1hdEljb24gfSBmcm9tICdAYW5ndWxhci9tYXRlcmlhbC9pY29uJztcbmltcG9ydCB7IE1hdFRvb2x0aXAgfSBmcm9tICdAYW5ndWxhci9tYXRlcmlhbC90b29sdGlwJztcblxuaW1wb3J0IHsgRmlsdGVyQ29uZmlnLCBGc0ZpbHRlck1vZHVsZSB9IGZyb20gJ0BmaXJlc3RpdGNoL2ZpbHRlcic7XG5pbXBvcnQgeyBGc01lbnVNb2R1bGUgfSBmcm9tICdAZmlyZXN0aXRjaC9tZW51JztcbmltcG9ydCB7IEZzTWVzc2FnZSB9IGZyb20gJ0BmaXJlc3RpdGNoL21lc3NhZ2UnO1xuaW1wb3J0IHsgRnNQcm9jZXNzIH0gZnJvbSAnQGZpcmVzdGl0Y2gvcHJvY2Vzcyc7XG5pbXBvcnQgeyBGc1Byb21wdCB9IGZyb20gJ0BmaXJlc3RpdGNoL3Byb21wdCc7XG5cbmltcG9ydCB7IFN1YmplY3QsIGRlYm91bmNlVGltZSwgbWFwLCBzd2l0Y2hNYXAsIHRhcCB9IGZyb20gJ3J4anMnO1xuXG5pbXBvcnQgeyB0YWtlVW50aWxEZXN0cm95ZWQgfSBmcm9tICdAYW5ndWxhci9jb3JlL3J4anMtaW50ZXJvcCc7XG5cbmltcG9ydCB7IFJlcG9ydERhdGEgfSBmcm9tICcuLi8uLi9kYXRhL3JlcG9ydC5kYXRhJztcbmltcG9ydCB7IExpc3RDb2x1bW5zQ29tcG9uZW50LCBMaXN0Q29sdW1uc0RpYWxvZ0RhdGEgfSBmcm9tICcuLi8uLi9kaWFsb2dzL2xpc3QtY29sdW1ucy9saXN0LWNvbHVtbnMuY29tcG9uZW50JztcbmltcG9ydCB7XG4gIENvbXBvbmVudERhdGEsXG4gIENvbXBvbmVudERhdGFTdGF0ZSxcbiAgQ29tcG9uZW50U2V0dGluZ3MsXG4gIFJlcG9ydENvbXBvbmVudCBhcyBSZXBvcnRDb21wb25lbnRNb2RlbCxcbiAgUmVwb3J0RmlsdGVyR3JvdXAsXG4gIFJlcG9ydExheW91dCxcbn0gZnJvbSAnLi4vLi4vaW50ZXJmYWNlcy9yZXBvcnQuaW50ZXJmYWNlJztcbmltcG9ydCB7IERFRkFVTFRfQ09NUE9ORU5UX1BBRERJTkcgfSBmcm9tICcuLi8uLi9sYXlvdXQnO1xuaW1wb3J0IHsgbGlzdEhpZGVhYmxlQ29sdW1ucyB9IGZyb20gJy4uLy4uL2xpc3QtY29uZmlnJztcbmltcG9ydCB7XG4gIExJU1RfU0VBUkNIX0lURU0sIGZpbHRlckl0ZW1Gb3JHcm91cCwgZ3JvdXBWYWx1ZXNGcm9tUXVlcnksIGxpc3RTZWFyY2hJdGVtLFxufSBmcm9tICcuLi8uLi9yZXBvcnQtZmlsdGVyLWl0ZW1zJztcbmltcG9ydCB7IG1vdmVkR3JvdXBWYWx1ZXMsIFJlcG9ydEZpbHRlclN0YXRlU2VydmljZSB9IGZyb20gJy4uLy4uL3NlcnZpY2VzL3JlcG9ydC1maWx0ZXItc3RhdGUuc2VydmljZSc7XG5pbXBvcnQgeyBDb21wb25lbnRDaGFydENvbXBvbmVudCB9IGZyb20gJy4uL2NvbXBvbmVudC1jaGFydC9jb21wb25lbnQtY2hhcnQuY29tcG9uZW50JztcbmltcG9ydCB7IENvbXBvbmVudEtwaUNvbXBvbmVudCB9IGZyb20gJy4uL2NvbXBvbmVudC1rcGkvY29tcG9uZW50LWtwaS5jb21wb25lbnQnO1xuaW1wb3J0IHsgQ29tcG9uZW50TGlzdENvbXBvbmVudCB9IGZyb20gJy4uL2NvbXBvbmVudC1saXN0L2NvbXBvbmVudC1saXN0LmNvbXBvbmVudCc7XG5pbXBvcnQgeyBDb21wb25lbnRUZXh0Q29tcG9uZW50IH0gZnJvbSAnLi4vY29tcG9uZW50LXRleHQvY29tcG9uZW50LXRleHQuY29tcG9uZW50JztcbmltcG9ydCB7IFRleHRUb2tlbkNvbnRleHQgfSBmcm9tICcuLi8uLi90ZXh0JztcbmltcG9ydCB7IENhbnZhc1NuYXBwZXIsIFBYX1BFUl9JTkNIIH0gZnJvbSAnLi4vcmVwb3J0LWNhbnZhcy9yZXBvcnQtY2FudmFzLmNvbXBvbmVudCc7XG5cblxuLy8gRnJlZWZvcm0gcmVzaXplIGhhbmRsZXMsIG5hbWVkIGJ5IGNvbXBhc3MgZGlyZWN0aW9uLlxuY29uc3QgSEFORExFUyA9IFsnbncnLCAnbicsICduZScsICdlJywgJ3NlJywgJ3MnLCAnc3cnLCAndyddIGFzIGNvbnN0O1xudHlwZSBIYW5kbGUgPSB0eXBlb2YgSEFORExFU1tudW1iZXJdO1xuXG4vLyBGbG93IHdpZHRoIHNuYXBzIHRvIHRoZSB1c2VmdWwgZnJhY3Rpb25zIG9mIGEgcGFnZSByb3cuXG5jb25zdCBGTE9XX1dJRFRIX1NUT1BTID0gWzI1LCAzMy4zMywgNTAsIDY2LjY3LCA3NSwgMTAwXTtcblxuY29uc3QgTUlOX1cgPSAwLjY7IC8vIGluY2hlc1xuY29uc3QgTUlOX0ggPSAwLjQ7IC8vIGluY2hlc1xuXG4vLyBUd28gcHJlc3NlcyBvbiBhIHRleHQgYmxvY2sgdGhpcyBjbG9zZSB0b2dldGhlciBvcGVuIGl0cyBlZGl0b3IuIERldGVjdGVkXG4vLyBoZXJlIHJhdGhlciB0aGFuIHdpdGggYSBkYmxjbGljayBsaXN0ZW5lciBiZWNhdXNlIHRoZSBkcmFnIGxvb3AgY2xhaW1zIHRoZVxuLy8gcG9pbnRlciBvbiBldmVyeSBwcmVzcywgYW5kIGEgYnJvd3NlciBpcyBub3Qgb2JsaWdlZCB0byBkZWxpdmVyIGRibGNsaWNrXG4vLyB0aHJvdWdoIGEgY2FwdHVyZWQsIGRlZmF1bHQtcHJldmVudGVkIHBvaW50ZXIuXG5jb25zdCBET1VCTEVfUFJFU1NfTVMgPSA0MDA7XG5cbi8vIE9uZSBjb21wb25lbnQgb24gdGhlIHBhZ2U6IHRpdGxlIGJhciwgdGhlIHR5cGUtc3BlY2lmaWMgYm9keSAoY2hhcnQgfCBsaXN0XG4vLyB8IGtwaSksIGEgbWVudSAoc2V0dGluZ3MsIGZpbHRlciB0b2dnbGVzLCBleHBvcnQpIOKAlCBhbmQgdGhlIGVkaXRpbmdcbi8vIGludGVyYWN0aW9uczpcbi8vXG4vLyAgIEZyZWVmb3JtOiBjbGljayBzZWxlY3RzOyB0aGUgc2VsZWN0aW9uIGZyYW1lIHNob3dzIDggcmVzaXplIGhhbmRsZXM7XG4vLyAgIGRyYWdnaW5nIHRoZSBib2R5IG1vdmVzIHdpdGggc21hcnQgYWxpZ25tZW50IGd1aWRlcyAodmlhIHRoZSBjYW52YXNcbi8vICAgc25hcHBlcik7IGV2ZXJ5dGhpbmcgd29ya3MgYXQgYW55IHpvb20gKHBpeGVsIGRlbHRhcyDDtyB6b29twrc5NiDihpIgaW5jaGVzKS5cbi8vXG4vLyAgIEZsb3c6IGRyYWdnaW5nIHJlb3JkZXJzIChkcm9wIHBvc2l0aW9uIGRlY2lkZWQgYnkgdGhlIGNhbnZhcyk7IHRoZSBFXG4vLyAgIGhhbmRsZSByZXNpemVzIGZsb3dXaWR0aCAlIChzbmFwcGluZyB0byAyNS8zMy81MC82Ni83NS8xMDApLCB0aGUgUyBoYW5kbGVcbi8vICAgcmVzaXplcyBoZWlnaHQgaW4gaW5jaGVzLlxuLy9cbi8vIENoYXJ0cyBhbmQgS1BJcyBmZXRjaCB0aGVpciBvd24gZGF0YSBoZXJlOyBsaXN0cyBmZXRjaCBpbnNpZGVcbi8vIENvbXBvbmVudExpc3RDb21wb25lbnQgdGhyb3VnaCBGc0xpc3QgcGFnaW5nLlxuQENvbXBvbmVudCh7XG4gIHNlbGVjdG9yOiAnYXBwLXJlcG9ydC1jb21wb25lbnQnLFxuICB0ZW1wbGF0ZVVybDogJy4vcmVwb3J0LWNvbXBvbmVudC5jb21wb25lbnQuaHRtbCcsXG4gIHN0eWxlVXJsczogWycuL3JlcG9ydC1jb21wb25lbnQuY29tcG9uZW50LnNjc3MnXSxcbiAgY2hhbmdlRGV0ZWN0aW9uOiBDaGFuZ2VEZXRlY3Rpb25TdHJhdGVneS5PblB1c2gsXG4gIHN0YW5kYWxvbmU6IHRydWUsXG4gIGltcG9ydHM6IFtcbiAgICBNYXRJY29uLFxuICAgIE1hdEljb25CdXR0b24sXG4gICAgTWF0VG9vbHRpcCxcbiAgICBGc0ZpbHRlck1vZHVsZSxcbiAgICBGc01lbnVNb2R1bGUsXG4gICAgQ29tcG9uZW50Q2hhcnRDb21wb25lbnQsXG4gICAgQ29tcG9uZW50S3BpQ29tcG9uZW50LFxuICAgIENvbXBvbmVudExpc3RDb21wb25lbnQsXG4gICAgQ29tcG9uZW50VGV4dENvbXBvbmVudCxcbiAgXSxcbn0pXG5leHBvcnQgY2xhc3MgUmVwb3J0Q29tcG9uZW50Q29tcG9uZW50IGltcGxlbWVudHMgT25Jbml0LCBPbkNoYW5nZXMge1xuXG4gIEBJbnB1dCgpIHB1YmxpYyByZXBvcnRJZDogbnVtYmVyO1xuICBASW5wdXQoKSBwdWJsaWMgY29tcG9uZW50OiBSZXBvcnRDb21wb25lbnRNb2RlbDtcbiAgQElucHV0KCkgcHVibGljIGdyb3VwczogTWFwPG51bWJlciwgUmVwb3J0RmlsdGVyR3JvdXA+O1xuICBASW5wdXQoKSBwdWJsaWMgZWRpdE1vZGUgPSBmYWxzZTtcbiAgQElucHV0KCkgcHVibGljIGxheW91dDogUmVwb3J0TGF5b3V0ID0gJ2ZyZWVmb3JtJztcbiAgLy8gVGhlIGNhbnZhcyB6b29tIOKAlCBjb252ZXJ0cyBvbi1zY3JlZW4gcGl4ZWwgZGVsdGFzIGJhY2sgdG8gaW5jaGVzLlxuICBASW5wdXQoKSBwdWJsaWMgem9vbSA9IDE7XG4gIEBJbnB1dCgpIHB1YmxpYyBzbmFwcGVyOiBDYW52YXNTbmFwcGVyIHwgbnVsbCA9IG51bGw7XG4gIEBJbnB1dCgpIHB1YmxpYyBzZWxlY3RlZCA9IGZhbHNlO1xuXG4gIEBPdXRwdXQoKSBwdWJsaWMgc2VsZWN0Q29tcG9uZW50ID0gbmV3IEV2ZW50RW1pdHRlcjxudW1iZXI+KCk7XG4gIEBPdXRwdXQoKSBwdWJsaWMgcG9zaXRpb25DaGFuZ2VkID0gbmV3IEV2ZW50RW1pdHRlcjx7IGNvbXBvbmVudElkOiBudW1iZXIgfSAmIFJlY29yZDxzdHJpbmcsIG51bWJlcj4+KCk7XG4gIEBPdXRwdXQoKSBwdWJsaWMgZmxvd1Jlb3JkZXIgPSBuZXcgRXZlbnRFbWl0dGVyPHsgY29tcG9uZW50SWQ6IG51bWJlcjsgY2xpZW50WDogbnVtYmVyOyBjbGllbnRZOiBudW1iZXIgfT4oKTtcbiAgQE91dHB1dCgpIHB1YmxpYyBvcGVuU2V0dGluZ3MgPSBuZXcgRXZlbnRFbWl0dGVyPFJlcG9ydENvbXBvbmVudE1vZGVsPigpO1xuXG4gIC8vIFdoYXQgYSB0ZXh0IGJsb2NrJ3Mge3t0b2tlbnN9fSBmaWxsIHdpdGggb24gdGhlIHBhZ2UgaXQgaXMgZHJhd24gb24uXG4gIHB1YmxpYyByZWFkb25seSB0b2tlbnMgPSBpbnB1dDxUZXh0VG9rZW5Db250ZXh0Pih7IHBhZ2VOdW1iZXI6IDEsIHBhZ2VOYW1lOiAnJywgcmVwb3J0TmFtZTogJycgfSk7XG5cbiAgLy8gQSB0ZXh0IGJsb2NrIHdhcyBkZWxldGVkIGZyb20gaXRzIG1lbnUg4oCUIHRoZSBjYW52YXMgZHJvcHMgaXQuXG4gIHB1YmxpYyByZWFkb25seSByZW1vdmVkID0gb3V0cHV0PG51bWJlcj4oKTtcblxuICAvLyBUaGUgdGV4dCBibG9jaydzIGVkaXRvciBpcyBvcGVuIChkb3VibGUtcHJlc3MgaW4gZWRpdCBtb2RlKS4gQ2xvc2VkIGJ5IGZvY3VzXG4gIC8vIGxlYXZpbmcgdGhlIGJsb2NrLCBieSBkZXNlbGVjdGluZyBpdCwgb3IgYnkgbGVhdmluZyBlZGl0IG1vZGUg4oCUIGVhY2ggb2ZcbiAgLy8gd2hpY2ggc2F2ZXMuXG4gIHB1YmxpYyByZWFkb25seSB0ZXh0RWRpdGluZyA9IHNpZ25hbChmYWxzZSk7XG5cbiAgQFZpZXdDaGlsZChDb21wb25lbnRDaGFydENvbXBvbmVudClcbiAgcHVibGljIGNoYXJ0Q29tcG9uZW50OiBDb21wb25lbnRDaGFydENvbXBvbmVudDtcblxuICAvLyBGcmVlZm9ybSByZXNpemUgaGFuZGxlcyBieSB0eXBlOiBhIGZpeGVkLWhlaWdodCBjb21wb25lbnQgKGNoYXJ0L2xpc3QpXG4gIC8vIGdldHMgYWxsIGVpZ2h0IChyZXNpemUgd2lkdGggQU5EIGhlaWdodCk7IGFuIGF1dG8taGVpZ2h0IG9uZSAoa3BpKSBnZXRzXG4gIC8vIG9ubHkgdGhlIHNpZGUgaGFuZGxlcyBzaW5jZSBpdHMgaGVpZ2h0IGZpdHMgaXRzIGNvbnRlbnQgYW5kIGNhbid0IGJlIHNldC5cbiAgcHVibGljIGdldCByZXNpemVIYW5kbGVzKCk6IHJlYWRvbmx5IEhhbmRsZVtdIHtcbiAgICByZXR1cm4gdGhpcy5faGVpZ2h0QXV0byA/IFsnZScsICd3J10gOiBIQU5ETEVTO1xuICB9XG5cbiAgLy8gVGhlIGNvbXBvbmVudCdzIGhlYWRlciBJUyBhbiBmcy1maWx0ZXI6IGhlYWRpbmcgdGVtcGxhdGUgPSBpdHMgdGl0bGUgKGFuZFxuICAvLyB0aGUgZHJhZyBoYW5kbGUpLCBhY3Rpb25zID0gdGhlIFNldHRpbmdzIC8gZmlsdGVyLXRvZ2dsZXMgLyBFeHBvcnQgbWVudSxcbiAgLy8gaXRlbXMgPSBpdHMgY29tcG9uZW50LWxldmVsIGZpbHRlciBncm91cHMsIGZvciBldmVyeSBjb21wb25lbnQgdHlwZSwgbGlzdHNcbiAgLy8gaW5jbHVkZWQsIHBsdXMgYSBsaXN0J3Mgc2VhcmNoIGJveC4gUmVidWlsdCB3aGVuIGEgZmlsdGVyIHRvZ2dsZSBjaGFuZ2VzIHdoaWNoIGdyb3VwcyBzaG93LFxuICAvLyBhbmQgd2hlbiB0aGUgc2V0dGluZ3MgZGlhbG9nIGNoYW5nZXMgdGhlIHRpdGxlIG9yIHBhZGRpbmc6IHNldHRpbmcgaXRcbiAgLy8gcmVwYWludHMgdGhlIGhlYWRlciBhbmQgYm9keS5cbiAgcHVibGljIHJlYWRvbmx5IGZpbHRlckNvbmZpZyA9IHNpZ25hbDxGaWx0ZXJDb25maWcgfCBudWxsPihudWxsKTtcblxuICBwdWJsaWMgcmVhZG9ubHkgZGF0YSA9IHNpZ25hbDxDb21wb25lbnREYXRhIHwgbnVsbD4obnVsbCk7XG4gIHB1YmxpYyByZWFkb25seSBsb2FkaW5nID0gc2lnbmFsKGZhbHNlKTtcbiAgcHVibGljIHJlYWRvbmx5IGVycm9yID0gc2lnbmFsPHN0cmluZyB8IG51bGw+KG51bGwpO1xuXG4gIHByaXZhdGUgX3JlZnJlc2gkID0gbmV3IFN1YmplY3Q8dm9pZD4oKTtcbiAgcHJpdmF0ZSBfcmVwb3J0RGF0YSA9IGluamVjdChSZXBvcnREYXRhKTtcbiAgcHJpdmF0ZSBfZmlsdGVyU3RhdGUgPSBpbmplY3QoUmVwb3J0RmlsdGVyU3RhdGVTZXJ2aWNlKTtcbiAgcHJpdmF0ZSBfcHJvY2VzcyA9IGluamVjdChGc1Byb2Nlc3MpO1xuICBwcml2YXRlIF9tZXNzYWdlID0gaW5qZWN0KEZzTWVzc2FnZSk7XG4gIHByaXZhdGUgX3Byb21wdCA9IGluamVjdChGc1Byb21wdCk7XG4gIHByaXZhdGUgX2RpYWxvZyA9IGluamVjdChNYXREaWFsb2cpO1xuICBwcml2YXRlIF9sYXN0UHJlc3MgPSAwO1xuICBwcml2YXRlIF9kZXN0cm95UmVmID0gaW5qZWN0KERlc3Ryb3lSZWYpO1xuICBwcml2YXRlIF96b25lID0gaW5qZWN0KE5nWm9uZSk7XG4gIHByaXZhdGUgX2hvc3Q6IEVsZW1lbnRSZWY8SFRNTEVsZW1lbnQ+ID0gaW5qZWN0KEVsZW1lbnRSZWYpO1xuXG4gIHB1YmxpYyBuZ09uSW5pdCgpOiB2b2lkIHtcbiAgICB0aGlzLl9idWlsZEZpbHRlckNvbmZpZygpO1xuXG4gICAgLy8gTGlzdHMgZmV0Y2ggdGhyb3VnaCBGc0xpc3Q7IHRleHQgaGFzIG5vdGhpbmcgdG8gZmV0Y2guXG4gICAgaWYgKHRoaXMuY29tcG9uZW50LnR5cGUgIT09ICdsaXN0JyAmJiAhdGhpcy5pc1RleHQpIHtcbiAgICAgIC8vIERlYm91bmNlZCBzbyBhIHJhcGlkIGZpbHRlciBzd2VlcCBmaXJlcyBvbmUgcXVlcnksIG5vdCBvbmUgcGVyIGNoYW5nZS5cbiAgICAgIHRoaXMuX3JlZnJlc2gkXG4gICAgICAgIC5waXBlKFxuICAgICAgICAgIGRlYm91bmNlVGltZSgzMDApLFxuICAgICAgICAgIHRha2VVbnRpbERlc3Ryb3llZCh0aGlzLl9kZXN0cm95UmVmKSxcbiAgICAgICAgKVxuICAgICAgICAuc3Vic2NyaWJlKCgpID0+IHRoaXMuX2xvYWQoKSk7XG5cbiAgICAgIHRoaXMuX2ZpbHRlclN0YXRlLmNoYW5nZXNGb3IodGhpcy5jb21wb25lbnQpXG4gICAgICAgIC5waXBlKHRha2VVbnRpbERlc3Ryb3llZCh0aGlzLl9kZXN0cm95UmVmKSlcbiAgICAgICAgLnN1YnNjcmliZSgoKSA9PiB0aGlzLl9yZWZyZXNoJC5uZXh0KCkpO1xuXG4gICAgICAvLyBBIGdyb3VwLWJ5IGNoYW5nZSByZS1idWNrZXRzIGV2ZXJ5IHRpbWUtc2VyaWVzIGNoYXJ0OyBpdCBpc24ndCBzY29wZWRcbiAgICAgIC8vIHRvIGEgZmlsdGVyIGdyb3VwLCBzbyBpdCByaWRlcyBpdHMgb3duIHN0cmVhbS5cbiAgICAgIGlmICh0aGlzLl9pc1RpbWVTZXJpZXMpIHtcbiAgICAgICAgdGhpcy5fZmlsdGVyU3RhdGUuZnJlcXVlbmN5Q2hhbmdlcygpXG4gICAgICAgICAgLnBpcGUodGFrZVVudGlsRGVzdHJveWVkKHRoaXMuX2Rlc3Ryb3lSZWYpKVxuICAgICAgICAgIC5zdWJzY3JpYmUoKCkgPT4gdGhpcy5fcmVmcmVzaCQubmV4dCgpKTtcbiAgICAgIH1cblxuICAgICAgdGhpcy5fbG9hZCgpO1xuICAgIH1cbiAgfVxuXG4gIC8vIFRoZSByZXBvcnQgcmVsb2FkcyAoZS5nLiBhZnRlciB0aGUgc2V0dGluZ3MgZGlhbG9nIGFkZHMvbW92ZXMgYSBmaWx0ZXIpXG4gIC8vIGhhbmQgdGhpcyBpbnN0YW5jZSBmcmVzaCBgY29tcG9uZW50YC9gZ3JvdXBzYCBpbnB1dHMgd2l0aG91dCByZS1ydW5uaW5nXG4gIC8vIG5nT25Jbml0LiBSZWJ1aWxkIHRoZSBoZWFkZXIgY29uZmlnIHNvIHRoZSBpbmxpbmUgY29tcG9uZW50LWZpbHRlciBzdHJpcFxuICAvLyByZWZsZWN0cyB0aGUgbmV3IGZpbHRlcnM7IHRoZSB0ZW1wbGF0ZSByZWNyZWF0ZXMgdGhlIGZzLWZpbHRlciB2aWFcbiAgLy8gYGZpbHRlcktleWAgc28gaXQgYWN0dWFsbHkgcmUtcmVhZHMgdGhpcyBjb25maWcuXG4gIHB1YmxpYyBuZ09uQ2hhbmdlcyhjaGFuZ2VzOiBTaW1wbGVDaGFuZ2VzKTogdm9pZCB7XG4gICAgLy8gQ2xpY2tpbmcgYXdheSAoZGVzZWxlY3QpIG9yIGxlYXZpbmcgZWRpdCBtb2RlIGNsb3NlcyBhbiBvcGVuIHRleHQgZWRpdG9yLFxuICAgIC8vIHdoaWNoIGlzIHdoYXQgc2F2ZXMgaXQuXG4gICAgaWYgKChjaGFuZ2VzLnNlbGVjdGVkICYmICF0aGlzLnNlbGVjdGVkKSB8fCAoY2hhbmdlcy5lZGl0TW9kZSAmJiAhdGhpcy5lZGl0TW9kZSkpIHtcbiAgICAgIHRoaXMudGV4dEVkaXRpbmcuc2V0KGZhbHNlKTtcbiAgICB9XG5cbiAgICBjb25zdCBmaWx0ZXJzQ2hhbmdlZCA9IChjaGFuZ2VzLmNvbXBvbmVudCAmJiAhY2hhbmdlcy5jb21wb25lbnQuZmlyc3RDaGFuZ2UpXG4gICAgICB8fCAoY2hhbmdlcy5ncm91cHMgJiYgIWNoYW5nZXMuZ3JvdXBzLmZpcnN0Q2hhbmdlKTtcblxuICAgIGlmIChmaWx0ZXJzQ2hhbmdlZCkge1xuICAgICAgdGhpcy5fYnVpbGRGaWx0ZXJDb25maWcoKTtcbiAgICB9XG4gIH1cblxuICAvLyBmcy1maWx0ZXIgcmVhZHMgaXRzIGNvbmZpZyBvbmx5IG9uY2UgYXQgaW5pdCwgc28gdGhlIGhlYWRlciBpcyBrZXllZCBvbiB3aGF0XG4gIC8vIGl0IHJlbmRlcnM6IHRoZSBzZXQgb2YgY29tcG9uZW50LWxldmVsIGZpbHRlciBncm91cHMgQU5EIHRoZSB0aXRsZSwgd2hpY2hcbiAgLy8gbGl2ZXMgaW4gZnMtZmlsdGVyJ3MgaGVhZGluZyB0ZW1wbGF0ZS4gZnMtZmlsdGVyIGlzIE9uUHVzaCBhbmQgdGhlIGhlYWRpbmcgaXNcbiAgLy8gcmVuZGVyZWQgaW5zaWRlIElUUyB2aWV3LCBzbyBtYXJraW5nIHRoaXMgY29tcG9uZW50IGRvZXMgbm90IHJlcGFpbnQgdGhlXG4gIC8vIHRpdGxlIOKAlCByZWNyZWF0aW5nIHRoZSBibG9jayBkb2VzLlxuICBwdWJsaWMgZ2V0IGZpbHRlcktleSgpOiBzdHJpbmcge1xuICAgIHJldHVybiBbXG4gICAgICB0aGlzLmNvbXBvbmVudC50aXRsZSxcbiAgICAgIC4uLnRoaXMuY29tcG9uZW50RmlsdGVyR3JvdXBzLm1hcCgoZ3JvdXApID0+IGAke2dyb3VwLmlkfToke2dyb3VwLmxldmVsfWApLFxuICAgIF0uam9pbignfCcpO1xuICB9XG5cbiAgcHVibGljIGdldCBpc1RleHQoKTogYm9vbGVhbiB7XG4gICAgcmV0dXJuIHRoaXMuY29tcG9uZW50LnR5cGUgPT09ICd0ZXh0JztcbiAgfVxuXG4gIC8vIE9wZW4gdGhlIHRleHQgZWRpdG9yIGluIHBsYWNlLlxuICBwdWJsaWMgZWRpdFRleHQoKTogdm9pZCB7XG4gICAgaWYgKCF0aGlzLmVkaXRNb2RlIHx8ICF0aGlzLmlzVGV4dCkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIHRoaXMuc2VsZWN0Q29tcG9uZW50LmVtaXQodGhpcy5jb21wb25lbnQuaWQpO1xuICAgIHRoaXMudGV4dEVkaXRpbmcuc2V0KHRydWUpO1xuICB9XG5cbiAgLy8gVGhlIGVkaXRvciBjbG9zZWQgd2l0aCBjaGFuZ2VkIGh0bWwuIEtlcHQgbG9jYWxseSBhdCBvbmNlIHNvIHRoZSBibG9ja1xuICAvLyByZS1yZW5kZXJzIHdoYXQgd2FzIHR5cGVkOyB0aGUgc2VydmVyIHJlYnVpbGRzIGl0IGZyb20gaXRzIGFsbG93bGlzdCwgd2hpY2hcbiAgLy8gZm9yIGFueXRoaW5nIHRoZSBlZGl0b3IgY2FuIHByb2R1Y2UgaXMgdGhlIHNhbWUgaHRtbC5cbiAgcHVibGljIG9uVGV4dFNhdmVkKGh0bWw6IHN0cmluZyk6IHZvaWQge1xuICAgIHRoaXMuY29tcG9uZW50LmNvbmZpZyA9IHsgLi4udGhpcy5jb21wb25lbnQuY29uZmlnLCBodG1sIH07XG4gICAgdGhpcy5fcmVwb3J0RGF0YS51cGRhdGVDb21wb25lbnQodGhpcy5yZXBvcnRJZCwgdGhpcy5jb21wb25lbnQuaWQsIHsgaHRtbCB9KVxuICAgICAgLnBpcGUodGFrZVVudGlsRGVzdHJveWVkKHRoaXMuX2Rlc3Ryb3lSZWYpKVxuICAgICAgLnN1YnNjcmliZSgpO1xuICB9XG5cbiAgcHVibGljIGRlbGV0ZVRleHQoKTogdm9pZCB7XG4gICAgdGhpcy5fcHJvbXB0LmNvbmZpcm0oe1xuICAgICAgdGl0bGU6ICdDb25maXJtJyxcbiAgICAgIHRlbXBsYXRlOiAnQXJlIHlvdSBzdXJlIHlvdSB3b3VsZCBsaWtlIHRvIGRlbGV0ZSB0aGlzIHRleHQ/JyxcbiAgICB9KVxuICAgICAgLnBpcGUoXG4gICAgICAgIHN3aXRjaE1hcCgoKSA9PiB0aGlzLl9yZXBvcnREYXRhLmRlbGV0ZUNvbXBvbmVudCh0aGlzLnJlcG9ydElkLCB0aGlzLmNvbXBvbmVudC5pZCkpLFxuICAgICAgICB0YWtlVW50aWxEZXN0cm95ZWQodGhpcy5fZGVzdHJveVJlZiksXG4gICAgICApXG4gICAgICAuc3Vic2NyaWJlKCgpID0+IHRoaXMucmVtb3ZlZC5lbWl0KHRoaXMuY29tcG9uZW50LmlkKSk7XG4gIH1cblxuICBwdWJsaWMgZ2V0IHRydW5jYXRlZCgpOiBib29sZWFuIHtcbiAgICByZXR1cm4gISF0aGlzLmRhdGEoKT8udHJ1bmNhdGVkO1xuICB9XG5cbiAgLy8gQ29udGVudCBwYWRkaW5nIChpbmNoZXMg4oaSIHB4IGF0IDk2L2luOyB0aGUgY2FudmFzIHpvb20gc2NhbGVzIHRoZSBwYWdlIGFzXG4gIC8vIGEgd2hvbGUpLiBFYWNoIGVkZ2UgZGVmYXVsdHMgdG8gMS84XCIuXG4gIHB1YmxpYyBnZXQgYm9keVBhZGRpbmcoKTogc3RyaW5nIHtcbiAgICBjb25zdCBwYWRkaW5nID0gdGhpcy5jb21wb25lbnQuY29uZmlnPy5wYWRkaW5nO1xuICAgIGNvbnN0IGVkZ2UgPSAodmFsdWU6IG51bWJlciB8IHVuZGVmaW5lZCkgPT4gYCR7KHZhbHVlID8/IERFRkFVTFRfQ09NUE9ORU5UX1BBRERJTkcpICogUFhfUEVSX0lOQ0h9cHhgO1xuXG4gICAgcmV0dXJuIGAke2VkZ2UocGFkZGluZz8udG9wKX0gJHtlZGdlKHBhZGRpbmc/LnJpZ2h0KX0gJHtlZGdlKHBhZGRpbmc/LmJvdHRvbSl9ICR7ZWRnZShwYWRkaW5nPy5sZWZ0KX1gO1xuICB9XG5cbiAgLy8gVGhlIGNvbXBvbmVudC1sZXZlbCBmaWx0ZXIgZ3JvdXBzIHRoYXQgc2hvdWxkIHJlbmRlciBhcyBhbiBpbmxpbmUgY29udHJvbFxuICAvLyBzdHJpcCBvbiBUSElTIGNvbXBvbmVudDogYSBncm91cCBpcyBpbmNsdWRlZCB3aGVuIGl0J3MgbGV2ZWw9Y29tcG9uZW50IGFuZFxuICAvLyBoYXMgYW4gZW5hYmxlZCwgc2Vzc2lvbi1vbiBmaWx0ZXIgaGVyZS4gUmVwb3J0LWxldmVsIGdyb3VwcyBsaXZlIGluIHRoZVxuICAvLyB0b3AgYmFyIGluc3RlYWQuIExpc3RzIHVzZSB0aGlzIHN0cmlwIGxpa2UgY2hhcnRzIGRvOiBhIHZhbHVlIHNldCBoZXJlIGlzXG4gIC8vIHRoZSBncm91cCdzIHZhbHVlLCBzbyBpdCByZWFjaGVzIGV2ZXJ5IGNvbXBvbmVudCBpbiB0aGUgZ3JvdXAuXG4gIHB1YmxpYyBnZXQgY29tcG9uZW50RmlsdGVyR3JvdXBzKCk6IFJlcG9ydEZpbHRlckdyb3VwW10ge1xuICAgIGlmICghdGhpcy5ncm91cHMpIHtcbiAgICAgIHJldHVybiBbXTtcbiAgICB9XG5cbiAgICBjb25zdCBncm91cElkcyA9IG5ldyBTZXQ8bnVtYmVyPigpO1xuICAgIGZvciAoY29uc3QgZmlsdGVyIG9mIHRoaXMuY29tcG9uZW50LmZpbHRlcnMgPz8gW10pIHtcbiAgICAgIGlmICghZmlsdGVyLmVuYWJsZWQgfHwgdGhpcy5fZmlsdGVyU3RhdGUuaXNGaWx0ZXJEaXNhYmxlZChmaWx0ZXIuaWQpKSB7XG4gICAgICAgIGNvbnRpbnVlO1xuICAgICAgfVxuICAgICAgY29uc3QgZ3JvdXAgPSB0aGlzLmdyb3Vwcy5nZXQoZmlsdGVyLmZpbHRlckdyb3VwSWQpO1xuICAgICAgaWYgKGdyb3VwICYmIChncm91cC5sZXZlbCA9PT0gJ2NvbXBvbmVudCcgfHwgZ3JvdXAubGV2ZWwgPT09ICdib3RoJykpIHtcbiAgICAgICAgZ3JvdXBJZHMuYWRkKGdyb3VwLmlkKTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICByZXR1cm4gWy4uLmdyb3VwSWRzXS5tYXAoKGlkKSA9PiB0aGlzLmdyb3Vwcy5nZXQoaWQpKS5maWx0ZXIoQm9vbGVhbik7XG4gIH1cblxuICBwdWJsaWMgc2V0dGluZ3MoKTogdm9pZCB7XG4gICAgdGhpcy5vcGVuU2V0dGluZ3MuZW1pdCh0aGlzLmNvbXBvbmVudCk7XG4gIH1cblxuICAvLyBXaGV0aGVyIHRoZSBtZW51IG9mZmVycyBDb2x1bW5zOiBhIHBsYWluIGxpc3Qgd2l0aCBtb3JlIHRoYW4gb25lXG4gIC8vIGNvbmZpZ3VyZWQgY29sdW1uLiBBIGNyb3NzLXRhYidzIGNvbHVtbnMgY29tZSBhbmQgZ28gd2l0aCB0aGUgZGF0YS5cbiAgcHVibGljIGdldCBoaWRlc0NvbHVtbnMoKTogYm9vbGVhbiB7XG4gICAgcmV0dXJuIHRoaXMuY29tcG9uZW50LnR5cGUgPT09ICdsaXN0JyAmJiBsaXN0SGlkZWFibGVDb2x1bW5zKHRoaXMuY29tcG9uZW50LmNvbmZpZykubGVuZ3RoID4gMTtcbiAgfVxuXG4gIC8vIFdoaWNoIG9mIGEgcGxhaW4gbGlzdCdzIGNvbHVtbnMgc2hvdy4gVGhlIGNob2ljZSBpcyB0aGUgdmlld2VyJ3MgKGtlcHQgaW5cbiAgLy8gdGhlIFVSTCwgbmV2ZXIgc2F2ZWQgdG8gdGhlIHJlcG9ydCksIGFuZCB0aGUgbGlzdCBoaWRlcyB0aGUgY29sdW1ucyBpblxuICAvLyBwbGFjZSwgd2l0aCBubyByZWZldGNoLlxuICBwdWJsaWMgY2hvb3NlQ29sdW1ucygpOiB2b2lkIHtcbiAgICBjb25zdCBjb2x1bW5zID0gKHRoaXMuY29tcG9uZW50LmNvbmZpZz8uY29sdW1ucyA/PyBbXSlcbiAgICAgIC5tYXAoKGNvbHVtbikgPT4gKHsgY29sdW1uOiBjb2x1bW4uY29sdW1uLCBsYWJlbDogY29sdW1uLmxhYmVsIHx8IGNvbHVtbi5jb2x1bW4gfSkpO1xuXG4gICAgdGhpcy5fZGlhbG9nLm9wZW48TGlzdENvbHVtbnNDb21wb25lbnQsIExpc3RDb2x1bW5zRGlhbG9nRGF0YSwgc3RyaW5nW10+KExpc3RDb2x1bW5zQ29tcG9uZW50LCB7XG4gICAgICBkYXRhOiB7IGNvbHVtbnMsIGhpZGRlbjogWy4uLnRoaXMuX2ZpbHRlclN0YXRlLmhpZGRlbkNvbHVtbnModGhpcy5jb21wb25lbnQuaWQpXSB9LFxuICAgICAgd2lkdGg6ICc0MDBweCcsXG4gICAgICBtYXhXaWR0aDogJzk1dncnLFxuICAgICAgYXV0b0ZvY3VzOiBmYWxzZSxcbiAgICB9KVxuICAgICAgLmFmdGVyQ2xvc2VkKClcbiAgICAgIC5waXBlKHRha2VVbnRpbERlc3Ryb3llZCh0aGlzLl9kZXN0cm95UmVmKSlcbiAgICAgIC5zdWJzY3JpYmUoKGhpZGRlbikgPT4ge1xuICAgICAgICAvLyBDYW5jZWwgY2xvc2VzIHdpdGggbm90aGluZywgd2hpY2ggY2hhbmdlcyBub3RoaW5nLlxuICAgICAgICBpZiAoaGlkZGVuKSB7XG4gICAgICAgICAgdGhpcy5fZmlsdGVyU3RhdGUuc2V0SGlkZGVuQ29sdW1ucyh0aGlzLmNvbXBvbmVudC5pZCwgaGlkZGVuKTtcbiAgICAgICAgfVxuICAgICAgfSk7XG4gIH1cblxuICAvLyBQcmVzZW50YXRpb24gc2V0dGluZ3Mgc2F2ZWQgZnJvbSB0aGUgc2V0dGluZ3MgZGlhbG9nLiBUaXRsZSBhbmQgcGFkZGluZyBhcmVcbiAgLy8gbm90IHBhcnQgb2YgdGhlIHF1ZXJ5LCBzbyB0aGUgZGF0YSBhbHJlYWR5IGZldGNoZWQgc3RpbGwgc3RhbmRzIOKAlCB0aGlzIG9ubHlcbiAgLy8gcmVwYWludHMuIFRoZSBoZWFkZXIgY29uZmlnIGlzIHJlYnVpbHQgYmVjYXVzZSBgZmlsdGVyS2V5YCBjaGFuZ2VzIHdpdGggdGhlXG4gIC8vIHRpdGxlIGFuZCByZWNyZWF0ZXMgdGhlIGZzLWZpbHRlciBibG9jayBhcm91bmQgaXQ7IHNldHRpbmcgdGhlIGNvbmZpZyBzaWduYWxcbiAgLy8gaXMgYWxzbyB3aGF0IHJlcGFpbnRzIHRoZSBuZXcgcGFkZGluZy4gVGhlIGNoYXJ0IGZvbGxvd3MgaXRzIGJveCBvbiBpdHMgb3duXG4gIC8vIChuZ3gtZWNoYXJ0cyBvYnNlcnZlcyB0aGUgaG9zdCksIHNvIG5vdGhpbmcgaXMgdG9sZCB0byByZXNpemUuXG4gIHB1YmxpYyBhcHBseVNldHRpbmdzKHNldHRpbmdzOiBDb21wb25lbnRTZXR0aW5ncyk6IHZvaWQge1xuICAgIHRoaXMuY29tcG9uZW50LnRpdGxlID0gc2V0dGluZ3MudGl0bGU7XG4gICAgdGhpcy5jb21wb25lbnQuY29uZmlnID0geyAuLi50aGlzLmNvbXBvbmVudC5jb25maWcsIHBhZGRpbmc6IHNldHRpbmdzLnBhZGRpbmcgfTtcblxuICAgIHRoaXMuX2J1aWxkRmlsdGVyQ29uZmlnKCk7XG4gIH1cblxuICAvLyBUaGUgQ1NWIGlzIHdoYXQgdGhlIHNjcmVlbiBzaG93cywgc28gaXQgY2FycmllcyB0aGUgc2FtZSBpbnRlcmFjdGlvbiBzdGF0ZVxuICAvLyB0aGUgc2NyZWVuIGZldGNoZWQgd2l0aDogdGhlIGdyb3VwLWJ5IGdyYWluIGZvciBhIHRpbWUtc2VyaWVzIGNoYXJ0LCBhbmQgdGhlXG4gIC8vIHZpZXdlcidzIGhlYWRlciBzb3J0LCBzZWFyY2ggYW5kIGhpZGRlbiBjb2x1bW5zIGZvciBhIGxpc3QuIEEgbm90ZSB0aGVcbiAgLy8gc2VydmVyIHJldHVybnMgKHRoZSBmaWxlIHdhcyBjdXQpIGlzIHNob3duIGJlZm9yZSB0aGUgZG93bmxvYWQgc3RhcnRzLCBzbyBhXG4gIC8vIHNob3J0IGZpbGUgbmV2ZXIgcGFzc2VzIGZvciB0aGUgd2hvbGUgcmVzdWx0LlxuICBwdWJsaWMgZXhwb3J0Q3N2KCk6IHZvaWQge1xuICAgIGNvbnN0IGZpbHRlcnMgPSB0aGlzLl9maWx0ZXJTdGF0ZS5yZXNvbHZlRm9yQ29tcG9uZW50KHRoaXMuY29tcG9uZW50KTtcbiAgICBjb25zdCBzdGF0ZTogQ29tcG9uZW50RGF0YVN0YXRlID0ge307XG5cbiAgICAvLyBBIGRlbGliZXJhdGUgbWlycm9yIG9mIHRoZSBzZXJ2ZXIncyBSZXBvcnRRdWVyeVJ1bm5lcjo6X2lzVGltZVNlcmllc0NoYXJ0LFxuICAgIC8vIHdoaWNoIGlzIGNhbm9uaWNhbCBhbmQgZHJvcHMgdGhlIGdyYWluIGZvciBldmVyeSBvdGhlciBjb21wb25lbnQuIEtlcHQgc29cbiAgICAvLyBhIHByb2R1Y3QgcGlubmVkIHRvIGFuIG9sZGVyIGZyYW1ld29yayBkb2VzIG5vdCByZS1idWNrZXQgYSBub24tdGltZSBjaGFydC5cbiAgICBpZiAodGhpcy5faXNUaW1lU2VyaWVzICYmIHRoaXMuX2ZpbHRlclN0YXRlLmZyZXF1ZW5jeSgpKSB7XG4gICAgICBzdGF0ZS5mcmVxdWVuY3kgPSB0aGlzLl9maWx0ZXJTdGF0ZS5mcmVxdWVuY3koKTtcbiAgICB9XG5cbiAgICBjb25zdCBpc0xpc3QgPSB0aGlzLmNvbXBvbmVudC50eXBlID09PSAnbGlzdCc7XG4gICAgY29uc3Qgc29ydCA9IGlzTGlzdCA/IHRoaXMuX2ZpbHRlclN0YXRlLmxpc3RTb3J0KHRoaXMuY29tcG9uZW50LmlkKSA6IG51bGw7XG4gICAgaWYgKHNvcnQpIHtcbiAgICAgIHN0YXRlLnNvcnQgPSBzb3J0O1xuICAgIH1cblxuICAgIC8vIEEgc2VhcmNoZWQgbGlzdCBleHBvcnRzIG9ubHkgdGhlIHJvd3MgdGhlIHNlYXJjaCBsZWF2ZXMsIGFzIG9uIHNjcmVlbi5cbiAgICBjb25zdCBzZWFyY2ggPSBpc0xpc3QgPyB0aGlzLl9maWx0ZXJTdGF0ZS5saXN0U2VhcmNoKHRoaXMuY29tcG9uZW50LmlkKSA6IG51bGw7XG4gICAgaWYgKHNlYXJjaCkge1xuICAgICAgc3RhdGUuc2VhcmNoID0gc2VhcmNoO1xuICAgIH1cblxuICAgIC8vIFRoZSBjb2x1bW5zIHRoZSB2aWV3ZXIgaGlkIHN0YXkgb3V0IG9mIHRoZSBmaWxlLCBhcyBvZmYgdGhlIHNjcmVlbi5cbiAgICBjb25zdCBoaWRkZW5Db2x1bW5zID0gaXNMaXN0ID8gdGhpcy5fZmlsdGVyU3RhdGUuaGlkZGVuQ29sdW1ucyh0aGlzLmNvbXBvbmVudC5pZCkgOiBbXTtcbiAgICBpZiAoaGlkZGVuQ29sdW1ucy5sZW5ndGgpIHtcbiAgICAgIHN0YXRlLmhpZGRlbkNvbHVtbnMgPSBbLi4uaGlkZGVuQ29sdW1uc107XG4gICAgfVxuXG4gICAgdGhpcy5fcHJvY2Vzcy5kb3dubG9hZChcbiAgICAgIGBFeHBvcnRpbmcgJHt0aGlzLmNvbXBvbmVudC50aXRsZSA/PyAnY29tcG9uZW50J31gLFxuICAgICAgdGhpcy5fcmVwb3J0RGF0YS5leHBvcnRDb21wb25lbnQodGhpcy5yZXBvcnRJZCwgdGhpcy5jb21wb25lbnQuaWQsIGZpbHRlcnMsIHN0YXRlKVxuICAgICAgICAucGlwZShcbiAgICAgICAgICB0YXAoKHsgbm90ZXMgfSkgPT4gbm90ZXM/Lmxlbmd0aCAmJiB0aGlzLl9tZXNzYWdlLndhcm5pbmcobm90ZXMuam9pbignICcpKSksXG4gICAgICAgICAgbWFwKCh7IHVybCB9KSA9PiB1cmwpLFxuICAgICAgICApLFxuICAgICk7XG4gIH1cblxuICAvLyBBbnkgaW50ZXJhY3Rpb24gaW5zaWRlIGEgY29tcG9uZW50IG11c3QgbmV2ZXIgc3RhcnQgYSBjYW52YXMgcGFuICh0aGVcbiAgLy8gem9vbS1wYW4gaG9zdCBsaXN0ZW5zIGZvciBtb3VzZWRvd24vdG91Y2hzdGFydCBhdCB0aGUgY29udGFpbmVyIGxldmVsKS5cbiAgcHVibGljIHN0b3BDYW52YXNQYW4oZXZlbnQ6IEV2ZW50KTogdm9pZCB7XG4gICAgZXZlbnQuc3RvcFByb3BhZ2F0aW9uKCk7XG4gIH1cblxuICBwdWJsaWMgb25Db21wb25lbnRQb2ludGVyRG93bihldmVudDogUG9pbnRlckV2ZW50KTogdm9pZCB7XG4gICAgZXZlbnQuc3RvcFByb3BhZ2F0aW9uKCk7XG4gICAgaWYgKHRoaXMuZWRpdE1vZGUgJiYgIXRoaXMuc2VsZWN0ZWQpIHtcbiAgICAgIHRoaXMuc2VsZWN0Q29tcG9uZW50LmVtaXQodGhpcy5jb21wb25lbnQuaWQpO1xuICAgIH1cbiAgfVxuXG4gIC8vIC0tLS0tIGVkaXQtbW9kZSBnZXN0dXJlcyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cblxuICBwdWJsaWMgb25EcmFnU3RhcnQoZXZlbnQ6IFBvaW50ZXJFdmVudCk6IHZvaWQge1xuICAgIGlmICghdGhpcy5lZGl0TW9kZSB8fCB0aGlzLnRleHRFZGl0aW5nKCkpIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICAvLyBBIHNlY29uZCBwcmVzcyBvbiBhIHRleHQgYmxvY2sgb3BlbnMgaXRzIGVkaXRvciBpbnN0ZWFkIG9mIGRyYWdnaW5nLlxuICAgIGlmICh0aGlzLmlzVGV4dCkge1xuICAgICAgY29uc3Qgbm93ID0gRGF0ZS5ub3coKTtcbiAgICAgIGNvbnN0IGlzRG91YmxlUHJlc3MgPSBub3cgLSB0aGlzLl9sYXN0UHJlc3MgPCBET1VCTEVfUFJFU1NfTVM7XG4gICAgICB0aGlzLl9sYXN0UHJlc3MgPSBub3c7XG5cbiAgICAgIGlmIChpc0RvdWJsZVByZXNzKSB7XG4gICAgICAgIGV2ZW50LnByZXZlbnREZWZhdWx0KCk7XG4gICAgICAgIGV2ZW50LnN0b3BQcm9wYWdhdGlvbigpO1xuICAgICAgICB0aGlzLmVkaXRUZXh0KCk7XG5cbiAgICAgICAgcmV0dXJuO1xuICAgICAgfVxuICAgIH1cblxuICAgIHRoaXMuc2VsZWN0Q29tcG9uZW50LmVtaXQodGhpcy5jb21wb25lbnQuaWQpO1xuXG4gICAgaWYgKHRoaXMubGF5b3V0ID09PSAnZmxvdycpIHtcbiAgICAgIHRoaXMuX2Zsb3dEcmFnKGV2ZW50KTtcblxuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIHRoaXMuX3RyYWNrKGV2ZW50LCAoZGVsdGFYLCBkZWx0YVkpID0+IHtcbiAgICAgIGxldCB4ID0gTWF0aC5tYXgoMCwgdGhpcy5fb3JpZ2luLnggKyB0aGlzLl9pbmNoZXMoZGVsdGFYKSk7XG4gICAgICBsZXQgeSA9IE1hdGgubWF4KDAsIHRoaXMuX29yaWdpbi55ICsgdGhpcy5faW5jaGVzKGRlbHRhWSkpO1xuXG4gICAgICBpZiAodGhpcy5zbmFwcGVyKSB7XG4gICAgICAgICh7IHgsIHkgfSA9IHRoaXMuc25hcHBlci5zbmFwTW92ZSh0aGlzLmNvbXBvbmVudCwgeCwgeSkpO1xuICAgICAgfVxuXG4gICAgICB0aGlzLmNvbXBvbmVudC54ID0geDtcbiAgICAgIHRoaXMuY29tcG9uZW50LnkgPSB5O1xuICAgICAgdGhpcy5fYXBwbHlHZW9tZXRyeSgpO1xuICAgIH0sICgpID0+IHRoaXMuX2VtaXRHZW9tZXRyeSgpKTtcbiAgfVxuXG4gIHB1YmxpYyBvblJlc2l6ZVN0YXJ0KGV2ZW50OiBQb2ludGVyRXZlbnQsIGhhbmRsZTogSGFuZGxlKTogdm9pZCB7XG4gICAgaWYgKCF0aGlzLmVkaXRNb2RlKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgdGhpcy5zZWxlY3RDb21wb25lbnQuZW1pdCh0aGlzLmNvbXBvbmVudC5pZCk7XG5cbiAgICBpZiAodGhpcy5sYXlvdXQgPT09ICdmbG93Jykge1xuICAgICAgdGhpcy5fZmxvd1Jlc2l6ZShldmVudCwgaGFuZGxlKTtcblxuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIHRoaXMuX3RyYWNrKGV2ZW50LCAoZGVsdGFYLCBkZWx0YVkpID0+IHtcbiAgICAgIGNvbnN0IGR4ID0gdGhpcy5faW5jaGVzKGRlbHRhWCk7XG4gICAgICBjb25zdCBkeSA9IHRoaXMuX2luY2hlcyhkZWx0YVkpO1xuICAgICAgbGV0IHsgeCwgeSwgdywgaCB9ID0gdGhpcy5fb3JpZ2luO1xuXG4gICAgICBpZiAoaGFuZGxlLmluY2x1ZGVzKCdlJykpIHtcbiAgICAgICAgdyA9IE1hdGgubWF4KE1JTl9XLCB0aGlzLl9vcmlnaW4udyArIGR4KTtcbiAgICAgIH1cbiAgICAgIGlmIChoYW5kbGUuaW5jbHVkZXMoJ3MnKSkge1xuICAgICAgICBoID0gTWF0aC5tYXgoTUlOX0gsIHRoaXMuX29yaWdpbi5oICsgZHkpO1xuICAgICAgfVxuICAgICAgaWYgKGhhbmRsZS5pbmNsdWRlcygndycpKSB7XG4gICAgICAgIGNvbnN0IGNsYW1wZWQgPSBNYXRoLm1pbihkeCwgdGhpcy5fb3JpZ2luLncgLSBNSU5fVyk7XG4gICAgICAgIHggPSB0aGlzLl9vcmlnaW4ueCArIGNsYW1wZWQ7XG4gICAgICAgIHcgPSB0aGlzLl9vcmlnaW4udyAtIGNsYW1wZWQ7XG4gICAgICB9XG4gICAgICBpZiAoaGFuZGxlLmluY2x1ZGVzKCduJykpIHtcbiAgICAgICAgY29uc3QgY2xhbXBlZCA9IE1hdGgubWluKGR5LCB0aGlzLl9vcmlnaW4uaCAtIE1JTl9IKTtcbiAgICAgICAgeSA9IHRoaXMuX29yaWdpbi55ICsgY2xhbXBlZDtcbiAgICAgICAgaCA9IHRoaXMuX29yaWdpbi5oIC0gY2xhbXBlZDtcbiAgICAgIH1cblxuICAgICAgbGV0IGdlb21ldHJ5ID0geyB4LCB5LCB3LCBoIH07XG4gICAgICBpZiAodGhpcy5zbmFwcGVyKSB7XG4gICAgICAgIGdlb21ldHJ5ID0gdGhpcy5zbmFwcGVyLnNuYXBSZXNpemUodGhpcy5jb21wb25lbnQsIGdlb21ldHJ5LCBoYW5kbGUpO1xuICAgICAgfVxuXG4gICAgICBPYmplY3QuYXNzaWduKHRoaXMuY29tcG9uZW50LCBnZW9tZXRyeSk7XG4gICAgICB0aGlzLl9hcHBseUdlb21ldHJ5KCk7XG4gICAgICB0aGlzLmNoYXJ0Q29tcG9uZW50Py5yZXNpemUoKTtcbiAgICB9LCAoKSA9PiB0aGlzLl9lbWl0R2VvbWV0cnkoKSk7XG4gIH1cblxuICAvLyAoUmUpYnVpbGQgdGhlIGhlYWRlciBmcy1maWx0ZXIgY29uZmlnOiBoZWFkaW5nIHRlbXBsYXRlIHJlbmRlcnMgdGhlIHRpdGxlXG4gIC8vIGFuZCBpdGVtcyBhcmUgdGhpcyBjb21wb25lbnQncyBjb21wb25lbnQtbGV2ZWwgZmlsdGVyIGdyb3Vwcy4gVGhlIGFjdGlvbnNcbiAgLy8gbWVudSAoU2V0dGluZ3MgLyBFeHBvcnQgQ1NWKSBpcyBOT1QgaGVyZSDigJQgaXQncyBhIHN0YW5kYWxvbmUga2ViYWIgZmxvYXRlZFxuICAvLyB0b3AtcmlnaHQgaW4gdGhlIHRlbXBsYXRlLCBzbyBpdHMgYnV0dG9uIGhlaWdodCBubyBsb25nZXIgZHJpdmVzIHRoZSBoZWFkZXJcbiAgLy8gcm93J3MgaGVpZ2h0ICh3aGljaCB3b3VsZCBvdGhlcndpc2UgaW5mbGF0ZSB0aGUgaGVhZGluZyBieSB+NDBweCkuXG4gIC8vXG4gIC8vIEEgbGlzdCBhbHNvIGdldHMgYSBzZWFyY2ggYm94IG92ZXIgaXRzIHRleHQgY29sdW1ucywgdW5sZXNzIGl0cyBoZWFkZXJcbiAgLy8gc2hvd3MgYSBrZXl3b3JkIGdyb3VwIChSZXBvcnRGaWx0ZXJTdGF0ZVNlcnZpY2UubGlzdFNlYXJjaGFibGUsIHdoaWNoIGFsc29cbiAgLy8gZHJvcHMgYSBzZWFyY2gga2VwdCBmcm9tIGJlZm9yZSBzdWNoIGEgZ3JvdXAgYXBwZWFyZWQpLlxuICAvL1xuICAvLyBgcmVwb3J0ZWRgIGlzIHdoYXQgdGhpcyBoZWFkZXIgbGFzdCByZXBvcnRlZCBmb3IgZWFjaCBvZiBpdHMgZ3JvdXBzLFxuICAvLyBzdGFydGluZyBmcm9tIHRoZSB2YWx1ZXMgaXQgaXMgYnVpbHQgd2l0aC4gQSBjaGFuZ2Ugc2V0cyBvbmx5IHRoZSBncm91cHNcbiAgLy8gd2hvc2UgaGVhZGVyIHZhbHVlIG1vdmVkIChtb3ZlZEdyb3VwVmFsdWVzKTogZnMtZmlsdGVyIHJlcG9ydHMgZXZlcnkgaXRlbVxuICAvLyBvbiBhbnkgY2hhbmdlLCBhbmQgYSBncm91cCBzaG93biBpbiB0aGUgcmVwb3J0IGJhciB0b28gbWF5IGhhdmUgY2hhbmdlZFxuICAvLyB0aGVyZSBzaW5jZSwgd2l0aG91dCB0aGlzIGhlYWRlciBiZWluZyByZXBhaW50ZWQuXG4gIHByaXZhdGUgX2J1aWxkRmlsdGVyQ29uZmlnKCk6IHZvaWQge1xuICAgIGNvbnN0IGdyb3VwcyA9IHRoaXMuY29tcG9uZW50RmlsdGVyR3JvdXBzO1xuICAgIGNvbnN0IGxpc3RTZWFyY2ggPSB0aGlzLl9maWx0ZXJTdGF0ZS5saXN0U2VhcmNoYWJsZSh0aGlzLmNvbXBvbmVudCk7XG4gICAgY29uc3QgcmVwb3J0ZWQgPSBuZXcgTWFwKGdyb3Vwcy5tYXAoKGdyb3VwKSA9PiBbZ3JvdXAuaWQsIHRoaXMuX2ZpbHRlclN0YXRlLnZhbHVlKGdyb3VwLmlkKSA/PyBudWxsXSkpO1xuXG4gICAgdGhpcy5maWx0ZXJDb25maWcuc2V0KHtcbiAgICAgIC8vIGZzLWZpbHRlciBuZXZlciB0b3VjaGVzIHRoZSBVUkwgb3IgcGVyc2lzdHMgZmlsdGVyIHN0YXRlLiBUaGUgdmFsdWVzXG4gICAgICAvLyBhcmUgb3duZWQgYnkgUmVwb3J0RmlsdGVyU3RhdGVTZXJ2aWNlLCB3aGljaCBmZWVkcyB0aGUgcmVwb3J0IHZpZXcnc1xuICAgICAgLy8gb25lIFVSTCB3cml0ZXIgKHJlcG9ydC11cmwtc3RhdGUudHMpLlxuICAgICAgcXVlcnlQYXJhbTogZmFsc2UsXG4gICAgICBwZXJzaXN0OiBmYWxzZSxcbiAgICAgIGl0ZW1zOiBbXG4gICAgICAgIC4uLmdyb3Vwcy5tYXAoKGdyb3VwKSA9PlxuICAgICAgICAgIGZpbHRlckl0ZW1Gb3JHcm91cChncm91cCwgdGhpcy5fcmVwb3J0RGF0YSwgdGhpcy5yZXBvcnRJZCwgdGhpcy5fZmlsdGVyU3RhdGUudmFsdWUoZ3JvdXAuaWQpKSksXG4gICAgICAgIC4uLihsaXN0U2VhcmNoID8gW2xpc3RTZWFyY2hJdGVtKHRoaXMuX2ZpbHRlclN0YXRlLmxpc3RTZWFyY2godGhpcy5jb21wb25lbnQuaWQpKV0gOiBbXSksXG4gICAgICBdLFxuICAgICAgLy8gVHlwaW5nIGluIHRoZSBzZWFyY2ggYm94IG11c3Qgbm90IHJlZmV0Y2ggdGhyb3VnaCB0aGUgZ3JvdXBzLCBub3Igc2V0XG4gICAgICAvLyBhIHN0YWxlIGdyb3VwIHZhbHVlIGJhY2ssIGFuZCBhIGdyb3VwIGNoYW5nZSBtdXN0IG5vdCByZWZldGNoIHRocm91Z2hcbiAgICAgIC8vIHRoZSBzZWFyY2guXG4gICAgICBjaGFuZ2U6IChxdWVyeSkgPT4ge1xuICAgICAgICBjb25zdCB2YWx1ZXMgPSBncm91cFZhbHVlc0Zyb21RdWVyeShxdWVyeSA/PyB7fSwgdGhpcy5jb21wb25lbnRGaWx0ZXJHcm91cHMpO1xuXG4gICAgICAgIGZvciAoY29uc3QgeyBncm91cElkLCB2YWx1ZSB9IG9mIG1vdmVkR3JvdXBWYWx1ZXMocmVwb3J0ZWQsIHZhbHVlcykpIHtcbiAgICAgICAgICB0aGlzLl9maWx0ZXJTdGF0ZS5zZXRWYWx1ZShncm91cElkLCB2YWx1ZSk7XG4gICAgICAgIH1cblxuICAgICAgICBpZiAobGlzdFNlYXJjaCkge1xuICAgICAgICAgIHRoaXMuX2ZpbHRlclN0YXRlLnNldExpc3RTZWFyY2godGhpcy5jb21wb25lbnQuaWQsIFN0cmluZyhxdWVyeT8uW0xJU1RfU0VBUkNIX0lURU1dID8/ICcnKSk7XG4gICAgICAgIH1cbiAgICAgIH0sXG4gICAgfSk7XG4gIH1cblxuICAvLyBGbG93OiBvbmx5IHRoZSBlYXN0IGhhbmRsZSByZXNpemVzICh3aWR0aCAlKS4gSGVpZ2h0IGlzIGFsd2F5cyBhdXRvIGluIGZsb3dcbiAgLy8gKHRoZSBib3ggZml0cyBpdHMgY29udGVudCksIHNvIHRoZXJlJ3Mgbm8gc291dGggaGFuZGxlIGhlcmUuXG4gIHByaXZhdGUgX2Zsb3dSZXNpemUoZXZlbnQ6IFBvaW50ZXJFdmVudCwgaGFuZGxlOiBIYW5kbGUpOiB2b2lkIHtcbiAgICBjb25zdCBwYWdlV2lkdGggPSB0aGlzLl9ob3N0Lm5hdGl2ZUVsZW1lbnQucGFyZW50RWxlbWVudD8uY2xpZW50V2lkdGggfHwgMTtcblxuICAgIHRoaXMuX3RyYWNrKGV2ZW50LCAoZGVsdGFYKSA9PiB7XG4gICAgICBpZiAoaGFuZGxlLmluY2x1ZGVzKCdlJykpIHtcbiAgICAgICAgY29uc3QgZGVsdGFQZXJjZW50ID0gKGRlbHRhWCAvIHRoaXMuem9vbSAvIHBhZ2VXaWR0aCkgKiAxMDA7XG4gICAgICAgIGNvbnN0IHJhdyA9IE1hdGgubWluKDEwMCwgTWF0aC5tYXgoMTAsIHRoaXMuX29yaWdpbi5mbG93V2lkdGggKyBkZWx0YVBlcmNlbnQpKTtcbiAgICAgICAgdGhpcy5jb21wb25lbnQuZmxvd1dpZHRoID0gdGhpcy5fc25hcEZsb3dXaWR0aChyYXcpO1xuICAgICAgICB0aGlzLl9ob3N0Lm5hdGl2ZUVsZW1lbnQuc3R5bGUud2lkdGggPSBgJHt0aGlzLmNvbXBvbmVudC5mbG93V2lkdGh9JWA7XG4gICAgICB9XG4gICAgfSwgKCkgPT4ge1xuICAgICAgdGhpcy5wb3NpdGlvbkNoYW5nZWQuZW1pdCh7XG4gICAgICAgIGNvbXBvbmVudElkOiB0aGlzLmNvbXBvbmVudC5pZCxcbiAgICAgICAgZmxvd1dpZHRoOiB0aGlzLmNvbXBvbmVudC5mbG93V2lkdGgsXG4gICAgICB9KTtcbiAgICB9KTtcbiAgfVxuXG4gIC8vIEZsb3c6IGRyYWcgbGlmdHMgdGhlIGNvbXBvbmVudCAoZ2hvc3QpIGFuZCB0aGUgY2FudmFzIGRlY2lkZXMgdGhlIGRyb3BcbiAgLy8gaW5kZXggZnJvbSB0aGUgcG9pbnRlciBwb3NpdGlvbi5cbiAgcHJpdmF0ZSBfZmxvd0RyYWcoZXZlbnQ6IFBvaW50ZXJFdmVudCk6IHZvaWQge1xuICAgIGNvbnN0IGhvc3QgPSB0aGlzLl9ob3N0Lm5hdGl2ZUVsZW1lbnQ7XG4gICAgbGV0IGxhc3RDbGllbnRYID0gZXZlbnQuY2xpZW50WDtcbiAgICBsZXQgbGFzdENsaWVudFkgPSBldmVudC5jbGllbnRZO1xuXG4gICAgaG9zdC5jbGFzc0xpc3QuYWRkKCdmbG93LWRyYWdnaW5nJyk7XG5cbiAgICB0aGlzLl90cmFjayhldmVudCwgKGRlbHRhWCwgZGVsdGFZLCBlKSA9PiB7XG4gICAgICBsYXN0Q2xpZW50WCA9IGUuY2xpZW50WDtcbiAgICAgIGxhc3RDbGllbnRZID0gZS5jbGllbnRZO1xuICAgICAgaG9zdC5zdHlsZS50cmFuc2Zvcm0gPSBgdHJhbnNsYXRlKCR7ZGVsdGFYIC8gdGhpcy56b29tfXB4LCAke2RlbHRhWSAvIHRoaXMuem9vbX1weClgO1xuICAgIH0sICgpID0+IHtcbiAgICAgIGhvc3QuY2xhc3NMaXN0LnJlbW92ZSgnZmxvdy1kcmFnZ2luZycpO1xuICAgICAgaG9zdC5zdHlsZS50cmFuc2Zvcm0gPSAnJztcbiAgICAgIHRoaXMuZmxvd1Jlb3JkZXIuZW1pdCh7XG4gICAgICAgIGNvbXBvbmVudElkOiB0aGlzLmNvbXBvbmVudC5pZCxcbiAgICAgICAgY2xpZW50WDogbGFzdENsaWVudFgsXG4gICAgICAgIGNsaWVudFk6IGxhc3RDbGllbnRZLFxuICAgICAgfSk7XG4gICAgfSk7XG4gIH1cblxuICBwcml2YXRlIF9vcmlnaW4gPSB7IHg6IDAsIHk6IDAsIHc6IDAsIGg6IDAsIGZsb3dXaWR0aDogNTAgfTtcblxuICAvLyBQb2ludGVyLWNhcHR1cmUgZ2VzdHVyZSBsb29wOiBydW5zIG91dHNpZGUgQW5ndWxhciwgcmVwYWludHMgaW1wZXJhdGl2ZWx5LFxuICAvLyBhbmQgZmluaXNoZXMgYmFjayBpbnNpZGUgQW5ndWxhciAoc2VsZWN0aW9uL3BlcnNpc3RlbmNlKS5cbiAgcHJpdmF0ZSBfdHJhY2soXG4gICAgZXZlbnQ6IFBvaW50ZXJFdmVudCxcbiAgICBvbk1vdmU6IChkZWx0YVg6IG51bWJlciwgZGVsdGFZOiBudW1iZXIsIGU6IFBvaW50ZXJFdmVudCkgPT4gdm9pZCxcbiAgICBvbkVuZDogKCkgPT4gdm9pZCxcbiAgKTogdm9pZCB7XG4gICAgZXZlbnQucHJldmVudERlZmF1bHQoKTtcbiAgICBldmVudC5zdG9wUHJvcGFnYXRpb24oKTtcblxuICAgIGNvbnN0IGhhbmRsZSA9IGV2ZW50LnRhcmdldCBhcyBIVE1MRWxlbWVudDtcbiAgICBoYW5kbGUuc2V0UG9pbnRlckNhcHR1cmUoZXZlbnQucG9pbnRlcklkKTtcblxuICAgIHRoaXMuX29yaWdpbiA9IHtcbiAgICAgIHg6IHRoaXMuY29tcG9uZW50LngsXG4gICAgICB5OiB0aGlzLmNvbXBvbmVudC55LFxuICAgICAgdzogdGhpcy5jb21wb25lbnQudyxcbiAgICAgIGg6IHRoaXMuY29tcG9uZW50LmgsXG4gICAgICBmbG93V2lkdGg6IHRoaXMuY29tcG9uZW50LmZsb3dXaWR0aCA/PyA1MCxcbiAgICB9O1xuICAgIGNvbnN0IHN0YXJ0WCA9IGV2ZW50LmNsaWVudFg7XG4gICAgY29uc3Qgc3RhcnRZID0gZXZlbnQuY2xpZW50WTtcblxuICAgIHRoaXMuX3pvbmUucnVuT3V0c2lkZUFuZ3VsYXIoKCkgPT4ge1xuICAgICAgY29uc3QgbW92ZSA9IChlOiBQb2ludGVyRXZlbnQpID0+IG9uTW92ZShlLmNsaWVudFggLSBzdGFydFgsIGUuY2xpZW50WSAtIHN0YXJ0WSwgZSk7XG4gICAgICBjb25zdCBlbmQgPSAoKSA9PiB7XG4gICAgICAgIGhhbmRsZS5yZWxlYXNlUG9pbnRlckNhcHR1cmUoZXZlbnQucG9pbnRlcklkKTtcbiAgICAgICAgaGFuZGxlLnJlbW92ZUV2ZW50TGlzdGVuZXIoJ3BvaW50ZXJtb3ZlJywgbW92ZSk7XG4gICAgICAgIGhhbmRsZS5yZW1vdmVFdmVudExpc3RlbmVyKCdwb2ludGVydXAnLCBlbmQpO1xuICAgICAgICBoYW5kbGUucmVtb3ZlRXZlbnRMaXN0ZW5lcigncG9pbnRlcmNhbmNlbCcsIGVuZCk7XG5cbiAgICAgICAgdGhpcy5fem9uZS5ydW4oKCkgPT4ge1xuICAgICAgICAgIHRoaXMuc25hcHBlcj8uY2xlYXIoKTtcbiAgICAgICAgICBvbkVuZCgpO1xuICAgICAgICB9KTtcbiAgICAgIH07XG5cbiAgICAgIGhhbmRsZS5hZGRFdmVudExpc3RlbmVyKCdwb2ludGVybW92ZScsIG1vdmUpO1xuICAgICAgaGFuZGxlLmFkZEV2ZW50TGlzdGVuZXIoJ3BvaW50ZXJ1cCcsIGVuZCk7XG4gICAgICBoYW5kbGUuYWRkRXZlbnRMaXN0ZW5lcigncG9pbnRlcmNhbmNlbCcsIGVuZCk7XG4gICAgfSk7XG4gIH1cblxuICBwcml2YXRlIF9lbWl0R2VvbWV0cnkoKTogdm9pZCB7XG4gICAgdGhpcy5jb21wb25lbnQueCA9IHRoaXMuX3JvdW5kKHRoaXMuY29tcG9uZW50LngpO1xuICAgIHRoaXMuY29tcG9uZW50LnkgPSB0aGlzLl9yb3VuZCh0aGlzLmNvbXBvbmVudC55KTtcbiAgICB0aGlzLmNvbXBvbmVudC53ID0gdGhpcy5fcm91bmQoTWF0aC5tYXgoTUlOX1csIHRoaXMuY29tcG9uZW50LncpKTtcbiAgICB0aGlzLmNvbXBvbmVudC5oID0gdGhpcy5fcm91bmQoTWF0aC5tYXgoTUlOX0gsIHRoaXMuY29tcG9uZW50LmgpKTtcbiAgICB0aGlzLl9hcHBseUdlb21ldHJ5KCk7XG4gICAgdGhpcy5jaGFydENvbXBvbmVudD8ucmVzaXplKCk7XG5cbiAgICB0aGlzLnBvc2l0aW9uQ2hhbmdlZC5lbWl0KHtcbiAgICAgIGNvbXBvbmVudElkOiB0aGlzLmNvbXBvbmVudC5pZCxcbiAgICAgIHg6IHRoaXMuY29tcG9uZW50LngsXG4gICAgICB5OiB0aGlzLmNvbXBvbmVudC55LFxuICAgICAgdzogdGhpcy5jb21wb25lbnQudyxcbiAgICAgIGg6IHRoaXMuY29tcG9uZW50LmgsXG4gICAgfSk7XG4gIH1cblxuICAvLyBBIGNoYXJ0IG9uIGEgdGltZSB4LWF4aXMg4oCUIHRoZSBvbmx5IGNvbXBvbmVudCB0aGUgcmVwb3J0J3MgZ3JvdXAtYnkgY29udHJvbFxuICAvLyBhcHBsaWVzIHRvLiBUaGUgc2VydmVyIG93bnMgdGhpcyBydWxlIChSZXBvcnRRdWVyeVJ1bm5lcjo6X2lzVGltZVNlcmllc0NoYXJ0KTtcbiAgLy8gdGhpcyBpcyBpdHMgZG9jdW1lbnRlZCBicm93c2VyLXNpZGUgbWlycm9yLCBmb3IgcHJvZHVjdHMgb24gYW4gb2xkZXIgZnJhbWV3b3JrLlxuICBwcml2YXRlIGdldCBfaXNUaW1lU2VyaWVzKCk6IGJvb2xlYW4ge1xuICAgIHJldHVybiB0aGlzLmNvbXBvbmVudC50eXBlID09PSAnY2hhcnQnICYmIHRoaXMuY29tcG9uZW50LmNvbmZpZz8ueEF4aXM/LmtpbmQgPT09ICd0aW1lJztcbiAgfVxuXG4gIC8vIEF1dG8gaGVpZ2h0IChib3ggZml0cyBpdHMgY29udGVudCkgdnMgZml4ZWQgKHVzZSBgaGAgZXhhY3RseSkuIERlcml2ZWQgZnJvbVxuICAvLyB0eXBlLCBzZXJ2ZXItc2lkZTogS1BJIHRpbGVzIGFyZSBhdXRvOyBjaGFydHMgYW5kIGxpc3RzIGFyZSBmaXhlZCDigJQgY2hhcnRzXG4gIC8vIGZpdCB0aGUgYm94IGFuZCBuZXZlciBvdmVyZmxvdywgbGlzdHMgc2Nyb2xsIGluc2lkZSBpdC5cbiAgcHJpdmF0ZSBnZXQgX2hlaWdodEF1dG8oKTogYm9vbGVhbiB7XG4gICAgcmV0dXJuIHRoaXMuY29tcG9uZW50LmF1dG9IZWlnaHQgIT09IGZhbHNlO1xuICB9XG5cbiAgLy8gRHJpdmVzIHRoZSBhdXRvLW9ubHkgQ1NTIGRlZmF1bHQgKGVtcHR5LXN0YXRlIGJhc2VsaW5lKSBzbyBpdCBuZXZlciBhcHBsaWVzXG4gIC8vIHRvIGEgZml4ZWQtaGVpZ2h0IGNvbXBvbmVudC5cbiAgQEhvc3RCaW5kaW5nKCdjbGFzcy5oZWlnaHQtYXV0bycpXG4gIHB1YmxpYyBnZXQgaGVpZ2h0QXV0bygpOiBib29sZWFuIHtcbiAgICByZXR1cm4gdGhpcy5faGVpZ2h0QXV0bztcbiAgfVxuXG4gIC8vIFNjcmVlbiBwaXhlbHMg4oaSIGluY2hlcyBhdCB0aGUgY3VycmVudCB6b29tLlxuICBwcml2YXRlIF9pbmNoZXMocGl4ZWxzOiBudW1iZXIpOiBudW1iZXIge1xuICAgIHJldHVybiBwaXhlbHMgLyAodGhpcy56b29tICogUFhfUEVSX0lOQ0gpO1xuICB9XG5cbiAgLy8gQ2xlYW4gcGVyc2lzdGVkIHZhbHVlczogaHVuZHJlZHRocyBvZiBhbiBpbmNoLlxuICBwcml2YXRlIF9yb3VuZCh2YWx1ZTogbnVtYmVyKTogbnVtYmVyIHtcbiAgICByZXR1cm4gTWF0aC5yb3VuZCh2YWx1ZSAqIDEwMCkgLyAxMDA7XG4gIH1cblxuICBwcml2YXRlIF9zbmFwRmxvd1dpZHRoKHZhbHVlOiBudW1iZXIpOiBudW1iZXIge1xuICAgIGZvciAoY29uc3Qgc3RvcCBvZiBGTE9XX1dJRFRIX1NUT1BTKSB7XG4gICAgICBpZiAoTWF0aC5hYnModmFsdWUgLSBzdG9wKSA8IDMpIHtcbiAgICAgICAgcmV0dXJuIHN0b3A7XG4gICAgICB9XG4gICAgfVxuXG4gICAgcmV0dXJuIE1hdGgucm91bmQodmFsdWUgKiAxMCkgLyAxMDtcbiAgfVxuXG4gIC8vIFRoZSBjYW52YXMgcG9zaXRpb25zIHRoZSBob3N0IHZpYSBbc3R5bGVdOyBtaWQtZ2VzdHVyZSB3ZSBzZXQgaXQgZGlyZWN0bHlcbiAgLy8gc28gT25QdXNoIG5ldmVyIHJlLXJlbmRlcnMgaW4gdGhlIG1vdmUgbG9vcC5cbiAgcHJpdmF0ZSBfYXBwbHlHZW9tZXRyeSgpOiB2b2lkIHtcbiAgICBjb25zdCBzdHlsZSA9IHRoaXMuX2hvc3QubmF0aXZlRWxlbWVudC5zdHlsZTtcbiAgICBzdHlsZS5sZWZ0ID0gYCR7dGhpcy5jb21wb25lbnQueCAqIFBYX1BFUl9JTkNIfXB4YDtcbiAgICBzdHlsZS50b3AgPSBgJHt0aGlzLmNvbXBvbmVudC55ICogUFhfUEVSX0lOQ0h9cHhgO1xuICAgIHN0eWxlLndpZHRoID0gYCR7dGhpcy5jb21wb25lbnQudyAqIFBYX1BFUl9JTkNIfXB4YDtcblxuICAgIC8vIEF1dG8gKGtwaSk6IG5vIGZpeGVkIGhlaWdodCDigJQgdGhlIGJveCBzaXplcyB0byBpdHMgY29udGVudC4gRml4ZWRcbiAgICAvLyAoY2hhcnQvbGlzdCk6IGBoYCBpcyB0aGUgZXhhY3QgaGVpZ2h0LiBNaXJyb3JzIHRoZSBjYW52YXMgW3N0eWxlXSBiaW5kaW5nXG4gICAgLy8gc28gdGhlIG1pZC1nZXN0dXJlIHBhaW50IG1hdGNoZXMgdGhlIHBvc3QtZ2VzdHVyZSByZS1yZW5kZXIuXG4gICAgaWYgKHRoaXMuX2hlaWdodEF1dG8pIHtcbiAgICAgIHN0eWxlLmhlaWdodCA9ICcnO1xuICAgIH0gZWxzZSB7XG4gICAgICBzdHlsZS5oZWlnaHQgPSBgJHt0aGlzLmNvbXBvbmVudC5oICogUFhfUEVSX0lOQ0h9cHhgO1xuICAgIH1cbiAgfVxuXG4gIC8vIC0tLS0tIGRhdGEgLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLVxuXG4gIHByaXZhdGUgX2xvYWQoKTogdm9pZCB7XG4gICAgdGhpcy5sb2FkaW5nLnNldCh0cnVlKTtcbiAgICB0aGlzLmVycm9yLnNldChudWxsKTtcblxuICAgIGNvbnN0IGZpbHRlcnMgPSB0aGlzLl9maWx0ZXJTdGF0ZS5yZXNvbHZlRm9yQ29tcG9uZW50KHRoaXMuY29tcG9uZW50KTtcbiAgICAvLyBUaW1lLXNlcmllcyBjaGFydHMgY2FycnkgdGhlIGdyb3VwLWJ5IGdyYWluIChpZiB0aGUgdmlld2VyIHBpY2tlZCBvbmUpIHNvXG4gICAgLy8gdGhlIGJhY2tlbmQgcmUtYnVja2V0czsgZXZlcnl0aGluZyBlbHNlIHNlbmRzIG5vIGludGVyYWN0aW9uIHN0YXRlIGhlcmUuXG4gICAgY29uc3Qgc3RhdGUgPSB0aGlzLl9pc1RpbWVTZXJpZXMgJiYgdGhpcy5fZmlsdGVyU3RhdGUuZnJlcXVlbmN5KClcbiAgICAgID8geyBmcmVxdWVuY3k6IHRoaXMuX2ZpbHRlclN0YXRlLmZyZXF1ZW5jeSgpIH1cbiAgICAgIDoge307XG5cbiAgICB0aGlzLl9yZXBvcnREYXRhLmNvbXBvbmVudERhdGEodGhpcy5yZXBvcnRJZCwgdGhpcy5jb21wb25lbnQuaWQsIGZpbHRlcnMsIHN0YXRlKVxuICAgICAgLnBpcGUodGFrZVVudGlsRGVzdHJveWVkKHRoaXMuX2Rlc3Ryb3lSZWYpKVxuICAgICAgLnN1YnNjcmliZSh7XG4gICAgICAgIG5leHQ6IChkYXRhOiBDb21wb25lbnREYXRhKSA9PiB7XG4gICAgICAgICAgdGhpcy5kYXRhLnNldChkYXRhKTtcbiAgICAgICAgICB0aGlzLmxvYWRpbmcuc2V0KGZhbHNlKTtcbiAgICAgICAgfSxcbiAgICAgICAgZXJyb3I6IChlcnJvcikgPT4ge1xuICAgICAgICAgIHRoaXMubG9hZGluZy5zZXQoZmFsc2UpO1xuICAgICAgICAgIHRoaXMuZXJyb3Iuc2V0KGVycm9yPy5lcnJvcj8ubWVzc2FnZSA/PyBlcnJvcj8ubWVzc2FnZSA/PyAnRmFpbGVkIHRvIGxvYWQgZGF0YScpO1xuICAgICAgICB9LFxuICAgICAgfSk7XG4gIH1cbn1cbiIsIjxkaXZcbiAgICBjbGFzcz1cImNvbXBvbmVudC1ib3hcIlxuICAgIFtjbGFzcy5lZGl0aW5nXT1cImVkaXRNb2RlXCJcbiAgICBbY2xhc3MudGV4dF09XCJpc1RleHRcIlxuICAgIFtjbGFzcy5zZWxlY3RlZF09XCJzZWxlY3RlZFwiXG4gICAgW3N0eWxlLnBhZGRpbmddPVwiYm9keVBhZGRpbmdcIlxuICAgIChwb2ludGVyZG93bik9XCJvbkNvbXBvbmVudFBvaW50ZXJEb3duKCRldmVudClcIlxuICAgIChtb3VzZWRvd24pPVwic3RvcENhbnZhc1BhbigkZXZlbnQpXCJcbiAgICAodG91Y2hzdGFydCk9XCJzdG9wQ2FudmFzUGFuKCRldmVudClcIj5cbiAgPCEtLSBUaGUgaGVhZGVyIGlzIGFuIGZzLWZpbHRlcjogaGVhZGluZyB0ZW1wbGF0ZSA9IHRpdGxlIChhbmQgdGhlIGVkaXQtbW9kZVxuICAgICAgIGRyYWcgaGFuZGxlKSwgYWN0aW9ucyA9IHRoZSBtZW51LCBpdGVtcyA9IGNvbXBvbmVudC1sZXZlbCBmaWx0ZXIgZ3JvdXBzLFxuICAgICAgIHRoZSBzYW1lIHN0cmlwIGZvciBldmVyeSB0eXBlIChsaXN0cyBpbmNsdWRlZCkuIGZzLWZpbHRlciByZWFkcyBpdHNcbiAgICAgICBjb25maWcgb25jZSwgc28gdGhlIGJsb2NrIGlzIGtleWVkIG9uIHRoZSBjb21wb25lbnQtZmlsdGVyIHNldCB0byBiZVxuICAgICAgIHJlY3JlYXRlZCB3aGVuIGl0IGNoYW5nZXMuIC0tPlxuICA8IS0tIEEgdGV4dCBibG9jayBoYXMgbm8gdGl0bGUgYmFyIOKAlCBpdCBJUyBpdHMgd29yZHMsIGxpa2UgYSB0ZXh0IGJveCBvbiBhXG4gICAgICAgc2xpZGUg4oCUIHNvIGl0IGdldHMgbmVpdGhlciB0aGUgaGVhZGVyIG5vciB0aGUgZGF0YSBhY3Rpb25zLiAtLT5cbiAgQGZvciAoa2V5IG9mIGlzVGV4dCA/IFtdIDogW2ZpbHRlcktleV07IHRyYWNrIGtleSkge1xuICAgIDxmcy1maWx0ZXJcbiAgICAgICAgY2xhc3M9XCJjb21wb25lbnQtZmlsdGVyXCJcbiAgICAgICAgW2NvbmZpZ109XCJmaWx0ZXJDb25maWcoKVwiPlxuICAgICAgPG5nLXRlbXBsYXRlIGZzRmlsdGVySGVhZGluZz5cbiAgICAgICAgPGRpdlxuICAgICAgICAgICAgY2xhc3M9XCJjb21wb25lbnQtdGl0bGVcIlxuICAgICAgICAgICAgKHBvaW50ZXJkb3duKT1cIm9uRHJhZ1N0YXJ0KCRldmVudClcIj5cbiAgICAgICAgICB7eyBjb21wb25lbnQudGl0bGUgfX1cbiAgICAgICAgICBAaWYgKHRydW5jYXRlZCkge1xuICAgICAgICAgICAgPG1hdC1pY29uXG4gICAgICAgICAgICAgICAgY2xhc3M9XCJ0cnVuY2F0ZWQtaWNvblwiXG4gICAgICAgICAgICAgICAgbWF0VG9vbHRpcD1cIlNob3dpbmcgYSB0cnVuY2F0ZWQgcmVzdWx0IOKAlCByZWZpbmUgdGhlIGZpbHRlcnMgdG8gc2VlIGV2ZXJ5dGhpbmcuXCI+XG4gICAgICAgICAgICAgIHdhcm5pbmdfYW1iZXJcbiAgICAgICAgICAgIDwvbWF0LWljb24+XG4gICAgICAgICAgfVxuICAgICAgICA8L2Rpdj5cbiAgICAgIDwvbmctdGVtcGxhdGU+XG4gICAgPC9mcy1maWx0ZXI+XG4gIH1cbiAgPCEtLSBUaGUgYWN0aW9ucyBtZW51IGlzIGZsb2F0ZWQgdG9wLXJpZ2h0IChhYnNvbHV0ZSkgcmF0aGVyIHRoYW4gbGl2aW5nIGluXG4gICAgICAgZnMtZmlsdGVyJ3MgYWN0aW9ucyBzbG90LCBzbyBpdHMgfjQwcHggYnV0dG9uIGhlaWdodCBubyBsb25nZXIgZHJpdmVzIHRoZVxuICAgICAgIGhlYWRlciByb3cncyBoZWlnaHQuIEl0IG92ZXJsYXlzIHRoZSBib3ggY29ybmVyOyB0aGUgaGVhZGluZyByZXNlcnZlc1xuICAgICAgIHJpZ2h0IHBhZGRpbmcgc28gYSBsb25nIHRpdGxlIGVsbGlwc2lzZXMgYmVmb3JlIGl0LiAtLT5cbiAgQGlmICghaXNUZXh0IHx8IChlZGl0TW9kZSAmJiAhdGV4dEVkaXRpbmcoKSkpIHtcbiAgICA8YnV0dG9uXG4gICAgICAgIG1hdC1pY29uLWJ1dHRvblxuICAgICAgICBjbGFzcz1cImNvbXBvbmVudC1tZW51XCJcbiAgICAgICAgW2ZzTWVudVRyaWdnZXJGb3JdPVwibWVudVwiXG4gICAgICAgIChwb2ludGVyZG93bik9XCIkZXZlbnQuc3RvcFByb3BhZ2F0aW9uKClcIlxuICAgICAgICAobW91c2Vkb3duKT1cInN0b3BDYW52YXNQYW4oJGV2ZW50KVwiPlxuICAgICAgPG1hdC1pY29uPm1vcmVfdmVydDwvbWF0LWljb24+XG4gICAgPC9idXR0b24+XG4gICAgPCEtLSBCZXNpZGUgaXRzIHRyaWdnZXIsIGluc2lkZSB0aGUgc2FtZSBibG9jazogYW4gZnMtbWVudSB0aGF0IGZpbmRzIG5vXG4gICAgICAgICB0cmlnZ2VyIG9mIGl0cyBvd24gZHJhd3Mgb25lLiAtLT5cbiAgICA8ZnMtbWVudSAjbWVudT5cbiAgICAgIDxuZy10ZW1wbGF0ZVxuICAgICAgICAgIGZzLW1lbnUtaXRlbVxuICAgICAgICAgIFtoaWRkZW5dPVwiIWlzVGV4dFwiXG4gICAgICAgICAgKGNsaWNrKT1cImVkaXRUZXh0KClcIj5cbiAgICAgICAgPG1hdC1pY29uPmVkaXQ8L21hdC1pY29uPlxuICAgICAgICA8c3Bhbj5FZGl0IHRleHQ8L3NwYW4+XG4gICAgICA8L25nLXRlbXBsYXRlPlxuICAgICAgPG5nLXRlbXBsYXRlXG4gICAgICAgICAgZnMtbWVudS1pdGVtXG4gICAgICAgICAgW2hpZGRlbl09XCIhaXNUZXh0XCJcbiAgICAgICAgICAoY2xpY2spPVwiZGVsZXRlVGV4dCgpXCI+XG4gICAgICAgIDxtYXQtaWNvbj5kZWxldGU8L21hdC1pY29uPlxuICAgICAgICA8c3Bhbj5EZWxldGU8L3NwYW4+XG4gICAgICA8L25nLXRlbXBsYXRlPlxuICAgICAgPG5nLXRlbXBsYXRlXG4gICAgICAgICAgZnMtbWVudS1pdGVtXG4gICAgICAgICAgW2hpZGRlbl09XCJpc1RleHRcIlxuICAgICAgICAgIChjbGljayk9XCJzZXR0aW5ncygpXCI+XG4gICAgICAgIDxtYXQtaWNvbj50dW5lPC9tYXQtaWNvbj5cbiAgICAgICAgPHNwYW4+U2V0dGluZ3M8L3NwYW4+XG4gICAgICA8L25nLXRlbXBsYXRlPlxuICAgICAgPG5nLXRlbXBsYXRlXG4gICAgICAgICAgZnMtbWVudS1pdGVtXG4gICAgICAgICAgW2hpZGRlbl09XCJpc1RleHRcIlxuICAgICAgICAgIChjbGljayk9XCJleHBvcnRDc3YoKVwiPlxuICAgICAgICA8bWF0LWljb24+ZG93bmxvYWQ8L21hdC1pY29uPlxuICAgICAgICA8c3Bhbj5FeHBvcnQgQ1NWPC9zcGFuPlxuICAgICAgPC9uZy10ZW1wbGF0ZT5cbiAgICAgIDxuZy10ZW1wbGF0ZVxuICAgICAgICAgIGZzLW1lbnUtaXRlbVxuICAgICAgICAgIFtoaWRkZW5dPVwiIWhpZGVzQ29sdW1uc1wiXG4gICAgICAgICAgKGNsaWNrKT1cImNob29zZUNvbHVtbnMoKVwiPlxuICAgICAgICA8bWF0LWljb24+dmlld19jb2x1bW48L21hdC1pY29uPlxuICAgICAgICA8c3Bhbj5Db2x1bW5zPC9zcGFuPlxuICAgICAgPC9uZy10ZW1wbGF0ZT5cbiAgICA8L2ZzLW1lbnU+XG4gIH1cbiAgPGRpdiBjbGFzcz1cImNvbXBvbmVudC1ib2R5XCI+XG4gICAgQGlmIChpc1RleHQpIHtcbiAgICAgIDxhcHAtcmVwb3J0LWNvbXBvbmVudC10ZXh0XG4gICAgICAgIFtodG1sXT1cImNvbXBvbmVudC5jb25maWc/Lmh0bWwgPz8gJydcIlxuICAgICAgICBbdG9rZW5zXT1cInRva2VucygpXCJcbiAgICAgICAgW2VkaXRpbmddPVwidGV4dEVkaXRpbmcoKVwiXG4gICAgICAgIChzYXZlZCk9XCJvblRleHRTYXZlZCgkZXZlbnQpXCJcbiAgICAgICAgKGVkaXRFbmRlZCk9XCJ0ZXh0RWRpdGluZy5zZXQoZmFsc2UpXCI+XG4gICAgICA8L2FwcC1yZXBvcnQtY29tcG9uZW50LXRleHQ+XG4gICAgfSBAZWxzZSBpZiAoY29tcG9uZW50LnR5cGUgPT09ICdsaXN0Jykge1xuICAgICAgPGFwcC1yZXBvcnQtY29tcG9uZW50LWxpc3RcbiAgICAgICAgW3JlcG9ydElkXT1cInJlcG9ydElkXCJcbiAgICAgICAgW2NvbXBvbmVudF09XCJjb21wb25lbnRcIj5cbiAgICAgIDwvYXBwLXJlcG9ydC1jb21wb25lbnQtbGlzdD5cbiAgICB9IEBlbHNlIGlmIChsb2FkaW5nKCkpIHtcbiAgICAgIDxkaXYgY2xhc3M9XCJjb21wb25lbnQtc3RhdGVcIj5cbiAgICAgICAgPGRpdiBjbGFzcz1cImxvYWRpbmctc2hpbW1lclwiPjwvZGl2PlxuICAgICAgPC9kaXY+XG4gICAgfSBAZWxzZSBpZiAoZXJyb3IoKSkge1xuICAgICAgPGRpdiBjbGFzcz1cImNvbXBvbmVudC1zdGF0ZSBlcnJvclwiPlxuICAgICAgICB7eyBlcnJvcigpIH19XG4gICAgICA8L2Rpdj5cbiAgICB9IEBlbHNlIGlmICghZGF0YSgpPy5yb3dzPy5sZW5ndGgpIHtcbiAgICAgIDxkaXYgY2xhc3M9XCJjb21wb25lbnQtc3RhdGVcIj5cbiAgICAgICAgTm8gZGF0YVxuICAgICAgPC9kaXY+XG4gICAgfSBAZWxzZSBpZiAoY29tcG9uZW50LnR5cGUgPT09ICdrcGknKSB7XG4gICAgICA8YXBwLXJlcG9ydC1jb21wb25lbnQta3BpXG4gICAgICAgIFtjb21wb25lbnRdPVwiY29tcG9uZW50XCJcbiAgICAgICAgW2RhdGFdPVwiZGF0YSgpXCI+XG4gICAgICA8L2FwcC1yZXBvcnQtY29tcG9uZW50LWtwaT5cbiAgICB9IEBlbHNlIHtcbiAgICAgIDxhcHAtcmVwb3J0LWNvbXBvbmVudC1jaGFydFxuICAgICAgICBbY29tcG9uZW50XT1cImNvbXBvbmVudFwiXG4gICAgICAgIFtkYXRhXT1cImRhdGEoKVwiPlxuICAgICAgPC9hcHAtcmVwb3J0LWNvbXBvbmVudC1jaGFydD5cbiAgICB9XG4gICAgPCEtLSBJbiBlZGl0IG1vZGUgYSB0cmFuc3BhcmVudCB2ZWlsIG92ZXIgdGhlIGJvZHkgbWFrZXMgdGhlIFdIT0xFXG4gICAgICAgICBjb21wb25lbnQgZHJhZ2dhYmxlIChpbmR1c3RyeSBzdGFuZGFyZDogeW91IGdyYWIgdGhlIG9iamVjdCwgbm90IGp1c3RcbiAgICAgICAgIGl0cyB0aXRsZSBiYXIpIGFuZCBrZWVwcyBpbm5lciB3aWRnZXRzIGZyb20gc3dhbGxvd2luZyB0aGUgZ2VzdHVyZS4gLS0+XG4gICAgQGlmIChlZGl0TW9kZSAmJiAhdGV4dEVkaXRpbmcoKSkge1xuICAgICAgPGRpdlxuICAgICAgICBjbGFzcz1cImRyYWctdmVpbFwiXG4gICAgICAgIChwb2ludGVyZG93bik9XCJvbkRyYWdTdGFydCgkZXZlbnQpXCI+XG4gICAgICA8L2Rpdj5cbiAgICB9XG4gIDwvZGl2PlxuPC9kaXY+XG48IS0tIEhhbmRsZXMgbGl2ZSBPVVRTSURFIHRoZSBjbGlwcGVkIGJveCBzbyB0aGV5IHN0cmFkZGxlIGl0cyBlZGdlcy4gLS0+XG5AaWYgKGVkaXRNb2RlICYmIHNlbGVjdGVkKSB7XG4gIEBpZiAobGF5b3V0ID09PSAnZnJlZWZvcm0nKSB7XG4gICAgQGZvciAoaGFuZGxlIG9mIHJlc2l6ZUhhbmRsZXM7IHRyYWNrIGhhbmRsZSkge1xuICAgICAgPGRpdlxuICAgICAgICBjbGFzcz1cImhhbmRsZSBoYW5kbGUte3sgaGFuZGxlIH19XCJcbiAgICAgICAgKG1vdXNlZG93bik9XCJzdG9wQ2FudmFzUGFuKCRldmVudClcIlxuICAgICAgICAocG9pbnRlcmRvd24pPVwib25SZXNpemVTdGFydCgkZXZlbnQsIGhhbmRsZSlcIj5cbiAgICAgIDwvZGl2PlxuICAgIH1cbiAgfSBAZWxzZSB7XG4gICAgPCEtLSBGbG93IGhlaWdodCBpcyBhbHdheXMgYXV0byAodGhlIGJveCBmaXRzIGl0cyBjb250ZW50KSwgc28gb25seSB0aGVcbiAgICAgICAgIGVhc3QgaGFuZGxlICh3aWR0aCAlKSBpcyBvZmZlcmVkIGhlcmUuIC0tPlxuICAgIDxkaXZcbiAgICAgIGNsYXNzPVwiaGFuZGxlIGhhbmRsZS1lXCJcbiAgICAgIG1hdFRvb2x0aXA9XCJXaWR0aCAoJSBvZiBwYWdlKVwiXG4gICAgICAobW91c2Vkb3duKT1cInN0b3BDYW52YXNQYW4oJGV2ZW50KVwiXG4gICAgICAocG9pbnRlcmRvd24pPVwib25SZXNpemVTdGFydCgkZXZlbnQsICdlJylcIj5cbiAgICA8L2Rpdj5cbiAgfVxufSJdfQ==
|
|
554
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoicmVwb3J0LWNvbXBvbmVudC5jb21wb25lbnQuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi8uLi8uLi9zcmMvYXBwL3JlcG9ydHMvY29tcG9uZW50cy9yZXBvcnQtY29tcG9uZW50L3JlcG9ydC1jb21wb25lbnQuY29tcG9uZW50LnRzIiwiLi4vLi4vLi4vLi4vLi4vLi4vc3JjL2FwcC9yZXBvcnRzL2NvbXBvbmVudHMvcmVwb3J0LWNvbXBvbmVudC9yZXBvcnQtY29tcG9uZW50LmNvbXBvbmVudC5odG1sIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBLE9BQU8sRUFDTCx1QkFBdUIsRUFBRSxTQUFTLEVBQUUsVUFBVSxFQUFFLFVBQVUsRUFDMUQsWUFBWSxFQUFFLFdBQVcsRUFBRSxLQUFLLEVBQUUsTUFBTSxFQUFxQixNQUFNLEVBQWlCLFNBQVMsRUFBRSxNQUFNLEVBQ3JHLEtBQUssRUFBRSxNQUFNLEVBQUUsTUFBTSxHQUN0QixNQUFNLGVBQWUsQ0FBQztBQUd2QixPQUFPLEVBQUUsYUFBYSxFQUFFLE1BQU0sMEJBQTBCLENBQUM7QUFDekQsT0FBTyxFQUFFLFNBQVMsRUFBRSxNQUFNLDBCQUEwQixDQUFDO0FBQ3JELE9BQU8sRUFBRSxPQUFPLEVBQUUsTUFBTSx3QkFBd0IsQ0FBQztBQUNqRCxPQUFPLEVBQUUsVUFBVSxFQUFFLE1BQU0sMkJBQTJCLENBQUM7QUFFdkQsT0FBTyxFQUFnQixjQUFjLEVBQUUsTUFBTSxvQkFBb0IsQ0FBQztBQUNsRSxPQUFPLEVBQUUsWUFBWSxFQUFFLE1BQU0sa0JBQWtCLENBQUM7QUFDaEQsT0FBTyxFQUFFLFNBQVMsRUFBRSxNQUFNLHFCQUFxQixDQUFDO0FBQ2hELE9BQU8sRUFBRSxTQUFTLEVBQUUsTUFBTSxxQkFBcUIsQ0FBQztBQUNoRCxPQUFPLEVBQUUsUUFBUSxFQUFFLE1BQU0sb0JBQW9CLENBQUM7QUFFOUMsT0FBTyxFQUFFLE9BQU8sRUFBRSxZQUFZLEVBQUUsR0FBRyxF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QXZCLEtBQUs7Z0JBRVcsZUFBZTtzQkFBL0IsTUFBTTtnQkFDVSxlQUFlO3NCQUEvQixNQUFNO2dCQUNVLFlBQVk7c0JBQTVCLE1BQU07Z0JBY0EsY0FBYztzQkFEcEIsU0FBUzt1QkFBQyx1QkFBdUI7Z0JBcWV2QixVQUFVO3NCQURwQixXQUFXO3VCQUFDLG1CQUFtQiIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7XG4gIENoYW5nZURldGVjdGlvblN0cmF0ZWd5LCBDb21wb25lbnQsIERlc3Ryb3lSZWYsIEVsZW1lbnRSZWYsXG4gIEV2ZW50RW1pdHRlciwgSG9zdEJpbmRpbmcsIElucHV0LCBOZ1pvbmUsIE9uQ2hhbmdlcywgT25Jbml0LCBPdXRwdXQsIFNpbXBsZUNoYW5nZXMsIFZpZXdDaGlsZCwgaW5qZWN0LFxuICBpbnB1dCwgb3V0cHV0LCBzaWduYWwsXG59IGZyb20gJ0Bhbmd1bGFyL2NvcmUnO1xuXG5cbmltcG9ydCB7IE1hdEljb25CdXR0b24gfSBmcm9tICdAYW5ndWxhci9tYXRlcmlhbC9idXR0b24nO1xuaW1wb3J0IHsgTWF0RGlhbG9nIH0gZnJvbSAnQGFuZ3VsYXIvbWF0ZXJpYWwvZGlhbG9nJztcbmltcG9ydCB7IE1hdEljb24gfSBmcm9tICdAYW5ndWxhci9tYXRlcmlhbC9pY29uJztcbmltcG9ydCB7IE1hdFRvb2x0aXAgfSBmcm9tICdAYW5ndWxhci9tYXRlcmlhbC90b29sdGlwJztcblxuaW1wb3J0IHsgRmlsdGVyQ29uZmlnLCBGc0ZpbHRlck1vZHVsZSB9IGZyb20gJ0BmaXJlc3RpdGNoL2ZpbHRlcic7XG5pbXBvcnQgeyBGc01lbnVNb2R1bGUgfSBmcm9tICdAZmlyZXN0aXRjaC9tZW51JztcbmltcG9ydCB7IEZzTWVzc2FnZSB9IGZyb20gJ0BmaXJlc3RpdGNoL21lc3NhZ2UnO1xuaW1wb3J0IHsgRnNQcm9jZXNzIH0gZnJvbSAnQGZpcmVzdGl0Y2gvcHJvY2Vzcyc7XG5pbXBvcnQgeyBGc1Byb21wdCB9IGZyb20gJ0BmaXJlc3RpdGNoL3Byb21wdCc7XG5cbmltcG9ydCB7IFN1YmplY3QsIGRlYm91bmNlVGltZSwgbWFwLCBzd2l0Y2hNYXAsIHRhcCB9IGZyb20gJ3J4anMnO1xuXG5pbXBvcnQgeyB0YWtlVW50aWxEZXN0cm95ZWQgfSBmcm9tICdAYW5ndWxhci9jb3JlL3J4anMtaW50ZXJvcCc7XG5cbmltcG9ydCB7IFJlcG9ydERhdGEgfSBmcm9tICcuLi8uLi9kYXRhL3JlcG9ydC5kYXRhJztcbmltcG9ydCB7IExpc3RDb2x1bW5zQ29tcG9uZW50LCBMaXN0Q29sdW1uc0RpYWxvZ0RhdGEgfSBmcm9tICcuLi8uLi9kaWFsb2dzL2xpc3QtY29sdW1ucy9saXN0LWNvbHVtbnMuY29tcG9uZW50JztcbmltcG9ydCB7XG4gIENvbXBvbmVudERhdGEsXG4gIENvbXBvbmVudERhdGFTdGF0ZSxcbiAgQ29tcG9uZW50U2V0dGluZ3MsXG4gIEtwaUNvbmZpZyxcbiAgUmVwb3J0Q29tcG9uZW50IGFzIFJlcG9ydENvbXBvbmVudE1vZGVsLFxuICBSZXBvcnRGaWx0ZXJHcm91cCxcbn0gZnJvbSAnLi4vLi4vaW50ZXJmYWNlcy9yZXBvcnQuaW50ZXJmYWNlJztcbmltcG9ydCB7IGtwaUNhcmRTZXR0aW5ncywgc2FtZUtwaUNhcmRTZXR0aW5ncyB9IGZyb20gJy4uLy4uL2twaS1jYXJkJztcbmltcG9ydCB7IERFRkFVTFRfQ09NUE9ORU5UX1BBRERJTkcgfSBmcm9tICcuLi8uLi9sYXlvdXQnO1xuaW1wb3J0IHsgbGlzdEhpZGVhYmxlQ29sdW1ucyB9IGZyb20gJy4uLy4uL2xpc3QtY29uZmlnJztcbmltcG9ydCB7XG4gIExJU1RfU0VBUkNIX0lURU0sIGZpbHRlckl0ZW1Gb3JHcm91cCwgZ3JvdXBWYWx1ZXNGcm9tUXVlcnksIGxpc3RTZWFyY2hJdGVtLFxufSBmcm9tICcuLi8uLi9yZXBvcnQtZmlsdGVyLWl0ZW1zJztcbmltcG9ydCB7IG1vdmVkR3JvdXBWYWx1ZXMsIFJlcG9ydEZpbHRlclN0YXRlU2VydmljZSB9IGZyb20gJy4uLy4uL3NlcnZpY2VzL3JlcG9ydC1maWx0ZXItc3RhdGUuc2VydmljZSc7XG5pbXBvcnQgeyBDb21wb25lbnRDaGFydENvbXBvbmVudCB9IGZyb20gJy4uL2NvbXBvbmVudC1jaGFydC9jb21wb25lbnQtY2hhcnQuY29tcG9uZW50JztcbmltcG9ydCB7IENvbXBvbmVudEtwaUNvbXBvbmVudCB9IGZyb20gJy4uL2NvbXBvbmVudC1rcGkvY29tcG9uZW50LWtwaS5jb21wb25lbnQnO1xuaW1wb3J0IHsgQ29tcG9uZW50TGlzdENvbXBvbmVudCB9IGZyb20gJy4uL2NvbXBvbmVudC1saXN0L2NvbXBvbmVudC1saXN0LmNvbXBvbmVudCc7XG5pbXBvcnQgeyBDb21wb25lbnRUZXh0Q29tcG9uZW50IH0gZnJvbSAnLi4vY29tcG9uZW50LXRleHQvY29tcG9uZW50LXRleHQuY29tcG9uZW50JztcbmltcG9ydCB7IFRleHRUb2tlbkNvbnRleHQgfSBmcm9tICcuLi8uLi90ZXh0JztcbmltcG9ydCB7IENhbnZhc1NuYXBwZXIsIFBYX1BFUl9JTkNIIH0gZnJvbSAnLi4vcmVwb3J0LWNhbnZhcy9yZXBvcnQtY2FudmFzLmNvbXBvbmVudCc7XG5cblxuLy8gUmVzaXplIGhhbmRsZXMsIG5hbWVkIGJ5IGNvbXBhc3MgZGlyZWN0aW9uLlxuY29uc3QgSEFORExFUyA9IFsnbncnLCAnbicsICduZScsICdlJywgJ3NlJywgJ3MnLCAnc3cnLCAndyddIGFzIGNvbnN0O1xudHlwZSBIYW5kbGUgPSB0eXBlb2YgSEFORExFU1tudW1iZXJdO1xuXG5jb25zdCBNSU5fVyA9IDAuNjsgLy8gaW5jaGVzXG5jb25zdCBNSU5fSCA9IDAuNDsgLy8gaW5jaGVzXG5cbi8vIFR3byBwcmVzc2VzIG9uIGEgdGV4dCBibG9jayB0aGlzIGNsb3NlIHRvZ2V0aGVyIG9wZW4gaXRzIGVkaXRvci4gRGV0ZWN0ZWRcbi8vIGhlcmUgcmF0aGVyIHRoYW4gd2l0aCBhIGRibGNsaWNrIGxpc3RlbmVyIGJlY2F1c2UgdGhlIGRyYWcgbG9vcCBjbGFpbXMgdGhlXG4vLyBwb2ludGVyIG9uIGV2ZXJ5IHByZXNzLCBhbmQgYSBicm93c2VyIGlzIG5vdCBvYmxpZ2VkIHRvIGRlbGl2ZXIgZGJsY2xpY2tcbi8vIHRocm91Z2ggYSBjYXB0dXJlZCwgZGVmYXVsdC1wcmV2ZW50ZWQgcG9pbnRlci5cbmNvbnN0IERPVUJMRV9QUkVTU19NUyA9IDQwMDtcblxuLy8gT25lIGNvbXBvbmVudCBvbiB0aGUgcGFnZTogdGl0bGUgYmFyLCB0aGUgdHlwZS1zcGVjaWZpYyBib2R5IChjaGFydCB8IGxpc3Rcbi8vIHwga3BpKSwgYSBtZW51IChzZXR0aW5ncywgZmlsdGVyIHRvZ2dsZXMsIGV4cG9ydCkg4oCUIGFuZCB0aGUgZWRpdGluZ1xuLy8gaW50ZXJhY3Rpb25zOiBjbGljayBzZWxlY3RzOyB0aGUgc2VsZWN0aW9uIGZyYW1lIHNob3dzIDggcmVzaXplIGhhbmRsZXM7XG4vLyBkcmFnZ2luZyB0aGUgYm9keSBtb3ZlcyB3aXRoIHNtYXJ0IGFsaWdubWVudCBndWlkZXMgKHZpYSB0aGUgY2FudmFzXG4vLyBzbmFwcGVyKTsgZXZlcnl0aGluZyB3b3JrcyBhdCBhbnkgem9vbSAocGl4ZWwgZGVsdGFzIMO3IHpvb23Ctzk2IOKGkiBpbmNoZXMpLlxuLy9cbi8vIENoYXJ0cyBhbmQgS1BJcyBmZXRjaCB0aGVpciBvd24gZGF0YSBoZXJlOyBsaXN0cyBmZXRjaCBpbnNpZGVcbi8vIENvbXBvbmVudExpc3RDb21wb25lbnQgdGhyb3VnaCBGc0xpc3QgcGFnaW5nLlxuQENvbXBvbmVudCh7XG4gIHNlbGVjdG9yOiAnYXBwLXJlcG9ydC1jb21wb25lbnQnLFxuICB0ZW1wbGF0ZVVybDogJy4vcmVwb3J0LWNvbXBvbmVudC5jb21wb25lbnQuaHRtbCcsXG4gIHN0eWxlVXJsczogWycuL3JlcG9ydC1jb21wb25lbnQuY29tcG9uZW50LnNjc3MnXSxcbiAgY2hhbmdlRGV0ZWN0aW9uOiBDaGFuZ2VEZXRlY3Rpb25TdHJhdGVneS5PblB1c2gsXG4gIHN0YW5kYWxvbmU6IHRydWUsXG4gIGltcG9ydHM6IFtcbiAgICBNYXRJY29uLFxuICAgIE1hdEljb25CdXR0b24sXG4gICAgTWF0VG9vbHRpcCxcbiAgICBGc0ZpbHRlck1vZHVsZSxcbiAgICBGc01lbnVNb2R1bGUsXG4gICAgQ29tcG9uZW50Q2hhcnRDb21wb25lbnQsXG4gICAgQ29tcG9uZW50S3BpQ29tcG9uZW50LFxuICAgIENvbXBvbmVudExpc3RDb21wb25lbnQsXG4gICAgQ29tcG9uZW50VGV4dENvbXBvbmVudCxcbiAgXSxcbn0pXG5leHBvcnQgY2xhc3MgUmVwb3J0Q29tcG9uZW50Q29tcG9uZW50IGltcGxlbWVudHMgT25Jbml0LCBPbkNoYW5nZXMge1xuXG4gIEBJbnB1dCgpIHB1YmxpYyByZXBvcnRJZDogbnVtYmVyO1xuICBASW5wdXQoKSBwdWJsaWMgY29tcG9uZW50OiBSZXBvcnRDb21wb25lbnRNb2RlbDtcbiAgQElucHV0KCkgcHVibGljIGdyb3VwczogTWFwPG51bWJlciwgUmVwb3J0RmlsdGVyR3JvdXA+O1xuICBASW5wdXQoKSBwdWJsaWMgZWRpdE1vZGUgPSBmYWxzZTtcbiAgLy8gVGhlIGNhbnZhcyB6b29tIOKAlCBjb252ZXJ0cyBvbi1zY3JlZW4gcGl4ZWwgZGVsdGFzIGJhY2sgdG8gaW5jaGVzLlxuICBASW5wdXQoKSBwdWJsaWMgem9vbSA9IDE7XG4gIEBJbnB1dCgpIHB1YmxpYyBzbmFwcGVyOiBDYW52YXNTbmFwcGVyIHwgbnVsbCA9IG51bGw7XG4gIEBJbnB1dCgpIHB1YmxpYyBzZWxlY3RlZCA9IGZhbHNlO1xuXG4gIEBPdXRwdXQoKSBwdWJsaWMgc2VsZWN0Q29tcG9uZW50ID0gbmV3IEV2ZW50RW1pdHRlcjxudW1iZXI+KCk7XG4gIEBPdXRwdXQoKSBwdWJsaWMgcG9zaXRpb25DaGFuZ2VkID0gbmV3IEV2ZW50RW1pdHRlcjx7IGNvbXBvbmVudElkOiBudW1iZXIgfSAmIFJlY29yZDxzdHJpbmcsIG51bWJlcj4+KCk7XG4gIEBPdXRwdXQoKSBwdWJsaWMgb3BlblNldHRpbmdzID0gbmV3IEV2ZW50RW1pdHRlcjxSZXBvcnRDb21wb25lbnRNb2RlbD4oKTtcblxuICAvLyBXaGF0IGEgdGV4dCBibG9jaydzIHt7dG9rZW5zfX0gZmlsbCB3aXRoIG9uIHRoZSBwYWdlIGl0IGlzIGRyYXduIG9uLlxuICBwdWJsaWMgcmVhZG9ubHkgdG9rZW5zID0gaW5wdXQ8VGV4dFRva2VuQ29udGV4dD4oeyBwYWdlTnVtYmVyOiAxLCBwYWdlTmFtZTogJycsIHJlcG9ydE5hbWU6ICcnIH0pO1xuXG4gIC8vIEEgdGV4dCBibG9jayB3YXMgZGVsZXRlZCBmcm9tIGl0cyBtZW51IOKAlCB0aGUgY2FudmFzIGRyb3BzIGl0LlxuICBwdWJsaWMgcmVhZG9ubHkgcmVtb3ZlZCA9IG91dHB1dDxudW1iZXI+KCk7XG5cbiAgLy8gVGhlIHRleHQgYmxvY2sncyBlZGl0b3IgaXMgb3BlbiAoZG91YmxlLXByZXNzIGluIGVkaXQgbW9kZSkuIENsb3NlZCBieSBmb2N1c1xuICAvLyBsZWF2aW5nIHRoZSBibG9jaywgYnkgZGVzZWxlY3RpbmcgaXQsIG9yIGJ5IGxlYXZpbmcgZWRpdCBtb2RlIOKAlCBlYWNoIG9mXG4gIC8vIHdoaWNoIHNhdmVzLlxuICBwdWJsaWMgcmVhZG9ubHkgdGV4dEVkaXRpbmcgPSBzaWduYWwoZmFsc2UpO1xuXG4gIEBWaWV3Q2hpbGQoQ29tcG9uZW50Q2hhcnRDb21wb25lbnQpXG4gIHB1YmxpYyBjaGFydENvbXBvbmVudDogQ29tcG9uZW50Q2hhcnRDb21wb25lbnQ7XG5cbiAgLy8gUmVzaXplIGhhbmRsZXMgYnkgdHlwZTogYSBmaXhlZC1oZWlnaHQgY29tcG9uZW50IChjaGFydC9saXN0KVxuICAvLyBnZXRzIGFsbCBlaWdodCAocmVzaXplIHdpZHRoIEFORCBoZWlnaHQpOyBhbiBhdXRvLWhlaWdodCBvbmUgKGtwaSkgZ2V0c1xuICAvLyBvbmx5IHRoZSBzaWRlIGhhbmRsZXMgc2luY2UgaXRzIGhlaWdodCBmaXRzIGl0cyBjb250ZW50IGFuZCBjYW4ndCBiZSBzZXQuXG4gIHB1YmxpYyBnZXQgcmVzaXplSGFuZGxlcygpOiByZWFkb25seSBIYW5kbGVbXSB7XG4gICAgcmV0dXJuIHRoaXMuX2hlaWdodEF1dG8gPyBbJ2UnLCAndyddIDogSEFORExFUztcbiAgfVxuXG4gIC8vIFRoZSBjb21wb25lbnQncyBoZWFkZXIgSVMgYW4gZnMtZmlsdGVyOiBoZWFkaW5nIHRlbXBsYXRlID0gaXRzIHRpdGxlIChhbmRcbiAgLy8gdGhlIGRyYWcgaGFuZGxlKSwgYWN0aW9ucyA9IHRoZSBTZXR0aW5ncyAvIGZpbHRlci10b2dnbGVzIC8gRXhwb3J0IG1lbnUsXG4gIC8vIGl0ZW1zID0gaXRzIGNvbXBvbmVudC1sZXZlbCBmaWx0ZXIgZ3JvdXBzLCBmb3IgZXZlcnkgY29tcG9uZW50IHR5cGUsIGxpc3RzXG4gIC8vIGluY2x1ZGVkLCBwbHVzIGEgbGlzdCdzIHNlYXJjaCBib3guIFJlYnVpbHQgd2hlbiBhIGZpbHRlciB0b2dnbGUgY2hhbmdlcyB3aGljaCBncm91cHMgc2hvdyxcbiAgLy8gYW5kIHdoZW4gdGhlIHNldHRpbmdzIGRpYWxvZyBjaGFuZ2VzIHRoZSB0aXRsZSBvciBwYWRkaW5nOiBzZXR0aW5nIGl0XG4gIC8vIHJlcGFpbnRzIHRoZSBoZWFkZXIgYW5kIGJvZHkuXG4gIHB1YmxpYyByZWFkb25seSBmaWx0ZXJDb25maWcgPSBzaWduYWw8RmlsdGVyQ29uZmlnIHwgbnVsbD4obnVsbCk7XG5cbiAgcHVibGljIHJlYWRvbmx5IGRhdGEgPSBzaWduYWw8Q29tcG9uZW50RGF0YSB8IG51bGw+KG51bGwpO1xuICBwdWJsaWMgcmVhZG9ubHkgbG9hZGluZyA9IHNpZ25hbChmYWxzZSk7XG4gIHB1YmxpYyByZWFkb25seSBlcnJvciA9IHNpZ25hbDxzdHJpbmcgfCBudWxsPihudWxsKTtcblxuICBwcml2YXRlIF9yZWZyZXNoJCA9IG5ldyBTdWJqZWN0PHZvaWQ+KCk7XG4gIHByaXZhdGUgX3JlcG9ydERhdGEgPSBpbmplY3QoUmVwb3J0RGF0YSk7XG4gIHByaXZhdGUgX2ZpbHRlclN0YXRlID0gaW5qZWN0KFJlcG9ydEZpbHRlclN0YXRlU2VydmljZSk7XG4gIHByaXZhdGUgX3Byb2Nlc3MgPSBpbmplY3QoRnNQcm9jZXNzKTtcbiAgcHJpdmF0ZSBfbWVzc2FnZSA9IGluamVjdChGc01lc3NhZ2UpO1xuICBwcml2YXRlIF9wcm9tcHQgPSBpbmplY3QoRnNQcm9tcHQpO1xuICBwcml2YXRlIF9kaWFsb2cgPSBpbmplY3QoTWF0RGlhbG9nKTtcbiAgcHJpdmF0ZSBfbGFzdFByZXNzID0gMDtcbiAgcHJpdmF0ZSBfZGVzdHJveVJlZiA9IGluamVjdChEZXN0cm95UmVmKTtcbiAgcHJpdmF0ZSBfem9uZSA9IGluamVjdChOZ1pvbmUpO1xuICBwcml2YXRlIF9ob3N0OiBFbGVtZW50UmVmPEhUTUxFbGVtZW50PiA9IGluamVjdChFbGVtZW50UmVmKTtcblxuICBwdWJsaWMgbmdPbkluaXQoKTogdm9pZCB7XG4gICAgdGhpcy5fYnVpbGRGaWx0ZXJDb25maWcoKTtcblxuICAgIC8vIExpc3RzIGZldGNoIHRocm91Z2ggRnNMaXN0OyB0ZXh0IGhhcyBub3RoaW5nIHRvIGZldGNoLlxuICAgIGlmICh0aGlzLmNvbXBvbmVudC50eXBlICE9PSAnbGlzdCcgJiYgIXRoaXMuaXNUZXh0KSB7XG4gICAgICAvLyBEZWJvdW5jZWQgc28gYSByYXBpZCBmaWx0ZXIgc3dlZXAgZmlyZXMgb25lIHF1ZXJ5LCBub3Qgb25lIHBlciBjaGFuZ2UuXG4gICAgICB0aGlzLl9yZWZyZXNoJFxuICAgICAgICAucGlwZShcbiAgICAgICAgICBkZWJvdW5jZVRpbWUoMzAwKSxcbiAgICAgICAgICB0YWtlVW50aWxEZXN0cm95ZWQodGhpcy5fZGVzdHJveVJlZiksXG4gICAgICAgIClcbiAgICAgICAgLnN1YnNjcmliZSgoKSA9PiB0aGlzLl9sb2FkKCkpO1xuXG4gICAgICB0aGlzLl9maWx0ZXJTdGF0ZS5jaGFuZ2VzRm9yKHRoaXMuY29tcG9uZW50KVxuICAgICAgICAucGlwZSh0YWtlVW50aWxEZXN0cm95ZWQodGhpcy5fZGVzdHJveVJlZikpXG4gICAgICAgIC5zdWJzY3JpYmUoKCkgPT4gdGhpcy5fcmVmcmVzaCQubmV4dCgpKTtcblxuICAgICAgLy8gQSBncm91cC1ieSBjaGFuZ2UgcmUtYnVja2V0cyBldmVyeSB0aW1lLXNlcmllcyBjaGFydDsgaXQgaXNuJ3Qgc2NvcGVkXG4gICAgICAvLyB0byBhIGZpbHRlciBncm91cCwgc28gaXQgcmlkZXMgaXRzIG93biBzdHJlYW0uXG4gICAgICBpZiAodGhpcy5faXNUaW1lU2VyaWVzKSB7XG4gICAgICAgIHRoaXMuX2ZpbHRlclN0YXRlLmZyZXF1ZW5jeUNoYW5nZXMoKVxuICAgICAgICAgIC5waXBlKHRha2VVbnRpbERlc3Ryb3llZCh0aGlzLl9kZXN0cm95UmVmKSlcbiAgICAgICAgICAuc3Vic2NyaWJlKCgpID0+IHRoaXMuX3JlZnJlc2gkLm5leHQoKSk7XG4gICAgICB9XG5cbiAgICAgIHRoaXMuX2xvYWQoKTtcbiAgICB9XG4gIH1cblxuICAvLyBUaGUgcmVwb3J0IHJlbG9hZHMgKGUuZy4gYWZ0ZXIgdGhlIHNldHRpbmdzIGRpYWxvZyBhZGRzL21vdmVzIGEgZmlsdGVyKVxuICAvLyBoYW5kIHRoaXMgaW5zdGFuY2UgZnJlc2ggYGNvbXBvbmVudGAvYGdyb3Vwc2AgaW5wdXRzIHdpdGhvdXQgcmUtcnVubmluZ1xuICAvLyBuZ09uSW5pdC4gUmVidWlsZCB0aGUgaGVhZGVyIGNvbmZpZyBzbyB0aGUgaW5saW5lIGNvbXBvbmVudC1maWx0ZXIgc3RyaXBcbiAgLy8gcmVmbGVjdHMgdGhlIG5ldyBmaWx0ZXJzOyB0aGUgdGVtcGxhdGUgcmVjcmVhdGVzIHRoZSBmcy1maWx0ZXIgdmlhXG4gIC8vIGBmaWx0ZXJLZXlgIHNvIGl0IGFjdHVhbGx5IHJlLXJlYWRzIHRoaXMgY29uZmlnLlxuICBwdWJsaWMgbmdPbkNoYW5nZXMoY2hhbmdlczogU2ltcGxlQ2hhbmdlcyk6IHZvaWQge1xuICAgIC8vIENsaWNraW5nIGF3YXkgKGRlc2VsZWN0KSBvciBsZWF2aW5nIGVkaXQgbW9kZSBjbG9zZXMgYW4gb3BlbiB0ZXh0IGVkaXRvcixcbiAgICAvLyB3aGljaCBpcyB3aGF0IHNhdmVzIGl0LlxuICAgIGlmICgoY2hhbmdlcy5zZWxlY3RlZCAmJiAhdGhpcy5zZWxlY3RlZCkgfHwgKGNoYW5nZXMuZWRpdE1vZGUgJiYgIXRoaXMuZWRpdE1vZGUpKSB7XG4gICAgICB0aGlzLnRleHRFZGl0aW5nLnNldChmYWxzZSk7XG4gICAgfVxuXG4gICAgY29uc3QgZmlsdGVyc0NoYW5nZWQgPSAoY2hhbmdlcy5jb21wb25lbnQgJiYgIWNoYW5nZXMuY29tcG9uZW50LmZpcnN0Q2hhbmdlKVxuICAgICAgfHwgKGNoYW5nZXMuZ3JvdXBzICYmICFjaGFuZ2VzLmdyb3Vwcy5maXJzdENoYW5nZSk7XG5cbiAgICBpZiAoZmlsdGVyc0NoYW5nZWQpIHtcbiAgICAgIHRoaXMuX2J1aWxkRmlsdGVyQ29uZmlnKCk7XG4gICAgfVxuICB9XG5cbiAgLy8gZnMtZmlsdGVyIHJlYWRzIGl0cyBjb25maWcgb25seSBvbmNlIGF0IGluaXQsIHNvIHRoZSBoZWFkZXIgaXMga2V5ZWQgb24gd2hhdFxuICAvLyBpdCByZW5kZXJzOiB0aGUgc2V0IG9mIGNvbXBvbmVudC1sZXZlbCBmaWx0ZXIgZ3JvdXBzIEFORCB0aGUgdGl0bGUsIHdoaWNoXG4gIC8vIGxpdmVzIGluIGZzLWZpbHRlcidzIGhlYWRpbmcgdGVtcGxhdGUuIGZzLWZpbHRlciBpcyBPblB1c2ggYW5kIHRoZSBoZWFkaW5nIGlzXG4gIC8vIHJlbmRlcmVkIGluc2lkZSBJVFMgdmlldywgc28gbWFya2luZyB0aGlzIGNvbXBvbmVudCBkb2VzIG5vdCByZXBhaW50IHRoZVxuICAvLyB0aXRsZSDigJQgcmVjcmVhdGluZyB0aGUgYmxvY2sgZG9lcy5cbiAgcHVibGljIGdldCBmaWx0ZXJLZXkoKTogc3RyaW5nIHtcbiAgICByZXR1cm4gW1xuICAgICAgdGhpcy5jb21wb25lbnQudGl0bGUsXG4gICAgICAuLi50aGlzLmNvbXBvbmVudEZpbHRlckdyb3Vwcy5tYXAoKGdyb3VwKSA9PiBgJHtncm91cC5pZH06JHtncm91cC5sZXZlbH1gKSxcbiAgICBdLmpvaW4oJ3wnKTtcbiAgfVxuXG4gIHB1YmxpYyBnZXQgaXNUZXh0KCk6IGJvb2xlYW4ge1xuICAgIHJldHVybiB0aGlzLmNvbXBvbmVudC50eXBlID09PSAndGV4dCc7XG4gIH1cblxuICAvLyBPcGVuIHRoZSB0ZXh0IGVkaXRvciBpbiBwbGFjZS5cbiAgcHVibGljIGVkaXRUZXh0KCk6IHZvaWQge1xuICAgIGlmICghdGhpcy5lZGl0TW9kZSB8fCAhdGhpcy5pc1RleHQpIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICB0aGlzLnNlbGVjdENvbXBvbmVudC5lbWl0KHRoaXMuY29tcG9uZW50LmlkKTtcbiAgICB0aGlzLnRleHRFZGl0aW5nLnNldCh0cnVlKTtcbiAgfVxuXG4gIC8vIFRoZSBlZGl0b3IgY2xvc2VkIHdpdGggY2hhbmdlZCBodG1sLiBLZXB0IGxvY2FsbHkgYXQgb25jZSBzbyB0aGUgYmxvY2tcbiAgLy8gcmUtcmVuZGVycyB3aGF0IHdhcyB0eXBlZDsgdGhlIHNlcnZlciByZWJ1aWxkcyBpdCBmcm9tIGl0cyBhbGxvd2xpc3QsIHdoaWNoXG4gIC8vIGZvciBhbnl0aGluZyB0aGUgZWRpdG9yIGNhbiBwcm9kdWNlIGlzIHRoZSBzYW1lIGh0bWwuXG4gIHB1YmxpYyBvblRleHRTYXZlZChodG1sOiBzdHJpbmcpOiB2b2lkIHtcbiAgICB0aGlzLmNvbXBvbmVudC5jb25maWcgPSB7IC4uLnRoaXMuY29tcG9uZW50LmNvbmZpZywgaHRtbCB9O1xuICAgIHRoaXMuX3JlcG9ydERhdGEudXBkYXRlQ29tcG9uZW50KHRoaXMucmVwb3J0SWQsIHRoaXMuY29tcG9uZW50LmlkLCB7IGh0bWwgfSlcbiAgICAgIC5waXBlKHRha2VVbnRpbERlc3Ryb3llZCh0aGlzLl9kZXN0cm95UmVmKSlcbiAgICAgIC5zdWJzY3JpYmUoKTtcbiAgfVxuXG4gIHB1YmxpYyBkZWxldGVUZXh0KCk6IHZvaWQge1xuICAgIHRoaXMuX3Byb21wdC5jb25maXJtKHtcbiAgICAgIHRpdGxlOiAnQ29uZmlybScsXG4gICAgICB0ZW1wbGF0ZTogJ0FyZSB5b3Ugc3VyZSB5b3Ugd291bGQgbGlrZSB0byBkZWxldGUgdGhpcyB0ZXh0PycsXG4gICAgfSlcbiAgICAgIC5waXBlKFxuICAgICAgICBzd2l0Y2hNYXAoKCkgPT4gdGhpcy5fcmVwb3J0RGF0YS5kZWxldGVDb21wb25lbnQodGhpcy5yZXBvcnRJZCwgdGhpcy5jb21wb25lbnQuaWQpKSxcbiAgICAgICAgdGFrZVVudGlsRGVzdHJveWVkKHRoaXMuX2Rlc3Ryb3lSZWYpLFxuICAgICAgKVxuICAgICAgLnN1YnNjcmliZSgoKSA9PiB0aGlzLnJlbW92ZWQuZW1pdCh0aGlzLmNvbXBvbmVudC5pZCkpO1xuICB9XG5cbiAgcHVibGljIGdldCB0cnVuY2F0ZWQoKTogYm9vbGVhbiB7XG4gICAgcmV0dXJuICEhdGhpcy5kYXRhKCk/LnRydW5jYXRlZDtcbiAgfVxuXG4gIC8vIENvbnRlbnQgcGFkZGluZyAoaW5jaGVzIOKGkiBweCBhdCA5Ni9pbjsgdGhlIGNhbnZhcyB6b29tIHNjYWxlcyB0aGUgcGFnZSBhc1xuICAvLyBhIHdob2xlKS4gRWFjaCBlZGdlIGRlZmF1bHRzIHRvIDEvOFwiLlxuICBwdWJsaWMgZ2V0IGJvZHlQYWRkaW5nKCk6IHN0cmluZyB7XG4gICAgY29uc3QgcGFkZGluZyA9IHRoaXMuY29tcG9uZW50LmNvbmZpZz8ucGFkZGluZztcbiAgICBjb25zdCBlZGdlID0gKHZhbHVlOiBudW1iZXIgfCB1bmRlZmluZWQpID0+IGAkeyh2YWx1ZSA/PyBERUZBVUxUX0NPTVBPTkVOVF9QQURESU5HKSAqIFBYX1BFUl9JTkNIfXB4YDtcblxuICAgIHJldHVybiBgJHtlZGdlKHBhZGRpbmc/LnRvcCl9ICR7ZWRnZShwYWRkaW5nPy5yaWdodCl9ICR7ZWRnZShwYWRkaW5nPy5ib3R0b20pfSAke2VkZ2UocGFkZGluZz8ubGVmdCl9YDtcbiAgfVxuXG4gIC8vIFRoZSBjb21wb25lbnQtbGV2ZWwgZmlsdGVyIGdyb3VwcyB0aGF0IHNob3VsZCByZW5kZXIgYXMgYW4gaW5saW5lIGNvbnRyb2xcbiAgLy8gc3RyaXAgb24gVEhJUyBjb21wb25lbnQ6IGEgZ3JvdXAgaXMgaW5jbHVkZWQgd2hlbiBpdCdzIGxldmVsPWNvbXBvbmVudCBhbmRcbiAgLy8gaGFzIGFuIGVuYWJsZWQsIHNlc3Npb24tb24gZmlsdGVyIGhlcmUuIFJlcG9ydC1sZXZlbCBncm91cHMgbGl2ZSBpbiB0aGVcbiAgLy8gdG9wIGJhciBpbnN0ZWFkLiBMaXN0cyB1c2UgdGhpcyBzdHJpcCBsaWtlIGNoYXJ0cyBkbzogYSB2YWx1ZSBzZXQgaGVyZSBpc1xuICAvLyB0aGUgZ3JvdXAncyB2YWx1ZSwgc28gaXQgcmVhY2hlcyBldmVyeSBjb21wb25lbnQgaW4gdGhlIGdyb3VwLlxuICBwdWJsaWMgZ2V0IGNvbXBvbmVudEZpbHRlckdyb3VwcygpOiBSZXBvcnRGaWx0ZXJHcm91cFtdIHtcbiAgICBpZiAoIXRoaXMuZ3JvdXBzKSB7XG4gICAgICByZXR1cm4gW107XG4gICAgfVxuXG4gICAgY29uc3QgZ3JvdXBJZHMgPSBuZXcgU2V0PG51bWJlcj4oKTtcbiAgICBmb3IgKGNvbnN0IGZpbHRlciBvZiB0aGlzLmNvbXBvbmVudC5maWx0ZXJzID8/IFtdKSB7XG4gICAgICBpZiAoIWZpbHRlci5lbmFibGVkIHx8IHRoaXMuX2ZpbHRlclN0YXRlLmlzRmlsdGVyRGlzYWJsZWQoZmlsdGVyLmlkKSkge1xuICAgICAgICBjb250aW51ZTtcbiAgICAgIH1cbiAgICAgIGNvbnN0IGdyb3VwID0gdGhpcy5ncm91cHMuZ2V0KGZpbHRlci5maWx0ZXJHcm91cElkKTtcbiAgICAgIGlmIChncm91cCAmJiAoZ3JvdXAubGV2ZWwgPT09ICdjb21wb25lbnQnIHx8IGdyb3VwLmxldmVsID09PSAnYm90aCcpKSB7XG4gICAgICAgIGdyb3VwSWRzLmFkZChncm91cC5pZCk7XG4gICAgICB9XG4gICAgfVxuXG4gICAgcmV0dXJuIFsuLi5ncm91cElkc10ubWFwKChpZCkgPT4gdGhpcy5ncm91cHMuZ2V0KGlkKSkuZmlsdGVyKEJvb2xlYW4pO1xuICB9XG5cbiAgcHVibGljIHNldHRpbmdzKCk6IHZvaWQge1xuICAgIHRoaXMub3BlblNldHRpbmdzLmVtaXQodGhpcy5jb21wb25lbnQpO1xuICB9XG5cbiAgLy8gV2hldGhlciB0aGUgbWVudSBvZmZlcnMgQ29sdW1uczogYSBwbGFpbiBsaXN0IHdpdGggbW9yZSB0aGFuIG9uZVxuICAvLyBjb25maWd1cmVkIGNvbHVtbi4gQSBjcm9zcy10YWIncyBjb2x1bW5zIGNvbWUgYW5kIGdvIHdpdGggdGhlIGRhdGEuXG4gIHB1YmxpYyBnZXQgaGlkZXNDb2x1bW5zKCk6IGJvb2xlYW4ge1xuICAgIHJldHVybiB0aGlzLmNvbXBvbmVudC50eXBlID09PSAnbGlzdCcgJiYgbGlzdEhpZGVhYmxlQ29sdW1ucyh0aGlzLmNvbXBvbmVudC5jb25maWcpLmxlbmd0aCA+IDE7XG4gIH1cblxuICAvLyBXaGljaCBvZiBhIHBsYWluIGxpc3QncyBjb2x1bW5zIHNob3cuIFRoZSBjaG9pY2UgaXMgdGhlIHZpZXdlcidzIChrZXB0IGluXG4gIC8vIHRoZSBVUkwsIG5ldmVyIHNhdmVkIHRvIHRoZSByZXBvcnQpLCBhbmQgdGhlIGxpc3QgaGlkZXMgdGhlIGNvbHVtbnMgaW5cbiAgLy8gcGxhY2UsIHdpdGggbm8gcmVmZXRjaC5cbiAgcHVibGljIGNob29zZUNvbHVtbnMoKTogdm9pZCB7XG4gICAgY29uc3QgY29sdW1ucyA9ICh0aGlzLmNvbXBvbmVudC5jb25maWc/LmNvbHVtbnMgPz8gW10pXG4gICAgICAubWFwKChjb2x1bW4pID0+ICh7IGNvbHVtbjogY29sdW1uLmNvbHVtbiwgbGFiZWw6IGNvbHVtbi5sYWJlbCB8fCBjb2x1bW4uY29sdW1uIH0pKTtcblxuICAgIHRoaXMuX2RpYWxvZy5vcGVuPExpc3RDb2x1bW5zQ29tcG9uZW50LCBMaXN0Q29sdW1uc0RpYWxvZ0RhdGEsIHN0cmluZ1tdPihMaXN0Q29sdW1uc0NvbXBvbmVudCwge1xuICAgICAgZGF0YTogeyBjb2x1bW5zLCBoaWRkZW46IFsuLi50aGlzLl9maWx0ZXJTdGF0ZS5oaWRkZW5Db2x1bW5zKHRoaXMuY29tcG9uZW50LmlkKV0gfSxcbiAgICAgIHdpZHRoOiAnNDAwcHgnLFxuICAgICAgbWF4V2lkdGg6ICc5NXZ3JyxcbiAgICAgIGF1dG9Gb2N1czogZmFsc2UsXG4gICAgfSlcbiAgICAgIC5hZnRlckNsb3NlZCgpXG4gICAgICAucGlwZSh0YWtlVW50aWxEZXN0cm95ZWQodGhpcy5fZGVzdHJveVJlZikpXG4gICAgICAuc3Vic2NyaWJlKChoaWRkZW4pID0+IHtcbiAgICAgICAgLy8gQ2FuY2VsIGNsb3NlcyB3aXRoIG5vdGhpbmcsIHdoaWNoIGNoYW5nZXMgbm90aGluZy5cbiAgICAgICAgaWYgKGhpZGRlbikge1xuICAgICAgICAgIHRoaXMuX2ZpbHRlclN0YXRlLnNldEhpZGRlbkNvbHVtbnModGhpcy5jb21wb25lbnQuaWQsIGhpZGRlbik7XG4gICAgICAgIH1cbiAgICAgIH0pO1xuICB9XG5cbiAgLy8gUHJlc2VudGF0aW9uIHNldHRpbmdzIHNhdmVkIGZyb20gdGhlIHNldHRpbmdzIGRpYWxvZy4gVGl0bGUgYW5kIHBhZGRpbmcgYXJlXG4gIC8vIG5vdCBwYXJ0IG9mIHRoZSBxdWVyeSwgc28gdGhlIGRhdGEgYWxyZWFkeSBmZXRjaGVkIHN0aWxsIHN0YW5kcyDigJQgdGhpcyBvbmx5XG4gIC8vIHJlcGFpbnRzLiBUaGUgaGVhZGVyIGNvbmZpZyBpcyByZWJ1aWx0IGJlY2F1c2UgYGZpbHRlcktleWAgY2hhbmdlcyB3aXRoIHRoZVxuICAvLyB0aXRsZSBhbmQgcmVjcmVhdGVzIHRoZSBmcy1maWx0ZXIgYmxvY2sgYXJvdW5kIGl0OyBzZXR0aW5nIHRoZSBjb25maWcgc2lnbmFsXG4gIC8vIGlzIGFsc28gd2hhdCByZXBhaW50cyB0aGUgbmV3IHBhZGRpbmcuIFRoZSBjaGFydCBmb2xsb3dzIGl0cyBib3ggb24gaXRzIG93blxuICAvLyAobmd4LWVjaGFydHMgb2JzZXJ2ZXMgdGhlIGhvc3QpLCBzbyBub3RoaW5nIGlzIHRvbGQgdG8gcmVzaXplLiBBIEtQSSdzIGNhcmRcbiAgLy8ga2V5cyBhcmUgZGlmZmVyZW50OiBzZXR0aW5ncy5rcGkgY2FycmllcyB0aGUga2V5cyB0aGUgc2VydmVyIHNhdmVkIChuZXZlclxuICAvLyB0aGUgb25lcyB0aGUgZGlhbG9nIHNlbnQpLCBhbmQgdGhlIHNlcnZlciBzZW5kcyB0aGUgdGFyZ2V0J3MgcHJvZ3Jlc3MgYW5kXG4gIC8vIHRoZSBzcGFya2xpbmUncyBwb2ludHMgd2l0aCB0aGUgZGF0YSwgc28gYSBjaGFuZ2UgdG8gdGhlbSByZWxvYWRzIGl0LlxuICBwdWJsaWMgYXBwbHlTZXR0aW5ncyhzZXR0aW5nczogQ29tcG9uZW50U2V0dGluZ3MpOiB2b2lkIHtcbiAgICBjb25zdCBjYXJkQ2hhbmdlZCA9ICEhc2V0dGluZ3Mua3BpXG4gICAgICAmJiAhc2FtZUtwaUNhcmRTZXR0aW5ncyhzZXR0aW5ncy5rcGksIGtwaUNhcmRTZXR0aW5ncyh0aGlzLmNvbXBvbmVudC5jb25maWcgYXMgS3BpQ29uZmlnKSk7XG5cbiAgICB0aGlzLmNvbXBvbmVudC50aXRsZSA9IHNldHRpbmdzLnRpdGxlO1xuICAgIHRoaXMuY29tcG9uZW50LmNvbmZpZyA9IHsgLi4udGhpcy5jb21wb25lbnQuY29uZmlnLCBwYWRkaW5nOiBzZXR0aW5ncy5wYWRkaW5nLCAuLi4oc2V0dGluZ3Mua3BpID8/IHt9KSB9O1xuXG4gICAgdGhpcy5fYnVpbGRGaWx0ZXJDb25maWcoKTtcblxuICAgIGlmIChjYXJkQ2hhbmdlZCkge1xuICAgICAgdGhpcy5fcmVmcmVzaCQubmV4dCgpO1xuICAgIH1cbiAgfVxuXG4gIC8vIFRoZSBDU1YgaXMgd2hhdCB0aGUgc2NyZWVuIHNob3dzLCBzbyBpdCBjYXJyaWVzIHRoZSBzYW1lIGludGVyYWN0aW9uIHN0YXRlXG4gIC8vIHRoZSBzY3JlZW4gZmV0Y2hlZCB3aXRoOiB0aGUgZ3JvdXAtYnkgZ3JhaW4gZm9yIGEgdGltZS1zZXJpZXMgY2hhcnQsIGFuZCB0aGVcbiAgLy8gdmlld2VyJ3MgaGVhZGVyIHNvcnQsIHNlYXJjaCBhbmQgaGlkZGVuIGNvbHVtbnMgZm9yIGEgbGlzdC4gQSBub3RlIHRoZVxuICAvLyBzZXJ2ZXIgcmV0dXJucyAodGhlIGZpbGUgd2FzIGN1dCkgaXMgc2hvd24gYmVmb3JlIHRoZSBkb3dubG9hZCBzdGFydHMsIHNvIGFcbiAgLy8gc2hvcnQgZmlsZSBuZXZlciBwYXNzZXMgZm9yIHRoZSB3aG9sZSByZXN1bHQuXG4gIHB1YmxpYyBleHBvcnRDc3YoKTogdm9pZCB7XG4gICAgY29uc3QgZmlsdGVycyA9IHRoaXMuX2ZpbHRlclN0YXRlLnJlc29sdmVGb3JDb21wb25lbnQodGhpcy5jb21wb25lbnQpO1xuICAgIGNvbnN0IHN0YXRlOiBDb21wb25lbnREYXRhU3RhdGUgPSB7fTtcblxuICAgIC8vIEEgZGVsaWJlcmF0ZSBtaXJyb3Igb2YgdGhlIHNlcnZlcidzIFJlcG9ydFF1ZXJ5UnVubmVyOjpfaXNUaW1lU2VyaWVzQ2hhcnQsXG4gICAgLy8gd2hpY2ggaXMgY2Fub25pY2FsIGFuZCBkcm9wcyB0aGUgZ3JhaW4gZm9yIGV2ZXJ5IG90aGVyIGNvbXBvbmVudC4gS2VwdCBzb1xuICAgIC8vIGEgcHJvZHVjdCBwaW5uZWQgdG8gYW4gb2xkZXIgZnJhbWV3b3JrIGRvZXMgbm90IHJlLWJ1Y2tldCBhIG5vbi10aW1lIGNoYXJ0LlxuICAgIGlmICh0aGlzLl9pc1RpbWVTZXJpZXMgJiYgdGhpcy5fZmlsdGVyU3RhdGUuZnJlcXVlbmN5KCkpIHtcbiAgICAgIHN0YXRlLmZyZXF1ZW5jeSA9IHRoaXMuX2ZpbHRlclN0YXRlLmZyZXF1ZW5jeSgpO1xuICAgIH1cblxuICAgIGNvbnN0IGlzTGlzdCA9IHRoaXMuY29tcG9uZW50LnR5cGUgPT09ICdsaXN0JztcbiAgICBjb25zdCBzb3J0ID0gaXNMaXN0ID8gdGhpcy5fZmlsdGVyU3RhdGUubGlzdFNvcnQodGhpcy5jb21wb25lbnQuaWQpIDogbnVsbDtcbiAgICBpZiAoc29ydCkge1xuICAgICAgc3RhdGUuc29ydCA9IHNvcnQ7XG4gICAgfVxuXG4gICAgLy8gQSBzZWFyY2hlZCBsaXN0IGV4cG9ydHMgb25seSB0aGUgcm93cyB0aGUgc2VhcmNoIGxlYXZlcywgYXMgb24gc2NyZWVuLlxuICAgIGNvbnN0IHNlYXJjaCA9IGlzTGlzdCA/IHRoaXMuX2ZpbHRlclN0YXRlLmxpc3RTZWFyY2godGhpcy5jb21wb25lbnQuaWQpIDogbnVsbDtcbiAgICBpZiAoc2VhcmNoKSB7XG4gICAgICBzdGF0ZS5zZWFyY2ggPSBzZWFyY2g7XG4gICAgfVxuXG4gICAgLy8gVGhlIGNvbHVtbnMgdGhlIHZpZXdlciBoaWQgc3RheSBvdXQgb2YgdGhlIGZpbGUsIGFzIG9mZiB0aGUgc2NyZWVuLlxuICAgIGNvbnN0IGhpZGRlbkNvbHVtbnMgPSBpc0xpc3QgPyB0aGlzLl9maWx0ZXJTdGF0ZS5oaWRkZW5Db2x1bW5zKHRoaXMuY29tcG9uZW50LmlkKSA6IFtdO1xuICAgIGlmIChoaWRkZW5Db2x1bW5zLmxlbmd0aCkge1xuICAgICAgc3RhdGUuaGlkZGVuQ29sdW1ucyA9IFsuLi5oaWRkZW5Db2x1bW5zXTtcbiAgICB9XG5cbiAgICB0aGlzLl9wcm9jZXNzLmRvd25sb2FkKFxuICAgICAgYEV4cG9ydGluZyAke3RoaXMuY29tcG9uZW50LnRpdGxlID8/ICdjb21wb25lbnQnfWAsXG4gICAgICB0aGlzLl9yZXBvcnREYXRhLmV4cG9ydENvbXBvbmVudCh0aGlzLnJlcG9ydElkLCB0aGlzLmNvbXBvbmVudC5pZCwgZmlsdGVycywgc3RhdGUpXG4gICAgICAgIC5waXBlKFxuICAgICAgICAgIHRhcCgoeyBub3RlcyB9KSA9PiBub3Rlcz8ubGVuZ3RoICYmIHRoaXMuX21lc3NhZ2Uud2FybmluZyhub3Rlcy5qb2luKCcgJykpKSxcbiAgICAgICAgICBtYXAoKHsgdXJsIH0pID0+IHVybCksXG4gICAgICAgICksXG4gICAgKTtcbiAgfVxuXG4gIC8vIEFueSBpbnRlcmFjdGlvbiBpbnNpZGUgYSBjb21wb25lbnQgbXVzdCBuZXZlciBzdGFydCBhIGNhbnZhcyBwYW4gKHRoZVxuICAvLyB6b29tLXBhbiBob3N0IGxpc3RlbnMgZm9yIG1vdXNlZG93bi90b3VjaHN0YXJ0IGF0IHRoZSBjb250YWluZXIgbGV2ZWwpLlxuICBwdWJsaWMgc3RvcENhbnZhc1BhbihldmVudDogRXZlbnQpOiB2b2lkIHtcbiAgICBldmVudC5zdG9wUHJvcGFnYXRpb24oKTtcbiAgfVxuXG4gIHB1YmxpYyBvbkNvbXBvbmVudFBvaW50ZXJEb3duKGV2ZW50OiBQb2ludGVyRXZlbnQpOiB2b2lkIHtcbiAgICBldmVudC5zdG9wUHJvcGFnYXRpb24oKTtcbiAgICBpZiAodGhpcy5lZGl0TW9kZSAmJiAhdGhpcy5zZWxlY3RlZCkge1xuICAgICAgdGhpcy5zZWxlY3RDb21wb25lbnQuZW1pdCh0aGlzLmNvbXBvbmVudC5pZCk7XG4gICAgfVxuICB9XG5cbiAgLy8gLS0tLS0gZWRpdC1tb2RlIGdlc3R1cmVzIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLVxuXG4gIHB1YmxpYyBvbkRyYWdTdGFydChldmVudDogUG9pbnRlckV2ZW50KTogdm9pZCB7XG4gICAgaWYgKCF0aGlzLmVkaXRNb2RlIHx8IHRoaXMudGV4dEVkaXRpbmcoKSkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIC8vIEEgc2Vjb25kIHByZXNzIG9uIGEgdGV4dCBibG9jayBvcGVucyBpdHMgZWRpdG9yIGluc3RlYWQgb2YgZHJhZ2dpbmcuXG4gICAgaWYgKHRoaXMuaXNUZXh0KSB7XG4gICAgICBjb25zdCBub3cgPSBEYXRlLm5vdygpO1xuICAgICAgY29uc3QgaXNEb3VibGVQcmVzcyA9IG5vdyAtIHRoaXMuX2xhc3RQcmVzcyA8IERPVUJMRV9QUkVTU19NUztcbiAgICAgIHRoaXMuX2xhc3RQcmVzcyA9IG5vdztcblxuICAgICAgaWYgKGlzRG91YmxlUHJlc3MpIHtcbiAgICAgICAgZXZlbnQucHJldmVudERlZmF1bHQoKTtcbiAgICAgICAgZXZlbnQuc3RvcFByb3BhZ2F0aW9uKCk7XG4gICAgICAgIHRoaXMuZWRpdFRleHQoKTtcblxuICAgICAgICByZXR1cm47XG4gICAgICB9XG4gICAgfVxuXG4gICAgdGhpcy5zZWxlY3RDb21wb25lbnQuZW1pdCh0aGlzLmNvbXBvbmVudC5pZCk7XG5cbiAgICB0aGlzLl90cmFjayhldmVudCwgKGRlbHRhWCwgZGVsdGFZKSA9PiB7XG4gICAgICBsZXQgeCA9IE1hdGgubWF4KDAsIHRoaXMuX29yaWdpbi54ICsgdGhpcy5faW5jaGVzKGRlbHRhWCkpO1xuICAgICAgbGV0IHkgPSBNYXRoLm1heCgwLCB0aGlzLl9vcmlnaW4ueSArIHRoaXMuX2luY2hlcyhkZWx0YVkpKTtcblxuICAgICAgaWYgKHRoaXMuc25hcHBlcikge1xuICAgICAgICAoeyB4LCB5IH0gPSB0aGlzLnNuYXBwZXIuc25hcE1vdmUodGhpcy5jb21wb25lbnQsIHgsIHkpKTtcbiAgICAgIH1cblxuICAgICAgdGhpcy5jb21wb25lbnQueCA9IHg7XG4gICAgICB0aGlzLmNvbXBvbmVudC55ID0geTtcbiAgICAgIHRoaXMuX2FwcGx5R2VvbWV0cnkoKTtcbiAgICB9LCAoKSA9PiB0aGlzLl9lbWl0R2VvbWV0cnkoKSk7XG4gIH1cblxuICBwdWJsaWMgb25SZXNpemVTdGFydChldmVudDogUG9pbnRlckV2ZW50LCBoYW5kbGU6IEhhbmRsZSk6IHZvaWQge1xuICAgIGlmICghdGhpcy5lZGl0TW9kZSkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIHRoaXMuc2VsZWN0Q29tcG9uZW50LmVtaXQodGhpcy5jb21wb25lbnQuaWQpO1xuXG4gICAgdGhpcy5fdHJhY2soZXZlbnQsIChkZWx0YVgsIGRlbHRhWSkgPT4ge1xuICAgICAgY29uc3QgZHggPSB0aGlzLl9pbmNoZXMoZGVsdGFYKTtcbiAgICAgIGNvbnN0IGR5ID0gdGhpcy5faW5jaGVzKGRlbHRhWSk7XG4gICAgICBsZXQgeyB4LCB5LCB3LCBoIH0gPSB0aGlzLl9vcmlnaW47XG5cbiAgICAgIGlmIChoYW5kbGUuaW5jbHVkZXMoJ2UnKSkge1xuICAgICAgICB3ID0gTWF0aC5tYXgoTUlOX1csIHRoaXMuX29yaWdpbi53ICsgZHgpO1xuICAgICAgfVxuICAgICAgaWYgKGhhbmRsZS5pbmNsdWRlcygncycpKSB7XG4gICAgICAgIGggPSBNYXRoLm1heChNSU5fSCwgdGhpcy5fb3JpZ2luLmggKyBkeSk7XG4gICAgICB9XG4gICAgICBpZiAoaGFuZGxlLmluY2x1ZGVzKCd3JykpIHtcbiAgICAgICAgY29uc3QgY2xhbXBlZCA9IE1hdGgubWluKGR4LCB0aGlzLl9vcmlnaW4udyAtIE1JTl9XKTtcbiAgICAgICAgeCA9IHRoaXMuX29yaWdpbi54ICsgY2xhbXBlZDtcbiAgICAgICAgdyA9IHRoaXMuX29yaWdpbi53IC0gY2xhbXBlZDtcbiAgICAgIH1cbiAgICAgIGlmIChoYW5kbGUuaW5jbHVkZXMoJ24nKSkge1xuICAgICAgICBjb25zdCBjbGFtcGVkID0gTWF0aC5taW4oZHksIHRoaXMuX29yaWdpbi5oIC0gTUlOX0gpO1xuICAgICAgICB5ID0gdGhpcy5fb3JpZ2luLnkgKyBjbGFtcGVkO1xuICAgICAgICBoID0gdGhpcy5fb3JpZ2luLmggLSBjbGFtcGVkO1xuICAgICAgfVxuXG4gICAgICBsZXQgZ2VvbWV0cnkgPSB7IHgsIHksIHcsIGggfTtcbiAgICAgIGlmICh0aGlzLnNuYXBwZXIpIHtcbiAgICAgICAgZ2VvbWV0cnkgPSB0aGlzLnNuYXBwZXIuc25hcFJlc2l6ZSh0aGlzLmNvbXBvbmVudCwgZ2VvbWV0cnksIGhhbmRsZSk7XG4gICAgICB9XG5cbiAgICAgIE9iamVjdC5hc3NpZ24odGhpcy5jb21wb25lbnQsIGdlb21ldHJ5KTtcbiAgICAgIHRoaXMuX2FwcGx5R2VvbWV0cnkoKTtcbiAgICAgIHRoaXMuY2hhcnRDb21wb25lbnQ/LnJlc2l6ZSgpO1xuICAgIH0sICgpID0+IHRoaXMuX2VtaXRHZW9tZXRyeSgpKTtcbiAgfVxuXG4gIC8vIChSZSlidWlsZCB0aGUgaGVhZGVyIGZzLWZpbHRlciBjb25maWc6IGhlYWRpbmcgdGVtcGxhdGUgcmVuZGVycyB0aGUgdGl0bGVcbiAgLy8gYW5kIGl0ZW1zIGFyZSB0aGlzIGNvbXBvbmVudCdzIGNvbXBvbmVudC1sZXZlbCBmaWx0ZXIgZ3JvdXBzLiBUaGUgYWN0aW9uc1xuICAvLyBtZW51IChTZXR0aW5ncyAvIEV4cG9ydCBDU1YpIGlzIE5PVCBoZXJlIOKAlCBpdCdzIGEgc3RhbmRhbG9uZSBrZWJhYiBmbG9hdGVkXG4gIC8vIHRvcC1yaWdodCBpbiB0aGUgdGVtcGxhdGUsIHNvIGl0cyBidXR0b24gaGVpZ2h0IG5vIGxvbmdlciBkcml2ZXMgdGhlIGhlYWRlclxuICAvLyByb3cncyBoZWlnaHQgKHdoaWNoIHdvdWxkIG90aGVyd2lzZSBpbmZsYXRlIHRoZSBoZWFkaW5nIGJ5IH40MHB4KS5cbiAgLy9cbiAgLy8gQSBsaXN0IGFsc28gZ2V0cyBhIHNlYXJjaCBib3ggb3ZlciBpdHMgdGV4dCBjb2x1bW5zLCB1bmxlc3MgaXRzIGhlYWRlclxuICAvLyBzaG93cyBhIGtleXdvcmQgZ3JvdXAgKFJlcG9ydEZpbHRlclN0YXRlU2VydmljZS5saXN0U2VhcmNoYWJsZSwgd2hpY2ggYWxzb1xuICAvLyBkcm9wcyBhIHNlYXJjaCBrZXB0IGZyb20gYmVmb3JlIHN1Y2ggYSBncm91cCBhcHBlYXJlZCkuXG4gIC8vXG4gIC8vIGByZXBvcnRlZGAgaXMgd2hhdCB0aGlzIGhlYWRlciBsYXN0IHJlcG9ydGVkIGZvciBlYWNoIG9mIGl0cyBncm91cHMsXG4gIC8vIHN0YXJ0aW5nIGZyb20gdGhlIHZhbHVlcyBpdCBpcyBidWlsdCB3aXRoLiBBIGNoYW5nZSBzZXRzIG9ubHkgdGhlIGdyb3Vwc1xuICAvLyB3aG9zZSBoZWFkZXIgdmFsdWUgbW92ZWQgKG1vdmVkR3JvdXBWYWx1ZXMpOiBmcy1maWx0ZXIgcmVwb3J0cyBldmVyeSBpdGVtXG4gIC8vIG9uIGFueSBjaGFuZ2UsIGFuZCBhIGdyb3VwIHNob3duIGluIHRoZSByZXBvcnQgYmFyIHRvbyBtYXkgaGF2ZSBjaGFuZ2VkXG4gIC8vIHRoZXJlIHNpbmNlLCB3aXRob3V0IHRoaXMgaGVhZGVyIGJlaW5nIHJlcGFpbnRlZC5cbiAgcHJpdmF0ZSBfYnVpbGRGaWx0ZXJDb25maWcoKTogdm9pZCB7XG4gICAgY29uc3QgZ3JvdXBzID0gdGhpcy5jb21wb25lbnRGaWx0ZXJHcm91cHM7XG4gICAgY29uc3QgbGlzdFNlYXJjaCA9IHRoaXMuX2ZpbHRlclN0YXRlLmxpc3RTZWFyY2hhYmxlKHRoaXMuY29tcG9uZW50KTtcbiAgICBjb25zdCByZXBvcnRlZCA9IG5ldyBNYXAoZ3JvdXBzLm1hcCgoZ3JvdXApID0+IFtncm91cC5pZCwgdGhpcy5fZmlsdGVyU3RhdGUudmFsdWUoZ3JvdXAuaWQpID8/IG51bGxdKSk7XG5cbiAgICB0aGlzLmZpbHRlckNvbmZpZy5zZXQoe1xuICAgICAgLy8gZnMtZmlsdGVyIG5ldmVyIHRvdWNoZXMgdGhlIFVSTCBvciBwZXJzaXN0cyBmaWx0ZXIgc3RhdGUuIFRoZSB2YWx1ZXNcbiAgICAgIC8vIGFyZSBvd25lZCBieSBSZXBvcnRGaWx0ZXJTdGF0ZVNlcnZpY2UsIHdoaWNoIGZlZWRzIHRoZSByZXBvcnQgdmlldydzXG4gICAgICAvLyBvbmUgVVJMIHdyaXRlciAocmVwb3J0LXVybC1zdGF0ZS50cykuXG4gICAgICBxdWVyeVBhcmFtOiBmYWxzZSxcbiAgICAgIHBlcnNpc3Q6IGZhbHNlLFxuICAgICAgaXRlbXM6IFtcbiAgICAgICAgLi4uZ3JvdXBzLm1hcCgoZ3JvdXApID0+XG4gICAgICAgICAgZmlsdGVySXRlbUZvckdyb3VwKGdyb3VwLCB0aGlzLl9yZXBvcnREYXRhLCB0aGlzLnJlcG9ydElkLCB0aGlzLl9maWx0ZXJTdGF0ZS52YWx1ZShncm91cC5pZCkpKSxcbiAgICAgICAgLi4uKGxpc3RTZWFyY2ggPyBbbGlzdFNlYXJjaEl0ZW0odGhpcy5fZmlsdGVyU3RhdGUubGlzdFNlYXJjaCh0aGlzLmNvbXBvbmVudC5pZCkpXSA6IFtdKSxcbiAgICAgIF0sXG4gICAgICAvLyBUeXBpbmcgaW4gdGhlIHNlYXJjaCBib3ggbXVzdCBub3QgcmVmZXRjaCB0aHJvdWdoIHRoZSBncm91cHMsIG5vciBzZXRcbiAgICAgIC8vIGEgc3RhbGUgZ3JvdXAgdmFsdWUgYmFjaywgYW5kIGEgZ3JvdXAgY2hhbmdlIG11c3Qgbm90IHJlZmV0Y2ggdGhyb3VnaFxuICAgICAgLy8gdGhlIHNlYXJjaC5cbiAgICAgIGNoYW5nZTogKHF1ZXJ5KSA9PiB7XG4gICAgICAgIGNvbnN0IHZhbHVlcyA9IGdyb3VwVmFsdWVzRnJvbVF1ZXJ5KHF1ZXJ5ID8/IHt9LCB0aGlzLmNvbXBvbmVudEZpbHRlckdyb3Vwcyk7XG5cbiAgICAgICAgZm9yIChjb25zdCB7IGdyb3VwSWQsIHZhbHVlIH0gb2YgbW92ZWRHcm91cFZhbHVlcyhyZXBvcnRlZCwgdmFsdWVzKSkge1xuICAgICAgICAgIHRoaXMuX2ZpbHRlclN0YXRlLnNldFZhbHVlKGdyb3VwSWQsIHZhbHVlKTtcbiAgICAgICAgfVxuXG4gICAgICAgIGlmIChsaXN0U2VhcmNoKSB7XG4gICAgICAgICAgdGhpcy5fZmlsdGVyU3RhdGUuc2V0TGlzdFNlYXJjaCh0aGlzLmNvbXBvbmVudC5pZCwgU3RyaW5nKHF1ZXJ5Py5bTElTVF9TRUFSQ0hfSVRFTV0gPz8gJycpKTtcbiAgICAgICAgfVxuICAgICAgfSxcbiAgICB9KTtcbiAgfVxuXG4gIHByaXZhdGUgX29yaWdpbiA9IHsgeDogMCwgeTogMCwgdzogMCwgaDogMCB9O1xuXG4gIC8vIFBvaW50ZXItY2FwdHVyZSBnZXN0dXJlIGxvb3A6IHJ1bnMgb3V0c2lkZSBBbmd1bGFyLCByZXBhaW50cyBpbXBlcmF0aXZlbHksXG4gIC8vIGFuZCBmaW5pc2hlcyBiYWNrIGluc2lkZSBBbmd1bGFyIChzZWxlY3Rpb24vcGVyc2lzdGVuY2UpLlxuICBwcml2YXRlIF90cmFjayhcbiAgICBldmVudDogUG9pbnRlckV2ZW50LFxuICAgIG9uTW92ZTogKGRlbHRhWDogbnVtYmVyLCBkZWx0YVk6IG51bWJlcikgPT4gdm9pZCxcbiAgICBvbkVuZDogKCkgPT4gdm9pZCxcbiAgKTogdm9pZCB7XG4gICAgZXZlbnQucHJldmVudERlZmF1bHQoKTtcbiAgICBldmVudC5zdG9wUHJvcGFnYXRpb24oKTtcblxuICAgIGNvbnN0IGhhbmRsZSA9IGV2ZW50LnRhcmdldCBhcyBIVE1MRWxlbWVudDtcbiAgICBoYW5kbGUuc2V0UG9pbnRlckNhcHR1cmUoZXZlbnQucG9pbnRlcklkKTtcblxuICAgIHRoaXMuX29yaWdpbiA9IHtcbiAgICAgIHg6IHRoaXMuY29tcG9uZW50LngsXG4gICAgICB5OiB0aGlzLmNvbXBvbmVudC55LFxuICAgICAgdzogdGhpcy5jb21wb25lbnQudyxcbiAgICAgIGg6IHRoaXMuY29tcG9uZW50LmgsXG4gICAgfTtcbiAgICBjb25zdCBzdGFydFggPSBldmVudC5jbGllbnRYO1xuICAgIGNvbnN0IHN0YXJ0WSA9IGV2ZW50LmNsaWVudFk7XG5cbiAgICB0aGlzLl96b25lLnJ1bk91dHNpZGVBbmd1bGFyKCgpID0+IHtcbiAgICAgIGNvbnN0IG1vdmUgPSAoZTogUG9pbnRlckV2ZW50KSA9PiBvbk1vdmUoZS5jbGllbnRYIC0gc3RhcnRYLCBlLmNsaWVudFkgLSBzdGFydFkpO1xuICAgICAgY29uc3QgZW5kID0gKCkgPT4ge1xuICAgICAgICBoYW5kbGUucmVsZWFzZVBvaW50ZXJDYXB0dXJlKGV2ZW50LnBvaW50ZXJJZCk7XG4gICAgICAgIGhhbmRsZS5yZW1vdmVFdmVudExpc3RlbmVyKCdwb2ludGVybW92ZScsIG1vdmUpO1xuICAgICAgICBoYW5kbGUucmVtb3ZlRXZlbnRMaXN0ZW5lcigncG9pbnRlcnVwJywgZW5kKTtcbiAgICAgICAgaGFuZGxlLnJlbW92ZUV2ZW50TGlzdGVuZXIoJ3BvaW50ZXJjYW5jZWwnLCBlbmQpO1xuXG4gICAgICAgIHRoaXMuX3pvbmUucnVuKCgpID0+IHtcbiAgICAgICAgICB0aGlzLnNuYXBwZXI/LmNsZWFyKCk7XG4gICAgICAgICAgb25FbmQoKTtcbiAgICAgICAgfSk7XG4gICAgICB9O1xuXG4gICAgICBoYW5kbGUuYWRkRXZlbnRMaXN0ZW5lcigncG9pbnRlcm1vdmUnLCBtb3ZlKTtcbiAgICAgIGhhbmRsZS5hZGRFdmVudExpc3RlbmVyKCdwb2ludGVydXAnLCBlbmQpO1xuICAgICAgaGFuZGxlLmFkZEV2ZW50TGlzdGVuZXIoJ3BvaW50ZXJjYW5jZWwnLCBlbmQpO1xuICAgIH0pO1xuICB9XG5cbiAgcHJpdmF0ZSBfZW1pdEdlb21ldHJ5KCk6IHZvaWQge1xuICAgIHRoaXMuY29tcG9uZW50LnggPSB0aGlzLl9yb3VuZCh0aGlzLmNvbXBvbmVudC54KTtcbiAgICB0aGlzLmNvbXBvbmVudC55ID0gdGhpcy5fcm91bmQodGhpcy5jb21wb25lbnQueSk7XG4gICAgdGhpcy5jb21wb25lbnQudyA9IHRoaXMuX3JvdW5kKE1hdGgubWF4KE1JTl9XLCB0aGlzLmNvbXBvbmVudC53KSk7XG4gICAgdGhpcy5jb21wb25lbnQuaCA9IHRoaXMuX3JvdW5kKE1hdGgubWF4KE1JTl9ILCB0aGlzLmNvbXBvbmVudC5oKSk7XG4gICAgdGhpcy5fYXBwbHlHZW9tZXRyeSgpO1xuICAgIHRoaXMuY2hhcnRDb21wb25lbnQ/LnJlc2l6ZSgpO1xuXG4gICAgdGhpcy5wb3NpdGlvbkNoYW5nZWQuZW1pdCh7XG4gICAgICBjb21wb25lbnRJZDogdGhpcy5jb21wb25lbnQuaWQsXG4gICAgICB4OiB0aGlzLmNvbXBvbmVudC54LFxuICAgICAgeTogdGhpcy5jb21wb25lbnQueSxcbiAgICAgIHc6IHRoaXMuY29tcG9uZW50LncsXG4gICAgICBoOiB0aGlzLmNvbXBvbmVudC5oLFxuICAgIH0pO1xuICB9XG5cbiAgLy8gQSBjaGFydCBvbiBhIHRpbWUgeC1heGlzIOKAlCB0aGUgb25seSBjb21wb25lbnQgdGhlIHJlcG9ydCdzIGdyb3VwLWJ5IGNvbnRyb2xcbiAgLy8gYXBwbGllcyB0by4gVGhlIHNlcnZlciBvd25zIHRoaXMgcnVsZSAoUmVwb3J0UXVlcnlSdW5uZXI6Ol9pc1RpbWVTZXJpZXNDaGFydCk7XG4gIC8vIHRoaXMgaXMgaXRzIGRvY3VtZW50ZWQgYnJvd3Nlci1zaWRlIG1pcnJvciwgZm9yIHByb2R1Y3RzIG9uIGFuIG9sZGVyIGZyYW1ld29yay5cbiAgcHJpdmF0ZSBnZXQgX2lzVGltZVNlcmllcygpOiBib29sZWFuIHtcbiAgICByZXR1cm4gdGhpcy5jb21wb25lbnQudHlwZSA9PT0gJ2NoYXJ0JyAmJiB0aGlzLmNvbXBvbmVudC5jb25maWc/LnhBeGlzPy5raW5kID09PSAndGltZSc7XG4gIH1cblxuICAvLyBBdXRvIGhlaWdodCAoYm94IGZpdHMgaXRzIGNvbnRlbnQpIHZzIGZpeGVkICh1c2UgYGhgIGV4YWN0bHkpLiBEZXJpdmVkIGZyb21cbiAgLy8gdHlwZSwgc2VydmVyLXNpZGU6IEtQSSB0aWxlcyBhcmUgYXV0bzsgY2hhcnRzIGFuZCBsaXN0cyBhcmUgZml4ZWQg4oCUIGNoYXJ0c1xuICAvLyBmaXQgdGhlIGJveCBhbmQgbmV2ZXIgb3ZlcmZsb3csIGxpc3RzIHNjcm9sbCBpbnNpZGUgaXQuXG4gIHByaXZhdGUgZ2V0IF9oZWlnaHRBdXRvKCk6IGJvb2xlYW4ge1xuICAgIHJldHVybiB0aGlzLmNvbXBvbmVudC5hdXRvSGVpZ2h0ICE9PSBmYWxzZTtcbiAgfVxuXG4gIC8vIERyaXZlcyB0aGUgYXV0by1vbmx5IENTUyBkZWZhdWx0IChlbXB0eS1zdGF0ZSBiYXNlbGluZSkgc28gaXQgbmV2ZXIgYXBwbGllc1xuICAvLyB0byBhIGZpeGVkLWhlaWdodCBjb21wb25lbnQuXG4gIEBIb3N0QmluZGluZygnY2xhc3MuaGVpZ2h0LWF1dG8nKVxuICBwdWJsaWMgZ2V0IGhlaWdodEF1dG8oKTogYm9vbGVhbiB7XG4gICAgcmV0dXJuIHRoaXMuX2hlaWdodEF1dG87XG4gIH1cblxuICAvLyBTY3JlZW4gcGl4ZWxzIOKGkiBpbmNoZXMgYXQgdGhlIGN1cnJlbnQgem9vbS5cbiAgcHJpdmF0ZSBfaW5jaGVzKHBpeGVsczogbnVtYmVyKTogbnVtYmVyIHtcbiAgICByZXR1cm4gcGl4ZWxzIC8gKHRoaXMuem9vbSAqIFBYX1BFUl9JTkNIKTtcbiAgfVxuXG4gIC8vIENsZWFuIHBlcnNpc3RlZCB2YWx1ZXM6IGh1bmRyZWR0aHMgb2YgYW4gaW5jaC5cbiAgcHJpdmF0ZSBfcm91bmQodmFsdWU6IG51bWJlcik6IG51bWJlciB7XG4gICAgcmV0dXJuIE1hdGgucm91bmQodmFsdWUgKiAxMDApIC8gMTAwO1xuICB9XG5cbiAgLy8gVGhlIGNhbnZhcyBwb3NpdGlvbnMgdGhlIGhvc3QgdmlhIFtzdHlsZV07IG1pZC1nZXN0dXJlIHdlIHNldCBpdCBkaXJlY3RseVxuICAvLyBzbyBPblB1c2ggbmV2ZXIgcmUtcmVuZGVycyBpbiB0aGUgbW92ZSBsb29wLlxuICBwcml2YXRlIF9hcHBseUdlb21ldHJ5KCk6IHZvaWQge1xuICAgIGNvbnN0IHN0eWxlID0gdGhpcy5faG9zdC5uYXRpdmVFbGVtZW50LnN0eWxlO1xuICAgIHN0eWxlLmxlZnQgPSBgJHt0aGlzLmNvbXBvbmVudC54ICogUFhfUEVSX0lOQ0h9cHhgO1xuICAgIHN0eWxlLnRvcCA9IGAke3RoaXMuY29tcG9uZW50LnkgKiBQWF9QRVJfSU5DSH1weGA7XG4gICAgc3R5bGUud2lkdGggPSBgJHt0aGlzLmNvbXBvbmVudC53ICogUFhfUEVSX0lOQ0h9cHhgO1xuXG4gICAgLy8gQXV0byAoa3BpKTogbm8gZml4ZWQgaGVpZ2h0IOKAlCB0aGUgYm94IHNpemVzIHRvIGl0cyBjb250ZW50LiBGaXhlZFxuICAgIC8vIChjaGFydC9saXN0KTogYGhgIGlzIHRoZSBleGFjdCBoZWlnaHQuIE1pcnJvcnMgdGhlIGNhbnZhcyBbc3R5bGVdIGJpbmRpbmdcbiAgICAvLyBzbyB0aGUgbWlkLWdlc3R1cmUgcGFpbnQgbWF0Y2hlcyB0aGUgcG9zdC1nZXN0dXJlIHJlLXJlbmRlci5cbiAgICBpZiAodGhpcy5faGVpZ2h0QXV0bykge1xuICAgICAgc3R5bGUuaGVpZ2h0ID0gJyc7XG4gICAgfSBlbHNlIHtcbiAgICAgIHN0eWxlLmhlaWdodCA9IGAke3RoaXMuY29tcG9uZW50LmggKiBQWF9QRVJfSU5DSH1weGA7XG4gICAgfVxuICB9XG5cbiAgLy8gLS0tLS0gZGF0YSAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG5cbiAgcHJpdmF0ZSBfbG9hZCgpOiB2b2lkIHtcbiAgICB0aGlzLmxvYWRpbmcuc2V0KHRydWUpO1xuICAgIHRoaXMuZXJyb3Iuc2V0KG51bGwpO1xuXG4gICAgY29uc3QgZmlsdGVycyA9IHRoaXMuX2ZpbHRlclN0YXRlLnJlc29sdmVGb3JDb21wb25lbnQodGhpcy5jb21wb25lbnQpO1xuICAgIC8vIFRpbWUtc2VyaWVzIGNoYXJ0cyBjYXJyeSB0aGUgZ3JvdXAtYnkgZ3JhaW4gKGlmIHRoZSB2aWV3ZXIgcGlja2VkIG9uZSkgc29cbiAgICAvLyB0aGUgYmFja2VuZCByZS1idWNrZXRzOyBldmVyeXRoaW5nIGVsc2Ugc2VuZHMgbm8gaW50ZXJhY3Rpb24gc3RhdGUgaGVyZS5cbiAgICBjb25zdCBzdGF0ZSA9IHRoaXMuX2lzVGltZVNlcmllcyAmJiB0aGlzLl9maWx0ZXJTdGF0ZS5mcmVxdWVuY3koKVxuICAgICAgPyB7IGZyZXF1ZW5jeTogdGhpcy5fZmlsdGVyU3RhdGUuZnJlcXVlbmN5KCkgfVxuICAgICAgOiB7fTtcblxuICAgIHRoaXMuX3JlcG9ydERhdGEuY29tcG9uZW50RGF0YSh0aGlzLnJlcG9ydElkLCB0aGlzLmNvbXBvbmVudC5pZCwgZmlsdGVycywgc3RhdGUpXG4gICAgICAucGlwZSh0YWtlVW50aWxEZXN0cm95ZWQodGhpcy5fZGVzdHJveVJlZikpXG4gICAgICAuc3Vic2NyaWJlKHtcbiAgICAgICAgbmV4dDogKGRhdGE6IENvbXBvbmVudERhdGEpID0+IHtcbiAgICAgICAgICB0aGlzLmRhdGEuc2V0KGRhdGEpO1xuICAgICAgICAgIHRoaXMubG9hZGluZy5zZXQoZmFsc2UpO1xuICAgICAgICB9LFxuICAgICAgICBlcnJvcjogKGVycm9yKSA9PiB7XG4gICAgICAgICAgdGhpcy5sb2FkaW5nLnNldChmYWxzZSk7XG4gICAgICAgICAgdGhpcy5lcnJvci5zZXQoZXJyb3I/LmVycm9yPy5tZXNzYWdlID8/IGVycm9yPy5tZXNzYWdlID8/ICdGYWlsZWQgdG8gbG9hZCBkYXRhJyk7XG4gICAgICAgIH0sXG4gICAgICB9KTtcbiAgfVxufVxuIiwiPGRpdlxuICAgIGNsYXNzPVwiY29tcG9uZW50LWJveFwiXG4gICAgW2NsYXNzLmVkaXRpbmddPVwiZWRpdE1vZGVcIlxuICAgIFtjbGFzcy50ZXh0XT1cImlzVGV4dFwiXG4gICAgW2NsYXNzLnNlbGVjdGVkXT1cInNlbGVjdGVkXCJcbiAgICBbc3R5bGUucGFkZGluZ109XCJib2R5UGFkZGluZ1wiXG4gICAgKHBvaW50ZXJkb3duKT1cIm9uQ29tcG9uZW50UG9pbnRlckRvd24oJGV2ZW50KVwiXG4gICAgKG1vdXNlZG93bik9XCJzdG9wQ2FudmFzUGFuKCRldmVudClcIlxuICAgICh0b3VjaHN0YXJ0KT1cInN0b3BDYW52YXNQYW4oJGV2ZW50KVwiPlxuICA8IS0tIFRoZSBoZWFkZXIgaXMgYW4gZnMtZmlsdGVyOiBoZWFkaW5nIHRlbXBsYXRlID0gdGl0bGUgKGFuZCB0aGUgZWRpdC1tb2RlXG4gICAgICAgZHJhZyBoYW5kbGUpLCBhY3Rpb25zID0gdGhlIG1lbnUsIGl0ZW1zID0gY29tcG9uZW50LWxldmVsIGZpbHRlciBncm91cHMsXG4gICAgICAgdGhlIHNhbWUgc3RyaXAgZm9yIGV2ZXJ5IHR5cGUgKGxpc3RzIGluY2x1ZGVkKS4gZnMtZmlsdGVyIHJlYWRzIGl0c1xuICAgICAgIGNvbmZpZyBvbmNlLCBzbyB0aGUgYmxvY2sgaXMga2V5ZWQgb24gdGhlIGNvbXBvbmVudC1maWx0ZXIgc2V0IHRvIGJlXG4gICAgICAgcmVjcmVhdGVkIHdoZW4gaXQgY2hhbmdlcy4gLS0+XG4gIDwhLS0gQSB0ZXh0IGJsb2NrIGhhcyBubyB0aXRsZSBiYXIg4oCUIGl0IElTIGl0cyB3b3JkcywgbGlrZSBhIHRleHQgYm94IG9uIGFcbiAgICAgICBzbGlkZSDigJQgc28gaXQgZ2V0cyBuZWl0aGVyIHRoZSBoZWFkZXIgbm9yIHRoZSBkYXRhIGFjdGlvbnMuIC0tPlxuICBAZm9yIChrZXkgb2YgaXNUZXh0ID8gW10gOiBbZmlsdGVyS2V5XTsgdHJhY2sga2V5KSB7XG4gICAgPGZzLWZpbHRlclxuICAgICAgICBjbGFzcz1cImNvbXBvbmVudC1maWx0ZXJcIlxuICAgICAgICBbY29uZmlnXT1cImZpbHRlckNvbmZpZygpXCI+XG4gICAgICA8bmctdGVtcGxhdGUgZnNGaWx0ZXJIZWFkaW5nPlxuICAgICAgICA8ZGl2XG4gICAgICAgICAgICBjbGFzcz1cImNvbXBvbmVudC10aXRsZVwiXG4gICAgICAgICAgICAocG9pbnRlcmRvd24pPVwib25EcmFnU3RhcnQoJGV2ZW50KVwiPlxuICAgICAgICAgIHt7IGNvbXBvbmVudC50aXRsZSB9fVxuICAgICAgICAgIEBpZiAodHJ1bmNhdGVkKSB7XG4gICAgICAgICAgICA8bWF0LWljb25cbiAgICAgICAgICAgICAgICBjbGFzcz1cInRydW5jYXRlZC1pY29uXCJcbiAgICAgICAgICAgICAgICBtYXRUb29sdGlwPVwiU2hvd2luZyBhIHRydW5jYXRlZCByZXN1bHQg4oCUIHJlZmluZSB0aGUgZmlsdGVycyB0byBzZWUgZXZlcnl0aGluZy5cIj5cbiAgICAgICAgICAgICAgd2FybmluZ19hbWJlclxuICAgICAgICAgICAgPC9tYXQtaWNvbj5cbiAgICAgICAgICB9XG4gICAgICAgIDwvZGl2PlxuICAgICAgPC9uZy10ZW1wbGF0ZT5cbiAgICA8L2ZzLWZpbHRlcj5cbiAgfVxuICA8IS0tIFRoZSBhY3Rpb25zIG1lbnUgaXMgZmxvYXRlZCB0b3AtcmlnaHQgKGFic29sdXRlKSByYXRoZXIgdGhhbiBsaXZpbmcgaW5cbiAgICAgICBmcy1maWx0ZXIncyBhY3Rpb25zIHNsb3QsIHNvIGl0cyB+NDBweCBidXR0b24gaGVpZ2h0IG5vIGxvbmdlciBkcml2ZXMgdGhlXG4gICAgICAgaGVhZGVyIHJvdydzIGhlaWdodC4gSXQgb3ZlcmxheXMgdGhlIGJveCBjb3JuZXI7IHRoZSBoZWFkaW5nIHJlc2VydmVzXG4gICAgICAgcmlnaHQgcGFkZGluZyBzbyBhIGxvbmcgdGl0bGUgZWxsaXBzaXNlcyBiZWZvcmUgaXQuIC0tPlxuICBAaWYgKCFpc1RleHQgfHwgKGVkaXRNb2RlICYmICF0ZXh0RWRpdGluZygpKSkge1xuICAgIDxidXR0b25cbiAgICAgICAgbWF0LWljb24tYnV0dG9uXG4gICAgICAgIGNsYXNzPVwiY29tcG9uZW50LW1lbnVcIlxuICAgICAgICBbZnNNZW51VHJpZ2dlckZvcl09XCJtZW51XCJcbiAgICAgICAgKHBvaW50ZXJkb3duKT1cIiRldmVudC5zdG9wUHJvcGFnYXRpb24oKVwiXG4gICAgICAgIChtb3VzZWRvd24pPVwic3RvcENhbnZhc1BhbigkZXZlbnQpXCI+XG4gICAgICA8bWF0LWljb24+bW9yZV92ZXJ0PC9tYXQtaWNvbj5cbiAgICA8L2J1dHRvbj5cbiAgICA8IS0tIEJlc2lkZSBpdHMgdHJpZ2dlciwgaW5zaWRlIHRoZSBzYW1lIGJsb2NrOiBhbiBmcy1tZW51IHRoYXQgZmluZHMgbm9cbiAgICAgICAgIHRyaWdnZXIgb2YgaXRzIG93biBkcmF3cyBvbmUuIC0tPlxuICAgIDxmcy1tZW51ICNtZW51PlxuICAgICAgPG5nLXRlbXBsYXRlXG4gICAgICAgICAgZnMtbWVudS1pdGVtXG4gICAgICAgICAgW2hpZGRlbl09XCIhaXNUZXh0XCJcbiAgICAgICAgICAoY2xpY2spPVwiZWRpdFRleHQoKVwiPlxuICAgICAgICA8bWF0LWljb24+ZWRpdDwvbWF0LWljb24+XG4gICAgICAgIDxzcGFuPkVkaXQgdGV4dDwvc3Bhbj5cbiAgICAgIDwvbmctdGVtcGxhdGU+XG4gICAgICA8bmctdGVtcGxhdGVcbiAgICAgICAgICBmcy1tZW51LWl0ZW1cbiAgICAgICAgICBbaGlkZGVuXT1cIiFpc1RleHRcIlxuICAgICAgICAgIChjbGljayk9XCJkZWxldGVUZXh0KClcIj5cbiAgICAgICAgPG1hdC1pY29uPmRlbGV0ZTwvbWF0LWljb24+XG4gICAgICAgIDxzcGFuPkRlbGV0ZTwvc3Bhbj5cbiAgICAgIDwvbmctdGVtcGxhdGU+XG4gICAgICA8bmctdGVtcGxhdGVcbiAgICAgICAgICBmcy1tZW51LWl0ZW1cbiAgICAgICAgICBbaGlkZGVuXT1cImlzVGV4dFwiXG4gICAgICAgICAgKGNsaWNrKT1cInNldHRpbmdzKClcIj5cbiAgICAgICAgPG1hdC1pY29uPnR1bmU8L21hdC1pY29uPlxuICAgICAgICA8c3Bhbj5TZXR0aW5nczwvc3Bhbj5cbiAgICAgIDwvbmctdGVtcGxhdGU+XG4gICAgICA8bmctdGVtcGxhdGVcbiAgICAgICAgICBmcy1tZW51LWl0ZW1cbiAgICAgICAgICBbaGlkZGVuXT1cImlzVGV4dFwiXG4gICAgICAgICAgKGNsaWNrKT1cImV4cG9ydENzdigpXCI+XG4gICAgICAgIDxtYXQtaWNvbj5kb3dubG9hZDwvbWF0LWljb24+XG4gICAgICAgIDxzcGFuPkV4cG9ydCBDU1Y8L3NwYW4+XG4gICAgICA8L25nLXRlbXBsYXRlPlxuICAgICAgPG5nLXRlbXBsYXRlXG4gICAgICAgICAgZnMtbWVudS1pdGVtXG4gICAgICAgICAgW2hpZGRlbl09XCIhaGlkZXNDb2x1bW5zXCJcbiAgICAgICAgICAoY2xpY2spPVwiY2hvb3NlQ29sdW1ucygpXCI+XG4gICAgICAgIDxtYXQtaWNvbj52aWV3X2NvbHVtbjwvbWF0LWljb24+XG4gICAgICAgIDxzcGFuPkNvbHVtbnM8L3NwYW4+XG4gICAgICA8L25nLXRlbXBsYXRlPlxuICAgIDwvZnMtbWVudT5cbiAgfVxuICA8ZGl2IGNsYXNzPVwiY29tcG9uZW50LWJvZHlcIj5cbiAgICBAaWYgKGlzVGV4dCkge1xuICAgICAgPGFwcC1yZXBvcnQtY29tcG9uZW50LXRleHRcbiAgICAgICAgW2h0bWxdPVwiY29tcG9uZW50LmNvbmZpZz8uaHRtbCA/PyAnJ1wiXG4gICAgICAgIFt0b2tlbnNdPVwidG9rZW5zKClcIlxuICAgICAgICBbZWRpdGluZ109XCJ0ZXh0RWRpdGluZygpXCJcbiAgICAgICAgKHNhdmVkKT1cIm9uVGV4dFNhdmVkKCRldmVudClcIlxuICAgICAgICAoZWRpdEVuZGVkKT1cInRleHRFZGl0aW5nLnNldChmYWxzZSlcIj5cbiAgICAgIDwvYXBwLXJlcG9ydC1jb21wb25lbnQtdGV4dD5cbiAgICB9IEBlbHNlIGlmIChjb21wb25lbnQudHlwZSA9PT0gJ2xpc3QnKSB7XG4gICAgICA8YXBwLXJlcG9ydC1jb21wb25lbnQtbGlzdFxuICAgICAgICBbcmVwb3J0SWRdPVwicmVwb3J0SWRcIlxuICAgICAgICBbY29tcG9uZW50XT1cImNvbXBvbmVudFwiPlxuICAgICAgPC9hcHAtcmVwb3J0LWNvbXBvbmVudC1saXN0PlxuICAgIH0gQGVsc2UgaWYgKGxvYWRpbmcoKSkge1xuICAgICAgPGRpdiBjbGFzcz1cImNvbXBvbmVudC1zdGF0ZVwiPlxuICAgICAgICA8ZGl2IGNsYXNzPVwibG9hZGluZy1zaGltbWVyXCI+PC9kaXY+XG4gICAgICA8L2Rpdj5cbiAgICB9IEBlbHNlIGlmIChlcnJvcigpKSB7XG4gICAgICA8ZGl2IGNsYXNzPVwiY29tcG9uZW50LXN0YXRlIGVycm9yXCI+XG4gICAgICAgIHt7IGVycm9yKCkgfX1cbiAgICAgIDwvZGl2PlxuICAgIH0gQGVsc2UgaWYgKCFkYXRhKCk/LnJvd3M/Lmxlbmd0aCkge1xuICAgICAgPGRpdiBjbGFzcz1cImNvbXBvbmVudC1zdGF0ZVwiPlxuICAgICAgICBObyBkYXRhXG4gICAgICA8L2Rpdj5cbiAgICB9IEBlbHNlIGlmIChjb21wb25lbnQudHlwZSA9PT0gJ2twaScpIHtcbiAgICAgIDxhcHAtcmVwb3J0LWNvbXBvbmVudC1rcGlcbiAgICAgICAgW2NvbXBvbmVudF09XCJjb21wb25lbnRcIlxuICAgICAgICBbZGF0YV09XCJkYXRhKClcIj5cbiAgICAgIDwvYXBwLXJlcG9ydC1jb21wb25lbnQta3BpPlxuICAgIH0gQGVsc2Uge1xuICAgICAgPGFwcC1yZXBvcnQtY29tcG9uZW50LWNoYXJ0XG4gICAgICAgIFtjb21wb25lbnRdPVwiY29tcG9uZW50XCJcbiAgICAgICAgW2RhdGFdPVwiZGF0YSgpXCI+XG4gICAgICA8L2FwcC1yZXBvcnQtY29tcG9uZW50LWNoYXJ0PlxuICAgIH1cbiAgICA8IS0tIEluIGVkaXQgbW9kZSBhIHRyYW5zcGFyZW50IHZlaWwgb3ZlciB0aGUgYm9keSBtYWtlcyB0aGUgV0hPTEVcbiAgICAgICAgIGNvbXBvbmVudCBkcmFnZ2FibGUgKGluZHVzdHJ5IHN0YW5kYXJkOiB5b3UgZ3JhYiB0aGUgb2JqZWN0LCBub3QganVzdFxuICAgICAgICAgaXRzIHRpdGxlIGJhcikgYW5kIGtlZXBzIGlubmVyIHdpZGdldHMgZnJvbSBzd2FsbG93aW5nIHRoZSBnZXN0dXJlLiAtLT5cbiAgICBAaWYgKGVkaXRNb2RlICYmICF0ZXh0RWRpdGluZygpKSB7XG4gICAgICA8ZGl2XG4gICAgICAgIGNsYXNzPVwiZHJhZy12ZWlsXCJcbiAgICAgICAgKHBvaW50ZXJkb3duKT1cIm9uRHJhZ1N0YXJ0KCRldmVudClcIj5cbiAgICAgIDwvZGl2PlxuICAgIH1cbiAgPC9kaXY+XG48L2Rpdj5cbjwhLS0gSGFuZGxlcyBsaXZlIE9VVFNJREUgdGhlIGNsaXBwZWQgYm94IHNvIHRoZXkgc3RyYWRkbGUgaXRzIGVkZ2VzLiAtLT5cbkBpZiAoZWRpdE1vZGUgJiYgc2VsZWN0ZWQpIHtcbiAgQGZvciAoaGFuZGxlIG9mIHJlc2l6ZUhhbmRsZXM7IHRyYWNrIGhhbmRsZSkge1xuICAgIDxkaXZcbiAgICAgIGNsYXNzPVwiaGFuZGxlIGhhbmRsZS17eyBoYW5kbGUgfX1cIlxuICAgICAgKG1vdXNlZG93bik9XCJzdG9wQ2FudmFzUGFuKCRldmVudClcIlxuICAgICAgKHBvaW50ZXJkb3duKT1cIm9uUmVzaXplU3RhcnQoJGV2ZW50LCBoYW5kbGUpXCI+XG4gICAgPC9kaXY+XG4gIH1cbn0iXX0=
|