speechrecorderng 2.21.4 → 2.22.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 (111) hide show
  1. package/{esm2015/lib/action/action.js → esm2020/lib/action/action.mjs} +0 -0
  2. package/{esm2015/lib/audio/audio_display.js → esm2020/lib/audio/audio_display.mjs} +5 -5
  3. package/esm2020/lib/audio/audio_player.mjs +276 -0
  4. package/esm2020/lib/audio/capture/capture.mjs +547 -0
  5. package/{esm2015/lib/audio/context.js → esm2020/lib/audio/context.mjs} +0 -0
  6. package/esm2020/lib/audio/dsp/level_measure.mjs +351 -0
  7. package/{esm2015/lib/audio/format.js → esm2020/lib/audio/format.mjs} +0 -0
  8. package/{esm2015/lib/audio/impl/wavformat.js → esm2020/lib/audio/impl/wavformat.mjs} +0 -0
  9. package/{esm2015/lib/audio/impl/wavwriter.js → esm2020/lib/audio/impl/wavwriter.mjs} +0 -0
  10. package/{esm2015/lib/audio/io/stream.js → esm2020/lib/audio/io/stream.mjs} +0 -0
  11. package/{esm2015/lib/audio/persistor.js → esm2020/lib/audio/persistor.mjs} +0 -0
  12. package/{esm2015/lib/audio/playback/player.js → esm2020/lib/audio/playback/player.mjs} +0 -0
  13. package/esm2020/lib/audio/ui/audio_canvas_layer_comp.mjs +376 -0
  14. package/{esm2015/lib/audio/ui/audio_display_control.js → esm2020/lib/audio/ui/audio_display_control.mjs} +5 -5
  15. package/{esm2015/lib/audio/ui/audio_display_scroll_pane.js → esm2020/lib/audio/ui/audio_display_scroll_pane.mjs} +5 -5
  16. package/{esm2015/lib/audio/ui/audiosignal.js → esm2020/lib/audio/ui/audiosignal.mjs} +5 -5
  17. package/{esm2015/lib/audio/ui/common.js → esm2020/lib/audio/ui/common.mjs} +0 -0
  18. package/esm2020/lib/audio/ui/container.mjs +431 -0
  19. package/{esm2015/lib/audio/ui/livelevel.js → esm2020/lib/audio/ui/livelevel.mjs} +5 -5
  20. package/{esm2015/lib/audio/ui/scroll_pane_horizontal.js → esm2020/lib/audio/ui/scroll_pane_horizontal.mjs} +4 -4
  21. package/{esm2015/lib/audio/ui/sonagram.js → esm2020/lib/audio/ui/sonagram.mjs} +5 -5
  22. package/{esm2015/lib/dsp/utils.js → esm2020/lib/dsp/utils.mjs} +0 -0
  23. package/{esm2015/lib/io/BinaryWriter.js → esm2020/lib/io/BinaryWriter.mjs} +0 -0
  24. package/{esm2015/lib/io/stream.js → esm2020/lib/io/stream.mjs} +0 -0
  25. package/{esm2015/lib/math/2d/geometry.js → esm2020/lib/math/2d/geometry.mjs} +0 -0
  26. package/{esm2015/lib/math/complex.js → esm2020/lib/math/complex.mjs} +0 -0
  27. package/{esm2015/lib/math/dft.js → esm2020/lib/math/dft.mjs} +0 -0
  28. package/{esm2015/lib/math/utils.js → esm2020/lib/math/utils.mjs} +0 -0
  29. package/esm2020/lib/media/utils.mjs +14 -0
  30. package/esm2020/lib/net/uploader.mjs +246 -0
  31. package/{esm2015/lib/speechrecorder/project/project.js → esm2020/lib/speechrecorder/project/project.mjs} +0 -0
  32. package/{esm2015/lib/speechrecorder/project/project.service.js → esm2020/lib/speechrecorder/project/project.service.mjs} +4 -4
  33. package/esm2020/lib/speechrecorder/recording.mjs +54 -0
  34. package/esm2020/lib/speechrecorder/recordings/recordings.service.mjs +246 -0
  35. package/{esm2015/lib/speechrecorder/script/script.js → esm2020/lib/speechrecorder/script/script.mjs} +2 -2
  36. package/{esm2015/lib/speechrecorder/script/script.service.js → esm2020/lib/speechrecorder/script/script.service.mjs} +4 -4
  37. package/esm2020/lib/speechrecorder/session/audiorecorder.mjs +1144 -0
  38. package/esm2020/lib/speechrecorder/session/controlpanel.mjs +449 -0
  39. package/{esm2015/lib/speechrecorder/session/item.js → esm2020/lib/speechrecorder/session/item.mjs} +1 -1
  40. package/{esm2015/lib/speechrecorder/session/progress.js → esm2020/lib/speechrecorder/session/progress.mjs} +5 -5
  41. package/{esm2015/lib/speechrecorder/session/prompting.js → esm2020/lib/speechrecorder/session/prompting.mjs} +21 -21
  42. package/esm2020/lib/speechrecorder/session/recorder_combi_pane.mjs +75 -0
  43. package/esm2020/lib/speechrecorder/session/recording_list.mjs +109 -0
  44. package/esm2020/lib/speechrecorder/session/recordingfile/recording-file-meta.component.mjs +126 -0
  45. package/{esm2015/lib/speechrecorder/session/recordingfile/recording-file-navi.component.js → esm2020/lib/speechrecorder/session/recordingfile/recording-file-navi.component.mjs} +5 -5
  46. package/esm2020/lib/speechrecorder/session/recordingfile/recording-file-u-i.component.mjs +168 -0
  47. package/esm2020/lib/speechrecorder/session/recordingfile/recording-file-view.component.mjs +415 -0
  48. package/{esm2015/lib/speechrecorder/session/recordingfile/recording-file.js → esm2020/lib/speechrecorder/session/recordingfile/recording-file.mjs} +1 -1
  49. package/esm2020/lib/speechrecorder/session/recordingfile/recordingfile-service.mjs +251 -0
  50. package/{esm2015/lib/speechrecorder/session/session.js → esm2020/lib/speechrecorder/session/session.mjs} +0 -0
  51. package/{esm2015/lib/speechrecorder/session/session.service.js → esm2020/lib/speechrecorder/session/session.service.mjs} +4 -4
  52. package/{esm2015/lib/speechrecorder/session/session_finished_dialog.js → esm2020/lib/speechrecorder/session/session_finished_dialog.mjs} +4 -4
  53. package/esm2020/lib/speechrecorder/session/sessionmanager.mjs +1274 -0
  54. package/{esm2015/lib/speechrecorder/session/warning_bar.js → esm2020/lib/speechrecorder/session/warning_bar.mjs} +5 -5
  55. package/{esm2015/lib/speechrecorder/spruploader.js → esm2020/lib/speechrecorder/spruploader.mjs} +4 -4
  56. package/{esm2015/lib/speechrecorder/startstopsignal/startstopsignal.js → esm2020/lib/speechrecorder/startstopsignal/startstopsignal.mjs} +0 -0
  57. package/{esm2015/lib/speechrecorder/startstopsignal/ui/simpletrafficlight.js → esm2020/lib/speechrecorder/startstopsignal/ui/simpletrafficlight.mjs} +5 -5
  58. package/esm2020/lib/speechrecorderng.component.mjs +427 -0
  59. package/{esm2015/lib/speechrecorderng.module.js → esm2020/lib/speechrecorderng.module.mjs} +12 -11
  60. package/{esm2015/lib/spr.config.js → esm2020/lib/spr.config.mjs} +4 -4
  61. package/{esm2015/lib/spr.module.version.js → esm2020/lib/spr.module.version.mjs} +2 -2
  62. package/{esm2015/lib/ui/canvas_layer_comp.js → esm2020/lib/ui/canvas_layer_comp.mjs} +4 -4
  63. package/{esm2015/lib/ui/message_dialog.js → esm2020/lib/ui/message_dialog.mjs} +4 -4
  64. package/{esm2015/lib/ui/recordingitem_display.js → esm2020/lib/ui/recordingitem_display.mjs} +9 -9
  65. package/{esm2015/lib/utils/css_utils.js → esm2020/lib/utils/css_utils.mjs} +0 -0
  66. package/{esm2015/lib/utils/scrollIntoViewToBottom.js → esm2020/lib/utils/scrollIntoViewToBottom.mjs} +4 -4
  67. package/{esm2015/lib/utils/ua-parser.js → esm2020/lib/utils/ua-parser.mjs} +0 -0
  68. package/{esm2015/lib/utils/utils.js → esm2020/lib/utils/utils.mjs} +0 -0
  69. package/esm2020/public-api.mjs +31 -0
  70. package/{esm2015/speechrecorderng.js → esm2020/speechrecorderng.mjs} +0 -0
  71. package/fesm2015/speechrecorderng.mjs +11991 -0
  72. package/fesm2015/speechrecorderng.mjs.map +1 -0
  73. package/{fesm2015/speechrecorderng.js → fesm2020/speechrecorderng.mjs} +1863 -285
  74. package/fesm2020/speechrecorderng.mjs.map +1 -0
  75. package/lib/media/utils.d.ts +3 -0
  76. package/lib/net/uploader.d.ts +4 -2
  77. package/lib/speechrecorder/recording.d.ts +14 -3
  78. package/lib/speechrecorder/recordings/recordings.service.d.ts +12 -5
  79. package/lib/speechrecorder/session/audiorecorder.d.ts +150 -0
  80. package/lib/speechrecorder/session/controlpanel.d.ts +2 -1
  81. package/lib/speechrecorder/session/item.d.ts +2 -2
  82. package/lib/speechrecorder/session/recorder_combi_pane.d.ts +26 -0
  83. package/lib/speechrecorder/session/recording_list.d.ts +19 -0
  84. package/lib/speechrecorder/session/recordingfile/recording-file-meta.component.d.ts +6 -2
  85. package/lib/speechrecorder/session/recordingfile/recording-file-view.component.d.ts +5 -4
  86. package/lib/speechrecorder/session/recordingfile/recording-file.d.ts +2 -2
  87. package/lib/speechrecorder/session/recordingfile/recordingfile-service.d.ts +5 -3
  88. package/lib/speechrecorder/session/sessionmanager.d.ts +5 -5
  89. package/lib/speechrecorderng.module.d.ts +31 -28
  90. package/lib/spr.module.version.d.ts +1 -1
  91. package/package.json +33 -20
  92. package/public-api.d.ts +2 -1
  93. package/bundles/speechrecorderng.umd.js +0 -10146
  94. package/bundles/speechrecorderng.umd.js.map +0 -1
  95. package/esm2015/lib/audio/audio_player.js +0 -274
  96. package/esm2015/lib/audio/capture/capture.js +0 -544
  97. package/esm2015/lib/audio/dsp/level_measure.js +0 -356
  98. package/esm2015/lib/audio/ui/audio_canvas_layer_comp.js +0 -364
  99. package/esm2015/lib/audio/ui/container.js +0 -412
  100. package/esm2015/lib/net/uploader.js +0 -220
  101. package/esm2015/lib/speechrecorder/recording.js +0 -38
  102. package/esm2015/lib/speechrecorder/recordings/recordings.service.js +0 -173
  103. package/esm2015/lib/speechrecorder/session/controlpanel.js +0 -446
  104. package/esm2015/lib/speechrecorder/session/recordingfile/recording-file-meta.component.js +0 -83
  105. package/esm2015/lib/speechrecorder/session/recordingfile/recording-file-u-i.component.js +0 -163
  106. package/esm2015/lib/speechrecorder/session/recordingfile/recording-file-view.component.js +0 -386
  107. package/esm2015/lib/speechrecorder/session/recordingfile/recordingfile-service.js +0 -191
  108. package/esm2015/lib/speechrecorder/session/sessionmanager.js +0 -1271
  109. package/esm2015/lib/speechrecorderng.component.js +0 -423
  110. package/esm2015/public-api.js +0 -30
  111. package/fesm2015/speechrecorderng.js.map +0 -1
@@ -1,163 +0,0 @@
1
- import { Component } from '@angular/core';
2
- import { MessageDialog } from "../../../ui/message_dialog";
3
- import { RecordingFileViewComponent } from "./recording-file-view.component";
4
- import * as i0 from "@angular/core";
5
- import * as i1 from "./recordingfile-service";
6
- import * as i2 from "../../recordings/recordings.service";
7
- import * as i3 from "../session.service";
8
- import * as i4 from "@angular/router";
9
- import * as i5 from "@angular/material/dialog";
10
- import * as i6 from "@angular/material/snack-bar";
11
- import * as i7 from "../../../audio/ui/audio_display_scroll_pane";
12
- import * as i8 from "./recording-file-meta.component";
13
- import * as i9 from "../../../audio/ui/audio_display_control";
14
- import * as i10 from "./recording-file-navi.component";
15
- import * as i11 from "@angular/material/button";
16
- export class RecordingFileUI extends RecordingFileViewComponent {
17
- constructor(recordingFileService, recordingService, sessionService, router, route, ref, eRef, dialog, snackBar) {
18
- super(recordingFileService, recordingService, sessionService, router, route, ref, eRef, dialog);
19
- this.recordingFileService = recordingFileService;
20
- this.recordingService = recordingService;
21
- this.sessionService = sessionService;
22
- this.router = router;
23
- this.route = route;
24
- this.ref = ref;
25
- this.eRef = eRef;
26
- this.dialog = dialog;
27
- this.snackBar = snackBar;
28
- this.savedEditSelection = null;
29
- this.editSaved = true;
30
- this.parentE = this.eRef.nativeElement;
31
- }
32
- ngAfterViewInit() {
33
- super.ngAfterViewInit();
34
- }
35
- applyButtonText() {
36
- if (this.audioClip) {
37
- let s = this.audioClip.selection;
38
- if (s) {
39
- return "Apply current selection as editing selection";
40
- }
41
- else {
42
- return "Cancel out editing selection";
43
- }
44
- }
45
- // just as fallback
46
- return "Apply selection";
47
- }
48
- loadRecFile(rfId) {
49
- this.editSaved = true;
50
- super.loadRecFile(rfId);
51
- }
52
- loadedRecfile() {
53
- super.loadedRecfile();
54
- if (this.audioClip) {
55
- this.audioClip.addSelectionObserver((clip) => {
56
- let s = clip.selection;
57
- this.editSaved = ((this.savedEditSelection == null && s == null) || this.savedEditSelection != null && this.savedEditSelection.equals(s));
58
- });
59
- }
60
- this.savedEditSelection = this.audioClip ? this.audioClip.selection : null;
61
- this.editSaved = true;
62
- }
63
- applySelection() {
64
- var _a;
65
- if (this.audioClip) {
66
- let ab = this.audioClip.buffer;
67
- let s = this.audioClip.selection;
68
- if (s && ab && ((_a = this.recordingFile) === null || _a === void 0 ? void 0 : _a.recordingFileId)) {
69
- let sr = ab.sampleRate;
70
- let sf = s.startFrame;
71
- let ef = s.endFrame;
72
- this.recordingFileService.saveEditSelection(this.recordingFile.recordingFileId, sr, sf, ef).subscribe((value) => { }, () => {
73
- this.dialog.open(MessageDialog, {
74
- data: {
75
- type: 'error',
76
- title: 'Save selection edit error',
77
- msg: "Could not save edit selection to WikiSpeech server!",
78
- advice: "Please check network connection and server state."
79
- }
80
- });
81
- }, () => {
82
- // Or use returned selection value from server?
83
- this.savedEditSelection = s;
84
- this.editSaved = true;
85
- this.snackBar.open('Selection edit saved successfully.', 'OK', { duration: 1500 });
86
- });
87
- }
88
- }
89
- }
90
- }
91
- RecordingFileUI.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "12.2.13", ngImport: i0, type: RecordingFileUI, deps: [{ token: i1.RecordingFileService }, { token: i2.RecordingService }, { token: i3.SessionService }, { token: i4.Router }, { token: i4.ActivatedRoute }, { token: i0.ChangeDetectorRef }, { token: i0.ElementRef }, { token: i5.MatDialog }, { token: i6.MatSnackBar }], target: i0.ɵɵFactoryTarget.Component });
92
- RecordingFileUI.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "12.0.0", version: "12.2.13", type: RecordingFileUI, selector: "app-audiodisplayplayer", usesInheritance: true, ngImport: i0, template: `
93
- <h1>Recording file editing</h1>
94
- <p>On export or delivery the editing selection of the recording file is cut out. If no editing selection is applied the original file is exported.</p>
95
-
96
- <audio-display-scroll-pane #audioDisplayScrollPane></audio-display-scroll-pane>
97
- <div class="ctrlview">
98
- <app-recording-file-meta [sessionId]="sessionId" [recordingFile]="recordingFile"></app-recording-file-meta>
99
- <audio-display-control [audioClip]="audioClip"
100
- [playStartAction]="playStartAction"
101
- [playSelectionAction]="playSelectionAction"
102
- [playStopAction]="playStopAction"
103
- [autoPlayOnSelectToggleAction]="ap?.autoPlayOnSelectToggleAction"
104
- [zoomInAction]="zoomInAction"
105
- [zoomOutAction]="zoomOutAction"
106
- [zoomSelectedAction]="zoomSelectedAction"
107
- [zoomFitToPanelAction]="zoomFitToPanelAction"></audio-display-control>
108
- <app-recording-file-navi [items]="availRecFiles?.length" [itemPos]="posInList" [version]="recordingFile?recordingFile.version:null" [versions]="versions" [firstAction]="firstAction" [prevAction]="prevAction" [nextAction]="nextAction" [lastAction]="lastAction" [selectVersion]="toVersionAction" [naviInfoLoading]="naviInfoLoading"></app-recording-file-navi>
109
- </div>
110
-
111
- <button mat-raised-button color="accent" (click)="applySelection()" [disabled]="editSaved">{{this.applyButtonText()}}</button>
112
- `, isInline: true, styles: [":host {\n flex: 2;\n display: flex;\n flex-direction: column;\n min-height:0;\n overflow: hidden;\n padding: 20px;\n z-index: 5;\n box-sizing: border-box;\n background-color: white;\n }", "\n .ctrlview{\n display: flex;\n flex-direction: row;\n }\n ", "\n audio-display-control{\n\n flex: 3;\n }\n "], components: [{ type: i7.AudioDisplayScrollPane, selector: "audio-display-scroll-pane", inputs: ["audioClip"], outputs: ["zoomInAction", "zoomOutAction", "zoomSelectedAction", "zoomFitToPanelAction"] }, { type: i8.RecordingFileMetaComponent, selector: "app-recording-file-meta", inputs: ["sessionId", "recordingFile"] }, { type: i9.AudioDisplayControl, selector: "audio-display-control", inputs: ["audioClip", "playStartAction", "playSelectionAction", "playStopAction", "zoomInAction", "zoomOutAction", "zoomFitToPanelAction", "zoomSelectedAction", "autoPlayOnSelectToggleAction"] }, { type: i10.RecordingFileNaviComponent, selector: "app-recording-file-navi", inputs: ["firstAction", "prevAction", "nextAction", "lastAction", "items", "itemPos", "selectVersion", "versions", "version", "naviInfoLoading"] }, { type: i11.MatButton, selector: "button[mat-button], button[mat-raised-button], button[mat-icon-button], button[mat-fab], button[mat-mini-fab], button[mat-stroked-button], button[mat-flat-button]", inputs: ["disabled", "disableRipple", "color"], exportAs: ["matButton"] }] });
113
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "12.2.13", ngImport: i0, type: RecordingFileUI, decorators: [{
114
- type: Component,
115
- args: [{
116
- selector: 'app-audiodisplayplayer',
117
- template: `
118
- <h1>Recording file editing</h1>
119
- <p>On export or delivery the editing selection of the recording file is cut out. If no editing selection is applied the original file is exported.</p>
120
-
121
- <audio-display-scroll-pane #audioDisplayScrollPane></audio-display-scroll-pane>
122
- <div class="ctrlview">
123
- <app-recording-file-meta [sessionId]="sessionId" [recordingFile]="recordingFile"></app-recording-file-meta>
124
- <audio-display-control [audioClip]="audioClip"
125
- [playStartAction]="playStartAction"
126
- [playSelectionAction]="playSelectionAction"
127
- [playStopAction]="playStopAction"
128
- [autoPlayOnSelectToggleAction]="ap?.autoPlayOnSelectToggleAction"
129
- [zoomInAction]="zoomInAction"
130
- [zoomOutAction]="zoomOutAction"
131
- [zoomSelectedAction]="zoomSelectedAction"
132
- [zoomFitToPanelAction]="zoomFitToPanelAction"></audio-display-control>
133
- <app-recording-file-navi [items]="availRecFiles?.length" [itemPos]="posInList" [version]="recordingFile?recordingFile.version:null" [versions]="versions" [firstAction]="firstAction" [prevAction]="prevAction" [nextAction]="nextAction" [lastAction]="lastAction" [selectVersion]="toVersionAction" [naviInfoLoading]="naviInfoLoading"></app-recording-file-navi>
134
- </div>
135
-
136
- <button mat-raised-button color="accent" (click)="applySelection()" [disabled]="editSaved">{{this.applyButtonText()}}</button>
137
- `,
138
- styles: [
139
- `:host {
140
- flex: 2;
141
- display: flex;
142
- flex-direction: column;
143
- min-height:0;
144
- overflow: hidden;
145
- padding: 20px;
146
- z-index: 5;
147
- box-sizing: border-box;
148
- background-color: white;
149
- }`, `
150
- .ctrlview{
151
- display: flex;
152
- flex-direction: row;
153
- }
154
- `, `
155
- audio-display-control{
156
-
157
- flex: 3;
158
- }
159
- `
160
- ]
161
- }]
162
- }], ctorParameters: function () { return [{ type: i1.RecordingFileService }, { type: i2.RecordingService }, { type: i3.SessionService }, { type: i4.Router }, { type: i4.ActivatedRoute }, { type: i0.ChangeDetectorRef }, { type: i0.ElementRef }, { type: i5.MatDialog }, { type: i6.MatSnackBar }]; } });
163
- //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoicmVjb3JkaW5nLWZpbGUtdS1pLmNvbXBvbmVudC5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uLy4uLy4uLy4uLy4uLy4uL3Byb2plY3RzL3NwZWVjaHJlY29yZGVybmcvc3JjL2xpYi9zcGVlY2hyZWNvcmRlci9zZXNzaW9uL3JlY29yZGluZ2ZpbGUvcmVjb3JkaW5nLWZpbGUtdS1pLmNvbXBvbmVudC50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiQUFBQSxPQUFPLEVBQ0wsU0FBUyxFQUlWLE1BQU0sZUFBZSxDQUFBO0FBT3RCLE9BQU8sRUFBQyxhQUFhLEVBQUMsTUFBTSw0QkFBNEIsQ0FBQztBQUV6RCxPQUFPLEVBQUMsMEJBQTBCLEVBQUMsTUFBTSxpQ0FBaUMsQ0FBQzs7Ozs7Ozs7Ozs7OztBQXNEM0UsTUFBTSxPQUFPLGVBQWdCLFNBQVEsMEJBQTBCO0lBSzdELFlBQXNCLG9CQUF5QyxFQUFXLGdCQUFpQyxFQUFXLGNBQTZCLEVBQVcsTUFBYSxFQUFXLEtBQXFCLEVBQVksR0FBc0IsRUFBVyxJQUFlLEVBQVksTUFBZ0IsRUFBUyxRQUFxQjtRQUMvVCxLQUFLLENBQUMsb0JBQW9CLEVBQUMsZ0JBQWdCLEVBQUMsY0FBYyxFQUFDLE1BQU0sRUFBQyxLQUFLLEVBQUMsR0FBRyxFQUFDLElBQUksRUFBQyxNQUFNLENBQUMsQ0FBQTtRQURwRSx5QkFBb0IsR0FBcEIsb0JBQW9CLENBQXFCO1FBQVcscUJBQWdCLEdBQWhCLGdCQUFnQixDQUFpQjtRQUFXLG1CQUFjLEdBQWQsY0FBYyxDQUFlO1FBQVcsV0FBTSxHQUFOLE1BQU0sQ0FBTztRQUFXLFVBQUssR0FBTCxLQUFLLENBQWdCO1FBQVksUUFBRyxHQUFILEdBQUcsQ0FBbUI7UUFBVyxTQUFJLEdBQUosSUFBSSxDQUFXO1FBQVksV0FBTSxHQUFOLE1BQU0sQ0FBVTtRQUFTLGFBQVEsR0FBUixRQUFRLENBQWE7UUFIalUsdUJBQWtCLEdBQWdCLElBQUksQ0FBQztRQUN2QyxjQUFTLEdBQVMsSUFBSSxDQUFBO1FBSXBCLElBQUksQ0FBQyxPQUFPLEdBQUMsSUFBSSxDQUFDLElBQUksQ0FBQyxhQUFhLENBQUM7SUFFdkMsQ0FBQztJQUVELGVBQWU7UUFDYixLQUFLLENBQUMsZUFBZSxFQUFFLENBQUE7SUFDekIsQ0FBQztJQUVELGVBQWU7UUFDYixJQUFHLElBQUksQ0FBQyxTQUFTLEVBQUU7WUFDakIsSUFBSSxDQUFDLEdBQUcsSUFBSSxDQUFDLFNBQVMsQ0FBQyxTQUFTLENBQUE7WUFDaEMsSUFBSSxDQUFDLEVBQUU7Z0JBQ0wsT0FBTyw4Q0FBOEMsQ0FBQzthQUN2RDtpQkFBSTtnQkFDSCxPQUFPLDhCQUE4QixDQUFDO2FBQ3ZDO1NBQ0Y7UUFDRCxtQkFBbUI7UUFDbkIsT0FBTyxpQkFBaUIsQ0FBQztJQUMzQixDQUFDO0lBRVMsV0FBVyxDQUFDLElBQW9CO1FBQ3hDLElBQUksQ0FBQyxTQUFTLEdBQUcsSUFBSSxDQUFDO1FBQ3RCLEtBQUssQ0FBQyxXQUFXLENBQUMsSUFBSSxDQUFDLENBQUM7SUFDMUIsQ0FBQztJQUVPLGFBQWE7UUFDckIsS0FBSyxDQUFDLGFBQWEsRUFBRSxDQUFDO1FBQ3RCLElBQUcsSUFBSSxDQUFDLFNBQVMsRUFBRTtZQUNqQixJQUFJLENBQUMsU0FBUyxDQUFDLG9CQUFvQixDQUFDLENBQUMsSUFBSSxFQUFFLEVBQUU7Z0JBQzNDLElBQUksQ0FBQyxHQUFHLElBQUksQ0FBQyxTQUFTLENBQUE7Z0JBQ3RCLElBQUksQ0FBQyxTQUFTLEdBQUcsQ0FBQyxDQUFDLElBQUksQ0FBQyxrQkFBa0IsSUFBSSxJQUFJLElBQUksQ0FBQyxJQUFJLElBQUksQ0FBQyxJQUFJLElBQUksQ0FBQyxrQkFBa0IsSUFBSSxJQUFJLElBQUksSUFBSSxDQUFDLGtCQUFrQixDQUFDLE1BQU0sQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFBO1lBQzNJLENBQUMsQ0FBQyxDQUFDO1NBQ0o7UUFDRCxJQUFJLENBQUMsa0JBQWtCLEdBQUcsSUFBSSxDQUFDLFNBQVMsQ0FBQSxDQUFDLENBQUEsSUFBSSxDQUFDLFNBQVMsQ0FBQyxTQUFTLENBQUEsQ0FBQyxDQUFBLElBQUksQ0FBQztRQUN2RSxJQUFJLENBQUMsU0FBUyxHQUFHLElBQUksQ0FBQTtJQUN2QixDQUFDO0lBRUMsY0FBYzs7UUFDWixJQUFHLElBQUksQ0FBQyxTQUFTLEVBQUU7WUFDakIsSUFBSSxFQUFFLEdBQUMsSUFBSSxDQUFDLFNBQVMsQ0FBQyxNQUFNLENBQUM7WUFDN0IsSUFBSSxDQUFDLEdBQUcsSUFBSSxDQUFDLFNBQVMsQ0FBQyxTQUFTLENBQUE7WUFDaEMsSUFBSSxDQUFDLElBQUksRUFBRSxLQUFJLE1BQUEsSUFBSSxDQUFDLGFBQWEsMENBQUUsZUFBZSxDQUFBLEVBQUU7Z0JBQ2xELElBQUksRUFBRSxHQUFFLEVBQUUsQ0FBQyxVQUFVLENBQUM7Z0JBQ3RCLElBQUksRUFBRSxHQUFHLENBQUMsQ0FBQyxVQUFVLENBQUM7Z0JBQ3RCLElBQUksRUFBRSxHQUFHLENBQUMsQ0FBQyxRQUFRLENBQUM7Z0JBQ3BCLElBQUksQ0FBQyxvQkFBb0IsQ0FBQyxpQkFBaUIsQ0FBQyxJQUFJLENBQUMsYUFBYSxDQUFDLGVBQWUsRUFBRSxFQUFFLEVBQUUsRUFBRSxFQUFFLEVBQUUsQ0FBQyxDQUFDLFNBQVMsQ0FBQyxDQUFDLEtBQUssRUFBRSxFQUFFLEdBQUUsQ0FBQyxFQUMvRyxHQUFHLEVBQUU7b0JBQ0gsSUFBSSxDQUFDLE1BQU0sQ0FBQyxJQUFJLENBQUMsYUFBYSxFQUFFO3dCQUU5QixJQUFJLEVBQUU7NEJBQ0osSUFBSSxFQUFFLE9BQU87NEJBQ2IsS0FBSyxFQUFFLDJCQUEyQjs0QkFDbEMsR0FBRyxFQUFFLHFEQUFxRDs0QkFDMUQsTUFBTSxFQUFFLG1EQUFtRDt5QkFDNUQ7cUJBQ0YsQ0FBQyxDQUFBO2dCQUNKLENBQUMsRUFDRCxHQUFHLEVBQUU7b0JBQ0gsK0NBQStDO29CQUMvQyxJQUFJLENBQUMsa0JBQWtCLEdBQUcsQ0FBQyxDQUFBO29CQUMzQixJQUFJLENBQUMsU0FBUyxHQUFHLElBQUksQ0FBQTtvQkFDckIsSUFBSSxDQUFDLFFBQVEsQ0FBQyxJQUFJLENBQUMsb0NBQW9DLEVBQUUsSUFBSSxFQUFFLEVBQUMsUUFBUSxFQUFFLElBQUksRUFBQyxDQUFDLENBQUE7Z0JBQ2xGLENBQUMsQ0FBQyxDQUFDO2FBQ1I7U0FDRjtJQUNILENBQUM7OzZHQXpFVSxlQUFlO2lHQUFmLGVBQWUscUZBN0NoQjs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7R0FvQlQ7NEZBeUJVLGVBQWU7a0JBakQzQixTQUFTO21CQUFDO29CQUVULFFBQVEsRUFBRSx3QkFBd0I7b0JBRWxDLFFBQVEsRUFBRTs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7R0FvQlQ7b0JBQ0QsTUFBTSxFQUFFO3dCQUNOOzs7Ozs7Ozs7O01BVUUsRUFBQzs7Ozs7S0FLRixFQUFDOzs7OztLQUtEO3FCQUFDO2lCQUVMIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHtcclxuICBDb21wb25lbnQsXHJcbiAgQ2hhbmdlRGV0ZWN0b3JSZWYsXHJcbiAgQWZ0ZXJWaWV3SW5pdCxcclxuICBFbGVtZW50UmVmXHJcbn0gZnJvbSAnQGFuZ3VsYXIvY29yZSdcclxuXHJcblxyXG5pbXBvcnQge0FjdGl2YXRlZFJvdXRlLCBSb3V0ZXJ9IGZyb20gXCJAYW5ndWxhci9yb3V0ZXJcIjtcclxuaW1wb3J0IHtSZWNvcmRpbmdGaWxlU2VydmljZX0gZnJvbSBcIi4vcmVjb3JkaW5nZmlsZS1zZXJ2aWNlXCI7XHJcbmltcG9ydCB7TWF0RGlhbG9nfSBmcm9tIFwiQGFuZ3VsYXIvbWF0ZXJpYWwvZGlhbG9nXCI7XHJcbmltcG9ydCB7U2VsZWN0aW9ufSBmcm9tIFwiLi4vLi4vLi4vYXVkaW8vcGVyc2lzdG9yXCI7XHJcbmltcG9ydCB7TWVzc2FnZURpYWxvZ30gZnJvbSBcIi4uLy4uLy4uL3VpL21lc3NhZ2VfZGlhbG9nXCI7XHJcbmltcG9ydCB7QWN0aW9ufSBmcm9tIFwiLi4vLi4vLi4vYWN0aW9uL2FjdGlvblwiO1xyXG5pbXBvcnQge1JlY29yZGluZ0ZpbGVWaWV3Q29tcG9uZW50fSBmcm9tIFwiLi9yZWNvcmRpbmctZmlsZS12aWV3LmNvbXBvbmVudFwiO1xyXG5pbXBvcnQge1Nlc3Npb25TZXJ2aWNlfSBmcm9tIFwiLi4vc2Vzc2lvbi5zZXJ2aWNlXCI7XHJcbmltcG9ydCB7UmVjb3JkaW5nU2VydmljZX0gZnJvbSBcIi4uLy4uL3JlY29yZGluZ3MvcmVjb3JkaW5ncy5zZXJ2aWNlXCI7XHJcbmltcG9ydCB7TWF0U25hY2tCYXJ9IGZyb20gXCJAYW5ndWxhci9tYXRlcmlhbC9zbmFjay1iYXJcIjtcclxuXHJcbkBDb21wb25lbnQoe1xyXG5cclxuICBzZWxlY3RvcjogJ2FwcC1hdWRpb2Rpc3BsYXlwbGF5ZXInLFxyXG5cclxuICB0ZW1wbGF0ZTogYFxyXG4gICAgICA8aDE+UmVjb3JkaW5nIGZpbGUgZWRpdGluZzwvaDE+XHJcbiAgICAgIDxwPk9uIGV4cG9ydCBvciBkZWxpdmVyeSB0aGUgZWRpdGluZyBzZWxlY3Rpb24gb2YgdGhlIHJlY29yZGluZyBmaWxlIGlzIGN1dCBvdXQuIElmIG5vIGVkaXRpbmcgc2VsZWN0aW9uIGlzIGFwcGxpZWQgdGhlIG9yaWdpbmFsIGZpbGUgaXMgZXhwb3J0ZWQuPC9wPlxyXG5cclxuICAgIDxhdWRpby1kaXNwbGF5LXNjcm9sbC1wYW5lICNhdWRpb0Rpc3BsYXlTY3JvbGxQYW5lPjwvYXVkaW8tZGlzcGxheS1zY3JvbGwtcGFuZT5cclxuICAgICAgPGRpdiBjbGFzcz1cImN0cmx2aWV3XCI+XHJcbiAgICAgICAgPGFwcC1yZWNvcmRpbmctZmlsZS1tZXRhIFtzZXNzaW9uSWRdPVwic2Vzc2lvbklkXCIgIFtyZWNvcmRpbmdGaWxlXT1cInJlY29yZGluZ0ZpbGVcIj48L2FwcC1yZWNvcmRpbmctZmlsZS1tZXRhPlxyXG4gICAgPGF1ZGlvLWRpc3BsYXktY29udHJvbCBbYXVkaW9DbGlwXT1cImF1ZGlvQ2xpcFwiXHJcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgW3BsYXlTdGFydEFjdGlvbl09XCJwbGF5U3RhcnRBY3Rpb25cIlxyXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgIFtwbGF5U2VsZWN0aW9uQWN0aW9uXT1cInBsYXlTZWxlY3Rpb25BY3Rpb25cIlxyXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgIFtwbGF5U3RvcEFjdGlvbl09XCJwbGF5U3RvcEFjdGlvblwiXHJcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgW2F1dG9QbGF5T25TZWxlY3RUb2dnbGVBY3Rpb25dPVwiYXA/LmF1dG9QbGF5T25TZWxlY3RUb2dnbGVBY3Rpb25cIlxyXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgIFt6b29tSW5BY3Rpb25dPVwiem9vbUluQWN0aW9uXCJcclxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICBbem9vbU91dEFjdGlvbl09XCJ6b29tT3V0QWN0aW9uXCJcclxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICBbem9vbVNlbGVjdGVkQWN0aW9uXT1cInpvb21TZWxlY3RlZEFjdGlvblwiXHJcbiAgICAgICAgICAgICAgICAgICAgICAgICAgIFt6b29tRml0VG9QYW5lbEFjdGlvbl09XCJ6b29tRml0VG9QYW5lbEFjdGlvblwiPjwvYXVkaW8tZGlzcGxheS1jb250cm9sPlxyXG4gICAgICAgIDxhcHAtcmVjb3JkaW5nLWZpbGUtbmF2aSBbaXRlbXNdPVwiYXZhaWxSZWNGaWxlcz8ubGVuZ3RoXCIgW2l0ZW1Qb3NdPVwicG9zSW5MaXN0XCIgW3ZlcnNpb25dPVwicmVjb3JkaW5nRmlsZT9yZWNvcmRpbmdGaWxlLnZlcnNpb246bnVsbFwiIFt2ZXJzaW9uc109XCJ2ZXJzaW9uc1wiIFtmaXJzdEFjdGlvbl09XCJmaXJzdEFjdGlvblwiIFtwcmV2QWN0aW9uXT1cInByZXZBY3Rpb25cIiBbbmV4dEFjdGlvbl09XCJuZXh0QWN0aW9uXCIgW2xhc3RBY3Rpb25dPVwibGFzdEFjdGlvblwiIFtzZWxlY3RWZXJzaW9uXT1cInRvVmVyc2lvbkFjdGlvblwiIFtuYXZpSW5mb0xvYWRpbmddPVwibmF2aUluZm9Mb2FkaW5nXCI+PC9hcHAtcmVjb3JkaW5nLWZpbGUtbmF2aT5cclxuICAgICAgPC9kaXY+XHJcblxyXG4gICAgICA8YnV0dG9uIG1hdC1yYWlzZWQtYnV0dG9uIGNvbG9yPVwiYWNjZW50XCIgKGNsaWNrKT1cImFwcGx5U2VsZWN0aW9uKClcIiBbZGlzYWJsZWRdPVwiZWRpdFNhdmVkXCI+e3t0aGlzLmFwcGx5QnV0dG9uVGV4dCgpfX08L2J1dHRvbj5cclxuICBgLFxyXG4gIHN0eWxlczogW1xyXG4gICAgYDpob3N0IHtcclxuICAgICAgICAgIGZsZXg6IDI7XHJcbiAgICAgICAgICBkaXNwbGF5OiBmbGV4O1xyXG4gICAgICAgICAgZmxleC1kaXJlY3Rpb246IGNvbHVtbjtcclxuICAgICAgICAgIG1pbi1oZWlnaHQ6MDtcclxuICAgICAgICAgIG92ZXJmbG93OiBoaWRkZW47XHJcbiAgICAgIHBhZGRpbmc6IDIwcHg7XHJcbiAgICAgIHotaW5kZXg6IDU7XHJcbiAgICAgIGJveC1zaXppbmc6IGJvcmRlci1ib3g7XHJcbiAgICAgIGJhY2tncm91bmQtY29sb3I6IHdoaXRlO1xyXG4gICAgfWAsYFxyXG4gICAgICAgIC5jdHJsdmlld3tcclxuICAgICAgICAgIGRpc3BsYXk6IGZsZXg7XHJcbiAgICAgICAgICBmbGV4LWRpcmVjdGlvbjogcm93O1xyXG4gICAgICAgIH1cclxuICAgIGAsYFxyXG4gICAgICBhdWRpby1kaXNwbGF5LWNvbnRyb2x7XHJcblxyXG4gICAgICAgIGZsZXg6IDM7XHJcbiAgICAgIH1cclxuICAgIGBdXHJcblxyXG59KVxyXG5leHBvcnQgY2xhc3MgUmVjb3JkaW5nRmlsZVVJIGV4dGVuZHMgUmVjb3JkaW5nRmlsZVZpZXdDb21wb25lbnQgaW1wbGVtZW50cyBBZnRlclZpZXdJbml0IHtcclxuXHJcbiAgc2F2ZWRFZGl0U2VsZWN0aW9uOlNlbGVjdGlvbnxudWxsPW51bGw7XHJcbiAgZWRpdFNhdmVkOmJvb2xlYW49dHJ1ZVxyXG5cclxuICBjb25zdHJ1Y3Rvcihwcm90ZWN0ZWQgcmVjb3JkaW5nRmlsZVNlcnZpY2U6UmVjb3JkaW5nRmlsZVNlcnZpY2UscHJvdGVjdGVkIHJlY29yZGluZ1NlcnZpY2U6UmVjb3JkaW5nU2VydmljZSxwcm90ZWN0ZWQgc2Vzc2lvblNlcnZpY2U6U2Vzc2lvblNlcnZpY2UscHJvdGVjdGVkIHJvdXRlcjpSb3V0ZXIscHJvdGVjdGVkIHJvdXRlOiBBY3RpdmF0ZWRSb3V0ZSwgcHJvdGVjdGVkIHJlZjogQ2hhbmdlRGV0ZWN0b3JSZWYscHJvdGVjdGVkIGVSZWY6RWxlbWVudFJlZiwgcHJvdGVjdGVkIGRpYWxvZzpNYXREaWFsb2cscHJpdmF0ZSBzbmFja0JhcjogTWF0U25hY2tCYXIpIHtcclxuICAgIHN1cGVyKHJlY29yZGluZ0ZpbGVTZXJ2aWNlLHJlY29yZGluZ1NlcnZpY2Usc2Vzc2lvblNlcnZpY2Uscm91dGVyLHJvdXRlLHJlZixlUmVmLGRpYWxvZylcclxuICAgIHRoaXMucGFyZW50RT10aGlzLmVSZWYubmF0aXZlRWxlbWVudDtcclxuXHJcbiAgfVxyXG5cclxuICBuZ0FmdGVyVmlld0luaXQoKSB7XHJcbiAgICBzdXBlci5uZ0FmdGVyVmlld0luaXQoKVxyXG4gIH1cclxuXHJcbiAgYXBwbHlCdXR0b25UZXh0KCk6c3RyaW5nIHtcclxuICAgIGlmKHRoaXMuYXVkaW9DbGlwKSB7XHJcbiAgICAgIGxldCBzID0gdGhpcy5hdWRpb0NsaXAuc2VsZWN0aW9uXHJcbiAgICAgIGlmIChzKSB7XHJcbiAgICAgICAgcmV0dXJuIFwiQXBwbHkgY3VycmVudCBzZWxlY3Rpb24gYXMgZWRpdGluZyBzZWxlY3Rpb25cIjtcclxuICAgICAgfWVsc2V7XHJcbiAgICAgICAgcmV0dXJuIFwiQ2FuY2VsIG91dCBlZGl0aW5nIHNlbGVjdGlvblwiO1xyXG4gICAgICB9XHJcbiAgICB9XHJcbiAgICAvLyBqdXN0IGFzIGZhbGxiYWNrXHJcbiAgICByZXR1cm4gXCJBcHBseSBzZWxlY3Rpb25cIjtcclxuICB9XHJcblxyXG4gIHByb3RlY3RlZCBsb2FkUmVjRmlsZShyZklkOm51bWJlciB8IHN0cmluZykge1xyXG4gICAgdGhpcy5lZGl0U2F2ZWQgPSB0cnVlO1xyXG4gICAgc3VwZXIubG9hZFJlY0ZpbGUocmZJZCk7XHJcbiAgfVxyXG5cclxucHJvdGVjdGVkIGxvYWRlZFJlY2ZpbGUoKSB7XHJcbiAgc3VwZXIubG9hZGVkUmVjZmlsZSgpO1xyXG4gIGlmKHRoaXMuYXVkaW9DbGlwKSB7XHJcbiAgICB0aGlzLmF1ZGlvQ2xpcC5hZGRTZWxlY3Rpb25PYnNlcnZlcigoY2xpcCkgPT4ge1xyXG4gICAgICBsZXQgcyA9IGNsaXAuc2VsZWN0aW9uXHJcbiAgICAgIHRoaXMuZWRpdFNhdmVkID0gKCh0aGlzLnNhdmVkRWRpdFNlbGVjdGlvbiA9PSBudWxsICYmIHMgPT0gbnVsbCkgfHwgdGhpcy5zYXZlZEVkaXRTZWxlY3Rpb24gIT0gbnVsbCAmJiB0aGlzLnNhdmVkRWRpdFNlbGVjdGlvbi5lcXVhbHMocykpXHJcbiAgICB9KTtcclxuICB9XHJcbiAgdGhpcy5zYXZlZEVkaXRTZWxlY3Rpb24gPSB0aGlzLmF1ZGlvQ2xpcD90aGlzLmF1ZGlvQ2xpcC5zZWxlY3Rpb246bnVsbDtcclxuICB0aGlzLmVkaXRTYXZlZCA9IHRydWVcclxufVxyXG5cclxuICBhcHBseVNlbGVjdGlvbigpe1xyXG4gICAgaWYodGhpcy5hdWRpb0NsaXApIHtcclxuICAgICAgbGV0IGFiPXRoaXMuYXVkaW9DbGlwLmJ1ZmZlcjtcclxuICAgICAgbGV0IHMgPSB0aGlzLmF1ZGlvQ2xpcC5zZWxlY3Rpb25cclxuICAgICAgaWYgKHMgJiYgYWIgJiYgdGhpcy5yZWNvcmRpbmdGaWxlPy5yZWNvcmRpbmdGaWxlSWQpIHtcclxuICAgICAgICBsZXQgc3I9IGFiLnNhbXBsZVJhdGU7XHJcbiAgICAgICAgbGV0IHNmID0gcy5zdGFydEZyYW1lO1xyXG4gICAgICAgIGxldCBlZiA9IHMuZW5kRnJhbWU7XHJcbiAgICAgICAgdGhpcy5yZWNvcmRpbmdGaWxlU2VydmljZS5zYXZlRWRpdFNlbGVjdGlvbih0aGlzLnJlY29yZGluZ0ZpbGUucmVjb3JkaW5nRmlsZUlkLCBzciwgc2YsIGVmKS5zdWJzY3JpYmUoKHZhbHVlKSA9PiB7fSxcclxuICAgICAgICAgICAgKCkgPT4ge1xyXG4gICAgICAgICAgICAgIHRoaXMuZGlhbG9nLm9wZW4oTWVzc2FnZURpYWxvZywge1xyXG5cclxuICAgICAgICAgICAgICAgIGRhdGE6IHtcclxuICAgICAgICAgICAgICAgICAgdHlwZTogJ2Vycm9yJyxcclxuICAgICAgICAgICAgICAgICAgdGl0bGU6ICdTYXZlIHNlbGVjdGlvbiBlZGl0IGVycm9yJyxcclxuICAgICAgICAgICAgICAgICAgbXNnOiBcIkNvdWxkIG5vdCBzYXZlIGVkaXQgc2VsZWN0aW9uIHRvIFdpa2lTcGVlY2ggc2VydmVyIVwiLFxyXG4gICAgICAgICAgICAgICAgICBhZHZpY2U6IFwiUGxlYXNlIGNoZWNrIG5ldHdvcmsgY29ubmVjdGlvbiBhbmQgc2VydmVyIHN0YXRlLlwiXHJcbiAgICAgICAgICAgICAgICB9XHJcbiAgICAgICAgICAgICAgfSlcclxuICAgICAgICAgICAgfSxcclxuICAgICAgICAgICAgKCkgPT4ge1xyXG4gICAgICAgICAgICAgIC8vIE9yIHVzZSByZXR1cm5lZCBzZWxlY3Rpb24gdmFsdWUgZnJvbSBzZXJ2ZXI/XHJcbiAgICAgICAgICAgICAgdGhpcy5zYXZlZEVkaXRTZWxlY3Rpb24gPSBzXHJcbiAgICAgICAgICAgICAgdGhpcy5lZGl0U2F2ZWQgPSB0cnVlXHJcbiAgICAgICAgICAgICAgdGhpcy5zbmFja0Jhci5vcGVuKCdTZWxlY3Rpb24gZWRpdCBzYXZlZCBzdWNjZXNzZnVsbHkuJywgJ09LJywge2R1cmF0aW9uOiAxNTAwfSlcclxuICAgICAgICAgICAgfSk7XHJcbiAgICAgIH1cclxuICAgIH1cclxuICB9XHJcblxyXG59XHJcblxyXG4iXX0=
@@ -1,386 +0,0 @@
1
- import { Component, ViewChild, } from '@angular/core';
2
- import { AudioDisplayPlayer } from "../../../audio/audio_player";
3
- import { AudioDisplayScrollPane } from "../../../audio/ui/audio_display_scroll_pane";
4
- import { AudioContextProvider } from "../../../audio/context";
5
- import { AudioClip } from "../../../audio/persistor";
6
- import { Selection } from "../../../audio/persistor";
7
- import { Action } from "../../../action/action";
8
- import { RecordingFileUtil } from "./recording-file";
9
- import * as i0 from "@angular/core";
10
- import * as i1 from "./recordingfile-service";
11
- import * as i2 from "../../recordings/recordings.service";
12
- import * as i3 from "../session.service";
13
- import * as i4 from "@angular/router";
14
- import * as i5 from "@angular/material/dialog";
15
- import * as i6 from "../../../audio/ui/audio_display_scroll_pane";
16
- import * as i7 from "./recording-file-meta.component";
17
- import * as i8 from "../../../audio/ui/audio_display_control";
18
- import * as i9 from "./recording-file-navi.component";
19
- export class ItemcodeIndex {
20
- }
21
- export class RecordingFileViewComponent extends AudioDisplayPlayer {
22
- constructor(recordingFileService, recordingService, sessionService, router, route, ref, eRef, dialog) {
23
- super(route, ref, eRef);
24
- this.recordingFileService = recordingFileService;
25
- this.recordingService = recordingService;
26
- this.sessionService = sessionService;
27
- this.router = router;
28
- this.route = route;
29
- this.ref = ref;
30
- this.eRef = eRef;
31
- this.dialog = dialog;
32
- //protected _recordingFileId: string | number = null;
33
- this.sessionId = null;
34
- this.sessionIdFromRoute = null;
35
- this.versions = null;
36
- this.recordingFile = null;
37
- this.routedByQueryParam = false;
38
- this.posInList = null;
39
- this.naviInfoLoading = false;
40
- this.parentE = this.eRef.nativeElement;
41
- this.firstAction = new Action('First');
42
- this.firstAction.onAction = () => {
43
- this.posInList = 0;
44
- this.navigateToRecordingFile();
45
- };
46
- this.prevAction = new Action('Previous');
47
- this.prevAction.onAction = () => this.prevFile();
48
- this.nextAction = new Action('Next');
49
- this.nextAction.onAction = () => this.nextFile();
50
- this.lastAction = new Action('Last');
51
- this.lastAction.onAction = () => {
52
- if (this.availRecFiles) {
53
- this.posInList = this.availRecFiles.length - 1;
54
- this.navigateToRecordingFile();
55
- }
56
- };
57
- this.toVersionAction = new Action('To version');
58
- this.toVersionAction.onAction = (ae) => this.toVersion(ae);
59
- }
60
- ngOnInit() {
61
- super.ngOnInit();
62
- }
63
- ngAfterViewInit() {
64
- super.ngAfterViewInit();
65
- this.route.queryParams.subscribe((params) => {
66
- let rfIdP = params['recordingFileId'];
67
- let sIdP = params['sessionId'];
68
- if (sIdP) {
69
- this.sessionIdFromRoute = sIdP;
70
- }
71
- if (rfIdP) {
72
- this.routedByQueryParam = true;
73
- this.loadRecFile(rfIdP);
74
- }
75
- });
76
- this.route.params.subscribe((params) => {
77
- let rfIdP = params['recordingFileId'];
78
- let sIdP = params['sessionId'];
79
- if (sIdP) {
80
- this.sessionIdFromRoute = sIdP;
81
- }
82
- if (rfIdP) {
83
- this.routedByQueryParam = false;
84
- this.loadRecFile(rfIdP);
85
- }
86
- });
87
- // if(this.sessionId){
88
- // this.loadSession(this.sessionId);
89
- // }
90
- }
91
- navigateToId(rfId) {
92
- if (this.routedByQueryParam) {
93
- this.router.navigate([], { relativeTo: this.route, queryParams: { 'recordingFileId': rfId } });
94
- }
95
- else {
96
- this.router.navigate(['../' + rfId], { relativeTo: this.route });
97
- }
98
- }
99
- navigateToRecordingFile() {
100
- if (this.posInList != null) {
101
- let latestNextRf = this.availRecFiles[this.posInList][0];
102
- let lnRfId = latestNextRf.recordingFileId;
103
- if (lnRfId) {
104
- this.navigateToId(lnRfId);
105
- }
106
- }
107
- }
108
- toVersion(ae) {
109
- let toRfId = null;
110
- let version = ae.value;
111
- if (this.posInList != null) {
112
- let cRfs = this.availRecFiles[this.posInList];
113
- let availVersionCnt = cRfs.length;
114
- for (let cRf of cRfs) {
115
- if (cRf.version === version) {
116
- toRfId = cRf.recordingFileId;
117
- break;
118
- }
119
- }
120
- }
121
- if (toRfId != null) {
122
- this.navigateToId(toRfId);
123
- }
124
- }
125
- prevFile() {
126
- if (this.posInList != null) {
127
- this.posInList--;
128
- }
129
- this.navigateToRecordingFile();
130
- }
131
- nextFile() {
132
- if (this.posInList != null) {
133
- this.posInList++;
134
- }
135
- this.navigateToRecordingFile();
136
- }
137
- positionInList() {
138
- if (this.availRecFiles && this.recordingFile) {
139
- let cic = this.recordingFile.recording.itemcode;
140
- let itemCnt = this.availRecFiles.length;
141
- for (let rfdi = 0; rfdi < itemCnt; rfdi++) {
142
- let ar = this.availRecFiles[rfdi][0].recording;
143
- if (cic === ar.itemcode) {
144
- return rfdi;
145
- }
146
- }
147
- }
148
- return null;
149
- }
150
- updatePos() {
151
- this.posInList = this.positionInList();
152
- this.toVersionAction.disabled = true;
153
- if (this.availRecFiles) {
154
- let avRfsLen = this.availRecFiles.length;
155
- if (this.posInList != null && avRfsLen > this.posInList) {
156
- let arfs = this.availRecFiles[this.posInList];
157
- if (arfs) {
158
- this.versions = new Array();
159
- for (let arf of arfs) {
160
- this.versions.push(arf.version);
161
- }
162
- this.toVersionAction.disabled = (this.versions.length < 2);
163
- }
164
- }
165
- }
166
- this.updateActions();
167
- }
168
- loadRecFile(rfId) {
169
- var _a;
170
- (_a = this.ap) === null || _a === void 0 ? void 0 : _a.stop();
171
- this.audioClip = null;
172
- this.recordingFile = null;
173
- this.posInList = null;
174
- this.updateActions();
175
- let audioContext = AudioContextProvider.audioContextInstance();
176
- if (audioContext) {
177
- this.recordingFileService.fetchRecordingFile(audioContext, rfId).subscribe(value => {
178
- this.status = 'Audio file loaded.';
179
- let clip = null;
180
- this.recordingFile = value;
181
- if (this.recordingFile) {
182
- let ab = this.recordingFile.audioBuffer;
183
- if (ab) {
184
- clip = new AudioClip(ab);
185
- let esffsr = null;
186
- let eeffsr = null;
187
- let esr = null;
188
- if (clip.buffer != null) {
189
- esr = ab.sampleRate;
190
- if (esr != null) {
191
- esffsr = RecordingFileUtil.editStartFrameForSampleRate(this.recordingFile, esr);
192
- eeffsr = RecordingFileUtil.editEndFrameForSampleRate(this.recordingFile, esr);
193
- }
194
- let sel = null;
195
- if (esffsr != null) {
196
- if (eeffsr != null) {
197
- sel = new Selection(ab.sampleRate, esffsr, eeffsr);
198
- }
199
- else {
200
- let ch0 = ab.getChannelData(0);
201
- let frameLength = ch0.length;
202
- sel = new Selection(esr, esffsr, frameLength);
203
- }
204
- }
205
- else if (eeffsr != null) {
206
- sel = new Selection(esr, 0, eeffsr);
207
- }
208
- clip.selection = sel;
209
- }
210
- }
211
- }
212
- this.audioClip = clip;
213
- this.loadedRecfile();
214
- }, error1 => {
215
- this.status = 'Error loading audio file!';
216
- });
217
- }
218
- }
219
- loadedRecfile() {
220
- if (this.recordingFile && !this.sessionId) {
221
- let sId = this.recordingFile.session;
222
- if (!sId) {
223
- sId = this.sessionIdFromRoute;
224
- }
225
- if (sId) {
226
- this.loadSession(sId);
227
- }
228
- }
229
- this.updatePos();
230
- this.ref.detectChanges();
231
- }
232
- updateActions() {
233
- let itemCnt = null;
234
- if (this.availRecFiles) {
235
- itemCnt = this.availRecFiles.length;
236
- }
237
- this.firstAction.disabled = (this.posInList == null || this.posInList == 0);
238
- this.prevAction.disabled = (this.posInList == null || this.posInList == 0);
239
- this.nextAction.disabled = (this.posInList == null || itemCnt == null || this.posInList >= itemCnt - 1);
240
- this.lastAction.disabled = (this.posInList == null || itemCnt == null || this.posInList >= itemCnt - 1);
241
- }
242
- loadSession(sessionId) {
243
- // load session and recording file meta data only when on init and when session changes
244
- if (sessionId != this.sessionId) {
245
- // tell UI that we are working...
246
- this.naviInfoLoading = true;
247
- this.sessionService.sessionObserver(sessionId).subscribe((s) => {
248
- // received session data
249
- this.sessionId = s.sessionId;
250
- // fetch recording file meta data list
251
- this.recordingService.recordingFileList(s.project, s.sessionId).subscribe((rfds) => {
252
- this.availRecFiles = new Array();
253
- // build structure indexed by itemcode
254
- let icIdx = new ItemcodeIndex();
255
- for (let rfdi = 0; rfdi < rfds.length; rfdi++) {
256
- let rfd = rfds[rfdi];
257
- if (rfd.date) {
258
- // convert date string for faster sorting later
259
- let rfdd = new Date(rfd.date);
260
- rfd._dateAsDateObj = rfdd;
261
- }
262
- let r = rfd.recording;
263
- let ic = r.itemcode;
264
- if (ic) {
265
- let exRfsForIc = icIdx[ic];
266
- if (exRfsForIc == null) {
267
- // itemcode not yet stored
268
- let arfd = new Array();
269
- arfd.push(rfd);
270
- icIdx[ic] = arfd;
271
- this.availRecFiles.push(arfd);
272
- }
273
- else {
274
- // rec file with itemcode already exists, add (push) this version ...
275
- exRfsForIc.push(rfd);
276
- // .. and sort latest version (highest version number) to lowest index
277
- exRfsForIc.sort((rfd1, rfd2) => {
278
- return rfd2.version - rfd1.version;
279
- });
280
- }
281
- }
282
- }
283
- // have unsorted ietmcode indexed recording files here
284
- // sort them ordered by date of latest version ascending
285
- this.availRecFiles.sort((rfs1, rfs2) => {
286
- let d1 = rfs2[0]._dateAsDateObj;
287
- let d2 = rfs1[0]._dateAsDateObj;
288
- if (d1 == null) {
289
- if (d2 == null) {
290
- return 0;
291
- }
292
- else {
293
- // Sort entries whose dates are not set to the end
294
- return -1;
295
- }
296
- }
297
- else {
298
- if (d2 == null) {
299
- // Sort entries whose dates are not set to the end
300
- return 1;
301
- }
302
- else {
303
- // Compare date by time in milliseconds value
304
- return d2.getTime() - d1.getTime();
305
- }
306
- }
307
- });
308
- this.updatePos();
309
- this.naviInfoLoading = false;
310
- this.ref.detectChanges();
311
- });
312
- });
313
- }
314
- }
315
- }
316
- RecordingFileViewComponent.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "12.2.13", ngImport: i0, type: RecordingFileViewComponent, deps: [{ token: i1.RecordingFileService }, { token: i2.RecordingService }, { token: i3.SessionService }, { token: i4.Router }, { token: i4.ActivatedRoute }, { token: i0.ChangeDetectorRef }, { token: i0.ElementRef }, { token: i5.MatDialog }], target: i0.ɵɵFactoryTarget.Component });
317
- RecordingFileViewComponent.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "12.0.0", version: "12.2.13", type: RecordingFileViewComponent, selector: "app-audiodisplayplayer", viewQueries: [{ propertyName: "ac", first: true, predicate: AudioDisplayScrollPane, descendants: true }], usesInheritance: true, ngImport: i0, template: `
318
-
319
- <audio-display-scroll-pane #audioDisplayScrollPane></audio-display-scroll-pane>
320
- <div class="ctrlview">
321
- <app-recording-file-meta [sessionId]="sessionId" [recordingFile]="recordingFile"></app-recording-file-meta>
322
-
323
- <audio-display-control [audioClip]="audioClip"
324
- [playStartAction]="playStartAction"
325
- [playSelectionAction]="playSelectionAction"
326
- [playStopAction]="playStopAction"
327
- [autoPlayOnSelectToggleAction]="ap?.autoPlayOnSelectToggleAction"
328
- [zoomInAction]="zoomInAction"
329
- [zoomOutAction]="zoomOutAction"
330
- [zoomSelectedAction]="zoomSelectedAction"
331
- [zoomFitToPanelAction]="zoomFitToPanelAction"></audio-display-control>
332
- <app-recording-file-navi [items]="availRecFiles?.length" [itemPos]="posInList" [version]="recordingFile?recordingFile.version:null" [versions]="versions" [firstAction]="firstAction" [prevAction]="prevAction" [nextAction]="nextAction" [lastAction]="lastAction" [selectVersion]="toVersionAction" [naviInfoLoading]="naviInfoLoading"></app-recording-file-navi>
333
- </div>
334
- `, isInline: true, styles: [":host {\n flex: 2;\n display: flex;\n flex-direction: column;\n min-height:0;\n overflow: hidden;\n padding: 20px;\n z-index: 5;\n box-sizing: border-box;\n background-color: white;\n }", "\n .ctrlview{\n display: flex;\n flex-direction: row;\n\n }\n ", "\n audio-display-control{\n\n flex: 3;\n }\n "], components: [{ type: i6.AudioDisplayScrollPane, selector: "audio-display-scroll-pane", inputs: ["audioClip"], outputs: ["zoomInAction", "zoomOutAction", "zoomSelectedAction", "zoomFitToPanelAction"] }, { type: i7.RecordingFileMetaComponent, selector: "app-recording-file-meta", inputs: ["sessionId", "recordingFile"] }, { type: i8.AudioDisplayControl, selector: "audio-display-control", inputs: ["audioClip", "playStartAction", "playSelectionAction", "playStopAction", "zoomInAction", "zoomOutAction", "zoomFitToPanelAction", "zoomSelectedAction", "autoPlayOnSelectToggleAction"] }, { type: i9.RecordingFileNaviComponent, selector: "app-recording-file-navi", inputs: ["firstAction", "prevAction", "nextAction", "lastAction", "items", "itemPos", "selectVersion", "versions", "version", "naviInfoLoading"] }] });
335
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "12.2.13", ngImport: i0, type: RecordingFileViewComponent, decorators: [{
336
- type: Component,
337
- args: [{
338
- selector: 'app-audiodisplayplayer',
339
- template: `
340
-
341
- <audio-display-scroll-pane #audioDisplayScrollPane></audio-display-scroll-pane>
342
- <div class="ctrlview">
343
- <app-recording-file-meta [sessionId]="sessionId" [recordingFile]="recordingFile"></app-recording-file-meta>
344
-
345
- <audio-display-control [audioClip]="audioClip"
346
- [playStartAction]="playStartAction"
347
- [playSelectionAction]="playSelectionAction"
348
- [playStopAction]="playStopAction"
349
- [autoPlayOnSelectToggleAction]="ap?.autoPlayOnSelectToggleAction"
350
- [zoomInAction]="zoomInAction"
351
- [zoomOutAction]="zoomOutAction"
352
- [zoomSelectedAction]="zoomSelectedAction"
353
- [zoomFitToPanelAction]="zoomFitToPanelAction"></audio-display-control>
354
- <app-recording-file-navi [items]="availRecFiles?.length" [itemPos]="posInList" [version]="recordingFile?recordingFile.version:null" [versions]="versions" [firstAction]="firstAction" [prevAction]="prevAction" [nextAction]="nextAction" [lastAction]="lastAction" [selectVersion]="toVersionAction" [naviInfoLoading]="naviInfoLoading"></app-recording-file-navi>
355
- </div>
356
- `,
357
- styles: [
358
- `:host {
359
- flex: 2;
360
- display: flex;
361
- flex-direction: column;
362
- min-height:0;
363
- overflow: hidden;
364
- padding: 20px;
365
- z-index: 5;
366
- box-sizing: border-box;
367
- background-color: white;
368
- }`, `
369
- .ctrlview{
370
- display: flex;
371
- flex-direction: row;
372
-
373
- }
374
- `, `
375
- audio-display-control{
376
-
377
- flex: 3;
378
- }
379
- `
380
- ]
381
- }]
382
- }], ctorParameters: function () { return [{ type: i1.RecordingFileService }, { type: i2.RecordingService }, { type: i3.SessionService }, { type: i4.Router }, { type: i4.ActivatedRoute }, { type: i0.ChangeDetectorRef }, { type: i0.ElementRef }, { type: i5.MatDialog }]; }, propDecorators: { ac: [{
383
- type: ViewChild,
384
- args: [AudioDisplayScrollPane]
385
- }] } });
386
- //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoicmVjb3JkaW5nLWZpbGUtdmlldy5jb21wb25lbnQuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi8uLi8uLi8uLi9wcm9qZWN0cy9zcGVlY2hyZWNvcmRlcm5nL3NyYy9saWIvc3BlZWNocmVjb3JkZXIvc2Vzc2lvbi9yZWNvcmRpbmdmaWxlL3JlY29yZGluZy1maWxlLXZpZXcuY29tcG9uZW50LnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBLE9BQU8sRUFDTCxTQUFTLEVBQ1QsU0FBUyxHQUdWLE1BQU0sZUFBZSxDQUFBO0FBUXRCLE9BQU8sRUFBQyxrQkFBa0IsRUFBQyxNQUFNLDZCQUE2QixDQUFDO0FBRS9ELE9BQU8sRUFBQyxzQkFBc0IsRUFBQyxNQUFNLDZDQUE2QyxDQUFDO0FBQ25GLE9BQU8sRUFBQyxvQkFBb0IsRUFBQyxNQUFNLHdCQUF3QixDQUFDO0FBQzVELE9BQU8sRUFBQyxTQUFTLEVBQUMsTUFBTSwwQkFBMEIsQ0FBQztBQUNuRCxPQUFPLEVBQUMsU0FBUyxFQUFDLE1BQU0sMEJBQTBCLENBQUM7QUFFbkQsT0FBTyxFQUFDLE1BQU0sRUFBYyxNQUFNLHdCQUF3QixDQUFDO0FBSTNELE9BQU8sRUFBQyxpQkFBaUIsRUFBQyxNQUFNLGtCQUFrQixDQUFDOzs7Ozs7Ozs7OztBQUduRCxNQUFNLE9BQU8sYUFBYTtDQUV6QjtBQWlERCxNQUFNLE9BQU8sMEJBQTJCLFNBQVEsa0JBQWtCO0lBMEJoRSxZQUFzQixvQkFBMEMsRUFBWSxnQkFBa0MsRUFBWSxjQUE4QixFQUFZLE1BQWEsRUFBVyxLQUFxQixFQUFZLEdBQXNCLEVBQVksSUFBZ0IsRUFBWSxNQUFpQjtRQUMxUyxLQUFLLENBQUMsS0FBSyxFQUFFLEdBQUcsRUFBRSxJQUFJLENBQUMsQ0FBQTtRQURILHlCQUFvQixHQUFwQixvQkFBb0IsQ0FBc0I7UUFBWSxxQkFBZ0IsR0FBaEIsZ0JBQWdCLENBQWtCO1FBQVksbUJBQWMsR0FBZCxjQUFjLENBQWdC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LEVBQUUsR0FBRyxFQUFFLENBQUMsT0FBTyxFQUFFLENBQUM7NkJBQ3BDO3lCQUNGO29CQUNILENBQUMsQ0FBQyxDQUFDO29CQUNILElBQUksQ0FBQyxTQUFTLEVBQUUsQ0FBQTtvQkFDaEIsSUFBSSxDQUFDLGVBQWUsR0FBQyxLQUFLLENBQUM7b0JBQzNCLElBQUksQ0FBQyxHQUFHLENBQUMsYUFBYSxFQUFFLENBQUM7Z0JBQzNCLENBQUMsQ0FBQyxDQUFDO1lBQ0wsQ0FBQyxDQUFDLENBQUM7U0FDSjtJQUNILENBQUM7O3dIQTFUVSwwQkFBMEI7NEdBQTFCLDBCQUEwQixrR0FlMUIsc0JBQXNCLHVFQTFEdkI7Ozs7Ozs7Ozs7Ozs7Ozs7O0dBaUJUOzRGQTBCVSwwQkFBMEI7a0JBL0N0QyxTQUFTO21CQUFDO29CQUVULFFBQVEsRUFBRSx3QkFBd0I7b0JBRWxDLFFBQVEsRUFBRTs7Ozs7Ozs7Ozs7Ozs7Ozs7R0FpQlQ7b0JBQ0QsTUFBTSxFQUFFO3dCQUNOOzs7Ozs7Ozs7O01BVUUsRUFBQzs7Ozs7O0tBTUYsRUFBQzs7Ozs7S0FLRDtxQkFBQztpQkFFTDswU0FpQlMsRUFBRTtzQkFEVCxTQUFTO3VCQUFDLHNCQUFzQiIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7XHJcbiAgQ29tcG9uZW50LFxyXG4gIFZpZXdDaGlsZCxcclxuICBDaGFuZ2VEZXRlY3RvclJlZixcclxuICBBZnRlclZpZXdJbml0LCBJbnB1dCwgRWxlbWVudFJlZiwgT25Jbml0LFxyXG59IGZyb20gJ0Bhbmd1bGFyL2NvcmUnXHJcblxyXG5cclxuaW1wb3J0IHtBY3RpdmF0ZWRSb3V0ZSwgUGFyYW1zLCBSb3V0ZSwgUm91dGVyfSBmcm9tIFwiQGFuZ3VsYXIvcm91dGVyXCI7XHJcblxyXG5cclxuaW1wb3J0IHtSZWNvcmRpbmdGaWxlU2VydmljZX0gZnJvbSBcIi4vcmVjb3JkaW5nZmlsZS1zZXJ2aWNlXCI7XHJcbmltcG9ydCB7TWF0RGlhbG9nfSBmcm9tIFwiQGFuZ3VsYXIvbWF0ZXJpYWwvZGlhbG9nXCI7XHJcbmltcG9ydCB7QXVkaW9EaXNwbGF5UGxheWVyfSBmcm9tIFwiLi4vLi4vLi4vYXVkaW8vYXVkaW9fcGxheWVyXCI7XHJcblxyXG5pbXBvcnQge0F1ZGlvRGlzcGxheVNjcm9sbFBhbmV9IGZyb20gXCIuLi8uLi8uLi9hdWRpby91aS9hdWRpb19kaXNwbGF5X3Njcm9sbF9wYW5lXCI7XHJcbmltcG9ydCB7QXVkaW9Db250ZXh0UHJvdmlkZXJ9IGZyb20gXCIuLi8uLi8uLi9hdWRpby9jb250ZXh0XCI7XHJcbmltcG9ydCB7QXVkaW9DbGlwfSBmcm9tIFwiLi4vLi4vLi4vYXVkaW8vcGVyc2lzdG9yXCI7XHJcbmltcG9ydCB7U2VsZWN0aW9ufSBmcm9tIFwiLi4vLi4vLi4vYXVkaW8vcGVyc2lzdG9yXCI7XHJcblxyXG5pbXBvcnQge0FjdGlvbiwgQWN0aW9uRXZlbnR9IGZyb20gXCIuLi8uLi8uLi9hY3Rpb24vYWN0aW9uXCI7XHJcbmltcG9ydCB7U2Vzc2lvblNlcnZpY2V9IGZyb20gXCIuLi9zZXNzaW9uLnNlcnZpY2VcIjtcclxuaW1wb3J0IHtSZWNvcmRpbmdTZXJ2aWNlfSBmcm9tIFwiLi4vLi4vcmVjb3JkaW5ncy9yZWNvcmRpbmdzLnNlcnZpY2VcIjtcclxuaW1wb3J0IHtSZWNvcmRpbmdGaWxlfSBmcm9tIFwiLi4vLi4vcmVjb3JkaW5nXCI7XHJcbmltcG9ydCB7UmVjb3JkaW5nRmlsZVV0aWx9IGZyb20gXCIuL3JlY29yZGluZy1maWxlXCI7XHJcblxyXG5cclxuZXhwb3J0IGNsYXNzIEl0ZW1jb2RlSW5kZXh7XHJcbiAgW2l0ZW1jb2RlOiBzdHJpbmddOiBBcnJheTxSZWNvcmRpbmdGaWxlPjtcclxufVxyXG5cclxuQENvbXBvbmVudCh7XHJcblxyXG4gIHNlbGVjdG9yOiAnYXBwLWF1ZGlvZGlzcGxheXBsYXllcicsXHJcblxyXG4gIHRlbXBsYXRlOiBgXHJcblxyXG4gICAgPGF1ZGlvLWRpc3BsYXktc2Nyb2xsLXBhbmUgI2F1ZGlvRGlzcGxheVNjcm9sbFBhbmU+PC9hdWRpby1kaXNwbGF5LXNjcm9sbC1wYW5lPlxyXG4gICAgPGRpdiBjbGFzcz1cImN0cmx2aWV3XCI+XHJcbiAgICAgIDxhcHAtcmVjb3JkaW5nLWZpbGUtbWV0YSBbc2Vzc2lvbklkXT1cInNlc3Npb25JZFwiIFtyZWNvcmRpbmdGaWxlXT1cInJlY29yZGluZ0ZpbGVcIj48L2FwcC1yZWNvcmRpbmctZmlsZS1tZXRhPlxyXG5cclxuICAgIDxhdWRpby1kaXNwbGF5LWNvbnRyb2wgW2F1ZGlvQ2xpcF09XCJhdWRpb0NsaXBcIlxyXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgIFtwbGF5U3RhcnRBY3Rpb25dPVwicGxheVN0YXJ0QWN0aW9uXCJcclxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICBbcGxheVNlbGVjdGlvbkFjdGlvbl09XCJwbGF5U2VsZWN0aW9uQWN0aW9uXCJcclxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICBbcGxheVN0b3BBY3Rpb25dPVwicGxheVN0b3BBY3Rpb25cIlxyXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgIFthdXRvUGxheU9uU2VsZWN0VG9nZ2xlQWN0aW9uXT1cImFwPy5hdXRvUGxheU9uU2VsZWN0VG9nZ2xlQWN0aW9uXCJcclxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICBbem9vbUluQWN0aW9uXT1cInpvb21JbkFjdGlvblwiXHJcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgW3pvb21PdXRBY3Rpb25dPVwiem9vbU91dEFjdGlvblwiXHJcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgW3pvb21TZWxlY3RlZEFjdGlvbl09XCJ6b29tU2VsZWN0ZWRBY3Rpb25cIlxyXG4gICAgICAgICAgICAgICAgICAgICAgICAgICBbem9vbUZpdFRvUGFuZWxBY3Rpb25dPVwiem9vbUZpdFRvUGFuZWxBY3Rpb25cIj48L2F1ZGlvLWRpc3BsYXktY29udHJvbD5cclxuICAgICAgPGFwcC1yZWNvcmRpbmctZmlsZS1uYXZpIFtpdGVtc109XCJhdmFpbFJlY0ZpbGVzPy5sZW5ndGhcIiBbaXRlbVBvc109XCJwb3NJbkxpc3RcIiBbdmVyc2lvbl09XCJyZWNvcmRpbmdGaWxlP3JlY29yZGluZ0ZpbGUudmVyc2lvbjpudWxsXCIgW3ZlcnNpb25zXT1cInZlcnNpb25zXCIgW2ZpcnN0QWN0aW9uXT1cImZpcnN0QWN0aW9uXCIgW3ByZXZBY3Rpb25dPVwicHJldkFjdGlvblwiIFtuZXh0QWN0aW9uXT1cIm5leHRBY3Rpb25cIiBbbGFzdEFjdGlvbl09XCJsYXN0QWN0aW9uXCIgW3NlbGVjdFZlcnNpb25dPVwidG9WZXJzaW9uQWN0aW9uXCIgW25hdmlJbmZvTG9hZGluZ109XCJuYXZpSW5mb0xvYWRpbmdcIj48L2FwcC1yZWNvcmRpbmctZmlsZS1uYXZpPlxyXG4gICAgICA8L2Rpdj5cclxuICBgLFxyXG4gIHN0eWxlczogW1xyXG4gICAgYDpob3N0IHtcclxuICAgICAgICAgIGZsZXg6IDI7XHJcbiAgICAgICAgICBkaXNwbGF5OiBmbGV4O1xyXG4gICAgICAgICAgZmxleC1kaXJlY3Rpb246IGNvbHVtbjtcclxuICAgICAgICAgIG1pbi1oZWlnaHQ6MDtcclxuICAgICAgICAgIG92ZXJmbG93OiBoaWRkZW47XHJcbiAgICAgIHBhZGRpbmc6IDIwcHg7XHJcbiAgICAgIHotaW5kZXg6IDU7XHJcbiAgICAgIGJveC1zaXppbmc6IGJvcmRlci1ib3g7XHJcbiAgICAgIGJhY2tncm91bmQtY29sb3I6IHdoaXRlO1xyXG4gICAgfWAsYFxyXG4gICAgICAgIC5jdHJsdmlld3tcclxuICAgICAgICAgIGRpc3BsYXk6IGZsZXg7XHJcbiAgICAgICAgICBmbGV4LWRpcmVjdGlvbjogcm93O1xyXG5cclxuICAgICAgICB9XHJcbiAgICBgLGBcclxuICAgICAgYXVkaW8tZGlzcGxheS1jb250cm9se1xyXG5cclxuICAgICAgICBmbGV4OiAzO1xyXG4gICAgICB9XHJcbiAgICBgXVxyXG5cclxufSlcclxuZXhwb3J0IGNsYXNzIFJlY29yZGluZ0ZpbGVWaWV3Q29tcG9uZW50IGV4dGVuZHMgQXVkaW9EaXNwbGF5UGxheWVyIGltcGxlbWVudHMgT25Jbml0LEFmdGVyVmlld0luaXQge1xyXG5cclxuICAvL3Byb3RlY3RlZCBfcmVjb3JkaW5nRmlsZUlkOiBzdHJpbmcgfCBudW1iZXIgPSBudWxsO1xyXG5cclxuICBzZXNzaW9uSWQ6IHN0cmluZyB8IG51bWJlciB8IG51bGw9IG51bGw7XHJcbiAgc2Vzc2lvbklkRnJvbVJvdXRlOnN0cmluZ3xudWxsPW51bGw7XHJcblxyXG4gIGF2YWlsUmVjRmlsZXMhOiBBcnJheTxBcnJheTxSZWNvcmRpbmdGaWxlPj47XHJcbiAgdmVyc2lvbnM6IEFycmF5PG51bWJlcj58bnVsbD1udWxsO1xyXG5cclxuICByZWNvcmRpbmdGaWxlOiBSZWNvcmRpbmdGaWxlfG51bGw9bnVsbDtcclxuICBwcml2YXRlIHJvdXRlZEJ5UXVlcnlQYXJhbT1mYWxzZTtcclxuICBwb3NJbkxpc3Q6IG51bWJlcnxudWxsPW51bGw7XHJcblxyXG5cclxuICBAVmlld0NoaWxkKEF1ZGlvRGlzcGxheVNjcm9sbFBhbmUpXHJcbiAgcHJpdmF0ZSBhYyE6IEF1ZGlvRGlzcGxheVNjcm9sbFBhbmU7XHJcblxyXG4gIGZpcnN0QWN0aW9uOiBBY3Rpb248dm9pZD47XHJcbiAgcHJldkFjdGlvbjogQWN0aW9uPHZvaWQ+O1xyXG4gIG5leHRBY3Rpb246IEFjdGlvbjx2b2lkPjtcclxuICBsYXN0QWN0aW9uOiBBY3Rpb248dm9pZD47XHJcbiAgdG9WZXJzaW9uQWN0aW9uOiBBY3Rpb248bnVtYmVyPjtcclxuXHJcbiAgbmF2aUluZm9Mb2FkaW5nPWZhbHNlO1xyXG5cclxuICBjb25zdHJ1Y3Rvcihwcm90ZWN0ZWQgcmVjb3JkaW5nRmlsZVNlcnZpY2U6IFJlY29yZGluZ0ZpbGVTZXJ2aWNlLCBwcm90ZWN0ZWQgcmVjb3JkaW5nU2VydmljZTogUmVjb3JkaW5nU2VydmljZSwgcHJvdGVjdGVkIHNlc3Npb25TZXJ2aWNlOiBTZXNzaW9uU2VydmljZSwgcHJvdGVjdGVkIHJvdXRlcjpSb3V0ZXIscHJvdGVjdGVkIHJvdXRlOiBBY3RpdmF0ZWRSb3V0ZSwgcHJvdGVjdGVkIHJlZjogQ2hhbmdlRGV0ZWN0b3JSZWYsIHByb3RlY3RlZCBlUmVmOiBFbGVtZW50UmVmLCBwcm90ZWN0ZWQgZGlhbG9nOiBNYXREaWFsb2cpIHtcclxuICAgIHN1cGVyKHJvdXRlLCByZWYsIGVSZWYpXHJcbiAgICB0aGlzLnBhcmVudEUgPSB0aGlzLmVSZWYubmF0aXZlRWxlbWVudDtcclxuICAgIHRoaXMuZmlyc3RBY3Rpb24gPSBuZXcgQWN0aW9uPHZvaWQ+KCdGaXJzdCcpO1xyXG4gICAgdGhpcy5maXJzdEFjdGlvbi5vbkFjdGlvbj0gKCk9PntcclxuICAgICAgdGhpcy5wb3NJbkxpc3Q9MDtcclxuICAgICAgdGhpcy5uYXZpZ2F0ZVRvUmVjb3JkaW5nRmlsZSgpO1xyXG4gICAgfVxyXG4gICAgdGhpcy5wcmV2QWN0aW9uID0gbmV3IEFjdGlvbjx2b2lkPignUHJldmlvdXMnKTtcclxuICAgIHRoaXMucHJldkFjdGlvbi5vbkFjdGlvbj0gKCk9PnRoaXMucHJldkZpbGUoKTtcclxuICAgIHRoaXMubmV4dEFjdGlvbiA9IG5ldyBBY3Rpb248dm9pZD4oJ05leHQnKTtcclxuICAgIHRoaXMubmV4dEFjdGlvbi5vbkFjdGlvbj0gKCk9PnRoaXMubmV4dEZpbGUoKTtcclxuICAgIHRoaXMubGFzdEFjdGlvbiA9IG5ldyBBY3Rpb248dm9pZD4oJ0xhc3QnKTtcclxuICAgIHRoaXMubGFzdEFjdGlvbi5vbkFjdGlvbj0gKCk9PntcclxuICAgICAgaWYodGhpcy5hdmFpbFJlY0ZpbGVzKSB7XHJcbiAgICAgICAgdGhpcy5wb3NJbkxpc3QgPSB0aGlzLmF2YWlsUmVjRmlsZXMubGVuZ3RoIC0gMTtcclxuICAgICAgICB0aGlzLm5hdmlnYXRlVG9SZWNvcmRpbmdGaWxlKCk7XHJcbiAgICAgIH1cclxuICAgIH1cclxuXHJcbiAgICB0aGlzLnRvVmVyc2lvbkFjdGlvbj1uZXcgQWN0aW9uPG51bWJlcj4oJ1RvIHZlcnNpb24nKTtcclxuICAgIHRoaXMudG9WZXJzaW9uQWN0aW9uLm9uQWN0aW9uPSAoYWUpPT50aGlzLnRvVmVyc2lvbihhZSk7XHJcbiAgfVxyXG5cclxuICBuZ09uSW5pdCgpIHtcclxuICAgIHN1cGVyLm5nT25Jbml0KCk7XHJcblxyXG4gIH1cclxuXHJcbiAgbmdBZnRlclZpZXdJbml0KCkge1xyXG4gICAgc3VwZXIubmdBZnRlclZpZXdJbml0KClcclxuICAgIHRoaXMucm91dGUucXVlcnlQYXJhbXMuc3Vic2NyaWJlKChwYXJhbXM6IFBhcmFtcykgPT4ge1xyXG4gICAgICBsZXQgcmZJZFAgPSBwYXJhbXNbJ3JlY29yZGluZ0ZpbGVJZCddO1xyXG4gICAgICBsZXQgc0lkUCA9IHBhcmFtc1snc2Vzc2lvbklkJ107XHJcbiAgICAgIGlmIChzSWRQKSB7XHJcbiAgICAgICB0aGlzLnNlc3Npb25JZEZyb21Sb3V0ZT1zSWRQO1xyXG4gICAgICB9XHJcbiAgICAgIGlmIChyZklkUCkge1xyXG4gICAgICAgIHRoaXMucm91dGVkQnlRdWVyeVBhcmFtPXRydWU7XHJcbiAgICAgICAgdGhpcy5sb2FkUmVjRmlsZShyZklkUCk7XHJcbiAgICAgIH1cclxuICAgIH0pO1xyXG4gICAgdGhpcy5yb3V0ZS5wYXJhbXMuc3Vic2NyaWJlKChwYXJhbXM6IFBhcmFtcykgPT4ge1xyXG4gICAgICBsZXQgcmZJZFAgPSBwYXJhbXNbJ3JlY29yZGluZ0ZpbGVJZCddO1xyXG4gICAgICBsZXQgc0lkUCA9IHBhcmFtc1snc2Vzc2lvbklkJ107XHJcbiAgICAgIGlmIChzSWRQKSB7XHJcbiAgICAgICAgdGhpcy5zZXNzaW9uSWRGcm9tUm91dGU9c0lkUDtcclxuICAgICAgfVxyXG4gICAgICBpZiAocmZJZFApIHtcclxuICAgICAgICB0aGlzLnJvdXRlZEJ5UXVlcnlQYXJhbT1mYWxzZTtcclxuICAgICAgICB0aGlzLmxvYWRSZWNGaWxlKHJmSWRQKTtcclxuICAgICAgfVxyXG4gICAgfSk7XHJcbiAgICAvLyBpZih0aGlzLnNlc3Npb25JZCl7XHJcbiAgICAvLyAgICAgdGhpcy5sb2FkU2Vzc2lvbih0aGlzLnNlc3Npb25JZCk7XHJcbiAgICAvLyB9XHJcbiAgfVxyXG5cclxuXHJcbiAgcHJpdmF0ZSBuYXZpZ2F0ZVRvSWQocmZJZDpudW1iZXJ8IHN0cmluZyl7XHJcblxyXG4gICAgaWYodGhpcy5yb3V0ZWRCeVF1ZXJ5UGFyYW0pe1xyXG4gICAgICB0aGlzLnJvdXRlci5uYXZpZ2F0ZShbXSwge3JlbGF0aXZlVG86IHRoaXMucm91dGUsIHF1ZXJ5UGFyYW1zOnsncmVjb3JkaW5nRmlsZUlkJzpyZklkfX0pXHJcbiAgICB9ZWxzZSB7XHJcbiAgICAgIHRoaXMucm91dGVyLm5hdmlnYXRlKFsnLi4vJyArIHJmSWRdLCB7cmVsYXRpdmVUbzogdGhpcy5yb3V0ZX0pO1xyXG4gICAgfVxyXG4gIH1cclxuXHJcbiAgcHJpdmF0ZSBuYXZpZ2F0ZVRvUmVjb3JkaW5nRmlsZSgpe1xyXG4gICAgaWYodGhpcy5wb3NJbkxpc3QhPW51bGwpIHtcclxuICAgICAgbGV0IGxhdGVzdE5leHRSZiA9IHRoaXMuYXZhaWxSZWNGaWxlc1t0aGlzLnBvc0luTGlzdF1bMF07XHJcbiAgICAgIGxldCBsblJmSWQgPSBsYXRlc3ROZXh0UmYucmVjb3JkaW5nRmlsZUlkO1xyXG4gICAgICBpZihsblJmSWQpIHtcclxuICAgICAgICB0aGlzLm5hdmlnYXRlVG9JZChsblJmSWQpO1xyXG4gICAgICB9XHJcbiAgICB9XHJcbiAgfVxyXG5cclxuICB0b1ZlcnNpb24oYWU6IEFjdGlvbkV2ZW50PG51bWJlcj4pIHtcclxuICAgIGxldCB0b1JmSWQgPSBudWxsO1xyXG4gICAgbGV0IHZlcnNpb24gPSBhZS52YWx1ZTtcclxuICAgIGlmKHRoaXMucG9zSW5MaXN0IT1udWxsKSB7XHJcbiAgICAgIGxldCBjUmZzID0gdGhpcy5hdmFpbFJlY0ZpbGVzW3RoaXMucG9zSW5MaXN0XTtcclxuICAgICAgbGV0IGF2YWlsVmVyc2lvbkNudCA9IGNSZnMubGVuZ3RoO1xyXG4gICAgICBmb3IgKGxldCBjUmYgb2YgY1Jmcykge1xyXG4gICAgICAgIGlmIChjUmYudmVyc2lvbiA9PT0gdmVyc2lvbikge1xyXG4gICAgICAgICAgdG9SZklkID0gY1JmLnJlY29yZGluZ0ZpbGVJZDtcclxuICAgICAgICAgIGJyZWFrO1xyXG4gICAgICAgIH1cclxuICAgICAgfVxyXG4gICAgfVxyXG4gICAgaWYgKHRvUmZJZCAhPSBudWxsKSB7XHJcbiAgICAgIHRoaXMubmF2aWdhdGVUb0lkKHRvUmZJZCk7XHJcbiAgICB9XHJcbiAgfVxyXG5cclxuXHJcbiAgcHJldkZpbGUoKSB7XHJcbiAgICBpZih0aGlzLnBvc0luTGlzdCE9bnVsbCkge1xyXG4gICAgICB0aGlzLnBvc0luTGlzdC0tO1xyXG4gICAgfVxyXG4gICAgdGhpcy5uYXZpZ2F0ZVRvUmVjb3JkaW5nRmlsZSgpXHJcbiAgfVxyXG4gIG5leHRGaWxlKCkge1xyXG4gICAgaWYodGhpcy5wb3NJbkxpc3QhPW51bGwpIHtcclxuICAgICAgdGhpcy5wb3NJbkxpc3QrKztcclxuICAgIH1cclxuICAgIHRoaXMubmF2aWdhdGVUb1JlY29yZGluZ0ZpbGUoKVxyXG4gIH1cclxuXHJcbiAgcHJpdmF0ZSBwb3NpdGlvbkluTGlzdCgpOm51bWJlciB8IG51bGx7XHJcbiAgICBpZiAodGhpcy5hdmFpbFJlY0ZpbGVzICYmIHRoaXMucmVjb3JkaW5nRmlsZSkge1xyXG4gICAgICBsZXQgY2ljID0gdGhpcy5yZWNvcmRpbmdGaWxlLnJlY29yZGluZy5pdGVtY29kZTtcclxuICAgICAgbGV0IGl0ZW1DbnQgPSB0aGlzLmF2YWlsUmVjRmlsZXMubGVuZ3RoXHJcbiAgICAgIGZvciAobGV0IHJmZGkgPSAwOyByZmRpIDwgaXRlbUNudDsgcmZkaSsrKSB7XHJcbiAgICAgICAgbGV0IGFyID0gdGhpcy5hdmFpbFJlY0ZpbGVzW3JmZGldWzBdLnJlY29yZGluZztcclxuICAgICAgICBpZiAoY2ljID09PSBhci5pdGVtY29kZSkge1xyXG4gICAgICAgICAgcmV0dXJuIHJmZGk7XHJcbiAgICAgICAgfVxyXG4gICAgICB9XHJcbiAgICB9XHJcbiAgICByZXR1cm4gbnVsbDtcclxuICB9XHJcblxyXG4gIHByaXZhdGUgdXBkYXRlUG9zKCl7XHJcbiAgICB0aGlzLnBvc0luTGlzdD10aGlzLnBvc2l0aW9uSW5MaXN0KCk7XHJcbiAgICB0aGlzLnRvVmVyc2lvbkFjdGlvbi5kaXNhYmxlZD10cnVlO1xyXG4gICAgaWYodGhpcy5hdmFpbFJlY0ZpbGVzKXtcclxuICAgICAgbGV0IGF2UmZzTGVuPXRoaXMuYXZhaWxSZWNGaWxlcy5sZW5ndGg7XHJcbiAgICAgIGlmKHRoaXMucG9zSW5MaXN0ICE9bnVsbCAmJiBhdlJmc0xlbj50aGlzLnBvc0luTGlzdCkge1xyXG4gICAgICAgIGxldCBhcmZzID0gdGhpcy5hdmFpbFJlY0ZpbGVzW3RoaXMucG9zSW5MaXN0XTtcclxuICAgICAgICBpZiAoYXJmcykge1xyXG4gICAgICAgICAgdGhpcy52ZXJzaW9ucyA9IG5ldyBBcnJheTxudW1iZXI+KCk7XHJcbiAgICAgICAgICBmb3IgKGxldCBhcmYgb2YgYXJmcykge1xyXG4gICAgICAgICAgICB0aGlzLnZlcnNpb25zLnB1c2goYXJmLnZlcnNpb24pXHJcbiAgICAgICAgICB9XHJcbiAgICAgICAgICB0aGlzLnRvVmVyc2lvbkFjdGlvbi5kaXNhYmxlZD0odGhpcy52ZXJzaW9ucy5sZW5ndGg8Mik7XHJcbiAgICAgICAgfVxyXG4gICAgICB9XHJcbiAgICB9XHJcbiAgICB0aGlzLnVwZGF0ZUFjdGlvbnMoKVxyXG4gIH1cclxuXHJcbiAgcHJvdGVjdGVkIGxvYWRSZWNGaWxlKHJmSWQ6bnVtYmVyIHwgc3RyaW5nKSB7XHJcbiAgICB0aGlzLmFwPy5zdG9wKCk7XHJcbiAgICB0aGlzLmF1ZGlvQ2xpcCA9bnVsbDtcclxuICAgIHRoaXMucmVjb3JkaW5nRmlsZT1udWxsO1xyXG4gICAgdGhpcy5wb3NJbkxpc3Q9bnVsbDtcclxuICAgIHRoaXMudXBkYXRlQWN0aW9ucygpO1xyXG4gICAgbGV0IGF1ZGlvQ29udGV4dCA9IEF1ZGlvQ29udGV4dFByb3ZpZGVyLmF1ZGlvQ29udGV4dEluc3RhbmNlKCk7XHJcbiAgICBpZihhdWRpb0NvbnRleHQpIHtcclxuICAgICAgdGhpcy5yZWNvcmRpbmdGaWxlU2VydmljZS5mZXRjaFJlY29yZGluZ0ZpbGUoYXVkaW9Db250ZXh0LCByZklkKS5zdWJzY3JpYmUodmFsdWUgPT4ge1xyXG4gICAgICAgIHRoaXMuc3RhdHVzID0gJ0F1ZGlvIGZpbGUgbG9hZGVkLic7XHJcbiAgICAgICAgbGV0IGNsaXAgPSBudWxsO1xyXG4gICAgICAgIHRoaXMucmVjb3JkaW5nRmlsZSA9IHZhbHVlO1xyXG4gICAgICAgIGlmICh0aGlzLnJlY29yZGluZ0ZpbGUpIHtcclxuICAgICAgICAgIGxldCBhYiA9IHRoaXMucmVjb3JkaW5nRmlsZS5hdWRpb0J1ZmZlcjtcclxuICAgICAgICAgIGlmIChhYikge1xyXG4gICAgICAgICAgICBjbGlwID0gbmV3IEF1ZGlvQ2xpcChhYik7XHJcblxyXG4gICAgICAgICAgICBsZXQgZXNmZnNyID0gbnVsbDtcclxuICAgICAgICAgICAgbGV0IGVlZmZzciA9IG51bGw7XHJcbiAgICAgICAgICAgIGxldCBlc3IgPSBudWxsO1xyXG5cclxuICAgICAgICAgICAgaWYgKGNsaXAuYnVmZmVyICE9IG51bGwpIHtcclxuICAgICAgICAgICAgICBlc3IgPSBhYi5zYW1wbGVSYXRlO1xyXG4gICAgICAgICAgICAgIGlmIChlc3IgIT0gbnVsbCkge1xyXG4gICAgICAgICAgICAgICAgZXNmZnNyID0gUmVjb3JkaW5nRmlsZVV0aWwuZWRpdFN0YXJ0RnJhbWVGb3JTYW1wbGVSYXRlKHRoaXMucmVjb3JkaW5nRmlsZSwgZXNyKTtcclxuICAgICAgICAgICAgICAgIGVlZmZzciA9IFJlY29yZGluZ0ZpbGVVdGlsLmVkaXRFbmRGcmFtZUZvclNhbXBsZVJhdGUodGhpcy5yZWNvcmRpbmdGaWxlLCBlc3IpO1xyXG4gICAgICAgICAgICAgIH1cclxuICAgICAgICAgICAgICBsZXQgc2VsOiBTZWxlY3Rpb24gfCBudWxsID0gbnVsbDtcclxuICAgICAgICAgICAgICBpZiAoZXNmZnNyICE9IG51bGwpIHtcclxuICAgICAgICAgICAgICAgIGlmIChlZWZmc3IgIT0gbnVsbCkge1xyXG4gICAgICAgICAgICAgICAgICBzZWwgPSBuZXcgU2VsZWN0aW9uKGFiLnNhbXBsZVJhdGUsIGVzZmZzciwgZWVmZnNyKTtcclxuICAgICAgICAgICAgICAgIH0gZWxzZSB7XHJcbiAgICAgICAgICAgICAgICAgIGxldCBjaDAgPSBhYi5nZXRDaGFubmVsRGF0YSgwKTtcclxuICAgICAgICAgICAgICAgICAgbGV0IGZyYW1lTGVuZ3RoID0gY2gwLmxlbmd0aDtcclxuICAgICAgICAgICAgICAgICAgc2VsID0gbmV3IFNlbGVjdGlvbihlc3IsIGVzZmZzciwgZnJhbWVMZW5ndGgpO1xyXG4gICAgICAgICAgICAgICAgfVxyXG4gICAgICAgICAgICAgIH0gZWxzZSBpZiAoZWVmZnNyICE9IG51bGwpIHtcclxuICAgICAgICAgICAgICAgIHNlbCA9IG5ldyBTZWxlY3Rpb24oZXNyLCAwLCBlZWZmc3IpO1xyXG4gICAgICAgICAgICAgIH1cclxuICAgICAgICAgICAgICBjbGlwLnNlbGVjdGlvbiA9IHNlbFxyXG4gICAgICAgICAgICB9XHJcbiAgICAgICAgICB9XHJcbiAgICAgICAgfVxyXG4gICAgICAgIHRoaXMuYXVkaW9DbGlwID0gY2xpcFxyXG4gICAgICAgIHRoaXMubG9hZGVkUmVjZmlsZSgpO1xyXG5cclxuICAgICAgfSwgZXJyb3IxID0+IHtcclxuICAgICAgICB0aGlzLnN0YXR1cyA9ICdFcnJvciBsb2FkaW5nIGF1ZGlvIGZpbGUhJztcclxuICAgICAgfSk7XHJcbiAgICB9XHJcbiAgfVxyXG5cclxuICBwcm90ZWN0ZWQgbG9hZGVkUmVjZmlsZSgpIHtcclxuICAgIGlmKHRoaXMucmVjb3JkaW5nRmlsZSAmJiAhdGhpcy5zZXNzaW9uSWQpIHtcclxuICAgICAgbGV0IHNJZD10aGlzLnJlY29yZGluZ0ZpbGUuc2Vzc2lvblxyXG4gICAgICBpZighc0lkKXtcclxuICAgICAgICBzSWQ9dGhpcy5zZXNzaW9uSWRGcm9tUm91dGU7XHJcbiAgICAgIH1cclxuICAgICAgaWYgKHNJZCkge1xyXG4gICAgICAgIHRoaXMubG9hZFNlc3Npb24oc0lkKTtcclxuICAgICAgfVxyXG4gICAgfVxyXG4gICAgdGhpcy51cGRhdGVQb3MoKTtcclxuICAgIHRoaXMucmVmLmRldGVjdENoYW5nZXMoKTtcclxuICB9XHJcblxyXG4gIHByaXZhdGUgdXBkYXRlQWN0aW9ucygpe1xyXG4gICAgbGV0IGl0ZW1DbnQ6bnVtYmVyfG51bGw9bnVsbDtcclxuICAgIGlmKHRoaXMuYXZhaWxSZWNGaWxlcykge1xyXG4gICAgICBpdGVtQ250ID0gdGhpcy5hdmFpbFJlY0ZpbGVzLmxlbmd0aDtcclxuICAgIH1cclxuICAgIHRoaXMuZmlyc3RBY3Rpb24uZGlzYWJsZWQ9KHRoaXMucG9zSW5MaXN0PT1udWxsIHx8IHRoaXMucG9zSW5MaXN0ID09IDApO1xyXG4gICAgdGhpcy5wcmV2QWN0aW9uLmRpc2FibGVkPSh0aGlzLnBvc0luTGlzdD09bnVsbCB8fCB0aGlzLnBvc0luTGlzdCA9PSAwKTtcclxuICAgIHRoaXMubmV4dEFjdGlvbi5kaXNhYmxlZD0odGhpcy5wb3NJbkxpc3Q9PW51bGwgfHwgaXRlbUNudD09bnVsbCB8fCB0aGlzLnBvc0luTGlzdCA+PSBpdGVtQ250IC0gMSk7XHJcbiAgICB0aGlzLmxhc3RBY3Rpb24uZGlzYWJsZWQ9KHRoaXMucG9zSW5MaXN0PT1udWxsIHx8IGl0ZW1DbnQ9PW51bGwgfHwgdGhpcy5wb3NJbkxpc3QgPj0gaXRlbUNudCAtIDEpO1xyXG4gIH1cclxuXHJcbiAgcHJpdmF0ZSBsb2FkU2Vzc2lvbihzZXNzaW9uSWQ6IHN0cmluZ3wgbnVtYmVyKSB7XHJcbiAgICAvLyBsb2FkIHNlc3Npb24gYW5kIHJlY29yZGluZyBmaWxlIG1ldGEgZGF0YSBvbmx5IHdoZW4gb24gaW5pdCBhbmQgd2hlbiBzZXNzaW9uIGNoYW5nZXNcclxuICAgIGlmICg8c3RyaW5nPnNlc3Npb25JZCAhPSA8c3RyaW5nPnRoaXMuc2Vzc2lvbklkKSB7XHJcbiAgICAgIC8vIHRlbGwgVUkgdGhhdCB3ZSBhcmUgd29ya2luZy4uLlxyXG4gICAgICB0aGlzLm5hdmlJbmZvTG9hZGluZz10cnVlO1xyXG4gICAgICB0aGlzLnNlc3Npb25TZXJ2aWNlLnNlc3Npb25PYnNlcnZlcig8c3RyaW5nPnNlc3Npb25JZCkuc3Vic2NyaWJlKChzKSA9PiB7XHJcbiAgICAgICAgLy8gcmVjZWl2ZWQgc2Vzc2lvbiBkYXRhXHJcbiAgICAgICAgdGhpcy5zZXNzaW9uSWQgPSBzLnNlc3Npb25JZDtcclxuICAgICAgICAvLyBmZXRjaCByZWNvcmRpbmcgZmlsZSBtZXRhIGRhdGEgbGlzdFxyXG4gICAgICAgIHRoaXMucmVjb3JkaW5nU2VydmljZS5yZWNvcmRpbmdGaWxlTGlzdChzLnByb2plY3QsIHMuc2Vzc2lvbklkKS5zdWJzY3JpYmUoKHJmZHMpID0+IHtcclxuICAgICAgICAgIHRoaXMuYXZhaWxSZWNGaWxlcyA9IG5ldyBBcnJheTxBcnJheTxSZWNvcmRpbmdGaWxlPj4oKTtcclxuICAgICAgICAgIC8vIGJ1aWxkIHN0cnVjdHVyZSBpbmRleGVkIGJ5IGl0ZW1jb2RlXHJcbiAgICAgICAgICBsZXQgaWNJZHggPSBuZXcgSXRlbWNvZGVJbmRleCgpO1xyXG4gICAgICAgICAgZm9yIChsZXQgcmZkaSA9IDA7IHJmZGkgPCByZmRzLmxlbmd0aDsgcmZkaSsrKSB7XHJcbiAgICAgICAgICAgIGxldCByZmQgPSByZmRzW3JmZGldO1xyXG4gICAgICAgICAgICBpZiAocmZkLmRhdGUpIHtcclxuICAgICAgICAgICAgICAvLyBjb252ZXJ0IGRhdGUgc3RyaW5nIGZvciBmYXN0ZXIgc29ydGluZyBsYXRlclxyXG4gICAgICAgICAgICAgIGxldCByZmRkID0gbmV3IERhdGUocmZkLmRhdGUpO1xyXG4gICAgICAgICAgICAgIHJmZC5fZGF0ZUFzRGF0ZU9iaiA9IHJmZGQ7XHJcbiAgICAgICAgICAgIH1cclxuICAgICAgICAgICAgbGV0IHIgPSByZmQucmVjb3JkaW5nO1xyXG4gICAgICAgICAgICBsZXQgaWMgPSByLml0ZW1jb2RlO1xyXG4gICAgICAgICAgICBpZihpYykge1xyXG4gICAgICAgICAgICAgIGxldCBleFJmc0ZvckljID0gaWNJZHhbaWNdO1xyXG4gICAgICAgICAgICAgIGlmIChleFJmc0ZvckljID09IG51bGwpIHtcclxuICAgICAgICAgICAgICAgIC8vIGl0ZW1jb2RlIG5vdCB5ZXQgc3RvcmVkXHJcbiAgICAgICAgICAgICAgICBsZXQgYXJmZCA9IG5ldyBBcnJheTxSZWNvcmRpbmdGaWxlPigpO1xyXG4gICAgICAgICAgICAgICAgYXJmZC5wdXNoKHJmZCk7XHJcbiAgICAgICAgICAgICAgICBpY0lkeFtpY10gPSBhcmZkO1xyXG4gICAgICAgICAgICAgICAgdGhpcy5hdmFpbFJlY0ZpbGVzLnB1c2goYXJmZCk7XHJcbiAgICAgICAgICAgICAgfSBlbHNlIHtcclxuICAgICAgICAgICAgICAgIC8vIHJlYyBmaWxlIHdpdGggaXRlbWNvZGUgYWxyZWFkeSBleGlzdHMsIGFkZCAocHVzaCkgdGhpcyB2ZXJzaW9uIC4uLlxyXG4gICAgICAgICAgICAgICAgZXhSZnNGb3JJYy5wdXNoKHJmZCk7XHJcbiAgICAgICAgICAgICAgICAvLyAuLiBhbmQgc29ydCBsYXRlc3QgdmVyc2lvbiAoaGlnaGVzdCB2ZXJzaW9uIG51bWJlcikgdG8gbG93ZXN0IGluZGV4XHJcbiAgICAgICAgICAgICAgICBleFJmc0ZvckljLnNvcnQoKHJmZDEsIHJmZDIpID0+IHtcclxuICAgICAgICAgICAgICAgICAgcmV0dXJuIHJmZDIudmVyc2lvbiAtIHJmZDEudmVyc2lvbjtcclxuICAgICAgICAgICAgICAgIH0pXHJcbiAgICAgICAgICAgICAgfVxyXG4gICAgICAgICAgICB9XHJcbiAgICAgICAgICB9XHJcbiAgICAgICAgICAvLyBoYXZlIHVuc29ydGVkIGlldG1jb2RlIGluZGV4ZWQgcmVjb3JkaW5nIGZpbGVzIGhlcmVcclxuICAgICAgICAgIC8vIHNvcnQgdGhlbSBvcmRlcmVkIGJ5IGRhdGUgb2YgbGF0ZXN0IHZlcnNpb24gYXNjZW5kaW5nXHJcbiAgICAgICAgICB0aGlzLmF2YWlsUmVjRmlsZXMuc29ydCgocmZzMSwgcmZzMikgPT4ge1xyXG4gICAgICAgICAgICBsZXQgZDEgPSByZnMyWzBdLl9kYXRlQXNEYXRlT2JqO1xyXG4gICAgICAgICAgICBsZXQgZDIgPSByZnMxWzBdLl9kYXRlQXNEYXRlT2JqO1xyXG4gICAgICAgICAgICBpZiAoZDEgPT0gbnVsbCkge1xyXG4gICAgICAgICAgICAgIGlmIChkMiA9PSBudWxsKSB7XHJcbiAgICAgICAgICAgICAgICByZXR1cm4gMDtcclxuICAgICAgICAgICAgICB9IGVsc2Uge1xyXG4gICAgICAgICAgICAgICAgLy8gU29ydCBlbnRyaWVzIHdob3NlIGRhdGVzIGFyZSBub3Qgc2V0IHRvIHRoZSBlbmRcclxuICAgICAgICAgICAgICAgIHJldHVybiAtMTtcclxuICAgICAgICAgICAgICB9XHJcbiAgICAgICAgICAgIH0gZWxzZSB7XHJcbiAgICAgICAgICAgICAgaWYgKGQyID09IG51bGwpIHtcclxuICAgICAgICAgICAgICAgIC8vIFNvcnQgZW50cmllcyB3aG9zZSBkYXRlcyBhcmUgbm90IHNldCB0byB0aGUgZW5kXHJcbiAgICAgICAgICAgICAgICByZXR1cm4gMTtcclxuICAgICAgICAgICAgICB9IGVsc2Uge1xyXG4gICAgICAgICAgICAgICAgLy8gQ29tcGFyZSBkYXRlIGJ5IHRpbWUgaW4gbWlsbGlzZWNvbmRzIHZhbHVlXHJcbiAgICAgICAgICAgICAgICByZXR1cm4gZDIuZ2V0VGltZSgpIC0gZDEuZ2V0VGltZSgpO1xyXG4gICAgICAgICAgICAgIH1cclxuICAgICAgICAgICAgfVxyXG4gICAgICAgICAgfSk7XHJcbiAgICAgICAgICB0aGlzLnVwZGF0ZVBvcygpXHJcbiAgICAgICAgICB0aGlzLm5hdmlJbmZvTG9hZGluZz1mYWxzZTtcclxuICAgICAgICAgIHRoaXMucmVmLmRldGVjdENoYW5nZXMoKTtcclxuICAgICAgICB9KTtcclxuICAgICAgfSk7XHJcbiAgICB9XHJcbiAgfVxyXG59XHJcblxyXG4iXX0=