@skyux/text-editor 11.30.1 → 12.0.0-alpha.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/documentation.json +295 -292
- package/fesm2022/skyux-text-editor.mjs +44 -44
- package/fesm2022/skyux-text-editor.mjs.map +1 -1
- package/package.json +18 -20
- package/esm2022/index.mjs +0 -10
- package/esm2022/lib/modules/rich-text-display/rich-text-display.component.mjs +0 -43
- package/esm2022/lib/modules/rich-text-display/rich-text-display.module.mjs +0 -16
- package/esm2022/lib/modules/shared/sky-text-editor-resources.module.mjs +0 -97
- package/esm2022/lib/modules/text-editor/defaults/font-list-defaults.mjs +0 -42
- package/esm2022/lib/modules/text-editor/defaults/font-size-list-defaults.mjs +0 -7
- package/esm2022/lib/modules/text-editor/defaults/link-window-options-defaults.mjs +0 -2
- package/esm2022/lib/modules/text-editor/defaults/menu-defaults.mjs +0 -5
- package/esm2022/lib/modules/text-editor/defaults/style-state-defaults.mjs +0 -15
- package/esm2022/lib/modules/text-editor/defaults/toolbar-action-defaults.mjs +0 -12
- package/esm2022/lib/modules/text-editor/menubar/text-editor-menubar.component.mjs +0 -195
- package/esm2022/lib/modules/text-editor/services/text-editor-adapter.service.mjs +0 -482
- package/esm2022/lib/modules/text-editor/services/text-editor-selection.service.mjs +0 -74
- package/esm2022/lib/modules/text-editor/services/text-editor.service.mjs +0 -65
- package/esm2022/lib/modules/text-editor/services/text-sanitization.service.mjs +0 -38
- package/esm2022/lib/modules/text-editor/text-editor.component.mjs +0 -514
- package/esm2022/lib/modules/text-editor/text-editor.module.mjs +0 -17
- package/esm2022/lib/modules/text-editor/toolbar/text-editor-toolbar.component.mjs +0 -223
- package/esm2022/lib/modules/text-editor/types/editor-command.mjs +0 -2
- package/esm2022/lib/modules/text-editor/types/editor-setting.mjs +0 -2
- package/esm2022/lib/modules/text-editor/types/font-state.mjs +0 -2
- package/esm2022/lib/modules/text-editor/types/link-window-options-type.mjs +0 -2
- package/esm2022/lib/modules/text-editor/types/menu-type.mjs +0 -2
- package/esm2022/lib/modules/text-editor/types/style-state.mjs +0 -2
- package/esm2022/lib/modules/text-editor/types/text-editor-merge-field.mjs +0 -2
- package/esm2022/lib/modules/text-editor/types/toolbar-action-type.mjs +0 -2
- package/esm2022/lib/modules/text-editor/url-modal/text-editor-url-modal-context.mjs +0 -6
- package/esm2022/lib/modules/text-editor/url-modal/text-editor-url-modal-result.mjs +0 -2
- package/esm2022/lib/modules/text-editor/url-modal/text-editor-url-modal.component.mjs +0 -147
- package/esm2022/lib/modules/text-editor/url-modal/text-editor-url-target.mjs +0 -9
- package/esm2022/skyux-text-editor.mjs +0 -5
|
@@ -1,195 +0,0 @@
|
|
|
1
|
-
import { CommonModule } from '@angular/common';
|
|
2
|
-
import { ChangeDetectionStrategy, Component, Input, booleanAttribute, inject, } from '@angular/core';
|
|
3
|
-
import { SkyLibResourcesService } from '@skyux/i18n';
|
|
4
|
-
import { SkyToolbarModule } from '@skyux/layout';
|
|
5
|
-
import { SkyDropdownMessageType, SkyDropdownModule, } from '@skyux/popovers';
|
|
6
|
-
import { SkyThemeModule } from '@skyux/theme';
|
|
7
|
-
import he from 'he';
|
|
8
|
-
import { Subject } from 'rxjs';
|
|
9
|
-
import { take, takeUntil } from 'rxjs/operators';
|
|
10
|
-
import { SkyTextEditorResourcesModule } from '../../shared/sky-text-editor-resources.module';
|
|
11
|
-
import { SkyTextEditorAdapterService } from '../services/text-editor-adapter.service';
|
|
12
|
-
import * as i0 from "@angular/core";
|
|
13
|
-
import * as i1 from "@angular/common";
|
|
14
|
-
import * as i2 from "@skyux/popovers";
|
|
15
|
-
import * as i3 from "@skyux/i18n";
|
|
16
|
-
import * as i4 from "@skyux/theme";
|
|
17
|
-
import * as i5 from "@skyux/layout";
|
|
18
|
-
const FORMAT_MENU_ACTION = 'skyux_text_editor_format_menu_action_';
|
|
19
|
-
const EDIT_MENU_ACTION = 'skyux_text_editor_edit_menu_action_';
|
|
20
|
-
/**
|
|
21
|
-
* @internal
|
|
22
|
-
*/
|
|
23
|
-
export class SkyTextEditorMenubarComponent {
|
|
24
|
-
constructor() {
|
|
25
|
-
this.editorFocusStream = new Subject();
|
|
26
|
-
this.menus = [];
|
|
27
|
-
this.mergeFields = [];
|
|
28
|
-
this.disabled = false;
|
|
29
|
-
this.editDropdownStream = new Subject();
|
|
30
|
-
this.formatDropdownStream = new Subject();
|
|
31
|
-
this.mergeFieldDropdownStream = new Subject();
|
|
32
|
-
this.#ngUnsubscribe = new Subject();
|
|
33
|
-
this.#adapterService = inject(SkyTextEditorAdapterService);
|
|
34
|
-
this.#resources = inject(SkyLibResourcesService);
|
|
35
|
-
}
|
|
36
|
-
#ngUnsubscribe;
|
|
37
|
-
#adapterService;
|
|
38
|
-
#resources;
|
|
39
|
-
ngOnInit() {
|
|
40
|
-
this.editorFocusStream
|
|
41
|
-
.pipe(takeUntil(this.#ngUnsubscribe))
|
|
42
|
-
.subscribe(() => {
|
|
43
|
-
this.#closeDropdowns();
|
|
44
|
-
});
|
|
45
|
-
this.#resources
|
|
46
|
-
.getStrings({
|
|
47
|
-
bold: FORMAT_MENU_ACTION + 'bold_label',
|
|
48
|
-
boldShort: FORMAT_MENU_ACTION + 'bold_key_shortcut',
|
|
49
|
-
italic: FORMAT_MENU_ACTION + 'italic_label',
|
|
50
|
-
italicShort: FORMAT_MENU_ACTION + 'italic_key_shortcut',
|
|
51
|
-
underline: FORMAT_MENU_ACTION + 'underline_label',
|
|
52
|
-
underlineShort: FORMAT_MENU_ACTION + 'underline_key_shortcut',
|
|
53
|
-
strikethrough: FORMAT_MENU_ACTION + 'strikethrough_label',
|
|
54
|
-
clearFormatting: FORMAT_MENU_ACTION + 'clear_formatting_label',
|
|
55
|
-
undo: EDIT_MENU_ACTION + 'undo_label',
|
|
56
|
-
undoShort: EDIT_MENU_ACTION + 'undo_key_shortcut',
|
|
57
|
-
redo: EDIT_MENU_ACTION + 'redo_label',
|
|
58
|
-
redoShort: EDIT_MENU_ACTION + 'redo_key_shortcut',
|
|
59
|
-
cut: EDIT_MENU_ACTION + 'cut_label',
|
|
60
|
-
cutShort: EDIT_MENU_ACTION + 'cut_key_shortcut',
|
|
61
|
-
copy: EDIT_MENU_ACTION + 'copy_label',
|
|
62
|
-
copyShort: EDIT_MENU_ACTION + 'copy_key_shortcut',
|
|
63
|
-
paste: EDIT_MENU_ACTION + 'paste_label',
|
|
64
|
-
pasteShort: EDIT_MENU_ACTION + 'paste_key_shortcut',
|
|
65
|
-
selectAll: EDIT_MENU_ACTION + 'select_all_label',
|
|
66
|
-
selectAllShort: EDIT_MENU_ACTION + 'select_all_key_shortcut',
|
|
67
|
-
})
|
|
68
|
-
.pipe(take(1), takeUntil(this.#ngUnsubscribe))
|
|
69
|
-
.subscribe((resources) => {
|
|
70
|
-
this.formatItems = [
|
|
71
|
-
{
|
|
72
|
-
function: () => this.execCommand('bold'),
|
|
73
|
-
label: resources.bold,
|
|
74
|
-
keyShortcut: resources.boldShort,
|
|
75
|
-
},
|
|
76
|
-
{
|
|
77
|
-
function: () => this.execCommand('italic'),
|
|
78
|
-
label: resources.italic,
|
|
79
|
-
keyShortcut: resources.italicShort,
|
|
80
|
-
},
|
|
81
|
-
{
|
|
82
|
-
function: () => this.execCommand('underline'),
|
|
83
|
-
label: resources.underline,
|
|
84
|
-
keyShortcut: resources.underlineShort,
|
|
85
|
-
},
|
|
86
|
-
{
|
|
87
|
-
function: () => this.execCommand('strikethrough'),
|
|
88
|
-
label: resources.strikethrough,
|
|
89
|
-
},
|
|
90
|
-
{
|
|
91
|
-
isDivider: true,
|
|
92
|
-
},
|
|
93
|
-
{
|
|
94
|
-
function: () => this.#clearFormat(),
|
|
95
|
-
label: resources.clearFormatting,
|
|
96
|
-
},
|
|
97
|
-
];
|
|
98
|
-
this.editItems = [
|
|
99
|
-
{
|
|
100
|
-
function: () => this.execCommand('undo'),
|
|
101
|
-
label: resources.undo,
|
|
102
|
-
keyShortcut: resources.undoShort,
|
|
103
|
-
},
|
|
104
|
-
{
|
|
105
|
-
function: () => this.execCommand('redo'),
|
|
106
|
-
label: resources.redo,
|
|
107
|
-
keyShortcut: resources.redoShort,
|
|
108
|
-
},
|
|
109
|
-
{
|
|
110
|
-
isDivider: true,
|
|
111
|
-
},
|
|
112
|
-
{
|
|
113
|
-
function: () => this.execCommand('cut'),
|
|
114
|
-
label: resources.cut,
|
|
115
|
-
keyShortcut: resources.cutShort,
|
|
116
|
-
},
|
|
117
|
-
{
|
|
118
|
-
function: () => this.execCommand('copy'),
|
|
119
|
-
label: resources.copy,
|
|
120
|
-
keyShortcut: resources.copyShort,
|
|
121
|
-
},
|
|
122
|
-
{
|
|
123
|
-
function: () => this.execCommand('paste'),
|
|
124
|
-
label: resources.paste,
|
|
125
|
-
keyShortcut: resources.pasteShort,
|
|
126
|
-
},
|
|
127
|
-
{
|
|
128
|
-
isDivider: true,
|
|
129
|
-
},
|
|
130
|
-
{
|
|
131
|
-
function: () => this.execCommand('selectAll'),
|
|
132
|
-
label: resources.selectAll,
|
|
133
|
-
keyShortcut: resources.selectAllShort,
|
|
134
|
-
},
|
|
135
|
-
];
|
|
136
|
-
});
|
|
137
|
-
}
|
|
138
|
-
ngOnDestroy() {
|
|
139
|
-
this.#ngUnsubscribe.next();
|
|
140
|
-
this.#ngUnsubscribe.complete();
|
|
141
|
-
}
|
|
142
|
-
execCommand(command, value = '') {
|
|
143
|
-
void this.#adapterService.execCommand({
|
|
144
|
-
command: command,
|
|
145
|
-
value: value,
|
|
146
|
-
});
|
|
147
|
-
}
|
|
148
|
-
insertMergeField(field) {
|
|
149
|
-
this.execCommand('insertHTML', '<img style="display: inline; cursor: grab;" data-fieldid="' +
|
|
150
|
-
he.escape(field.id) +
|
|
151
|
-
'" data-fielddisplay="' +
|
|
152
|
-
he.escape(field.name) +
|
|
153
|
-
'" src="' +
|
|
154
|
-
(field.previewImageUrl ||
|
|
155
|
-
this.#adapterService.getMergeFieldDataURI(field.name)) +
|
|
156
|
-
'">');
|
|
157
|
-
}
|
|
158
|
-
#closeDropdowns() {
|
|
159
|
-
this.editDropdownStream.next({ type: SkyDropdownMessageType.Close });
|
|
160
|
-
this.formatDropdownStream.next({ type: SkyDropdownMessageType.Close });
|
|
161
|
-
this.mergeFieldDropdownStream.next({ type: SkyDropdownMessageType.Close });
|
|
162
|
-
}
|
|
163
|
-
#clearFormat() {
|
|
164
|
-
const currentSelection = this.#adapterService.getCurrentSelection();
|
|
165
|
-
/* istanbul ignore else */
|
|
166
|
-
if (currentSelection &&
|
|
167
|
-
currentSelection.rangeCount > 0 &&
|
|
168
|
-
currentSelection.getRangeAt(0).toString().length <= 0) {
|
|
169
|
-
this.execCommand('selectAll');
|
|
170
|
-
}
|
|
171
|
-
this.execCommand('removeFormat');
|
|
172
|
-
}
|
|
173
|
-
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.13", ngImport: i0, type: SkyTextEditorMenubarComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
|
|
174
|
-
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "18.2.13", type: SkyTextEditorMenubarComponent, isStandalone: true, selector: "sky-text-editor-menubar", inputs: { editorFocusStream: "editorFocusStream", menus: "menus", mergeFields: "mergeFields", disabled: ["disabled", "disabled", booleanAttribute] }, ngImport: i0, template: "@for (menu of menus; track menu) {\n <sky-toolbar-item\n class=\"sky-text-editor-menu\"\n [ngClass]=\"'sky-text-editor-menu-' + menu\"\n >\n @switch (menu) {\n @case ('edit') {\n <sky-dropdown\n label=\"Edit menu\"\n [disabled]=\"disabled\"\n [messageStream]=\"editDropdownStream\"\n >\n <sky-dropdown-button>\n {{\n 'skyux_text_editor_menubar_dropdown_button_edit_label'\n | skyLibResources\n }}\n </sky-dropdown-button>\n <sky-dropdown-menu>\n @for (editItem of editItems; track editItem) {\n <sky-dropdown-item>\n @if (!editItem.isDivider) {\n <button type=\"button\" (click)=\"editItem?.function()\">\n {{ editItem.label }}\n @if (editItem.keyShortcut) {\n <div\n class=\"sky-text-editor-menu-key-shortcut\"\n [skyThemeClass]=\"{\n 'sky-font-deemphasized': 'modern',\n 'sky-deemphasized': 'default'\n }\"\n >\n {{ editItem.keyShortcut }}\n </div>\n }\n </button>\n } @else {\n <div\n class=\"sky-text-editor-dropdown-item-divider\"\n role=\"divider\"\n ></div>\n }\n </sky-dropdown-item>\n }\n </sky-dropdown-menu>\n </sky-dropdown>\n }\n @case ('format') {\n <sky-dropdown\n label=\"Format menu\"\n [disabled]=\"disabled\"\n [messageStream]=\"formatDropdownStream\"\n >\n <sky-dropdown-button>\n {{\n 'skyux_text_editor_menubar_dropdown_button_format_label'\n | skyLibResources\n }}\n </sky-dropdown-button>\n <sky-dropdown-menu>\n @for (formatItem of formatItems; track formatItem) {\n <sky-dropdown-item>\n @if (!formatItem.isDivider) {\n <button type=\"button\" (click)=\"formatItem?.function()\">\n {{ formatItem.label }}\n @if (formatItem.keyShortcut) {\n <div\n class=\"sky-text-editor-menu-key-shortcut\"\n [skyThemeClass]=\"{\n 'sky-font-deemphasized': 'modern',\n 'sky-deemphasized': 'default'\n }\"\n >\n {{ formatItem.keyShortcut }}\n </div>\n }\n </button>\n } @else {\n <div\n class=\"sky-text-editor-dropdown-item-divider\"\n role=\"divider\"\n ></div>\n }\n </sky-dropdown-item>\n }\n </sky-dropdown-menu>\n </sky-dropdown>\n }\n @case ('merge-field') {\n @if (mergeFields && mergeFields.length > 0) {\n <sky-dropdown\n label=\"Insert merge field\"\n [disabled]=\"disabled\"\n [messageStream]=\"mergeFieldDropdownStream\"\n >\n <sky-dropdown-button>\n {{\n 'skyux_text_editor_menubar_dropdown_button_insert_label'\n | skyLibResources\n }}\n </sky-dropdown-button>\n <sky-dropdown-menu>\n @for (mergeField of mergeFields; track mergeField) {\n <sky-dropdown-item>\n <button type=\"button\" (click)=\"insertMergeField(mergeField)\">\n {{ mergeField.name }}\n </button>\n </sky-dropdown-item>\n }\n </sky-dropdown-menu>\n </sky-dropdown>\n }\n }\n }\n </sky-toolbar-item>\n}\n", styles: [".sky-text-editor-dropdown-item-divider{border:0;padding:0;height:1px;margin:9px 1px;overflow:hidden;background:transparent;border-bottom:1px solid rgba(0,0,0,.1);cursor:default;filter:none}.sky-text-editor-menu-key-shortcut{float:right;margin-left:15px}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "directive", type: i1.NgClass, selector: "[ngClass]", inputs: ["class", "ngClass"] }, { kind: "ngmodule", type: SkyDropdownModule }, { kind: "component", type: i2.λ2, selector: "sky-dropdown-button" }, { kind: "component", type: i2.λ3, selector: "sky-dropdown", inputs: ["buttonStyle", "buttonType", "disabled", "label", "horizontalAlignment", "messageStream", "title", "trigger"] }, { kind: "component", type: i2.λ1, selector: "sky-dropdown-item", inputs: ["ariaRole"] }, { kind: "component", type: i2.λ4, selector: "sky-dropdown-menu", inputs: ["ariaLabelledBy", "ariaRole", "useNativeFocus"], outputs: ["menuChanges"] }, { kind: "ngmodule", type: SkyTextEditorResourcesModule }, { kind: "pipe", type: i3.SkyLibResourcesPipe, name: "skyLibResources" }, { kind: "ngmodule", type: SkyThemeModule }, { kind: "directive", type: i4.λ2, selector: "[skyThemeClass]", inputs: ["class", "skyThemeClass"] }, { kind: "ngmodule", type: SkyToolbarModule }, { kind: "component", type: i5.λ39, selector: "sky-toolbar-item" }], changeDetection: i0.ChangeDetectionStrategy.OnPush }); }
|
|
175
|
-
}
|
|
176
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.13", ngImport: i0, type: SkyTextEditorMenubarComponent, decorators: [{
|
|
177
|
-
type: Component,
|
|
178
|
-
args: [{ standalone: true, selector: 'sky-text-editor-menubar', changeDetection: ChangeDetectionStrategy.OnPush, imports: [
|
|
179
|
-
CommonModule,
|
|
180
|
-
SkyDropdownModule,
|
|
181
|
-
SkyTextEditorResourcesModule,
|
|
182
|
-
SkyThemeModule,
|
|
183
|
-
SkyToolbarModule,
|
|
184
|
-
], template: "@for (menu of menus; track menu) {\n <sky-toolbar-item\n class=\"sky-text-editor-menu\"\n [ngClass]=\"'sky-text-editor-menu-' + menu\"\n >\n @switch (menu) {\n @case ('edit') {\n <sky-dropdown\n label=\"Edit menu\"\n [disabled]=\"disabled\"\n [messageStream]=\"editDropdownStream\"\n >\n <sky-dropdown-button>\n {{\n 'skyux_text_editor_menubar_dropdown_button_edit_label'\n | skyLibResources\n }}\n </sky-dropdown-button>\n <sky-dropdown-menu>\n @for (editItem of editItems; track editItem) {\n <sky-dropdown-item>\n @if (!editItem.isDivider) {\n <button type=\"button\" (click)=\"editItem?.function()\">\n {{ editItem.label }}\n @if (editItem.keyShortcut) {\n <div\n class=\"sky-text-editor-menu-key-shortcut\"\n [skyThemeClass]=\"{\n 'sky-font-deemphasized': 'modern',\n 'sky-deemphasized': 'default'\n }\"\n >\n {{ editItem.keyShortcut }}\n </div>\n }\n </button>\n } @else {\n <div\n class=\"sky-text-editor-dropdown-item-divider\"\n role=\"divider\"\n ></div>\n }\n </sky-dropdown-item>\n }\n </sky-dropdown-menu>\n </sky-dropdown>\n }\n @case ('format') {\n <sky-dropdown\n label=\"Format menu\"\n [disabled]=\"disabled\"\n [messageStream]=\"formatDropdownStream\"\n >\n <sky-dropdown-button>\n {{\n 'skyux_text_editor_menubar_dropdown_button_format_label'\n | skyLibResources\n }}\n </sky-dropdown-button>\n <sky-dropdown-menu>\n @for (formatItem of formatItems; track formatItem) {\n <sky-dropdown-item>\n @if (!formatItem.isDivider) {\n <button type=\"button\" (click)=\"formatItem?.function()\">\n {{ formatItem.label }}\n @if (formatItem.keyShortcut) {\n <div\n class=\"sky-text-editor-menu-key-shortcut\"\n [skyThemeClass]=\"{\n 'sky-font-deemphasized': 'modern',\n 'sky-deemphasized': 'default'\n }\"\n >\n {{ formatItem.keyShortcut }}\n </div>\n }\n </button>\n } @else {\n <div\n class=\"sky-text-editor-dropdown-item-divider\"\n role=\"divider\"\n ></div>\n }\n </sky-dropdown-item>\n }\n </sky-dropdown-menu>\n </sky-dropdown>\n }\n @case ('merge-field') {\n @if (mergeFields && mergeFields.length > 0) {\n <sky-dropdown\n label=\"Insert merge field\"\n [disabled]=\"disabled\"\n [messageStream]=\"mergeFieldDropdownStream\"\n >\n <sky-dropdown-button>\n {{\n 'skyux_text_editor_menubar_dropdown_button_insert_label'\n | skyLibResources\n }}\n </sky-dropdown-button>\n <sky-dropdown-menu>\n @for (mergeField of mergeFields; track mergeField) {\n <sky-dropdown-item>\n <button type=\"button\" (click)=\"insertMergeField(mergeField)\">\n {{ mergeField.name }}\n </button>\n </sky-dropdown-item>\n }\n </sky-dropdown-menu>\n </sky-dropdown>\n }\n }\n }\n </sky-toolbar-item>\n}\n", styles: [".sky-text-editor-dropdown-item-divider{border:0;padding:0;height:1px;margin:9px 1px;overflow:hidden;background:transparent;border-bottom:1px solid rgba(0,0,0,.1);cursor:default;filter:none}.sky-text-editor-menu-key-shortcut{float:right;margin-left:15px}\n"] }]
|
|
185
|
-
}], propDecorators: { editorFocusStream: [{
|
|
186
|
-
type: Input
|
|
187
|
-
}], menus: [{
|
|
188
|
-
type: Input
|
|
189
|
-
}], mergeFields: [{
|
|
190
|
-
type: Input
|
|
191
|
-
}], disabled: [{
|
|
192
|
-
type: Input,
|
|
193
|
-
args: [{ transform: booleanAttribute }]
|
|
194
|
-
}] } });
|
|
195
|
-
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoidGV4dC1lZGl0b3ItbWVudWJhci5jb21wb25lbnQuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi8uLi8uLi8uLi8uLi8uLi9saWJzL2NvbXBvbmVudHMvdGV4dC1lZGl0b3Ivc3JjL2xpYi9tb2R1bGVzL3RleHQtZWRpdG9yL21lbnViYXIvdGV4dC1lZGl0b3ItbWVudWJhci5jb21wb25lbnQudHMiLCIuLi8uLi8uLi8uLi8uLi8uLi8uLi8uLi8uLi9saWJzL2NvbXBvbmVudHMvdGV4dC1lZGl0b3Ivc3JjL2xpYi9tb2R1bGVzL3RleHQtZWRpdG9yL21lbnViYXIvdGV4dC1lZGl0b3ItbWVudWJhci5jb21wb25lbnQuaHRtbCJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiQUFBQSxPQUFPLEVBQUUsWUFBWSxFQUFFLE1BQU0saUJBQWlCLENBQUM7QUFDL0MsT0FBTyxFQUNMLHVCQUF1QixFQUN2QixTQUFTLEVBQ1QsS0FBSyxFQUdMLGdCQUFnQixFQUNoQixNQUFNLEdBQ1AsTUFBTSxlQUFlLENBQUM7QUFDdkIsT0FBTyxFQUFFLHNCQUFzQixFQUFFLE1BQU0sYUFBYSxDQUFDO0FBQ3JELE9BQU8sRUFBRSxnQkFBZ0IsRUFBRSxNQUFNLGVBQWUsQ0FBQztBQUNqRCxPQUFPLEVBRUwsc0JBQXNCLEVBQ3RCLGlCQUFpQixHQUNsQixNQUFNLGlCQUFpQixDQUFDO0FBQ3pCLE9BQU8sRUFBRSxjQUFjLEVBQUUsTUFBTSxjQUFjLENBQUM7QUFFOUMsT0FBTyxFQUFFLE1BQU0sSUFBSSxDQUFDO0FBQ3BCLE9BQU8sRUFBRSxPQUFPLEVBQUUsTUFBTSxNQUFNLENBQUM7QUFDL0IsT0FBTyxFQUFFLElBQUksRUFBRSxTQUFTLEVBQUUsTUFBTSxnQkFBZ0IsQ0FBQztBQUVqRCxPQUFPLEVBQUUsNEJBQTRCLEVBQUUsTUFBTSwrQ0FBK0MsQ0FBQztBQUM3RixPQUFPLEVBQUUsMkJBQTJCLEVBQUUsTUFBTSx5Q0FBeUMsQ0FBQzs7Ozs7OztBQUl0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LHVCQUF1QixDQUFDLE1BQU0sV0FDdEM7d0JBQ1AsWUFBWTt3QkFDWixpQkFBaUI7d0JBQ2pCLDRCQUE0Qjt3QkFDNUIsY0FBYzt3QkFDZCxnQkFBZ0I7cUJBQ2pCOzhCQUlNLGlCQUFpQjtzQkFEdkIsS0FBSztnQkFJQyxLQUFLO3NCQURYLEtBQUs7Z0JBSUMsV0FBVztzQkFEakIsS0FBSztnQkFJQyxRQUFRO3NCQURkLEtBQUs7dUJBQUMsRUFBRSxTQUFTLEVBQUUsZ0JBQWdCLEVBQUUiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBDb21tb25Nb2R1bGUgfSBmcm9tICdAYW5ndWxhci9jb21tb24nO1xuaW1wb3J0IHtcbiAgQ2hhbmdlRGV0ZWN0aW9uU3RyYXRlZ3ksXG4gIENvbXBvbmVudCxcbiAgSW5wdXQsXG4gIE9uRGVzdHJveSxcbiAgT25Jbml0LFxuICBib29sZWFuQXR0cmlidXRlLFxuICBpbmplY3QsXG59IGZyb20gJ0Bhbmd1bGFyL2NvcmUnO1xuaW1wb3J0IHsgU2t5TGliUmVzb3VyY2VzU2VydmljZSB9IGZyb20gJ0Bza3l1eC9pMThuJztcbmltcG9ydCB7IFNreVRvb2xiYXJNb2R1bGUgfSBmcm9tICdAc2t5dXgvbGF5b3V0JztcbmltcG9ydCB7XG4gIFNreURyb3Bkb3duTWVzc2FnZSxcbiAgU2t5RHJvcGRvd25NZXNzYWdlVHlwZSxcbiAgU2t5RHJvcGRvd25Nb2R1bGUsXG59IGZyb20gJ0Bza3l1eC9wb3BvdmVycyc7XG5pbXBvcnQgeyBTa3lUaGVtZU1vZHVsZSB9IGZyb20gJ0Bza3l1eC90aGVtZSc7XG5cbmltcG9ydCBoZSBmcm9tICdoZSc7XG5pbXBvcnQgeyBTdWJqZWN0IH0gZnJvbSAncnhqcyc7XG5pbXBvcnQgeyB0YWtlLCB0YWtlVW50aWwgfSBmcm9tICdyeGpzL29wZXJhdG9ycyc7XG5cbmltcG9ydCB7IFNreVRleHRFZGl0b3JSZXNvdXJjZXNNb2R1bGUgfSBmcm9tICcuLi8uLi9zaGFyZWQvc2t5LXRleHQtZWRpdG9yLXJlc291cmNlcy5tb2R1bGUnO1xuaW1wb3J0IHsgU2t5VGV4dEVkaXRvckFkYXB0ZXJTZXJ2aWNlIH0gZnJvbSAnLi4vc2VydmljZXMvdGV4dC1lZGl0b3ItYWRhcHRlci5zZXJ2aWNlJztcbmltcG9ydCB7IFNreVRleHRFZGl0b3JNZW51VHlwZSB9IGZyb20gJy4uL3R5cGVzL21lbnUtdHlwZSc7XG5pbXBvcnQgeyBTa3lUZXh0RWRpdG9yTWVyZ2VGaWVsZCB9IGZyb20gJy4uL3R5cGVzL3RleHQtZWRpdG9yLW1lcmdlLWZpZWxkJztcblxuY29uc3QgRk9STUFUX01FTlVfQUNUSU9OID0gJ3NreXV4X3RleHRfZWRpdG9yX2Zvcm1hdF9tZW51X2FjdGlvbl8nO1xuY29uc3QgRURJVF9NRU5VX0FDVElPTiA9ICdza3l1eF90ZXh0X2VkaXRvcl9lZGl0X21lbnVfYWN0aW9uXyc7XG5cbi8qKlxuICogQGludGVybmFsXG4gKi9cbkBDb21wb25lbnQoe1xuICBzdGFuZGFsb25lOiB0cnVlLFxuICBzZWxlY3RvcjogJ3NreS10ZXh0LWVkaXRvci1tZW51YmFyJyxcbiAgdGVtcGxhdGVVcmw6ICcuL3RleHQtZWRpdG9yLW1lbnViYXIuY29tcG9uZW50Lmh0bWwnLFxuICBzdHlsZVVybHM6IFsnLi90ZXh0LWVkaXRvci1tZW51YmFyLmNvbXBvbmVudC5zY3NzJ10sXG4gIGNoYW5nZURldGVjdGlvbjogQ2hhbmdlRGV0ZWN0aW9uU3RyYXRlZ3kuT25QdXNoLFxuICBpbXBvcnRzOiBbXG4gICAgQ29tbW9uTW9kdWxlLFxuICAgIFNreURyb3Bkb3duTW9kdWxlLFxuICAgIFNreVRleHRFZGl0b3JSZXNvdXJjZXNNb2R1bGUsXG4gICAgU2t5VGhlbWVNb2R1bGUsXG4gICAgU2t5VG9vbGJhck1vZHVsZSxcbiAgXSxcbn0pXG5leHBvcnQgY2xhc3MgU2t5VGV4dEVkaXRvck1lbnViYXJDb21wb25lbnQgaW1wbGVtZW50cyBPbkRlc3Ryb3ksIE9uSW5pdCB7XG4gIEBJbnB1dCgpXG4gIHB1YmxpYyBlZGl0b3JGb2N1c1N0cmVhbSA9IG5ldyBTdWJqZWN0PHZvaWQ+KCk7XG5cbiAgQElucHV0KClcbiAgcHVibGljIG1lbnVzOiBTa3lUZXh0RWRpdG9yTWVudVR5cGVbXSA9IFtdO1xuXG4gIEBJbnB1dCgpXG4gIHB1YmxpYyBtZXJnZUZpZWxkczogU2t5VGV4dEVkaXRvck1lcmdlRmllbGRbXSA9IFtdO1xuXG4gIEBJbnB1dCh7IHRyYW5zZm9ybTogYm9vbGVhbkF0dHJpYnV0ZSB9KVxuICBwdWJsaWMgZGlzYWJsZWQgPSBmYWxzZTtcblxuICBwdWJsaWMgZWRpdERyb3Bkb3duU3RyZWFtID0gbmV3IFN1YmplY3Q8U2t5RHJvcGRvd25NZXNzYWdlPigpO1xuXG4gIHB1YmxpYyBlZGl0SXRlbXM6XG4gICAgfCB7XG4gICAgICAgIGZ1bmN0aW9uPzogKCkgPT4gdm9pZDtcbiAgICAgICAgaXNEaXZpZGVyPzogYm9vbGVhbjtcbiAgICAgICAgbGFiZWw/OiBzdHJpbmc7XG4gICAgICAgIGtleVNob3J0Y3V0Pzogc3RyaW5nO1xuICAgICAgfVtdXG4gICAgfCB1bmRlZmluZWQ7XG5cbiAgcHVibGljIGZvcm1hdERyb3Bkb3duU3RyZWFtID0gbmV3IFN1YmplY3Q8U2t5RHJvcGRvd25NZXNzYWdlPigpO1xuXG4gIHB1YmxpYyBmb3JtYXRJdGVtczpcbiAgICB8IHtcbiAgICAgICAgZnVuY3Rpb24/OiAoKSA9PiB2b2lkO1xuICAgICAgICBpc0RpdmlkZXI/OiBib29sZWFuO1xuICAgICAgICBsYWJlbD86IHN0cmluZztcbiAgICAgICAga2V5U2hvcnRjdXQ/OiBzdHJpbmc7XG4gICAgICB9W11cbiAgICB8IHVuZGVmaW5lZDtcblxuICBwdWJsaWMgbWVyZ2VGaWVsZERyb3Bkb3duU3RyZWFtID0gbmV3IFN1YmplY3Q8U2t5RHJvcGRvd25NZXNzYWdlPigpO1xuXG4gICNuZ1Vuc3Vic2NyaWJlID0gbmV3IFN1YmplY3Q8dm9pZD4oKTtcblxuICByZWFkb25seSAjYWRhcHRlclNlcnZpY2UgPSBpbmplY3QoU2t5VGV4dEVkaXRvckFkYXB0ZXJTZXJ2aWNlKTtcbiAgcmVhZG9ubHkgI3Jlc291cmNlcyA9IGluamVjdChTa3lMaWJSZXNvdXJjZXNTZXJ2aWNlKTtcblxuICBwdWJsaWMgbmdPbkluaXQoKTogdm9pZCB7XG4gICAgdGhpcy5lZGl0b3JGb2N1c1N0cmVhbVxuICAgICAgLnBpcGUodGFrZVVudGlsKHRoaXMuI25nVW5zdWJzY3JpYmUpKVxuICAgICAgLnN1YnNjcmliZSgoKSA9PiB7XG4gICAgICAgIHRoaXMuI2Nsb3NlRHJvcGRvd25zKCk7XG4gICAgICB9KTtcblxuICAgIHRoaXMuI3Jlc291cmNlc1xuICAgICAgLmdldFN0cmluZ3Moe1xuICAgICAgICBib2xkOiBGT1JNQVRfTUVOVV9BQ1RJT04gKyAnYm9sZF9sYWJlbCcsXG4gICAgICAgIGJvbGRTaG9ydDogRk9STUFUX01FTlVfQUNUSU9OICsgJ2JvbGRfa2V5X3Nob3J0Y3V0JyxcbiAgICAgICAgaXRhbGljOiBGT1JNQVRfTUVOVV9BQ1RJT04gKyAnaXRhbGljX2xhYmVsJyxcbiAgICAgICAgaXRhbGljU2hvcnQ6IEZPUk1BVF9NRU5VX0FDVElPTiArICdpdGFsaWNfa2V5X3Nob3J0Y3V0JyxcbiAgICAgICAgdW5kZXJsaW5lOiBGT1JNQVRfTUVOVV9BQ1RJT04gKyAndW5kZXJsaW5lX2xhYmVsJyxcbiAgICAgICAgdW5kZXJsaW5lU2hvcnQ6IEZPUk1BVF9NRU5VX0FDVElPTiArICd1bmRlcmxpbmVfa2V5X3Nob3J0Y3V0JyxcbiAgICAgICAgc3RyaWtldGhyb3VnaDogRk9STUFUX01FTlVfQUNUSU9OICsgJ3N0cmlrZXRocm91Z2hfbGFiZWwnLFxuICAgICAgICBjbGVhckZvcm1hdHRpbmc6IEZPUk1BVF9NRU5VX0FDVElPTiArICdjbGVhcl9mb3JtYXR0aW5nX2xhYmVsJyxcbiAgICAgICAgdW5kbzogRURJVF9NRU5VX0FDVElPTiArICd1bmRvX2xhYmVsJyxcbiAgICAgICAgdW5kb1Nob3J0OiBFRElUX01FTlVfQUNUSU9OICsgJ3VuZG9fa2V5X3Nob3J0Y3V0JyxcbiAgICAgICAgcmVkbzogRURJVF9NRU5VX0FDVElPTiArICdyZWRvX2xhYmVsJyxcbiAgICAgICAgcmVkb1Nob3J0OiBFRElUX01FTlVfQUNUSU9OICsgJ3JlZG9fa2V5X3Nob3J0Y3V0JyxcbiAgICAgICAgY3V0OiBFRElUX01FTlVfQUNUSU9OICsgJ2N1dF9sYWJlbCcsXG4gICAgICAgIGN1dFNob3J0OiBFRElUX01FTlVfQUNUSU9OICsgJ2N1dF9rZXlfc2hvcnRjdXQnLFxuICAgICAgICBjb3B5OiBFRElUX01FTlVfQUNUSU9OICsgJ2NvcHlfbGFiZWwnLFxuICAgICAgICBjb3B5U2hvcnQ6IEVESVRfTUVOVV9BQ1RJT04gKyAnY29weV9rZXlfc2hvcnRjdXQnLFxuICAgICAgICBwYXN0ZTogRURJVF9NRU5VX0FDVElPTiArICdwYXN0ZV9sYWJlbCcsXG4gICAgICAgIHBhc3RlU2hvcnQ6IEVESVRfTUVOVV9BQ1RJT04gKyAncGFzdGVfa2V5X3Nob3J0Y3V0JyxcbiAgICAgICAgc2VsZWN0QWxsOiBFRElUX01FTlVfQUNUSU9OICsgJ3NlbGVjdF9hbGxfbGFiZWwnLFxuICAgICAgICBzZWxlY3RBbGxTaG9ydDogRURJVF9NRU5VX0FDVElPTiArICdzZWxlY3RfYWxsX2tleV9zaG9ydGN1dCcsXG4gICAgICB9KVxuICAgICAgLnBpcGUodGFrZSgxKSwgdGFrZVVudGlsKHRoaXMuI25nVW5zdWJzY3JpYmUpKVxuICAgICAgLnN1YnNjcmliZSgocmVzb3VyY2VzKSA9PiB7XG4gICAgICAgIHRoaXMuZm9ybWF0SXRlbXMgPSBbXG4gICAgICAgICAge1xuICAgICAgICAgICAgZnVuY3Rpb246ICgpID0+IHRoaXMuZXhlY0NvbW1hbmQoJ2JvbGQnKSxcbiAgICAgICAgICAgIGxhYmVsOiByZXNvdXJjZXMuYm9sZCxcbiAgICAgICAgICAgIGtleVNob3J0Y3V0OiByZXNvdXJjZXMuYm9sZFNob3J0LFxuICAgICAgICAgIH0sXG4gICAgICAgICAge1xuICAgICAgICAgICAgZnVuY3Rpb246ICgpID0+IHRoaXMuZXhlY0NvbW1hbmQoJ2l0YWxpYycpLFxuICAgICAgICAgICAgbGFiZWw6IHJlc291cmNlcy5pdGFsaWMsXG4gICAgICAgICAgICBrZXlTaG9ydGN1dDogcmVzb3VyY2VzLml0YWxpY1Nob3J0LFxuICAgICAgICAgIH0sXG4gICAgICAgICAge1xuICAgICAgICAgICAgZnVuY3Rpb246ICgpID0+IHRoaXMuZXhlY0NvbW1hbmQoJ3VuZGVybGluZScpLFxuICAgICAgICAgICAgbGFiZWw6IHJlc291cmNlcy51bmRlcmxpbmUsXG4gICAgICAgICAgICBrZXlTaG9ydGN1dDogcmVzb3VyY2VzLnVuZGVybGluZVNob3J0LFxuICAgICAgICAgIH0sXG4gICAgICAgICAge1xuICAgICAgICAgICAgZnVuY3Rpb246ICgpID0+IHRoaXMuZXhlY0NvbW1hbmQoJ3N0cmlrZXRocm91Z2gnKSxcbiAgICAgICAgICAgIGxhYmVsOiByZXNvdXJjZXMuc3RyaWtldGhyb3VnaCxcbiAgICAgICAgICB9LFxuICAgICAgICAgIHtcbiAgICAgICAgICAgIGlzRGl2aWRlcjogdHJ1ZSxcbiAgICAgICAgICB9LFxuICAgICAgICAgIHtcbiAgICAgICAgICAgIGZ1bmN0aW9uOiAoKSA9PiB0aGlzLiNjbGVhckZvcm1hdCgpLFxuICAgICAgICAgICAgbGFiZWw6IHJlc291cmNlcy5jbGVhckZvcm1hdHRpbmcsXG4gICAgICAgICAgfSxcbiAgICAgICAgXTtcbiAgICAgICAgdGhpcy5lZGl0SXRlbXMgPSBbXG4gICAgICAgICAge1xuICAgICAgICAgICAgZnVuY3Rpb246ICgpID0+IHRoaXMuZXhlY0NvbW1hbmQoJ3VuZG8nKSxcbiAgICAgICAgICAgIGxhYmVsOiByZXNvdXJjZXMudW5kbyxcbiAgICAgICAgICAgIGtleVNob3J0Y3V0OiByZXNvdXJjZXMudW5kb1Nob3J0LFxuICAgICAgICAgIH0sXG4gICAgICAgICAge1xuICAgICAgICAgICAgZnVuY3Rpb246ICgpID0+IHRoaXMuZXhlY0NvbW1hbmQoJ3JlZG8nKSxcbiAgICAgICAgICAgIGxhYmVsOiByZXNvdXJjZXMucmVkbyxcbiAgICAgICAgICAgIGtleVNob3J0Y3V0OiByZXNvdXJjZXMucmVkb1Nob3J0LFxuICAgICAgICAgIH0sXG4gICAgICAgICAge1xuICAgICAgICAgICAgaXNEaXZpZGVyOiB0cnVlLFxuICAgICAgICAgIH0sXG4gICAgICAgICAge1xuICAgICAgICAgICAgZnVuY3Rpb246ICgpID0+IHRoaXMuZXhlY0NvbW1hbmQoJ2N1dCcpLFxuICAgICAgICAgICAgbGFiZWw6IHJlc291cmNlcy5jdXQsXG4gICAgICAgICAgICBrZXlTaG9ydGN1dDogcmVzb3VyY2VzLmN1dFNob3J0LFxuICAgICAgICAgIH0sXG4gICAgICAgICAge1xuICAgICAgICAgICAgZnVuY3Rpb246ICgpID0+IHRoaXMuZXhlY0NvbW1hbmQoJ2NvcHknKSxcbiAgICAgICAgICAgIGxhYmVsOiByZXNvdXJjZXMuY29weSxcbiAgICAgICAgICAgIGtleVNob3J0Y3V0OiByZXNvdXJjZXMuY29weVNob3J0LFxuICAgICAgICAgIH0sXG4gICAgICAgICAge1xuICAgICAgICAgICAgZnVuY3Rpb246ICgpID0+IHRoaXMuZXhlY0NvbW1hbmQoJ3Bhc3RlJyksXG4gICAgICAgICAgICBsYWJlbDogcmVzb3VyY2VzLnBhc3RlLFxuICAgICAgICAgICAga2V5U2hvcnRjdXQ6IHJlc291cmNlcy5wYXN0ZVNob3J0LFxuICAgICAgICAgIH0sXG4gICAgICAgICAge1xuICAgICAgICAgICAgaXNEaXZpZGVyOiB0cnVlLFxuICAgICAgICAgIH0sXG4gICAgICAgICAge1xuICAgICAgICAgICAgZnVuY3Rpb246ICgpID0+IHRoaXMuZXhlY0NvbW1hbmQoJ3NlbGVjdEFsbCcpLFxuICAgICAgICAgICAgbGFiZWw6IHJlc291cmNlcy5zZWxlY3RBbGwsXG4gICAgICAgICAgICBrZXlTaG9ydGN1dDogcmVzb3VyY2VzLnNlbGVjdEFsbFNob3J0LFxuICAgICAgICAgIH0sXG4gICAgICAgIF07XG4gICAgICB9KTtcbiAgfVxuXG4gIHB1YmxpYyBuZ09uRGVzdHJveSgpOiB2b2lkIHtcbiAgICB0aGlzLiNuZ1Vuc3Vic2NyaWJlLm5leHQoKTtcbiAgICB0aGlzLiNuZ1Vuc3Vic2NyaWJlLmNvbXBsZXRlKCk7XG4gIH1cblxuICBwdWJsaWMgZXhlY0NvbW1hbmQoY29tbWFuZDogc3RyaW5nLCB2YWx1ZSA9ICcnKTogdm9pZCB7XG4gICAgdm9pZCB0aGlzLiNhZGFwdGVyU2VydmljZS5leGVjQ29tbWFuZCh7XG4gICAgICBjb21tYW5kOiBjb21tYW5kLFxuICAgICAgdmFsdWU6IHZhbHVlLFxuICAgIH0pO1xuICB9XG5cbiAgcHVibGljIGluc2VydE1lcmdlRmllbGQoZmllbGQ6IFNreVRleHRFZGl0b3JNZXJnZUZpZWxkKTogdm9pZCB7XG4gICAgdGhpcy5leGVjQ29tbWFuZChcbiAgICAgICdpbnNlcnRIVE1MJyxcbiAgICAgICc8aW1nIHN0eWxlPVwiZGlzcGxheTogaW5saW5lOyBjdXJzb3I6IGdyYWI7XCIgZGF0YS1maWVsZGlkPVwiJyArXG4gICAgICAgIGhlLmVzY2FwZShmaWVsZC5pZCkgK1xuICAgICAgICAnXCIgZGF0YS1maWVsZGRpc3BsYXk9XCInICtcbiAgICAgICAgaGUuZXNjYXBlKGZpZWxkLm5hbWUpICtcbiAgICAgICAgJ1wiIHNyYz1cIicgK1xuICAgICAgICAoZmllbGQucHJldmlld0ltYWdlVXJsIHx8XG4gICAgICAgICAgdGhpcy4jYWRhcHRlclNlcnZpY2UuZ2V0TWVyZ2VGaWVsZERhdGFVUkkoZmllbGQubmFtZSkpICtcbiAgICAgICAgJ1wiPicsXG4gICAgKTtcbiAgfVxuXG4gICNjbG9zZURyb3Bkb3ducygpOiB2b2lkIHtcbiAgICB0aGlzLmVkaXREcm9wZG93blN0cmVhbS5uZXh0KHsgdHlwZTogU2t5RHJvcGRvd25NZXNzYWdlVHlwZS5DbG9zZSB9KTtcbiAgICB0aGlzLmZvcm1hdERyb3Bkb3duU3RyZWFtLm5leHQoeyB0eXBlOiBTa3lEcm9wZG93bk1lc3NhZ2VUeXBlLkNsb3NlIH0pO1xuICAgIHRoaXMubWVyZ2VGaWVsZERyb3Bkb3duU3RyZWFtLm5leHQoeyB0eXBlOiBTa3lEcm9wZG93bk1lc3NhZ2VUeXBlLkNsb3NlIH0pO1xuICB9XG5cbiAgI2NsZWFyRm9ybWF0KCk6IHZvaWQge1xuICAgIGNvbnN0IGN1cnJlbnRTZWxlY3Rpb24gPSB0aGlzLiNhZGFwdGVyU2VydmljZS5nZXRDdXJyZW50U2VsZWN0aW9uKCk7XG4gICAgLyogaXN0YW5idWwgaWdub3JlIGVsc2UgKi9cbiAgICBpZiAoXG4gICAgICBjdXJyZW50U2VsZWN0aW9uICYmXG4gICAgICBjdXJyZW50U2VsZWN0aW9uLnJhbmdlQ291bnQgPiAwICYmXG4gICAgICBjdXJyZW50U2VsZWN0aW9uLmdldFJhbmdlQXQoMCkudG9TdHJpbmcoKS5sZW5ndGggPD0gMFxuICAgICkge1xuICAgICAgdGhpcy5leGVjQ29tbWFuZCgnc2VsZWN0QWxsJyk7XG4gICAgfVxuICAgIHRoaXMuZXhlY0NvbW1hbmQoJ3JlbW92ZUZvcm1hdCcpO1xuICB9XG59XG4iLCJAZm9yIChtZW51IG9mIG1lbnVzOyB0cmFjayBtZW51KSB7XG4gIDxza3ktdG9vbGJhci1pdGVtXG4gICAgY2xhc3M9XCJza3ktdGV4dC1lZGl0b3ItbWVudVwiXG4gICAgW25nQ2xhc3NdPVwiJ3NreS10ZXh0LWVkaXRvci1tZW51LScgKyBtZW51XCJcbiAgPlxuICAgIEBzd2l0Y2ggKG1lbnUpIHtcbiAgICAgIEBjYXNlICgnZWRpdCcpIHtcbiAgICAgICAgPHNreS1kcm9wZG93blxuICAgICAgICAgIGxhYmVsPVwiRWRpdCBtZW51XCJcbiAgICAgICAgICBbZGlzYWJsZWRdPVwiZGlzYWJsZWRcIlxuICAgICAgICAgIFttZXNzYWdlU3RyZWFtXT1cImVkaXREcm9wZG93blN0cmVhbVwiXG4gICAgICAgID5cbiAgICAgICAgICA8c2t5LWRyb3Bkb3duLWJ1dHRvbj5cbiAgICAgICAgICAgIHt7XG4gICAgICAgICAgICAgICdza3l1eF90ZXh0X2VkaXRvcl9tZW51YmFyX2Ryb3Bkb3duX2J1dHRvbl9lZGl0X2xhYmVsJ1xuICAgICAgICAgICAgICAgIHwgc2t5TGliUmVzb3VyY2VzXG4gICAgICAgICAgICB9fVxuICAgICAgICAgIDwvc2t5LWRyb3Bkb3duLWJ1dHRvbj5cbiAgICAgICAgICA8c2t5LWRyb3Bkb3duLW1lbnU+XG4gICAgICAgICAgICBAZm9yIChlZGl0SXRlbSBvZiBlZGl0SXRlbXM7IHRyYWNrIGVkaXRJdGVtKSB7XG4gICAgICAgICAgICAgIDxza3ktZHJvcGRvd24taXRlbT5cbiAgICAgICAgICAgICAgICBAaWYgKCFlZGl0SXRlbS5pc0RpdmlkZXIpIHtcbiAgICAgICAgICAgICAgICAgIDxidXR0b24gdHlwZT1cImJ1dHRvblwiIChjbGljayk9XCJlZGl0SXRlbT8uZnVuY3Rpb24oKVwiPlxuICAgICAgICAgICAgICAgICAgICB7eyBlZGl0SXRlbS5sYWJlbCB9fVxuICAgICAgICAgICAgICAgICAgICBAaWYgKGVkaXRJdGVtLmtleVNob3J0Y3V0KSB7XG4gICAgICAgICAgICAgICAgICAgICAgPGRpdlxuICAgICAgICAgICAgICAgICAgICAgICAgY2xhc3M9XCJza3ktdGV4dC1lZGl0b3ItbWVudS1rZXktc2hvcnRjdXRcIlxuICAgICAgICAgICAgICAgICAgICAgICAgW3NreVRoZW1lQ2xhc3NdPVwie1xuICAgICAgICAgICAgICAgICAgICAgICAgICAnc2t5LWZvbnQtZGVlbXBoYXNpemVkJzogJ21vZGVybicsXG4gICAgICAgICAgICAgICAgICAgICAgICAgICdza3ktZGVlbXBoYXNpemVkJzogJ2RlZmF1bHQnXG4gICAgICAgICAgICAgICAgICAgICAgICB9XCJcbiAgICAgICAgICAgICAgICAgICAgICA+XG4gICAgICAgICAgICAgICAgICAgICAgICB7eyBlZGl0SXRlbS5rZXlTaG9ydGN1dCB9fVxuICAgICAgICAgICAgICAgICAgICAgIDwvZGl2PlxuICAgICAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgICA8L2J1dHRvbj5cbiAgICAgICAgICAgICAgICB9IEBlbHNlIHtcbiAgICAgICAgICAgICAgICAgIDxkaXZcbiAgICAgICAgICAgICAgICAgICAgY2xhc3M9XCJza3ktdGV4dC1lZGl0b3ItZHJvcGRvd24taXRlbS1kaXZpZGVyXCJcbiAgICAgICAgICAgICAgICAgICAgcm9sZT1cImRpdmlkZXJcIlxuICAgICAgICAgICAgICAgICAgPjwvZGl2PlxuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgPC9za3ktZHJvcGRvd24taXRlbT5cbiAgICAgICAgICAgIH1cbiAgICAgICAgICA8L3NreS1kcm9wZG93bi1tZW51PlxuICAgICAgICA8L3NreS1kcm9wZG93bj5cbiAgICAgIH1cbiAgICAgIEBjYXNlICgnZm9ybWF0Jykge1xuICAgICAgICA8c2t5LWRyb3Bkb3duXG4gICAgICAgICAgbGFiZWw9XCJGb3JtYXQgbWVudVwiXG4gICAgICAgICAgW2Rpc2FibGVkXT1cImRpc2FibGVkXCJcbiAgICAgICAgICBbbWVzc2FnZVN0cmVhbV09XCJmb3JtYXREcm9wZG93blN0cmVhbVwiXG4gICAgICAgID5cbiAgICAgICAgICA8c2t5LWRyb3Bkb3duLWJ1dHRvbj5cbiAgICAgICAgICAgIHt7XG4gICAgICAgICAgICAgICdza3l1eF90ZXh0X2VkaXRvcl9tZW51YmFyX2Ryb3Bkb3duX2J1dHRvbl9mb3JtYXRfbGFiZWwnXG4gICAgICAgICAgICAgICAgfCBza3lMaWJSZXNvdXJjZXNcbiAgICAgICAgICAgIH19XG4gICAgICAgICAgPC9za3ktZHJvcGRvd24tYnV0dG9uPlxuICAgICAgICAgIDxza3ktZHJvcGRvd24tbWVudT5cbiAgICAgICAgICAgIEBmb3IgKGZvcm1hdEl0ZW0gb2YgZm9ybWF0SXRlbXM7IHRyYWNrIGZvcm1hdEl0ZW0pIHtcbiAgICAgICAgICAgICAgPHNreS1kcm9wZG93bi1pdGVtPlxuICAgICAgICAgICAgICAgIEBpZiAoIWZvcm1hdEl0ZW0uaXNEaXZpZGVyKSB7XG4gICAgICAgICAgICAgICAgICA8YnV0dG9uIHR5cGU9XCJidXR0b25cIiAoY2xpY2spPVwiZm9ybWF0SXRlbT8uZnVuY3Rpb24oKVwiPlxuICAgICAgICAgICAgICAgICAgICB7eyBmb3JtYXRJdGVtLmxhYmVsIH19XG4gICAgICAgICAgICAgICAgICAgIEBpZiAoZm9ybWF0SXRlbS5rZXlTaG9ydGN1dCkge1xuICAgICAgICAgICAgICAgICAgICAgIDxkaXZcbiAgICAgICAgICAgICAgICAgICAgICAgIGNsYXNzPVwic2t5LXRleHQtZWRpdG9yLW1lbnUta2V5LXNob3J0Y3V0XCJcbiAgICAgICAgICAgICAgICAgICAgICAgIFtza3lUaGVtZUNsYXNzXT1cIntcbiAgICAgICAgICAgICAgICAgICAgICAgICAgJ3NreS1mb250LWRlZW1waGFzaXplZCc6ICdtb2Rlcm4nLFxuICAgICAgICAgICAgICAgICAgICAgICAgICAnc2t5LWRlZW1waGFzaXplZCc6ICdkZWZhdWx0J1xuICAgICAgICAgICAgICAgICAgICAgICAgfVwiXG4gICAgICAgICAgICAgICAgICAgICAgPlxuICAgICAgICAgICAgICAgICAgICAgICAge3sgZm9ybWF0SXRlbS5rZXlTaG9ydGN1dCB9fVxuICAgICAgICAgICAgICAgICAgICAgIDwvZGl2PlxuICAgICAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgICA8L2J1dHRvbj5cbiAgICAgICAgICAgICAgICB9IEBlbHNlIHtcbiAgICAgICAgICAgICAgICAgIDxkaXZcbiAgICAgICAgICAgICAgICAgICAgY2xhc3M9XCJza3ktdGV4dC1lZGl0b3ItZHJvcGRvd24taXRlbS1kaXZpZGVyXCJcbiAgICAgICAgICAgICAgICAgICAgcm9sZT1cImRpdmlkZXJcIlxuICAgICAgICAgICAgICAgICAgPjwvZGl2PlxuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgPC9za3ktZHJvcGRvd24taXRlbT5cbiAgICAgICAgICAgIH1cbiAgICAgICAgICA8L3NreS1kcm9wZG93bi1tZW51PlxuICAgICAgICA8L3NreS1kcm9wZG93bj5cbiAgICAgIH1cbiAgICAgIEBjYXNlICgnbWVyZ2UtZmllbGQnKSB7XG4gICAgICAgIEBpZiAobWVyZ2VGaWVsZHMgJiYgbWVyZ2VGaWVsZHMubGVuZ3RoID4gMCkge1xuICAgICAgICAgIDxza3ktZHJvcGRvd25cbiAgICAgICAgICAgIGxhYmVsPVwiSW5zZXJ0IG1lcmdlIGZpZWxkXCJcbiAgICAgICAgICAgIFtkaXNhYmxlZF09XCJkaXNhYmxlZFwiXG4gICAgICAgICAgICBbbWVzc2FnZVN0cmVhbV09XCJtZXJnZUZpZWxkRHJvcGRvd25TdHJlYW1cIlxuICAgICAgICAgID5cbiAgICAgICAgICAgIDxza3ktZHJvcGRvd24tYnV0dG9uPlxuICAgICAgICAgICAgICB7e1xuICAgICAgICAgICAgICAgICdza3l1eF90ZXh0X2VkaXRvcl9tZW51YmFyX2Ryb3Bkb3duX2J1dHRvbl9pbnNlcnRfbGFiZWwnXG4gICAgICAgICAgICAgICAgICB8IHNreUxpYlJlc291cmNlc1xuICAgICAgICAgICAgICB9fVxuICAgICAgICAgICAgPC9za3ktZHJvcGRvd24tYnV0dG9uPlxuICAgICAgICAgICAgPHNreS1kcm9wZG93bi1tZW51PlxuICAgICAgICAgICAgICBAZm9yIChtZXJnZUZpZWxkIG9mIG1lcmdlRmllbGRzOyB0cmFjayBtZXJnZUZpZWxkKSB7XG4gICAgICAgICAgICAgICAgPHNreS1kcm9wZG93bi1pdGVtPlxuICAgICAgICAgICAgICAgICAgPGJ1dHRvbiB0eXBlPVwiYnV0dG9uXCIgKGNsaWNrKT1cImluc2VydE1lcmdlRmllbGQobWVyZ2VGaWVsZClcIj5cbiAgICAgICAgICAgICAgICAgICAge3sgbWVyZ2VGaWVsZC5uYW1lIH19XG4gICAgICAgICAgICAgICAgICA8L2J1dHRvbj5cbiAgICAgICAgICAgICAgICA8L3NreS1kcm9wZG93bi1pdGVtPlxuICAgICAgICAgICAgICB9XG4gICAgICAgICAgICA8L3NreS1kcm9wZG93bi1tZW51PlxuICAgICAgICAgIDwvc2t5LWRyb3Bkb3duPlxuICAgICAgICB9XG4gICAgICB9XG4gICAgfVxuICA8L3NreS10b29sYmFyLWl0ZW0+XG59XG4iXX0=
|