@angular-generic-table/core 5.0.0-alpha.1 → 5.0.0-rc.10
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/README.md +13 -134
- package/angular-generic-table-core.d.ts +2 -19
- package/esm2020/angular-generic-table-core.mjs +5 -0
- package/esm2020/lib/core.component.mjs +122 -0
- package/esm2020/lib/core.module.mjs +23 -0
- package/esm2020/lib/core.service.mjs +14 -0
- package/esm2020/lib/enums/order.enum.mjs +6 -0
- package/esm2020/lib/models/table-column.interface.mjs +2 -0
- package/esm2020/lib/models/table-config.interface.mjs +2 -0
- package/esm2020/lib/models/table-info.interface.mjs +2 -0
- package/esm2020/lib/models/table-meta.interface.mjs +2 -0
- package/esm2020/lib/models/table-row.interface.mjs +2 -0
- package/esm2020/lib/models/table-sort.interface.mjs +2 -0
- package/esm2020/lib/pagination/pagination.component.mjs +63 -0
- package/esm2020/lib/pagination/pagination.module.mjs +18 -0
- package/esm2020/lib/pipes/capital-case.pipe.mjs +17 -0
- package/esm2020/lib/pipes/dash-case.pipe.mjs +17 -0
- package/esm2020/lib/pipes/dynamic.pipe.mjs +25 -0
- package/esm2020/lib/pipes/highlight.pipe.mjs +48 -0
- package/esm2020/lib/pipes/sort-class.pipe.mjs +16 -0
- package/esm2020/lib/utilities/utilities.mjs +39 -0
- package/esm2020/public-api.mjs +15 -0
- package/fesm2015/angular-generic-table-core.mjs +384 -0
- package/fesm2015/angular-generic-table-core.mjs.map +1 -0
- package/fesm2020/angular-generic-table-core.mjs +381 -0
- package/fesm2020/angular-generic-table-core.mjs.map +1 -0
- package/lib/core.component.d.ts +33 -0
- package/lib/core.module.d.ts +12 -1
- package/lib/core.service.d.ts +6 -0
- package/lib/enums/order.enum.d.ts +4 -0
- package/lib/models/table-column.interface.d.ts +15 -0
- package/lib/models/table-config.interface.d.ts +15 -0
- package/lib/models/table-info.interface.d.ts +4 -0
- package/lib/models/table-meta.interface.d.ts +8 -0
- package/lib/models/table-row.interface.d.ts +4 -0
- package/lib/models/table-sort.interface.d.ts +5 -0
- package/lib/pagination/pagination.component.d.ts +14 -0
- package/lib/pagination/pagination.module.d.ts +8 -0
- package/lib/pipes/capital-case.pipe.d.ts +7 -0
- package/lib/pipes/dash-case.pipe.d.ts +4 -1
- package/lib/pipes/dynamic.pipe.d.ts +9 -0
- package/lib/pipes/highlight.pipe.d.ts +7 -0
- package/lib/pipes/sort-class.pipe.d.ts +11 -0
- package/lib/utilities/utilities.d.ts +6 -0
- package/package.json +26 -24
- package/public-api.d.ts +11 -0
- package/scss/index.scss +102 -0
- package/CHANGELOG.md +0 -461
- package/LICENSE.md +0 -201
- package/angular-generic-table-core.metadata.json +0 -1
- package/bundles/angular-generic-table-core.umd.js +0 -3675
- package/bundles/angular-generic-table-core.umd.js.map +0 -1
- package/bundles/angular-generic-table-core.umd.min.js +0 -2
- package/bundles/angular-generic-table-core.umd.min.js.map +0 -1
- package/css/generic-table.css +0 -168
- package/css/generic-table.css.map +0 -9
- package/css/generic-table.min.css +0 -2
- package/css/generic-table.min.css.map +0 -1
- package/esm2015/angular-generic-table-core.js +0 -28
- package/esm2015/angular-generic-table-core.metadata.json +0 -1
- package/esm2015/lib/components/generic-table/generic-table.component.js +0 -1738
- package/esm2015/lib/components/generic-table/generic-table.component.metadata.json +0 -1
- package/esm2015/lib/components/gt-checkbox/gt-checkbox.component.js +0 -88
- package/esm2015/lib/components/gt-checkbox/gt-checkbox.component.metadata.json +0 -1
- package/esm2015/lib/components/gt-custom-component-factory/gt-custom-component-factory.component.js +0 -112
- package/esm2015/lib/components/gt-custom-component-factory/gt-custom-component-factory.component.metadata.json +0 -1
- package/esm2015/lib/components/gt-drilldown/gt-drilldown.component.js +0 -53
- package/esm2015/lib/components/gt-drilldown/gt-drilldown.component.metadata.json +0 -1
- package/esm2015/lib/components/gt-dropdown/gt-dropdown.component.js +0 -176
- package/esm2015/lib/components/gt-dropdown/gt-dropdown.component.metadata.json +0 -1
- package/esm2015/lib/components/gt-expanding-row/gt-expanding-row.component.js +0 -147
- package/esm2015/lib/components/gt-expanding-row/gt-expanding-row.component.metadata.json +0 -1
- package/esm2015/lib/components/gt-pagination/gt-pagination.component.js +0 -141
- package/esm2015/lib/components/gt-pagination/gt-pagination.component.metadata.json +0 -1
- package/esm2015/lib/components/gt-table-info/gt-table-info.component.js +0 -103
- package/esm2015/lib/components/gt-table-info/gt-table-info.component.metadata.json +0 -1
- package/esm2015/lib/core.module.js +0 -96
- package/esm2015/lib/core.module.metadata.json +0 -1
- package/esm2015/lib/directives/component-anchor.directive.js +0 -65
- package/esm2015/lib/directives/component-anchor.directive.metadata.json +0 -1
- package/esm2015/lib/directives/gt-column-width.directive.js +0 -73
- package/esm2015/lib/directives/gt-column-width.directive.metadata.json +0 -1
- package/esm2015/lib/interfaces/gt-config-field.js +0 -96
- package/esm2015/lib/interfaces/gt-config-field.metadata.json +0 -1
- package/esm2015/lib/interfaces/gt-config-setting.js +0 -41
- package/esm2015/lib/interfaces/gt-config-setting.metadata.json +0 -1
- package/esm2015/lib/interfaces/gt-config-total.js +0 -20
- package/esm2015/lib/interfaces/gt-config-total.metadata.json +0 -1
- package/esm2015/lib/interfaces/gt-config.js +0 -24
- package/esm2015/lib/interfaces/gt-config.metadata.json +0 -1
- package/esm2015/lib/interfaces/gt-event.js +0 -16
- package/esm2015/lib/interfaces/gt-event.metadata.json +0 -1
- package/esm2015/lib/interfaces/gt-information.js +0 -38
- package/esm2015/lib/interfaces/gt-information.metadata.json +0 -1
- package/esm2015/lib/interfaces/gt-options.js +0 -55
- package/esm2015/lib/interfaces/gt-options.metadata.json +0 -1
- package/esm2015/lib/interfaces/gt-render-field.js +0 -29
- package/esm2015/lib/interfaces/gt-render-field.metadata.json +0 -1
- package/esm2015/lib/interfaces/gt-row-meta.js +0 -18
- package/esm2015/lib/interfaces/gt-row-meta.metadata.json +0 -1
- package/esm2015/lib/interfaces/gt-row.js +0 -20
- package/esm2015/lib/interfaces/gt-row.metadata.json +0 -1
- package/esm2015/lib/interfaces/gt-texts.js +0 -36
- package/esm2015/lib/interfaces/gt-texts.metadata.json +0 -1
- package/esm2015/lib/pipes/dash-case.pipe.js +0 -30
- package/esm2015/lib/pipes/dash-case.pipe.metadata.json +0 -1
- package/esm2015/lib/pipes/gt-chunk.pipe.js +0 -52
- package/esm2015/lib/pipes/gt-chunk.pipe.metadata.json +0 -1
- package/esm2015/lib/pipes/gt-column-class.pipe.js +0 -51
- package/esm2015/lib/pipes/gt-column-class.pipe.metadata.json +0 -1
- package/esm2015/lib/pipes/gt-filter.pipe.js +0 -60
- package/esm2015/lib/pipes/gt-filter.pipe.metadata.json +0 -1
- package/esm2015/lib/pipes/gt-highlight.pipe.js +0 -72
- package/esm2015/lib/pipes/gt-highlight.pipe.metadata.json +0 -1
- package/esm2015/lib/pipes/gt-is-editable.pipe.js +0 -37
- package/esm2015/lib/pipes/gt-is-editable.pipe.metadata.json +0 -1
- package/esm2015/lib/pipes/gt-is-observable.pipe.js +0 -31
- package/esm2015/lib/pipes/gt-is-observable.pipe.metadata.json +0 -1
- package/esm2015/lib/pipes/gt-meta.pipe.js +0 -54
- package/esm2015/lib/pipes/gt-meta.pipe.metadata.json +0 -1
- package/esm2015/lib/pipes/gt-order-by.pipe.js +0 -202
- package/esm2015/lib/pipes/gt-order-by.pipe.metadata.json +0 -1
- package/esm2015/lib/pipes/gt-property.pipe.js +0 -52
- package/esm2015/lib/pipes/gt-property.pipe.metadata.json +0 -1
- package/esm2015/lib/pipes/gt-render.pipe.js +0 -173
- package/esm2015/lib/pipes/gt-render.pipe.metadata.json +0 -1
- package/esm2015/lib/pipes/gt-row-class.pipe.js +0 -66
- package/esm2015/lib/pipes/gt-row-class.pipe.metadata.json +0 -1
- package/esm2015/lib/pipes/gt-search.pipe.js +0 -114
- package/esm2015/lib/pipes/gt-search.pipe.metadata.json +0 -1
- package/esm2015/lib/pipes/gt-totals-position.pipe.js +0 -35
- package/esm2015/lib/pipes/gt-totals-position.pipe.metadata.json +0 -1
- package/esm2015/lib/pipes/gt-totals.pipe.js +0 -46
- package/esm2015/lib/pipes/gt-totals.pipe.metadata.json +0 -1
- package/esm2015/lib/pipes/gt-visible.pipe.js +0 -71
- package/esm2015/lib/pipes/gt-visible.pipe.metadata.json +0 -1
- package/esm2015/public_api.js +0 -18
- package/esm2015/public_api.metadata.json +0 -1
- package/esm5/angular-generic-table-core.js +0 -28
- package/esm5/angular-generic-table-core.metadata.json +0 -1
- package/esm5/lib/components/generic-table/generic-table.component.js +0 -1813
- package/esm5/lib/components/generic-table/generic-table.component.metadata.json +0 -1
- package/esm5/lib/components/gt-checkbox/gt-checkbox.component.js +0 -100
- package/esm5/lib/components/gt-checkbox/gt-checkbox.component.metadata.json +0 -1
- package/esm5/lib/components/gt-custom-component-factory/gt-custom-component-factory.component.js +0 -136
- package/esm5/lib/components/gt-custom-component-factory/gt-custom-component-factory.component.metadata.json +0 -1
- package/esm5/lib/components/gt-drilldown/gt-drilldown.component.js +0 -41
- package/esm5/lib/components/gt-drilldown/gt-drilldown.component.metadata.json +0 -1
- package/esm5/lib/components/gt-dropdown/gt-dropdown.component.js +0 -179
- package/esm5/lib/components/gt-dropdown/gt-dropdown.component.metadata.json +0 -1
- package/esm5/lib/components/gt-expanding-row/gt-expanding-row.component.js +0 -173
- package/esm5/lib/components/gt-expanding-row/gt-expanding-row.component.metadata.json +0 -1
- package/esm5/lib/components/gt-pagination/gt-pagination.component.js +0 -149
- package/esm5/lib/components/gt-pagination/gt-pagination.component.metadata.json +0 -1
- package/esm5/lib/components/gt-table-info/gt-table-info.component.js +0 -111
- package/esm5/lib/components/gt-table-info/gt-table-info.component.metadata.json +0 -1
- package/esm5/lib/core.module.js +0 -100
- package/esm5/lib/core.module.metadata.json +0 -1
- package/esm5/lib/directives/component-anchor.directive.js +0 -66
- package/esm5/lib/directives/component-anchor.directive.metadata.json +0 -1
- package/esm5/lib/directives/gt-column-width.directive.js +0 -81
- package/esm5/lib/directives/gt-column-width.directive.metadata.json +0 -1
- package/esm5/lib/interfaces/gt-config-field.js +0 -96
- package/esm5/lib/interfaces/gt-config-field.metadata.json +0 -1
- package/esm5/lib/interfaces/gt-config-setting.js +0 -41
- package/esm5/lib/interfaces/gt-config-setting.metadata.json +0 -1
- package/esm5/lib/interfaces/gt-config-total.js +0 -20
- package/esm5/lib/interfaces/gt-config-total.metadata.json +0 -1
- package/esm5/lib/interfaces/gt-config.js +0 -24
- package/esm5/lib/interfaces/gt-config.metadata.json +0 -1
- package/esm5/lib/interfaces/gt-event.js +0 -16
- package/esm5/lib/interfaces/gt-event.metadata.json +0 -1
- package/esm5/lib/interfaces/gt-information.js +0 -38
- package/esm5/lib/interfaces/gt-information.metadata.json +0 -1
- package/esm5/lib/interfaces/gt-options.js +0 -55
- package/esm5/lib/interfaces/gt-options.metadata.json +0 -1
- package/esm5/lib/interfaces/gt-render-field.js +0 -29
- package/esm5/lib/interfaces/gt-render-field.metadata.json +0 -1
- package/esm5/lib/interfaces/gt-row-meta.js +0 -18
- package/esm5/lib/interfaces/gt-row-meta.metadata.json +0 -1
- package/esm5/lib/interfaces/gt-row.js +0 -20
- package/esm5/lib/interfaces/gt-row.metadata.json +0 -1
- package/esm5/lib/interfaces/gt-texts.js +0 -36
- package/esm5/lib/interfaces/gt-texts.metadata.json +0 -1
- package/esm5/lib/pipes/dash-case.pipe.js +0 -38
- package/esm5/lib/pipes/dash-case.pipe.metadata.json +0 -1
- package/esm5/lib/pipes/gt-chunk.pipe.js +0 -70
- package/esm5/lib/pipes/gt-chunk.pipe.metadata.json +0 -1
- package/esm5/lib/pipes/gt-column-class.pipe.js +0 -61
- package/esm5/lib/pipes/gt-column-class.pipe.metadata.json +0 -1
- package/esm5/lib/pipes/gt-filter.pipe.js +0 -73
- package/esm5/lib/pipes/gt-filter.pipe.metadata.json +0 -1
- package/esm5/lib/pipes/gt-highlight.pipe.js +0 -77
- package/esm5/lib/pipes/gt-highlight.pipe.metadata.json +0 -1
- package/esm5/lib/pipes/gt-is-editable.pipe.js +0 -47
- package/esm5/lib/pipes/gt-is-editable.pipe.metadata.json +0 -1
- package/esm5/lib/pipes/gt-is-observable.pipe.js +0 -39
- package/esm5/lib/pipes/gt-is-observable.pipe.metadata.json +0 -1
- package/esm5/lib/pipes/gt-meta.pipe.js +0 -65
- package/esm5/lib/pipes/gt-meta.pipe.metadata.json +0 -1
- package/esm5/lib/pipes/gt-order-by.pipe.js +0 -223
- package/esm5/lib/pipes/gt-order-by.pipe.metadata.json +0 -1
- package/esm5/lib/pipes/gt-property.pipe.js +0 -63
- package/esm5/lib/pipes/gt-property.pipe.metadata.json +0 -1
- package/esm5/lib/pipes/gt-render.pipe.js +0 -182
- package/esm5/lib/pipes/gt-render.pipe.metadata.json +0 -1
- package/esm5/lib/pipes/gt-row-class.pipe.js +0 -75
- package/esm5/lib/pipes/gt-row-class.pipe.metadata.json +0 -1
- package/esm5/lib/pipes/gt-search.pipe.js +0 -125
- package/esm5/lib/pipes/gt-search.pipe.metadata.json +0 -1
- package/esm5/lib/pipes/gt-totals-position.pipe.js +0 -45
- package/esm5/lib/pipes/gt-totals-position.pipe.metadata.json +0 -1
- package/esm5/lib/pipes/gt-totals.pipe.js +0 -57
- package/esm5/lib/pipes/gt-totals.pipe.metadata.json +0 -1
- package/esm5/lib/pipes/gt-visible.pipe.js +0 -79
- package/esm5/lib/pipes/gt-visible.pipe.metadata.json +0 -1
- package/esm5/public_api.js +0 -18
- package/esm5/public_api.metadata.json +0 -1
- package/fesm2015/angular-generic-table-core.js +0 -3285
- package/fesm2015/angular-generic-table-core.js.map +0 -1
- package/fesm5/angular-generic-table-core.js +0 -3574
- package/fesm5/angular-generic-table-core.js.map +0 -1
- package/lib/components/generic-table/generic-table.component.d.ts +0 -282
- package/lib/components/gt-checkbox/gt-checkbox.component.d.ts +0 -12
- package/lib/components/gt-custom-component-factory/gt-custom-component-factory.component.d.ts +0 -27
- package/lib/components/gt-drilldown/gt-drilldown.component.d.ts +0 -6
- package/lib/components/gt-dropdown/gt-dropdown.component.d.ts +0 -21
- package/lib/components/gt-expanding-row/gt-expanding-row.component.d.ts +0 -34
- package/lib/components/gt-pagination/gt-pagination.component.d.ts +0 -11
- package/lib/components/gt-table-info/gt-table-info.component.d.ts +0 -15
- package/lib/directives/component-anchor.directive.d.ts +0 -10
- package/lib/directives/gt-column-width.directive.d.ts +0 -11
- package/lib/interfaces/gt-config-field.d.ts +0 -87
- package/lib/interfaces/gt-config-setting.d.ts +0 -21
- package/lib/interfaces/gt-config-total.d.ts +0 -8
- package/lib/interfaces/gt-config.d.ts +0 -12
- package/lib/interfaces/gt-event.d.ts +0 -4
- package/lib/interfaces/gt-information.d.ts +0 -15
- package/lib/interfaces/gt-options.d.ts +0 -27
- package/lib/interfaces/gt-render-field.d.ts +0 -19
- package/lib/interfaces/gt-row-meta.d.ts +0 -5
- package/lib/interfaces/gt-row.d.ts +0 -6
- package/lib/interfaces/gt-texts.d.ts +0 -14
- package/lib/pipes/gt-chunk.pipe.d.ts +0 -8
- package/lib/pipes/gt-column-class.pipe.d.ts +0 -6
- package/lib/pipes/gt-filter.pipe.d.ts +0 -5
- package/lib/pipes/gt-highlight.pipe.d.ts +0 -7
- package/lib/pipes/gt-is-editable.pipe.d.ts +0 -4
- package/lib/pipes/gt-is-observable.pipe.d.ts +0 -4
- package/lib/pipes/gt-meta.pipe.d.ts +0 -5
- package/lib/pipes/gt-order-by.pipe.d.ts +0 -11
- package/lib/pipes/gt-property.pipe.d.ts +0 -7
- package/lib/pipes/gt-render.pipe.d.ts +0 -19
- package/lib/pipes/gt-row-class.pipe.d.ts +0 -5
- package/lib/pipes/gt-search.pipe.d.ts +0 -10
- package/lib/pipes/gt-totals-position.pipe.d.ts +0 -5
- package/lib/pipes/gt-totals.pipe.d.ts +0 -4
- package/lib/pipes/gt-visible.pipe.d.ts +0 -9
- package/public_api.d.ts +0 -18
- package/scss/generic-table.scss +0 -246
|
@@ -1,1813 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* @fileoverview added by tsickle
|
|
3
|
-
* @suppress {checkTypes} checked by tsc
|
|
4
|
-
*/
|
|
5
|
-
import * as tslib_1 from "tslib";
|
|
6
|
-
import { Component, EventEmitter, Input, Output, Renderer2, Type } from '@angular/core';
|
|
7
|
-
import { GtMetaPipe } from '../../pipes/gt-meta.pipe';
|
|
8
|
-
// unsupported: template constraints.
|
|
9
|
-
// unsupported: template constraints.
|
|
10
|
-
/**
|
|
11
|
-
* @template R, C
|
|
12
|
-
*/
|
|
13
|
-
var GenericTableComponent = /** @class */ (function () {
|
|
14
|
-
function GenericTableComponent(renderer, gtMetaPipe) {
|
|
15
|
-
var _this = this;
|
|
16
|
-
this.renderer = renderer;
|
|
17
|
-
this.gtMetaPipe = gtMetaPipe;
|
|
18
|
-
this.columnWidth = {};
|
|
19
|
-
this.sortOrder = [];
|
|
20
|
-
this.metaInfo = {};
|
|
21
|
-
this.selectedRows = [];
|
|
22
|
-
this.openRows = [];
|
|
23
|
-
this._gtSettings = [];
|
|
24
|
-
this._gtFields = [];
|
|
25
|
-
this.gtDefaultTexts = {
|
|
26
|
-
loading: 'Loading...',
|
|
27
|
-
noData: 'No data',
|
|
28
|
-
noMatchingData: 'No data matching results found',
|
|
29
|
-
noVisibleColumnsHeading: 'No visible columns',
|
|
30
|
-
noVisibleColumns: 'Please select at least one column to be visible.',
|
|
31
|
-
tableInfo: 'Showing #recordFrom to #recordTo of #recordsAfterSearch entries.',
|
|
32
|
-
tableInfoAfterSearch: 'Showing #recordFrom to #recordTo of #recordsAfterSearch entries (filtered from a total of #recordsAll entries).',
|
|
33
|
-
csvDownload: 'download',
|
|
34
|
-
sortLabel: 'Sort:',
|
|
35
|
-
paginateNext: 'Next page',
|
|
36
|
-
paginatePrevious: 'Previous page',
|
|
37
|
-
inlineEditEdited: 'Press enter to save'
|
|
38
|
-
};
|
|
39
|
-
this.gtTexts = this.gtDefaultTexts;
|
|
40
|
-
this.gtEvent = new EventEmitter();
|
|
41
|
-
this.gtDefaultOptions = {
|
|
42
|
-
csvDelimiter: ';',
|
|
43
|
-
stack: false,
|
|
44
|
-
lazyLoad: false,
|
|
45
|
-
cache: false,
|
|
46
|
-
debounceTime: 200,
|
|
47
|
-
highlightSearch: false,
|
|
48
|
-
rowSelection: false,
|
|
49
|
-
rowSelectionAllowMultiple: true,
|
|
50
|
-
rowExpandAllowMultiple: true,
|
|
51
|
-
numberOfRows: 10,
|
|
52
|
-
reportColumnWidth: false,
|
|
53
|
-
allowUnsorted: true,
|
|
54
|
-
mutateData: true
|
|
55
|
-
};
|
|
56
|
-
this._gtOptions = this.gtDefaultOptions;
|
|
57
|
-
this.store = [];
|
|
58
|
-
this.loading = true;
|
|
59
|
-
this.debounceTimer = null;
|
|
60
|
-
this.lazyAllSelected = false;
|
|
61
|
-
this.gtInfo = {
|
|
62
|
-
pageCurrent: 1,
|
|
63
|
-
pageTotal: 0,
|
|
64
|
-
recordFrom: 0,
|
|
65
|
-
recordTo: 0,
|
|
66
|
-
recordLength: this.gtOptions.numberOfRows,
|
|
67
|
-
recordsAll: 0,
|
|
68
|
-
recordsAfterFilter: 0,
|
|
69
|
-
recordsAfterSearch: 0
|
|
70
|
-
};
|
|
71
|
-
this.refreshPipe = false;
|
|
72
|
-
this.refreshTotals = false;
|
|
73
|
-
this.refreshSorting = false;
|
|
74
|
-
this.refreshFilter = false;
|
|
75
|
-
this.refreshPageArray = false;
|
|
76
|
-
this.editedRows = {};
|
|
77
|
-
this.data = { exportData: [] };
|
|
78
|
-
/**
|
|
79
|
-
* Sort table by object key.
|
|
80
|
-
* @param objectKey - name of key to sort on.
|
|
81
|
-
* @param event - such as key press during sorting.
|
|
82
|
-
*/
|
|
83
|
-
this.gtSort = function (objectKey, event) {
|
|
84
|
-
this.inlineEditCancel(); // cancel inline editing
|
|
85
|
-
// loop through current settings
|
|
86
|
-
for (var /** @type {?} */ i = 0; i < this._gtSettings.length; i++) {
|
|
87
|
-
if (this._gtSettings[i].objectKey === objectKey) {
|
|
88
|
-
// check if sorting is disabled...
|
|
89
|
-
if (this._gtSettings[i].sort &&
|
|
90
|
-
this._gtSettings[i].sort.indexOf('disable') !== -1) {
|
|
91
|
-
// ...if so, exit function without applying any sorting
|
|
92
|
-
return;
|
|
93
|
-
}
|
|
94
|
-
else if (/* check if sorting is undefined... */ typeof this._gtSettings[i]
|
|
95
|
-
.sort === 'undefined') {
|
|
96
|
-
// ...is so, set sorting property to enable
|
|
97
|
-
this._gtSettings[i].sort = 'enable';
|
|
98
|
-
}
|
|
99
|
-
}
|
|
100
|
-
}
|
|
101
|
-
// check length
|
|
102
|
-
var /** @type {?} */ ctrlKey = event.metaKey || event.ctrlKey;
|
|
103
|
-
var /** @type {?} */ sort = this.sortOrder.slice(0);
|
|
104
|
-
var /** @type {?} */ match = -1;
|
|
105
|
-
var /** @type {?} */ matchDesc = -1;
|
|
106
|
-
var /** @type {?} */ pos = -1;
|
|
107
|
-
// check if property already exits
|
|
108
|
-
for (var /** @type {?} */ i = 0; i < sort.length; i++) {
|
|
109
|
-
var /** @type {?} */ hit = sort[i].indexOf(objectKey);
|
|
110
|
-
if (hit !== -1) {
|
|
111
|
-
match = this.sortOrder.indexOf(objectKey);
|
|
112
|
-
matchDesc =
|
|
113
|
-
match === -1 ? this.sortOrder.indexOf('-' + objectKey) : match;
|
|
114
|
-
pos = Math.max(match, matchDesc);
|
|
115
|
-
}
|
|
116
|
-
}
|
|
117
|
-
// if ctrl key or meta key is press together with sort...
|
|
118
|
-
if (ctrlKey) {
|
|
119
|
-
if (this.sortOrder[this.sortOrder.length - 1] === '$$gtInitialRowIndex') {
|
|
120
|
-
this.sortOrder.pop();
|
|
121
|
-
}
|
|
122
|
-
switch (pos) {
|
|
123
|
-
// ...and property is not sorted before...
|
|
124
|
-
case -1:
|
|
125
|
-
// ...add property to sorting
|
|
126
|
-
this.sortOrder.push(objectKey);
|
|
127
|
-
break;
|
|
128
|
-
default:
|
|
129
|
-
// ...and property is sorted before...
|
|
130
|
-
if (match !== -1) {
|
|
131
|
-
// ...change from asc to desc if sorted asc
|
|
132
|
-
this.sortOrder[pos] = '-' + objectKey;
|
|
133
|
-
}
|
|
134
|
-
else if (this.sortOrder.length > 1) {
|
|
135
|
-
// ...remove sorting if sorted desc
|
|
136
|
-
if (ctrlKey) {
|
|
137
|
-
this.sortOrder[pos] = objectKey;
|
|
138
|
-
}
|
|
139
|
-
else {
|
|
140
|
-
this.sortOrder.splice(pos, 1);
|
|
141
|
-
}
|
|
142
|
-
}
|
|
143
|
-
else if (this.sortOrder.length === 1) {
|
|
144
|
-
// ...set sorting to asc if only sorted property
|
|
145
|
-
this.sortOrder[pos] = objectKey;
|
|
146
|
-
}
|
|
147
|
-
break;
|
|
148
|
-
}
|
|
149
|
-
}
|
|
150
|
-
else {
|
|
151
|
-
/* if ctrl key or meta key is not press together with sort... */
|
|
152
|
-
switch (pos) {
|
|
153
|
-
// ...and property is not sorted before...
|
|
154
|
-
case -1:
|
|
155
|
-
// ...sort by property
|
|
156
|
-
this.sortOrder = [objectKey];
|
|
157
|
-
break;
|
|
158
|
-
default:
|
|
159
|
-
// ...change from desc to asc and vise versa
|
|
160
|
-
this.sortOrder =
|
|
161
|
-
match !== -1
|
|
162
|
-
? ['-' + objectKey]
|
|
163
|
-
: ctrlKey || !this.gtOptions.allowUnsorted
|
|
164
|
-
? [objectKey]
|
|
165
|
-
: [];
|
|
166
|
-
break;
|
|
167
|
-
}
|
|
168
|
-
}
|
|
169
|
-
// update settings object with new sorting information
|
|
170
|
-
for (var /** @type {?} */ i = 0; i < this._gtSettings.length; i++) {
|
|
171
|
-
if (this._gtSettings[i].objectKey === objectKey) {
|
|
172
|
-
switch (this._gtSettings[i].sort) {
|
|
173
|
-
// if sorted asc...
|
|
174
|
-
case 'asc':
|
|
175
|
-
// ...change to desc
|
|
176
|
-
this._gtSettings[i].sort = 'desc';
|
|
177
|
-
break;
|
|
178
|
-
// if sorted desc...
|
|
179
|
-
case 'desc':
|
|
180
|
-
// ...change to asc if it's the only sorted property otherwise remove sorting
|
|
181
|
-
this._gtSettings[i].sort =
|
|
182
|
-
(this.sortOrder.length === 1 && sort.length < 2) ||
|
|
183
|
-
ctrlKey ||
|
|
184
|
-
!this.gtOptions.allowUnsorted
|
|
185
|
-
? 'asc'
|
|
186
|
-
: 'enable';
|
|
187
|
-
break;
|
|
188
|
-
// if sorting enabled...
|
|
189
|
-
case 'enable':
|
|
190
|
-
// ...change to asc
|
|
191
|
-
this._gtSettings[i].sort = 'asc';
|
|
192
|
-
break;
|
|
193
|
-
}
|
|
194
|
-
this._gtSettings[i].sortOrder =
|
|
195
|
-
this._gtSettings[i].sort === 'enable'
|
|
196
|
-
? this._gtSettings.length - 1
|
|
197
|
-
: this.sortOrder.indexOf(objectKey) === -1
|
|
198
|
-
? this.sortOrder.indexOf('-' + objectKey)
|
|
199
|
-
: this.sortOrder.indexOf(objectKey);
|
|
200
|
-
}
|
|
201
|
-
else if (this._gtSettings[i].sort &&
|
|
202
|
-
this._gtSettings[i].sort.indexOf('disable') === -1 &&
|
|
203
|
-
this.sortOrder.indexOf(this._gtSettings[i].objectKey) === -1 &&
|
|
204
|
-
this.sortOrder.indexOf('-' + this._gtSettings[i].objectKey) === -1) {
|
|
205
|
-
this._gtSettings[i].sort = 'enable';
|
|
206
|
-
this._gtSettings[i].sortOrder = this._gtSettings.length - 1;
|
|
207
|
-
}
|
|
208
|
-
}
|
|
209
|
-
// refresh sorting pipe
|
|
210
|
-
this.refreshSorting = !this.refreshSorting;
|
|
211
|
-
this.refreshPageArray = !this.refreshPageArray;
|
|
212
|
-
// sort by initial sort order as last resort
|
|
213
|
-
this.sortOrder.push('$$gtInitialRowIndex');
|
|
214
|
-
// emit sort event
|
|
215
|
-
this.gtEvent.emit({
|
|
216
|
-
name: 'gt-sorting-applied',
|
|
217
|
-
value: this.sortOrder
|
|
218
|
-
});
|
|
219
|
-
};
|
|
220
|
-
/**
|
|
221
|
-
* Change number of rows to be displayed.
|
|
222
|
-
* @param rowLength - total number of rows.
|
|
223
|
-
* @param reset - should page be reset to first page.
|
|
224
|
-
*/
|
|
225
|
-
this.changeRowLength = function (rowLength, reset) {
|
|
226
|
-
var /** @type {?} */ lengthValue = isNaN(parseInt(rowLength, 10))
|
|
227
|
-
? 0
|
|
228
|
-
: parseInt(rowLength, 10);
|
|
229
|
-
var /** @type {?} */ newPosition = 1;
|
|
230
|
-
if (!lengthValue && this.gtData) {
|
|
231
|
-
lengthValue = this.gtData.length;
|
|
232
|
-
}
|
|
233
|
-
// if reset is not true and we're not lazy loading data...
|
|
234
|
-
if (reset !== true && this._gtOptions.lazyLoad !== true) {
|
|
235
|
-
// ...get current position in record set
|
|
236
|
-
var /** @type {?} */ currentRecord = this.gtInfo.recordLength * (this.gtInfo.pageCurrent - 1);
|
|
237
|
-
var /** @type {?} */ currentPosition = this._gtData.indexOf(this._gtData[currentRecord]) + 1;
|
|
238
|
-
// ...get new position
|
|
239
|
-
newPosition = Math.ceil(currentPosition / lengthValue);
|
|
240
|
-
}
|
|
241
|
-
// change row length
|
|
242
|
-
this.gtInfo.recordLength = lengthValue;
|
|
243
|
-
// go to new position
|
|
244
|
-
this.gtInfo.pageCurrent = newPosition;
|
|
245
|
-
// if lazy loading data...
|
|
246
|
-
if (this._gtOptions.lazyLoad) {
|
|
247
|
-
// ...replace data with place holders for new data
|
|
248
|
-
this._gtData[0] = this.loadingContent(lengthValue);
|
|
249
|
-
// ...empty current store
|
|
250
|
-
this.store = [];
|
|
251
|
-
}
|
|
252
|
-
// this.updateRecordRange();
|
|
253
|
-
this.gtEvent.emit({
|
|
254
|
-
name: 'gt-row-length-changed',
|
|
255
|
-
value: lengthValue
|
|
256
|
-
});
|
|
257
|
-
};
|
|
258
|
-
/**
|
|
259
|
-
* Force a redraw of table rows.
|
|
260
|
-
* As the table uses pure pipes, we need to force a redraw if an object in the array is changed to see the changes.
|
|
261
|
-
*/
|
|
262
|
-
this.redraw = function ($event) {
|
|
263
|
-
this.refreshSorting = !this.refreshSorting;
|
|
264
|
-
this.refreshPageArray = !this.refreshPageArray;
|
|
265
|
-
this.refreshPipe = !this.refreshPipe;
|
|
266
|
-
};
|
|
267
|
-
/**
|
|
268
|
-
* Go to next page.
|
|
269
|
-
*/
|
|
270
|
-
this.nextPage = function () {
|
|
271
|
-
var /** @type {?} */ page = this.gtInfo.pageCurrent === this.gtInfo.pageTotal
|
|
272
|
-
? this.gtInfo.pageTotal
|
|
273
|
-
: this.gtInfo.pageCurrent + 1;
|
|
274
|
-
this.goToPage(page);
|
|
275
|
-
};
|
|
276
|
-
/**
|
|
277
|
-
* Go to previous page.
|
|
278
|
-
*/
|
|
279
|
-
this.previousPage = function () {
|
|
280
|
-
var /** @type {?} */ page = this.gtInfo.pageCurrent === 1 ? 1 : this.gtInfo.pageCurrent - 1;
|
|
281
|
-
this.goToPage(page);
|
|
282
|
-
};
|
|
283
|
-
/**
|
|
284
|
-
* Request more data (used when lazy loading)
|
|
285
|
-
*/
|
|
286
|
-
this.getData = function () {
|
|
287
|
-
// ...emit event requesting for more data
|
|
288
|
-
this.gtEvent.emit({
|
|
289
|
-
name: 'gt-page-changed-lazy',
|
|
290
|
-
value: {
|
|
291
|
-
pageCurrent: this.gtInfo.pageCurrent,
|
|
292
|
-
recordLength: this.gtInfo.recordLength
|
|
293
|
-
}
|
|
294
|
-
});
|
|
295
|
-
};
|
|
296
|
-
/**
|
|
297
|
-
* Go to specific page.
|
|
298
|
-
* @param page - page number.
|
|
299
|
-
*/
|
|
300
|
-
this.goToPage = function (page) {
|
|
301
|
-
var _this = this;
|
|
302
|
-
var /** @type {?} */ previousPage = this.gtInfo.pageCurrent;
|
|
303
|
-
this.gtInfo.pageCurrent = page;
|
|
304
|
-
this.inlineEditCancel(); // cancel inline edit
|
|
305
|
-
// if lazy loading and if page contains no records...
|
|
306
|
-
if (this._gtOptions.lazyLoad) {
|
|
307
|
-
// ...if data for current page contains no entries...
|
|
308
|
-
if (this._gtOptions.cache === false ||
|
|
309
|
-
this._gtData[this.gtInfo.pageCurrent - 1].length === 0) {
|
|
310
|
-
// ...create temporary content while waiting for data
|
|
311
|
-
this._gtData[this.gtInfo.pageCurrent - 1] = this.loadingContent(this.gtInfo.recordLength);
|
|
312
|
-
this.loading = true; // loading true
|
|
313
|
-
}
|
|
314
|
-
// ...if first entry in current page equals our loading placeholder...
|
|
315
|
-
if (this._gtData[this.gtInfo.pageCurrent - 1][0][this.loadingProperty] ===
|
|
316
|
-
this.gtTexts.loading) {
|
|
317
|
-
// ...get data
|
|
318
|
-
clearTimeout(this.debounceTimer);
|
|
319
|
-
this.debounceTimer = setTimeout(function () {
|
|
320
|
-
_this.getData();
|
|
321
|
-
}, this._gtOptions.debounceTime);
|
|
322
|
-
}
|
|
323
|
-
}
|
|
324
|
-
// this.updateRecordRange();
|
|
325
|
-
// ...emit page change event
|
|
326
|
-
if (previousPage !== page) {
|
|
327
|
-
this.gtEvent.emit({
|
|
328
|
-
name: 'gt-page-changed',
|
|
329
|
-
value: {
|
|
330
|
-
pageCurrent: this.gtInfo.pageCurrent,
|
|
331
|
-
pagePrevious: previousPage,
|
|
332
|
-
recordLength: this.gtInfo.recordLength
|
|
333
|
-
}
|
|
334
|
-
});
|
|
335
|
-
}
|
|
336
|
-
};
|
|
337
|
-
/**
|
|
338
|
-
* Sort by sort order
|
|
339
|
-
*/
|
|
340
|
-
this.getSortOrder = function (a, b) {
|
|
341
|
-
if (a.sortOrder < b.sortOrder) {
|
|
342
|
-
return -1;
|
|
343
|
-
}
|
|
344
|
-
if (a.sortOrder > b.sortOrder || typeof a.sortOrder === 'undefined') {
|
|
345
|
-
return 1;
|
|
346
|
-
}
|
|
347
|
-
return 0;
|
|
348
|
-
};
|
|
349
|
-
/**
|
|
350
|
-
* Sort by column order
|
|
351
|
-
*/
|
|
352
|
-
this.getColumnOrder = function (a, b) {
|
|
353
|
-
if (a.columnOrder === undefined) {
|
|
354
|
-
return -1;
|
|
355
|
-
}
|
|
356
|
-
if (a.columnOrder < b.columnOrder) {
|
|
357
|
-
return -1;
|
|
358
|
-
}
|
|
359
|
-
if (a.columnOrder > b.columnOrder) {
|
|
360
|
-
return 1;
|
|
361
|
-
}
|
|
362
|
-
return 0;
|
|
363
|
-
};
|
|
364
|
-
/**
|
|
365
|
-
* Create a deep copy of data
|
|
366
|
-
*/
|
|
367
|
-
this.cloneDeep = function (o) {
|
|
368
|
-
return JSON.parse(JSON.stringify(o));
|
|
369
|
-
};
|
|
370
|
-
/**
|
|
371
|
-
* Return property
|
|
372
|
-
*/
|
|
373
|
-
this.getProperty = function (array, key) {
|
|
374
|
-
for (var /** @type {?} */ i = 0; i < array.length; i++) {
|
|
375
|
-
if (array[i].objectKey === key) {
|
|
376
|
-
return array[i];
|
|
377
|
-
}
|
|
378
|
-
}
|
|
379
|
-
};
|
|
380
|
-
this.restructureSorting = function () {
|
|
381
|
-
/**
|
|
382
|
-
* Check and store sort order upon initialization.
|
|
383
|
-
* This is done by checking sort properties in the settings array of the table, if no sorting is defined
|
|
384
|
-
* we'll sort the data by the first visible and enabled column in the table(ascending). Please note that actually
|
|
385
|
-
* sorting have to be done server side when lazy loading data for obvious reasons.
|
|
386
|
-
*/
|
|
387
|
-
var /** @type {?} */ sorting = [];
|
|
388
|
-
if (this._gtSettings) {
|
|
389
|
-
// ...sort settings by sort order
|
|
390
|
-
this._gtSettings.sort(this.getSortOrder);
|
|
391
|
-
// ...loop through settings
|
|
392
|
-
for (var /** @type {?} */ i = 0; i < this._gtSettings.length; i++) {
|
|
393
|
-
var /** @type {?} */ setting = this._gtSettings[i];
|
|
394
|
-
// ...if sorted ascending...
|
|
395
|
-
if (setting.sort === 'asc') {
|
|
396
|
-
// ... add to sorting
|
|
397
|
-
sorting.push(setting.objectKey);
|
|
398
|
-
}
|
|
399
|
-
else if (setting.sort === 'desc') {
|
|
400
|
-
/* ...else if sorted descending... */
|
|
401
|
-
// ... add to sorting
|
|
402
|
-
sorting.push('-' + setting.objectKey);
|
|
403
|
-
}
|
|
404
|
-
}
|
|
405
|
-
// ...if no sorting applied...
|
|
406
|
-
if (sorting.length === 0) {
|
|
407
|
-
sorting.push('$$gtRowId');
|
|
408
|
-
/*// ...sort settings by column order
|
|
409
|
-
this._gtSettings.sort(this.getColumnOrder);
|
|
410
|
-
|
|
411
|
-
// ...loop through settings
|
|
412
|
-
for (let i = 0; i < this._gtSettings.length; i++) {
|
|
413
|
-
const setting = this._gtSettings[i];
|
|
414
|
-
|
|
415
|
-
// ...if column is enabled and visible...
|
|
416
|
-
if (setting.enabled !== false && setting.visible !== false) {
|
|
417
|
-
// ...add first match and exit function
|
|
418
|
-
this.sortOrder = [this._gtSettings[i].objectKey];
|
|
419
|
-
return;
|
|
420
|
-
}
|
|
421
|
-
}*/
|
|
422
|
-
}
|
|
423
|
-
}
|
|
424
|
-
if (this.sortOrder.length === 0) {
|
|
425
|
-
this.sortOrder = sorting;
|
|
426
|
-
}
|
|
427
|
-
};
|
|
428
|
-
/**
|
|
429
|
-
* Extend object function.
|
|
430
|
-
*/
|
|
431
|
-
this.extend = function (a, b) {
|
|
432
|
-
for (var /** @type {?} */ key in b) {
|
|
433
|
-
if (b.hasOwnProperty(key)) {
|
|
434
|
-
a[key] = b[key];
|
|
435
|
-
}
|
|
436
|
-
}
|
|
437
|
-
return a;
|
|
438
|
-
};
|
|
439
|
-
this.gtEvent.subscribe(function ($event) {
|
|
440
|
-
if ($event.name === 'gt-info') {
|
|
441
|
-
_this.updateRecordRange();
|
|
442
|
-
}
|
|
443
|
-
if ($event.name === 'gt-row-updated') {
|
|
444
|
-
_this.updateTotals();
|
|
445
|
-
}
|
|
446
|
-
});
|
|
447
|
-
}
|
|
448
|
-
Object.defineProperty(GenericTableComponent.prototype, "gtRowComponent", {
|
|
449
|
-
get: /**
|
|
450
|
-
* @return {?}
|
|
451
|
-
*/
|
|
452
|
-
function () {
|
|
453
|
-
return this._gtRowComponent;
|
|
454
|
-
},
|
|
455
|
-
set: /**
|
|
456
|
-
* @param {?} value
|
|
457
|
-
* @return {?}
|
|
458
|
-
*/
|
|
459
|
-
function (value) {
|
|
460
|
-
console.warn('GtRowComponent has been deprecated and support will be removed in a future release, see https://github.com/hjalmers/angular-generic-table/issues/34');
|
|
461
|
-
this._gtRowComponent = value;
|
|
462
|
-
},
|
|
463
|
-
enumerable: true,
|
|
464
|
-
configurable: true
|
|
465
|
-
});
|
|
466
|
-
Object.defineProperty(GenericTableComponent.prototype, "hasEdits", {
|
|
467
|
-
get: /**
|
|
468
|
-
* @return {?}
|
|
469
|
-
*/
|
|
470
|
-
function () {
|
|
471
|
-
return Object.keys(this.editedRows).length > 0;
|
|
472
|
-
},
|
|
473
|
-
enumerable: true,
|
|
474
|
-
configurable: true
|
|
475
|
-
});
|
|
476
|
-
Object.defineProperty(GenericTableComponent.prototype, "gtOptions", {
|
|
477
|
-
get: /**
|
|
478
|
-
* @return {?}
|
|
479
|
-
*/
|
|
480
|
-
function () {
|
|
481
|
-
return this._gtOptions;
|
|
482
|
-
},
|
|
483
|
-
set: /**
|
|
484
|
-
* @param {?} value
|
|
485
|
-
* @return {?}
|
|
486
|
-
*/
|
|
487
|
-
function (value) {
|
|
488
|
-
this._gtOptions = value;
|
|
489
|
-
// if number of rows is passed and if number of rows differs from current record length...
|
|
490
|
-
if (this.gtOptions.numberOfRows &&
|
|
491
|
-
this.gtInfo.recordLength !== this.gtOptions.numberOfRows) {
|
|
492
|
-
// ...update record length and redraw table
|
|
493
|
-
this.gtInfo.recordLength = this.gtOptions.numberOfRows;
|
|
494
|
-
this.redraw();
|
|
495
|
-
}
|
|
496
|
-
// ...extend gtOptions default values with values passed into component
|
|
497
|
-
this._gtOptions = /** @type {?} */ (this.extend(this.gtDefaultOptions, this._gtOptions));
|
|
498
|
-
},
|
|
499
|
-
enumerable: true,
|
|
500
|
-
configurable: true
|
|
501
|
-
});
|
|
502
|
-
Object.defineProperty(GenericTableComponent.prototype, "gtTotals", {
|
|
503
|
-
get: /**
|
|
504
|
-
* @return {?}
|
|
505
|
-
*/
|
|
506
|
-
function () {
|
|
507
|
-
return this._gtTotals;
|
|
508
|
-
},
|
|
509
|
-
set: /**
|
|
510
|
-
* @param {?} value
|
|
511
|
-
* @return {?}
|
|
512
|
-
*/
|
|
513
|
-
function (value) {
|
|
514
|
-
this._gtTotals = value;
|
|
515
|
-
},
|
|
516
|
-
enumerable: true,
|
|
517
|
-
configurable: true
|
|
518
|
-
});
|
|
519
|
-
Object.defineProperty(GenericTableComponent.prototype, "gtFields", {
|
|
520
|
-
get: /**
|
|
521
|
-
* @return {?}
|
|
522
|
-
*/
|
|
523
|
-
function () {
|
|
524
|
-
return this._gtFields;
|
|
525
|
-
},
|
|
526
|
-
set: /**
|
|
527
|
-
* @param {?} value
|
|
528
|
-
* @return {?}
|
|
529
|
-
*/
|
|
530
|
-
function (value) {
|
|
531
|
-
this._gtFields = value;
|
|
532
|
-
var /** @type {?} */ COLUMNS_WITH_CLASS_NAMES = this._gtFields
|
|
533
|
-
.map(function (column) { return column; })
|
|
534
|
-
.filter(function (column) { return column.classNames; });
|
|
535
|
-
// TODO: remove deprecated warning when setting has been removed
|
|
536
|
-
if (COLUMNS_WITH_CLASS_NAMES.length > 0) {
|
|
537
|
-
console.warn('Field setting "classNames" have been deprecated in favor for "columnClass" and will be removed in the future, please update field settings for column with object key: ' +
|
|
538
|
-
COLUMNS_WITH_CLASS_NAMES[0].objectKey);
|
|
539
|
-
}
|
|
540
|
-
},
|
|
541
|
-
enumerable: true,
|
|
542
|
-
configurable: true
|
|
543
|
-
});
|
|
544
|
-
Object.defineProperty(GenericTableComponent.prototype, "gtSettings", {
|
|
545
|
-
get: /**
|
|
546
|
-
* @return {?}
|
|
547
|
-
*/
|
|
548
|
-
function () {
|
|
549
|
-
return this._gtSettings;
|
|
550
|
-
},
|
|
551
|
-
set: /**
|
|
552
|
-
* @param {?} value
|
|
553
|
-
* @return {?}
|
|
554
|
-
*/
|
|
555
|
-
function (value) {
|
|
556
|
-
this._gtSettings = value;
|
|
557
|
-
// loop through current settings
|
|
558
|
-
for (var /** @type {?} */ i = 0; i < this._gtSettings.length; i++) {
|
|
559
|
-
// set sort enabled/disabled setting
|
|
560
|
-
this._gtSettings[i].sortEnabled =
|
|
561
|
-
this._gtSettings[i].sortEnabled !== false
|
|
562
|
-
? (this._gtSettings[i].sortEnabled = !(this._gtSettings[i].sort &&
|
|
563
|
-
this._gtSettings[i].sort.indexOf('disable') !== -1))
|
|
564
|
-
: false;
|
|
565
|
-
// check if sorting is undefined...
|
|
566
|
-
if (typeof this._gtSettings[i].sort === 'undefined') {
|
|
567
|
-
// ...is so, set sorting property to enable
|
|
568
|
-
this._gtSettings[i].sort = 'enable';
|
|
569
|
-
}
|
|
570
|
-
// check if column order is undefined...
|
|
571
|
-
if (typeof this._gtSettings[i].columnOrder === 'undefined' &&
|
|
572
|
-
this._gtSettings[i].enabled !== false) {
|
|
573
|
-
// ...is so, set sorting property to enable
|
|
574
|
-
this._gtSettings[i].columnOrder = this._gtSettings[i - 1]
|
|
575
|
-
? this._gtSettings[i - 1].columnOrder + 1
|
|
576
|
-
: 0;
|
|
577
|
-
}
|
|
578
|
-
// check if column lock settings are undefined...
|
|
579
|
-
if (typeof this._gtSettings[i].lockSettings === 'undefined') {
|
|
580
|
-
// ...if so, set lock settings to false unless field is disabled (enable === false)
|
|
581
|
-
this._gtSettings[i].lockSettings =
|
|
582
|
-
this._gtSettings[i].enabled === false || false;
|
|
583
|
-
}
|
|
584
|
-
}
|
|
585
|
-
this.restructureSorting();
|
|
586
|
-
},
|
|
587
|
-
enumerable: true,
|
|
588
|
-
configurable: true
|
|
589
|
-
});
|
|
590
|
-
Object.defineProperty(GenericTableComponent.prototype, "gtData", {
|
|
591
|
-
get: /**
|
|
592
|
-
* @return {?}
|
|
593
|
-
*/
|
|
594
|
-
function () {
|
|
595
|
-
return this._gtData;
|
|
596
|
-
},
|
|
597
|
-
set: /**
|
|
598
|
-
* @param {?} initialData
|
|
599
|
-
* @return {?}
|
|
600
|
-
*/
|
|
601
|
-
function (initialData) {
|
|
602
|
-
var _this = this;
|
|
603
|
-
var /** @type {?} */ data = this._gtOptions.mutateData
|
|
604
|
-
? tslib_1.__spread(initialData) : this.cloneDeep(initialData);
|
|
605
|
-
if (this.gtOptions.lazyLoad && this.gtInfo) {
|
|
606
|
-
this.gtMetaPipe.transform(data, this.gtOptions.rowIndex, this.gtInfo.pageCurrent - 1, this.gtInfo.recordLength);
|
|
607
|
-
if (this.lazyAllSelected) {
|
|
608
|
-
var /** @type {?} */ UNIQUE_ROWS_1 = this.selectedRows.map(function (row) { return row.$$gtRowId; });
|
|
609
|
-
data.map(function (row) {
|
|
610
|
-
if (UNIQUE_ROWS_1.indexOf(row.$$gtRowId) === -1) {
|
|
611
|
-
_this.selectedRows.push(row);
|
|
612
|
-
}
|
|
613
|
-
});
|
|
614
|
-
this._updateMetaInfo(this.selectedRows, 'isSelected', true);
|
|
615
|
-
}
|
|
616
|
-
}
|
|
617
|
-
else {
|
|
618
|
-
this.gtMetaPipe.transform(data, this.gtOptions.rowIndex);
|
|
619
|
-
}
|
|
620
|
-
if (this.gtOptions.rowSelectionInitialState) {
|
|
621
|
-
data.map(function (row) {
|
|
622
|
-
var /** @type {?} */ selected = typeof _this.gtOptions.rowSelectionInitialState === 'function'
|
|
623
|
-
? _this.gtOptions.rowSelectionInitialState(row)
|
|
624
|
-
: _this.gtOptions.rowSelectionInitialState;
|
|
625
|
-
if (selected) {
|
|
626
|
-
if (typeof _this.metaInfo[row.$$gtRowId] === 'undefined') {
|
|
627
|
-
_this.metaInfo[row.$$gtRowId] = { isSelected: true };
|
|
628
|
-
}
|
|
629
|
-
else {
|
|
630
|
-
_this.metaInfo[row.$$gtRowId].isSelected = true;
|
|
631
|
-
}
|
|
632
|
-
_this.selectedRows.push(row);
|
|
633
|
-
}
|
|
634
|
-
});
|
|
635
|
-
}
|
|
636
|
-
if (this.gtOptions.rowExpandInitialState &&
|
|
637
|
-
this.gtOptions.rowExpandInitialComponent) {
|
|
638
|
-
data.map(function (row) {
|
|
639
|
-
var /** @type {?} */ expanded = typeof _this.gtOptions.rowExpandInitialState === 'function'
|
|
640
|
-
? _this.gtOptions.rowExpandInitialState(row)
|
|
641
|
-
: _this.gtOptions.rowExpandInitialState;
|
|
642
|
-
_this.expandedRow = _this.gtOptions.rowExpandInitialComponent;
|
|
643
|
-
if (expanded) {
|
|
644
|
-
if (typeof _this.metaInfo[row.$$gtRowId] === 'undefined') {
|
|
645
|
-
_this.metaInfo[row.$$gtRowId] = { isOpen: true };
|
|
646
|
-
}
|
|
647
|
-
else {
|
|
648
|
-
_this.metaInfo[row.$$gtRowId].isOpen = true;
|
|
649
|
-
}
|
|
650
|
-
}
|
|
651
|
-
});
|
|
652
|
-
}
|
|
653
|
-
this._gtData = data;
|
|
654
|
-
},
|
|
655
|
-
enumerable: true,
|
|
656
|
-
configurable: true
|
|
657
|
-
});
|
|
658
|
-
/**
|
|
659
|
-
* Update record range.
|
|
660
|
-
* @return {?}
|
|
661
|
-
*/
|
|
662
|
-
GenericTableComponent.prototype.updateRecordRange = /**
|
|
663
|
-
* Update record range.
|
|
664
|
-
* @return {?}
|
|
665
|
-
*/
|
|
666
|
-
function () {
|
|
667
|
-
this.gtInfo.recordFrom =
|
|
668
|
-
this.gtInfo.recordsAfterSearch === 0
|
|
669
|
-
? 0
|
|
670
|
-
: (this.gtInfo.pageCurrent - 1) * this.gtInfo.recordLength + 1;
|
|
671
|
-
this.gtInfo.recordTo =
|
|
672
|
-
this.gtInfo.recordsAfterSearch <
|
|
673
|
-
this.gtInfo.pageCurrent * this.gtInfo.recordLength
|
|
674
|
-
? this.gtInfo.recordsAfterSearch
|
|
675
|
-
: this.gtInfo.pageCurrent * this.gtInfo.recordLength;
|
|
676
|
-
};
|
|
677
|
-
/**
|
|
678
|
-
* Update totals.
|
|
679
|
-
* @return {?}
|
|
680
|
-
*/
|
|
681
|
-
GenericTableComponent.prototype.updateTotals = /**
|
|
682
|
-
* Update totals.
|
|
683
|
-
* @return {?}
|
|
684
|
-
*/
|
|
685
|
-
function () {
|
|
686
|
-
this.refreshTotals = !this.refreshTotals;
|
|
687
|
-
};
|
|
688
|
-
/**
|
|
689
|
-
* Get meta data for row.
|
|
690
|
-
* @param {?} row
|
|
691
|
-
* @return {?}
|
|
692
|
-
*/
|
|
693
|
-
GenericTableComponent.prototype.getRowState = /**
|
|
694
|
-
* Get meta data for row.
|
|
695
|
-
* @param {?} row
|
|
696
|
-
* @return {?}
|
|
697
|
-
*/
|
|
698
|
-
function (row) {
|
|
699
|
-
return typeof this.metaInfo[row.$$gtRowId] === 'undefined'
|
|
700
|
-
? null
|
|
701
|
-
: this.metaInfo[row.$$gtRowId];
|
|
702
|
-
};
|
|
703
|
-
/**
|
|
704
|
-
* Expand all rows.
|
|
705
|
-
* @param {?} expandedRow - component to render when rows are expanded.
|
|
706
|
-
* @return {?}
|
|
707
|
-
*/
|
|
708
|
-
GenericTableComponent.prototype.expandAllRows = /**
|
|
709
|
-
* Expand all rows.
|
|
710
|
-
* @param {?} expandedRow - component to render when rows are expanded.
|
|
711
|
-
* @return {?}
|
|
712
|
-
*/
|
|
713
|
-
function (expandedRow) {
|
|
714
|
-
this.expandedRow = expandedRow;
|
|
715
|
-
this._toggleAllRowProperty('isOpen', true);
|
|
716
|
-
};
|
|
717
|
-
/**
|
|
718
|
-
* Collapse all rows.
|
|
719
|
-
* @return {?}
|
|
720
|
-
*/
|
|
721
|
-
GenericTableComponent.prototype.collapseAllRows = /**
|
|
722
|
-
* Collapse all rows.
|
|
723
|
-
* @return {?}
|
|
724
|
-
*/
|
|
725
|
-
function () {
|
|
726
|
-
this._toggleAllRowProperty('isOpen', false);
|
|
727
|
-
};
|
|
728
|
-
/**
|
|
729
|
-
* Select all rows.
|
|
730
|
-
* @return {?}
|
|
731
|
-
*/
|
|
732
|
-
GenericTableComponent.prototype.selectAllRows = /**
|
|
733
|
-
* Select all rows.
|
|
734
|
-
* @return {?}
|
|
735
|
-
*/
|
|
736
|
-
function () {
|
|
737
|
-
this._toggleAllRowProperty('isSelected', true);
|
|
738
|
-
};
|
|
739
|
-
/**
|
|
740
|
-
* Deselect all rows.
|
|
741
|
-
* @return {?}
|
|
742
|
-
*/
|
|
743
|
-
GenericTableComponent.prototype.deselectAllRows = /**
|
|
744
|
-
* Deselect all rows.
|
|
745
|
-
* @return {?}
|
|
746
|
-
*/
|
|
747
|
-
function () {
|
|
748
|
-
this._toggleAllRowProperty('isSelected', false);
|
|
749
|
-
};
|
|
750
|
-
/**
|
|
751
|
-
* Toggle all rows.
|
|
752
|
-
* @return {?}
|
|
753
|
-
*/
|
|
754
|
-
GenericTableComponent.prototype.toggleAllRows = /**
|
|
755
|
-
* Toggle all rows.
|
|
756
|
-
* @return {?}
|
|
757
|
-
*/
|
|
758
|
-
function () {
|
|
759
|
-
if (this._gtOptions.lazyLoad) {
|
|
760
|
-
if (!this.lazyAllSelected || this.selectedRows.length === 0) {
|
|
761
|
-
this.selectAllRows();
|
|
762
|
-
this.lazyAllSelected = true;
|
|
763
|
-
}
|
|
764
|
-
else {
|
|
765
|
-
this.deselectAllRows();
|
|
766
|
-
this.lazyAllSelected = false;
|
|
767
|
-
}
|
|
768
|
-
}
|
|
769
|
-
else {
|
|
770
|
-
if (this.selectedRows.length !== this.gtData.length) {
|
|
771
|
-
this.selectAllRows();
|
|
772
|
-
}
|
|
773
|
-
else {
|
|
774
|
-
this.deselectAllRows();
|
|
775
|
-
}
|
|
776
|
-
}
|
|
777
|
-
};
|
|
778
|
-
/**
|
|
779
|
-
* Toggle row collapsed state ie. expanded/open or collapsed/closed.
|
|
780
|
-
* @param {?} row - row object that should be expanded/collapsed.
|
|
781
|
-
* @param {?=} expandedRow - component to render when row is expanded.
|
|
782
|
-
* @return {?}
|
|
783
|
-
*/
|
|
784
|
-
GenericTableComponent.prototype.toggleCollapse = /**
|
|
785
|
-
* Toggle row collapsed state ie. expanded/open or collapsed/closed.
|
|
786
|
-
* @param {?} row - row object that should be expanded/collapsed.
|
|
787
|
-
* @param {?=} expandedRow - component to render when row is expanded.
|
|
788
|
-
* @return {?}
|
|
789
|
-
*/
|
|
790
|
-
function (row, expandedRow) {
|
|
791
|
-
if (expandedRow) {
|
|
792
|
-
this.expandedRow = expandedRow;
|
|
793
|
-
}
|
|
794
|
-
this._toggleRowProperty(row, 'isOpen');
|
|
795
|
-
};
|
|
796
|
-
/**
|
|
797
|
-
* Toggle row selected state ie. selected or not.
|
|
798
|
-
* @param {?} row - row object that should be selected/deselected.
|
|
799
|
-
* @return {?}
|
|
800
|
-
*/
|
|
801
|
-
GenericTableComponent.prototype.toggleSelect = /**
|
|
802
|
-
* Toggle row selected state ie. selected or not.
|
|
803
|
-
* @param {?} row - row object that should be selected/deselected.
|
|
804
|
-
* @return {?}
|
|
805
|
-
*/
|
|
806
|
-
function (row) {
|
|
807
|
-
this._toggleRowProperty(row, 'isSelected');
|
|
808
|
-
};
|
|
809
|
-
/**
|
|
810
|
-
* @param {?} row
|
|
811
|
-
* @param {?} $event
|
|
812
|
-
* @return {?}
|
|
813
|
-
*/
|
|
814
|
-
GenericTableComponent.prototype.rowClick = /**
|
|
815
|
-
* @param {?} row
|
|
816
|
-
* @param {?} $event
|
|
817
|
-
* @return {?}
|
|
818
|
-
*/
|
|
819
|
-
function (row, $event) {
|
|
820
|
-
this.gtEvent.emit({
|
|
821
|
-
name: 'gt-row-clicked',
|
|
822
|
-
value: { row: row, event: $event }
|
|
823
|
-
});
|
|
824
|
-
};
|
|
825
|
-
/**
|
|
826
|
-
* Update row data.
|
|
827
|
-
* @param {?} row - row object that has been edited.
|
|
828
|
-
* @param {?} oldValue - row object before edit.
|
|
829
|
-
* @return {?}
|
|
830
|
-
*/
|
|
831
|
-
GenericTableComponent.prototype.updateRow = /**
|
|
832
|
-
* Update row data.
|
|
833
|
-
* @param {?} row - row object that has been edited.
|
|
834
|
-
* @param {?} oldValue - row object before edit.
|
|
835
|
-
* @return {?}
|
|
836
|
-
*/
|
|
837
|
-
function (row, oldValue) {
|
|
838
|
-
this._toggleRowProperty(row, 'isUpdated', oldValue);
|
|
839
|
-
};
|
|
840
|
-
/**
|
|
841
|
-
* removes a row from the table
|
|
842
|
-
* @param {?} row - the row object to remove
|
|
843
|
-
* @return {?}
|
|
844
|
-
*/
|
|
845
|
-
GenericTableComponent.prototype.removeRow = /**
|
|
846
|
-
* removes a row from the table
|
|
847
|
-
* @param {?} row - the row object to remove
|
|
848
|
-
* @return {?}
|
|
849
|
-
*/
|
|
850
|
-
function (row) {
|
|
851
|
-
if (this.isRowSelected(row)) {
|
|
852
|
-
this.toggleSelect(row);
|
|
853
|
-
}
|
|
854
|
-
var /** @type {?} */ index = this._gtData.indexOf(row);
|
|
855
|
-
this._gtData.splice(index, 1);
|
|
856
|
-
};
|
|
857
|
-
/**
|
|
858
|
-
* check if a row is selected
|
|
859
|
-
* @param {?} row - row object
|
|
860
|
-
* @return {?}
|
|
861
|
-
*/
|
|
862
|
-
GenericTableComponent.prototype.isRowSelected = /**
|
|
863
|
-
* check if a row is selected
|
|
864
|
-
* @param {?} row - row object
|
|
865
|
-
* @return {?}
|
|
866
|
-
*/
|
|
867
|
-
function (row) {
|
|
868
|
-
return (this.metaInfo[row.$$gtRowId] && this.metaInfo[row.$$gtRowId].isSelected);
|
|
869
|
-
};
|
|
870
|
-
/**
|
|
871
|
-
* Update meta info for all rows, ie. isSelected, isOpen.
|
|
872
|
-
* @param {?} array - array that holds rows that need to be updated.
|
|
873
|
-
* @param {?} property - name of property that should be changed/toggled.
|
|
874
|
-
* @param {?} active - should rows be expanded/open, selected.
|
|
875
|
-
* @param {?=} exception - update all rows except this one.
|
|
876
|
-
* @return {?}
|
|
877
|
-
*/
|
|
878
|
-
GenericTableComponent.prototype._updateMetaInfo = /**
|
|
879
|
-
* Update meta info for all rows, ie. isSelected, isOpen.
|
|
880
|
-
* @param {?} array - array that holds rows that need to be updated.
|
|
881
|
-
* @param {?} property - name of property that should be changed/toggled.
|
|
882
|
-
* @param {?} active - should rows be expanded/open, selected.
|
|
883
|
-
* @param {?=} exception - update all rows except this one.
|
|
884
|
-
* @return {?}
|
|
885
|
-
*/
|
|
886
|
-
function (array, property, active, exception) {
|
|
887
|
-
for (var /** @type {?} */ i = 0; i < array.length; i++) {
|
|
888
|
-
if (!this.metaInfo[array[i].$$gtRowId]) {
|
|
889
|
-
this.metaInfo[array[i].$$gtRowId] = {};
|
|
890
|
-
}
|
|
891
|
-
if (exception && array[i].$$gtRowId === exception.$$gtRowId) {
|
|
892
|
-
}
|
|
893
|
-
else {
|
|
894
|
-
this.metaInfo[array[i].$$gtRowId][property] = active;
|
|
895
|
-
}
|
|
896
|
-
}
|
|
897
|
-
};
|
|
898
|
-
/**
|
|
899
|
-
* Push selected/expanded lazy loaded rows to array with meta data.
|
|
900
|
-
* @param {?} target - array to which rows should be added.
|
|
901
|
-
* @param {?} source - array that holds rows that should be added.
|
|
902
|
-
* @return {?} array with added rows.
|
|
903
|
-
*/
|
|
904
|
-
GenericTableComponent.prototype._pushLazyRows = /**
|
|
905
|
-
* Push selected/expanded lazy loaded rows to array with meta data.
|
|
906
|
-
* @param {?} target - array to which rows should be added.
|
|
907
|
-
* @param {?} source - array that holds rows that should be added.
|
|
908
|
-
* @return {?} array with added rows.
|
|
909
|
-
*/
|
|
910
|
-
function (target, source) {
|
|
911
|
-
var /** @type {?} */ UNIQUE_ROWS = target.map(function (row) { return row.$$gtRowId; });
|
|
912
|
-
for (var /** @type {?} */ i = 0; i < source.length; i++) {
|
|
913
|
-
// only add if not already in list
|
|
914
|
-
if (UNIQUE_ROWS.indexOf(source[i].$$gtRowId) === -1) {
|
|
915
|
-
target.push(source[i]);
|
|
916
|
-
}
|
|
917
|
-
}
|
|
918
|
-
return target;
|
|
919
|
-
};
|
|
920
|
-
/**
|
|
921
|
-
* Toggle meta info for all rows, ie. isSelected, isOpen.
|
|
922
|
-
* @param {?} property - name of property that should be changed/toggled.
|
|
923
|
-
* @param {?} active - should rows be expanded/open, selected.
|
|
924
|
-
* @return {?}
|
|
925
|
-
*/
|
|
926
|
-
GenericTableComponent.prototype._toggleAllRowProperty = /**
|
|
927
|
-
* Toggle meta info for all rows, ie. isSelected, isOpen.
|
|
928
|
-
* @param {?} property - name of property that should be changed/toggled.
|
|
929
|
-
* @param {?} active - should rows be expanded/open, selected.
|
|
930
|
-
* @return {?}
|
|
931
|
-
*/
|
|
932
|
-
function (property, active) {
|
|
933
|
-
var /** @type {?} */ eventName;
|
|
934
|
-
var /** @type {?} */ eventValue;
|
|
935
|
-
switch (property) {
|
|
936
|
-
case 'isOpen':
|
|
937
|
-
// check if multiple expanded rows are allowed...
|
|
938
|
-
if (this._gtOptions.rowExpandAllowMultiple === false) {
|
|
939
|
-
// ...if not, exit function
|
|
940
|
-
console.log('feature disabled: enable by setting "rowExpandAllowMultiple = true"');
|
|
941
|
-
return;
|
|
942
|
-
}
|
|
943
|
-
if (active) {
|
|
944
|
-
eventName = 'expand-all';
|
|
945
|
-
this.openRows = this._gtOptions.lazyLoad
|
|
946
|
-
? this._pushLazyRows(this.openRows, this._gtData[this.gtInfo.pageCurrent - 1].slice())
|
|
947
|
-
: this._gtData.slice();
|
|
948
|
-
this._updateMetaInfo(this.openRows, property, active);
|
|
949
|
-
}
|
|
950
|
-
else {
|
|
951
|
-
eventName = 'collapse-all';
|
|
952
|
-
this._updateMetaInfo(this.openRows, property, active);
|
|
953
|
-
this.openRows = [];
|
|
954
|
-
}
|
|
955
|
-
eventValue = {
|
|
956
|
-
expandedRows: this.openRows,
|
|
957
|
-
changedRow: 'all'
|
|
958
|
-
};
|
|
959
|
-
break;
|
|
960
|
-
case 'isSelected':
|
|
961
|
-
// check if multi row selection is allowed...
|
|
962
|
-
if (this._gtOptions.rowSelectionAllowMultiple === false) {
|
|
963
|
-
// ...if not, exit function
|
|
964
|
-
console.log('feature disabled: enable by setting "rowSelectionAllowMultiple = true"');
|
|
965
|
-
return;
|
|
966
|
-
}
|
|
967
|
-
if (active) {
|
|
968
|
-
eventName = 'select-all';
|
|
969
|
-
this.selectedRows = this._gtOptions.lazyLoad
|
|
970
|
-
? this._pushLazyRows(this.selectedRows, this._gtData[this.gtInfo.pageCurrent - 1].slice())
|
|
971
|
-
: this._gtData.slice();
|
|
972
|
-
this._updateMetaInfo(this.selectedRows, property, active);
|
|
973
|
-
}
|
|
974
|
-
else {
|
|
975
|
-
eventName = 'deselect-all';
|
|
976
|
-
this._updateMetaInfo(this.selectedRows, property, active);
|
|
977
|
-
this.selectedRows = [];
|
|
978
|
-
}
|
|
979
|
-
eventValue = {
|
|
980
|
-
selectedRows: this.selectedRows,
|
|
981
|
-
changedRow: 'all'
|
|
982
|
-
};
|
|
983
|
-
break;
|
|
984
|
-
}
|
|
985
|
-
this.gtEvent.emit({
|
|
986
|
-
name: 'gt-row-' + eventName,
|
|
987
|
-
value: eventValue
|
|
988
|
-
});
|
|
989
|
-
};
|
|
990
|
-
/**
|
|
991
|
-
* Toggle meta info for row, ie. isSelected, isOpen.
|
|
992
|
-
* @param {?} row - row object.
|
|
993
|
-
* @param {?} property - name of property that should be changed/toggled.
|
|
994
|
-
* @param {?=} propertyValues - optional property values that can be passed.
|
|
995
|
-
* @return {?}
|
|
996
|
-
*/
|
|
997
|
-
GenericTableComponent.prototype._toggleRowProperty = /**
|
|
998
|
-
* Toggle meta info for row, ie. isSelected, isOpen.
|
|
999
|
-
* @param {?} row - row object.
|
|
1000
|
-
* @param {?} property - name of property that should be changed/toggled.
|
|
1001
|
-
* @param {?=} propertyValues - optional property values that can be passed.
|
|
1002
|
-
* @return {?}
|
|
1003
|
-
*/
|
|
1004
|
-
function (row, property, propertyValues) {
|
|
1005
|
-
var /** @type {?} */ eventName;
|
|
1006
|
-
var /** @type {?} */ eventValue;
|
|
1007
|
-
// make sure gtRowId exists on row object
|
|
1008
|
-
if (typeof row.$$gtRowId !== 'undefined') {
|
|
1009
|
-
// check if meta info exists for row
|
|
1010
|
-
if (!this.metaInfo[row.$$gtRowId]) {
|
|
1011
|
-
// if not, add object to store meta info
|
|
1012
|
-
this.metaInfo[row.$$gtRowId] = {};
|
|
1013
|
-
}
|
|
1014
|
-
switch (property) {
|
|
1015
|
-
case 'isOpen':
|
|
1016
|
-
var /** @type {?} */ opened = this.metaInfo[row.$$gtRowId][property];
|
|
1017
|
-
// check if multiple expanded rows are allowed...
|
|
1018
|
-
if (this._gtOptions.rowExpandAllowMultiple === false) {
|
|
1019
|
-
// ...if not, collapse all rows except current row
|
|
1020
|
-
this._updateMetaInfo(this.openRows, property, false, row);
|
|
1021
|
-
this.openRows = [];
|
|
1022
|
-
}
|
|
1023
|
-
// check if row is expanded
|
|
1024
|
-
if (!opened) {
|
|
1025
|
-
eventName = 'expand';
|
|
1026
|
-
// add row to expanded rows
|
|
1027
|
-
this.openRows.push(row);
|
|
1028
|
-
}
|
|
1029
|
-
else {
|
|
1030
|
-
eventName = 'collapse';
|
|
1031
|
-
// loop through expanded rows...
|
|
1032
|
-
for (var /** @type {?} */ i = 0; i < this.openRows.length; i++) {
|
|
1033
|
-
// if expanded row equals passed row...
|
|
1034
|
-
if (this.openRows[i].$$gtRowId === row.$$gtRowId) {
|
|
1035
|
-
// ...remove row from expanded rows...
|
|
1036
|
-
this.openRows.splice(i, 1);
|
|
1037
|
-
// ...and exit loop
|
|
1038
|
-
break;
|
|
1039
|
-
}
|
|
1040
|
-
}
|
|
1041
|
-
}
|
|
1042
|
-
eventValue = {
|
|
1043
|
-
expandedRows: this.openRows,
|
|
1044
|
-
changedRow: row
|
|
1045
|
-
};
|
|
1046
|
-
break;
|
|
1047
|
-
case 'isSelected':
|
|
1048
|
-
var /** @type {?} */ selected = this.metaInfo[row.$$gtRowId][property];
|
|
1049
|
-
// check if multi row selection is allowed...
|
|
1050
|
-
if (this._gtOptions.rowSelectionAllowMultiple === false) {
|
|
1051
|
-
// ...if not, deselect all rows except current row
|
|
1052
|
-
this._updateMetaInfo(this.selectedRows, property, false, row);
|
|
1053
|
-
this.selectedRows = [];
|
|
1054
|
-
}
|
|
1055
|
-
// check if row is selected
|
|
1056
|
-
if (!selected) {
|
|
1057
|
-
eventName = 'select';
|
|
1058
|
-
// add row to selected rows
|
|
1059
|
-
this.selectedRows.push(row);
|
|
1060
|
-
}
|
|
1061
|
-
else {
|
|
1062
|
-
if (this.gtOptions.lazyLoad && this.lazyAllSelected) {
|
|
1063
|
-
this.lazyAllSelected = false;
|
|
1064
|
-
}
|
|
1065
|
-
eventName = 'deselect';
|
|
1066
|
-
// loop through selected rows...
|
|
1067
|
-
for (var /** @type {?} */ i = 0; i < this.selectedRows.length; i++) {
|
|
1068
|
-
// if selected row equals passed row...
|
|
1069
|
-
if (this.selectedRows[i].$$gtRowId === row.$$gtRowId) {
|
|
1070
|
-
// ...remove row from selected rows...
|
|
1071
|
-
this.selectedRows.splice(i, 1);
|
|
1072
|
-
// ...and exit loop
|
|
1073
|
-
break;
|
|
1074
|
-
}
|
|
1075
|
-
}
|
|
1076
|
-
}
|
|
1077
|
-
eventValue = {
|
|
1078
|
-
selectedRows: this.selectedRows,
|
|
1079
|
-
changedRow: row
|
|
1080
|
-
};
|
|
1081
|
-
break;
|
|
1082
|
-
case 'isUpdated':
|
|
1083
|
-
eventName = 'updated';
|
|
1084
|
-
var /** @type {?} */ oldValue = propertyValues;
|
|
1085
|
-
// check if edit object exists for row
|
|
1086
|
-
if (typeof this.metaInfo[row.$$gtRowId][property] === 'undefined') {
|
|
1087
|
-
this.metaInfo[row.$$gtRowId][property] = {
|
|
1088
|
-
originalValue: oldValue,
|
|
1089
|
-
oldValue: oldValue,
|
|
1090
|
-
newValue: row
|
|
1091
|
-
};
|
|
1092
|
-
}
|
|
1093
|
-
else {
|
|
1094
|
-
this.metaInfo[row.$$gtRowId][property].oldValue = oldValue;
|
|
1095
|
-
this.metaInfo[row.$$gtRowId][property].newValue = row;
|
|
1096
|
-
}
|
|
1097
|
-
eventValue = this.metaInfo[row.$$gtRowId][property];
|
|
1098
|
-
this.redraw();
|
|
1099
|
-
this.inlineEditCancel(row);
|
|
1100
|
-
// this.gtData = [...this.gtData.map((r) => { return{...r}; })];
|
|
1101
|
-
break;
|
|
1102
|
-
}
|
|
1103
|
-
this.gtEvent.emit({
|
|
1104
|
-
name: 'gt-row-' + eventName,
|
|
1105
|
-
value: eventValue
|
|
1106
|
-
});
|
|
1107
|
-
if (property !== 'isUpdated') {
|
|
1108
|
-
this.metaInfo[row.$$gtRowId][property] = !this.metaInfo[row.$$gtRowId][property];
|
|
1109
|
-
}
|
|
1110
|
-
}
|
|
1111
|
-
};
|
|
1112
|
-
/**
|
|
1113
|
-
* Update column.
|
|
1114
|
-
* @param {?} $event - key up event.
|
|
1115
|
-
* @param {?} row - row object.
|
|
1116
|
-
* @param {?} column - column object.
|
|
1117
|
-
* @return {?}
|
|
1118
|
-
*/
|
|
1119
|
-
GenericTableComponent.prototype.gtUpdateColumn = /**
|
|
1120
|
-
* Update column.
|
|
1121
|
-
* @param {?} $event - key up event.
|
|
1122
|
-
* @param {?} row - row object.
|
|
1123
|
-
* @param {?} column - column object.
|
|
1124
|
-
* @return {?}
|
|
1125
|
-
*/
|
|
1126
|
-
function ($event, row, column) {
|
|
1127
|
-
this._editRow(row, column);
|
|
1128
|
-
};
|
|
1129
|
-
/**
|
|
1130
|
-
* Dropdown select.
|
|
1131
|
-
* @param {?} row - row object.
|
|
1132
|
-
* @param {?} column - column object.
|
|
1133
|
-
* @return {?}
|
|
1134
|
-
*/
|
|
1135
|
-
GenericTableComponent.prototype.gtDropdownSelect = /**
|
|
1136
|
-
* Dropdown select.
|
|
1137
|
-
* @param {?} row - row object.
|
|
1138
|
-
* @param {?} column - column object.
|
|
1139
|
-
* @return {?}
|
|
1140
|
-
*/
|
|
1141
|
-
function (row, column) {
|
|
1142
|
-
var /** @type {?} */ oldValue = tslib_1.__assign({}, row);
|
|
1143
|
-
row[column.objectKey] = column.renderValue;
|
|
1144
|
-
this.updateRow(row, oldValue);
|
|
1145
|
-
};
|
|
1146
|
-
/**
|
|
1147
|
-
* @param {?} row
|
|
1148
|
-
* @param {?} column
|
|
1149
|
-
* @return {?}
|
|
1150
|
-
*/
|
|
1151
|
-
GenericTableComponent.prototype._editRow = /**
|
|
1152
|
-
* @param {?} row
|
|
1153
|
-
* @param {?} column
|
|
1154
|
-
* @return {?}
|
|
1155
|
-
*/
|
|
1156
|
-
function (row, column) {
|
|
1157
|
-
var /** @type {?} */ OBJECT_KEY = column.objectKey; // declare object key which contains changes
|
|
1158
|
-
// check if cell has changed value
|
|
1159
|
-
column.edited = row[column.objectKey] !== column.renderValue;
|
|
1160
|
-
// check if row contains changes...
|
|
1161
|
-
if (!this.editedRows[row.$$gtRowId]) {
|
|
1162
|
-
// if not, create an object for the changed row
|
|
1163
|
-
this.editedRows[row.$$gtRowId] = {
|
|
1164
|
-
changes: {},
|
|
1165
|
-
// create placeholder for changes
|
|
1166
|
-
row: row // store reference to the row that should be updated
|
|
1167
|
-
};
|
|
1168
|
-
}
|
|
1169
|
-
// store changed column under changes if it has been edited
|
|
1170
|
-
if (column.edited) {
|
|
1171
|
-
this.editedRows[row.$$gtRowId].changes[OBJECT_KEY] = column;
|
|
1172
|
-
}
|
|
1173
|
-
else {
|
|
1174
|
-
// delete change object if column is unchanged
|
|
1175
|
-
delete this.editedRows[row.$$gtRowId].changes[OBJECT_KEY];
|
|
1176
|
-
// check how many columns have been changed
|
|
1177
|
-
var /** @type {?} */ CHANGED_COLUMNS = Object.keys(this.editedRows[row.$$gtRowId].changes).length;
|
|
1178
|
-
if (CHANGED_COLUMNS === 0) {
|
|
1179
|
-
// delete row from edited rows if no columns have been edited
|
|
1180
|
-
delete this.editedRows[row.$$gtRowId];
|
|
1181
|
-
}
|
|
1182
|
-
}
|
|
1183
|
-
// if no listener is present...
|
|
1184
|
-
if (!this.globalInlineEditListener) {
|
|
1185
|
-
// ...listen for update event
|
|
1186
|
-
this._listenForKeydownEvent();
|
|
1187
|
-
}
|
|
1188
|
-
};
|
|
1189
|
-
/**
|
|
1190
|
-
* Listen for key down event - listen for key down event during inline edit.
|
|
1191
|
-
* @return {?}
|
|
1192
|
-
*/
|
|
1193
|
-
GenericTableComponent.prototype._listenForKeydownEvent = /**
|
|
1194
|
-
* Listen for key down event - listen for key down event during inline edit.
|
|
1195
|
-
* @return {?}
|
|
1196
|
-
*/
|
|
1197
|
-
function () {
|
|
1198
|
-
var _this = this;
|
|
1199
|
-
// add global listener for key down events
|
|
1200
|
-
this.globalInlineEditListener = this.renderer.listen('document', 'keydown', function ($event) {
|
|
1201
|
-
switch ($event.key) {
|
|
1202
|
-
case 'Enter': // update data object
|
|
1203
|
-
// update data object
|
|
1204
|
-
_this.inlineEditUpdate();
|
|
1205
|
-
break;
|
|
1206
|
-
case 'Escape': // cancel
|
|
1207
|
-
// cancel
|
|
1208
|
-
_this.inlineEditCancel();
|
|
1209
|
-
break;
|
|
1210
|
-
}
|
|
1211
|
-
});
|
|
1212
|
-
};
|
|
1213
|
-
/**
|
|
1214
|
-
* Inline edit update - accept changes and update row values.
|
|
1215
|
-
* @return {?}
|
|
1216
|
-
*/
|
|
1217
|
-
GenericTableComponent.prototype.inlineEditUpdate = /**
|
|
1218
|
-
* Inline edit update - accept changes and update row values.
|
|
1219
|
-
* @return {?}
|
|
1220
|
-
*/
|
|
1221
|
-
function () {
|
|
1222
|
-
var _this = this;
|
|
1223
|
-
// loop through rows that have been edited
|
|
1224
|
-
Object.keys(this.editedRows).map(function (key) {
|
|
1225
|
-
var /** @type {?} */ ROW = _this.editedRows[key].row; // row to update
|
|
1226
|
-
var /** @type {?} */ CHANGES = _this.editedRows[key].changes; // changes to the row
|
|
1227
|
-
// loop through changes in row
|
|
1228
|
-
Object.keys(CHANGES).map(function (objectKey) {
|
|
1229
|
-
var /** @type {?} */ oldValue = tslib_1.__assign({}, ROW);
|
|
1230
|
-
ROW[objectKey] = CHANGES[objectKey].renderValue; // update data value
|
|
1231
|
-
_this.updateRow(ROW, oldValue); // update meta info for row and send event
|
|
1232
|
-
CHANGES[objectKey].edited = false; // disable edit mode
|
|
1233
|
-
});
|
|
1234
|
-
});
|
|
1235
|
-
// clear rows marked as edited as the rows have been updated
|
|
1236
|
-
this.editedRows = {};
|
|
1237
|
-
// remove listener
|
|
1238
|
-
this._stopListeningForKeydownEvent();
|
|
1239
|
-
};
|
|
1240
|
-
/**
|
|
1241
|
-
* Inline edit cancel - cancel and reset inline edits.
|
|
1242
|
-
* @param {?=} row
|
|
1243
|
-
* @return {?}
|
|
1244
|
-
*/
|
|
1245
|
-
GenericTableComponent.prototype.inlineEditCancel = /**
|
|
1246
|
-
* Inline edit cancel - cancel and reset inline edits.
|
|
1247
|
-
* @param {?=} row
|
|
1248
|
-
* @return {?}
|
|
1249
|
-
*/
|
|
1250
|
-
function (row) {
|
|
1251
|
-
var _this = this;
|
|
1252
|
-
if (row) {
|
|
1253
|
-
delete this.editedRows[row.$$gtRowId];
|
|
1254
|
-
// remove listener
|
|
1255
|
-
this._stopListeningForKeydownEvent();
|
|
1256
|
-
return;
|
|
1257
|
-
}
|
|
1258
|
-
// loop through rows that have been edited
|
|
1259
|
-
Object.keys(this.editedRows).map(function (key) {
|
|
1260
|
-
var /** @type {?} */ ROW = _this.editedRows[key].row; // row to update
|
|
1261
|
-
var /** @type {?} */ CHANGES = _this.editedRows[key].changes; // changes to the row
|
|
1262
|
-
// loop through changes in row
|
|
1263
|
-
Object.keys(CHANGES).map(function (objectKey) {
|
|
1264
|
-
CHANGES[objectKey].renderValue = ROW[objectKey]; // reset rendered value
|
|
1265
|
-
CHANGES[objectKey].edited = false; // disable edit mode
|
|
1266
|
-
});
|
|
1267
|
-
});
|
|
1268
|
-
// clear rows marked as edited as the rows have been updated
|
|
1269
|
-
this.editedRows = {};
|
|
1270
|
-
// remove listener
|
|
1271
|
-
this._stopListeningForKeydownEvent();
|
|
1272
|
-
};
|
|
1273
|
-
/**
|
|
1274
|
-
* Stop listening for key down event - stop listening for key down events passed during inline edit.
|
|
1275
|
-
* @return {?}
|
|
1276
|
-
*/
|
|
1277
|
-
GenericTableComponent.prototype._stopListeningForKeydownEvent = /**
|
|
1278
|
-
* Stop listening for key down event - stop listening for key down events passed during inline edit.
|
|
1279
|
-
* @return {?}
|
|
1280
|
-
*/
|
|
1281
|
-
function () {
|
|
1282
|
-
if (this.globalInlineEditListener) {
|
|
1283
|
-
this.globalInlineEditListener();
|
|
1284
|
-
this.globalInlineEditListener = null;
|
|
1285
|
-
}
|
|
1286
|
-
};
|
|
1287
|
-
/**
|
|
1288
|
-
* Apply filter(s).
|
|
1289
|
-
* @param {?} filter - object containing key value pairs, where value should be array of values.
|
|
1290
|
-
* @return {?}
|
|
1291
|
-
*/
|
|
1292
|
-
GenericTableComponent.prototype.gtApplyFilter = /**
|
|
1293
|
-
* Apply filter(s).
|
|
1294
|
-
* @param {?} filter - object containing key value pairs, where value should be array of values.
|
|
1295
|
-
* @return {?}
|
|
1296
|
-
*/
|
|
1297
|
-
function (filter) {
|
|
1298
|
-
this.gtInfo.filter = filter;
|
|
1299
|
-
// go to first page
|
|
1300
|
-
this.goToPage(1);
|
|
1301
|
-
this.updateTotals();
|
|
1302
|
-
};
|
|
1303
|
-
/**
|
|
1304
|
-
* Clear/remove applied filter(s).
|
|
1305
|
-
* @return {?}
|
|
1306
|
-
*/
|
|
1307
|
-
GenericTableComponent.prototype.gtClearFilter = /**
|
|
1308
|
-
* Clear/remove applied filter(s).
|
|
1309
|
-
* @return {?}
|
|
1310
|
-
*/
|
|
1311
|
-
function () {
|
|
1312
|
-
this.gtInfo.filter = false;
|
|
1313
|
-
this.updateTotals();
|
|
1314
|
-
// this.updateRecordRange();
|
|
1315
|
-
};
|
|
1316
|
-
/**
|
|
1317
|
-
* Search
|
|
1318
|
-
* @param {?} value - string containing one or more words
|
|
1319
|
-
* @return {?}
|
|
1320
|
-
*/
|
|
1321
|
-
GenericTableComponent.prototype.gtSearch = /**
|
|
1322
|
-
* Search
|
|
1323
|
-
* @param {?} value - string containing one or more words
|
|
1324
|
-
* @return {?}
|
|
1325
|
-
*/
|
|
1326
|
-
function (value) {
|
|
1327
|
-
this.gtInfo.searchTerms = value;
|
|
1328
|
-
// always go to first page when searching
|
|
1329
|
-
this.goToPage(1);
|
|
1330
|
-
this.updateTotals();
|
|
1331
|
-
};
|
|
1332
|
-
/**
|
|
1333
|
-
* Add rows
|
|
1334
|
-
* @param {?} rows - rows to add
|
|
1335
|
-
* @return {?} new data array.
|
|
1336
|
-
*/
|
|
1337
|
-
GenericTableComponent.prototype.gtAdd = /**
|
|
1338
|
-
* Add rows
|
|
1339
|
-
* @param {?} rows - rows to add
|
|
1340
|
-
* @return {?} new data array.
|
|
1341
|
-
*/
|
|
1342
|
-
function (rows) {
|
|
1343
|
-
this.gtData = tslib_1.__spread(this.gtData, rows);
|
|
1344
|
-
return tslib_1.__spread(this.gtData);
|
|
1345
|
-
};
|
|
1346
|
-
/**
|
|
1347
|
-
* Delete row
|
|
1348
|
-
* @param {?} objectKey - object key you want to find match with
|
|
1349
|
-
* @param {?} value - the value that should be deleted
|
|
1350
|
-
* @param {?=} match - all: delete all matches, first: delete first match (default)
|
|
1351
|
-
* @return {?} new data array.
|
|
1352
|
-
*/
|
|
1353
|
-
GenericTableComponent.prototype.gtDelete = /**
|
|
1354
|
-
* Delete row
|
|
1355
|
-
* @param {?} objectKey - object key you want to find match with
|
|
1356
|
-
* @param {?} value - the value that should be deleted
|
|
1357
|
-
* @param {?=} match - all: delete all matches, first: delete first match (default)
|
|
1358
|
-
* @return {?} new data array.
|
|
1359
|
-
*/
|
|
1360
|
-
function (objectKey, value, match) {
|
|
1361
|
-
if (match === void 0) { match = 'first'; }
|
|
1362
|
-
if (match === 'first') {
|
|
1363
|
-
for (var /** @type {?} */ i = 0; i < this.gtData.length; i++) {
|
|
1364
|
-
if (this.gtData[i][objectKey] === value) {
|
|
1365
|
-
if (this.isRowSelected(this.gtData[i])) {
|
|
1366
|
-
this.toggleSelect(this.gtData[i]);
|
|
1367
|
-
}
|
|
1368
|
-
this.gtData.splice(i, 1);
|
|
1369
|
-
this.gtData = tslib_1.__spread(this.gtData);
|
|
1370
|
-
if (match === 'first') {
|
|
1371
|
-
break;
|
|
1372
|
-
}
|
|
1373
|
-
}
|
|
1374
|
-
}
|
|
1375
|
-
}
|
|
1376
|
-
else {
|
|
1377
|
-
for (var /** @type {?} */ i = this.gtData.length; i > 0; i--) {
|
|
1378
|
-
if (this.gtData[i - 1][objectKey] === value) {
|
|
1379
|
-
if (this.isRowSelected(this.gtData[i - 1])) {
|
|
1380
|
-
this.toggleSelect(this.gtData[i - 1]);
|
|
1381
|
-
}
|
|
1382
|
-
this.gtData.splice(i - 1, 1);
|
|
1383
|
-
this.gtData = tslib_1.__spread(this.gtData);
|
|
1384
|
-
}
|
|
1385
|
-
}
|
|
1386
|
-
}
|
|
1387
|
-
return tslib_1.__spread(this.gtData);
|
|
1388
|
-
};
|
|
1389
|
-
/**
|
|
1390
|
-
* Create store to hold previously loaded records.
|
|
1391
|
-
* @param {?} records - total number of records in store.
|
|
1392
|
-
* @param {?} perPage - how many records to show per page.
|
|
1393
|
-
* @return {?} a nested array to hold records per page.
|
|
1394
|
-
*/
|
|
1395
|
-
GenericTableComponent.prototype.createStore = /**
|
|
1396
|
-
* Create store to hold previously loaded records.
|
|
1397
|
-
* @param {?} records - total number of records in store.
|
|
1398
|
-
* @param {?} perPage - how many records to show per page.
|
|
1399
|
-
* @return {?} a nested array to hold records per page.
|
|
1400
|
-
*/
|
|
1401
|
-
function (records, perPage) {
|
|
1402
|
-
var /** @type {?} */ stores = Math.ceil(records / perPage);
|
|
1403
|
-
var /** @type {?} */ store = [];
|
|
1404
|
-
for (var /** @type {?} */ i = 0; i < stores; i++) {
|
|
1405
|
-
store[i] = [];
|
|
1406
|
-
}
|
|
1407
|
-
return store;
|
|
1408
|
-
};
|
|
1409
|
-
/**
|
|
1410
|
-
* Create placeholders for rows while loading data from back-end.
|
|
1411
|
-
* @param {?} perPage - how many records to show per page.
|
|
1412
|
-
* @return {?} an array containing empty records to be presented while fetching real data.
|
|
1413
|
-
*/
|
|
1414
|
-
GenericTableComponent.prototype.loadingContent = /**
|
|
1415
|
-
* Create placeholders for rows while loading data from back-end.
|
|
1416
|
-
* @param {?} perPage - how many records to show per page.
|
|
1417
|
-
* @return {?} an array containing empty records to be presented while fetching real data.
|
|
1418
|
-
*/
|
|
1419
|
-
function (perPage) {
|
|
1420
|
-
// create row object
|
|
1421
|
-
var /** @type {?} */ rowObject = {
|
|
1422
|
-
$$loading: true
|
|
1423
|
-
};
|
|
1424
|
-
var /** @type {?} */ order = 0;
|
|
1425
|
-
// sort settings by column order
|
|
1426
|
-
this._gtSettings.sort(this.getColumnOrder);
|
|
1427
|
-
// loop through all settings objects...
|
|
1428
|
-
for (var /** @type {?} */ i = 0; i < this._gtSettings.length; i++) {
|
|
1429
|
-
var /** @type {?} */ setting = this._gtSettings[i];
|
|
1430
|
-
// ...if column is visible and enabled...
|
|
1431
|
-
if (setting.visible !== false && setting.enabled !== false) {
|
|
1432
|
-
// ...if first column, set value to loading text otherwise leave it empty
|
|
1433
|
-
if (order === 0) {
|
|
1434
|
-
rowObject[setting.objectKey] = this.gtTexts.loading;
|
|
1435
|
-
this.loadingProperty = setting.objectKey;
|
|
1436
|
-
}
|
|
1437
|
-
else {
|
|
1438
|
-
rowObject[setting.objectKey] = '';
|
|
1439
|
-
}
|
|
1440
|
-
order++;
|
|
1441
|
-
}
|
|
1442
|
-
else {
|
|
1443
|
-
rowObject[setting.objectKey] = '';
|
|
1444
|
-
}
|
|
1445
|
-
}
|
|
1446
|
-
// create content placeholder
|
|
1447
|
-
var /** @type {?} */ contentPlaceholder = [];
|
|
1448
|
-
// create equal number of rows as rows per page
|
|
1449
|
-
for (var /** @type {?} */ i = 0; i < perPage; i++) {
|
|
1450
|
-
// ...add temporary row object
|
|
1451
|
-
contentPlaceholder.push(rowObject);
|
|
1452
|
-
}
|
|
1453
|
-
return contentPlaceholder;
|
|
1454
|
-
};
|
|
1455
|
-
/**
|
|
1456
|
-
* Export data as CSV
|
|
1457
|
-
* @param {?=} fileName - optional file name (overrides default file name).
|
|
1458
|
-
* @param {?=} useBOM - use BOM (byte order marker).
|
|
1459
|
-
* @return {?}
|
|
1460
|
-
*/
|
|
1461
|
-
GenericTableComponent.prototype.exportCSV = /**
|
|
1462
|
-
* Export data as CSV
|
|
1463
|
-
* @param {?=} fileName - optional file name (overrides default file name).
|
|
1464
|
-
* @param {?=} useBOM - use BOM (byte order marker).
|
|
1465
|
-
* @return {?}
|
|
1466
|
-
*/
|
|
1467
|
-
function (fileName, useBOM) {
|
|
1468
|
-
var _this = this;
|
|
1469
|
-
if (useBOM === void 0) { useBOM = false; }
|
|
1470
|
-
var /** @type {?} */ data = this.data.exportData;
|
|
1471
|
-
var /** @type {?} */ csv = '';
|
|
1472
|
-
var /** @type {?} */ BOM = '\uFEFF';
|
|
1473
|
-
// csv export headers
|
|
1474
|
-
for (var /** @type {?} */ i = 0; i < this._gtSettings.length; i++) {
|
|
1475
|
-
if (this._gtSettings[i].export !== false) {
|
|
1476
|
-
csv += this.getProperty(this._gtFields, this._gtSettings[i].objectKey)
|
|
1477
|
-
.name;
|
|
1478
|
-
if (i < this._gtSettings.length - 1) {
|
|
1479
|
-
csv += this._gtOptions.csvDelimiter;
|
|
1480
|
-
}
|
|
1481
|
-
}
|
|
1482
|
-
}
|
|
1483
|
-
// csv export body
|
|
1484
|
-
data.forEach(function (row) {
|
|
1485
|
-
csv += '\n';
|
|
1486
|
-
for (var /** @type {?} */ i = 0; i < _this._gtSettings.length; i++) {
|
|
1487
|
-
if (_this._gtSettings[i].export !== false) {
|
|
1488
|
-
// get field settings
|
|
1489
|
-
var /** @type {?} */ fieldSetting = _this.getProperty(_this._gtFields, _this._gtSettings[i].objectKey);
|
|
1490
|
-
// get export value, if export function is defined use it otherwise check for value function and as a last resort export raw data
|
|
1491
|
-
var /** @type {?} */ exportValue = fieldSetting.export && typeof fieldSetting.export === 'function'
|
|
1492
|
-
? fieldSetting.export(row)
|
|
1493
|
-
: fieldSetting.value && typeof fieldSetting.value === 'function'
|
|
1494
|
-
? fieldSetting.value(row)
|
|
1495
|
-
: row[_this._gtSettings[i].objectKey];
|
|
1496
|
-
// escape export value using double quotes (") if export value contains delimiter
|
|
1497
|
-
exportValue =
|
|
1498
|
-
typeof exportValue === 'string' &&
|
|
1499
|
-
exportValue.indexOf(_this._gtOptions.csvDelimiter) !== -1
|
|
1500
|
-
? '"' + exportValue + '"'
|
|
1501
|
-
: exportValue;
|
|
1502
|
-
csv += exportValue;
|
|
1503
|
-
if (i < _this._gtSettings.length - 1) {
|
|
1504
|
-
csv += _this._gtOptions.csvDelimiter;
|
|
1505
|
-
}
|
|
1506
|
-
}
|
|
1507
|
-
}
|
|
1508
|
-
});
|
|
1509
|
-
var /** @type {?} */ blob = new Blob([(useBOM ? BOM : '') + csv], {
|
|
1510
|
-
type: 'text/csv;charset=utf-8'
|
|
1511
|
-
});
|
|
1512
|
-
if (window.navigator.msSaveOrOpenBlob) {
|
|
1513
|
-
navigator.msSaveOrOpenBlob(blob, fileName ? fileName + '.csv' : this.gtTexts.csvDownload + '.csv');
|
|
1514
|
-
}
|
|
1515
|
-
else {
|
|
1516
|
-
var /** @type {?} */ link = document.createElement('a');
|
|
1517
|
-
link.style.display = 'none';
|
|
1518
|
-
document.body.appendChild(link);
|
|
1519
|
-
if (link.download !== undefined) {
|
|
1520
|
-
link.setAttribute('href', 'data:text/csv;charset=utf-8,' +
|
|
1521
|
-
encodeURIComponent((useBOM ? BOM : '') + csv)); // URL.createObjectURL(blob));
|
|
1522
|
-
link.setAttribute('download', fileName ? fileName + '.csv' : this.gtTexts.csvDownload + '.csv');
|
|
1523
|
-
document.body.appendChild(link);
|
|
1524
|
-
link.click();
|
|
1525
|
-
}
|
|
1526
|
-
else {
|
|
1527
|
-
csv = 'data:text/csv;charset=utf-8,' + (useBOM ? BOM : '') + csv;
|
|
1528
|
-
window.open(encodeURIComponent(csv));
|
|
1529
|
-
}
|
|
1530
|
-
document.body.removeChild(link);
|
|
1531
|
-
}
|
|
1532
|
-
// emit export event
|
|
1533
|
-
this.gtEvent.emit({
|
|
1534
|
-
name: 'gt-exported-csv',
|
|
1535
|
-
value: fileName ? fileName : this.gtTexts.csvDownload + '.csv'
|
|
1536
|
-
});
|
|
1537
|
-
};
|
|
1538
|
-
/**
|
|
1539
|
-
* @return {?}
|
|
1540
|
-
*/
|
|
1541
|
-
GenericTableComponent.prototype.ngOnInit = /**
|
|
1542
|
-
* @return {?}
|
|
1543
|
-
*/
|
|
1544
|
-
function () {
|
|
1545
|
-
// if number of row to display from start is set to null or 0...
|
|
1546
|
-
if (!this.gtOptions.numberOfRows) {
|
|
1547
|
-
// ...change row length
|
|
1548
|
-
this.changeRowLength(this.gtOptions.numberOfRows);
|
|
1549
|
-
}
|
|
1550
|
-
this.restructureSorting();
|
|
1551
|
-
};
|
|
1552
|
-
/**
|
|
1553
|
-
* @param {?} changes
|
|
1554
|
-
* @return {?}
|
|
1555
|
-
*/
|
|
1556
|
-
GenericTableComponent.prototype.ngOnChanges = /**
|
|
1557
|
-
* @param {?} changes
|
|
1558
|
-
* @return {?}
|
|
1559
|
-
*/
|
|
1560
|
-
function (changes) {
|
|
1561
|
-
// if gt texts have changed...
|
|
1562
|
-
if (changes['gtTexts']) {
|
|
1563
|
-
// ...extend gtOptions default values with values passed into component
|
|
1564
|
-
this.gtTexts = /** @type {?} */ (this.extend(this.gtDefaultTexts, this.gtTexts));
|
|
1565
|
-
}
|
|
1566
|
-
// if lazy loading data and paging information is available...
|
|
1567
|
-
if (this.gtOptions.lazyLoad && this.gtInfo) {
|
|
1568
|
-
// ...calculate total number of pages
|
|
1569
|
-
this.gtInfo.pageTotal = Math.ceil(this.gtInfo.recordsAfterSearch / this.gtInfo.recordLength);
|
|
1570
|
-
// ...declare store position
|
|
1571
|
-
var /** @type {?} */ storePosition = this.gtInfo.pageCurrent - 1;
|
|
1572
|
-
// ...and if store is empty or page length has changed...
|
|
1573
|
-
if (this.store.length === 0 ||
|
|
1574
|
-
this.store[0].length !== this.gtInfo.recordLength) {
|
|
1575
|
-
// ...create store
|
|
1576
|
-
this.store = this.createStore(this.gtInfo.recordsAfterSearch, this.gtInfo.recordLength);
|
|
1577
|
-
}
|
|
1578
|
-
// ...store retrieved data in store at store position
|
|
1579
|
-
this.store[storePosition] = this.gtData;
|
|
1580
|
-
this.gtInfo.visibleRecords = tslib_1.__spread(this.gtData); // add visible rows
|
|
1581
|
-
// replace data with store
|
|
1582
|
-
this._gtData = this.store;
|
|
1583
|
-
this.loading = false;
|
|
1584
|
-
this.updateRecordRange();
|
|
1585
|
-
this.gtEvent.emit({
|
|
1586
|
-
name: 'gt-info',
|
|
1587
|
-
value: this.gtInfo
|
|
1588
|
-
});
|
|
1589
|
-
}
|
|
1590
|
-
else if (this._gtData &&
|
|
1591
|
-
this._gtData.length >= 0 &&
|
|
1592
|
-
changes['gtData'] &&
|
|
1593
|
-
changes['gtData'].previousValue) {
|
|
1594
|
-
this.loading = false;
|
|
1595
|
-
}
|
|
1596
|
-
else if (changes['gtData'] &&
|
|
1597
|
-
changes['gtData'].firstChange &&
|
|
1598
|
-
this._gtData &&
|
|
1599
|
-
this._gtData.length > 0) {
|
|
1600
|
-
this.loading = false;
|
|
1601
|
-
}
|
|
1602
|
-
};
|
|
1603
|
-
/**
|
|
1604
|
-
* @param {?} index
|
|
1605
|
-
* @param {?} item
|
|
1606
|
-
* @return {?}
|
|
1607
|
-
*/
|
|
1608
|
-
GenericTableComponent.prototype.trackByFn = /**
|
|
1609
|
-
* @param {?} index
|
|
1610
|
-
* @param {?} item
|
|
1611
|
-
* @return {?}
|
|
1612
|
-
*/
|
|
1613
|
-
function (index, item) {
|
|
1614
|
-
return item.$$gtRowId;
|
|
1615
|
-
};
|
|
1616
|
-
/**
|
|
1617
|
-
* @param {?} index
|
|
1618
|
-
* @param {?} item
|
|
1619
|
-
* @return {?}
|
|
1620
|
-
*/
|
|
1621
|
-
GenericTableComponent.prototype.trackByColumnFn = /**
|
|
1622
|
-
* @param {?} index
|
|
1623
|
-
* @param {?} item
|
|
1624
|
-
* @return {?}
|
|
1625
|
-
*/
|
|
1626
|
-
function (index, item) {
|
|
1627
|
-
return item.objectKey;
|
|
1628
|
-
};
|
|
1629
|
-
/**
|
|
1630
|
-
* @return {?}
|
|
1631
|
-
*/
|
|
1632
|
-
GenericTableComponent.prototype.ngOnDestroy = /**
|
|
1633
|
-
* @return {?}
|
|
1634
|
-
*/
|
|
1635
|
-
function () {
|
|
1636
|
-
// remove listener
|
|
1637
|
-
this._stopListeningForKeydownEvent();
|
|
1638
|
-
};
|
|
1639
|
-
GenericTableComponent.decorators = [
|
|
1640
|
-
{ type: Component, args: [{
|
|
1641
|
-
selector: 'generic-table',
|
|
1642
|
-
template: "<table class=\"table\" ngClass=\"{{gtClasses}} {{gtOptions.stack ? 'table-stacked':''}}\"\n *ngIf=\"gtFields && gtSettings && (gtFields | gtVisible:gtSettings:refreshPipe).length > 0\">\n <thead>\n <tr>\n <th class=\"gt-sort-label\" *ngIf=\"gtOptions.stack\">{{gtTexts.sortLabel}}</th>\n <th *ngFor=\"let column of gtSettings | gtVisible:gtSettings:refreshPipe\"\n ngClass=\"{{column.objectKey +'-column' | dashCase}} {{gtFields | gtProperty:column.objectKey:'classNames'}} {{column.sortEnabled ? 'sort-'+column.sort:''}} {{column.sortEnabled && column.sortOrder >= 0 ? 'sort-order-'+column.sortOrder:''}} {{ gtFields | gtColumnClass:column }}\"\n (click)=\"column.sortEnabled ? gtSort(column.objectKey,$event):'';\">\n <span *ngIf=\"!(gtFields | gtProperty:column.objectKey:'header')\">{{gtFields | gtProperty:column.objectKey:'name'}}</span>\n <gt-custom-component-factory *ngIf=\"(gtFields | gtProperty:column.objectKey:'header')\"\n [type]=\"(gtFields | gtProperty:column.objectKey:'header')?.type\"\n [injector]=\"(gtFields | gtProperty:column.objectKey:'header')?.injector\"\n [column]=\"gtFields | gtProperty:column.objectKey:'name'\"></gt-custom-component-factory>\n <gt-checkbox *ngIf=\"(gtFields | gtProperty:column.objectKey:'columnComponent')?.type === 'checkbox'\" [checked]=\"(gtOptions.lazyLoad ? lazyAllSelected:selectedRows.length === gtData.length)\" (changed)=\"toggleAllRows()\"></gt-checkbox>\n </th>\n </tr>\n </thead>\n <ng-template\n [ngIf]=\"gtTotals && (gtOptions.lazyLoad === false ? (gtData | gtFilter:gtInfo.filter:gtInfo:refreshFilter:gtData.length | gtSearch:gtInfo.searchTerms:gtInfo:gtSettings:gtFields:gtData.length).length > 0 : gtData.length > 0)\">\n <thead class=\"gt-totals\">\n <tr *ngFor=\"let total of gtTotals | gtTotalsPosition\">\n <td *ngFor=\"let column of gtSettings | gtVisible:gtSettings:refreshPipe;let i = index;\"\n ngClass=\"{{column.objectKey +'-totals-column' | dashCase}} {{gtFields | gtProperty:column.objectKey:'classNames'}} {{ gtFields | gtColumnClass:column }}\">\n <span *ngIf=\"i === 0\" class=\"float-left\">{{total.name}}</span><span\n [innerHTML]=\"total.fields[column.objectKey] | gtTotals:(total.update === false || gtOptions.lazyLoad === true) ? gtData:(gtData | gtFilter:gtInfo.filter:gtInfo:refreshFilter:gtData.length | gtSearch:gtInfo.searchTerms:gtInfo:gtSettings:gtFields:gtData.length):column.objectKey:refreshTotals\"></span>\n </td>\n </tr>\n </thead>\n <tfoot class=\"gt-totals\">\n <tr *ngFor=\"let total of gtTotals | gtTotalsPosition:'footer'\">\n <td *ngFor=\"let column of gtSettings | gtVisible:gtSettings:refreshPipe;let i = index;\"\n ngClass=\"{{column.objectKey +'-totals-column' | dashCase}} {{gtFields | gtProperty:column.objectKey:'classNames'}} {{ gtFields | gtColumnClass:column }}\">\n <span *ngIf=\"i === 0\" class=\"float-left\">{{total.name}}</span><span\n [innerHTML]=\"total.fields[column.objectKey] | gtTotals:(total.update === false || gtOptions.lazyLoad === true) ? gtData:(gtData | gtFilter:gtInfo.filter:gtInfo:refreshFilter:gtData.length | gtSearch:gtInfo.searchTerms:gtInfo:gtSettings:gtFields:gtData.length):column.objectKey:refreshTotals\"></span>\n </td>\n </tr>\n </tfoot>\n </ng-template>\n <tbody *ngIf=\"gtData && gtInfo\">\n <ng-template class=\"table-rows\" ngFor let-row let-last=\"last\" [ngForTrackBy]=\"trackByFn\"\n [ngForOf]=\"gtOptions.lazyLoad && gtInfo ? (gtData[gtInfo.pageCurrent-1]) : (gtData | gtFilter:gtInfo.filter:gtInfo:refreshFilter:gtData.length | gtSearch:gtInfo.searchTerms:gtInfo:gtSettings:gtFields:gtData.length | gtOrderBy:sortOrder:gtFields:refreshSorting:gtData.length | gtChunk:gtInfo:gtInfo.recordLength:gtInfo.pageCurrent:refreshPageArray:gtData.length:gtEvent:data | gtRowClass:gtFields)\">\n <tr [ngClass]=\"{'row-selected':metaInfo[row.$$gtRowId]?.isSelected, 'row-open':metaInfo[row.$$gtRowId]?.isOpen, 'row-loading':loading, 'row-expandable':gtRowComponent}\"\n class=\"{{row.$$gtRowClass}}\"\n (click)=\"gtOptions.rowSelection ? toggleSelect(row):rowClick(row, $event)\">\n <td *ngFor=\"let column of row | gtRender:gtSettings:gtFields:refreshPipe:loading:gtOptions.highlightSearch:gtInfo.searchTerms;trackBy:trackByColumnFn\"\n ngClass=\"{{column.objectKey +'-column' | dashCase}} {{gtFields | gtProperty:column.objectKey:'classNames'}} {{(gtFields | gtProperty:column.objectKey:'inlineEdit') ? 'gt-inline-edit':''}} {{column.edited ? 'gt-edited':''}} {{ gtFields | gtColumnClass:column:row }}\">\n <span class=\"gt-row-label\"\n *ngIf=\"gtOptions.stack\">{{(gtFields | gtProperty:column.objectKey:'stackedHeading') ? (gtFields | gtProperty:column.objectKey:'stackedHeading') : (gtFields | gtProperty:column.objectKey:'name')}}</span>\n <gt-custom-component-factory *ngIf=\"column.columnComponent && column.columnComponent.type !== 'checkbox'\" class=\"gt-row-content\"\n [type]=\"column.columnComponent.type\"\n [injector]=\"column.columnComponent.injector\" [row]=\"row\"\n [column]=\"column\" (redrawEvent)=\"redraw($event)\"\n [searchTerms]=\"gtInfo.searchTerms\" (searchEvent)=\"redraw($event)\"\n (click)=\"column.click ? column.click(row,column,$event):'';column.expand ? toggleCollapse(row, column.expand):''\"></gt-custom-component-factory>\n <span *ngIf=\"!column.columnComponent && (!(gtFields | gtProperty:column.objectKey:'inlineEdit') || ((gtFields | gtProperty:column.objectKey:'inlineEdit')?.active | gtIsObservable) && !((gtFields | gtProperty:column.objectKey:'inlineEdit')?.active | async) || (!((gtFields | gtProperty:column.objectKey:'inlineEdit')?.active | gtIsObservable) && !((gtFields | gtProperty:column.objectKey:'inlineEdit')?.active | gtIsEditable:row:refreshPipe)))\"\n class=\"gt-row-content\" [innerHTML]=\"column.renderValue\"\n (click)=\"column.click ? column.click(row,column,$event):'';column.expand ? toggleCollapse(row, column.expand):''\"></span>\n <ng-template\n [ngIf]=\"!column.columnComponent && (((gtFields | gtProperty:column.objectKey:'inlineEdit')?.active | gtIsObservable) && ((gtFields | gtProperty:column.objectKey:'inlineEdit')?.active | async) || ((gtFields | gtProperty:column.objectKey:'inlineEdit')?.active | gtIsEditable:row:refreshPipe))\">\n <ng-template [ngIf]=\"([true,'email','number','password', 'text'].indexOf((gtFields | gtProperty:column.objectKey:'inlineEdit').type) !== -1) || !(gtFields | gtProperty:column.objectKey:'inlineEdit').type\">\n <input class=\"inline-edit\" [attr.type]=\"!(gtFields | gtProperty:column.objectKey:'inlineEdit').type ? 'text' : !((gtFields | gtProperty:column.objectKey:'inlineEdit').type | gtIsObservable) ? (gtFields | gtProperty:column.objectKey:'inlineEdit').type:(gtFields | gtProperty:column.objectKey:'inlineEdit').type | async\" [(ngModel)]=\"column.renderValue\"\n (input)=\"gtUpdateColumn($event,row, column)\">\n <span class=\"gt-inline-edit-notice\">{{gtTexts.inlineEditEdited}}</span>\n </ng-template>\n <gt-dropdown\n *ngIf=\"(((gtFields | gtProperty:column.objectKey:'inlineEdit').type) && ((gtFields | gtProperty:column.objectKey:'inlineEdit').type).length > 0) || ((gtFields | gtProperty:column.objectKey:'inlineEdit').type | gtIsObservable)\"\n [options]=\"!((gtFields | gtProperty:column.objectKey:'inlineEdit').type | gtIsObservable) ? (gtFields | gtProperty:column.objectKey:'inlineEdit').type : (gtFields | gtProperty:column.objectKey:'inlineEdit').type | async\"\n [id]=\"'_' + row.$$gtRowId + '_' + column.objectKey\"\n [(selected)]=\"column.renderValue\" (selectedChange)=\"gtDropdownSelect(row, column)\">Add\n inline editing module\n </gt-dropdown>\n </ng-template>\n <ng-template [ngIf]=\"!column.columnComponent && !((gtFields | gtProperty:column.objectKey:'inlineEdit')?.active) \">\n <ng-template\n [ngIf]=\"[true,'email','number','password'].indexOf(gtFields | gtProperty:column.objectKey:'inlineEdit') !== -1\">\n <input class=\"inline-edit\" [attr.type]=\"(gtFields | gtProperty:column.objectKey:'inlineEdit') === true ? 'text':(gtFields | gtProperty:column.objectKey:'inlineEdit')\" [(ngModel)]=\"column.renderValue\"\n (input)=\"gtUpdateColumn($event,row, column)\">\n <span class=\"gt-inline-edit-notice\">{{gtTexts.inlineEditEdited}}</span>\n </ng-template>\n <gt-dropdown\n *ngIf=\"(gtFields | gtProperty:column.objectKey:'inlineEdit') && [true,'email','number','password'].indexOf(gtFields | gtProperty:column.objectKey:'inlineEdit') === -1\"\n [options]=\"gtFields | gtProperty:column.objectKey:'inlineEdit'\"\n [id]=\"'_' + row.$$gtRowId + '_' + column.objectKey\"\n [(selected)]=\"column.renderValue\" (selectedChange)=\"gtDropdownSelect(row, column)\">Add\n inline editing module\n </gt-dropdown>\n </ng-template>\n <gt-checkbox *ngIf=\"column.columnComponent && column.columnComponent.type === 'checkbox'\" [checked]=\"metaInfo[row.$$gtRowId]?.isSelected\" (changed)=\"toggleSelect(row)\"></gt-checkbox>\n </td>\n </tr>\n <tr class=\"row-expanded\" *ngIf=\"metaInfo[row.$$gtRowId]?.isOpen\">\n <td [attr.colspan]=\"(gtFields | gtVisible:gtSettings:refreshPipe).length\">\n <gt-expanding-row [row]=\"row\"\n [type]=\"expandedRow.component ? expandedRow.component:gtRowComponent\"\n [columnWidth]=\"columnWidth\"\n [gtFields]=\"gtFields\"\n [gtOptions]=\"gtOptions\"\n [gtEvent]=\"gtEvent\"\n [gtInfo]=\"gtInfo\"\n [gtSettings]=\"gtSettings\"\n [data]=\"expandedRow.data ? expandedRow.data:row\"\n (redrawEvent)=\"redraw($event)\"\n (toggleRowEvent)=\"toggleCollapse($event)\"></gt-expanding-row>\n </td>\n </tr>\n <tr *ngIf=\"gtOptions.reportColumnWidth && last\">\n <td style=\"padding: 0; border:none;\"\n *ngFor=\"let column of gtSettings | gtVisible:gtSettings:refreshPipe\" gtColumnWidth\n [objectKey]=\"column.objectKey\" [widths]=\"columnWidth\"></td>\n </tr>\n </ng-template>\n <tr *ngIf=\"gtInfo.pageTotal === 0 && (gtInfo.searchTerms || gtInfo.filter) && !loading\">\n <td class=\"gt-no-matching-results\" [attr.colspan]=\"(gtFields | gtVisible:gtSettings).length\">\n {{gtTexts.noMatchingData}}\n </td>\n </tr>\n <tr *ngIf=\"gtInfo.pageTotal === 0 && !(gtInfo.searchTerms || gtInfo.filter) && !loading\">\n <td class=\"gt-no-results\" [attr.colspan]=\"(gtFields | gtVisible:gtSettings).length\">{{gtTexts.noData}}\n </td>\n </tr>\n <tr *ngIf=\"gtInfo.pageTotal === 0 && loading\">\n <td class=\"gt-loading-data\" [attr.colspan]=\"(gtFields | gtVisible:gtSettings).length\">{{gtTexts.loading}}</td>\n </tr>\n </tbody>\n</table>\n<table class=\"table\" ngClass=\"{{gtClasses}} {{gtOptions.stack ? 'table-stacked':''}}\"\n *ngIf=\"gtFields && gtSettings && (gtFields | gtVisible:gtSettings:refreshPipe).length === 0\">\n <thead>\n <tr>\n <th class=\"gt-no-visible-columns\">{{gtTexts.noVisibleColumnsHeading}}</th>\n </tr>\n </thead>\n <tbody>\n <tr>\n <td class=\"gt-no-visible-columns\">{{gtTexts.noVisibleColumns}}</td>\n </tr>\n </tbody>\n</table>\n<table class=\"table\" ngClass=\"{{gtClasses}} {{gtOptions.stack ? 'table-stacked':''}}\"\n *ngIf=\"!gtFields || !gtSettings\">\n <thead>\n <tr>\n <th class=\"gt-loading-config\"> </th>\n </tr>\n </thead>\n <tbody>\n <tr>\n <td class=\"gt-loading-config\"> </td>\n </tr>\n </tbody>\n</table>\n"
|
|
1643
|
-
}] }
|
|
1644
|
-
];
|
|
1645
|
-
/** @nocollapse */
|
|
1646
|
-
GenericTableComponent.ctorParameters = function () { return [
|
|
1647
|
-
{ type: Renderer2, },
|
|
1648
|
-
{ type: GtMetaPipe, },
|
|
1649
|
-
]; };
|
|
1650
|
-
GenericTableComponent.propDecorators = {
|
|
1651
|
-
"gtOptions": [{ type: Input },],
|
|
1652
|
-
"gtTotals": [{ type: Input },],
|
|
1653
|
-
"gtFields": [{ type: Input },],
|
|
1654
|
-
"gtSettings": [{ type: Input },],
|
|
1655
|
-
"gtData": [{ type: Input },],
|
|
1656
|
-
"gtRowComponent": [{ type: Input },],
|
|
1657
|
-
"gtTexts": [{ type: Input },],
|
|
1658
|
-
"gtClasses": [{ type: Input },],
|
|
1659
|
-
"gtEvent": [{ type: Output },],
|
|
1660
|
-
"gtInfo": [{ type: Input },],
|
|
1661
|
-
};
|
|
1662
|
-
return GenericTableComponent;
|
|
1663
|
-
}());
|
|
1664
|
-
export { GenericTableComponent };
|
|
1665
|
-
function GenericTableComponent_tsickle_Closure_declarations() {
|
|
1666
|
-
/** @type {!Array<{type: !Function, args: (undefined|!Array<?>)}>} */
|
|
1667
|
-
GenericTableComponent.decorators;
|
|
1668
|
-
/**
|
|
1669
|
-
* @nocollapse
|
|
1670
|
-
* @type {function(): !Array<(null|{type: ?, decorators: (undefined|!Array<{type: !Function, args: (undefined|!Array<?>)}>)})>}
|
|
1671
|
-
*/
|
|
1672
|
-
GenericTableComponent.ctorParameters;
|
|
1673
|
-
/** @type {!Object<string,!Array<{type: !Function, args: (undefined|!Array<?>)}>>} */
|
|
1674
|
-
GenericTableComponent.propDecorators;
|
|
1675
|
-
/** @type {?} */
|
|
1676
|
-
GenericTableComponent.prototype.columnWidth;
|
|
1677
|
-
/** @type {?} */
|
|
1678
|
-
GenericTableComponent.prototype.configObject;
|
|
1679
|
-
/** @type {?} */
|
|
1680
|
-
GenericTableComponent.prototype.sortOrder;
|
|
1681
|
-
/** @type {?} */
|
|
1682
|
-
GenericTableComponent.prototype.metaInfo;
|
|
1683
|
-
/** @type {?} */
|
|
1684
|
-
GenericTableComponent.prototype.selectedRows;
|
|
1685
|
-
/** @type {?} */
|
|
1686
|
-
GenericTableComponent.prototype.openRows;
|
|
1687
|
-
/** @type {?} */
|
|
1688
|
-
GenericTableComponent.prototype._gtSettings;
|
|
1689
|
-
/** @type {?} */
|
|
1690
|
-
GenericTableComponent.prototype._gtFields;
|
|
1691
|
-
/** @type {?} */
|
|
1692
|
-
GenericTableComponent.prototype._gtData;
|
|
1693
|
-
/** @type {?} */
|
|
1694
|
-
GenericTableComponent.prototype._gtTotals;
|
|
1695
|
-
/** @type {?} */
|
|
1696
|
-
GenericTableComponent.prototype._gtRowComponent;
|
|
1697
|
-
/** @type {?} */
|
|
1698
|
-
GenericTableComponent.prototype.expandedRow;
|
|
1699
|
-
/** @type {?} */
|
|
1700
|
-
GenericTableComponent.prototype.gtDefaultTexts;
|
|
1701
|
-
/** @type {?} */
|
|
1702
|
-
GenericTableComponent.prototype.gtTexts;
|
|
1703
|
-
/** @type {?} */
|
|
1704
|
-
GenericTableComponent.prototype.gtClasses;
|
|
1705
|
-
/** @type {?} */
|
|
1706
|
-
GenericTableComponent.prototype.gtEvent;
|
|
1707
|
-
/** @type {?} */
|
|
1708
|
-
GenericTableComponent.prototype.gtDefaultOptions;
|
|
1709
|
-
/** @type {?} */
|
|
1710
|
-
GenericTableComponent.prototype._gtOptions;
|
|
1711
|
-
/** @type {?} */
|
|
1712
|
-
GenericTableComponent.prototype.store;
|
|
1713
|
-
/** @type {?} */
|
|
1714
|
-
GenericTableComponent.prototype.loading;
|
|
1715
|
-
/** @type {?} */
|
|
1716
|
-
GenericTableComponent.prototype.debounceTimer;
|
|
1717
|
-
/** @type {?} */
|
|
1718
|
-
GenericTableComponent.prototype.loadingProperty;
|
|
1719
|
-
/** @type {?} */
|
|
1720
|
-
GenericTableComponent.prototype.lazyAllSelected;
|
|
1721
|
-
/** @type {?} */
|
|
1722
|
-
GenericTableComponent.prototype.gtInfo;
|
|
1723
|
-
/** @type {?} */
|
|
1724
|
-
GenericTableComponent.prototype.refreshPipe;
|
|
1725
|
-
/** @type {?} */
|
|
1726
|
-
GenericTableComponent.prototype.refreshTotals;
|
|
1727
|
-
/** @type {?} */
|
|
1728
|
-
GenericTableComponent.prototype.refreshSorting;
|
|
1729
|
-
/** @type {?} */
|
|
1730
|
-
GenericTableComponent.prototype.refreshFilter;
|
|
1731
|
-
/** @type {?} */
|
|
1732
|
-
GenericTableComponent.prototype.refreshPageArray;
|
|
1733
|
-
/** @type {?} */
|
|
1734
|
-
GenericTableComponent.prototype.globalInlineEditListener;
|
|
1735
|
-
/** @type {?} */
|
|
1736
|
-
GenericTableComponent.prototype.editedRows;
|
|
1737
|
-
/** @type {?} */
|
|
1738
|
-
GenericTableComponent.prototype.data;
|
|
1739
|
-
/**
|
|
1740
|
-
* Sort table by object key.
|
|
1741
|
-
* \@param objectKey - name of key to sort on.
|
|
1742
|
-
* \@param event - such as key press during sorting.
|
|
1743
|
-
* @type {?}
|
|
1744
|
-
*/
|
|
1745
|
-
GenericTableComponent.prototype.gtSort;
|
|
1746
|
-
/**
|
|
1747
|
-
* Change number of rows to be displayed.
|
|
1748
|
-
* \@param rowLength - total number of rows.
|
|
1749
|
-
* \@param reset - should page be reset to first page.
|
|
1750
|
-
* @type {?}
|
|
1751
|
-
*/
|
|
1752
|
-
GenericTableComponent.prototype.changeRowLength;
|
|
1753
|
-
/**
|
|
1754
|
-
* Force a redraw of table rows.
|
|
1755
|
-
* As the table uses pure pipes, we need to force a redraw if an object in the array is changed to see the changes.
|
|
1756
|
-
* @type {?}
|
|
1757
|
-
*/
|
|
1758
|
-
GenericTableComponent.prototype.redraw;
|
|
1759
|
-
/**
|
|
1760
|
-
* Go to next page.
|
|
1761
|
-
* @type {?}
|
|
1762
|
-
*/
|
|
1763
|
-
GenericTableComponent.prototype.nextPage;
|
|
1764
|
-
/**
|
|
1765
|
-
* Go to previous page.
|
|
1766
|
-
* @type {?}
|
|
1767
|
-
*/
|
|
1768
|
-
GenericTableComponent.prototype.previousPage;
|
|
1769
|
-
/**
|
|
1770
|
-
* Request more data (used when lazy loading)
|
|
1771
|
-
* @type {?}
|
|
1772
|
-
*/
|
|
1773
|
-
GenericTableComponent.prototype.getData;
|
|
1774
|
-
/**
|
|
1775
|
-
* Go to specific page.
|
|
1776
|
-
* \@param page - page number.
|
|
1777
|
-
* @type {?}
|
|
1778
|
-
*/
|
|
1779
|
-
GenericTableComponent.prototype.goToPage;
|
|
1780
|
-
/**
|
|
1781
|
-
* Sort by sort order
|
|
1782
|
-
* @type {?}
|
|
1783
|
-
*/
|
|
1784
|
-
GenericTableComponent.prototype.getSortOrder;
|
|
1785
|
-
/**
|
|
1786
|
-
* Sort by column order
|
|
1787
|
-
* @type {?}
|
|
1788
|
-
*/
|
|
1789
|
-
GenericTableComponent.prototype.getColumnOrder;
|
|
1790
|
-
/**
|
|
1791
|
-
* Create a deep copy of data
|
|
1792
|
-
* @type {?}
|
|
1793
|
-
*/
|
|
1794
|
-
GenericTableComponent.prototype.cloneDeep;
|
|
1795
|
-
/**
|
|
1796
|
-
* Return property
|
|
1797
|
-
* @type {?}
|
|
1798
|
-
*/
|
|
1799
|
-
GenericTableComponent.prototype.getProperty;
|
|
1800
|
-
/** @type {?} */
|
|
1801
|
-
GenericTableComponent.prototype.restructureSorting;
|
|
1802
|
-
/**
|
|
1803
|
-
* Extend object function.
|
|
1804
|
-
* @type {?}
|
|
1805
|
-
*/
|
|
1806
|
-
GenericTableComponent.prototype.extend;
|
|
1807
|
-
/** @type {?} */
|
|
1808
|
-
GenericTableComponent.prototype.renderer;
|
|
1809
|
-
/** @type {?} */
|
|
1810
|
-
GenericTableComponent.prototype.gtMetaPipe;
|
|
1811
|
-
}
|
|
1812
|
-
|
|
1813
|
-
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZ2VuZXJpYy10YWJsZS5jb21wb25lbnQuanMiLCJzb3VyY2VSb290Ijoibmc6Ly9AYW5ndWxhci1nZW5lcmljLXRhYmxlL2NvcmUvIiwic291cmNlcyI6WyJsaWIvY29tcG9uZW50cy9nZW5lcmljLXRhYmxlL2dlbmVyaWMtdGFibGUuY29tcG9uZW50LnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7Ozs7O0FBQUEsT0FBTyxFQUNOLFNBQVMsRUFDVCxZQUFZLEVBQ1osS0FBSyxFQUlMLE1BQU0sRUFDTixTQUFTLEVBRVQsSUFBSSxFQUNKLE1BQU0sZUFBZSxDQUFDO0FBWXZCLE9BQU8sRUFBRSxVQUFVLEVBQUUsTUFBTSwwQkFBMEIsQ0FBQzs7Ozs7OztJQXFhckQsK0JBQW9CLFFBQW1CLEVBQVUsVUFBc0I7UUFBdkUsaUJBU0M7UUFUbUIsYUFBUSxHQUFSLFFBQVEsQ0FBVztRQUFVLGVBQVUsR0FBVixVQUFVLENBQVk7MkJBbkYxQyxFQUFFO3lCQUVBLEVBQUU7d0JBQ21CLEVBQUU7NEJBQ2xCLEVBQUU7d0JBQ04sRUFBRTsyQkFDTyxFQUFFO3lCQUNFLEVBQUU7OEJBUWQ7WUFDaEMsT0FBTyxFQUFFLFlBQVk7WUFDckIsTUFBTSxFQUFFLFNBQVM7WUFDakIsY0FBYyxFQUFFLGdDQUFnQztZQUNoRCx1QkFBdUIsRUFBRSxvQkFBb0I7WUFDN0MsZ0JBQWdCLEVBQUUsa0RBQWtEO1lBQ3BFLFNBQVMsRUFDUixrRUFBa0U7WUFDbkUsb0JBQW9CLEVBQ25CLGtIQUFrSDtZQUNuSCxXQUFXLEVBQUUsVUFBVTtZQUN2QixTQUFTLEVBQUUsT0FBTztZQUNsQixZQUFZLEVBQUUsV0FBVztZQUN6QixnQkFBZ0IsRUFBRSxlQUFlO1lBQ2pDLGdCQUFnQixFQUFFLHFCQUFxQjtTQUN2Qzt1QkFDMkIsSUFBSSxDQUFDLGNBQWM7dUJBRUosSUFBSSxZQUFZLEVBQUU7Z0NBQ3hCO1lBQ3BDLFlBQVksRUFBRSxHQUFHO1lBQ2pCLEtBQUssRUFBRSxLQUFLO1lBQ1osUUFBUSxF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LElBQUksQ0FBQyxPQUFPLEdBQUcsS0FBSyxDQUFDO1NBQ3JCO0tBQ0Q7Ozs7OztJQUVELHlDQUFTOzs7OztJQUFULFVBQVUsS0FBYSxFQUFFLElBQVc7UUFDbkMsT0FBTyxJQUFJLENBQUMsU0FBUyxDQUFDO0tBQ3RCOzs7Ozs7SUFFRCwrQ0FBZTs7Ozs7SUFBZixVQUFnQixLQUFhLEVBQUUsSUFBNkI7UUFDM0QsT0FBTyxJQUFJLENBQUMsU0FBUyxDQUFDO0tBQ3RCOzs7O0lBRUQsMkNBQVc7OztJQUFYOztRQUVDLElBQUksQ0FBQyw2QkFBNkIsRUFBRSxDQUFDO0tBQ3JDOztnQkFybkRELFNBQVMsU0FBQztvQkFDVixRQUFRLEVBQUUsZUFBZTtvQkFDekIsUUFBUSxFQUFFLGlpWUF1SlY7aUJBQ0E7Ozs7Z0JBM0tBLFNBQVM7Z0JBZUQsVUFBVTs7OzhCQTJMakIsS0FBSzs2QkFxQkwsS0FBSzs2QkFJTCxLQUFLOytCQWNMLEtBQUs7MkJBeUNMLEtBQUs7bUNBK0RMLEtBQUs7NEJBdUNMLEtBQUs7OEJBQ0wsS0FBSzs0QkFDTCxNQUFNOzJCQXVCTixLQUFLOztnQ0FqYVA7O1NBb0xhLHFCQUFxQiIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7XG5cdENvbXBvbmVudCxcblx0RXZlbnRFbWl0dGVyLFxuXHRJbnB1dCxcblx0T25DaGFuZ2VzLFxuXHRPbkRlc3Ryb3ksXG5cdE9uSW5pdCxcblx0T3V0cHV0LFxuXHRSZW5kZXJlcjIsXG5cdFNpbXBsZUNoYW5nZXMsXG5cdFR5cGVcbn0gZnJvbSAnQGFuZ3VsYXIvY29yZSc7XG5pbXBvcnQgeyBHdFJvdyB9IGZyb20gJy4uLy4uL2ludGVyZmFjZXMvZ3Qtcm93JztcbmltcG9ydCB7IEd0RXhwYW5kZWRSb3cgfSBmcm9tICcuLi9ndC1leHBhbmRpbmctcm93L2d0LWV4cGFuZGluZy1yb3cuY29tcG9uZW50JztcbmltcG9ydCB7IEd0T3B0aW9ucyB9IGZyb20gJy4uLy4uL2ludGVyZmFjZXMvZ3Qtb3B0aW9ucyc7XG5pbXBvcnQgeyBHdENvbmZpZ0ZpZWxkIH0gZnJvbSAnLi4vLi4vaW50ZXJmYWNlcy9ndC1jb25maWctZmllbGQnO1xuaW1wb3J0IHsgR3RDb25maWdTZXR0aW5nIH0gZnJvbSAnLi4vLi4vaW50ZXJmYWNlcy9ndC1jb25maWctc2V0dGluZyc7XG5pbXBvcnQgeyBHdFJvd01ldGEgfSBmcm9tICcuLi8uLi9pbnRlcmZhY2VzL2d0LXJvdy1tZXRhJztcbmltcG9ydCB7IEd0VGV4dHMgfSBmcm9tICcuLi8uLi9pbnRlcmZhY2VzL2d0LXRleHRzJztcbmltcG9ydCB7IEd0Q29uZmlnIH0gZnJvbSAnLi4vLi4vaW50ZXJmYWNlcy9ndC1jb25maWcnO1xuaW1wb3J0IHsgR3RFdmVudCB9IGZyb20gJy4uLy4uL2ludGVyZmFjZXMvZ3QtZXZlbnQnO1xuaW1wb3J0IHsgR3RJbmZvcm1hdGlvbiB9IGZyb20gJy4uLy4uL2ludGVyZmFjZXMvZ3QtaW5mb3JtYXRpb24nO1xuaW1wb3J0IHsgR3RSZW5kZXJGaWVsZCB9IGZyb20gJy4uLy4uL2ludGVyZmFjZXMvZ3QtcmVuZGVyLWZpZWxkJztcbmltcG9ydCB7IEd0TWV0YVBpcGUgfSBmcm9tICcuLi8uLi9waXBlcy9ndC1tZXRhLnBpcGUnO1xuXG5AQ29tcG9uZW50KHtcblx0c2VsZWN0b3I6ICdnZW5lcmljLXRhYmxlJyxcblx0dGVtcGxhdGU6IGA8dGFibGUgY2xhc3M9XCJ0YWJsZVwiIG5nQ2xhc3M9XCJ7e2d0Q2xhc3Nlc319IHt7Z3RPcHRpb25zLnN0YWNrID8gJ3RhYmxlLXN0YWNrZWQnOicnfX1cIlxuICAgICAgICpuZ0lmPVwiZ3RGaWVsZHMgJiYgZ3RTZXR0aW5ncyAmJiAoZ3RGaWVsZHMgfCBndFZpc2libGU6Z3RTZXR0aW5nczpyZWZyZXNoUGlwZSkubGVuZ3RoID4gMFwiPlxuICA8dGhlYWQ+XG4gIDx0cj5cbiAgICA8dGggY2xhc3M9XCJndC1zb3J0LWxhYmVsXCIgKm5nSWY9XCJndE9wdGlvbnMuc3RhY2tcIj57e2d0VGV4dHMuc29ydExhYmVsfX08L3RoPlxuICAgIDx0aCAqbmdGb3I9XCJsZXQgY29sdW1uIG9mIGd0U2V0dGluZ3MgfCBndFZpc2libGU6Z3RTZXR0aW5nczpyZWZyZXNoUGlwZVwiXG4gICAgICAgIG5nQ2xhc3M9XCJ7e2NvbHVtbi5vYmplY3RLZXkgKyctY29sdW1uJyB8IGRhc2hDYXNlfX0ge3tndEZpZWxkcyB8IGd0UHJvcGVydHk6Y29sdW1uLm9iamVjdEtleTonY2xhc3NOYW1lcyd9fSB7e2NvbHVtbi5zb3J0RW5hYmxlZCA/ICdzb3J0LScrY29sdW1uLnNvcnQ6Jyd9fSB7e2NvbHVtbi5zb3J0RW5hYmxlZCAmJiBjb2x1bW4uc29ydE9yZGVyID49IDAgID8gJ3NvcnQtb3JkZXItJytjb2x1bW4uc29ydE9yZGVyOicnfX0ge3sgZ3RGaWVsZHMgfCBndENvbHVtbkNsYXNzOmNvbHVtbiB9fVwiXG4gICAgICAgIChjbGljayk9XCJjb2x1bW4uc29ydEVuYWJsZWQgPyBndFNvcnQoY29sdW1uLm9iamVjdEtleSwkZXZlbnQpOicnO1wiPlxuICAgICAgPHNwYW4gKm5nSWY9XCIhKGd0RmllbGRzIHwgZ3RQcm9wZXJ0eTpjb2x1bW4ub2JqZWN0S2V5OidoZWFkZXInKVwiPnt7Z3RGaWVsZHMgfCBndFByb3BlcnR5OmNvbHVtbi5vYmplY3RLZXk6J25hbWUnfX08L3NwYW4+XG4gICAgICA8Z3QtY3VzdG9tLWNvbXBvbmVudC1mYWN0b3J5ICpuZ0lmPVwiKGd0RmllbGRzIHwgZ3RQcm9wZXJ0eTpjb2x1bW4ub2JqZWN0S2V5OidoZWFkZXInKVwiXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFt0eXBlXT1cIihndEZpZWxkcyB8IGd0UHJvcGVydHk6Y29sdW1uLm9iamVjdEtleTonaGVhZGVyJyk/LnR5cGVcIlxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBbaW5qZWN0b3JdPVwiKGd0RmllbGRzIHwgZ3RQcm9wZXJ0eTpjb2x1bW4ub2JqZWN0S2V5OidoZWFkZXInKT8uaW5qZWN0b3JcIlxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBbY29sdW1uXT1cImd0RmllbGRzIHwgZ3RQcm9wZXJ0eTpjb2x1bW4ub2JqZWN0S2V5OiduYW1lJ1wiPjwvZ3QtY3VzdG9tLWNvbXBvbmVudC1mYWN0b3J5PlxuICAgICAgPGd0LWNoZWNrYm94ICpuZ0lmPVwiKGd0RmllbGRzIHwgZ3RQcm9wZXJ0eTpjb2x1bW4ub2JqZWN0S2V5Oidjb2x1bW5Db21wb25lbnQnKT8udHlwZSA9PT0gJ2NoZWNrYm94J1wiIFtjaGVja2VkXT1cIihndE9wdGlvbnMubGF6eUxvYWQgPyBsYXp5QWxsU2VsZWN0ZWQ6c2VsZWN0ZWRSb3dzLmxlbmd0aCA9PT0gZ3REYXRhLmxlbmd0aClcIiAoY2hhbmdlZCk9XCJ0b2dnbGVBbGxSb3dzKClcIj48L2d0LWNoZWNrYm94PlxuICAgIDwvdGg+XG4gIDwvdHI+XG4gIDwvdGhlYWQ+XG4gIDxuZy10ZW1wbGF0ZVxuICAgIFtuZ0lmXT1cImd0VG90YWxzICYmIChndE9wdGlvbnMubGF6eUxvYWQgPT09IGZhbHNlID8gKGd0RGF0YSB8IGd0RmlsdGVyOmd0SW5mby5maWx0ZXI6Z3RJbmZvOnJlZnJlc2hGaWx0ZXI6Z3REYXRhLmxlbmd0aCB8IGd0U2VhcmNoOmd0SW5mby5zZWFyY2hUZXJtczpndEluZm86Z3RTZXR0aW5nczpndEZpZWxkczpndERhdGEubGVuZ3RoKS5sZW5ndGggPiAwIDogZ3REYXRhLmxlbmd0aCA+IDApXCI+XG4gICAgPHRoZWFkIGNsYXNzPVwiZ3QtdG90YWxzXCI+XG4gICAgPHRyICpuZ0Zvcj1cImxldCB0b3RhbCBvZiBndFRvdGFscyB8IGd0VG90YWxzUG9zaXRpb25cIj5cbiAgICAgIDx0ZCAqbmdGb3I9XCJsZXQgY29sdW1uIG9mIGd0U2V0dGluZ3MgfCBndFZpc2libGU6Z3RTZXR0aW5nczpyZWZyZXNoUGlwZTtsZXQgaSA9IGluZGV4O1wiXG4gICAgICAgICAgbmdDbGFzcz1cInt7Y29sdW1uLm9iamVjdEtleSArJy10b3RhbHMtY29sdW1uJyB8IGRhc2hDYXNlfX0ge3tndEZpZWxkcyB8IGd0UHJvcGVydHk6Y29sdW1uLm9iamVjdEtleTonY2xhc3NOYW1lcyd9fSB7eyBndEZpZWxkcyB8IGd0Q29sdW1uQ2xhc3M6Y29sdW1uIH19XCI+XG4gICAgICAgIDxzcGFuICpuZ0lmPVwiaSA9PT0gMFwiIGNsYXNzPVwiZmxvYXQtbGVmdFwiPnt7dG90YWwubmFtZX19PC9zcGFuPjxzcGFuXG4gICAgICAgIFtpbm5lckhUTUxdPVwidG90YWwuZmllbGRzW2NvbHVtbi5vYmplY3RLZXldIHwgZ3RUb3RhbHM6KHRvdGFsLnVwZGF0ZSA9PT0gZmFsc2UgfHwgZ3RPcHRpb25zLmxhenlMb2FkID09PSB0cnVlKSA/IGd0RGF0YTooZ3REYXRhIHwgZ3RGaWx0ZXI6Z3RJbmZvLmZpbHRlcjpndEluZm86cmVmcmVzaEZpbHRlcjpndERhdGEubGVuZ3RoIHwgZ3RTZWFyY2g6Z3RJbmZvLnNlYXJjaFRlcm1zOmd0SW5mbzpndFNldHRpbmdzOmd0RmllbGRzOmd0RGF0YS5sZW5ndGgpOmNvbHVtbi5vYmplY3RLZXk6cmVmcmVzaFRvdGFsc1wiPjwvc3Bhbj5cbiAgICAgIDwvdGQ+XG4gICAgPC90cj5cbiAgICA8L3RoZWFkPlxuICAgIDx0Zm9vdCBjbGFzcz1cImd0LXRvdGFsc1wiPlxuICAgIDx0ciAqbmdGb3I9XCJsZXQgdG90YWwgb2YgZ3RUb3RhbHMgfCBndFRvdGFsc1Bvc2l0aW9uOidmb290ZXInXCI+XG4gICAgICA8dGQgKm5nRm9yPVwibGV0IGNvbHVtbiBvZiBndFNldHRpbmdzIHwgZ3RWaXNpYmxlOmd0U2V0dGluZ3M6cmVmcmVzaFBpcGU7bGV0IGkgPSBpbmRleDtcIlxuICAgICAgICAgIG5nQ2xhc3M9XCJ7e2NvbHVtbi5vYmplY3RLZXkgKyctdG90YWxzLWNvbHVtbicgfCBkYXNoQ2FzZX19IHt7Z3RGaWVsZHMgfCBndFByb3BlcnR5OmNvbHVtbi5vYmplY3RLZXk6J2NsYXNzTmFtZXMnfX0ge3sgZ3RGaWVsZHMgfCBndENvbHVtbkNsYXNzOmNvbHVtbiB9fVwiPlxuICAgICAgICA8c3BhbiAqbmdJZj1cImkgPT09IDBcIiBjbGFzcz1cImZsb2F0LWxlZnRcIj57e3RvdGFsLm5hbWV9fTwvc3Bhbj48c3BhblxuICAgICAgICBbaW5uZXJIVE1MXT1cInRvdGFsLmZpZWxkc1tjb2x1bW4ub2JqZWN0S2V5XSB8IGd0VG90YWxzOih0b3RhbC51cGRhdGUgPT09IGZhbHNlIHx8IGd0T3B0aW9ucy5sYXp5TG9hZCA9PT0gdHJ1ZSkgPyBndERhdGE6KGd0RGF0YSB8IGd0RmlsdGVyOmd0SW5mby5maWx0ZXI6Z3RJbmZvOnJlZnJlc2hGaWx0ZXI6Z3REYXRhLmxlbmd0aCB8IGd0U2VhcmNoOmd0SW5mby5zZWFyY2hUZXJtczpndEluZm86Z3RTZXR0aW5nczpndEZpZWxkczpndERhdGEubGVuZ3RoKTpjb2x1bW4ub2JqZWN0S2V5OnJlZnJlc2hUb3RhbHNcIj48L3NwYW4+XG4gICAgICA8L3RkPlxuICAgIDwvdHI+XG4gICAgPC90Zm9vdD5cbiAgPC9uZy10ZW1wbGF0ZT5cbiAgPHRib2R5ICpuZ0lmPVwiZ3REYXRhICYmIGd0SW5mb1wiPlxuICA8bmctdGVtcGxhdGUgY2xhc3M9XCJ0YWJsZS1yb3dzXCIgbmdGb3IgbGV0LXJvdyBsZXQtbGFzdD1cImxhc3RcIiBbbmdGb3JUcmFja0J5XT1cInRyYWNrQnlGblwiXG4gICAgICAgICAgICAgICBbbmdGb3JPZl09XCJndE9wdGlvbnMubGF6eUxvYWQgJiYgZ3RJbmZvID8gKGd0RGF0YVtndEluZm8ucGFnZUN1cnJlbnQtMV0pIDogKGd0RGF0YSB8IGd0RmlsdGVyOmd0SW5mby5maWx0ZXI6Z3RJbmZvOnJlZnJlc2hGaWx0ZXI6Z3REYXRhLmxlbmd0aCB8IGd0U2VhcmNoOmd0SW5mby5zZWFyY2hUZXJtczpndEluZm86Z3RTZXR0aW5nczpndEZpZWxkczpndERhdGEubGVuZ3RoIHwgZ3RPcmRlckJ5OnNvcnRPcmRlcjpndEZpZWxkczpyZWZyZXNoU29ydGluZzpndERhdGEubGVuZ3RoIHwgZ3RDaHVuazpndEluZm86Z3RJbmZvLnJlY29yZExlbmd0aDpndEluZm8ucGFnZUN1cnJlbnQ6cmVmcmVzaFBhZ2VBcnJheTpndERhdGEubGVuZ3RoOmd0RXZlbnQ6ZGF0YSB8IGd0Um93Q2xhc3M6Z3RGaWVsZHMpXCI+XG4gICAgPHRyIFtuZ0NsYXNzXT1cInsncm93LXNlbGVjdGVkJzptZXRhSW5mb1tyb3cuJCRndFJvd0lkXT8uaXNTZWxlY3RlZCwgJ3Jvdy1vcGVuJzptZXRhSW5mb1tyb3cuJCRndFJvd0lkXT8uaXNPcGVuLCAncm93LWxvYWRpbmcnOmxvYWRpbmcsICdyb3ctZXhwYW5kYWJsZSc6Z3RSb3dDb21wb25lbnR9XCJcbiAgICAgICAgY2xhc3M9XCJ7e3Jvdy4kJGd0Um93Q2xhc3N9fVwiXG4gICAgICAgIChjbGljayk9XCJndE9wdGlvbnMucm93U2VsZWN0aW9uID8gdG9nZ2xlU2VsZWN0KHJvdyk6cm93Q2xpY2socm93LCAkZXZlbnQpXCI+XG4gICAgICA8dGQgKm5nRm9yPVwibGV0IGNvbHVtbiBvZiByb3cgfCBndFJlbmRlcjpndFNldHRpbmdzOmd0RmllbGRzOnJlZnJlc2hQaXBlOmxvYWRpbmc6Z3RPcHRpb25zLmhpZ2hsaWdodFNlYXJjaDpndEluZm8uc2VhcmNoVGVybXM7dHJhY2tCeTp0cmFja0J5Q29sdW1uRm5cIlxuICAgICAgICAgIG5nQ2xhc3M9XCJ7e2NvbHVtbi5vYmplY3RLZXkgKyctY29sdW1uJyB8IGRhc2hDYXNlfX0ge3tndEZpZWxkcyB8IGd0UHJvcGVydHk6Y29sdW1uLm9iamVjdEtleTonY2xhc3NOYW1lcyd9fSB7eyhndEZpZWxkcyB8IGd0UHJvcGVydHk6Y29sdW1uLm9iamVjdEtleTonaW5saW5lRWRpdCcpID8gJ2d0LWlubGluZS1lZGl0JzonJ319IHt7Y29sdW1uLmVkaXRlZCA/ICdndC1lZGl0ZWQnOicnfX0ge3sgZ3RGaWVsZHMgfCBndENvbHVtbkNsYXNzOmNvbHVtbjpyb3cgfX1cIj5cbiAgICAgICAgICAgICAgICAgICAgICAgIDxzcGFuIGNsYXNzPVwiZ3Qtcm93LWxhYmVsXCJcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICpuZ0lmPVwiZ3RPcHRpb25zLnN0YWNrXCI+e3soZ3RGaWVsZHMgfCBndFByb3BlcnR5OmNvbHVtbi5vYmplY3RLZXk6J3N0YWNrZWRIZWFkaW5nJykgPyAoZ3RGaWVsZHMgfCBndFByb3BlcnR5OmNvbHVtbi5vYmplY3RLZXk6J3N0YWNrZWRIZWFkaW5nJykgOiAoZ3RGaWVsZHMgfCBndFByb3BlcnR5OmNvbHVtbi5vYmplY3RLZXk6J25hbWUnKX19PC9zcGFuPlxuICAgICAgICA8Z3QtY3VzdG9tLWNvbXBvbmVudC1mYWN0b3J5ICpuZ0lmPVwiY29sdW1uLmNvbHVtbkNvbXBvbmVudCAmJiBjb2x1bW4uY29sdW1uQ29tcG9uZW50LnR5cGUgIT09ICdjaGVja2JveCdcIiBjbGFzcz1cImd0LXJvdy1jb250ZW50XCJcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBbdHlwZV09XCJjb2x1bW4uY29sdW1uQ29tcG9uZW50LnR5cGVcIlxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFtpbmplY3Rvcl09XCJjb2x1bW4uY29sdW1uQ29tcG9uZW50LmluamVjdG9yXCIgW3Jvd109XCJyb3dcIlxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFtjb2x1bW5dPVwiY29sdW1uXCIgKHJlZHJhd0V2ZW50KT1cInJlZHJhdygkZXZlbnQpXCJcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBbc2VhcmNoVGVybXNdPVwiZ3RJbmZvLnNlYXJjaFRlcm1zXCIgIChzZWFyY2hFdmVudCk9XCJyZWRyYXcoJGV2ZW50KVwiXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKGNsaWNrKT1cImNvbHVtbi5jbGljayA/IGNvbHVtbi5jbGljayhyb3csY29sdW1uLCRldmVudCk6Jyc7Y29sdW1uLmV4cGFuZCA/IHRvZ2dsZUNvbGxhcHNlKHJvdywgY29sdW1uLmV4cGFuZCk6JydcIj48L2d0LWN1c3RvbS1jb21wb25lbnQtZmFjdG9yeT5cbiAgICAgICAgPHNwYW4gKm5nSWY9XCIhY29sdW1uLmNvbHVtbkNvbXBvbmVudCAmJiAoIShndEZpZWxkcyB8IGd0UHJvcGVydHk6Y29sdW1uLm9iamVjdEtleTonaW5saW5lRWRpdCcpIHx8ICgoZ3RGaWVsZHMgfCBndFByb3BlcnR5OmNvbHVtbi5vYmplY3RLZXk6J2lubGluZUVkaXQnKT8uYWN0aXZlIHwgZ3RJc09ic2VydmFibGUpICYmICEoKGd0RmllbGRzIHwgZ3RQcm9wZXJ0eTpjb2x1bW4ub2JqZWN0S2V5OidpbmxpbmVFZGl0Jyk/LmFjdGl2ZSB8IGFzeW5jKSB8fCAoISgoZ3RGaWVsZHMgfCBndFByb3BlcnR5OmNvbHVtbi5vYmplY3RLZXk6J2lubGluZUVkaXQnKT8uYWN0aXZlIHwgZ3RJc09ic2VydmFibGUpICYmICEoKGd0RmllbGRzIHwgZ3RQcm9wZXJ0eTpjb2x1bW4ub2JqZWN0S2V5OidpbmxpbmVFZGl0Jyk/LmFjdGl2ZSB8IGd0SXNFZGl0YWJsZTpyb3c6cmVmcmVzaFBpcGUpKSlcIlxuICAgICAgICAgICAgICBjbGFzcz1cImd0LXJvdy1jb250ZW50XCIgW2lubmVySFRNTF09XCJjb2x1bW4ucmVuZGVyVmFsdWVcIlxuICAgICAgICAgICAgICAoY2xpY2spPVwiY29sdW1uLmNsaWNrID8gY29sdW1uLmNsaWNrKHJvdyxjb2x1bW4sJGV2ZW50KTonJztjb2x1bW4uZXhwYW5kID8gdG9nZ2xlQ29sbGFwc2Uocm93LCBjb2x1bW4uZXhwYW5kKTonJ1wiPjwvc3Bhbj5cbiAgICAgICAgPG5nLXRlbXBsYXRlXG4gICAgICAgICAgW25nSWZdPVwiIWNvbHVtbi5jb2x1bW5Db21wb25lbnQgJiYgKCgoZ3RGaWVsZHMgfCBndFByb3BlcnR5OmNvbHVtbi5vYmplY3RLZXk6J2lubGluZUVkaXQnKT8uYWN0aXZlIHwgZ3RJc09ic2VydmFibGUpICYmICgoZ3RGaWVsZHMgfCBndFByb3BlcnR5OmNvbHVtbi5vYmplY3RLZXk6J2lubGluZUVkaXQnKT8uYWN0aXZlIHwgYXN5bmMpIHx8ICgoZ3RGaWVsZHMgfCBndFByb3BlcnR5OmNvbHVtbi5vYmplY3RLZXk6J2lubGluZUVkaXQnKT8uYWN0aXZlIHwgZ3RJc0VkaXRhYmxlOnJvdzpyZWZyZXNoUGlwZSkpXCI+XG4gICAgICAgICAgPG5nLXRlbXBsYXRlIFtuZ0lmXT1cIihbdHJ1ZSwnZW1haWwnLCdudW1iZXInLCdwYXNzd29yZCcsICd0ZXh0J10uaW5kZXhPZigoZ3RGaWVsZHMgfCBndFByb3BlcnR5OmNvbHVtbi5vYmplY3RLZXk6J2lubGluZUVkaXQnKS50eXBlKSAhPT0gLTEpIHx8ICEoZ3RGaWVsZHMgfCBndFByb3BlcnR5OmNvbHVtbi5vYmplY3RLZXk6J2lubGluZUVkaXQnKS50eXBlXCI+XG4gICAgICAgICAgICA8aW5wdXQgY2xhc3M9XCJpbmxpbmUtZWRpdFwiIFthdHRyLnR5cGVdPVwiIShndEZpZWxkcyB8IGd0UHJvcGVydHk6Y29sdW1uLm9iamVjdEtleTonaW5saW5lRWRpdCcpLnR5cGUgPyAndGV4dCcgOiAhKChndEZpZWxkcyB8IGd0UHJvcGVydHk6Y29sdW1uLm9iamVjdEtleTonaW5saW5lRWRpdCcpLnR5cGUgfCBndElzT2JzZXJ2YWJsZSkgPyAoZ3RGaWVsZHMgfCBndFByb3BlcnR5OmNvbHVtbi5vYmplY3RLZXk6J2lubGluZUVkaXQnKS50eXBlOihndEZpZWxkcyB8IGd0UHJvcGVydHk6Y29sdW1uLm9iamVjdEtleTonaW5saW5lRWRpdCcpLnR5cGUgfCBhc3luY1wiIFsobmdNb2RlbCldPVwiY29sdW1uLnJlbmRlclZhbHVlXCJcbiAgICAgICAgICAgICAgICAgICAoaW5wdXQpPVwiZ3RVcGRhdGVDb2x1bW4oJGV2ZW50LHJvdywgY29sdW1uKVwiPlxuICAgICAgICAgICAgPHNwYW4gY2xhc3M9XCJndC1pbmxpbmUtZWRpdC1ub3RpY2VcIj57e2d0VGV4dHMuaW5saW5lRWRpdEVkaXRlZH19PC9zcGFuPlxuICAgICAgICAgIDwvbmctdGVtcGxhdGU+XG4gICAgICAgICAgPGd0LWRyb3Bkb3duXG4gICAgICAgICAgICAqbmdJZj1cIigoKGd0RmllbGRzIHwgZ3RQcm9wZXJ0eTpjb2x1bW4ub2JqZWN0S2V5OidpbmxpbmVFZGl0JykudHlwZSkgJiYgKChndEZpZWxkcyB8IGd0UHJvcGVydHk6Y29sdW1uLm9iamVjdEtleTonaW5saW5lRWRpdCcpLnR5cGUpLmxlbmd0aCA+IDApIHx8ICgoZ3RGaWVsZHMgfCBndFByb3BlcnR5OmNvbHVtbi5vYmplY3RLZXk6J2lubGluZUVkaXQnKS50eXBlIHwgZ3RJc09ic2VydmFibGUpXCJcbiAgICAgICAgICAgIFtvcHRpb25zXT1cIiEoKGd0RmllbGRzIHwgZ3RQcm9wZXJ0eTpjb2x1bW4ub2JqZWN0S2V5OidpbmxpbmVFZGl0JykudHlwZSB8IGd0SXNPYnNlcnZhYmxlKSA/IChndEZpZWxkcyB8IGd0UHJvcGVydHk6Y29sdW1uLm9iamVjdEtleTonaW5saW5lRWRpdCcpLnR5cGUgOiAoZ3RGaWVsZHMgfCBndFByb3BlcnR5OmNvbHVtbi5vYmplY3RLZXk6J2lubGluZUVkaXQnKS50eXBlIHwgYXN5bmNcIlxuICAgICAgICAgICAgW2lkXT1cIidfJyArIHJvdy4kJGd0Um93SWQgKyAnXycgKyBjb2x1bW4ub2JqZWN0S2V5XCJcbiAgICAgICAgICAgIFsoc2VsZWN0ZWQpXT1cImNvbHVtbi5yZW5kZXJWYWx1ZVwiIChzZWxlY3RlZENoYW5nZSk9XCJndERyb3Bkb3duU2VsZWN0KHJvdywgY29sdW1uKVwiPkFkZFxuICAgICAgICAgICAgaW5saW5lIGVkaXRpbmcgbW9kdWxlXG4gICAgICAgICAgPC9ndC1kcm9wZG93bj5cbiAgICAgICAgPC9uZy10ZW1wbGF0ZT5cbiAgICAgICAgPG5nLXRlbXBsYXRlIFtuZ0lmXT1cIiFjb2x1bW4uY29sdW1uQ29tcG9uZW50ICYmICEoKGd0RmllbGRzIHwgZ3RQcm9wZXJ0eTpjb2x1bW4ub2JqZWN0S2V5OidpbmxpbmVFZGl0Jyk/LmFjdGl2ZSkgXCI+XG4gICAgICAgICAgPG5nLXRlbXBsYXRlXG4gICAgICAgICAgICBbbmdJZl09XCJbdHJ1ZSwnZW1haWwnLCdudW1iZXInLCdwYXNzd29yZCddLmluZGV4T2YoZ3RGaWVsZHMgfCBndFByb3BlcnR5OmNvbHVtbi5vYmplY3RLZXk6J2lubGluZUVkaXQnKSAhPT0gLTFcIj5cbiAgICAgICAgICAgIDxpbnB1dCBjbGFzcz1cImlubGluZS1lZGl0XCIgW2F0dHIudHlwZV09XCIoZ3RGaWVsZHMgfCBndFByb3BlcnR5OmNvbHVtbi5vYmplY3RLZXk6J2lubGluZUVkaXQnKSA9PT0gdHJ1ZSA/ICd0ZXh0JzooZ3RGaWVsZHMgfCBndFByb3BlcnR5OmNvbHVtbi5vYmplY3RLZXk6J2lubGluZUVkaXQnKVwiIFsobmdNb2RlbCldPVwiY29sdW1uLnJlbmRlclZhbHVlXCJcbiAgICAgICAgICAgICAgICAgICAoaW5wdXQpPVwiZ3RVcGRhdGVDb2x1bW4oJGV2ZW50LHJvdywgY29sdW1uKVwiPlxuICAgICAgICAgICAgPHNwYW4gY2xhc3M9XCJndC1pbmxpbmUtZWRpdC1ub3RpY2VcIj57e2d0VGV4dHMuaW5saW5lRWRpdEVkaXRlZH19PC9zcGFuPlxuICAgICAgICAgIDwvbmctdGVtcGxhdGU+XG4gICAgICAgICAgPGd0LWRyb3Bkb3duXG4gICAgICAgICAgICAqbmdJZj1cIihndEZpZWxkcyB8IGd0UHJvcGVydHk6Y29sdW1uLm9iamVjdEtleTonaW5saW5lRWRpdCcpICYmIFt0cnVlLCdlbWFpbCcsJ251bWJlcicsJ3Bhc3N3b3JkJ10uaW5kZXhPZihndEZpZWxkcyB8IGd0UHJvcGVydHk6Y29sdW1uLm9iamVjdEtleTonaW5saW5lRWRpdCcpID09PSAtMVwiXG4gICAgICAgICAgICBbb3B0aW9uc109XCJndEZpZWxkcyB8IGd0UHJvcGVydHk6Y29sdW1uLm9iamVjdEtleTonaW5saW5lRWRpdCdcIlxuICAgICAgICAgICAgW2lkXT1cIidfJyArIHJvdy4kJGd0Um93SWQgKyAnXycgKyBjb2x1bW4ub2JqZWN0S2V5XCJcbiAgICAgICAgICAgIFsoc2VsZWN0ZWQpXT1cImNvbHVtbi5yZW5kZXJWYWx1ZVwiIChzZWxlY3RlZENoYW5nZSk9XCJndERyb3Bkb3duU2VsZWN0KHJvdywgY29sdW1uKVwiPkFkZFxuICAgICAgICAgICAgaW5saW5lIGVkaXRpbmcgbW9kdWxlXG4gICAgICAgICAgPC9ndC1kcm9wZG93bj5cbiAgICAgICAgPC9uZy10ZW1wbGF0ZT5cbiAgICAgICAgPGd0LWNoZWNrYm94ICpuZ0lmPVwiY29sdW1uLmNvbHVtbkNvbXBvbmVudCAmJiBjb2x1bW4uY29sdW1uQ29tcG9uZW50LnR5cGUgPT09ICdjaGVja2JveCdcIiBbY2hlY2tlZF09XCJtZXRhSW5mb1tyb3cuJCRndFJvd0lkXT8uaXNTZWxlY3RlZFwiIChjaGFuZ2VkKT1cInRvZ2dsZVNlbGVjdChyb3cpXCI+PC9ndC1jaGVja2JveD5cbiAgICAgIDwvdGQ+XG4gICAgPC90cj5cbiAgICA8dHIgY2xhc3M9XCJyb3ctZXhwYW5kZWRcIiAqbmdJZj1cIm1ldGFJbmZvW3Jvdy4kJGd0Um93SWRdPy5pc09wZW5cIj5cbiAgICAgIDx0ZCBbYXR0ci5jb2xzcGFuXT1cIihndEZpZWxkcyB8IGd0VmlzaWJsZTpndFNldHRpbmdzOnJlZnJlc2hQaXBlKS5sZW5ndGhcIj5cbiAgICAgICAgPGd0LWV4cGFuZGluZy1yb3cgW3Jvd109XCJyb3dcIlxuICAgICAgICAgICAgICAgICAgICAgICAgICBbdHlwZV09XCJleHBhbmRlZFJvdy5jb21wb25lbnQgPyBleHBhbmRlZFJvdy5jb21wb25lbnQ6Z3RSb3dDb21wb25lbnRcIlxuICAgICAgICAgICAgICAgICAgICAgICAgICBbY29sdW1uV2lkdGhdPVwiY29sdW1uV2lkdGhcIlxuICAgICAgICAgICAgICAgICAgICAgICAgICBbZ3RGaWVsZHNdPVwiZ3RGaWVsZHNcIlxuICAgICAgICAgICAgICAgICAgICAgICAgICBbZ3RPcHRpb25zXT1cImd0T3B0aW9uc1wiXG4gICAgICAgICAgICAgICAgICAgICAgICAgIFtndEV2ZW50XT1cImd0RXZlbnRcIlxuICAgICAgICAgICAgICAgICAgICAgICAgICBbZ3RJbmZvXT1cImd0SW5mb1wiXG4gICAgICAgICAgICAgICAgICAgICAgICAgIFtndFNldHRpbmdzXT1cImd0U2V0dGluZ3NcIlxuICAgICAgICAgICAgICAgICAgICAgICAgICBbZGF0YV09XCJleHBhbmRlZFJvdy5kYXRhID8gZXhwYW5kZWRSb3cuZGF0YTpyb3dcIlxuICAgICAgICAgICAgICAgICAgICAgICAgICAocmVkcmF3RXZlbnQpPVwicmVkcmF3KCRldmVudClcIlxuICAgICAgICAgICAgICAgICAgICAgICAgICAodG9nZ2xlUm93RXZlbnQpPVwidG9nZ2xlQ29sbGFwc2UoJGV2ZW50KVwiPjwvZ3QtZXhwYW5kaW5nLXJvdz5cbiAgICAgIDwvdGQ+XG4gICAgPC90cj5cbiAgICA8dHIgKm5nSWY9XCJndE9wdGlvbnMucmVwb3J0Q29sdW1uV2lkdGggJiYgbGFzdFwiPlxuICAgICAgPHRkIHN0eWxlPVwicGFkZGluZzogMDsgYm9yZGVyOm5vbmU7XCJcbiAgICAgICAgICAqbmdGb3I9XCJsZXQgY29sdW1uIG9mIGd0U2V0dGluZ3MgfCBndFZpc2libGU6Z3RTZXR0aW5nczpyZWZyZXNoUGlwZVwiIGd0Q29sdW1uV2lkdGhcbiAgICAgICAgICBbb2JqZWN0S2V5XT1cImNvbHVtbi5vYmplY3RLZXlcIiBbd2lkdGhzXT1cImNvbHVtbldpZHRoXCI+PC90ZD5cbiAgICA8L3RyPlxuICA8L25nLXRlbXBsYXRlPlxuICA8dHIgKm5nSWY9XCJndEluZm8ucGFnZVRvdGFsID09PSAwICYmIChndEluZm8uc2VhcmNoVGVybXMgfHwgZ3RJbmZvLmZpbHRlcikgJiYgIWxvYWRpbmdcIj5cbiAgICA8dGQgY2xhc3M9XCJndC1uby1tYXRjaGluZy1yZXN1bHRzXCIgW2F0dHIuY29sc3Bhbl09XCIoZ3RGaWVsZHMgfCBndFZpc2libGU6Z3RTZXR0aW5ncykubGVuZ3RoXCI+XG4gICAgICB7e2d0VGV4dHMubm9NYXRjaGluZ0RhdGF9fVxuICAgIDwvdGQ+XG4gIDwvdHI+XG4gIDx0ciAqbmdJZj1cImd0SW5mby5wYWdlVG90YWwgPT09IDAgJiYgIShndEluZm8uc2VhcmNoVGVybXMgfHwgZ3RJbmZvLmZpbHRlcikgJiYgIWxvYWRpbmdcIj5cbiAgICA8dGQgY2xhc3M9XCJndC1uby1yZXN1bHRzXCIgW2F0dHIuY29sc3Bhbl09XCIoZ3RGaWVsZHMgfCBndFZpc2libGU6Z3RTZXR0aW5ncykubGVuZ3RoXCI+e3tndFRleHRzLm5vRGF0YX19XG4gICAgPC90ZD5cbiAgPC90cj5cbiAgPHRyICpuZ0lmPVwiZ3RJbmZvLnBhZ2VUb3RhbCA9PT0gMCAmJiBsb2FkaW5nXCI+XG4gICAgPHRkIGNsYXNzPVwiZ3QtbG9hZGluZy1kYXRhXCIgW2F0dHIuY29sc3Bhbl09XCIoZ3RGaWVsZHMgfCBndFZpc2libGU6Z3RTZXR0aW5ncykubGVuZ3RoXCI+e3tndFRleHRzLmxvYWRpbmd9fTwvdGQ+XG4gIDwvdHI+XG4gIDwvdGJvZHk+XG48L3RhYmxlPlxuPHRhYmxlIGNsYXNzPVwidGFibGVcIiBuZ0NsYXNzPVwie3tndENsYXNzZXN9fSB7e2d0T3B0aW9ucy5zdGFjayA/ICd0YWJsZS1zdGFja2VkJzonJ319XCJcbiAgICAgICAqbmdJZj1cImd0RmllbGRzICYmIGd0U2V0dGluZ3MgJiYgKGd0RmllbGRzIHwgZ3RWaXNpYmxlOmd0U2V0dGluZ3M6cmVmcmVzaFBpcGUpLmxlbmd0aCA9PT0gMFwiPlxuICA8dGhlYWQ+XG4gIDx0cj5cbiAgICA8dGggY2xhc3M9XCJndC1uby12aXNpYmxlLWNvbHVtbnNcIj57e2d0VGV4dHMubm9WaXNpYmxlQ29sdW1uc0hlYWRpbmd9fTwvdGg+XG4gIDwvdHI+XG4gIDwvdGhlYWQ+XG4gIDx0Ym9keT5cbiAgPHRyPlxuICAgIDx0ZCBjbGFzcz1cImd0LW5vLXZpc2libGUtY29sdW1uc1wiPnt7Z3RUZXh0cy5ub1Zpc2libGVDb2x1bW5zfX08L3RkPlxuICA8L3RyPlxuICA8L3Rib2R5PlxuPC90YWJsZT5cbjx0YWJsZSBjbGFzcz1cInRhYmxlXCIgbmdDbGFzcz1cInt7Z3RDbGFzc2VzfX0ge3tndE9wdGlvbnMuc3RhY2sgPyAndGFibGUtc3RhY2tlZCc6Jyd9fVwiXG4gICAgICAgKm5nSWY9XCIhZ3RGaWVsZHMgfHwgIWd0U2V0dGluZ3NcIj5cbiAgPHRoZWFkPlxuICA8dHI+XG4gICAgPHRoIGNsYXNzPVwiZ3QtbG9hZGluZy1jb25maWdcIj4mbmJzcDs8L3RoPlxuICA8L3RyPlxuICA8L3RoZWFkPlxuICA8dGJvZHk+XG4gIDx0cj5cbiAgICA8dGQgY2xhc3M9XCJndC1sb2FkaW5nLWNvbmZpZ1wiPiZuYnNwOzwvdGQ+XG4gIDwvdHI+XG4gIDwvdGJvZHk+XG48L3RhYmxlPlxuYFxufSlcbmV4cG9ydCBjbGFzcyBHZW5lcmljVGFibGVDb21wb25lbnQ8UiBleHRlbmRzIEd0Um93LCBDIGV4dGVuZHMgR3RFeHBhbmRlZFJvdzxSPj5cblx0aW1wbGVtZW50cyBPbkluaXQsIE9uQ2hhbmdlcywgT25EZXN0cm95IHtcblx0Z2V0IGd0Um93Q29tcG9uZW50KCk6IFR5cGU8Qz4ge1xuXHRcdHJldHVybiB0aGlzLl9ndFJvd0NvbXBvbmVudDtcblx0fVxuXG5cdGdldCBoYXNFZGl0cygpOiBib29sZWFuIHtcblx0XHRyZXR1cm4gT2JqZWN0LmtleXModGhpcy5lZGl0ZWRSb3dzKS5sZW5ndGggPiAwO1xuXHR9XG5cblx0Z2V0IGd0T3B0aW9ucygpOiBHdE9wdGlvbnMge1xuXHRcdHJldHVybiB0aGlzLl9ndE9wdGlvbnM7XG5cdH1cblxuXHRnZXQgZ3RUb3RhbHMoKTogYW55IHtcblx0XHRyZXR1cm4gdGhpcy5fZ3RUb3RhbHM7XG5cdH1cblxuXHRnZXQgZ3RGaWVsZHMoKTogR3RDb25maWdGaWVsZDxSLCBhbnk+W10ge1xuXHRcdHJldHVybiB0aGlzLl9ndEZpZWxkcztcblx0fVxuXG5cdGdldCBndFNldHRpbmdzKCk6IEd0Q29uZmlnU2V0dGluZ1tdIHtcblx0XHRyZXR1cm4gdGhpcy5fZ3RTZXR0aW5ncztcblx0fVxuXG5cdGdldCBndERhdGEoKTogQXJyYXk8YW55PiB7XG5cdFx0cmV0dXJuIHRoaXMuX2d0RGF0YTtcblx0fVxuXG5cdEBJbnB1dCgpXG5cdHNldCBndE9wdGlvbnModmFsdWU6IEd0T3B0aW9ucykge1xuXHRcdHRoaXMuX2d0T3B0aW9ucyA9IHZhbHVlO1xuXG5cdFx0Ly8gaWYgbnVtYmVyIG9mIHJvd3MgaXMgcGFzc2VkIGFuZCBpZiBudW1iZXIgb2Ygcm93cyBkaWZmZXJzIGZyb20gY3VycmVudCByZWNvcmQgbGVuZ3RoLi4uXG5cdFx0aWYgKFxuXHRcdFx0dGhpcy5ndE9wdGlvbnMubnVtYmVyT2ZSb3dzICYmXG5cdFx0XHR0aGlzLmd0SW5mby5yZWNvcmRMZW5ndGggIT09IHRoaXMuZ3RPcHRpb25zLm51bWJlck9mUm93c1xuXHRcdCkge1xuXHRcdFx0Ly8gLi4udXBkYXRlIHJlY29yZCBsZW5ndGggYW5kIHJlZHJhdyB0YWJsZVxuXHRcdFx0dGhpcy5ndEluZm8ucmVjb3JkTGVuZ3RoID0gdGhpcy5ndE9wdGlvbnMubnVtYmVyT2ZSb3dzO1xuXHRcdFx0dGhpcy5yZWRyYXcoKTtcblx0XHR9XG5cblx0XHQvLyAuLi5leHRlbmQgZ3RPcHRpb25zIGRlZmF1bHQgdmFsdWVzIHdpdGggdmFsdWVzIHBhc3NlZCBpbnRvIGNvbXBvbmVudFxuXHRcdHRoaXMuX2d0T3B0aW9ucyA9IDxHdE9wdGlvbnM+dGhpcy5leHRlbmQoXG5cdFx0XHR0aGlzLmd0RGVmYXVsdE9wdGlvbnMsXG5cdFx0XHR0aGlzLl9ndE9wdGlvbnNcblx0XHQpO1xuXHR9XG5cblx0QElucHV0KClcblx0c2V0IGd0VG90YWxzKHZhbHVlOiBhbnkpIHtcblx0XHR0aGlzLl9ndFRvdGFscyA9IHZhbHVlO1xuXHR9XG5cdEBJbnB1dCgpXG5cdHNldCBndEZpZWxkcyh2YWx1ZTogR3RDb25maWdGaWVsZDxSLCBhbnk+W10pIHtcblx0XHR0aGlzLl9ndEZpZWxkcyA9IHZhbHVlO1xuXHRcdGNvbnN0IENPTFVNTlNfV0lUSF9DTEFTU19OQU1FUyA9IHRoaXMuX2d0RmllbGRzXG5cdFx0XHQubWFwKGNvbHVtbiA9PiBjb2x1bW4pXG5cdFx0XHQuZmlsdGVyKGNvbHVtbiA9PiBjb2x1bW4uY2xhc3NOYW1lcyk7XG5cdFx0Ly8gVE9ETzogcmVtb3ZlIGRlcHJlY2F0ZWQgd2FybmluZyB3aGVuIHNldHRpbmcgaGFzIGJlZW4gcmVtb3ZlZFxuXHRcdGlmIChDT0xVTU5TX1dJVEhfQ0xBU1NfTkFNRVMubGVuZ3RoID4gMCkge1xuXHRcdFx0Y29uc29sZS53YXJuKFxuXHRcdFx0XHQnRmllbGQgc2V0dGluZyBcImNsYXNzTmFtZXNcIiBoYXZlIGJlZW4gZGVwcmVjYXRlZCBpbiBmYXZvciBmb3IgXCJjb2x1bW5DbGFzc1wiIGFuZCB3aWxsIGJlIHJlbW92ZWQgaW4gdGhlIGZ1dHVyZSwgcGxlYXNlIHVwZGF0ZSBmaWVsZCBzZXR0aW5ncyBmb3IgY29sdW1uIHdpdGggb2JqZWN0IGtleTogJyArXG5cdFx0XHRcdFx0Q09MVU1OU19XSVRIX0NMQVNTX05BTUVTWzBdLm9iamVjdEtleVxuXHRcdFx0KTtcblx0XHR9XG5cdH1cblx0QElucHV0KClcblx0c2V0IGd0U2V0dGluZ3ModmFsdWU6IEd0Q29uZmlnU2V0dGluZ1tdKSB7XG5cdFx0dGhpcy5fZ3RTZXR0aW5ncyA9IHZhbHVlO1xuXG5cdFx0Ly8gbG9vcCB0aHJvdWdoIGN1cnJlbnQgc2V0dGluZ3Ncblx0XHRmb3IgKGxldCBpID0gMDsgaSA8IHRoaXMuX2d0U2V0dGluZ3MubGVuZ3RoOyBpKyspIHtcblx0XHRcdC8vIHNldCBzb3J0IGVuYWJsZWQvZGlzYWJsZWQgc2V0dGluZ1xuXHRcdFx0dGhpcy5fZ3RTZXR0aW5nc1tpXS5zb3J0RW5hYmxlZCA9XG5cdFx0XHRcdHRoaXMuX2d0U2V0dGluZ3NbaV0uc29ydEVuYWJsZWQgIT09IGZhbHNlXG5cdFx0XHRcdFx0PyAodGhpcy5fZ3RTZXR0aW5nc1tpXS5zb3J0RW5hYmxlZCA9ICEoXG5cdFx0XHRcdFx0XHRcdHRoaXMuX2d0U2V0dGluZ3NbaV0uc29ydCAmJlxuXHRcdFx0XHRcdFx0XHR0aGlzLl9ndFNldHRpbmdzW2ldLnNvcnQuaW5kZXhPZignZGlzYWJsZScpICE9PSAtMVxuXHRcdFx0XHRcdCAgKSlcblx0XHRcdFx0XHQ6IGZhbHNlO1xuXG5cdFx0XHQvLyBjaGVjayBpZiBzb3J0aW5nIGlzIHVuZGVmaW5lZC4uLlxuXHRcdFx0aWYgKHR5cGVvZiB0aGlzLl9ndFNldHRpbmdzW2ldLnNvcnQgPT09ICd1bmRlZmluZWQnKSB7XG5cdFx0XHRcdC8vIC4uLmlzIHNvLCBzZXQgc29ydGluZyBwcm9wZXJ0eSB0byBlbmFibGVcblx0XHRcdFx0dGhpcy5fZ3RTZXR0aW5nc1tpXS5zb3J0ID0gJ2VuYWJsZSc7XG5cdFx0XHR9XG5cblx0XHRcdC8vIGNoZWNrIGlmIGNvbHVtbiBvcmRlciBpcyB1bmRlZmluZWQuLi5cblx0XHRcdGlmIChcblx0XHRcdFx0dHlwZW9mIHRoaXMuX2d0U2V0dGluZ3NbaV0uY29sdW1uT3JkZXIgPT09ICd1bmRlZmluZWQnICYmXG5cdFx0XHRcdHRoaXMuX2d0U2V0dGluZ3NbaV0uZW5hYmxlZCAhPT0gZmFsc2Vcblx0XHRcdCkge1xuXHRcdFx0XHQvLyAuLi5pcyBzbywgc2V0IHNvcnRpbmcgcHJvcGVydHkgdG8gZW5hYmxlXG5cdFx0XHRcdHRoaXMuX2d0U2V0dGluZ3NbaV0uY29sdW1uT3JkZXIgPSB0aGlzLl9ndFNldHRpbmdzW2kgLSAxXVxuXHRcdFx0XHRcdD8gdGhpcy5fZ3RTZXR0aW5nc1tpIC0gMV0uY29sdW1uT3JkZXIgKyAxXG5cdFx0XHRcdFx0OiAwO1xuXHRcdFx0fVxuXG5cdFx0XHQvLyBjaGVjayBpZiBjb2x1bW4gbG9jayBzZXR0aW5ncyBhcmUgdW5kZWZpbmVkLi4uXG5cdFx0XHRpZiAodHlwZW9mIHRoaXMuX2d0U2V0dGluZ3NbaV0ubG9ja1NldHRpbmdzID09PSAndW5kZWZpbmVkJykge1xuXHRcdFx0XHQvLyAuLi5pZiBzbywgc2V0IGxvY2sgc2V0dGluZ3MgdG8gZmFsc2UgdW5sZXNzIGZpZWxkIGlzIGRpc2FibGVkIChlbmFibGUgPT09IGZhbHNlKVxuXHRcdFx0XHR0aGlzLl9ndFNldHRpbmdzW2ldLmxvY2tTZXR0aW5ncyA9XG5cdFx0XHRcdFx0dGhpcy5fZ3RTZXR0aW5nc1tpXS5lbmFibGVkID09PSBmYWxzZSB8fCBmYWxzZTtcblx0XHRcdH1cblx0XHR9XG5cdFx0dGhpcy5yZXN0cnVjdHVyZVNvcnRpbmcoKTtcblx0fVxuXHRASW5wdXQoKVxuXHRzZXQgZ3REYXRhKGluaXRpYWxEYXRhOiBBcnJheTxhbnk+KSB7XG5cdFx0Y29uc3QgZGF0YSA9IHRoaXMuX2d0T3B0aW9ucy5tdXRhdGVEYXRhXG5cdFx0XHQ/IFsuLi5pbml0aWFsRGF0YV1cblx0XHRcdDogdGhpcy5jbG9uZURlZXAoaW5pdGlhbERhdGEpO1xuXHRcdGlmICh0aGlzLmd0T3B0aW9ucy5sYXp5TG9hZCAmJiB0aGlzLmd0SW5mbykge1xuXHRcdFx0dGhpcy5ndE1ldGFQaXBlLnRyYW5zZm9ybShcblx0XHRcdFx0ZGF0YSxcblx0XHRcdFx0dGhpcy5ndE9wdGlvbnMucm93SW5kZXgsXG5cdFx0XHRcdHRoaXMuZ3RJbmZvLnBhZ2VDdXJyZW50IC0gMSxcblx0XHRcdFx0dGhpcy5ndEluZm8ucmVjb3JkTGVuZ3RoXG5cdFx0XHQpO1xuXHRcdFx0aWYgKHRoaXMubGF6eUFsbFNlbGVjdGVkKSB7XG5cdFx0XHRcdGNvbnN0IFVOSVFVRV9ST1dTID0gdGhpcy5zZWxlY3RlZFJvd3MubWFwKHJvdyA9PiByb3cuJCRndFJvd0lkKTtcblx0XHRcdFx0ZGF0YS5tYXAocm93ID0+IHtcblx0XHRcdFx0XHRpZiAoVU5JUVVFX1JPV1MuaW5kZXhPZihyb3cuJCRndFJvd0lkKSA9PT0gLTEpIHtcblx0XHRcdFx0XHRcdHRoaXMuc2VsZWN0ZWRSb3dzLnB1c2gocm93KTtcblx0XHRcdFx0XHR9XG5cdFx0XHRcdH0pO1xuXHRcdFx0XHR0aGlzLl91cGRhdGVNZXRhSW5mbyh0aGlzLnNlbGVjdGVkUm93cywgJ2lzU2VsZWN0ZWQnLCB0cnVlKTtcblx0XHRcdH1cblx0XHR9IGVsc2Uge1xuXHRcdFx0dGhpcy5ndE1ldGFQaXBlLnRyYW5zZm9ybShkYXRhLCB0aGlzLmd0T3B0aW9ucy5yb3dJbmRleCk7XG5cdFx0fVxuXHRcdGlmICh0aGlzLmd0T3B0aW9ucy5yb3dTZWxlY3Rpb25Jbml0aWFsU3RhdGUpIHtcblx0XHRcdGRhdGEubWFwKHJvdyA9PiB7XG5cdFx0XHRcdGNvbnN0IHNlbGVjdGVkID1cblx0XHRcdFx0XHR0eXBlb2YgdGhpcy5ndE9wdGlvbnMucm93U2VsZWN0aW9uSW5pdGlhbFN0YXRlID09PSAnZnVuY3Rpb24nXG5cdFx0XHRcdFx0XHQ/IHRoaXMuZ3RPcHRpb25zLnJvd1NlbGVjdGlvbkluaXRpYWxTdGF0ZShyb3cpXG5cdFx0XHRcdFx0XHQ6IHRoaXMuZ3RPcHRpb25zLnJvd1NlbGVjdGlvbkluaXRpYWxTdGF0ZTtcblx0XHRcdFx0aWYgKHNlbGVjdGVkKSB7XG5cdFx0XHRcdFx0aWYgKHR5cGVvZiB0aGlzLm1ldGFJbmZvW3Jvdy4kJGd0Um93SWRdID09PSAndW5kZWZpbmVkJykge1xuXHRcdFx0XHRcdFx0dGhpcy5tZXRhSW5mb1tyb3cuJCRndFJvd0lkXSA9IHsgaXNTZWxlY3RlZDogdHJ1ZSB9O1xuXHRcdFx0XHRcdH0gZWxzZSB7XG5cdFx0XHRcdFx0XHR0aGlzLm1ldGFJbmZvW3Jvdy4kJGd0Um93SWRdLmlzU2VsZWN0ZWQgPSB0cnVlO1xuXHRcdFx0XHRcdH1cblx0XHRcdFx0XHR0aGlzLnNlbGVjdGVkUm93cy5wdXNoKHJvdyk7XG5cdFx0XHRcdH1cblx0XHRcdH0pO1xuXHRcdH1cblx0XHRpZiAoXG5cdFx0XHR0aGlzLmd0T3B0aW9ucy5yb3dFeHBhbmRJbml0aWFsU3RhdGUgJiZcblx0XHRcdHRoaXMuZ3RPcHRpb25zLnJvd0V4cGFuZEluaXRpYWxDb21wb25lbnRcblx0XHQpIHtcblx0XHRcdGRhdGEubWFwKHJvdyA9PiB7XG5cdFx0XHRcdGNvbnN0IGV4cGFuZGVkID1cblx0XHRcdFx0XHR0eXBlb2YgdGhpcy5ndE9wdGlvbnMucm93RXhwYW5kSW5pdGlhbFN0YXRlID09PSAnZnVuY3Rpb24nXG5cdFx0XHRcdFx0XHQ/IHRoaXMuZ3RPcHRpb25zLnJvd0V4cGFuZEluaXRpYWxTdGF0ZShyb3cpXG5cdFx0XHRcdFx0XHQ6IHRoaXMuZ3RPcHRpb25zLnJvd0V4cGFuZEluaXRpYWxTdGF0ZTtcblx0XHRcdFx0dGhpcy5leHBhbmRlZFJvdyA9IHRoaXMuZ3RPcHRpb25zLnJvd0V4cGFuZEluaXRpYWxDb21wb25lbnQ7XG5cblx0XHRcdFx0aWYgKGV4cGFuZGVkKSB7XG5cdFx0XHRcdFx0aWYgKHR5cGVvZiB0aGlzLm1ldGFJbmZvW3Jvdy4kJGd0Um93SWRdID09PSAndW5kZWZpbmVkJykge1xuXHRcdFx0XHRcdFx0dGhpcy5tZXRhSW5mb1tyb3cuJCRndFJvd0lkXSA9IHsgaXNPcGVuOiB0cnVlIH07XG5cdFx0XHRcdFx0fSBlbHNlIHtcblx0XHRcdFx0XHRcdHRoaXMubWV0YUluZm9bcm93LiQkZ3RSb3dJZF0uaXNPcGVuID0gdHJ1ZTtcblx0XHRcdFx0XHR9XG5cdFx0XHRcdH1cblx0XHRcdH0pO1xuXHRcdH1cblx0XHR0aGlzLl9ndERhdGEgPSBkYXRhO1xuXHR9XG5cblx0QElucHV0KClcblx0c2V0IGd0Um93Q29tcG9uZW50KHZhbHVlOiBUeXBlPEM+KSB7XG5cdFx0Y29uc29sZS53YXJuKFxuXHRcdFx0J0d0Um93Q29tcG9uZW50IGhhcyBiZWVuIGRlcHJlY2F0ZWQgYW5kIHN1cHBvcnQgd2lsbCBiZSByZW1vdmVkIGluIGEgZnV0dXJlIHJlbGVhc2UsIHNlZSBodHRwczovL2dpdGh1Yi5jb20vaGphbG1lcnMvYW5ndWxhci1nZW5lcmljLXRhYmxlL2lzc3Vlcy8zNCdcblx0XHQpO1xuXHRcdHRoaXMuX2d0Um93Q29tcG9uZW50ID0gdmFsdWU7XG5cdH1cblxuXHRwdWJsaWMgY29sdW1uV2lkdGg6IE9iamVjdCA9IHt9O1xuXHRwdWJsaWMgY29uZmlnT2JqZWN0OiBHdENvbmZpZzxSPjtcblx0cHVibGljIHNvcnRPcmRlcjogQXJyYXk8YW55PiA9IFtdO1xuXHRwdWJsaWMgbWV0YUluZm86IHsgW2d0Um93SWQ6IHN0cmluZ106IEd0Um93TWV0YSB9ID0ge307XG5cdHB1YmxpYyBzZWxlY3RlZFJvd3M6IEFycmF5PEd0Um93PiA9IFtdO1xuXHRwdWJsaWMgb3BlblJvd3M6IEFycmF5PEd0Um93PiA9IFtdO1xuXHRwcml2YXRlIF9ndFNldHRpbmdzOiBHdENvbmZpZ1NldHRpbmdbXSA9IFtdO1xuXHRwcml2YXRlIF9ndEZpZWxkczogR3RDb25maWdGaWVsZDxSLCBhbnk+W10gPSBbXTtcblx0cHJpdmF0ZSBfZ3REYXRhOiBBcnJheTxhbnk+O1xuXHRwcml2YXRlIF9ndFRvdGFsczogYW55O1xuXHRwcml2YXRlIF9ndFJvd0NvbXBvbmVudDogVHlwZTxDPjtcblx0cHVibGljIGV4cGFuZGVkUm93OiB7XG5cdFx0Y29tcG9uZW50OiBUeXBlPEM+O1xuXHRcdGRhdGE/OiBBcnJheTxhbnk+O1xuXHR9O1xuXHRwdWJsaWMgZ3REZWZhdWx0VGV4dHM6IEd0VGV4dHMgPSB7XG5cdFx0bG9hZGluZzogJ0xvYWRpbmcuLi4nLFxuXHRcdG5vRGF0YTogJ05vIGRhdGEnLFxuXHRcdG5vTWF0Y2hpbmdEYXRhOiAnTm8gZGF0YSBtYXRjaGluZyByZXN1bHRzIGZvdW5kJyxcblx0XHRub1Zpc2libGVDb2x1bW5zSGVhZGluZzogJ05vIHZpc2libGUgY29sdW1ucycsXG5cdFx0bm9WaXNpYmxlQ29sdW1uczogJ1BsZWFzZSBzZWxlY3QgYXQgbGVhc3Qgb25lIGNvbHVtbiB0byBiZSB2aXNpYmxlLicsXG5cdFx0dGFibGVJbmZvOlxuXHRcdFx0J1Nob3dpbmcgI3JlY29yZEZyb20gdG8gI3JlY29yZFRvIG9mICNyZWNvcmRzQWZ0ZXJTZWFyY2ggZW50cmllcy4nLFxuXHRcdHRhYmxlSW5mb0FmdGVyU2VhcmNoOlxuXHRcdFx0J1Nob3dpbmcgICNyZWNvcmRGcm9tIHRvICNyZWNvcmRUbyBvZiAjcmVjb3Jkc0FmdGVyU2VhcmNoIGVudHJpZXMgKGZpbHRlcmVkIGZyb20gYSB0b3RhbCBvZiAjcmVjb3Jkc0FsbCBlbnRyaWVzKS4nLFxuXHRcdGNzdkRvd25sb2FkOiAnZG93bmxvYWQnLFxuXHRcdHNvcnRMYWJlbDogJ1NvcnQ6Jyxcblx0XHRwYWdpbmF0ZU5leHQ6ICdOZXh0IHBhZ2UnLFxuXHRcdHBhZ2luYXRlUHJldmlvdXM6ICdQcmV2aW91cyBwYWdlJyxcblx0XHRpbmxpbmVFZGl0RWRpdGVkOiAnUHJlc3MgZW50ZXIgdG8gc2F2ZSdcblx0fTtcblx0QElucHV0KCkgZ3RUZXh0czogR3RUZXh0cyA9IHRoaXMuZ3REZWZhdWx0VGV4dHM7XG5cdEBJbnB1dCgpIGd0Q2xhc3Nlczogc3RyaW5nO1xuXHRAT3V0cHV0KCkgZ3RFdmVudDogRXZlbnRFbWl0dGVyPEd0RXZlbnQ+ID0gbmV3IEV2ZW50RW1pdHRlcigpO1xuXHRwdWJsaWMgZ3REZWZhdWx0T3B0aW9uczogR3RPcHRpb25zID0ge1xuXHRcdGNzdkRlbGltaXRlcjogJzsnLFxuXHRcdHN0YWNrOiBmYWxzZSxcblx0XHRsYXp5TG9hZDogZmFsc2UsXG5cdFx0Y2FjaGU6IGZhbHNlLFxuXHRcdGRlYm91bmNlVGltZTogMjAwLFxuXHRcdGhpZ2hsaWdodFNlYXJjaDogZmFsc2UsXG5cdFx0cm93U2VsZWN0aW9uOiBmYWxzZSxcblx0XHRyb3dTZWxlY3Rpb25BbGxvd011bHRpcGxlOiB0cnVlLFxuXHRcdHJvd0V4cGFuZEFsbG93TXVsdGlwbGU6IHRydWUsXG5cdFx0bnVtYmVyT2ZSb3dzOiAxMCxcblx0XHRyZXBvcnRDb2x1bW5XaWR0aDogZmFsc2UsXG5cdFx0YWxsb3dVbnNvcnRlZDogdHJ1ZSxcblx0XHRtdXRhdGVEYXRhOiB0cnVlXG5cdH07XG5cdHByaXZhdGUgX2d0T3B0aW9uczogR3RPcHRpb25zID0gdGhpcy5ndERlZmF1bHRPcHRpb25zO1xuXHRwdWJsaWMgc3RvcmU6IEFycmF5PGFueT4gPSBbXTtcblx0cHVibGljIGxvYWRpbmcgPSB0cnVlO1xuXHRwcml2YXRlIGRlYm91bmNlVGltZXI6IHZvaWQgPSBudWxsO1xuXHRwdWJsaWMgbG9hZGluZ1Byb3BlcnR5OiBzdHJpbmc7XG5cdHB1YmxpYyBsYXp5QWxsU2VsZWN0ZWQgPSBmYWxzZTtcblxuXHRASW5wdXQoKVxuXHRndEluZm86IEd0SW5mb3JtYXRpb24gPSB7XG5cdFx0cGFnZUN1cnJlbnQ6IDEsXG5cdFx0cGFnZVRvdGFsOiAwLFxuXHRcdHJlY29yZEZyb206IDAsXG5cdFx0cmVjb3JkVG86IDAsXG5cdFx0cmVjb3JkTGVuZ3RoOiB0aGlzLmd0T3B0aW9ucy5udW1iZXJPZlJvd3MsXG5cdFx0cmVjb3Jkc0FsbDogMCxcblx0XHRyZWNvcmRzQWZ0ZXJGaWx0ZXI6IDAsXG5cdFx0cmVjb3Jkc0FmdGVyU2VhcmNoOiAwXG5cdH07XG5cblx0cHVibGljIHJlZnJlc2hQaXBlID0gZmFsc2U7XG5cdHB1YmxpYyByZWZyZXNoVG90YWxzID0gZmFsc2U7XG5cdHB1YmxpYyByZWZyZXNoU29ydGluZyA9IGZhbHNlO1xuXHRwdWJsaWMgcmVmcmVzaEZpbHRlciA9IGZhbHNlO1xuXHRwdWJsaWMgcmVmcmVzaFBhZ2VBcnJheSA9IGZhbHNlO1xuXHRwcml2YXRlIGdsb2JhbElubGluZUVkaXRMaXN0ZW5lcjogRnVuY3Rpb247XG5cdHB1YmxpYyBlZGl0ZWRSb3dzOiB7XG5cdFx0W2tleTogc3RyaW5nXToge1xuXHRcdFx0Y2hhbmdlczogeyBba2V5OiBzdHJpbmddOiBHdFJlbmRlckZpZWxkPEd0Um93LCBhbnk+IH07XG5cdFx0XHRyb3c6IEd0Um93O1xuXHRcdH07XG5cdH0gPSB7fTtcblxuXHRwdWJsaWMgZGF0YTogeyBleHBvcnREYXRhOiBBcnJheTxhbnk+IH0gPSB7IGV4cG9ydERhdGE6IFtdIH07IC8vIFN0b3JlIGZpbHRlcmVkIGRhdGEgZm9yIGV4cG9ydFxuXG5cdGNvbnN0cnVjdG9yKHByaXZhdGUgcmVuZGVyZXI6IFJlbmRlcmVyMiwgcHJpdmF0ZSBndE1ldGFQaXBlOiBHdE1ldGFQaXBlKSB7XG5cdFx0dGhpcy5ndEV2ZW50LnN1YnNjcmliZSgoJGV2ZW50OiBHdEV2ZW50KSA9PiB7XG5cdFx0XHRpZiAoJGV2ZW50Lm5hbWUgPT09ICdndC1pbmZvJykge1xuXHRcdFx0XHR0aGlzLnVwZGF0ZVJlY29yZFJhbmdlKCk7XG5cdFx0XHR9XG5cdFx0XHRpZiAoJGV2ZW50Lm5hbWUgPT09ICdndC1yb3ctdXBkYXRlZCcpIHtcblx0XHRcdFx0dGhpcy51cGRhdGVUb3RhbHMoKTtcblx0XHRcdH1cblx0XHR9KTtcblx0fVxuXG5cdC8qKlxuXHQgKiBTb3J0IHRhYmxlIGJ5IG9iamVjdCBrZXkuXG5cdCAqIEBwYXJhbSBvYmplY3RLZXkgLSBuYW1lIG9mIGtleSB0byBzb3J0IG9uLlxuXHQgKiBAcGFyYW0gZXZlbnQgLSBzdWNoIGFzIGtleSBwcmVzcyBkdXJpbmcgc29ydGluZy5cblx0ICovXG5cdHB1YmxpYyBndFNvcnQgPSBmdW5jdGlvbihvYmplY3RLZXk6IHN0cmluZywgZXZlbnQ6IGFueSkge1xuXHRcdHRoaXMuaW5saW5lRWRpdENhbmNlbCgpOyAvLyBjYW5jZWwgaW5saW5lIGVkaXRpbmdcblxuXHRcdC8vIGxvb3AgdGhyb3VnaCBjdXJyZW50IHNldHRpbmdzXG5cdFx0Zm9yIChsZXQgaSA9IDA7IGkgPCB0aGlzLl9ndFNldHRpbmdzLmxlbmd0aDsgaSsrKSB7XG5cdFx0XHRpZiAodGhpcy5fZ3RTZXR0aW5nc1tpXS5vYmplY3RLZXkgPT09IG9iamVjdEtleSkge1xuXHRcdFx0XHQvLyBjaGVjayBpZiBzb3J0aW5nIGlzIGRpc2FibGVkLi4uXG5cdFx0XHRcdGlmIChcblx0XHRcdFx0XHR0aGlzLl9ndFNldHRpbmdzW2ldLnNvcnQgJiZcblx0XHRcdFx0XHR0aGlzLl9ndFNldHRpbmdzW2ldLnNvcnQuaW5kZXhPZignZGlzYWJsZScpICE9PSAtMVxuXHRcdFx0XHQpIHtcblx0XHRcdFx0XHQvLyAuLi5pZiBzbywgZXhpdCBmdW5jdGlvbiB3aXRob3V0IGFwcGx5aW5nIGFueSBzb3J0aW5nXG5cdFx0XHRcdFx0cmV0dXJuO1xuXHRcdFx0XHR9IGVsc2UgaWYgKFxuXHRcdFx0XHRcdC8qIGNoZWNrIGlmIHNvcnRpbmcgaXMgdW5kZWZpbmVkLi4uICovIHR5cGVvZiB0aGlzLl9ndFNldHRpbmdzW2ldXG5cdFx0XHRcdFx0XHQuc29ydCA9PT0gJ3VuZGVmaW5lZCdcblx0XHRcdFx0KSB7XG5cdFx0XHRcdFx0Ly8gLi4uaXMgc28sIHNldCBzb3J0aW5nIHByb3BlcnR5IHRvIGVuYWJsZVxuXHRcdFx0XHRcdHRoaXMuX2d0U2V0dGluZ3NbaV0uc29ydCA9ICdlbmFibGUnO1xuXHRcdFx0XHR9XG5cdFx0XHR9XG5cdFx0fVxuXG5cdFx0Ly8gY2hlY2sgbGVuZ3RoXG5cdFx0Y29uc3QgY3RybEtleSA9IGV2ZW50Lm1ldGFLZXkgfHwgZXZlbnQuY3RybEtleTtcblx0XHRjb25zdCBzb3J0ID0gdGhpcy5zb3J0T3JkZXIuc2xpY2UoMCk7XG5cblx0XHRsZXQgbWF0Y2ggPSAtMTtcblx0XHRsZXQgbWF0Y2hEZXNjID0gLTE7XG5cdFx0bGV0IHBvcyA9IC0xO1xuXG5cdFx0Ly8gY2hlY2sgaWYgcHJvcGVydHkgYWxyZWFkeSBleGl0c1xuXHRcdGZvciAobGV0IGkgPSAwOyBpIDwgc29ydC5sZW5ndGg7IGkrKykge1xuXHRcdFx0Y29uc3QgaGl0ID0gc29ydFtpXS5pbmRleE9mKG9iamVjdEtleSk7XG5cdFx0XHRpZiAoaGl0ICE9PSAtMSkge1xuXHRcdFx0XHRtYXRjaCA9IHRoaXMuc29ydE9yZGVyLmluZGV4T2Yob2JqZWN0S2V5KTtcblx0XHRcdFx0bWF0Y2hEZXNjID1cblx0XHRcdFx0XHRtYXRjaCA9PT0gLTEgPyB0aGlzLnNvcnRPcmRlci5pbmRleE9mKCctJyArIG9iamVjdEtleSkgOiBtYXRjaDtcblx0XHRcdFx0cG9zID0gTWF0aC5tYXgobWF0Y2gsIG1hdGNoRGVzYyk7XG5cdFx0XHR9XG5cdFx0fVxuXG5cdFx0Ly8gaWYgY3RybCBrZXkgb3IgbWV0YSBrZXkgaXMgcHJlc3MgdG9nZXRoZXIgd2l0aCBzb3J0Li4uXG5cdFx0aWYgKGN0cmxLZXkpIHtcblx0XHRcdGlmICh0aGlzLnNvcnRPcmRlclt0aGlzLnNvcnRPcmRlci5sZW5ndGggLSAxXSA9PT0gJyQkZ3RJbml0aWFsUm93SW5kZXgnKSB7XG5cdFx0XHRcdHRoaXMuc29ydE9yZGVyLnBvcCgpO1xuXHRcdFx0fVxuXHRcdFx0c3dpdGNoIChwb3MpIHtcblx0XHRcdFx0Ly8gLi4uYW5kIHByb3BlcnR5IGlzIG5vdCBzb3J0ZWQgYmVmb3JlLi4uXG5cdFx0XHRcdGNhc2UgLTE6XG5cdFx0XHRcdFx0Ly8gLi4uYWRkIHByb3BlcnR5IHRvIHNvcnRpbmdcblx0XHRcdFx0XHR0aGlzLnNvcnRPcmRlci5wdXNoKG9iamVjdEtleSk7XG5cdFx0XHRcdFx0YnJlYWs7XG5cdFx0XHRcdGRlZmF1bHQ6XG5cdFx0XHRcdFx0Ly8gLi4uYW5kIHByb3BlcnR5IGlzIHNvcnRlZCBiZWZvcmUuLi5cblx0XHRcdFx0XHRpZiAobWF0Y2ggIT09IC0xKSB7XG5cdFx0XHRcdFx0XHQvLyAuLi5jaGFuZ2UgZnJvbSBhc2MgdG8gZGVzYyBpZiBzb3J0ZWQgYXNjXG5cdFx0XHRcdFx0XHR0aGlzLnNvcnRPcmRlcltwb3NdID0gJy0nICsgb2JqZWN0S2V5O1xuXHRcdFx0XHRcdH0gZWxzZSBpZiAodGhpcy5zb3J0T3JkZXIubGVuZ3RoID4gMSkge1xuXHRcdFx0XHRcdFx0Ly8gLi4ucmVtb3ZlIHNvcnRpbmcgaWYgc29ydGVkIGRlc2Ncblx0XHRcdFx0XHRcdGlmIChjdHJsS2V5KSB7XG5cdFx0XHRcdFx0XHRcdHRoaXMuc29ydE9yZGVyW3Bvc10gPSBvYmplY3RLZXk7XG5cdFx0XHRcdFx0XHR9IGVsc2Uge1xuXHRcdFx0XHRcdFx0XHR0aGlzLnNvcnRPcmRlci5zcGxpY2UocG9zLCAxKTtcblx0XHRcdFx0XHRcdH1cblx0XHRcdFx0XHR9IGVsc2UgaWYgKHRoaXMuc29ydE9yZGVyLmxlbmd0aCA9PT0gMSkge1xuXHRcdFx0XHRcdFx0Ly8gLi4uc2V0IHNvcnRpbmcgdG8gYXNjIGlmIG9ubHkgc29ydGVkIHByb3BlcnR5XG5cdFx0XHRcdFx0XHR0aGlzLnNvcnRPcmRlcltwb3NdID0gb2JqZWN0S2V5O1xuXHRcdFx0XHRcdH1cblx0XHRcdFx0XHRicmVhaztcblx0XHRcdH1cblx0XHR9IGVsc2Uge1xuXHRcdFx0LyogaWYgY3RybCBrZXkgb3IgbWV0YSBrZXkgaXMgbm90IHByZXNzIHRvZ2V0aGVyIHdpdGggc29ydC4uLiAqL1xuXHRcdFx0c3dpdGNoIChwb3MpIHtcblx0XHRcdFx0Ly8gLi4uYW5kIHByb3BlcnR5IGlzIG5vdCBzb3J0ZWQgYmVmb3JlLi4uXG5cdFx0XHRcdGNhc2UgLTE6XG5cdFx0XHRcdFx0Ly8gLi4uc29ydCBieSBwcm9wZXJ0eVxuXHRcdFx0XHRcdHRoaXMuc29ydE9yZGVyID0gW29iamVjdEtleV07XG5cdFx0XHRcdFx0YnJlYWs7XG5cdFx0XHRcdGRlZmF1bHQ6XG5cdFx0XHRcdFx0Ly8gLi4uY2hhbmdlIGZyb20gZGVzYyB0byBhc2MgYW5kIHZpc2UgdmVyc2Fcblx0XHRcdFx0XHR0aGlzLnNvcnRPcmRlciA9XG5cdFx0XHRcdFx0XHRtYXRjaCAhPT0gLTFcblx0XHRcdFx0XHRcdFx0PyBbJy0nICsgb2JqZWN0S2V5XVxuXHRcdFx0XHRcdFx0XHQ6IGN0cmxLZXkgfHwgIXRoaXMuZ3RPcHRpb25zLmFsbG93VW5zb3J0ZWRcblx0XHRcdFx0XHRcdFx0XHQ/IFtvYmplY3RLZXldXG5cdFx0XHRcdFx0XHRcdFx0OiBbXTtcblx0XHRcdFx0XHRicmVhaztcblx0XHRcdH1cblx0XHR9XG5cblx0XHQvLyB1cGRhdGUgc2V0dGluZ3Mgb2JqZWN0IHdpdGggbmV3IHNvcnRpbmcgaW5mb3JtYXRpb25cblx0XHRmb3IgKGxldCBpID0gMDsgaSA8IHRoaXMuX2d0U2V0dGluZ3MubGVuZ3RoOyBpKyspIHtcblx0XHRcdGlmICh0aGlzLl9ndFNldHRpbmdzW2ldLm9iamVjdEtleSA9PT0gb2JqZWN0S2V5KSB7XG5cdFx0XHRcdHN3aXRjaCAodGhpcy5fZ3RTZXR0aW5nc1tpXS5zb3J0KSB7XG5cdFx0XHRcdFx0Ly8gaWYgc29ydGVkIGFzYy4uLlxuXHRcdFx0XHRcdGNhc2UgJ2FzYyc6XG5cdFx0XHRcdFx0XHQvLyAuLi5jaGFuZ2UgdG8gZGVzY1xuXHRcdFx0XHRcdFx0dGhpcy5fZ3RTZXR0aW5nc1tpXS5zb3J0ID0gJ2Rlc2MnO1xuXHRcdFx0XHRcdFx0YnJlYWs7XG5cdFx0XHRcdFx0Ly8gaWYgc29ydGVkIGRlc2MuLi5cblx0XHRcdFx0XHRjYXNlICdkZXNjJzpcblx0XHRcdFx0XHRcdC8vIC4uLmNoYW5nZSB0byBhc2MgaWYgaXQncyB0aGUgb25seSBzb3J0ZWQgcHJvcGVydHkgb3RoZXJ3aXNlIHJlbW92ZSBzb3J0aW5nXG5cdFx0XHRcdFx0XHR0aGlzLl9ndFNldHRpbmdzW2ldLnNvcnQgPVxuXHRcdFx0XHRcdFx0XHQodGhpcy5zb3J0T3JkZXIubGVuZ3RoID09PSAxICYmIHNvcnQubGVuZ3RoIDwgMikgfHxcblx0XHRcdFx0XHRcdFx0Y3RybEtleSB8fFxuXHRcdFx0XHRcdFx0XHQhdGhpcy5ndE9wdGlvbnMuYWxsb3dVbnNvcnRlZFxuXHRcdFx0XHRcdFx0XHRcdD8gJ2FzYydcblx0XHRcdFx0XHRcdFx0XHQ6ICdlbmFibGUnO1xuXHRcdFx0XHRcdFx0YnJlYWs7XG5cdFx0XHRcdFx0Ly8gaWYgc29ydGluZyBlbmFibGVkLi4uXG5cdFx0XHRcdFx0Y2FzZSAnZW5hYmxlJzpcblx0XHRcdFx0XHRcdC8vIC4uLmNoYW5nZSB0byBhc2Ncblx0XHRcdFx0XHRcdHRoaXMuX2d0U2V0dGluZ3NbaV0uc29ydCA9ICdhc2MnO1xuXHRcdFx0XHRcdFx0YnJlYWs7XG5cdFx0XHRcdH1cblx0XHRcdFx0dGhpcy5fZ3RTZXR0aW5nc1tpXS5zb3J0T3JkZXIgPVxuXHRcdFx0XHRcdHRoaXMuX2d0U2V0dGluZ3NbaV0uc29ydCA9PT0gJ2VuYWJsZSdcblx0XHRcdFx0XHRcdD8gdGhpcy5fZ3RTZXR0aW5ncy5sZW5ndGggLSAxXG5cdFx0XHRcdFx0XHQ6IHRoaXMuc29ydE9yZGVyLmluZGV4T2Yob2JqZWN0S2V5KSA9PT0gLTFcblx0XHRcdFx0XHRcdFx0PyB0aGlzLnNvcnRPcmRlci5pbmRleE9mKCctJyArIG9iamVjdEtleSlcblx0XHRcdFx0XHRcdFx0OiB0aGlzLnNvcnRPcmRlci5pbmRleE9mKG9iamVjdEtleSk7XG5cdFx0XHR9IGVsc2UgaWYgKFxuXHRcdFx0XHR0aGlzLl9ndFNldHRpbmdzW2ldLnNvcnQgJiZcblx0XHRcdFx0dGhpcy5fZ3RTZXR0aW5nc1tpXS5zb3J0LmluZGV4T2YoJ2Rpc2FibGUnKSA9PT0gLTEgJiZcblx0XHRcdFx0dGhpcy5zb3J0T3JkZXIuaW5kZXhPZih0aGlzLl9ndFNldHRpbmdzW2ldLm9iamVjdEtleSkgPT09IC0xICYmXG5cdFx0XHRcdHRoaXMuc29ydE9yZGVyLmluZGV4T2YoJy0nICsgdGhpcy5fZ3RTZXR0aW5nc1tpXS5vYmplY3RLZXkpID09PSAtMVxuXHRcdFx0KSB7XG5cdFx0XHRcdHRoaXMuX2d0U2V0dGluZ3NbaV0uc29ydCA9ICdlbmFibGUnO1xuXHRcdFx0XHR0aGlzLl9ndFNldHRpbmdzW2ldLnNvcnRPcmRlciA9IHRoaXMuX2d0U2V0dGluZ3MubGVuZ3RoIC0gMTtcblx0XHRcdH1cblx0XHR9XG5cblx0XHQvLyByZWZyZXNoIHNvcnRpbmcgcGlwZVxuXHRcdHRoaXMucmVmcmVzaFNvcnRpbmcgPSAhdGhpcy5yZWZyZXNoU29ydGluZztcblx0XHR0aGlzLnJlZnJlc2hQYWdlQXJyYXkgPSAhdGhpcy5yZWZyZXNoUGFnZUFycmF5O1xuXG5cdFx0Ly8gc29ydCBieSBpbml0aWFsIHNvcnQgb3JkZXIgYXMgbGFzdCByZXNvcnRcblx0XHR0aGlzLnNvcnRPcmRlci5wdXNoKCckJGd0SW5pdGlhbFJvd0luZGV4Jyk7XG5cblx0XHQvLyBlbWl0IHNvcnQgZXZlbnRcblx0XHR0aGlzLmd0RXZlbnQuZW1pdCh7XG5cdFx0XHRuYW1lOiAnZ3Qtc29ydGluZy1hcHBsaWVkJyxcblx0XHRcdHZhbHVlOiB0aGlzLnNvcnRPcmRlclxuXHRcdH0pO1xuXHR9O1xuXG5cdC8qKlxuXHQgKiBDaGFuZ2UgbnVtYmVyIG9mIHJvd3MgdG8gYmUgZGlzcGxheWVkLlxuXHQgKiBAcGFyYW0gcm93TGVuZ3RoIC0gdG90YWwgbnVtYmVyIG9mIHJvd3MuXG5cdCAqIEBwYXJhbSByZXNldCAtIHNob3VsZCBwYWdlIGJlIHJlc2V0IHRvIGZpcnN0IHBhZ2UuXG5cdCAqL1xuXHRwdWJsaWMgY2hhbmdlUm93TGVuZ3RoID0gZnVuY3Rpb24ocm93TGVuZ3RoOiBhbnksIHJlc2V0PzogYm9vbGVhbikge1xuXHRcdGxldCBsZW5ndGhWYWx1ZSA9IGlzTmFOKHBhcnNlSW50KHJvd0xlbmd0aCwgMTApKVxuXHRcdFx0PyAwXG5cdFx0XHQ6IHBhcnNlSW50KHJvd0xlbmd0aCwgMTApO1xuXHRcdGxldCBuZXdQb3NpdGlvbiA9IDE7XG5cblx0XHRpZiAoIWxlbmd0aFZhbHVlICYmIHRoaXMuZ3REYXRhKSB7XG5cdFx0XHRsZW5ndGhWYWx1ZSA9IHRoaXMuZ3REYXRhLmxlbmd0aDtcblx0XHR9XG5cblx0XHQvLyBpZiByZXNldCBpcyBub3QgdHJ1ZSBhbmQgd2UncmUgbm90IGxhenkgbG9hZGluZyBkYXRhLi4uXG5cdFx0aWYgKHJlc2V0ICE9PSB0cnVlICYmIHRoaXMuX2d0T3B0aW9ucy5sYXp5TG9hZCAhPT0gdHJ1ZSkge1xuXHRcdFx0Ly8gLi4uZ2V0IGN1cnJlbnQgcG9zaXRpb24gaW4gcmVjb3JkIHNldFxuXHRcdFx0Y29uc3QgY3VycmVudFJlY29yZCA9XG5cdFx0XHRcdHRoaXMuZ3RJbmZvLnJlY29yZExlbmd0aCAqICh0aGlzLmd0SW5mby5wYWdlQ3VycmVudCAtIDEpO1xuXHRcdFx0Y29uc3QgY3VycmVudFBvc2l0aW9uID1cblx0XHRcdFx0dGhpcy5fZ3REYXRhLmluZGV4T2YodGhpcy5fZ3REYXRhW2N1cnJlbnRSZWNvcmRdKSArIDE7XG5cblx0XHRcdC8vIC4uLmdldCBuZXcgcG9zaXRpb25cblx0XHRcdG5ld1Bvc2l0aW9uID0gTWF0aC5jZWlsKGN1cnJlbnRQb3NpdGlvbiAvIGxlbmd0aFZhbHVlKTtcblx0XHR9XG5cblx0XHQvLyBjaGFuZ2Ugcm93IGxlbmd0aFxuXHRcdHRoaXMuZ3RJbmZvLnJlY29yZExlbmd0aCA9IGxlbmd0aFZhbHVlO1xuXG5cdFx0Ly8gZ28gdG8gbmV3IHBvc2l0aW9uXG5cdFx0dGhpcy5ndEluZm8ucGFnZUN1cnJlbnQgPSBuZXdQb3NpdGlvbjtcblxuXHRcdC8vIGlmIGxhenkgbG9hZGluZyBkYXRhLi4uXG5cdFx0aWYgKHRoaXMuX2d0T3B0aW9ucy5sYXp5TG9hZCkge1xuXHRcdFx0Ly8gLi4ucmVwbGFjZSBkYXRhIHdpdGggcGxhY2UgaG9sZGVycyBmb3IgbmV3IGRhdGFcblx0XHRcdHRoaXMuX2d0RGF0YVswXSA9IHRoaXMubG9hZGluZ0NvbnRlbnQobGVuZ3RoVmFsdWUpO1xuXG5cdFx0XHQvLyAuLi5lbXB0eSBjdXJyZW50IHN0b3JlXG5cdFx0XHR0aGlzLnN0b3JlID0gW107XG5cdFx0fVxuXG5cdFx0Ly8gdGhpcy51cGRhdGVSZWNvcmRSYW5nZSgpO1xuXG5cdFx0dGhpcy5ndEV2ZW50LmVtaXQoe1xuXHRcdFx0bmFtZTogJ2d0LXJvdy1sZW5ndGgtY2hhbmdlZCcsXG5cdFx0XHR2YWx1ZTogbGVuZ3RoVmFsdWVcblx0XHR9KTtcblx0fTtcblxuXHQvKipcblx0ICogRm9yY2UgYSByZWRyYXcgb2YgdGFibGUgcm93cy5cblx0ICogQXMgdGhlIHRhYmxlIHVzZXMgcHVyZSBwaXBlcywgd2UgbmVlZCB0byBmb3JjZSBhIHJlZHJhdyBpZiBhbiBvYmplY3QgaW4gdGhlIGFycmF5IGlzIGNoYW5nZWQgdG8gc2VlIHRoZSBjaGFuZ2VzLlxuXHQgKi9cblx0cHVibGljIHJlZHJhdyA9IGZ1bmN0aW9uKCRldmVudD86IGFueSkge1xuXHRcdHRoaXMucmVmcmVzaFNvcnRpbmcgPSAhdGhpcy5yZWZyZXNoU29ydGluZztcblx0XHR0aGlzLnJlZnJlc2hQYWdlQXJyYXkgPSAhdGhpcy5yZWZyZXNoUGFnZUFycmF5O1xuXHRcdHRoaXMucmVmcmVzaFBpcGUgPSAhdGhpcy5yZWZyZXNoUGlwZTtcblx0fTtcblxuXHQvKiogVXBkYXRlIHJlY29yZCByYW5nZS4gKi9cblx0cHJpdmF0ZSB1cGRhdGVSZWNvcmRSYW5nZSgpIHtcblx0XHR0aGlzLmd0SW5mby5yZWNvcmRGcm9tID1cblx0XHRcdHRoaXMuZ3RJbmZvLnJlY29yZHNBZnRlclNlYXJjaCA9PT0gMFxuXHRcdFx0XHQ/IDBcblx0XHRcdFx0OiAodGhpcy5ndEluZm8ucGFnZUN1cnJlbnQgLSAxKSAqIHRoaXMuZ3RJbmZvLnJlY29yZExlbmd0aCArIDE7XG5cdFx0dGhpcy5ndEluZm8ucmVjb3JkVG8gPVxuXHRcdFx0dGhpcy5ndEluZm8ucmVjb3Jkc0FmdGVyU2VhcmNoIDxcblx0XHRcdHRoaXMuZ3RJbmZvLnBhZ2VDdXJyZW50ICogdGhpcy5ndEluZm8ucmVjb3JkTGVuZ3RoXG5cdFx0XHRcdD8gdGhpcy5ndEluZm8ucmVjb3Jkc0FmdGVyU2VhcmNoXG5cdFx0XHRcdDogdGhpcy5ndEluZm8ucGFnZUN1cnJlbnQgKiB0aGlzLmd0SW5mby5yZWNvcmRMZW5ndGg7XG5cdH1cblxuXHQvKiogVXBkYXRlIHRvdGFscy4gKi9cblx0cHJpdmF0ZSB1cGRhdGVUb3RhbHMoKSB7XG5cdFx0dGhpcy5yZWZyZXNoVG90YWxzID0gIXRoaXMucmVmcmVzaFRvdGFscztcblx0fVxuXG5cdC8qKiBHbyB0byBuZXh0IHBhZ2UuICovXG5cdHB1YmxpYyBuZXh0UGFnZSA9IGZ1bmN0aW9uKCkge1xuXHRcdGNvbnN0IHBhZ2UgPVxuXHRcdFx0dGhpcy5ndEluZm8ucGFnZUN1cnJlbnQgPT09IHRoaXMuZ3RJbmZvLnBhZ2VUb3RhbFxuXHRcdFx0XHQ/IHRoaXMuZ3RJbmZvLnBhZ2VUb3RhbFxuXHRcdFx0XHQ6IHRoaXMuZ3RJbmZvLnBhZ2VDdXJyZW50ICsgMTtcblx0XHR0aGlzLmdvVG9QYWdlKHBhZ2UpO1xuXHR9O1xuXG5cdC8qKiBHbyB0byBwcmV2aW91cyBwYWdlLiAqL1xuXHRwdWJsaWMgcHJldmlvdXNQYWdlID0gZnVuY3Rpb24oKSB7XG5cdFx0Y29uc3QgcGFnZSA9XG5cdFx0XHR0aGlzLmd0SW5mby5wYWdlQ3VycmVudCA9PT0gMSA/IDEgOiB0aGlzLmd0SW5mby5wYWdlQ3VycmVudCAtIDE7XG5cdFx0dGhpcy5nb1RvUGFnZShwYWdlKTtcblx0fTtcblxuXHQvKiogUmVxdWVzdCBtb3JlIGRhdGEgKHVzZWQgd2hlbiBsYXp5IGxvYWRpbmcpICovXG5cdHByaXZhdGUgZ2V0RGF0YSA9IGZ1bmN0aW9uKCkge1xuXHRcdC8vIC4uLmVtaXQgZXZlbnQgcmVxdWVzdGluZyBmb3IgbW9yZSBkYXRhXG5cdFx0dGhpcy5ndEV2ZW50LmVtaXQoe1xuXHRcdFx0bmFtZTogJ2d0LXBhZ2UtY2hhbmdlZC1sYXp5Jyxcblx0XHRcdHZhbHVlOiB7XG5cdFx0XHRcdHBhZ2VDdXJyZW50OiB0aGlzLmd0SW5mby5wYWdlQ3VycmVudCxcblx0XHRcdFx0cmVjb3JkTGVuZ3RoOiB0aGlzLmd0SW5mby5yZWNvcmRMZW5ndGhcblx0XHRcdH1cblx0XHR9KTtcblx0fTtcblxuXHQvKipcblx0ICogR28gdG8gc3BlY2lmaWMgcGFnZS5cblx0ICogQHBhcmFtIHBhZ2UgLSBwYWdlIG51bWJlci5cblx0ICovXG5cdHB1YmxpYyBnb1RvUGFnZSA9IGZ1bmN0aW9uKHBhZ2U6IG51bWJlcikge1xuXHRcdGNvbnN0IHByZXZpb3VzUGFnZSA9IHRoaXMuZ3RJbmZvLnBhZ2VDdXJyZW50O1xuXHRcdHRoaXMuZ3RJbmZvLnBhZ2VDdXJyZW50ID0gcGFnZTtcblx0XHR0aGlzLmlubGluZUVkaXRDYW5jZWwoKTsgLy8gY2FuY2VsIGlubGluZSBlZGl0XG5cblx0XHQvLyBpZiBsYXp5IGxvYWRpbmcgYW5kIGlmIHBhZ2UgY29udGFpbnMgbm8gcmVjb3Jkcy4uLlxuXHRcdGlmICh0aGlzLl9ndE9wdGlvbnMubGF6eUxvYWQpIHtcblx0XHRcdC8vIC4uLmlmIGRhdGEgZm9yIGN1cnJlbnQgcGFnZSBjb250YWlucyBubyBlbnRyaWVzLi4uXG5cdFx0XHRpZiAoXG5cdFx0XHRcdHRoaXMuX2d0T3B0aW9ucy5jYWNoZSA9PT0gZmFsc2UgfHxcblx0XHRcdFx0dGhpcy5fZ3REYXRhW3RoaXMuZ3RJbmZvLnBhZ2VDdXJyZW50IC0gMV0ubGVuZ3RoID09PSAwXG5cdFx0XHQpIHtcblx0XHRcdFx0Ly8gLi4uY3JlYXRlIHRlbXBvcmFyeSBjb250ZW50IHdoaWxlIHdhaXRpbmcgZm9yIGRhdGFcblx0XHRcdFx0dGhpcy5fZ3REYXRhW3RoaXMuZ3RJbmZvLnBhZ2VDdXJyZW50IC0gMV0gPSB0aGlzLmxvYWRpbmdDb250ZW50KFxuXHRcdFx0XHRcdHRoaXMuZ3RJbmZvLnJlY29yZExlbmd0aFxuXHRcdFx0XHQpO1xuXHRcdFx0XHR0aGlzLmxvYWRpbmcgPSB0cnVlOyAvLyBsb2FkaW5nIHRydWVcblx0XHRcdH1cblx0XHRcdC8vIC4uLmlmIGZpcnN0IGVudHJ5IGluIGN1cnJlbnQgcGFnZSBlcXVhbHMgb3VyIGxvYWRpbmcgcGxhY2Vob2xkZXIuLi5cblx0XHRcdGlmIChcblx0XHRcdFx0dGhpcy5fZ3REYXRhW3RoaXMuZ3RJbmZvLnBhZ2VDdXJyZW50IC0gMV1bMF1bdGhpcy5sb2FkaW5nUHJvcGVydHldID09PVxuXHRcdFx0XHR0aGlzLmd0VGV4dHMubG9hZGluZ1xuXHRcdFx0KSB7XG5cdFx0XHRcdC8vIC4uLmdldCBkYXRhXG5cdFx0XHRcdGNsZWFyVGltZW91dCh0aGlzLmRlYm91bmNlVGltZXIpO1xuXHRcdFx0XHR0aGlzLmRlYm91bmNlVGltZXIgPSBzZXRUaW1lb3V0KCgpID0+IHtcblx0XHRcdFx0XHR0aGlzLmdldERhdGEoKTtcblx0XHRcdFx0fSwgdGhpcy5fZ3RPcHRpb25zLmRlYm91bmNlVGltZSk7XG5cdFx0XHR9XG5cdFx0fVxuXG5cdFx0Ly8gdGhpcy51cGRhdGVSZWNvcmRSYW5nZSgpO1xuXG5cdFx0Ly8gLi4uZW1pdCBwYWdlIGNoYW5nZSBldmVudFxuXHRcdGlmIChwcmV2aW91c1BhZ2UgIT09IHBhZ2UpIHtcblx0XHRcdHRoaXMuZ3RFdmVudC5lbWl0KHtcblx0XHRcdFx0bmFtZTogJ2d0LXBhZ2UtY2hhbmdlZCcsXG5cdFx0XHRcdHZhbHVlOiB7XG5cdFx0XHRcdFx0cGFnZUN1cnJlbnQ6IHRoaXMuZ3RJbmZvLnBhZ2VDdXJyZW50LFxuXHRcdFx0XHRcdHBhZ2VQcmV2aW91czogcHJldmlvdXNQYWdlLFxuXHRcdFx0XHRcdHJlY29yZExlbmd0aDogdGhpcy5ndEluZm8ucmVjb3JkTGVuZ3RoXG5cdFx0XHRcdH1cblx0XHRcdH0pO1xuXHRcdH1cblx0fTtcblxuXHQvKipcblx0ICogR2V0IG1ldGEgZGF0YSBmb3Igcm93LlxuXHQgKi9cblx0cHVibGljIGdldFJvd1N0YXRlKHJvdzogUik6IEd0Um93TWV0YSB7XG5cdFx0cmV0dXJuIHR5cGVvZiB0aGlzLm1ldGFJbmZvW3Jvdy4kJGd0Um93SWRdID09PSAndW5kZWZpbmVkJ1xuXHRcdFx0PyBudWxsXG5cdFx0XHQ6IHRoaXMubWV0YUluZm9bcm93LiQkZ3RSb3dJZF07XG5cdH1cblxuXHQvKipcblx0ICogRXhwYW5kIGFsbCByb3dzLlxuXHQgKiBAcGFyYW0gZXhwYW5kZWRSb3cgLSBjb21wb25lbnQgdG8gcmVuZGVyIHdoZW4gcm93cyBhcmUgZXhwYW5kZWQuXG5cdCAqL1xuXHRwdWJsaWMgZXhwYW5kQWxsUm93cyhleHBhbmRlZFJvdzogeyBjb21wb25lbnQ6IFR5cGU8Qz47IGRhdGE/OiBhbnkgfSk6IHZvaWQge1xuXHRcdHRoaXMuZXhwYW5kZWRSb3cgPSBleHBhbmRlZFJvdztcblx0XHR0aGlzLl90b2dnbGVBbGxSb3dQcm9wZXJ0eSgnaXNPcGVuJywgdHJ1ZSk7XG5cdH1cblxuXHQvKipcblx0ICogQ29sbGFwc2UgYWxsIHJvd3MuXG5cdCAqL1xuXHRwdWJsaWMgY29sbGFwc2VBbGxSb3dzKCk6IHZvaWQge1xuXHRcdHRoaXMuX3RvZ2dsZUFsbFJvd1Byb3BlcnR5KCdpc09wZW4nLCBmYWxzZSk7XG5cdH1cblxuXHQvKipcblx0ICogU2VsZWN0IGFsbCByb3dzLlxuXHQgKi9cblx0cHVibGljIHNlbGVjdEFsbFJvd3MoKTogdm9pZCB7XG5cdFx0dGhpcy5fdG9nZ2xlQWxsUm93UHJvcGVydHkoJ2lzU2VsZWN0ZWQnLCB0cnVlKTtcblx0fVxuXG5cdC8qKlxuXHQgKiBEZXNlbGVjdCBhbGwgcm93cy5cblx0ICovXG5cdHB1YmxpYyBkZXNlbGVjdEFsbFJvd3MoKTogdm9pZCB7XG5cdFx0dGhpcy5fdG9nZ2xlQWxsUm93UHJvcGVydHkoJ2lzU2VsZWN0ZWQnLCBmYWxzZSk7XG5cdH1cblx0LyoqXG5cdCAqIFRvZ2dsZSBhbGwgcm93cy5cblx0ICovXG5cdHB1YmxpYyB0b2dnbGVBbGxSb3dzKCk6IHZvaWQge1xuXHRcdGlmICh0aGlzLl9ndE9wdGlvbnMubGF6eUxvYWQpIHtcblx0XHRcdGlmICghdGhpcy5sYXp5QWxsU2VsZWN0ZWQgfHwgdGhpcy5zZWxlY3RlZFJvd3MubGVuZ3RoID09PSAwKSB7XG5cdFx0XHRcdHRoaXMuc2VsZWN0QWxsUm93cygpO1xuXHRcdFx0XHR0aGlzLmxhenlBbGxTZWxlY3RlZCA9IHRydWU7XG5cdFx0XHR9IGVsc2Uge1xuXHRcdFx0XHR0aGlzLmRlc2VsZWN0QWxsUm93cygpO1xuXHRcdFx0XHR0aGlzLmxhenlBbGxTZWxlY3RlZCA9IGZhbHNlO1xuXHRcdFx0fVxuXHRcdH0gZWxzZSB7XG5cdFx0XHRpZiAodGhpcy5zZWxlY3RlZFJvd3MubGVuZ3RoICE9PSB0aGlzLmd0RGF0YS5sZW5ndGgpIHtcblx0XHRcdFx0dGhpcy5zZWxlY3RBbGxSb3dzKCk7XG5cdFx0XHR9IGVsc2Uge1xuXHRcdFx0XHR0aGlzLmRlc2VsZWN0QWxsUm93cygpO1xuXHRcdFx0fVxuXHRcdH1cblx0fVxuXG5cdC8qKlxuXHQgKiBUb2dnbGUgcm93IGNvbGxhcHNlZCBzdGF0ZSBpZS4gZXhwYW5kZWQvb3BlbiBvciBjb2xsYXBzZWQvY2xvc2VkLlxuXHQgKiBAcGFyYW0gcm93IC0gcm93IG9iamVjdCB0aGF0IHNob3VsZCBiZSBleHBhbmRlZC9jb2xsYXBzZWQuXG5cdCAqIEBwYXJhbSBleHBhbmRlZFJvdyAtIGNvbXBvbmVudCB0byByZW5kZXIgd2hlbiByb3cgaXMgZXhwYW5kZWQuXG5cdCAqL1xuXHRwdWJsaWMgdG9nZ2xlQ29sbGFwc2UoXG5cdFx0cm93OiBHdFJvdyxcblx0XHRleHBhbmRlZFJvdz86IHsgY29tcG9uZW50OiBUeXBlPEM+OyBkYXRhPzogYW55IH1cblx0KSB7XG5cdFx0aWYgKGV4cGFuZGVkUm93KSB7XG5cdFx0XHR0aGlzLmV4cGFuZGVkUm93ID0gZXhwYW5kZWRSb3c7XG5cdFx0fVxuXHRcdHRoaXMuX3RvZ2dsZVJvd1Byb3BlcnR5KHJvdywgJ2lzT3BlbicpO1xuXHR9XG5cblx0LyoqXG5cdCAqIFRvZ2dsZSByb3cgc2VsZWN0ZWQgc3RhdGUgaWUuIHNlbGVjdGVkIG9yIG5vdC5cblx0ICogQHBhcmFtIHJvdyAtIHJvdyBvYmplY3QgdGhhdCBzaG91bGQgYmUgc2VsZWN0ZWQvZGVzZWxlY3RlZC5cblx0ICovXG5cdHB1YmxpYyB0b2dnbGVTZWxlY3Qocm93OiBHdFJvdykge1xuXHRcdHRoaXMuX3RvZ2dsZVJvd1Byb3BlcnR5KHJvdywgJ2lzU2VsZWN0ZWQnKTtcblx0fVxuXG5cdHB1YmxpYyByb3dDbGljayhyb3c6IEd0Um93LCAkZXZlbnQ6IE1vdXNlRXZlbnQpIHtcblx0XHR0aGlzLmd0RXZlbnQuZW1pdCh7XG5cdFx0XHRuYW1lOiAnZ3Qtcm93LWNsaWNrZWQnLFxuXHRcdFx0dmFsdWU6IHsgcm93OiByb3csIGV2ZW50OiAkZXZlbnQgfVxuXHRcdH0pO1xuXHR9XG5cblx0LyoqXG5cdCAqIFVwZGF0ZSByb3cgZGF0YS5cblx0ICogQHBhcmFtIHJvdyAtIHJvdyBvYmplY3QgdGhhdCBoYXMgYmVlbiBlZGl0ZWQuXG5cdCAqIEBwYXJhbSBvbGRWYWx1ZSAtIHJvdyBvYmplY3QgYmVmb3JlIGVkaXQuXG5cdCAqL1xuXHRwdWJsaWMgdXBkYXRlUm93KHJvdzogR3RSb3csIG9sZFZhbHVlOiBHdFJvdykge1xuXHRcdHRoaXMuX3RvZ2dsZVJvd1Byb3BlcnR5KHJvdywgJ2lzVXBkYXRlZCcsIG9sZFZhbHVlKTtcblx0fVxuXG5cdC8qKlxuXHQgKiByZW1vdmVzIGEgcm93IGZyb20gdGhlIHRhYmxlXG5cdCAqIEBwYXJhbSByb3cgLSB0aGUgcm93IG9iamVjdCB0byByZW1vdmVcblx0ICovXG5cdHB1YmxpYyByZW1vdmVSb3cocm93OiBHdFJvdykge1xuXHRcdGlmICh0aGlzLmlzUm93U2VsZWN0ZWQocm93KSkge1xuXHRcdFx0dGhpcy50b2dnbGVTZWxlY3Qocm93KTtcblx0XHR9XG5cdFx0Y29uc3QgaW5kZXggPSB0aGlzLl9ndERhdGEuaW5kZXhPZihyb3cpO1xuXHRcdHRoaXMuX2d0RGF0YS5zcGxpY2UoaW5kZXgsIDEpO1xuXHR9XG5cblx0LyoqXG5cdCAqIGNoZWNrIGlmIGEgcm93IGlzIHNlbGVjdGVkXG5cdCAqIEBwYXJhbSByb3cgLSByb3cgb2JqZWN0XG5cdCAqL1xuXHRwdWJsaWMgaXNSb3dTZWxlY3RlZChyb3c6IEd0Um93KTogYm9vbGVhbiB7XG5cdFx0cmV0dXJuIChcblx0XHRcdHRoaXMubWV0YUluZm9bcm93LiQkZ3RSb3dJZF0gJiYgdGhpcy5tZXRhSW5mb1tyb3cuJCRndFJvd0lkXS5pc1NlbGVjdGVkXG5cdFx0KTtcblx0fVxuXG5cdC8qKlxuXHQgKiBVcGRhdGUgbWV0YSBpbmZvIGZvciBhbGwgcm93cywgaWUuIGlzU2VsZWN0ZWQsIGlzT3Blbi5cblx0ICogQHBhcmFtIGFycmF5IC0gYXJyYXkgdGhhdCBob2xkcyByb3dzIHRoYXQgbmVlZCB0byBiZSB1cGRhdGVkLlxuXHQgKiBAcGFyYW0gcHJvcGVydHkgLSBuYW1lIG9mIHByb3BlcnR5IHRoYXQgc2hvdWxkIGJlIGNoYW5nZWQvdG9nZ2xlZC5cblx0ICogQHBhcmFtIGFjdGl2ZSAtIHNob3VsZCByb3dzIGJlIGV4cGFuZGVkL29wZW4sIHNlbGVjdGVkLlxuXHQgKiBAcGFyYW0gZXhjZXB0aW9uIC0gdXBkYXRlIGFsbCByb3dzIGV4Y2VwdCB0aGlzIG9uZS5cblx0ICovXG5cdHByaXZhdGUgX3VwZGF0ZU1ldGFJbmZvKFxuXHRcdGFycmF5OiBBcnJheTxHdFJvdz4sXG5cdFx0cHJvcGVydHk6IHN0cmluZyxcblx0XHRhY3RpdmU6IGJvb2xlYW4sXG5cdFx0ZXhjZXB0aW9uPzogR3RSb3dcblx0KSB7XG5cdFx0Zm9yIChsZXQgaSA9IDA7IGkgPCBhcnJheS5sZW5ndGg7IGkrKykge1xuXHRcdFx0aWYgKCF0aGlzLm1ldGFJbmZvW2FycmF5W2ldLiQkZ3RSb3dJZF0pIHtcblx0XHRcdFx0dGhpcy5tZXRhSW5mb1thcnJheVtpXS4kJGd0Um93SWRdID0ge307XG5cdFx0XHR9XG5cdFx0XHRpZiAoZXhjZXB0aW9uICYmIGFycmF5W2ldLiQkZ3RSb3dJZCA9PT0gZXhjZXB0aW9uLiQkZ3RSb3dJZCkge1xuXHRcdFx0fSBlbHNlIHtcblx0XHRcdFx0dGhpcy5tZXRhSW5mb1thcnJheVtpXS4kJGd0Um93SWRdW3Byb3BlcnR5XSA9IGFjdGl2ZTtcblx0XHRcdH1cblx0XHR9XG5cdH1cblxuXHQvKipcblx0ICogUHVzaCBzZWxlY3RlZC9leHBhbmRlZCBsYXp5IGxvYWRlZCByb3dzIHRvIGFycmF5IHdpdGggbWV0YSBkYXRhLlxuXHQgKiBAcGFyYW0gdGFyZ2V0IC0gYXJyYXkgdG8gd2hpY2ggcm93cyBzaG91bGQgYmUgYWRkZWQuXG5cdCAqIEBwYXJhbSBzb3VyY2UgLSBhcnJheSB0aGF0IGhvbGRzIHJvd3MgdGhhdCBzaG91bGQgYmUgYWRkZWQuXG5cdCAqIEByZXR1cm5zIGFycmF5IHdpdGggYWRkZWQgcm93cy5cblx0ICovXG5cdHByaXZhdGUgX3B1c2hMYXp5Um93cyhcblx0XHR0YXJnZXQ6IEFycmF5PEd0Um93Pixcblx0XHRzb3VyY2U6IEFycmF5PEd0Um93PlxuXHQpOiBBcnJheTxHdFJvdz4ge1xuXHRcdGNvbnN0IFVOSVFVRV9ST1dTID0gdGFyZ2V0Lm1hcChyb3cgPT4gcm93LiQkZ3RSb3dJZCk7XG5cdFx0Zm9yIChsZXQgaSA9IDA7IGkgPCBzb3VyY2UubGVuZ3RoOyBpKyspIHtcblx0XHRcdC8vIG9ubHkgYWRkIGlmIG5vdCBhbHJlYWR5IGluIGxpc3Rcblx0XHRcdGlmIChVTklRVUVfUk9XUy5pbmRleE9mKHNvdXJjZVtpXS4kJGd0Um93SWQpID09PSAtMSkge1xuXHRcdFx0XHR0YXJnZXQucHVzaChzb3VyY2VbaV0pO1xuXHRcdFx0fVxuXHRcdH1cblx0XHRyZXR1cm4gdGFyZ2V0O1xuXHR9XG5cblx0LyoqXG5cdCAqIFRvZ2dsZSBtZXRhIGluZm8gZm9yIGFsbCByb3dzLCBpZS4gaXNTZWxlY3RlZCwgaXNPcGVuLlxuXHQgKiBAcGFyYW0gcHJvcGVydHkgLSBuYW1lIG9mIHByb3BlcnR5IHRoYXQgc2hvdWxkIGJlIGNoYW5nZWQvdG9nZ2xlZC5cblx0ICogQHBhcmFtIGFjdGl2ZSAtIHNob3VsZCByb3dzIGJlIGV4cGFuZGVkL29wZW4sIHNlbGVjdGVkLlxuXHQgKi9cblx0cHJpdmF0ZSBfdG9nZ2xlQWxsUm93UHJvcGVydHkocHJvcGVydHk6IHN0cmluZywgYWN0aXZlOiBib29sZWFuKSB7XG5cdFx0bGV0IGV2ZW50TmFtZTogc3RyaW5nO1xuXHRcdGxldCBldmVudFZhbHVlOiBhbnk7XG5cdFx0c3dpdGNoIChwcm9wZXJ0eSkge1xuXHRcdFx0Y2FzZSAnaXNPcGVuJzpcblx0XHRcdFx0Ly8gY2hlY2sgaWYgbXVsdGlwbGUgZXhwYW5kZWQgcm93cyBhcmUgYWxsb3dlZC4uLlxuXHRcdFx0XHRpZiAodGhpcy5fZ3RPcHRpb25zLnJvd0V4cGFuZEFsbG93TXVsdGlwbGUgPT09IGZhbHNlKSB7XG5cdFx0XHRcdFx0Ly8gLi4uaWYgbm90LCBleGl0IGZ1bmN0aW9uXG5cdFx0XHRcdFx0Y29uc29sZS5sb2coXG5cdFx0XHRcdFx0XHQnZmVhdHVyZSBkaXNhYmxlZDogZW5hYmxlIGJ5IHNldHRpbmcgXCJyb3dFeHBhbmRBbGxvd011bHRpcGxlID0gdHJ1ZVwiJ1xuXHRcdFx0XHRcdCk7XG5cdFx0XHRcdFx0cmV0dXJuO1xuXHRcdFx0XHR9XG5cdFx0XHRcdGlmIChhY3RpdmUpIHtcblx0XHRcdFx0XHRldmVudE5hbWUgPSAnZXhwYW5kLWFsbCc7XG5cdFx0XHRcdFx0dGhpcy5vcGVuUm93cyA9IHRoaXMuX2d0T3B0aW9ucy5sYXp5TG9hZFxuXHRcdFx0XHRcdFx0PyB0aGlzLl9wdXNoTGF6eVJvd3MoXG5cdFx0XHRcdFx0XHRcdFx0dGhpcy5vcGVuUm93cyxcblx0XHRcdFx0XHRcdFx0XHR0aGlzLl9ndERhdGFbdGhpcy5ndEluZm8ucGFnZUN1cnJlbnQgLSAxXS5zbGljZSgpXG5cdFx0XHRcdFx0XHQgIClcblx0XHRcdFx0XHRcdDogdGhpcy5fZ3REYXRhLnNsaWNlKCk7XG5cdFx0XHRcdFx0dGhpcy5fdXBkYXRlTWV0YUluZm8odGhpcy5vcGVuUm93cywgcHJvcGVydHksIGFjdGl2ZSk7XG5cdFx0XHRcdH0gZWxzZSB7XG5cdFx0XHRcdFx0ZXZlbnROYW1lID0gJ2NvbGxhcHNlLWFsbCc7XG5cdFx0XHRcdFx0dGhpcy5fdXBkYXRlTWV0YUluZm8odGhpcy5vcGVuUm93cywgcHJvcGVydHksIGFjdGl2ZSk7XG5cdFx0XHRcdFx0dGhpcy5vcGVuUm93cyA9IFtdO1xuXHRcdFx0XHR9XG5cdFx0XHRcdGV2ZW50VmFsdWUgPSB7XG5cdFx0XHRcdFx0ZXhwYW5kZWRSb3dzOiB0aGlzLm9wZW5Sb3dzLFxuXHRcdFx0XHRcdGNoYW5nZWRSb3c6ICdhbGwnXG5cdFx0XHRcdH07XG5cdFx0XHRcdGJyZWFrO1xuXHRcdFx0Y2FzZSAnaXNTZWxlY3RlZCc6XG5cdFx0XHRcdC8vIGNoZWNrIGlmIG11bHRpIHJvdyBzZWxlY3Rpb24gaXMgYWxsb3dlZC4uLlxuXHRcdFx0XHRpZiAodGhpcy5fZ3RPcHRpb25zLnJvd1NlbGVjdGlvbkFsbG93TXVsdGlwbGUgPT09IGZhbHNlKSB7XG5cdFx0XHRcdFx0Ly8gLi4uaWYgbm90LCBleGl0IGZ1bmN0aW9uXG5cdFx0XHRcdFx0Y29uc29sZS5sb2coXG5cdFx0XHRcdFx0XHQnZmVhdHVyZSBkaXNhYmxlZDogZW5hYmxlIGJ5IHNldHRpbmcgXCJyb3dTZWxlY3Rpb25BbGxvd011bHRpcGxlID0gdHJ1ZVwiJ1xuXHRcdFx0XHRcdCk7XG5cdFx0XHRcdFx0cmV0dXJuO1xuXHRcdFx0XHR9XG5cdFx0XHRcdGlmIChhY3RpdmUpIHtcblx0XHRcdFx0XHRldmVudE5hbWUgPSAnc2VsZWN0LWFsbCc7XG5cdFx0XHRcdFx0dGhpcy5zZWxlY3RlZFJvd3MgPSB0aGlzLl9ndE9wdGlvbnMubGF6eUxvYWRcblx0XHRcdFx0XHRcdD8gdGhpcy5fcHVzaExhenlSb3dzKFxuXHRcdFx0XHRcdFx0XHRcdHRoaXMuc2VsZWN0ZWRSb3dzLFxuXHRcdFx0XHRcdFx0XHRcdHRoaXMuX2d0RGF0YVt0aGlzLmd0SW5mby5wYWdlQ3VycmVudCAtIDFdLnNsaWNlKClcblx0XHRcdFx0XHRcdCAgKVxuXHRcdFx0XHRcdFx0OiB0aGlzLl9ndERhdGEuc2xpY2UoKTtcblx0XHRcdFx0XHR0aGlzLl91cGRhdGVNZXRhSW5mbyh0aGlzLnNlbGVjdGVkUm93cywgcHJvcGVydHksIGFjdGl2ZSk7XG5cdFx0XHRcdH0gZWxzZSB7XG5cdFx0XHRcdFx0ZXZlbnROYW1lID0gJ2Rlc2VsZWN0LWFsbCc7XG5cdFx0XHRcdFx0dGhpcy5fdXBkYXRlTWV0YUluZm8odGhpcy5zZWxlY3RlZFJvd3MsIHByb3BlcnR5LCBhY3RpdmUpO1xuXHRcdFx0XHRcdHRoaXMuc2VsZWN0ZWRSb3dzID0gW107XG5cdFx0XHRcdH1cblx0XHRcdFx0ZXZlbnRWYWx1ZSA9IHtcblx0XHRcdFx0XHRzZWxlY3RlZFJvd3M6IHRoaXMuc2VsZWN0ZWRSb3dzLFxuXHRcdFx0XHRcdGNoYW5nZWRSb3c6ICdhbGwnXG5cdFx0XHRcdH07XG5cblx0XHRcdFx0YnJlYWs7XG5cdFx0fVxuXHRcdHRoaXMuZ3RFdmVudC5lbWl0KHtcblx0XHRcdG5hbWU6ICdndC1yb3ctJyArIGV2ZW50TmFtZSxcblx0XHRcdHZhbHVlOiBldmVudFZhbHVlXG5cdFx0fSk7XG5cdH1cblxuXHQvKipcblx0ICogVG9nZ2xlIG1ldGEgaW5mbyBmb3Igcm93LCBpZS4gaXNTZWxlY3RlZCwgaXNPcGVuLlxuXHQgKiBAcGFyYW0gcm93IC0gcm93IG9iamVjdC5cblx0ICogQHBhcmFtIHByb3BlcnR5IC0gbmFtZSBvZiBwcm9wZXJ0eSB0aGF0IHNob3VsZCBiZSBjaGFuZ2VkL3RvZ2dsZWQuXG5cdCAqIEBwYXJhbSBwcm9wZXJ0eVZhbHVlcyAtIG9wdGlvbmFsIHByb3BlcnR5IHZhbHVlcyB0aGF0IGNhbiBiZSBwYXNzZWQuXG5cdCAqL1xuXHRwcml2YXRlIF90b2dnbGVSb3dQcm9wZXJ0eShcblx0XHRyb3c6IEd0Um93LFxuXHRcdHByb3BlcnR5OiBzdHJpbmcsXG5cdFx0cHJvcGVydHlWYWx1ZXM/OiBhbnlcblx0KSB7XG5cdFx0bGV0IGV2ZW50TmFtZTogc3RyaW5nO1xuXHRcdGxldCBldmVudFZhbHVlOiBhbnk7XG5cdFx0Ly8gbWFrZSBzdXJlIGd0Um93SWQgZXhpc3RzIG9uIHJvdyBvYmplY3Rcblx0XHRpZiAodHlwZW9mIHJvdy4kJGd0Um93SWQgIT09ICd1bmRlZmluZWQnKSB7XG5cdFx0XHQvLyBjaGVjayBpZiBtZXRhIGluZm8gZXhpc3RzIGZvciByb3dcblx0XHRcdGlmICghdGhpcy5tZXRhSW5mb1tyb3cuJCRndFJvd0lkXSkge1xuXHRcdFx0XHQvLyBpZiBub3QsIGFkZCBvYmplY3QgdG8gc3RvcmUgbWV0YSBpbmZvXG5cdFx0XHRcdHRoaXMubWV0YUluZm9bcm93LiQkZ3RSb3dJZF0gPSB7fTtcblx0XHRcdH1cblxuXHRcdFx0c3dpdGNoIChwcm9wZXJ0eSkge1xuXHRcdFx0XHRjYXNlICdpc09wZW4nOlxuXHRcdFx0XHRcdGNvbnN0IG9wZW5lZCA9IHRoaXMubWV0YUluZm9bcm93LiQkZ3RSb3dJZF1bcHJvcGVydHldO1xuXG5cdFx0XHRcdFx0Ly8gY2hlY2sgaWYgbXVsdGlwbGUgZXhwYW5kZWQgcm93cyBhcmUgYWxsb3dlZC4uLlxuXHRcdFx0XHRcdGlmICh0aGlzLl9ndE9wdGlvbnMucm93RXhwYW5kQWxsb3dNdWx0aXBsZSA9PT0gZmFsc2UpIHtcblx0XHRcdFx0XHRcdC8vIC4uLmlmIG5vdCwgY29sbGFwc2UgYWxsIHJvd3MgZXhjZXB0IGN1cnJlbnQgcm93XG5cdFx0XHRcdFx0XHR0aGlzLl91cGRhdGVNZXRhSW5mbyh0aGlzLm9wZW5Sb3dzLCBwcm9wZXJ0eSwgZmFsc2UsIHJvdyk7XG5cdFx0XHRcdFx0XHR0aGlzLm9wZW5Sb3dzID0gW107XG5cdFx0XHRcdFx0fVxuXG5cdFx0XHRcdFx0Ly8gY2hlY2sgaWYgcm93IGlzIGV4cGFuZGVkXG5cdFx0XHRcdFx0aWYgKCFvcGVuZWQpIHtcblx0XHRcdFx0XHRcdGV2ZW50TmFtZSA9ICdleHBhbmQnO1xuXHRcdFx0XHRcdFx0Ly8gYWRkIHJvdyB0byBleHBhbmRlZCByb3dzXG5cdFx0XHRcdFx0XHR0aGlzLm9wZW5Sb3dzLnB1c2gocm93KTtcblx0XHRcdFx0XHR9IGVsc2Uge1xuXHRcdFx0XHRcdFx0ZXZlbnROYW1lID0gJ2NvbGxhcHNlJztcblx0XHRcdFx0XHRcdC8vIGxvb3AgdGhyb3VnaCBleHBhbmRlZCByb3dzLi4uXG5cdFx0XHRcdFx0XHRmb3IgKGxldCBpID0gMDsgaSA8IHRoaXMub3BlblJvd3MubGVuZ3RoOyBpKyspIHtcblx0XHRcdFx0XHRcdFx0Ly8gaWYgZXhwYW5kZWQgcm93IGVxdWFscyBwYXNzZWQgcm93Li4uXG5cdFx0XHRcdFx0XHRcdGlmICh0aGlzLm9wZW5Sb3dzW2ldLiQkZ3RSb3dJZCA9PT0gcm93LiQkZ3RSb3dJZCkge1xuXHRcdFx0XHRcdFx0XHRcdC8vIC4uLnJlbW92ZSByb3cgZnJvbSBleHBhbmRlZCByb3dzLi4uXG5cdFx0XHRcdFx0XHRcdFx0dGhpcy5vcGVuUm93cy5zcGxpY2UoaSwgMSk7XG5cblx0XHRcdFx0XHRcdFx0XHQvLyAuLi5hbmQgZXhpdCBsb29wXG5cdFx0XHRcdFx0XHRcdFx0YnJlYWs7XG5cdFx0XHRcdFx0XHRcdH1cblx0XHRcdFx0XHRcdH1cblx0XHRcdFx0XHR9XG5cdFx0XHRcdFx0ZXZlbnRWYWx1ZSA9IHtcblx0XHRcdFx0XHRcdGV4cGFuZGVkUm93czogdGhpcy5vcGVuUm93cyxcblx0XHRcdFx0XHRcdGNoYW5nZWRSb3c6IHJvd1xuXHRcdFx0XHRcdH07XG5cdFx0XHRcdFx0YnJlYWs7XG5cdFx0XHRcdGNhc2UgJ2lzU2VsZWN0ZWQnOlxuXHRcdFx0XHRcdGNvbnN0IHNlbGVjdGVkID0gdGhpcy5tZXRhSW5mb1tyb3cuJCRndFJvd0lkXVtwcm9wZXJ0eV07XG5cblx0XHRcdFx0XHQvLyBjaGVjayBpZiBtdWx0aSByb3cgc2VsZWN0aW9uIGlzIGFsbG93ZWQuLi5cblx0XHRcdFx0XHRpZiAodGhpcy5fZ3RPcHRpb25zLnJvd1NlbGVjdGlvbkFsbG93TXVsdGlwbGUgPT09IGZhbHNlKSB7XG5cdFx0XHRcdFx0XHQvLyAuLi5pZiBub3QsIGRlc2VsZWN0IGFsbCByb3dzIGV4Y2VwdCBjdXJyZW50IHJvd1xuXHRcdFx0XHRcdFx0dGhpcy5fdXBkYXRlTWV0YUluZm8odGhpcy5zZWxlY3RlZFJvd3MsIHByb3BlcnR5LCBmYWxzZSwgcm93KTtcblx0XHRcdFx0XHRcdHRoaXMuc2VsZWN0ZWRSb3dzID0gW107XG5cdFx0XHRcdFx0fVxuXG5cdFx0XHRcdFx0Ly8gY2hlY2sgaWYgcm93IGlzIHNlbGVjdGVkXG5cdFx0XHRcdFx0aWYgKCFzZWxlY3RlZCkge1xuXHRcdFx0XHRcdFx0ZXZlbnROYW1lID0gJ3NlbGVjdCc7XG5cdFx0XHRcdFx0XHQvLyBhZGQgcm93IHRvIHNlbGVjdGVkIHJvd3Ncblx0XHRcdFx0XHRcdHRoaXMuc2VsZWN0ZWRSb3dzLnB1c2gocm93KTtcblx0XHRcdFx0XHR9IGVsc2Uge1xuXHRcdFx0XHRcdFx0aWYgKHRoaXMuZ3RPcHRpb25zLmxhenlMb2FkICYmIHRoaXMubGF6eUFsbFNlbGVjdGVkKSB7XG5cdFx0XHRcdFx0XHRcdHRoaXMubGF6eUFsbFNlbGVjdGVkID0gZmFsc2U7XG5cdFx0XHRcdFx0XHR9XG5cdFx0XHRcdFx0XHRldmVudE5hbWUgPSAnZGVzZWxlY3QnO1xuXHRcdFx0XHRcdFx0Ly8gbG9vcCB0aHJvdWdoIHNlbGVjdGVkIHJvd3MuLi5cblx0XHRcdFx0XHRcdGZvciAobGV0IGkgPSAwOyBpIDwgdGhpcy5zZWxlY3RlZFJvd3MubGVuZ3RoOyBpKyspIHtcblx0XHRcdFx0XHRcdFx0Ly8gaWYgc2VsZWN0ZWQgcm93IGVxdWFscyBwYXNzZWQgcm93Li4uXG5cdFx0XHRcdFx0XHRcdGlmICh0aGlzLnNlbGVjdGVkUm93c1tpXS4kJGd0Um93SWQgPT09IHJvdy4kJGd0Um93SWQpIHtcblx0XHRcdFx0XHRcdFx0XHQvLyAuLi5yZW1vdmUgcm93IGZyb20gc2VsZWN0ZWQgcm93cy4uLlxuXHRcdFx0XHRcdFx0XHRcdHRoaXMuc2VsZWN0ZWRSb3dzLnNwbGljZShpLCAxKTtcblxuXHRcdFx0XHRcdFx0XHRcdC8vIC4uLmFuZCBleGl0IGxvb3Bcblx0XHRcdFx0XHRcdFx0XHRicmVhaztcblx0XHRcdFx0XHRcdFx0fVxuXHRcdFx0XHRcdFx0fVxuXHRcdFx0XHRcdH1cblx0XHRcdFx0XHRldmVudFZhbHVlID0ge1xuXHRcdFx0XHRcdFx0c2VsZWN0ZWRSb3dzOiB0aGlzLnNlbGVjdGVkUm93cyxcblx0XHRcdFx0XHRcdGNoYW5nZWRSb3c6IHJvd1xuXHRcdFx0XHRcdH07XG5cdFx0XHRcdFx0YnJlYWs7XG5cblx0XHRcdFx0Y2FzZSAnaXNVcGRhdGVkJzpcblx0XHRcdFx0XHRldmVudE5hbWUgPSAndXBkYXRlZCc7XG5cdFx0XHRcdFx0Y29uc3Qgb2xkVmFsdWUgPSBwcm9wZXJ0eVZhbHVlcztcblx0XHRcdFx0XHQvLyBjaGVjayBpZiBlZGl0IG9iamVjdCBleGlzdHMgZm9yIHJvd1xuXHRcdFx0XHRcdGlmICh0eXBlb2YgdGhpcy5tZXRhSW5mb1tyb3cuJCRndFJvd0lkXVtwcm9wZXJ0eV0gPT09ICd1bmRlZmluZWQnKSB7XG5cdFx0XHRcdFx0XHR0aGlzLm1ldGFJbmZvW3Jvdy4kJGd0Um93SWRdW3Byb3BlcnR5XSA9IHtcblx0XHRcdFx0XHRcdFx0b3JpZ2luYWxWYWx1ZTogb2xkVmFsdWUsXG5cdFx0XHRcdFx0XHRcdG9sZFZhbHVlOiBvbGRWYWx1ZSxcblx0XHRcdFx0XHRcdFx0bmV3VmFsdWU6IHJvd1xuXHRcdFx0XHRcdFx0fTtcblx0XHRcdFx0XHR9IGVsc2Uge1xuXHRcdFx0XHRcdFx0dGhpcy5tZXRhSW5mb1tyb3cuJCRndFJvd0lkXVtwcm9wZXJ0eV0ub2xkVmFsdWUgPSBvbGRWYWx1ZTtcblx0XHRcdFx0XHRcdHRoaXMubWV0YUluZm9bcm93LiQkZ3RSb3dJZF1bcHJvcGVydHldLm5ld1ZhbHVlID0gcm93O1xuXHRcdFx0XHRcdH1cblx0XHRcdFx0XHRldmVudFZhbHVlID0gdGhpcy5tZXRhSW5mb1tyb3cuJCRndFJvd0lkXVtwcm9wZXJ0eV07XG5cdFx0XHRcdFx0dGhpcy5yZWRyYXcoKTtcblx0XHRcdFx0XHR0aGlzLmlubGluZUVkaXRDYW5jZWwocm93KTtcblx0XHRcdFx0XHQvLyB0aGlzLmd0RGF0YSA9IFsuLi50aGlzLmd0RGF0YS5tYXAoKHIpID0+IHsgcmV0dXJuey4uLnJ9OyB9KV07XG5cdFx0XHRcdFx0YnJlYWs7XG5cdFx0XHR9XG5cdFx0XHR0aGlzLmd0RXZlbnQuZW1pdCh7XG5cdFx0XHRcdG5hbWU6ICdndC1yb3ctJyArIGV2ZW50TmFtZSxcblx0XHRcdFx0dmFsdWU6IGV2ZW50VmFsdWVcblx0XHRcdH0pO1xuXHRcdFx0aWYgKHByb3BlcnR5ICE9PSAnaXNVcGRhdGVkJykge1xuXHRcdFx0XHR0aGlzLm1ldGFJbmZvW3Jvdy4kJGd0Um93SWRdW3Byb3BlcnR5XSA9ICF0aGlzLm1ldGFJbmZvW3Jvdy4kJGd0Um93SWRdW1xuXHRcdFx0XHRcdHByb3BlcnR5XG5cdFx0XHRcdF07XG5cdFx0XHR9XG5cdFx0fVxuXHR9XG5cblx0LyoqXG5cdCAqIFVwZGF0ZSBjb2x1bW4uXG5cdCAqIEBwYXJhbSAkZXZlbnQgLSBrZXkgdXAgZXZlbnQuXG5cdCAqIEBwYXJhbSByb3cgLSByb3cgb2JqZWN0LlxuXHQgKiBAcGFyYW0gY29sdW1uIC0gY29sdW1uIG9iamVjdC5cblx0ICovXG5cdHB1YmxpYyBndFVwZGF0ZUNvbHVtbihcblx0XHQkZXZlbnQ6IEtleWJvYXJkRXZlbnQsXG5cdFx0cm93OiBHdFJvdyxcblx0XHRjb2x1bW46IEd0UmVuZGVyRmllbGQ8YW55LCBhbnk+XG5cdCkge1xuXHRcdHRoaXMuX2VkaXRSb3cocm93LCBjb2x1bW4pO1xuXHR9XG5cblx0LyoqXG5cdCAqIERyb3Bkb3duIHNlbGVjdC5cblx0ICogQHBhcmFtIHJvdyAtIHJvdyBvYmplY3QuXG5cdCAqIEBwYXJhbSBjb2x1bW4gLSBjb2x1bW4gb2JqZWN0LlxuXHQgKi9cblx0cHVibGljIGd0RHJvcGRvd25TZWxlY3Qocm93OiBHdFJvdywgY29sdW1uOiBHdFJlbmRlckZpZWxkPGFueSwgYW55Pikge1xuXHRcdGNvbnN0IG9sZFZhbHVlID0geyAuLi5yb3cgfTtcblx0XHRyb3dbY29sdW1uLm9iamVjdEtleV0gPSBjb2x1bW4ucmVuZGVyVmFsdWU7XG5cdFx0dGhpcy51cGRhdGVSb3cocm93LCBvbGRWYWx1ZSk7XG5cdH1cblxuXHRwcml2YXRlIF9lZGl0Um93KHJvdzogR3RSb3csIGNvbHVtbjogR3RSZW5kZXJGaWVsZDxhbnksIGFueT4pIHtcblx0XHRjb25zdCBPQkpFQ1RfS0VZID0gY29sdW1uLm9iamVjdEtleTsgLy8gZGVjbGFyZSBvYmplY3Qga2V5IHdoaWNoIGNvbnRhaW5zIGNoYW5nZXNcblxuXHRcdC8vIGNoZWNrIGlmIGNlbGwgaGFzIGNoYW5nZWQgdmFsdWVcblx0XHRjb2x1bW4uZWRpdGVkID0gcm93W2NvbHVtbi5vYmplY3RLZXldICE9PSBjb2x1bW4ucmVuZGVyVmFsdWU7XG5cdFx0Ly8gY2hlY2sgaWYgcm93IGNvbnRhaW5zIGNoYW5nZXMuLi5cblx0XHRpZiAoIXRoaXMuZWRpdGVkUm93c1tyb3cuJCRndFJvd0lkXSkge1xuXHRcdFx0Ly8gaWYgbm90LCBjcmVhdGUgYW4gb2JqZWN0IGZvciB0aGUgY2hhbmdlZCByb3dcblx0XHRcdHRoaXMuZWRpdGVkUm93c1tyb3cuJCRndFJvd0lkXSA9IHtcblx0XHRcdFx0Y2hhbmdlczoge30sIC8vIGNyZWF0ZSBwbGFjZWhvbGRlciBmb3IgY2hhbmdlc1xuXHRcdFx0XHRyb3c6IHJvdyAvLyBzdG9yZSByZWZlcmVuY2UgdG8gdGhlIHJvdyB0aGF0IHNob3VsZCBiZSB1cGRhdGVkXG5cdFx0XHR9O1xuXHRcdH1cblxuXHRcdC8vIHN0b3JlIGNoYW5nZWQgY29sdW1uIHVuZGVyIGNoYW5nZXMgaWYgaXQgaGFzIGJlZW4gZWRpdGVkXG5cdFx0aWYgKGNvbHVtbi5lZGl0ZWQpIHtcblx0XHRcdHRoaXMuZWRpdGVkUm93c1tyb3cuJCRndFJvd0lkXS5jaGFuZ2VzW09CSkVDVF9LRVldID0gY29sdW1uO1xuXHRcdH0gZWxzZSB7XG5cdFx0XHQvLyBkZWxldGUgY2hhbmdlIG9iamVjdCBpZiBjb2x1bW4gaXMgdW5jaGFuZ2VkXG5cdFx0XHRkZWxldGUgdGhpcy5lZGl0ZWRSb3dzW3Jvdy4kJGd0Um93SWRdLmNoYW5nZXNbT0JKRUNUX0tFWV07XG5cdFx0XHQvLyBjaGVjayBob3cgbWFueSBjb2x1bW5zIGhhdmUgYmVlbiBjaGFuZ2VkXG5cdFx0XHRjb25zdCBDSEFOR0VEX0NPTFVNTlMgPSBPYmplY3Qua2V5cyhcblx0XHRcdFx0dGhpcy5lZGl0ZWRSb3dzW3Jvdy4kJGd0Um93SWRdLmNoYW5nZXNcblx0XHRcdCkubGVuZ3RoO1xuXHRcdFx0aWYgKENIQU5HRURfQ09MVU1OUyA9PT0gMCkge1xuXHRcdFx0XHQvLyBkZWxldGUgcm93IGZyb20gZWRpdGVkIHJvd3MgaWYgbm8gY29sdW1ucyBoYXZlIGJlZW4gZWRpdGVkXG5cdFx0XHRcdGRlbGV0ZSB0aGlzLmVkaXRlZFJvd3Nbcm93LiQkZ3RSb3dJZF07XG5cdFx0XHR9XG5cdFx0fVxuXHRcdC8vIGlmIG5vIGxpc3RlbmVyIGlzIHByZXNlbnQuLi5cblx0XHRpZiAoIXRoaXMuZ2xvYmFsSW5saW5lRWRpdExpc3RlbmVyKSB7XG5cdFx0XHQvLyAuLi5saXN0ZW4gZm9yIHVwZGF0ZSBldmVudFxuXHRcdFx0dGhpcy5fbGlzdGVuRm9yS2V5ZG93bkV2ZW50KCk7XG5cdFx0fVxuXHR9XG5cdC8qKlxuXHQgKiBMaXN0ZW4gZm9yIGtleSBkb3duIGV2ZW50IC0gbGlzdGVuIGZvciBrZXkgZG93biBldmVudCBkdXJpbmcgaW5saW5lIGVkaXQuXG5cdCAqL1xuXHRwcml2YXRlIF9saXN0ZW5Gb3JLZXlkb3duRXZlbnQoKSB7XG5cdFx0Ly8gYWRkIGdsb2JhbCBsaXN0ZW5lciBmb3Iga2V5IGRvd24gZXZlbnRzXG5cdFx0dGhpcy5nbG9iYWxJbmxpbmVFZGl0TGlzdGVuZXIgPSB0aGlzLnJlbmRlcmVyLmxpc3Rlbihcblx0XHRcdCdkb2N1bWVudCcsXG5cdFx0XHQna2V5ZG93bicsXG5cdFx0XHQkZXZlbnQgPT4ge1xuXHRcdFx0XHRzd2l0Y2ggKCRldmVudC5rZXkpIHtcblx0XHRcdFx0XHRjYXNlICdFbnRlcic6IC8vIHVwZGF0ZSBkYXRhIG9iamVjdFxuXHRcdFx0XHRcdFx0dGhpcy5pbmxpbmVFZGl0VXBkYXRlKCk7XG5cdFx0XHRcdFx0XHRicmVhaztcblx0XHRcdFx0XHRjYXNlICdFc2NhcGUnOiAvLyBjYW5jZWxcblx0XHRcdFx0XHRcdHRoaXMuaW5saW5lRWRpdENhbmNlbCgpO1xuXHRcdFx0XHRcdFx0YnJlYWs7XG5cdFx0XHRcdH1cblx0XHRcdH1cblx0XHQpO1xuXHR9XG5cdC8qKlxuXHQgKiBJbmxpbmUgZWRpdCB1cGRhdGUgLSBhY2NlcHQgY2hhbmdlcyBhbmQgdXBkYXRlIHJvdyB2YWx1ZXMuXG5cdCAqL1xuXHRwdWJsaWMgaW5saW5lRWRpdFVwZGF0ZSgpIHtcblx0XHQvLyBsb29wIHRocm91Z2ggcm93cyB0aGF0IGhhdmUgYmVlbiBlZGl0ZWRcblx0XHRPYmplY3Qua2V5cyh0aGlzLmVkaXRlZFJvd3MpLm1hcChrZXkgPT4ge1xuXHRcdFx0Y29uc3QgUk9XID0gdGhpcy5lZGl0ZWRSb3dzW2tleV0ucm93OyAvLyByb3cgdG8gdXBkYXRlXG5cdFx0XHRjb25zdCBDSEFOR0VTID0gdGhpcy5lZGl0ZWRSb3dzW2tleV0uY2hhbmdlczsgLy8gY2hhbmdlcyB0byB0aGUgcm93XG5cblx0XHRcdC8vIGxvb3AgdGhyb3VnaCBjaGFuZ2VzIGluIHJvd1xuXHRcdFx0T2JqZWN0LmtleXMoQ0hBTkdFUykubWFwKG9iamVjdEtleSA9PiB7XG5cdFx0XHRcdGNvbnN0IG9sZFZhbHVlID0geyAuLi5ST1cgfTtcblx0XHRcdFx0Uk9XW29iamVjdEtleV0gPSBDSEFOR0VTW29iamVjdEtleV0ucmVuZGVyVmFsdWU7IC8vIHVwZGF0ZSBkYXRhIHZhbHVlXG5cdFx0XHRcdHRoaXMudXBkYXRlUm93KFJPVywgb2xkVmFsdWUpOyAvLyB1cGRhdGUgbWV0YSBpbmZvIGZvciByb3cgYW5kIHNlbmQgZXZlbnRcblx0XHRcdFx0Q0hBTkdFU1tvYmplY3RLZXldLmVkaXRlZCA9IGZhbHNlOyAvLyBkaXNhYmxlIGVkaXQgbW9kZVxuXHRcdFx0fSk7XG5cdFx0fSk7XG5cdFx0Ly8gY2xlYXIgcm93cyBtYXJrZWQgYXMgZWRpdGVkIGFzIHRoZSByb3dzIGhhdmUgYmVlbiB1cGRhdGVkXG5cdFx0dGhpcy5lZGl0ZWRSb3dzID0ge307XG5cdFx0Ly8gcmVtb3ZlIGxpc3RlbmVyXG5cdFx0dGhpcy5fc3RvcExpc3RlbmluZ0ZvcktleWRvd25FdmVudCgpO1xuXHR9XG5cdC8qKlxuXHQgKiBJbmxpbmUgZWRpdCBjYW5jZWwgLSBjYW5jZWwgYW5kIHJlc2V0IGlubGluZSBlZGl0cy5cblx0ICovXG5cdHB1YmxpYyBpbmxpbmVFZGl0Q2FuY2VsKHJvdz86IEd0Um93KSB7XG5cdFx0aWYgKHJvdykge1xuXHRcdFx0ZGVsZXRlIHRoaXMuZWRpdGVkUm93c1tyb3cuJCRndFJvd0lkXTtcblx0XHRcdC8vIHJlbW92ZSBsaXN0ZW5lclxuXHRcdFx0dGhpcy5fc3RvcExpc3RlbmluZ0ZvcktleWRvd25FdmVudCgpO1xuXHRcdFx0cmV0dXJuO1xuXHRcdH1cblxuXHRcdC8vIGxvb3AgdGhyb3VnaCByb3dzIHRoYXQgaGF2ZSBiZWVuIGVkaXRlZFxuXHRcdE9iamVjdC5rZXlzKHRoaXMuZWRpdGVkUm93cykubWFwKGtleSA9PiB7XG5cdFx0XHRjb25zdCBST1cgPSB0aGlzLmVkaXRlZFJvd3Nba2V5XS5yb3c7IC8vIHJvdyB0byB1cGRhdGVcblx0XHRcdGNvbnN0IENIQU5HRVMgPSB0aGlzLmVkaXRlZFJvd3Nba2V5XS5jaGFuZ2VzOyAvLyBjaGFuZ2VzIHRvIHRoZSByb3dcblxuXHRcdFx0Ly8gbG9vcCB0aHJvdWdoIGNoYW5nZXMgaW4gcm93XG5cdFx0XHRPYmplY3Qua2V5cyhDSEFOR0VTKS5tYXAob2JqZWN0S2V5ID0+IHtcblx0XHRcdFx0Q0hBTkdFU1tvYmplY3RLZXldLnJlbmRlclZhbHVlID0gUk9XW29iamVjdEtleV07IC8vIHJlc2V0IHJlbmRlcmVkIHZhbHVlXG5cdFx0XHRcdENIQU5HRVNbb2JqZWN0S2V5XS5lZGl0ZWQgPSBmYWxzZTsgLy8gZGlzYWJsZSBlZGl0IG1vZGVcblx0XHRcdH0pO1xuXHRcdH0pO1xuXHRcdC8vIGNsZWFyIHJvd3MgbWFya2VkIGFzIGVkaXRlZCBhcyB0aGUgcm93cyBoYXZlIGJlZW4gdXBkYXRlZFxuXHRcdHRoaXMuZWRpdGVkUm93cyA9IHt9O1xuXHRcdC8vIHJlbW92ZSBsaXN0ZW5lclxuXHRcdHRoaXMuX3N0b3BMaXN0ZW5pbmdGb3JLZXlkb3duRXZlbnQoKTtcblx0fVxuXHQvKipcblx0ICogU3RvcCBsaXN0ZW5pbmcgZm9yIGtleSBkb3duIGV2ZW50IC0gc3RvcCBsaXN0ZW5pbmcgZm9yIGtleSBkb3duIGV2ZW50cyBwYXNzZWQgZHVyaW5nIGlubGluZSBlZGl0LlxuXHQgKi9cblx0cHJpdmF0ZSBfc3RvcExpc3RlbmluZ0ZvcktleWRvd25FdmVudCgpIHtcblx0XHRpZiAodGhpcy5nbG9iYWxJbmxpbmVFZGl0TGlzdGVuZXIpIHtcblx0XHRcdHRoaXMuZ2xvYmFsSW5saW5lRWRpdExpc3RlbmVyKCk7XG5cdFx0XHR0aGlzLmdsb2JhbElubGluZUVkaXRMaXN0ZW5lciA9IG51bGw7XG5cdFx0fVxuXHR9XG5cblx0LyoqXG5cdCAqIEFwcGx5IGZpbHRlcihzKS5cblx0ICogQHBhcmFtIGZpbHRlciAtIG9iamVjdCBjb250YWluaW5nIGtleSB2YWx1ZSBwYWlycywgd2hlcmUgdmFsdWUgc2hvdWxkIGJlIGFycmF5IG9mIHZhbHVlcy5cblx0ICovXG5cdHB1YmxpYyBndEFwcGx5RmlsdGVyKGZpbHRlcjogT2JqZWN0KSB7XG5cdFx0dGhpcy5ndEluZm8uZmlsdGVyID0gZmlsdGVyO1xuXHRcdC8vIGdvIHRvIGZpcnN0IHBhZ2Vcblx0XHR0aGlzLmdvVG9QYWdlKDEpO1xuXHRcdHRoaXMudXBkYXRlVG90YWxzKCk7XG5cdH1cblxuXHQvKiogQ2xlYXIvcmVtb3ZlIGFwcGxpZWQgZmlsdGVyKHMpLiAqL1xuXHRwdWJsaWMgZ3RDbGVhckZpbHRlcigpIHtcblx0XHR0aGlzLmd0SW5mby5maWx0ZXIgPSBmYWxzZTtcblx0XHR0aGlzLnVwZGF0ZVRvdGFscygpO1xuXHRcdC8vIHRoaXMudXBkYXRlUmVjb3JkUmFuZ2UoKTtcblx0fVxuXG5cdC8qKlxuXHQgKiBTZWFyY2hcblx0ICogQHBhcmFtIHZhbHVlIC0gc3RyaW5nIGNvbnRhaW5pbmcgb25lIG9yIG1vcmUgd29yZHNcblx0ICovXG5cdHB1YmxpYyBndFNlYXJjaCh2YWx1ZTogc3RyaW5nKSB7XG5cdFx0dGhpcy5ndEluZm8uc2VhcmNoVGVybXMgPSB2YWx1ZTtcblx0XHQvLyBhbHdheXMgZ28gdG8gZmlyc3QgcGFnZSB3aGVuIHNlYXJjaGluZ1xuXHRcdHRoaXMuZ29Ub1BhZ2UoMSk7XG5cdFx0dGhpcy51cGRhdGVUb3RhbHMoKTtcblx0fVxuXG5cdC8qKlxuXHQgKiBBZGQgcm93c1xuXHQgKiBAcGFyYW0gcm93cyAtIHJvd3MgdG8gYWRkXG5cdCAqIEByZXR1cm5zIG5ldyBkYXRhIGFycmF5LlxuXHQgKi9cblx0cHVibGljIGd0QWRkKHJvd3M6IEFycmF5PFI+KTogUmVhZG9ubHlBcnJheTxSPiB7XG5cdFx0dGhpcy5ndERhdGEgPSBbLi4udGhpcy5ndERhdGEsIC4uLnJvd3NdO1xuXHRcdHJldHVybiBbLi4udGhpcy5ndERhdGFdO1xuXHR9XG5cblx0LyoqXG5cdCAqIERlbGV0ZSByb3dcblx0ICogQHBhcmFtIG9iamVjdEtleSAtIG9iamVjdCBrZXkgeW91IHdhbnQgdG8gZmluZCBtYXRjaCB3aXRoXG5cdCAqIEBwYXJhbSB2YWx1ZSAtIHRoZSB2YWx1ZSB0aGF0IHNob3VsZCBiZSBkZWxldGVkXG5cdCAqIEBwYXJhbSBtYXRjaCAtIGFsbDogZGVsZXRlIGFsbCBtYXRjaGVzLCBmaXJzdDogZGVsZXRlIGZpcnN0IG1hdGNoIChkZWZhdWx0KVxuXHQgKiBAcmV0dXJucyBuZXcgZGF0YSBhcnJheS5cblx0ICovXG5cdHB1YmxpYyBndERlbGV0ZShcblx0XHRvYmplY3RLZXk6IHN0cmluZyxcblx0XHR2YWx1ZTogc3RyaW5nIHwgbnVtYmVyLFxuXHRcdG1hdGNoOiAnZmlyc3QnIHwgJ2FsbCcgPSAnZmlyc3QnXG5cdCk6IFJlYWRvbmx5QXJyYXk8Uj4ge1xuXHRcdGlmIChtYXRjaCA9PT0gJ2ZpcnN0Jykge1xuXHRcdFx0Zm9yIChsZXQgaSA9IDA7IGkgPCB0aGlzLmd0RGF0YS5sZW5ndGg7IGkrKykge1xuXHRcdFx0XHRpZiAodGhpcy5ndERhdGFbaV1bb2JqZWN0S2V5XSA9PT0gdmFsdWUpIHtcblx0XHRcdFx0XHRpZiAodGhpcy5pc1Jvd1NlbGVjdGVkKHRoaXMuZ3REYXRhW2ldKSkge1xuXHRcdFx0XHRcdFx0dGhpcy50b2dnbGVTZWxlY3QodGhpcy5ndERhdGFbaV0pO1xuXHRcdFx0XHRcdH1cblx0XHRcdFx0XHR0aGlzLmd0RGF0YS5zcGxpY2UoaSwgMSk7XG5cdFx0XHRcdFx0dGhpcy5ndERhdGEgPSBbLi4udGhpcy5ndERhdGFdO1xuXHRcdFx0XHRcdGlmIChtYXRjaCA9PT0gJ2ZpcnN0Jykge1xuXHRcdFx0XHRcdFx0YnJlYWs7XG5cdFx0XHRcdFx0fVxuXHRcdFx0XHR9XG5cdFx0XHR9XG5cdFx0fSBlbHNlIHtcblx0XHRcdGZvciAobGV0IGkgPSB0aGlzLmd0RGF0YS5sZW5ndGg7IGkgPiAwOyBpLS0pIHtcblx0XHRcdFx0aWYgKHRoaXMuZ3REYXRhW2kgLSAxXVtvYmplY3RLZXldID09PSB2YWx1ZSkge1xuXHRcdFx0XHRcdGlmICh0aGlzLmlzUm93U2VsZWN0ZWQodGhpcy5ndERhdGFbaSAtIDFdKSkge1xuXHRcdFx0XHRcdFx0dGhpcy50b2dnbGVTZWxlY3QodGhpcy5ndERhdGFbaSAtIDFdKTtcblx0XHRcdFx0XHR9XG5cdFx0XHRcdFx0dGhpcy5ndERhdGEuc3BsaWNlKGkgLSAxLCAxKTtcblx0XHRcdFx0XHR0aGlzLmd0RGF0YSA9IFsuLi50aGlzLmd0RGF0YV07XG5cdFx0XHRcdH1cblx0XHRcdH1cblx0XHR9XG5cdFx0cmV0dXJuIFsuLi50aGlzLmd0RGF0YV07XG5cdH1cblxuXHQvKipcblx0ICogQ3JlYXRlIHN0b3JlIHRvIGhvbGQgcHJldmlvdXNseSBsb2FkZWQgcmVjb3Jkcy5cblx0ICogQHBhcmFtIHJlY29yZHMgLSB0b3RhbCBudW1iZXIgb2YgcmVjb3JkcyBpbiBzdG9yZS5cblx0ICogQHBhcmFtIHBlclBhZ2UgLSBob3cgbWFueSByZWNvcmRzIHRvIHNob3cgcGVyIHBhZ2UuXG5cdCAqIEByZXR1cm5zIGEgbmVzdGVkIGFycmF5IHRvIGhvbGQgcmVjb3JkcyBwZXIgcGFnZS5cblx0ICovXG5cdHByaXZhdGUgY3JlYXRlU3RvcmUocmVjb3JkczogbnVtYmVyLCBwZXJQYWdlOiBudW1iZXIpOiBBcnJheTxBcnJheTxhbnk+PiB7XG5cdFx0Y29uc3Qgc3RvcmVzID0gTWF0aC5jZWlsKHJlY29yZHMgLyBwZXJQYWdlKTtcblx0XHRjb25zdCBzdG9yZTogQXJyYXk8QXJyYXk8YW55Pj4gPSBbXTtcblx0XHRmb3IgKGxldCBpID0gMDsgaSA8IHN0b3JlczsgaSsrKSB7XG5cdFx0XHRzdG9yZVtpXSA9IFtdO1xuXHRcdH1cblx0XHRyZXR1cm4gc3RvcmU7XG5cdH1cblxuXHQvKipcblx0ICogQ3JlYXRlIHBsYWNlaG9sZGVycyBmb3Igcm93cyB3aGlsZSBsb2FkaW5nIGRhdGEgZnJvbSBiYWNrLWVuZC5cblx0ICogQHBhcmFtIHBlclBhZ2UgLSBob3cgbWFueSByZWNvcmRzIHRvIHNob3cgcGVyIHBhZ2UuXG5cdCAqIEByZXR1cm5zIGFuIGFycmF5IGNvbnRhaW5pbmcgZW1wdHkgcmVjb3JkcyB0byBiZSBwcmVzZW50ZWQgd2hpbGUgZmV0Y2hpbmcgcmVhbCBkYXRhLlxuXHQgKi9cblx0cHJpdmF0ZSBsb2FkaW5nQ29udGVudChwZXJQYWdlOiBudW1iZXIpIHtcblx0XHQvLyBjcmVhdGUgcm93IG9iamVjdFxuXHRcdGNvbnN0IHJvd09iamVjdDogT2JqZWN0ID0ge1xuXHRcdFx0JCRsb2FkaW5nOiB0cnVlXG5cdFx0fTtcblx0XHRsZXQgb3JkZXIgPSAwO1xuXG5cdFx0Ly8gc29ydCBzZXR0aW5ncyBieSBjb2x1bW4gb3JkZXJcblx0XHR0aGlzLl9ndFNldHRpbmdzLnNvcnQodGhpcy5nZXRDb2x1bW5PcmRlcik7XG5cblx0XHQvLyBsb29wIHRocm91Z2ggYWxsIHNldHRpbmdzIG9iamVjdHMuLi5cblx0XHRmb3IgKGxldCBpID0gMDsgaSA8IHRoaXMuX2d0U2V0dGluZ3MubGVuZ3RoOyBpKyspIHtcblx0XHRcdGNvbnN0IHNldHRpbmcgPSB0aGlzLl9ndFNldHRpbmdzW2ldO1xuXG5cdFx0XHQvLyAuLi5pZiBjb2x1bW4gaXMgdmlzaWJsZSBhbmQgZW5hYmxlZC4uLlxuXHRcdFx0aWYgKHNldHRpbmcudmlzaWJsZSAhPT0gZmFsc2UgJiYgc2V0dGluZy5lbmFibGVkICE9PSBmYWxzZSkge1xuXHRcdFx0XHQvLyAuLi5pZiBmaXJzdCBjb2x1bW4sIHNldCB2YWx1ZSB0byBsb2FkaW5nIHRleHQgb3RoZXJ3aXNlIGxlYXZlIGl0IGVtcHR5XG5cdFx0XHRcdGlmIChvcmRlciA9PT0gMCkge1xuXHRcdFx0XHRcdHJvd09iamVjdFtzZXR0aW5nLm9iamVjdEtleV0gPSB0aGlzLmd0VGV4dHMubG9hZGluZztcblx0XHRcdFx0XHR0aGlzLmxvYWRpbmdQcm9wZXJ0eSA9IHNldHRpbmcub2JqZWN0S2V5O1xuXHRcdFx0XHR9IGVsc2Uge1xuXHRcdFx0XHRcdHJvd09iamVjdFtzZXR0aW5nLm9iamVjdEtleV0gPSAnJztcblx0XHRcdFx0fVxuXHRcdFx0XHRvcmRlcisrO1xuXHRcdFx0fSBlbHNlIHtcblx0XHRcdFx0cm93T2JqZWN0W3NldHRpbmcub2JqZWN0S2V5XSA9ICcnO1xuXHRcdFx0fVxuXHRcdH1cblxuXHRcdC8vIGNyZWF0ZSBjb250ZW50IHBsYWNlaG9sZGVyXG5cdFx0Y29uc3QgY29udGVudFBsYWNlaG9sZGVyOiBBcnJheTxhbnk+ID0gW107XG5cblx0XHQvLyBjcmVhdGUgZXF1YWwgbnVtYmVyIG9mIHJvd3MgYXMgcm93cyBwZXIgcGFnZVxuXHRcdGZvciAobGV0IGkgPSAwOyBpIDwgcGVyUGFnZTsgaSsrKSB7XG5cdFx0XHQvLyAuLi5hZGQgdGVtcG9yYXJ5IHJvdyBvYmplY3Rcblx0XHRcdGNvbnRlbnRQbGFjZWhvbGRlci5wdXNoKHJvd09iamVjdCk7XG5cdFx0fVxuXHRcdHJldHVybiBjb250ZW50UGxhY2Vob2xkZXI7XG5cdH1cblxuXHQvLyBUT0RPOiBtb3ZlIHRvIGhlbHBlciBmdW5jdGlvbnNcblx0LyoqIFNvcnQgYnkgc29ydCBvcmRlciAqL1xuXHRwcml2YXRlIGdldFNvcnRPcmRlciA9IGZ1bmN0aW9uKGE6IEd0Q29uZmlnU2V0dGluZywgYjogR3RDb25maWdTZXR0aW5nKSB7XG5cdFx0aWYgKGEuc29ydE9yZGVyIDwgYi5zb3J0T3JkZXIpIHtcblx0XHRcdHJldHVybiAtMTtcblx0XHR9XG5cdFx0aWYgKGEuc29ydE9yZGVyID4gYi5zb3J0T3JkZXIgfHwgdHlwZW9mIGEuc29ydE9yZGVyID09PSAndW5kZWZpbmVkJykge1xuXHRcdFx0cmV0dXJuIDE7XG5cdFx0fVxuXHRcdHJldHVybiAwO1xuXHR9O1xuXG5cdC8vIFRPRE86IG1vdmUgdG8gaGVscGVyIGZ1bmN0aW9uc1xuXHQvKiogU29ydCBieSBjb2x1bW4gb3JkZXIgKi9cblx0cHJpdmF0ZSBnZXRDb2x1bW5PcmRlciA9IGZ1bmN0aW9uKGE6IEd0Q29uZmlnU2V0dGluZywgYjogR3RDb25maWdTZXR0aW5nKSB7XG5cdFx0aWYgKGEuY29sdW1uT3JkZXIgPT09IHVuZGVmaW5lZCkge1xuXHRcdFx0cmV0dXJuIC0xO1xuXHRcdH1cblx0XHRpZiAoYS5jb2x1bW5PcmRlciA8IGIuY29sdW1uT3JkZXIpIHtcblx0XHRcdHJldHVybiAtMTtcblx0XHR9XG5cdFx0aWYgKGEuY29sdW1uT3JkZXIgPiBiLmNvbHVtbk9yZGVyKSB7XG5cdFx0XHRyZXR1cm4gMTtcblx0XHR9XG5cdFx0cmV0dXJuIDA7XG5cdH07XG5cblx0Ly8gVE9ETzogbW92ZSB0byBoZWxwZXIgZnVuY3Rpb25zXG5cdC8qKiBDcmVhdGUgYSBkZWVwIGNvcHkgb2YgZGF0YSAqL1xuXHRwcml2YXRlIGNsb25lRGVlcCA9IGZ1bmN0aW9uKG86IGFueSkge1xuXHRcdHJldHVybiBKU09OLnBhcnNlKEpTT04uc3RyaW5naWZ5KG8pKTtcblx0fTtcblxuXHQvKiogRXhwb3J0IGRhdGEgYXMgQ1NWXG5cdCAqIEBwYXJhbSBmaWxlTmFtZSAtIG9wdGlvbmFsIGZpbGUgbmFtZSAob3ZlcnJpZGVzIGRlZmF1bHQgZmlsZSBuYW1lKS5cblx0ICogQHBhcmFtIHVzZUJPTSAtIHVzZSBCT00gKGJ5dGUgb3JkZXIgbWFya2VyKS5cblx0ICovXG5cdHB1YmxpYyBleHBvcnRDU1YoZmlsZU5hbWU/OiBzdHJpbmcsIHVzZUJPTTogYm9vbGVhbiA9IGZhbHNlKSB7XG5cdFx0Y29uc3QgZGF0YSA9IHRoaXMuZGF0YS5leHBvcnREYXRhO1xuXHRcdGxldCBjc3YgPSAnJztcblx0XHRjb25zdCBCT00gPSAnXFx1RkVGRic7XG5cblx0XHQvLyBjc3YgZXhwb3J0IGhlYWRlcnNcblx0XHRmb3IgKGxldCBpID0gMDsgaSA8IHRoaXMuX2d0U2V0dGluZ3MubGVuZ3RoOyBpKyspIHtcblx0XHRcdGlmICh0aGlzLl9ndFNldHRpbmdzW2ldLmV4cG9ydCAhPT0gZmFsc2UpIHtcblx0XHRcdFx0Y3N2ICs9IHRoaXMuZ2V0UHJvcGVydHkodGhpcy5fZ3RGaWVsZHMsIHRoaXMuX2d0U2V0dGluZ3NbaV0ub2JqZWN0S2V5KVxuXHRcdFx0XHRcdC5uYW1lO1xuXG5cdFx0XHRcdGlmIChpIDwgdGhpcy5fZ3RTZXR0aW5ncy5sZW5ndGggLSAxKSB7XG5cdFx0XHRcdFx0Y3N2ICs9IHRoaXMuX2d0T3B0aW9ucy5jc3ZEZWxpbWl0ZXI7XG5cdFx0XHRcdH1cblx0XHRcdH1cblx0XHR9XG5cblx0XHQvLyBjc3YgZXhwb3J0IGJvZHlcblx0XHRkYXRhLmZvckVhY2gocm93ID0+IHtcblx0XHRcdGNzdiArPSAnXFxuJztcblx0XHRcdGZvciAobGV0IGkgPSAwOyBpIDwgdGhpcy5fZ3RTZXR0aW5ncy5sZW5ndGg7IGkrKykge1xuXHRcdFx0XHRpZiAodGhpcy5fZ3RTZXR0aW5nc1tpXS5leHBvcnQgIT09IGZhbHNlKSB7XG5cdFx0XHRcdFx0Ly8gZ2V0IGZpZWxkIHNldHRpbmdzXG5cdFx0XHRcdFx0Y29uc3QgZmllbGRTZXR0aW5nID0gdGhpcy5nZXRQcm9wZXJ0eShcblx0XHRcdFx0XHRcdHRoaXMuX2d0RmllbGRzLFxuXHRcdFx0XHRcdFx0dGhpcy5fZ3RTZXR0aW5nc1tpXS5vYmplY3RLZXlcblx0XHRcdFx0XHQpO1xuXG5cdFx0XHRcdFx0Ly8gZ2V0IGV4cG9ydCB2YWx1ZSwgaWYgZXhwb3J0IGZ1bmN0aW9uIGlzIGRlZmluZWQgdXNlIGl0IG90aGVyd2lzZSBjaGVjayBmb3IgdmFsdWUgZnVuY3Rpb24gYW5kIGFzIGEgbGFzdCByZXNvcnQgZXhwb3J0IHJhdyBkYXRhXG5cdFx0XHRcdFx0bGV0IGV4cG9ydFZhbHVlOiBzdHJpbmcgPVxuXHRcdFx0XHRcdFx0ZmllbGRTZXR0aW5nLmV4cG9ydCAmJiB0eXBlb2YgZmllbGRTZXR0aW5nLmV4cG9ydCA9PT0gJ2Z1bmN0aW9uJ1xuXHRcdFx0XHRcdFx0XHQ/IGZpZWxkU2V0dGluZy5leHBvcnQocm93KVxuXHRcdFx0XHRcdFx0XHQ6IGZpZWxkU2V0dGluZy52YWx1ZSAmJiB0eXBlb2YgZmllbGRTZXR0aW5nLnZhbHVlID09PSAnZnVuY3Rpb24nXG5cdFx0XHRcdFx0XHRcdFx0PyBmaWVsZFNldHRpbmcudmFsdWUocm93KVxuXHRcdFx0XHRcdFx0XHRcdDogcm93W3RoaXMuX2d0U2V0dGluZ3NbaV0ub2JqZWN0S2V5XTtcblxuXHRcdFx0XHRcdC8vIGVzY2FwZSBleHBvcnQgdmFsdWUgdXNpbmcgZG91YmxlIHF1b3RlcyAoXCIpIGlmIGV4cG9ydCB2YWx1ZSBjb250YWlucyBkZWxpbWl0ZXJcblx0XHRcdFx0XHRleHBvcnRWYWx1ZSA9XG5cdFx0XHRcdFx0XHR0eXBlb2YgZXhwb3J0VmFsdWUgPT09ICdzdHJpbmcnICYmXG5cdFx0XHRcdFx0XHRleHBvcnRWYWx1ZS5pbmRleE9mKHRoaXMuX2d0T3B0aW9ucy5jc3ZEZWxpbWl0ZXIpICE9PSAtMVxuXHRcdFx0XHRcdFx0XHQ/ICdcIicgKyBleHBvcnRWYWx1ZSArICdcIidcblx0XHRcdFx0XHRcdFx0OiBleHBvcnRWYWx1ZTtcblxuXHRcdFx0XHRcdGNzdiArPSBleHBvcnRWYWx1ZTtcblx0XHRcdFx0XHRpZiAoaSA8IHRoaXMuX2d0U2V0dGluZ3MubGVuZ3RoIC0gMSkge1xuXHRcdFx0XHRcdFx0Y3N2ICs9IHRoaXMuX2d0T3B0aW9ucy5jc3ZEZWxpbWl0ZXI7XG5cdFx0XHRcdFx0fVxuXHRcdFx0XHR9XG5cdFx0XHR9XG5cdFx0fSk7XG5cblx0XHRjb25zdCBibG9iID0gbmV3IEJsb2IoWyh1c2VCT00gPyBCT00gOiAnJykgKyBjc3ZdLCB7XG5cdFx0XHR0eXBlOiAndGV4dC9jc3Y7Y2hhcnNldD11dGYtOCdcblx0XHR9KTtcblxuXHRcdGlmICh3aW5kb3cubmF2aWdhdG9yLm1zU2F2ZU9yT3BlbkJsb2IpIHtcblx0XHRcdG5hdmlnYXRvci5tc1NhdmVPck9wZW5CbG9iKFxuXHRcdFx0XHRibG9iLFxuXHRcdFx0XHRmaWxlTmFtZSA/IGZpbGVOYW1lICsgJy5jc3YnIDogdGhpcy5ndFRleHRzLmNzdkRvd25sb2FkICsgJy5jc3YnXG5cdFx0XHQpO1xuXHRcdH0gZWxzZSB7XG5cdFx0XHRjb25zdCBsaW5rID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnYScpO1xuXHRcdFx0bGluay5zdHlsZS5kaXNwbGF5ID0gJ25vbmUnO1xuXHRcdFx0ZG9jdW1lbnQuYm9keS5hcHBlbmRDaGlsZChsaW5rKTtcblx0XHRcdGlmIChsaW5rLmRvd25sb2FkICE9PSB1bmRlZmluZWQpIHtcblx0XHRcdFx0bGluay5zZXRBdHRyaWJ1dGUoXG5cdFx0XHRcdFx0J2hyZWYnLFxuXHRcdFx0XHRcdCdkYXRhOnRleHQvY3N2O2NoYXJzZXQ9dXRmLTgsJyArXG5cdFx0XHRcdFx0XHRlbmNvZGVVUklDb21wb25lbnQoKHVzZUJPTSA/IEJPTSA6ICcnKSArIGNzdilcblx0XHRcdFx0KTsgLy8gVVJMLmNyZWF0ZU9iamVjdFVSTChibG9iKSk7XG5cdFx0XHRcdGxpbmsuc2V0QXR0cmlidXRlKFxuXHRcdFx0XHRcdCdkb3dubG9hZCcsXG5cdFx0XHRcdFx0ZmlsZU5hbWUgPyBmaWxlTmFtZSArICcuY3N2JyA6IHRoaXMuZ3RUZXh0cy5jc3ZEb3dubG9hZCArICcuY3N2J1xuXHRcdFx0XHQpO1xuXHRcdFx0XHRkb2N1bWVudC5ib2R5LmFwcGVuZENoaWxkKGxpbmspO1xuXHRcdFx0XHRsaW5rLmNsaWNrKCk7XG5cdFx0XHR9IGVsc2Uge1xuXHRcdFx0XHRjc3YgPSAnZGF0YTp0ZXh0L2NzdjtjaGFyc2V0PXV0Zi04LCcgKyAodXNlQk9NID8gQk9NIDogJycpICsgY3N2O1xuXHRcdFx0XHR3aW5kb3cub3BlbihlbmNvZGVVUklDb21wb25lbnQoY3N2KSk7XG5cdFx0XHR9XG5cdFx0XHRkb2N1bWVudC5ib2R5LnJlbW92ZUNoaWxkKGxpbmspO1xuXHRcdH1cblxuXHRcdC8vIGVtaXQgZXhwb3J0IGV2ZW50XG5cdFx0dGhpcy5ndEV2ZW50LmVtaXQoe1xuXHRcdFx0bmFtZTogJ2d0LWV4cG9ydGVkLWNzdicsXG5cdFx0XHR2YWx1ZTogZmlsZU5hbWUgPyBmaWxlTmFtZSA6IHRoaXMuZ3RUZXh0cy5jc3ZEb3dubG9hZCArICcuY3N2J1xuXHRcdH0pO1xuXHR9XG5cblx0LyoqIFJldHVybiBwcm9wZXJ0eSAqL1xuXHRwcml2YXRlIGdldFByb3BlcnR5ID0gZnVuY3Rpb24oYXJyYXk6IEFycmF5PGFueT4sIGtleTogc3RyaW5nKSB7XG5cdFx0Zm9yIChsZXQgaSA9IDA7IGkgPCBhcnJheS5sZW5ndGg7IGkrKykge1xuXHRcdFx0aWYgKGFycmF5W2ldLm9iamVjdEtleSA9PT0ga2V5KSB7XG5cdFx0XHRcdHJldHVybiBhcnJheVtpXTtcblx0XHRcdH1cblx0XHR9XG5cdH07XG5cblx0cHJpdmF0ZSByZXN0cnVjdHVyZVNvcnRpbmcgPSBmdW5jdGlvbigpIHtcblx0XHQvKiogQ2hlY2sgYW5kIHN0b3JlIHNvcnQgb3JkZXIgdXBvbiBpbml0aWFsaXphdGlvbi5cblx0XHQgKiAgVGhpcyBpcyBkb25lIGJ5IGNoZWNraW5nIHNvcnQgcHJvcGVydGllcyBpbiB0aGUgc2V0dGluZ3MgYXJyYXkgb2YgdGhlIHRhYmxlLCBpZiBubyBzb3J0aW5nIGlzIGRlZmluZWRcblx0XHQgKiAgd2UnbGwgc29ydCB0aGUgZGF0YSBieSB0aGUgZmlyc3QgdmlzaWJsZSBhbmQgZW5hYmxlZCBjb2x1bW4gaW4gdGhlIHRhYmxlKGFzY2VuZGluZykuIFBsZWFzZSBub3RlIHRoYXQgYWN0dWFsbHlcblx0XHQgKiAgc29ydGluZyBoYXZlIHRvIGJlIGRvbmUgc2VydmVyIHNpZGUgd2hlbiBsYXp5IGxvYWRpbmcgZGF0YSBmb3Igb2J2aW91cyByZWFzb25zLiAgKi9cblx0XHQvLyBjcmVhdGUgc29ydGluZyBhcnJheVxuXHRcdGNvbnN0IHNvcnRpbmcgPSBbXTtcblx0XHRpZiAodGhpcy5fZ3RTZXR0aW5ncykge1xuXHRcdFx0Ly8gLi4uc29ydCBzZXR0aW5ncyBieSBzb3J0IG9yZGVyXG5cdFx0XHR0aGlzLl9ndFNldHRpbmdzLnNvcnQodGhpcy5nZXRTb3J0T3JkZXIpO1xuXG5cdFx0XHQvLyAuLi5sb29wIHRocm91Z2ggc2V0dGluZ3Ncblx0XHRcdGZvciAobGV0IGkgPSAwOyBpIDwgdGhpcy5fZ3RTZXR0aW5ncy5sZW5ndGg7IGkrKykge1xuXHRcdFx0XHRjb25zdCBzZXR0aW5nID0gdGhpcy5fZ3RTZXR0aW5nc1tpXTtcblxuXHRcdFx0XHQvLyAuLi5pZiBzb3J0ZWQgYXNjZW5kaW5nLi4uXG5cdFx0XHRcdGlmIChzZXR0aW5nLnNvcnQgPT09ICdhc2MnKSB7XG5cdFx0XHRcdFx0Ly8gLi4uIGFkZCB0byBzb3J0aW5nXG5cdFx0XHRcdFx0c29ydGluZy5wdXNoKHNldHRpbmcub2JqZWN0S2V5KTtcblx0XHRcdFx0fSBlbHNlIGlmIChzZXR0aW5nLnNvcnQgPT09ICdkZXNjJykge1xuXHRcdFx0XHRcdC8qIC4uLmVsc2UgaWYgc29ydGVkIGRlc2NlbmRpbmcuLi4gKi8gLy8gLi4uIGFkZCB0byBzb3J0aW5nXG5cdFx0XHRcdFx0c29ydGluZy5wdXNoKCctJyArIHNldHRpbmcub2JqZWN0S2V5KTtcblx0XHRcdFx0fVxuXHRcdFx0fVxuXHRcdFx0Ly8gLi4uaWYgbm8gc29ydGluZyBhcHBsaWVkLi4uXG5cdFx0XHRpZiAoc29ydGluZy5sZW5ndGggPT09IDApIHtcblx0XHRcdFx0c29ydGluZy5wdXNoKCckJGd0Um93SWQnKTtcblx0XHRcdFx0LyovLyAuLi5zb3J0IHNldHRpbmdzIGJ5IGNvbHVtbiBvcmRlclxuXHRcdFx0XHR0aGlzLl9ndFNldHRpbmdzLnNvcnQodGhpcy5nZXRDb2x1bW5PcmRlcik7XG5cblx0XHRcdFx0Ly8gLi4ubG9vcCB0aHJvdWdoIHNldHRpbmdzXG5cdFx0XHRcdGZvciAobGV0IGkgPSAwOyBpIDwgdGhpcy5fZ3RTZXR0aW5ncy5sZW5ndGg7IGkrKykge1xuXHRcdFx0XHRcdGNvbnN0IHNldHRpbmcgPSB0aGlzLl9ndFNldHRpbmdzW2ldO1xuXG5cdFx0XHRcdFx0Ly8gLi4uaWYgY29sdW1uIGlzIGVuYWJsZWQgYW5kIHZpc2libGUuLi5cblx0XHRcdFx0XHRpZiAoc2V0dGluZy5lbmFibGVkICE9PSBmYWxzZSAmJiBzZXR0aW5nLnZpc2libGUgIT09IGZhbHNlKSB7XG5cdFx0XHRcdFx0XHQvLyAuLi5hZGQgZmlyc3QgbWF0Y2ggYW5kIGV4aXQgZnVuY3Rpb25cblx0XHRcdFx0XHRcdHRoaXMuc29ydE9yZGVyID0gW3RoaXMuX2d0U2V0dGluZ3NbaV0ub2JqZWN0S2V5XTtcblx0XHRcdFx0XHRcdHJldHVybjtcblx0XHRcdFx0XHR9XG5cdFx0XHRcdH0qL1xuXHRcdFx0fVxuXHRcdH1cblxuXHRcdGlmICh0aGlzLnNvcnRPcmRlci5sZW5ndGggPT09IDApIHtcblx0XHRcdHRoaXMuc29ydE9yZGVyID0gc29ydGluZztcblx0XHR9XG5cdH07XG5cblx0bmdPbkluaXQoKSB7XG5cdFx0Ly8gaWYgbnVtYmVyIG9mIHJvdyB0byBkaXNwbGF5IGZyb20gc3RhcnQgaXMgc2V0IHRvIG51bGwgb3IgMC4uLlxuXHRcdGlmICghdGhpcy5ndE9wdGlvbnMubnVtYmVyT2ZSb3dzKSB7XG5cdFx0XHQvLyAuLi5jaGFuZ2Ugcm93IGxlbmd0aFxuXHRcdFx0dGhpcy5jaGFuZ2VSb3dMZW5ndGgodGhpcy5ndE9wdGlvbnMubnVtYmVyT2ZSb3dzKTtcblx0XHR9XG5cdFx0dGhpcy5yZXN0cnVjdHVyZVNvcnRpbmcoKTtcblx0fVxuXG5cdC8qKlxuXHQgKiAgRXh0ZW5kIG9iamVjdCBmdW5jdGlvbi5cblx0ICovXG5cdHByaXZhdGUgZXh0ZW5kID0gZnVuY3Rpb24oYTogT2JqZWN0LCBiOiBPYmplY3QpIHtcblx0XHRmb3IgKGNvbnN0IGtleSBpbiBiKSB7XG5cdFx0XHRpZiAoYi5oYXNPd25Qcm9wZXJ0eShrZXkpKSB7XG5cdFx0XHRcdGFba2V5XSA9IGJba2V5XTtcblx0XHRcdH1cblx0XHR9XG5cdFx0cmV0dXJuIGE7XG5cdH07XG5cblx0bmdPbkNoYW5nZXMoY2hhbmdlczogU2ltcGxlQ2hhbmdlcykge1xuXHRcdC8vIGlmIGd0IHRleHRzIGhhdmUgY2hhbmdlZC4uLlxuXHRcdGlmIChjaGFuZ2VzWydndFRleHRzJ10pIHtcblx0XHRcdC8vIC4uLmV4dGVuZCBndE9wdGlvbnMgZGVmYXVsdCB2YWx1ZXMgd2l0aCB2YWx1ZXMgcGFzc2VkIGludG8gY29tcG9uZW50XG5cdFx0XHR0aGlzLmd0VGV4dHMgPSA8R3RUZXh0cz50aGlzLmV4dGVuZCh0aGlzLmd0RGVmYXVsdFRleHRzLCB0aGlzLmd0VGV4dHMpO1xuXHRcdH1cblxuXHRcdC8vIGlmIGxhenkgbG9hZGluZyBkYXRhIGFuZCBwYWdpbmcgaW5mb3JtYXRpb24gaXMgYXZhaWxhYmxlLi4uXG5cdFx0aWYgKHRoaXMuZ3RPcHRpb25zLmxhenlMb2FkICYmIHRoaXMuZ3RJbmZvKSB7XG5cdFx0XHQvLyAuLi5jYWxjdWxhdGUgdG90YWwgbnVtYmVyIG9mIHBhZ2VzXG5cdFx0XHR0aGlzLmd0SW5mby5wYWdlVG90YWwgPSBNYXRoLmNlaWwoXG5cdFx0XHRcdHRoaXMuZ3RJbmZvLnJlY29yZHNBZnRlclNlYXJjaCAvIHRoaXMuZ3RJbmZvLnJlY29yZExlbmd0aFxuXHRcdFx0KTtcblxuXHRcdFx0Ly8gLi4uZGVjbGFyZSBzdG9yZSBwb3NpdGlvblxuXHRcdFx0Y29uc3Qgc3RvcmVQb3NpdGlvbiA9IHRoaXMuZ3RJbmZvLnBhZ2VDdXJyZW50IC0gMTtcblxuXHRcdFx0Ly8gLi4uYW5kIGlmIHN0b3JlIGlzIGVtcHR5IG9yIHBhZ2UgbGVuZ3RoIGhhcyBjaGFuZ2VkLi4uXG5cdFx0XHRpZiAoXG5cdFx0XHRcdHRoaXMuc3RvcmUubGVuZ3RoID09PSAwIHx8XG5cdFx0XHRcdHRoaXMuc3RvcmVbMF0ubGVuZ3RoICE9PSB0aGlzLmd0SW5mby5yZWNvcmRMZW5ndGhcblx0XHRcdCkge1xuXHRcdFx0XHQvLyAuLi5jcmVhdGUgc3RvcmVcblx0XHRcdFx0dGhpcy5zdG9yZSA9IHRoaXMuY3JlYXRlU3RvcmUoXG5cdFx0XHRcdFx0dGhpcy5ndEluZm8ucmVjb3Jkc0FmdGVyU2VhcmNoLFxuXHRcdFx0XHRcdHRoaXMuZ3RJbmZvLnJlY29yZExlbmd0aFxuXHRcdFx0XHQpO1xuXHRcdFx0fVxuXG5cdFx0XHQvLyAuLi5zdG9yZSByZXRyaWV2ZWQgZGF0YSBpbiBzdG9yZSBhdCBzdG9yZSBwb3NpdGlvblxuXHRcdFx0dGhpcy5zdG9yZVtzdG9yZVBvc2l0aW9uXSA9IHRoaXMuZ3REYXRhO1xuXHRcdFx0dGhpcy5ndEluZm8udmlzaWJsZVJlY29yZHMgPSBbLi4udGhpcy5ndERhdGFdOyAvLyBhZGQgdmlzaWJsZSByb3dzXG5cblx0XHRcdC8vIHJlcGxhY2UgZGF0YSB3aXRoIHN0b3JlXG5cdFx0XHR0aGlzLl9ndERhdGEgPSB0aGlzLnN0b3JlO1xuXHRcdFx0dGhpcy5sb2FkaW5nID0gZmFsc2U7XG5cdFx0XHR0aGlzLnVwZGF0ZVJlY29yZFJhbmdlKCk7XG5cdFx0XHR0aGlzLmd0RXZlbnQuZW1pdCh7XG5cdFx0XHRcdG5hbWU6ICdndC1pbmZvJyxcblx0XHRcdFx0dmFsdWU6IHRoaXMuZ3RJbmZvXG5cdFx0XHR9KTtcblx0XHR9IGVsc2UgaWYgKFxuXHRcdFx0dGhpcy5fZ3REYXRhICYmXG5cdFx0XHR0aGlzLl9ndERhdGEubGVuZ3RoID49IDAgJiZcblx0XHRcdGNoYW5nZXNbJ2d0RGF0YSddICYmXG5cdFx0XHRjaGFuZ2VzWydndERhdGEnXS5wcmV2aW91c1ZhbHVlXG5cdFx0KSB7XG5cdFx0XHR0aGlzLmxvYWRpbmcgPSBmYWxzZTtcblx0XHR9IGVsc2UgaWYgKFxuXHRcdFx0Y2hhbmdlc1snZ3REYXRhJ10gJiZcblx0XHRcdGNoYW5nZXNbJ2d0RGF0YSddLmZpcnN0Q2hhbmdlICYmXG5cdFx0XHR0aGlzLl9ndERhdGEgJiZcblx0XHRcdHRoaXMuX2d0RGF0YS5sZW5ndGggPiAwXG5cdFx0KSB7XG5cdFx0XHR0aGlzLmxvYWRpbmcgPSBmYWxzZTtcblx0XHR9XG5cdH1cblxuXHR0cmFja0J5Rm4oaW5kZXg6IG51bWJlciwgaXRlbTogR3RSb3cpIHtcblx0XHRyZXR1cm4gaXRlbS4kJGd0Um93SWQ7XG5cdH1cblxuXHR0cmFja0J5Q29sdW1uRm4oaW5kZXg6IG51bWJlciwgaXRlbTogR3RDb25maWdGaWVsZDxhbnksIGFueT4pIHtcblx0XHRyZXR1cm4gaXRlbS5vYmplY3RLZXk7XG5cdH1cblxuXHRuZ09uRGVzdHJveSgpIHtcblx0XHQvLyByZW1vdmUgbGlzdGVuZXJcblx0XHR0aGlzLl9zdG9wTGlzdGVuaW5nRm9yS2V5ZG93bkV2ZW50KCk7XG5cdH1cbn1cbiJdfQ==
|