@firestitch/report 18.8.1 → 18.9.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (47) hide show
  1. package/app/reports/components/component-text/component-text.component.d.ts +47 -2
  2. package/app/reports/components/component-text/value-embed.plugin.d.ts +67 -0
  3. package/app/reports/components/report-canvas/report-canvas.component.d.ts +34 -9
  4. package/app/reports/components/report-component/report-component.component.d.ts +10 -1
  5. package/app/reports/data/report.data.d.ts +2 -1
  6. package/app/reports/dialogs/component-settings/component-settings.component.d.ts +8 -0
  7. package/app/reports/enums/report-value-formula.enum.d.ts +6 -0
  8. package/app/reports/export/report-export-collector.service.d.ts +22 -0
  9. package/app/reports/export/report-export.service.d.ts +3 -1
  10. package/app/reports/export/report-pdf.service.d.ts +18 -2
  11. package/app/reports/export/report-pptx.service.d.ts +15 -2
  12. package/app/reports/export/report-text-layout.service.d.ts +35 -0
  13. package/app/reports/format.d.ts +2 -0
  14. package/app/reports/interfaces/report.interface.d.ts +21 -2
  15. package/app/reports/layout.d.ts +2 -0
  16. package/app/reports/services/report-filter-state.service.d.ts +1 -1
  17. package/app/reports/text.d.ts +50 -0
  18. package/app/reports/values.d.ts +17 -0
  19. package/esm2022/app/reports/components/component-text/component-text.component.mjs +213 -16
  20. package/esm2022/app/reports/components/component-text/value-embed.plugin.mjs +484 -0
  21. package/esm2022/app/reports/components/report-canvas/report-canvas.component.mjs +260 -34
  22. package/esm2022/app/reports/components/report-component/report-component.component.mjs +65 -19
  23. package/esm2022/app/reports/data/report.data.mjs +19 -1
  24. package/esm2022/app/reports/dialogs/component-settings/component-settings.component.mjs +134 -23
  25. package/esm2022/app/reports/enums/report-value-formula.enum.mjs +14 -0
  26. package/esm2022/app/reports/export/report-export-collector.service.mjs +147 -43
  27. package/esm2022/app/reports/export/report-export.service.mjs +57 -19
  28. package/esm2022/app/reports/export/report-pdf.service.mjs +304 -65
  29. package/esm2022/app/reports/export/report-pptx.service.mjs +276 -58
  30. package/esm2022/app/reports/export/report-text-layout.service.mjs +241 -0
  31. package/esm2022/app/reports/format.mjs +12 -9
  32. package/esm2022/app/reports/interfaces/report.interface.mjs +1 -1
  33. package/esm2022/app/reports/layout.mjs +11 -1
  34. package/esm2022/app/reports/services/report-filter-state.service.mjs +19 -10
  35. package/esm2022/app/reports/text.mjs +293 -85
  36. package/esm2022/app/reports/values.mjs +183 -0
  37. package/esm2022/app/reports/views/report/fs-ai-report.component.mjs +4 -1
  38. package/esm2022/app/reports/views/report/report.component.mjs +4 -1
  39. package/esm2022/public_api.mjs +2 -1
  40. package/fesm2022/{firestitch-report-echarts-CFnbJx44.mjs → firestitch-report-echarts-DBMOHmBF.mjs} +2 -2
  41. package/fesm2022/{firestitch-report-echarts-CFnbJx44.mjs.map → firestitch-report-echarts-DBMOHmBF.mjs.map} +1 -1
  42. package/fesm2022/{firestitch-report-firestitch-report-CSylkyko.mjs → firestitch-report-firestitch-report-CqbXT1gh.mjs} +3270 -947
  43. package/fesm2022/firestitch-report-firestitch-report-CqbXT1gh.mjs.map +1 -0
  44. package/fesm2022/firestitch-report.mjs +1 -1
  45. package/package.json +1 -1
  46. package/public_api.d.ts +1 -0
  47. package/fesm2022/firestitch-report-firestitch-report-CSylkyko.mjs.map +0 -1
@@ -2,36 +2,43 @@ import { Injectable, inject } from '@angular/core';
2
2
  import { FsPrompt } from '@firestitch/prompt';
3
3
  import { EMPTY, from, of } from 'rxjs';
4
4
  import { catchError, switchMap } from 'rxjs/operators';
5
- import { ReportExportCollectorService, failedPageNames } from './report-export-collector.service';
5
+ import { escapeHtml } from '../text';
6
+ import { ReportExportCollectorService, failedPageNames, } from './report-export-collector.service';
6
7
  import { PDF_LIST_ROWS, ReportPdfService } from './report-pdf.service';
7
8
  import { PPTX_LIST_ROWS, ReportPptxService } from './report-pptx.service';
8
9
  import * as i0 from "@angular/core";
9
- // What the user chose when told the export is incomplete. Retry re-runs the
10
- // whole collection — the queries that failed were killed on a clock, not on
11
- // anything about the data, so a second attempt against a warmed database
12
- // genuinely often succeeds.
10
+ // What the user chose at an export gate. Retry, offered only when the export
11
+ // is incomplete, re-runs the whole collection — the queries that failed were
12
+ // killed on a clock, not on anything about the data, so a second attempt
13
+ // against a warmed database genuinely often succeeds. Download keeps going.
13
14
  const RETRY = 'retry';
14
15
  const DOWNLOAD = 'download';
15
- // Runs a report export end to end: collect every tile, refuse to write a file
16
- // that is missing any of them without saying so, then render.
16
+ // Runs a report export end to end: collect every tile and value, refuse to
17
+ // write a file that is missing any of them without saying so, build it, refuse
18
+ // to save one whose text does not fit its boxes without saying so, then save.
17
19
  //
18
- // The gate is the reason this sits between the collector and the renderers
20
+ // The gates are the reason this sits between the collector and the renderers
19
21
  // rather than in either of them. A deck with five blank pages is worse than no
20
22
  // deck: it looks finished, so it gets emailed to a client, and the pages that
21
23
  // are missing are exactly the ones nobody thinks to check. The renderers can
22
24
  // only describe a hole they are handed; the collector only knows one tile at a
23
25
  // time. Whether the FILE should exist is a decision about the whole report, and
24
26
  // this is the only place that sees it.
27
+ //
28
+ // Failures are decided before the build, which is the expensive part (every
29
+ // chart drawn offscreen, every text block measured), so neither a Retry nor a
30
+ // Cancel pays for one. Text that does not fit its box is known only after it:
31
+ // the build is what measures it.
25
32
  export class ReportExportService {
26
33
  _collector = inject(ReportExportCollectorService);
27
34
  _pdfService = inject(ReportPdfService);
28
35
  _pptxService = inject(ReportPptxService);
29
36
  _prompt = inject(FsPrompt);
30
37
  pdf(report) {
31
- return this._run(report, PDF_LIST_ROWS, (collected) => this._pdfService.export(collected));
38
+ return this._run(report, PDF_LIST_ROWS, (collected) => this._pdfService.build(collected));
32
39
  }
33
40
  powerpoint(report) {
34
- return this._run(report, PPTX_LIST_ROWS, (collected) => this._pptxService.export(collected));
41
+ return this._run(report, PPTX_LIST_ROWS, (collected) => this._pptxService.build(collected));
35
42
  }
36
43
  // Retry re-collects the WHOLE report, not just the tiles that failed. Every
37
44
  // number in one file has to have been true at one moment: refetching four
@@ -40,19 +47,25 @@ export class ReportExportService {
40
47
  //
41
48
  // listRows is the format's own list cap, carried into the retry so a second
42
49
  // attempt fetches what the first did.
43
- _run(report, listRows, render) {
50
+ _run(report, listRows, build) {
44
51
  return this._collector.collect(report, listRows)
45
- .pipe(switchMap((collected) => this._gate(collected)
52
+ .pipe(switchMap((collected) => this._failureGate(collected)
46
53
  .pipe(switchMap((choice) => choice === RETRY
47
- ? this._run(report, listRows, render)
48
- : from(render(collected))))));
54
+ ? this._run(report, listRows, build)
55
+ : this._buildAndSave(collected, build)))));
56
+ }
57
+ // Builds the file, then saves it once the overflow gate lets it through.
58
+ _buildAndSave(collected, build) {
59
+ return from(build(collected))
60
+ .pipe(switchMap((built) => this._overflowGate(built)
61
+ .pipe(switchMap(() => from(Promise.resolve(built.save()))))));
49
62
  }
50
63
  // Resolves to DOWNLOAD when the export is whole (or the user accepted an
51
64
  // incomplete one) and to RETRY when they want another attempt. Cancelling
52
65
  // ends the export quietly: EMPTY completes without emitting, so nothing
53
- // renders and no error surfaces — they know what they just declined.
54
- _gate(collected) {
55
- const failed = failedPageNames(collected);
66
+ // builds and no error surfaces — they know what they just declined.
67
+ _failureGate(collected) {
68
+ const failed = failedPageNames(collected).map(escapeHtml);
56
69
  if (!failed.length) {
57
70
  return of(DOWNLOAD);
58
71
  }
@@ -61,7 +74,7 @@ export class ReportExportService {
61
74
  : `${failed.length} pages could not be generated: <strong>${failed.join('</strong>, <strong>')}</strong>`;
62
75
  return this._prompt.confirm({
63
76
  title: 'Export is incomplete',
64
- template: `${pages}. This usually means those tiles took too long to load. `
77
+ template: `${pages}. This usually means those tiles or values took too long to load. `
65
78
  + 'Retry, or download the file with those pages marked as missing.',
66
79
  buttons: [
67
80
  { label: 'Retry', value: RETRY, color: 'primary' },
@@ -71,10 +84,35 @@ export class ReportExportService {
71
84
  })
72
85
  .pipe(catchError(() => EMPTY));
73
86
  }
87
+ // Resolves to DOWNLOAD when every text block fits its box in the built file,
88
+ // or the user accepted one that does not. There is no Retry: the words are
89
+ // the report's own, so a second attempt would build the same file. Each block
90
+ // is named by its page and the start of its words, and the note says what
91
+ // this format does with the rest. Cancelling ends the export quietly, as at
92
+ // the failure gate, and the built file is dropped unsaved.
93
+ _overflowGate(built) {
94
+ if (!built.overflows.length) {
95
+ return of(DOWNLOAD);
96
+ }
97
+ // A block with no words to quote (an empty table, say) is named by its
98
+ // page alone, not by an empty pair of quotes.
99
+ const blocks = built.overflows
100
+ .map((overflow) => `<strong>${escapeHtml(overflow.page)}</strong>`
101
+ + (overflow.snippet ? ` (“${escapeHtml(overflow.snippet)}”)` : ''));
102
+ return this._prompt.confirm({
103
+ title: 'Text does not fit',
104
+ template: `Some text does not fit its box: ${blocks.join(', ')}. ${built.overflowNote}`,
105
+ buttons: [
106
+ { label: 'Download Anyway', value: DOWNLOAD, color: 'primary' },
107
+ { label: 'Cancel', cancel: true, color: '' },
108
+ ],
109
+ })
110
+ .pipe(catchError(() => EMPTY));
111
+ }
74
112
  static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: ReportExportService, deps: [], target: i0.ɵɵFactoryTarget.Injectable });
75
113
  static ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: ReportExportService });
76
114
  }
77
115
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: ReportExportService, decorators: [{
78
116
  type: Injectable
79
117
  }] });
80
- //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoicmVwb3J0LWV4cG9ydC5zZXJ2aWNlLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vLi4vc3JjL2FwcC9yZXBvcnRzL2V4cG9ydC9yZXBvcnQtZXhwb3J0LnNlcnZpY2UudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUFFLFVBQVUsRUFBRSxNQUFNLEVBQUUsTUFBTSxlQUFlLENBQUM7QUFFbkQsT0FBTyxFQUFFLFFBQVEsRUFBRSxNQUFNLG9CQUFvQixDQUFDO0FBRTlDLE9BQU8sRUFBRSxLQUFLLEVBQWMsSUFBSSxFQUFFLEVBQUUsRUFBRSxNQUFNLE1BQU0sQ0FBQztBQUNuRCxPQUFPLEVBQUUsVUFBVSxFQUFFLFNBQVMsRUFBRSxNQUFNLGdCQUFnQixDQUFDO0FBR3ZELE9BQU8sRUFBbUIsNEJBQTRCLEVBQUUsZUFBZSxFQUFFLE1BQU0sbUNBQW1DLENBQUM7QUFDbkgsT0FBTyxFQUFFLGFBQWEsRUFBRSxnQkFBZ0IsRUFBRSxNQUFNLHNCQUFzQixDQUFDO0FBQ3ZFLE9BQU8sRUFBRSxjQUFjLEVBQUUsaUJBQWlCLEVBQUUsTUFBTSx1QkFBdUIsQ0FBQzs7QUFHMUUsNEVBQTRFO0FBQzVFLDRFQUE0RTtBQUM1RSx5RUFBeUU7QUFDekUsNEJBQTRCO0FBQzVCLE1BQU0sS0FBSyxHQUFHLE9BQU8sQ0FBQztBQUN0QixNQUFNLFFBQVEsR0FBRyxVQUFVLENBQUM7QUFFNUIsOEVBQThFO0FBQzlFLDhEQUE4RDtBQUM5RCxFQUFFO0FBQ0YsMkVBQTJFO0FBQzNFLCtFQUErRTtBQUMvRSw4RUFBOEU7QUFDOUUsNkVBQTZFO0FBQzdFLCtFQUErRTtBQUMvRSxnRkFBZ0Y7QUFDaEYsdUNBQXVDO0FBRXZDLE1BQU0sT0FBTyxtQkFBbUI7SUFFdEIsVUFBVSxHQUFHLE1BQU0sQ0FBQyw0QkFBNEIsQ0FBQyxDQUFDO0lBQ2xELFdBQVcsR0FBRyxNQUFNLENBQUMsZ0JBQWdCLENBQUMsQ0FBQztJQUN2QyxZQUFZLEdB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cm9tICdAYW5ndWxhci9jb3JlJztcblxuaW1wb3J0IHsgRnNQcm9tcHQgfSBmcm9tICdAZmlyZXN0aXRjaC9wcm9tcHQnO1xuXG5pbXBvcnQgeyBFTVBUWSwgT2JzZXJ2YWJsZSwgZnJvbSwgb2YgfSBmcm9tICdyeGpzJztcbmltcG9ydCB7IGNhdGNoRXJyb3IsIHN3aXRjaE1hcCB9IGZyb20gJ3J4anMvb3BlcmF0b3JzJztcblxuaW1wb3J0IHsgUmVwb3J0IH0gZnJvbSAnLi4vaW50ZXJmYWNlcy9yZXBvcnQuaW50ZXJmYWNlJztcbmltcG9ydCB7IENvbGxlY3RlZFJlcG9ydCwgUmVwb3J0RXhwb3J0Q29sbGVjdG9yU2VydmljZSwgZmFpbGVkUGFnZU5hbWVzIH0gZnJvbSAnLi9yZXBvcnQtZXhwb3J0LWNvbGxlY3Rvci5zZXJ2aWNlJztcbmltcG9ydCB7IFBERl9MSVNUX1JPV1MsIFJlcG9ydFBkZlNlcnZpY2UgfSBmcm9tICcuL3JlcG9ydC1wZGYuc2VydmljZSc7XG5pbXBvcnQgeyBQUFRYX0xJU1RfUk9XUywgUmVwb3J0UHB0eFNlcnZpY2UgfSBmcm9tICcuL3JlcG9ydC1wcHR4LnNlcnZpY2UnO1xuXG5cbi8vIFdoYXQgdGhlIHVzZXIgY2hvc2Ugd2hlbiB0b2xkIHRoZSBleHBvcnQgaXMgaW5jb21wbGV0ZS4gUmV0cnkgcmUtcnVucyB0aGVcbi8vIHdob2xlIGNvbGxlY3Rpb24g4oCUIHRoZSBxdWVyaWVzIHRoYXQgZmFpbGVkIHdlcmUga2lsbGVkIG9uIGEgY2xvY2ssIG5vdCBvblxuLy8gYW55dGhpbmcgYWJvdXQgdGhlIGRhdGEsIHNvIGEgc2Vjb25kIGF0dGVtcHQgYWdhaW5zdCBhIHdhcm1lZCBkYXRhYmFzZVxuLy8gZ2VudWluZWx5IG9mdGVuIHN1Y2NlZWRzLlxuY29uc3QgUkVUUlkgPSAncmV0cnknO1xuY29uc3QgRE9XTkxPQUQgPSAnZG93bmxvYWQnO1xuXG4vLyBSdW5zIGEgcmVwb3J0IGV4cG9ydCBlbmQgdG8gZW5kOiBjb2xsZWN0IGV2ZXJ5IHRpbGUsIHJlZnVzZSB0byB3cml0ZSBhIGZpbGVcbi8vIHRoYXQgaXMgbWlzc2luZyBhbnkgb2YgdGhlbSB3aXRob3V0IHNheWluZyBzbywgdGhlbiByZW5kZXIuXG4vL1xuLy8gVGhlIGdhdGUgaXMgdGhlIHJlYXNvbiB0aGlzIHNpdHMgYmV0d2VlbiB0aGUgY29sbGVjdG9yIGFuZCB0aGUgcmVuZGVyZXJzXG4vLyByYXRoZXIgdGhhbiBpbiBlaXRoZXIgb2YgdGhlbS4gQSBkZWNrIHdpdGggZml2ZSBibGFuayBwYWdlcyBpcyB3b3JzZSB0aGFuIG5vXG4vLyBkZWNrOiBpdCBsb29rcyBmaW5pc2hlZCwgc28gaXQgZ2V0cyBlbWFpbGVkIHRvIGEgY2xpZW50LCBhbmQgdGhlIHBhZ2VzIHRoYXRcbi8vIGFyZSBtaXNzaW5nIGFyZSBleGFjdGx5IHRoZSBvbmVzIG5vYm9keSB0aGlua3MgdG8gY2hlY2suIFRoZSByZW5kZXJlcnMgY2FuXG4vLyBvbmx5IGRlc2NyaWJlIGEgaG9sZSB0aGV5IGFyZSBoYW5kZWQ7IHRoZSBjb2xsZWN0b3Igb25seSBrbm93cyBvbmUgdGlsZSBhdCBhXG4vLyB0aW1lLiBXaGV0aGVyIHRoZSBGSUxFIHNob3VsZCBleGlzdCBpcyBhIGRlY2lzaW9uIGFib3V0IHRoZSB3aG9sZSByZXBvcnQsIGFuZFxuLy8gdGhpcyBpcyB0aGUgb25seSBwbGFjZSB0aGF0IHNlZXMgaXQuXG5ASW5qZWN0YWJsZSgpXG5leHBvcnQgY2xhc3MgUmVwb3J0RXhwb3J0U2VydmljZSB7XG5cbiAgcHJpdmF0ZSBfY29sbGVjdG9yID0gaW5qZWN0KFJlcG9ydEV4cG9ydENvbGxlY3RvclNlcnZpY2UpO1xuICBwcml2YXRlIF9wZGZTZXJ2aWNlID0gaW5qZWN0KFJlcG9ydFBkZlNlcnZpY2UpO1xuICBwcml2YXRlIF9wcHR4U2VydmljZSA9IGluamVjdChSZXBvcnRQcHR4U2VydmljZSk7XG4gIHByaXZhdGUgX3Byb21wdCA9IGluamVjdChGc1Byb21wdCk7XG5cbiAgcHVibGljIHBkZihyZXBvcnQ6IFJlcG9ydCk6IE9ic2VydmFibGU8dW5rbm93bj4ge1xuICAgIHJldHVybiB0aGlzLl9ydW4ocmVwb3J0LCBQREZfTElTVF9ST1dTLCAoY29sbGVjdGVkKSA9PiB0aGlzLl9wZGZTZXJ2aWNlLmV4cG9ydChjb2xsZWN0ZWQpKTtcbiAgfVxuXG4gIHB1YmxpYyBwb3dlcnBvaW50KHJlcG9ydDogUmVwb3J0KTogT2JzZXJ2YWJsZTx1bmtub3duPiB7XG4gICAgcmV0dXJuIHRoaXMuX3J1bihyZXBvcnQsIFBQVFhfTElTVF9ST1dTLCAoY29sbGVjdGVkKSA9PiB0aGlzLl9wcHR4U2VydmljZS5leHBvcnQoY29sbGVjdGVkKSk7XG4gIH1cblxuICAvLyBSZXRyeSByZS1jb2xsZWN0cyB0aGUgV0hPTEUgcmVwb3J0LCBub3QganVzdCB0aGUgdGlsZXMgdGhhdCBmYWlsZWQuIEV2ZXJ5XG4gIC8vIG51bWJlciBpbiBvbmUgZmlsZSBoYXMgdG8gaGF2ZSBiZWVuIHRydWUgYXQgb25lIG1vbWVudDogcmVmZXRjaGluZyBmb3VyXG4gIC8vIHRpbGVzIGFuZCBrZWVwaW5nIG5pbmUgZnJvbSB0aHJlZSBtaW51dGVzIGFnbyBwcm9kdWNlcyBhIGRlY2sgd2hvc2UgcGFnZXNcbiAgLy8gZGlzYWdyZWUgd2l0aCBlYWNoIG90aGVyLCBhbmQgbm90aGluZyBvbiBpdCB3b3VsZCBzYXkgc28uXG4gIC8vXG4gIC8vIGxpc3RSb3dzIGlzIHRoZSBmb3JtYXQncyBvd24gbGlzdCBjYXAsIGNhcnJpZWQgaW50byB0aGUgcmV0cnkgc28gYSBzZWNvbmRcbiAgLy8gYXR0ZW1wdCBmZXRjaGVzIHdoYXQgdGhlIGZpcnN0IGRpZC5cbiAgcHJpdmF0ZSBfcnVuKFxuICAgIHJlcG9ydDogUmVwb3J0LFxuICAgIGxpc3RSb3dzOiBudW1iZXIsXG4gICAgcmVuZGVyOiAoY29sbGVjdGVkOiBDb2xsZWN0ZWRSZXBvcnQpID0+IFByb21pc2U8dm9pZD4sXG4gICk6IE9ic2VydmFibGU8dW5rbm93bj4ge1xuICAgIHJldHVybiB0aGlzLl9jb2xsZWN0b3IuY29sbGVjdChyZXBvcnQsIGxpc3RSb3dzKVxuICAgICAgLnBpcGUoXG4gICAgICAgIHN3aXRjaE1hcCgoY29sbGVjdGVkKSA9PiB0aGlzLl9nYXRlKGNvbGxlY3RlZClcbiAgICAgICAgICAucGlwZShcbiAgICAgICAgICAgIHN3aXRjaE1hcCgoY2hvaWNlKSA9PiBjaG9pY2UgPT09IFJFVFJZXG4gICAgICAgICAgICAgID8gdGhpcy5fcnVuKHJlcG9ydCwgbGlzdFJvd3MsIHJlbmRlcilcbiAgICAgICAgICAgICAgOiBmcm9tKHJlbmRlcihjb2xsZWN0ZWQpKSksXG4gICAgICAgICAgKSksXG4gICAgICApO1xuICB9XG5cbiAgLy8gUmVzb2x2ZXMgdG8gRE9XTkxPQUQgd2hlbiB0aGUgZXhwb3J0IGlzIHdob2xlIChvciB0aGUgdXNlciBhY2NlcHRlZCBhblxuICAvLyBpbmNvbXBsZXRlIG9uZSkgYW5kIHRvIFJFVFJZIHdoZW4gdGhleSB3YW50IGFub3RoZXIgYXR0ZW1wdC4gQ2FuY2VsbGluZ1xuICAvLyBlbmRzIHRoZSBleHBvcnQgcXVpZXRseTogRU1QVFkgY29tcGxldGVzIHdpdGhvdXQgZW1pdHRpbmcsIHNvIG5vdGhpbmdcbiAgLy8gcmVuZGVycyBhbmQgbm8gZXJyb3Igc3VyZmFjZXMg4oCUIHRoZXkga25vdyB3aGF0IHRoZXkganVzdCBkZWNsaW5lZC5cbiAgcHJpdmF0ZSBfZ2F0ZShjb2xsZWN0ZWQ6IENvbGxlY3RlZFJlcG9ydCk6IE9ic2VydmFibGU8c3RyaW5nPiB7XG4gICAgY29uc3QgZmFpbGVkID0gZmFpbGVkUGFnZU5hbWVzKGNvbGxlY3RlZCk7XG4gICAgaWYgKCFmYWlsZWQubGVuZ3RoKSB7XG4gICAgICByZXR1cm4gb2YoRE9XTkxPQUQpO1xuICAgIH1cblxuICAgIGNvbnN0IHBhZ2VzID0gZmFpbGVkLmxlbmd0aCA9PT0gMVxuICAgICAgPyBgPHN0cm9uZz4ke2ZhaWxlZFswXX08L3N0cm9uZz4gY291bGQgbm90IGJlIGdlbmVyYXRlZGBcbiAgICAgIDogYCR7ZmFpbGVkLmxlbmd0aH0gcGFnZXMgY291bGQgbm90IGJlIGdlbmVyYXRlZDogPHN0cm9uZz4ke2ZhaWxlZC5qb2luKCc8L3N0cm9uZz4sIDxzdHJvbmc+Jyl9PC9zdHJvbmc+YDtcblxuICAgIHJldHVybiB0aGlzLl9wcm9tcHQuY29uZmlybSh7XG4gICAgICB0aXRsZTogJ0V4cG9ydCBpcyBpbmNvbXBsZXRlJyxcbiAgICAgIHRlbXBsYXRlOiBgJHtwYWdlc30uIFRoaXMgdXN1YWxseSBtZWFucyB0aG9zZSB0aWxlcyB0b29rIHRvbyBsb25nIHRvIGxvYWQuIGBcbiAgICAgICAgKyAnUmV0cnksIG9yIGRvd25sb2FkIHRoZSBmaWxlIHdpdGggdGhvc2UgcGFnZXMgbWFya2VkIGFzIG1pc3NpbmcuJyxcbiAgICAgIGJ1dHRvbnM6IFtcbiAgICAgICAgeyBsYWJlbDogJ1JldHJ5JywgdmFsdWU6IFJFVFJZLCBjb2xvcjogJ3ByaW1hcnknIH0sXG4gICAgICAgIHsgbGFiZWw6ICdEb3dubG9hZCBBbnl3YXknLCB2YWx1ZTogRE9XTkxPQUQsIGNvbG9yOiAnJyB9LFxuICAgICAgICB7IGxhYmVsOiAnQ2FuY2VsJywgY2FuY2VsOiB0cnVlLCBjb2xvcjogJycgfSxcbiAgICAgIF0sXG4gICAgfSlcbiAgICAgIC5waXBlKGNhdGNoRXJyb3IoKCkgPT4gRU1QVFkpKTtcbiAgfVxufVxuIl19
118
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoicmVwb3J0LWV4cG9ydC5zZXJ2aWNlLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vLi4vc3JjL2FwcC9yZXBvcnRzL2V4cG9ydC9yZXBvcnQtZXhwb3J0LnNlcnZpY2UudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUFFLFVBQVUsRUFBRSxNQUFNLEVBQUUsTUFBTSxlQUFlLENBQUM7QUFFbkQsT0FBTyxFQUFFLFFBQVEsRUFBRSxNQUFNLG9CQUFvQixDQUFDO0FBRTlDLE9BQU8sRUFBRSxLQUFLLEVBQWMsSUFBSSxFQUFFLEVBQUUsRUFBRSxNQUFNLE1BQU0sQ0FBQztBQUNuRCxPQUFPLEVBQUUsVUFBVSxFQUFFLFNBQVMsRUFBRSxNQUFNLGdCQUFnQixDQUFDO0FBR3ZELE9BQU8sRUFBRSxVQUFVLEVBQUUsTUFBTSxTQUFTLENBQUM7QUFDckMsT0FBTyxFQUN5Qiw0QkFBNEIsRUFBRSxlQUFlLEdBQzVFLE1BQU0sbUNBQW1DLENBQUM7QUFDM0MsT0FBTyxFQUFFLGFBQWEsRUFBRSxnQkFBZ0IsRUFBRSxNQUFNLHNCQUFzQixDQUFDO0FBQ3ZFLE9BQU8sRUFBRSxjQUFjLEVBQUUsaUJBQWlCLEVBQUUsTUFBTSx1QkFBdUIsQ0FBQzs7QUFHMUUsNkVBQTZFO0FBQzdFLDZFQUE2RTtBQUM3RSx5RUFBeUU7QUFDekUsNEVBQTRFO0FBQzVFLE1BQU0sS0FBSyxHQUFHLE9BQU8sQ0FBQztBQUN0QixNQUFNLFFBQVEsR0FBRyxVQUFVLENBQUM7QUFFNUIsMkVBQTJFO0FBQzNFLCtFQUErRTtBQUMvRSw4RUFBOEU7QUFDOUUsRUFBRTtBQUNGLDZFQUE2RTtBQUM3RSwrRUFBK0U7QUFDL0UsOEVBQThFO0FBQzlFLDZFQUE2RTtBQUM3RSwrRUFBK0U7QUFDL0UsZ0ZBQWdGO0FBQ2hGLHVDQUF1QztBQUN2QyxFQUFFO0FBQ0YsNEVBQTRFO0FBQzVFLDhFQUE4RTtBQUM5RSw4RUFBOEU7QUFDOUUsaUNBQWlDO0FBRWpD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QUFDLElBQUksQ0FBQyxJQUFJLENBQUMsS0FBSyxLQUFLLENBQUMsWUFBWSxFQUFFO1lBQ3ZGLE9BQU8sRUFBRTtnQkFDUCxFQUFFLEtBQUssRUFBRSxpQkFBaUIsRUFBRSxLQUFLLEVBQUUsUUFBUSxFQUFFLEtBQUssRUFBRSxTQUFTLEVBQUU7Z0JBQy9ELEVBQUUsS0FBSyxFQUFFLFFBQVEsRUFBRSxNQUFNLEVBQUUsSUFBSSxFQUFFLEtBQUssRUFBRSxFQUFFLEVBQUU7YUFDN0M7U0FDRixDQUFDO2FBQ0MsSUFBSSxDQUFDLFVBQVUsQ0FBQyxHQUFHLEVBQUUsQ0FBQyxLQUFLLENBQUMsQ0FBQyxDQUFDO0lBQ25DLENBQUM7d0dBekdVLG1CQUFtQjs0R0FBbkIsbUJBQW1COzs0RkFBbkIsbUJBQW1CO2tCQUQvQixVQUFVIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgSW5qZWN0YWJsZSwgaW5qZWN0IH0gZnJvbSAnQGFuZ3VsYXIvY29yZSc7XG5cbmltcG9ydCB7IEZzUHJvbXB0IH0gZnJvbSAnQGZpcmVzdGl0Y2gvcHJvbXB0JztcblxuaW1wb3J0IHsgRU1QVFksIE9ic2VydmFibGUsIGZyb20sIG9mIH0gZnJvbSAncnhqcyc7XG5pbXBvcnQgeyBjYXRjaEVycm9yLCBzd2l0Y2hNYXAgfSBmcm9tICdyeGpzL29wZXJhdG9ycyc7XG5cbmltcG9ydCB7IFJlcG9ydCB9IGZyb20gJy4uL2ludGVyZmFjZXMvcmVwb3J0LmludGVyZmFjZSc7XG5pbXBvcnQgeyBlc2NhcGVIdG1sIH0gZnJvbSAnLi4vdGV4dCc7XG5pbXBvcnQge1xuICBCdWlsdEV4cG9ydCwgQ29sbGVjdGVkUmVwb3J0LCBSZXBvcnRFeHBvcnRDb2xsZWN0b3JTZXJ2aWNlLCBmYWlsZWRQYWdlTmFtZXMsXG59IGZyb20gJy4vcmVwb3J0LWV4cG9ydC1jb2xsZWN0b3Iuc2VydmljZSc7XG5pbXBvcnQgeyBQREZfTElTVF9ST1dTLCBSZXBvcnRQZGZTZXJ2aWNlIH0gZnJvbSAnLi9yZXBvcnQtcGRmLnNlcnZpY2UnO1xuaW1wb3J0IHsgUFBUWF9MSVNUX1JPV1MsIFJlcG9ydFBwdHhTZXJ2aWNlIH0gZnJvbSAnLi9yZXBvcnQtcHB0eC5zZXJ2aWNlJztcblxuXG4vLyBXaGF0IHRoZSB1c2VyIGNob3NlIGF0IGFuIGV4cG9ydCBnYXRlLiBSZXRyeSwgb2ZmZXJlZCBvbmx5IHdoZW4gdGhlIGV4cG9ydFxuLy8gaXMgaW5jb21wbGV0ZSwgcmUtcnVucyB0aGUgd2hvbGUgY29sbGVjdGlvbiDigJQgdGhlIHF1ZXJpZXMgdGhhdCBmYWlsZWQgd2VyZVxuLy8ga2lsbGVkIG9uIGEgY2xvY2ssIG5vdCBvbiBhbnl0aGluZyBhYm91dCB0aGUgZGF0YSwgc28gYSBzZWNvbmQgYXR0ZW1wdFxuLy8gYWdhaW5zdCBhIHdhcm1lZCBkYXRhYmFzZSBnZW51aW5lbHkgb2Z0ZW4gc3VjY2VlZHMuIERvd25sb2FkIGtlZXBzIGdvaW5nLlxuY29uc3QgUkVUUlkgPSAncmV0cnknO1xuY29uc3QgRE9XTkxPQUQgPSAnZG93bmxvYWQnO1xuXG4vLyBSdW5zIGEgcmVwb3J0IGV4cG9ydCBlbmQgdG8gZW5kOiBjb2xsZWN0IGV2ZXJ5IHRpbGUgYW5kIHZhbHVlLCByZWZ1c2UgdG9cbi8vIHdyaXRlIGEgZmlsZSB0aGF0IGlzIG1pc3NpbmcgYW55IG9mIHRoZW0gd2l0aG91dCBzYXlpbmcgc28sIGJ1aWxkIGl0LCByZWZ1c2Vcbi8vIHRvIHNhdmUgb25lIHdob3NlIHRleHQgZG9lcyBub3QgZml0IGl0cyBib3hlcyB3aXRob3V0IHNheWluZyBzbywgdGhlbiBzYXZlLlxuLy9cbi8vIFRoZSBnYXRlcyBhcmUgdGhlIHJlYXNvbiB0aGlzIHNpdHMgYmV0d2VlbiB0aGUgY29sbGVjdG9yIGFuZCB0aGUgcmVuZGVyZXJzXG4vLyByYXRoZXIgdGhhbiBpbiBlaXRoZXIgb2YgdGhlbS4gQSBkZWNrIHdpdGggZml2ZSBibGFuayBwYWdlcyBpcyB3b3JzZSB0aGFuIG5vXG4vLyBkZWNrOiBpdCBsb29rcyBmaW5pc2hlZCwgc28gaXQgZ2V0cyBlbWFpbGVkIHRvIGEgY2xpZW50LCBhbmQgdGhlIHBhZ2VzIHRoYXRcbi8vIGFyZSBtaXNzaW5nIGFyZSBleGFjdGx5IHRoZSBvbmVzIG5vYm9keSB0aGlua3MgdG8gY2hlY2suIFRoZSByZW5kZXJlcnMgY2FuXG4vLyBvbmx5IGRlc2NyaWJlIGEgaG9sZSB0aGV5IGFyZSBoYW5kZWQ7IHRoZSBjb2xsZWN0b3Igb25seSBrbm93cyBvbmUgdGlsZSBhdCBhXG4vLyB0aW1lLiBXaGV0aGVyIHRoZSBGSUxFIHNob3VsZCBleGlzdCBpcyBhIGRlY2lzaW9uIGFib3V0IHRoZSB3aG9sZSByZXBvcnQsIGFuZFxuLy8gdGhpcyBpcyB0aGUgb25seSBwbGFjZSB0aGF0IHNlZXMgaXQuXG4vL1xuLy8gRmFpbHVyZXMgYXJlIGRlY2lkZWQgYmVmb3JlIHRoZSBidWlsZCwgd2hpY2ggaXMgdGhlIGV4cGVuc2l2ZSBwYXJ0IChldmVyeVxuLy8gY2hhcnQgZHJhd24gb2Zmc2NyZWVuLCBldmVyeSB0ZXh0IGJsb2NrIG1lYXN1cmVkKSwgc28gbmVpdGhlciBhIFJldHJ5IG5vciBhXG4vLyBDYW5jZWwgcGF5cyBmb3Igb25lLiBUZXh0IHRoYXQgZG9lcyBub3QgZml0IGl0cyBib3ggaXMga25vd24gb25seSBhZnRlciBpdDpcbi8vIHRoZSBidWlsZCBpcyB3aGF0IG1lYXN1cmVzIGl0LlxuQEluamVjdGFibGUoKVxuZXhwb3J0IGNsYXNzIFJlcG9ydEV4cG9ydFNlcnZpY2Uge1xuXG4gIHByaXZhdGUgX2NvbGxlY3RvciA9IGluamVjdChSZXBvcnRFeHBvcnRDb2xsZWN0b3JTZXJ2aWNlKTtcbiAgcHJpdmF0ZSBfcGRmU2VydmljZSA9IGluamVjdChSZXBvcnRQZGZTZXJ2aWNlKTtcbiAgcHJpdmF0ZSBfcHB0eFNlcnZpY2UgPSBpbmplY3QoUmVwb3J0UHB0eFNlcnZpY2UpO1xuICBwcml2YXRlIF9wcm9tcHQgPSBpbmplY3QoRnNQcm9tcHQpO1xuXG4gIHB1YmxpYyBwZGYocmVwb3J0OiBSZXBvcnQpOiBPYnNlcnZhYmxlPHVua25vd24+IHtcbiAgICByZXR1cm4gdGhpcy5fcnVuKHJlcG9ydCwgUERGX0xJU1RfUk9XUywgKGNvbGxlY3RlZCkgPT4gdGhpcy5fcGRmU2VydmljZS5idWlsZChjb2xsZWN0ZWQpKTtcbiAgfVxuXG4gIHB1YmxpYyBwb3dlcnBvaW50KHJlcG9ydDogUmVwb3J0KTogT2JzZXJ2YWJsZTx1bmtub3duPiB7XG4gICAgcmV0dXJuIHRoaXMuX3J1bihyZXBvcnQsIFBQVFhfTElTVF9ST1dTLCAoY29sbGVjdGVkKSA9PiB0aGlzLl9wcHR4U2VydmljZS5idWlsZChjb2xsZWN0ZWQpKTtcbiAgfVxuXG4gIC8vIFJldHJ5IHJlLWNvbGxlY3RzIHRoZSBXSE9MRSByZXBvcnQsIG5vdCBqdXN0IHRoZSB0aWxlcyB0aGF0IGZhaWxlZC4gRXZlcnlcbiAgLy8gbnVtYmVyIGluIG9uZSBmaWxlIGhhcyB0byBoYXZlIGJlZW4gdHJ1ZSBhdCBvbmUgbW9tZW50OiByZWZldGNoaW5nIGZvdXJcbiAgLy8gdGlsZXMgYW5kIGtlZXBpbmcgbmluZSBmcm9tIHRocmVlIG1pbnV0ZXMgYWdvIHByb2R1Y2VzIGEgZGVjayB3aG9zZSBwYWdlc1xuICAvLyBkaXNhZ3JlZSB3aXRoIGVhY2ggb3RoZXIsIGFuZCBub3RoaW5nIG9uIGl0IHdvdWxkIHNheSBzby5cbiAgLy9cbiAgLy8gbGlzdFJvd3MgaXMgdGhlIGZvcm1hdCdzIG93biBsaXN0IGNhcCwgY2FycmllZCBpbnRvIHRoZSByZXRyeSBzbyBhIHNlY29uZFxuICAvLyBhdHRlbXB0IGZldGNoZXMgd2hhdCB0aGUgZmlyc3QgZGlkLlxuICBwcml2YXRlIF9ydW4oXG4gICAgcmVwb3J0OiBSZXBvcnQsXG4gICAgbGlzdFJvd3M6IG51bWJlcixcbiAgICBidWlsZDogKGNvbGxlY3RlZDogQ29sbGVjdGVkUmVwb3J0KSA9PiBQcm9taXNlPEJ1aWx0RXhwb3J0PixcbiAgKTogT2JzZXJ2YWJsZTx1bmtub3duPiB7XG4gICAgcmV0dXJuIHRoaXMuX2NvbGxlY3Rvci5jb2xsZWN0KHJlcG9ydCwgbGlzdFJvd3MpXG4gICAgICAucGlwZShcbiAgICAgICAgc3dpdGNoTWFwKChjb2xsZWN0ZWQpID0+IHRoaXMuX2ZhaWx1cmVHYXRlKGNvbGxlY3RlZClcbiAgICAgICAgICAucGlwZShcbiAgICAgICAgICAgIHN3aXRjaE1hcCgoY2hvaWNlKSA9PiBjaG9pY2UgPT09IFJFVFJZXG4gICAgICAgICAgICAgID8gdGhpcy5fcnVuKHJlcG9ydCwgbGlzdFJvd3MsIGJ1aWxkKVxuICAgICAgICAgICAgICA6IHRoaXMuX2J1aWxkQW5kU2F2ZShjb2xsZWN0ZWQsIGJ1aWxkKSksXG4gICAgICAgICAgKSksXG4gICAgICApO1xuICB9XG5cbiAgLy8gQnVpbGRzIHRoZSBmaWxlLCB0aGVuIHNhdmVzIGl0IG9uY2UgdGhlIG92ZXJmbG93IGdhdGUgbGV0cyBpdCB0aHJvdWdoLlxuICBwcml2YXRlIF9idWlsZEFuZFNhdmUoXG4gICAgY29sbGVjdGVkOiBDb2xsZWN0ZWRSZXBvcnQsXG4gICAgYnVpbGQ6IChjb2xsZWN0ZWQ6IENvbGxlY3RlZFJlcG9ydCkgPT4gUHJvbWlzZTxCdWlsdEV4cG9ydD4sXG4gICk6IE9ic2VydmFibGU8dW5rbm93bj4ge1xuICAgIHJldHVybiBmcm9tKGJ1aWxkKGNvbGxlY3RlZCkpXG4gICAgICAucGlwZShcbiAgICAgICAgc3dpdGNoTWFwKChidWlsdCkgPT4gdGhpcy5fb3ZlcmZsb3dHYXRlKGJ1aWx0KVxuICAgICAgICAgIC5waXBlKFxuICAgICAgICAgICAgc3dpdGNoTWFwKCgpID0+IGZyb20oUHJvbWlzZS5yZXNvbHZlKGJ1aWx0LnNhdmUoKSkpKSxcbiAgICAgICAgICApKSxcbiAgICAgICk7XG4gIH1cblxuICAvLyBSZXNvbHZlcyB0byBET1dOTE9BRCB3aGVuIHRoZSBleHBvcnQgaXMgd2hvbGUgKG9yIHRoZSB1c2VyIGFjY2VwdGVkIGFuXG4gIC8vIGluY29tcGxldGUgb25lKSBhbmQgdG8gUkVUUlkgd2hlbiB0aGV5IHdhbnQgYW5vdGhlciBhdHRlbXB0LiBDYW5jZWxsaW5nXG4gIC8vIGVuZHMgdGhlIGV4cG9ydCBxdWlldGx5OiBFTVBUWSBjb21wbGV0ZXMgd2l0aG91dCBlbWl0dGluZywgc28gbm90aGluZ1xuICAvLyBidWlsZHMgYW5kIG5vIGVycm9yIHN1cmZhY2VzIOKAlCB0aGV5IGtub3cgd2hhdCB0aGV5IGp1c3QgZGVjbGluZWQuXG4gIHByaXZhdGUgX2ZhaWx1cmVHYXRlKGNvbGxlY3RlZDogQ29sbGVjdGVkUmVwb3J0KTogT2JzZXJ2YWJsZTxzdHJpbmc+IHtcbiAgICBjb25zdCBmYWlsZWQgPSBmYWlsZWRQYWdlTmFtZXMoY29sbGVjdGVkKS5tYXAoZXNjYXBlSHRtbCk7XG4gICAgaWYgKCFmYWlsZWQubGVuZ3RoKSB7XG4gICAgICByZXR1cm4gb2YoRE9XTkxPQUQpO1xuICAgIH1cblxuICAgIGNvbnN0IHBhZ2VzID0gZmFpbGVkLmxlbmd0aCA9PT0gMVxuICAgICAgPyBgPHN0cm9uZz4ke2ZhaWxlZFswXX08L3N0cm9uZz4gY291bGQgbm90IGJlIGdlbmVyYXRlZGBcbiAgICAgIDogYCR7ZmFpbGVkLmxlbmd0aH0gcGFnZXMgY291bGQgbm90IGJlIGdlbmVyYXRlZDogPHN0cm9uZz4ke2ZhaWxlZC5qb2luKCc8L3N0cm9uZz4sIDxzdHJvbmc+Jyl9PC9zdHJvbmc+YDtcblxuICAgIHJldHVybiB0aGlzLl9wcm9tcHQuY29uZmlybSh7XG4gICAgICB0aXRsZTogJ0V4cG9ydCBpcyBpbmNvbXBsZXRlJyxcbiAgICAgIHRlbXBsYXRlOiBgJHtwYWdlc30uIFRoaXMgdXN1YWxseSBtZWFucyB0aG9zZSB0aWxlcyBvciB2YWx1ZXMgdG9vayB0b28gbG9uZyB0byBsb2FkLiBgXG4gICAgICAgICsgJ1JldHJ5LCBvciBkb3dubG9hZCB0aGUgZmlsZSB3aXRoIHRob3NlIHBhZ2VzIG1hcmtlZCBhcyBtaXNzaW5nLicsXG4gICAgICBidXR0b25zOiBbXG4gICAgICAgIHsgbGFiZWw6ICdSZXRyeScsIHZhbHVlOiBSRVRSWSwgY29sb3I6ICdwcmltYXJ5JyB9LFxuICAgICAgICB7IGxhYmVsOiAnRG93bmxvYWQgQW55d2F5JywgdmFsdWU6IERPV05MT0FELCBjb2xvcjogJycgfSxcbiAgICAgICAgeyBsYWJlbDogJ0NhbmNlbCcsIGNhbmNlbDogdHJ1ZSwgY29sb3I6ICcnIH0sXG4gICAgICBdLFxuICAgIH0pXG4gICAgICAucGlwZShjYXRjaEVycm9yKCgpID0+IEVNUFRZKSk7XG4gIH1cblxuICAvLyBSZXNvbHZlcyB0byBET1dOTE9BRCB3aGVuIGV2ZXJ5IHRleHQgYmxvY2sgZml0cyBpdHMgYm94IGluIHRoZSBidWlsdCBmaWxlLFxuICAvLyBvciB0aGUgdXNlciBhY2NlcHRlZCBvbmUgdGhhdCBkb2VzIG5vdC4gVGhlcmUgaXMgbm8gUmV0cnk6IHRoZSB3b3JkcyBhcmVcbiAgLy8gdGhlIHJlcG9ydCdzIG93biwgc28gYSBzZWNvbmQgYXR0ZW1wdCB3b3VsZCBidWlsZCB0aGUgc2FtZSBmaWxlLiBFYWNoIGJsb2NrXG4gIC8vIGlzIG5hbWVkIGJ5IGl0cyBwYWdlIGFuZCB0aGUgc3RhcnQgb2YgaXRzIHdvcmRzLCBhbmQgdGhlIG5vdGUgc2F5cyB3aGF0XG4gIC8vIHRoaXMgZm9ybWF0IGRvZXMgd2l0aCB0aGUgcmVzdC4gQ2FuY2VsbGluZyBlbmRzIHRoZSBleHBvcnQgcXVpZXRseSwgYXMgYXRcbiAgLy8gdGhlIGZhaWx1cmUgZ2F0ZSwgYW5kIHRoZSBidWlsdCBmaWxlIGlzIGRyb3BwZWQgdW5zYXZlZC5cbiAgcHJpdmF0ZSBfb3ZlcmZsb3dHYXRlKGJ1aWx0OiBCdWlsdEV4cG9ydCk6IE9ic2VydmFibGU8c3RyaW5nPiB7XG4gICAgaWYgKCFidWlsdC5vdmVyZmxvd3MubGVuZ3RoKSB7XG4gICAgICByZXR1cm4gb2YoRE9XTkxPQUQpO1xuICAgIH1cblxuICAgIC8vIEEgYmxvY2sgd2l0aCBubyB3b3JkcyB0byBxdW90ZSAoYW4gZW1wdHkgdGFibGUsIHNheSkgaXMgbmFtZWQgYnkgaXRzXG4gICAgLy8gcGFnZSBhbG9uZSwgbm90IGJ5IGFuIGVtcHR5IHBhaXIgb2YgcXVvdGVzLlxuICAgIGNvbnN0IGJsb2NrcyA9IGJ1aWx0Lm92ZXJmbG93c1xuICAgICAgLm1hcCgob3ZlcmZsb3cpID0+IGA8c3Ryb25nPiR7ZXNjYXBlSHRtbChvdmVyZmxvdy5wYWdlKX08L3N0cm9uZz5gXG4gICAgICAgICsgKG92ZXJmbG93LnNuaXBwZXQgPyBgICjigJwke2VzY2FwZUh0bWwob3ZlcmZsb3cuc25pcHBldCl94oCdKWAgOiAnJykpO1xuXG4gICAgcmV0dXJuIHRoaXMuX3Byb21wdC5jb25maXJtKHtcbiAgICAgIHRpdGxlOiAnVGV4dCBkb2VzIG5vdCBmaXQnLFxuICAgICAgdGVtcGxhdGU6IGBTb21lIHRleHQgZG9lcyBub3QgZml0IGl0cyBib3g6ICR7YmxvY2tzLmpvaW4oJywgJyl9LiAke2J1aWx0Lm92ZXJmbG93Tm90ZX1gLFxuICAgICAgYnV0dG9uczogW1xuICAgICAgICB7IGxhYmVsOiAnRG93bmxvYWQgQW55d2F5JywgdmFsdWU6IERPV05MT0FELCBjb2xvcjogJ3ByaW1hcnknIH0sXG4gICAgICAgIHsgbGFiZWw6ICdDYW5jZWwnLCBjYW5jZWw6IHRydWUsIGNvbG9yOiAnJyB9LFxuICAgICAgXSxcbiAgICB9KVxuICAgICAgLnBpcGUoY2F0Y2hFcnJvcigoKSA9PiBFTVBUWSkpO1xuICB9XG59XG4iXX0=