@hivegpt/hiveai-angular 0.0.582 → 0.0.584
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/bundles/hivegpt-hiveai-angular.umd.js +209 -382
- package/bundles/hivegpt-hiveai-angular.umd.js.map +1 -1
- package/bundles/hivegpt-hiveai-angular.umd.min.js +1 -1
- package/bundles/hivegpt-hiveai-angular.umd.min.js.map +1 -1
- package/esm2015/hivegpt-hiveai-angular.js +4 -5
- package/esm2015/lib/components/voice-agent/services/voice-agent.service.js +174 -165
- package/esm2015/lib/components/voice-agent/voice-agent.module.js +3 -5
- package/fesm2015/hivegpt-hiveai-angular.js +173 -323
- package/fesm2015/hivegpt-hiveai-angular.js.map +1 -1
- package/hivegpt-hiveai-angular.d.ts +3 -4
- package/hivegpt-hiveai-angular.d.ts.map +1 -1
- package/hivegpt-hiveai-angular.metadata.json +1 -1
- package/lib/components/voice-agent/services/voice-agent.service.d.ts +24 -15
- package/lib/components/voice-agent/services/voice-agent.service.d.ts.map +1 -1
- package/lib/components/voice-agent/voice-agent.module.d.ts +2 -2
- package/lib/components/voice-agent/voice-agent.module.d.ts.map +1 -1
- package/package.json +1 -1
- package/esm2015/lib/components/voice-agent/services/websocket-voice-client.service.js +0 -163
- package/lib/components/voice-agent/services/websocket-voice-client.service.d.ts +0 -52
- package/lib/components/voice-agent/services/websocket-voice-client.service.d.ts.map +0 -1
|
@@ -3,12 +3,11 @@
|
|
|
3
3
|
*/
|
|
4
4
|
export * from './public-api';
|
|
5
5
|
export { NotificationSocket as ɵd } from './lib/components/NotificationSocket';
|
|
6
|
-
export { BotHtmlEditorComponent as
|
|
6
|
+
export { BotHtmlEditorComponent as ɵh } from './lib/components/bot-html-editor/bot-html-editor.component';
|
|
7
7
|
export { BotsService as ɵa } from './lib/components/bot.service';
|
|
8
8
|
export { ConversationService as ɵc } from './lib/components/conversation.service';
|
|
9
9
|
export { SocketService as ɵb } from './lib/components/socket-service.service';
|
|
10
10
|
export { TranslationService as ɵe } from './lib/components/translations/translation.service';
|
|
11
|
-
export { VideoPlayerComponent as
|
|
12
|
-
export {
|
|
13
|
-
|
|
14
|
-
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiaGl2ZWdwdC1oaXZlYWktYW5ndWxhci5qcyIsInNvdXJjZVJvb3QiOiIvVXNlcnMvcm9oaXR0aGFrdXIvaGl2ZS1ncHQvSGl2ZUFJLVBhY2thZ2VzL0FuZ3VsYXIvcHJvamVjdHMvaGl2ZWdwdC9ldmVudHNncHQtYW5ndWxhci9zcmMvIiwic291cmNlcyI6WyJoaXZlZ3B0LWhpdmVhaS1hbmd1bGFyLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBOztHQUVHO0FBRUgsY0FBYyxjQUFjLENBQUM7QUFFN0IsT0FBTyxFQUFDLGtCQUFrQixJQUFJLEVBQUUsRUFBQyxNQUFNLHFDQUFxQyxDQUFDO0FBQzdFLE9BQU8sRUFBQyxzQkFBc0IsSUFBSSxFQUFFLEVBQUMsTUFBTSw0REFBNEQsQ0FBQztBQUN4RyxPQUFPLEVBQUMsV0FBVyxJQUFJLEVBQUUsRUFBQyxNQUFNLDhCQUE4QixDQUFDO0FBQy9ELE9BQU8sRUFBQyxtQkFBbUIsSUFBSSxFQUFFLEVBQUMsTUFBTSx1Q0FBdUMsQ0FBQztBQUNoRixPQUFPLEVBQUMsYUFBYSxJQUFJLEVBQUUsRUFBQyxNQUFNLHlDQUF5QyxDQUFDO0FBQzVFLE9BQU8sRUFBQyxrQkFBa0IsSUFBSSxFQUFFLEVBQUMsTUFBTSxtREFBbUQsQ0FBQztBQUMzRixPQUFPLEVBQUMsb0JBQW9CLElBQUksRUFBRSxFQUFDLE1BQU0sc0RBQXNELENBQUM7QUFDaEcsT0FBTyxFQUFDLDJCQUEyQixJQUFJLEVBQUUsRUFBQyxNQUFNLHNFQUFzRSxDQUFDO0FBQ3ZILE9BQU8sRUFBQyxZQUFZLElBQUksRUFBRSxFQUFDLE1BQU0sNEJBQTRCLENBQUMiLCJzb3VyY2VzQ29udGVudCI6WyIvKipcbiAqIEdlbmVyYXRlZCBidW5kbGUgaW5kZXguIERvIG5vdCBlZGl0LlxuICovXG5cbmV4cG9ydCAqIGZyb20gJy4vcHVibGljLWFwaSc7XG5cbmV4cG9ydCB7Tm90aWZpY2F0aW9uU29ja2V0IGFzIMm1ZH0gZnJvbSAnLi9saWIvY29tcG9uZW50cy9Ob3RpZmljYXRpb25Tb2NrZXQnO1xuZXhwb3J0IHtCb3RIdG1sRWRpdG9yQ29tcG9uZW50IGFzIMm1aX0gZnJvbSAnLi9saWIvY29tcG9uZW50cy9ib3QtaHRtbC1lZGl0b3IvYm90LWh0bWwtZWRpdG9yLmNvbXBvbmVudCc7XG5leHBvcnQge0JvdHNTZXJ2aWNlIGFzIMm1YX0gZnJvbSAnLi9saWIvY29tcG9uZW50cy9ib3Quc2VydmljZSc7XG5leHBvcnQge0NvbnZlcnNhdGlvblNlcnZpY2UgYXMgybVjfSBmcm9tICcuL2xpYi9jb21wb25lbnRzL2NvbnZlcnNhdGlvbi5zZXJ2aWNlJztcbmV4cG9ydCB7U29ja2V0U2VydmljZSBhcyDJtWJ9IGZyb20gJy4vbGliL2NvbXBvbmVudHMvc29ja2V0LXNlcnZpY2Uuc2VydmljZSc7XG5leHBvcnQge1RyYW5zbGF0aW9uU2VydmljZSBhcyDJtWV9IGZyb20gJy4vbGliL2NvbXBvbmVudHMvdHJhbnNsYXRpb25zL3RyYW5zbGF0aW9uLnNlcnZpY2UnO1xuZXhwb3J0IHtWaWRlb1BsYXllckNvbXBvbmVudCBhcyDJtWd9IGZyb20gJy4vbGliL2NvbXBvbmVudHMvdmlkZW8tcGxheWVyL3ZpZGVvLXBsYXllci5jb21wb25lbnQnO1xuZXhwb3J0IHtXZWJTb2NrZXRWb2ljZUNsaWVudFNlcnZpY2UgYXMgybVmfSBmcm9tICcuL2xpYi9jb21wb25lbnRzL3ZvaWNlLWFnZW50L3NlcnZpY2VzL3dlYnNvY2tldC12b2ljZS1jbGllbnQuc2VydmljZSc7XG5leHBvcnQge1NhZmVIdG1sUGlwZSBhcyDJtWh9IGZyb20gJy4vbGliL3BpcGVzL3NhZmUtaHRtbC5waXBlJzsiXX0=
|
|
11
|
+
export { VideoPlayerComponent as ɵf } from './lib/components/video-player/video-player.component';
|
|
12
|
+
export { SafeHtmlPipe as ɵg } from './lib/pipes/safe-html.pipe';
|
|
13
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiaGl2ZWdwdC1oaXZlYWktYW5ndWxhci5qcyIsInNvdXJjZVJvb3QiOiIvVXNlcnMvcm9oaXR0aGFrdXIvaGl2ZS1ncHQvSGl2ZUFJLVBhY2thZ2VzL0FuZ3VsYXIvcHJvamVjdHMvaGl2ZWdwdC9ldmVudHNncHQtYW5ndWxhci9zcmMvIiwic291cmNlcyI6WyJoaXZlZ3B0LWhpdmVhaS1hbmd1bGFyLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBOztHQUVHO0FBRUgsY0FBYyxjQUFjLENBQUM7QUFFN0IsT0FBTyxFQUFDLGtCQUFrQixJQUFJLEVBQUUsRUFBQyxNQUFNLHFDQUFxQyxDQUFDO0FBQzdFLE9BQU8sRUFBQyxzQkFBc0IsSUFBSSxFQUFFLEVBQUMsTUFBTSw0REFBNEQsQ0FBQztBQUN4RyxPQUFPLEVBQUMsV0FBVyxJQUFJLEVBQUUsRUFBQyxNQUFNLDhCQUE4QixDQUFDO0FBQy9ELE9BQU8sRUFBQyxtQkFBbUIsSUFBSSxFQUFFLEVBQUMsTUFBTSx1Q0FBdUMsQ0FBQztBQUNoRixPQUFPLEVBQUMsYUFBYSxJQUFJLEVBQUUsRUFBQyxNQUFNLHlDQUF5QyxDQUFDO0FBQzVFLE9BQU8sRUFBQyxrQkFBa0IsSUFBSSxFQUFFLEVBQUMsTUFBTSxtREFBbUQsQ0FBQztBQUMzRixPQUFPLEVBQUMsb0JBQW9CLElBQUksRUFBRSxFQUFDLE1BQU0sc0RBQXNELENBQUM7QUFDaEcsT0FBTyxFQUFDLFlBQVksSUFBSSxFQUFFLEVBQUMsTUFBTSw0QkFBNEIsQ0FBQyIsInNvdXJjZXNDb250ZW50IjpbIi8qKlxuICogR2VuZXJhdGVkIGJ1bmRsZSBpbmRleC4gRG8gbm90IGVkaXQuXG4gKi9cblxuZXhwb3J0ICogZnJvbSAnLi9wdWJsaWMtYXBpJztcblxuZXhwb3J0IHtOb3RpZmljYXRpb25Tb2NrZXQgYXMgybVkfSBmcm9tICcuL2xpYi9jb21wb25lbnRzL05vdGlmaWNhdGlvblNvY2tldCc7XG5leHBvcnQge0JvdEh0bWxFZGl0b3JDb21wb25lbnQgYXMgybVofSBmcm9tICcuL2xpYi9jb21wb25lbnRzL2JvdC1odG1sLWVkaXRvci9ib3QtaHRtbC1lZGl0b3IuY29tcG9uZW50JztcbmV4cG9ydCB7Qm90c1NlcnZpY2UgYXMgybVhfSBmcm9tICcuL2xpYi9jb21wb25lbnRzL2JvdC5zZXJ2aWNlJztcbmV4cG9ydCB7Q29udmVyc2F0aW9uU2VydmljZSBhcyDJtWN9IGZyb20gJy4vbGliL2NvbXBvbmVudHMvY29udmVyc2F0aW9uLnNlcnZpY2UnO1xuZXhwb3J0IHtTb2NrZXRTZXJ2aWNlIGFzIMm1Yn0gZnJvbSAnLi9saWIvY29tcG9uZW50cy9zb2NrZXQtc2VydmljZS5zZXJ2aWNlJztcbmV4cG9ydCB7VHJhbnNsYXRpb25TZXJ2aWNlIGFzIMm1ZX0gZnJvbSAnLi9saWIvY29tcG9uZW50cy90cmFuc2xhdGlvbnMvdHJhbnNsYXRpb24uc2VydmljZSc7XG5leHBvcnQge1ZpZGVvUGxheWVyQ29tcG9uZW50IGFzIMm1Zn0gZnJvbSAnLi9saWIvY29tcG9uZW50cy92aWRlby1wbGF5ZXIvdmlkZW8tcGxheWVyLmNvbXBvbmVudCc7XG5leHBvcnQge1NhZmVIdG1sUGlwZSBhcyDJtWd9IGZyb20gJy4vbGliL3BpcGVzL3NhZmUtaHRtbC5waXBlJzsiXX0=
|
|
@@ -1,27 +1,33 @@
|
|
|
1
1
|
import { __awaiter } from "tslib";
|
|
2
2
|
import { isPlatformBrowser } from '@angular/common';
|
|
3
|
-
import { Inject, Injectable, PLATFORM_ID } from '@angular/core';
|
|
4
|
-
import { BehaviorSubject,
|
|
5
|
-
import {
|
|
3
|
+
import { Inject, Injectable, NgZone, PLATFORM_ID } from '@angular/core';
|
|
4
|
+
import { BehaviorSubject, Subject, Subscription } from 'rxjs';
|
|
5
|
+
import { take } from 'rxjs/operators';
|
|
6
|
+
import { PipecatClient, RTVIEvent } from '@pipecat-ai/client-js';
|
|
7
|
+
import { WebSocketTransport } from '@pipecat-ai/websocket-transport';
|
|
6
8
|
import { PlatformTokenRefreshService } from '../../../services/platform-token-refresh.service';
|
|
7
9
|
import { AudioAnalyzerService } from './audio-analyzer.service';
|
|
8
|
-
import { WebSocketVoiceClientService } from './websocket-voice-client.service';
|
|
9
10
|
import * as i0 from "@angular/core";
|
|
10
11
|
import * as i1 from "./audio-analyzer.service";
|
|
11
|
-
import * as i2 from "
|
|
12
|
-
import * as i3 from "../../../services/platform-token-refresh.service";
|
|
12
|
+
import * as i2 from "../../../services/platform-token-refresh.service";
|
|
13
13
|
/**
|
|
14
|
-
* Voice agent orchestrator
|
|
15
|
-
*
|
|
16
|
-
*
|
|
14
|
+
* Voice agent orchestrator using the official PipecatClient SDK.
|
|
15
|
+
*
|
|
16
|
+
* Audio flow (mirrors the React reference implementation):
|
|
17
|
+
* - Local mic: acquired by PipecatClient.initDevices(); local track fed to
|
|
18
|
+
* AudioAnalyzerService for waveform visualisation.
|
|
19
|
+
* - Bot audio: received as a MediaStreamTrack via RTVIEvent.TrackStarted,
|
|
20
|
+
* played through a hidden <audio> element.
|
|
21
|
+
* - All binary protobuf framing / RTVI protocol handled by
|
|
22
|
+
* @pipecat-ai/client-js + @pipecat-ai/websocket-transport.
|
|
17
23
|
*/
|
|
18
24
|
export class VoiceAgentService {
|
|
19
|
-
constructor(audioAnalyzer,
|
|
25
|
+
constructor(audioAnalyzer, platformTokenRefresh, ngZone,
|
|
20
26
|
/** `Object` not `object` — ngc metadata collection rejects the `object` type in DI params. */
|
|
21
27
|
platformId) {
|
|
22
28
|
this.audioAnalyzer = audioAnalyzer;
|
|
23
|
-
this.wsClient = wsClient;
|
|
24
29
|
this.platformTokenRefresh = platformTokenRefresh;
|
|
30
|
+
this.ngZone = ngZone;
|
|
25
31
|
this.platformId = platformId;
|
|
26
32
|
this.callStateSubject = new BehaviorSubject('idle');
|
|
27
33
|
this.statusTextSubject = new BehaviorSubject('');
|
|
@@ -33,8 +39,8 @@ export class VoiceAgentService {
|
|
|
33
39
|
this.botTranscriptSubject = new Subject();
|
|
34
40
|
this.callStartTime = 0;
|
|
35
41
|
this.durationInterval = null;
|
|
36
|
-
this.
|
|
37
|
-
this.
|
|
42
|
+
this.pcClient = null;
|
|
43
|
+
this.botAudioElement = null;
|
|
38
44
|
this.subscriptions = new Subscription();
|
|
39
45
|
this.destroy$ = new Subject();
|
|
40
46
|
this.callState$ = this.callStateSubject.asObservable();
|
|
@@ -46,25 +52,17 @@ export class VoiceAgentService {
|
|
|
46
52
|
this.userTranscript$ = this.userTranscriptSubject.asObservable();
|
|
47
53
|
this.botTranscript$ = this.botTranscriptSubject.asObservable();
|
|
48
54
|
this.subscriptions.add(this.audioAnalyzer.audioLevels$.subscribe((levels) => this.audioLevelsSubject.next(levels)));
|
|
49
|
-
this.subscriptions.add(this.wsClient.remoteClose$
|
|
50
|
-
.pipe(takeUntil(this.destroy$))
|
|
51
|
-
.subscribe(() => void this.handleRemoteClose()));
|
|
52
55
|
}
|
|
53
56
|
ngOnDestroy() {
|
|
54
57
|
this.destroy$.next();
|
|
55
58
|
this.subscriptions.unsubscribe();
|
|
56
|
-
this.disconnect();
|
|
59
|
+
void this.disconnect();
|
|
57
60
|
}
|
|
58
|
-
/** Reset to idle
|
|
61
|
+
/** Reset to idle (e.g. when modal re-opens so user can click Start Call). */
|
|
59
62
|
resetToIdle() {
|
|
60
63
|
if (this.callStateSubject.value === 'idle')
|
|
61
64
|
return;
|
|
62
|
-
this.
|
|
63
|
-
this.stopDurationTimer();
|
|
64
|
-
this.callStartTime = 0;
|
|
65
|
-
this.audioAnalyzer.stop();
|
|
66
|
-
this.stopLocalMic();
|
|
67
|
-
this.wsClient.disconnect();
|
|
65
|
+
void this.disconnect();
|
|
68
66
|
this.callStateSubject.next('idle');
|
|
69
67
|
this.statusTextSubject.next('');
|
|
70
68
|
this.durationSubject.next('0:00');
|
|
@@ -72,7 +70,7 @@ export class VoiceAgentService {
|
|
|
72
70
|
connect(apiUrl, token, botId, conversationId, apiKey, eventToken, eventId, eventUrl, domainAuthority, usersApiUrl) {
|
|
73
71
|
return __awaiter(this, void 0, void 0, function* () {
|
|
74
72
|
if (this.callStateSubject.value !== 'idle') {
|
|
75
|
-
console.warn('Call already in progress');
|
|
73
|
+
console.warn('[HiveGpt Voice] Call already in progress');
|
|
76
74
|
return;
|
|
77
75
|
}
|
|
78
76
|
try {
|
|
@@ -85,185 +83,196 @@ export class VoiceAgentService {
|
|
|
85
83
|
.ensureValidAccessToken(token, usersApiUrl)
|
|
86
84
|
.pipe(take(1))
|
|
87
85
|
.toPromise();
|
|
88
|
-
if (ensured === null || ensured === void 0 ? void 0 : ensured.accessToken)
|
|
86
|
+
if (ensured === null || ensured === void 0 ? void 0 : ensured.accessToken)
|
|
89
87
|
accessToken = ensured.accessToken;
|
|
90
|
-
}
|
|
91
88
|
}
|
|
92
89
|
catch (e) {
|
|
93
|
-
console.warn('[HiveGpt Voice] Token refresh
|
|
90
|
+
console.warn('[HiveGpt Voice] Token refresh failed', e);
|
|
94
91
|
}
|
|
95
92
|
}
|
|
96
93
|
const baseUrl = apiUrl.replace(/\/$/, '');
|
|
97
|
-
const
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
94
|
+
const pcClient = new PipecatClient({
|
|
95
|
+
transport: new WebSocketTransport(),
|
|
96
|
+
enableMic: true,
|
|
97
|
+
enableCam: false,
|
|
98
|
+
callbacks: {
|
|
99
|
+
onConnected: () => this.ngZone.run(() => this.onPipecatConnected()),
|
|
100
|
+
onDisconnected: () => this.ngZone.run(() => this.onPipecatDisconnected()),
|
|
101
|
+
onBotReady: () => this.ngZone.run(() => this.onBotReady()),
|
|
102
|
+
onUserTranscript: (data) => this.ngZone.run(() => this.userTranscriptSubject.next({ text: data.text, final: !!data.final })),
|
|
103
|
+
onBotTranscript: (data) => this.ngZone.run(() => this.botTranscriptSubject.next(data.text)),
|
|
104
|
+
onError: (err) => {
|
|
105
|
+
this.ngZone.run(() => {
|
|
106
|
+
console.error('[HiveGpt Voice] PipecatClient error', err);
|
|
107
|
+
this.callStateSubject.next('ended');
|
|
108
|
+
this.statusTextSubject.next('Connection failed');
|
|
109
|
+
});
|
|
110
|
+
},
|
|
111
|
+
},
|
|
112
|
+
});
|
|
113
|
+
this.pcClient = pcClient;
|
|
114
|
+
// Bot audio arrives as a MediaStreamTrack — wire to a hidden <audio> element
|
|
115
|
+
pcClient.on(RTVIEvent.TrackStarted, (track, participant) => {
|
|
116
|
+
if (!(participant === null || participant === void 0 ? void 0 : participant.local) && track.kind === 'audio') {
|
|
117
|
+
this.ngZone.run(() => this.setupBotAudioTrack(track));
|
|
118
|
+
}
|
|
119
|
+
});
|
|
120
|
+
// Speaking state comes straight from RTVI events
|
|
121
|
+
pcClient.on(RTVIEvent.BotStartedSpeaking, () => this.ngZone.run(() => this.onBotStartedSpeaking()));
|
|
122
|
+
pcClient.on(RTVIEvent.BotStoppedSpeaking, () => this.ngZone.run(() => this.onBotStoppedSpeaking()));
|
|
123
|
+
pcClient.on(RTVIEvent.UserStartedSpeaking, () => this.ngZone.run(() => {
|
|
124
|
+
this.isUserSpeakingSubject.next(true);
|
|
125
|
+
this.callStateSubject.next('listening');
|
|
126
|
+
}));
|
|
127
|
+
pcClient.on(RTVIEvent.UserStoppedSpeaking, () => this.ngZone.run(() => {
|
|
128
|
+
this.isUserSpeakingSubject.next(false);
|
|
129
|
+
if (this.callStateSubject.value === 'listening') {
|
|
130
|
+
this.callStateSubject.next('connected');
|
|
131
|
+
}
|
|
132
|
+
}));
|
|
133
|
+
// Acquire mic (triggers browser permission prompt)
|
|
134
|
+
yield pcClient.initDevices();
|
|
135
|
+
// Build headers using the browser Headers API (required by pipecat's APIRequest type)
|
|
136
|
+
const requestHeaders = new Headers();
|
|
137
|
+
requestHeaders.append('Authorization', `Bearer ${accessToken}`);
|
|
138
|
+
requestHeaders.append('x-api-key', apiKey);
|
|
139
|
+
requestHeaders.append('hive-bot-id', botId);
|
|
140
|
+
requestHeaders.append('domain-authority', domainAuthority);
|
|
141
|
+
requestHeaders.append('eventUrl', eventUrl);
|
|
142
|
+
requestHeaders.append('eventId', eventId);
|
|
143
|
+
requestHeaders.append('eventToken', eventToken);
|
|
144
|
+
requestHeaders.append('ngrok-skip-browser-warning', 'true');
|
|
145
|
+
// POST to /ai/ask-voice-socket → receives { ws_url } → WebSocketTransport connects
|
|
146
|
+
yield pcClient.startBotAndConnect({
|
|
147
|
+
endpoint: `${baseUrl}/ai/ask-voice-socket`,
|
|
148
|
+
headers: requestHeaders,
|
|
149
|
+
requestData: {
|
|
113
150
|
bot_id: botId,
|
|
114
151
|
conversation_id: conversationId,
|
|
115
152
|
voice: 'alloy',
|
|
116
|
-
}
|
|
153
|
+
},
|
|
117
154
|
});
|
|
118
|
-
if (!res.ok) {
|
|
119
|
-
throw new Error(`HTTP ${res.status}`);
|
|
120
|
-
}
|
|
121
|
-
const json = yield res.json();
|
|
122
|
-
const wsUrl = (typeof (json === null || json === void 0 ? void 0 : json.ws_url) === 'string' && json.ws_url) ||
|
|
123
|
-
(typeof (json === null || json === void 0 ? void 0 : json.rn_ws_url) === 'string' && json.rn_ws_url);
|
|
124
|
-
if (!wsUrl) {
|
|
125
|
-
throw new Error('No ws_url in response');
|
|
126
|
-
}
|
|
127
|
-
const untilCallEnds$ = merge(this.destroy$, this.endCall$);
|
|
128
|
-
this.subscriptions.add(this.wsClient.userTranscript$
|
|
129
|
-
.pipe(takeUntil(untilCallEnds$))
|
|
130
|
-
.subscribe((t) => this.userTranscriptSubject.next(t)));
|
|
131
|
-
this.subscriptions.add(this.wsClient.botTranscript$
|
|
132
|
-
.pipe(takeUntil(untilCallEnds$))
|
|
133
|
-
.subscribe((t) => this.botTranscriptSubject.next(t)));
|
|
134
|
-
this.subscriptions.add(this.wsClient.opened$
|
|
135
|
-
.pipe(takeUntil(untilCallEnds$), take(1))
|
|
136
|
-
.subscribe(() => void this.onWebsocketOpened()));
|
|
137
|
-
this.wsClient.connect(wsUrl);
|
|
138
155
|
}
|
|
139
156
|
catch (error) {
|
|
140
|
-
console.error('
|
|
157
|
+
console.error('[HiveGpt Voice] connect failed', error);
|
|
141
158
|
this.callStateSubject.next('ended');
|
|
142
|
-
yield this.
|
|
159
|
+
yield this.cleanupPipecatClient();
|
|
143
160
|
this.statusTextSubject.next('Connection failed');
|
|
144
161
|
throw error;
|
|
145
162
|
}
|
|
146
163
|
});
|
|
147
164
|
}
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
try {
|
|
154
|
-
yield this.startLocalMic();
|
|
155
|
-
this.statusTextSubject.next('Connected');
|
|
156
|
-
this.callStateSubject.next('connected');
|
|
157
|
-
this.wireSpeakingState();
|
|
158
|
-
}
|
|
159
|
-
catch (err) {
|
|
160
|
-
console.error('[HiveGpt Voice] Mic or session setup failed', err);
|
|
161
|
-
this.callStateSubject.next('ended');
|
|
162
|
-
this.statusTextSubject.next('Microphone unavailable');
|
|
163
|
-
yield this.disconnect();
|
|
164
|
-
}
|
|
165
|
-
});
|
|
165
|
+
onPipecatConnected() {
|
|
166
|
+
this.callStateSubject.next('connected');
|
|
167
|
+
this.statusTextSubject.next('Connected');
|
|
168
|
+
this.isMicMutedSubject.next(false);
|
|
169
|
+
this.startLocalMicAnalyzer();
|
|
166
170
|
}
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
]).pipe(map(([local, server]) => local || server), distinctUntilChanged(), startWith(false));
|
|
175
|
-
this.subscriptions.add(combineLatest([assistantTalking$, userTalking$])
|
|
176
|
-
.pipe(takeUntil(untilCallEnds$))
|
|
177
|
-
.subscribe(([bot, user]) => {
|
|
178
|
-
const current = this.callStateSubject.value;
|
|
179
|
-
if (user) {
|
|
180
|
-
this.isUserSpeakingSubject.next(true);
|
|
181
|
-
this.callStateSubject.next('listening');
|
|
182
|
-
}
|
|
183
|
-
else {
|
|
184
|
-
this.isUserSpeakingSubject.next(false);
|
|
185
|
-
}
|
|
186
|
-
if (user) {
|
|
187
|
-
return;
|
|
188
|
-
}
|
|
189
|
-
if (bot) {
|
|
190
|
-
if (this.callStartTime === 0) {
|
|
191
|
-
this.callStartTime = Date.now();
|
|
192
|
-
this.startDurationTimer();
|
|
193
|
-
}
|
|
194
|
-
this.callStateSubject.next('talking');
|
|
195
|
-
}
|
|
196
|
-
else if (current === 'talking' || current === 'listening') {
|
|
197
|
-
this.callStateSubject.next('connected');
|
|
198
|
-
}
|
|
199
|
-
}));
|
|
171
|
+
onPipecatDisconnected() {
|
|
172
|
+
this.stopDurationTimer();
|
|
173
|
+
this.callStartTime = 0;
|
|
174
|
+
this.audioAnalyzer.stop();
|
|
175
|
+
this.stopBotAudio();
|
|
176
|
+
this.callStateSubject.next('ended');
|
|
177
|
+
this.statusTextSubject.next('Call Ended');
|
|
200
178
|
}
|
|
201
|
-
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
throw new Error('No audio track');
|
|
209
|
-
}
|
|
210
|
-
this.localMicStream = stream;
|
|
211
|
-
this.isMicMutedSubject.next(!track.enabled);
|
|
212
|
-
this.audioAnalyzer.start(stream);
|
|
213
|
-
});
|
|
179
|
+
onBotReady() {
|
|
180
|
+
var _a, _b, _c;
|
|
181
|
+
// Retry track wiring in case tracks weren't ready at onConnected
|
|
182
|
+
this.startLocalMicAnalyzer();
|
|
183
|
+
const botTrack = (_c = (_b = (_a = this.pcClient) === null || _a === void 0 ? void 0 : _a.tracks()) === null || _b === void 0 ? void 0 : _b.bot) === null || _c === void 0 ? void 0 : _c.audio;
|
|
184
|
+
if (botTrack)
|
|
185
|
+
this.setupBotAudioTrack(botTrack);
|
|
214
186
|
}
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
187
|
+
startLocalMicAnalyzer() {
|
|
188
|
+
var _a, _b, _c;
|
|
189
|
+
const localTrack = (_c = (_b = (_a = this.pcClient) === null || _a === void 0 ? void 0 : _a.tracks()) === null || _b === void 0 ? void 0 : _b.local) === null || _c === void 0 ? void 0 : _c.audio;
|
|
190
|
+
if (localTrack) {
|
|
191
|
+
this.audioAnalyzer.start(new MediaStream([localTrack]));
|
|
219
192
|
}
|
|
220
193
|
}
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
this.
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
194
|
+
onBotStartedSpeaking() {
|
|
195
|
+
if (this.callStartTime === 0) {
|
|
196
|
+
this.callStartTime = Date.now();
|
|
197
|
+
this.startDurationTimer();
|
|
198
|
+
}
|
|
199
|
+
this.callStateSubject.next('talking');
|
|
200
|
+
}
|
|
201
|
+
onBotStoppedSpeaking() {
|
|
202
|
+
if (this.callStateSubject.value === 'talking') {
|
|
203
|
+
this.callStateSubject.next('connected');
|
|
204
|
+
}
|
|
205
|
+
}
|
|
206
|
+
setupBotAudioTrack(track) {
|
|
207
|
+
var _a;
|
|
208
|
+
if (!this.botAudioElement) {
|
|
209
|
+
this.botAudioElement = new Audio();
|
|
210
|
+
this.botAudioElement.autoplay = true;
|
|
211
|
+
}
|
|
212
|
+
const existing = (_a = this.botAudioElement.srcObject) === null || _a === void 0 ? void 0 : _a.getAudioTracks()[0];
|
|
213
|
+
if ((existing === null || existing === void 0 ? void 0 : existing.id) === track.id)
|
|
214
|
+
return;
|
|
215
|
+
this.botAudioElement.srcObject = new MediaStream([track]);
|
|
216
|
+
this.botAudioElement.play().catch((err) => console.warn('[HiveGpt Voice] Bot audio play blocked', err));
|
|
217
|
+
}
|
|
218
|
+
stopBotAudio() {
|
|
219
|
+
var _a;
|
|
220
|
+
if (this.botAudioElement) {
|
|
221
|
+
try {
|
|
222
|
+
this.botAudioElement.pause();
|
|
223
|
+
(_a = this.botAudioElement.srcObject) === null || _a === void 0 ? void 0 : _a.getAudioTracks().forEach((t) => t.stop());
|
|
224
|
+
this.botAudioElement.srcObject = null;
|
|
225
|
+
}
|
|
226
|
+
catch (_b) {
|
|
227
|
+
// ignore
|
|
228
|
+
}
|
|
229
|
+
this.botAudioElement = null;
|
|
230
|
+
}
|
|
234
231
|
}
|
|
235
232
|
disconnect() {
|
|
236
233
|
return __awaiter(this, void 0, void 0, function* () {
|
|
237
|
-
this.endCall$.next();
|
|
238
234
|
this.stopDurationTimer();
|
|
239
235
|
this.callStartTime = 0;
|
|
240
236
|
this.audioAnalyzer.stop();
|
|
241
|
-
this.
|
|
242
|
-
this.
|
|
237
|
+
this.stopBotAudio();
|
|
238
|
+
yield this.cleanupPipecatClient();
|
|
243
239
|
this.callStateSubject.next('ended');
|
|
244
240
|
this.statusTextSubject.next('Call Ended');
|
|
245
241
|
});
|
|
246
242
|
}
|
|
243
|
+
cleanupPipecatClient() {
|
|
244
|
+
return __awaiter(this, void 0, void 0, function* () {
|
|
245
|
+
if (this.pcClient) {
|
|
246
|
+
try {
|
|
247
|
+
yield this.pcClient.disconnect();
|
|
248
|
+
}
|
|
249
|
+
catch (_a) {
|
|
250
|
+
// ignore
|
|
251
|
+
}
|
|
252
|
+
this.pcClient = null;
|
|
253
|
+
}
|
|
254
|
+
});
|
|
255
|
+
}
|
|
247
256
|
toggleMic() {
|
|
248
|
-
|
|
257
|
+
if (!this.pcClient)
|
|
258
|
+
return;
|
|
249
259
|
const nextMuted = !this.isMicMutedSubject.value;
|
|
250
|
-
|
|
251
|
-
if (track) {
|
|
252
|
-
track.enabled = !nextMuted;
|
|
253
|
-
}
|
|
260
|
+
this.pcClient.enableMic(!nextMuted);
|
|
254
261
|
this.isMicMutedSubject.next(nextMuted);
|
|
262
|
+
if (nextMuted)
|
|
263
|
+
this.isUserSpeakingSubject.next(false);
|
|
255
264
|
}
|
|
256
265
|
startDurationTimer() {
|
|
257
|
-
const
|
|
266
|
+
const tick = () => {
|
|
258
267
|
if (this.callStartTime > 0) {
|
|
259
268
|
const elapsed = Math.floor((Date.now() - this.callStartTime) / 1000);
|
|
260
|
-
const
|
|
261
|
-
const
|
|
262
|
-
this.durationSubject.next(`${
|
|
269
|
+
const m = Math.floor(elapsed / 60);
|
|
270
|
+
const s = elapsed % 60;
|
|
271
|
+
this.durationSubject.next(`${m}:${String(s).padStart(2, '0')}`);
|
|
263
272
|
}
|
|
264
273
|
};
|
|
265
|
-
|
|
266
|
-
this.durationInterval = setInterval(
|
|
274
|
+
tick();
|
|
275
|
+
this.durationInterval = setInterval(tick, 1000);
|
|
267
276
|
}
|
|
268
277
|
stopDurationTimer() {
|
|
269
278
|
if (this.durationInterval) {
|
|
@@ -272,7 +281,7 @@ export class VoiceAgentService {
|
|
|
272
281
|
}
|
|
273
282
|
}
|
|
274
283
|
}
|
|
275
|
-
VoiceAgentService.ɵprov = i0.ɵɵdefineInjectable({ factory: function VoiceAgentService_Factory() { return new VoiceAgentService(i0.ɵɵinject(i1.AudioAnalyzerService), i0.ɵɵinject(i2.
|
|
284
|
+
VoiceAgentService.ɵprov = i0.ɵɵdefineInjectable({ factory: function VoiceAgentService_Factory() { return new VoiceAgentService(i0.ɵɵinject(i1.AudioAnalyzerService), i0.ɵɵinject(i2.PlatformTokenRefreshService), i0.ɵɵinject(i0.NgZone), i0.ɵɵinject(i0.PLATFORM_ID)); }, token: VoiceAgentService, providedIn: "root" });
|
|
276
285
|
VoiceAgentService.decorators = [
|
|
277
286
|
{ type: Injectable, args: [{
|
|
278
287
|
providedIn: 'root',
|
|
@@ -280,8 +289,8 @@ VoiceAgentService.decorators = [
|
|
|
280
289
|
];
|
|
281
290
|
VoiceAgentService.ctorParameters = () => [
|
|
282
291
|
{ type: AudioAnalyzerService },
|
|
283
|
-
{ type: WebSocketVoiceClientService },
|
|
284
292
|
{ type: PlatformTokenRefreshService },
|
|
293
|
+
{ type: NgZone },
|
|
285
294
|
{ type: Object, decorators: [{ type: Inject, args: [PLATFORM_ID,] }] }
|
|
286
295
|
];
|
|
287
|
-
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoidm9pY2UtYWdlbnQuc2VydmljZS5qcyIsInNvdXJjZVJvb3QiOiIvVXNlcnMvcm9oaXR0aGFrdXIvaGl2ZS1ncHQvSGl2ZUFJLVBhY2thZ2VzL0FuZ3VsYXIvcHJvamVjdHMvaGl2ZWdwdC9ldmVudHNncHQtYW5ndWxhci9zcmMvIiwic291cmNlcyI6WyJsaWIvY29tcG9uZW50cy92b2ljZS1hZ2VudC9zZXJ2aWNlcy92b2ljZS1hZ2VudC5zZXJ2aWNlLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7QUFBQSxPQUFPLEVBQUUsaUJBQWlCLEVBQUUsTUFBTSxpQkFBaUIsQ0FBQztBQUNwRCxPQUFPLEVBQUUsTUFBTSxFQUFFLFVBQVUsRUFBYSxXQUFXLEVBQUUsTUFBTSxlQUFlLENBQUM7QUFDM0UsT0FBTyxFQUNMLGVBQWUsRUFDZixhQUFhLEVBQ2IsTUFBTSxFQUNOLEtBQUssRUFFTCxFQUFFLEVBQ0YsT0FBTyxFQUNQLFlBQVksRUFDWixLQUFLLEdBQ04sTUFBTSxNQUFNLENBQUM7QUFDZCxPQUFPLEVBQ0wsb0JBQW9CLEVBQ3BCLEdBQUcsRUFDSCxTQUFTLEVBQ1QsU0FBUyxFQUNULElBQUksRUFDSixTQUFTLEdBQ1YsTUFBTSxnQkFBZ0IsQ0FBQztBQUN4QixPQUFPLEVBQUUsMkJBQTJCLEVBQUUsTUFBTSxrREFBa0QsQ0FBQztBQUMvRixPQUFPLEVBQUUsb0JBQW9CLEVBQUUsTUFBTSwwQkFBMEIsQ0FBQztBQUNoRSxPQUFPLEVBQUUsMkJBQTJCLEVBQUUsTUFBTSxrQ0FBa0MsQ0FBQzs7Ozs7QUFlL0U7Ozs7R0FJRztBQUlILE1BQU0sT0FBTyxpQkFBaUI7SUE4QjVCLFlBQ1UsYUFBbUMsRUFDbkMsUUFBcUMsRUFDckMsb0JBQWlEO0lBQ3pELDhGQUE4RjtJQUNqRSxVQUFrQjtRQUp2QyxrQkFBYSxHQUFiLGFBQWEsQ0FBc0I7UUFDbkMsYUFBUSxHQUFSLFFBQVEsQ0FBNkI7UUFDckMseUJBQW9CLEdBQXBCLG9CQUFvQixDQUE2QjtRQUU1QixlQUFV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LE9BQU8sQ0FBQyxDQUFDLFFBQVEsQ0FBQyxDQUFDLEVBQUUsR0FBRyxDQUFDLEVBQUUsQ0FDakQsQ0FBQzthQUNIO1FBQ0gsQ0FBQyxDQUFDO1FBQ0YsY0FBYyxFQUFFLENBQUM7UUFDakIsSUFBSSxDQUFDLGdCQUFnQixHQUFHLFdBQVcsQ0FBQyxjQUFjLEVBQUUsSUFBSSxDQUFDLENBQUM7SUFDNUQsQ0FBQztJQUVPLGlCQUFpQjtRQUN2QixJQUFJLElBQUksQ0FBQyxnQkFBZ0IsRUFBRTtZQUN6QixhQUFhLENBQUMsSUFBSSxDQUFDLGdCQUFnQixDQUFDLENBQUM7WUFDckMsSUFBSSxDQUFDLGdCQUFnQixHQUFHLElBQUksQ0FBQztTQUM5QjtJQUNILENBQUM7Ozs7WUE1VEYsVUFBVSxTQUFDO2dCQUNWLFVBQVUsRUFBRSxNQUFNO2FBQ25COzs7WUF2QlEsb0JBQW9CO1lBQ3BCLDJCQUEyQjtZQUYzQiwyQkFBMkI7WUE0RFMsTUFBTSx1QkFBOUMsTUFBTSxTQUFDLFdBQVciLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBpc1BsYXRmb3JtQnJvd3NlciB9IGZyb20gJ0Bhbmd1bGFyL2NvbW1vbic7XG5pbXBvcnQgeyBJbmplY3QsIEluamVjdGFibGUsIE9uRGVzdHJveSwgUExBVEZPUk1fSUQgfSBmcm9tICdAYW5ndWxhci9jb3JlJztcbmltcG9ydCB7XG4gIEJlaGF2aW9yU3ViamVjdCxcbiAgY29tYmluZUxhdGVzdCxcbiAgY29uY2F0LFxuICBtZXJnZSxcbiAgT2JzZXJ2YWJsZSxcbiAgb2YsXG4gIFN1YmplY3QsXG4gIFN1YnNjcmlwdGlvbixcbiAgdGltZXIsXG59IGZyb20gJ3J4anMnO1xuaW1wb3J0IHtcbiAgZGlzdGluY3RVbnRpbENoYW5nZWQsXG4gIG1hcCxcbiAgc3RhcnRXaXRoLFxuICBzd2l0Y2hNYXAsXG4gIHRha2UsXG4gIHRha2VVbnRpbCxcbn0gZnJvbSAncnhqcy9vcGVyYXRvcnMnO1xuaW1wb3J0IHsgUGxhdGZvcm1Ub2tlblJlZnJlc2hTZXJ2aWNlIH0gZnJvbSAnLi4vLi4vLi4vc2VydmljZXMvcGxhdGZvcm0tdG9rZW4tcmVmcmVzaC5zZXJ2aWNlJztcbmltcG9ydCB7IEF1ZGlvQW5hbHl6ZXJTZXJ2aWNlIH0gZnJvbSAnLi9hdWRpby1hbmFseXplci5zZXJ2aWNlJztcbmltcG9ydCB7IFdlYlNvY2tldFZvaWNlQ2xpZW50U2VydmljZSB9IGZyb20gJy4vd2Vic29ja2V0LXZvaWNlLWNsaWVudC5zZXJ2aWNlJztcblxuZXhwb3J0IHR5cGUgQ2FsbFN0YXRlID1cbiAgfCAnaWRsZSdcbiAgfCAnY29ubmVjdGluZydcbiAgfCAnY29ubmVjdGVkJ1xuICB8ICdsaXN0ZW5pbmcnXG4gIHwgJ3RhbGtpbmcnXG4gIHwgJ2VuZGVkJztcblxuZXhwb3J0IGludGVyZmFjZSBUcmFuc2NyaXB0RGF0YSB7XG4gIHRleHQ6IHN0cmluZztcbiAgZmluYWw6IGJvb2xlYW47XG59XG5cbi8qKlxuICogVm9pY2UgYWdlbnQgb3JjaGVzdHJhdG9yOiBzaW5nbGUgV2ViU29ja2V0IChgd3NfdXJsYCBmcm9tIFBPU1QgL2FpL2Fzay12b2ljZS1zb2NrZXQpXG4gKiBmb3Igc2Vzc2lvbiBldmVudHMsIHRyYW5zY3JpcHRzLCBhbmQgb3B0aW9uYWwgc3BlYWtpbmcgaGludHM7IGxvY2FsIG1pYyBmb3IgY2FwdHVyZVxuICogYW5kIHdhdmVmb3JtIG9ubHkgKG5vIERhaWx5L1dlYlJUQyByb29tKS5cbiAqL1xuQEluamVjdGFibGUoe1xuICBwcm92aWRlZEluOiAncm9vdCcsXG59KVxuZXhwb3J0IGNsYXNzIFZvaWNlQWdlbnRTZXJ2aWNlIGltcGxlbWVudHMgT25EZXN0cm95IHtcbiAgcHJpdmF0ZSBjYWxsU3RhdGVTdWJqZWN0ID0gbmV3IEJlaGF2aW9yU3ViamVjdDxDYWxsU3RhdGU+KCdpZGxlJyk7XG4gIHByaXZhdGUgc3RhdHVzVGV4dFN1YmplY3QgPSBuZXcgQmVoYXZpb3JTdWJqZWN0PHN0cmluZz4oJycpO1xuICBwcml2YXRlIGR1cmF0aW9uU3ViamVjdCA9IG5ldyBCZWhhdmlvclN1YmplY3Q8c3RyaW5nPignMDA6MDAnKTtcbiAgcHJpdmF0ZSBpc01pY011dGVkU3ViamVjdCA9IG5ldyBCZWhhdmlvclN1YmplY3Q8Ym9vbGVhbj4oZmFsc2UpO1xuICBwcml2YXRlIGlzVXNlclNwZWFraW5nU3ViamVjdCA9IG5ldyBCZWhhdmlvclN1YmplY3Q8Ym9vbGVhbj4oZmFsc2UpO1xuICBwcml2YXRlIGF1ZGlvTGV2ZWxzU3ViamVjdCA9IG5ldyBCZWhhdmlvclN1YmplY3Q8bnVtYmVyW10+KFtdKTtcbiAgcHJpdmF0ZSB1c2VyVHJhbnNjcmlwdFN1YmplY3QgPSBuZXcgU3ViamVjdDxUcmFuc2NyaXB0RGF0YT4oKTtcbiAgcHJpdmF0ZSBib3RUcmFuc2NyaXB0U3ViamVjdCA9IG5ldyBTdWJqZWN0PHN0cmluZz4oKTtcblxuICBwcml2YXRlIGNhbGxTdGFydFRpbWUgPSAwO1xuICBwcml2YXRlIGR1cmF0aW9uSW50ZXJ2YWw6IFJldHVyblR5cGU8dHlwZW9mIHNldEludGVydmFsPiB8IG51bGwgPSBudWxsO1xuXG4gIHByaXZhdGUgbG9jYWxNaWNTdHJlYW06IE1lZGlhU3RyZWFtIHwgbnVsbCA9IG51bGw7XG4gIHByaXZhdGUgcmVhZG9ubHkgZW5kQ2FsbCQgPSBuZXcgU3ViamVjdDx2b2lkPigpO1xuXG4gIHByaXZhdGUgc3Vic2NyaXB0aW9ucyA9IG5ldyBTdWJzY3JpcHRpb24oKTtcbiAgcHJpdmF0ZSBkZXN0cm95JCA9IG5ldyBTdWJqZWN0PHZvaWQ+KCk7XG5cbiAgY2FsbFN0YXRlJDogT2JzZXJ2YWJsZTxDYWxsU3RhdGU+ID0gdGhpcy5jYWxsU3RhdGVTdWJqZWN0LmFzT2JzZXJ2YWJsZSgpO1xuICBzdGF0dXNUZXh0JDogT2JzZXJ2YWJsZTxzdHJpbmc+ID0gdGhpcy5zdGF0dXNUZXh0U3ViamVjdC5hc09ic2VydmFibGUoKTtcbiAgZHVyYXRpb24kOiBPYnNlcnZhYmxlPHN0cmluZz4gPSB0aGlzLmR1cmF0aW9uU3ViamVjdC5hc09ic2VydmFibGUoKTtcbiAgaXNNaWNNdXRlZCQ6IE9ic2VydmFibGU8Ym9vbGVhbj4gPSB0aGlzLmlzTWljTXV0ZWRTdWJqZWN0LmFzT2JzZXJ2YWJsZSgpO1xuICBpc1VzZXJTcGVha2luZyQ6IE9ic2VydmFibGU8Ym9vbGVhbj4gPVxuICAgIHRoaXMuaXNVc2VyU3BlYWtpbmdTdWJqZWN0LmFzT2JzZXJ2YWJsZSgpO1xuICBhdWRpb0xldmVscyQ6IE9ic2VydmFibGU8bnVtYmVyW10+ID0gdGhpcy5hdWRpb0xldmVsc1N1YmplY3QuYXNPYnNlcnZhYmxlKCk7XG4gIHVzZXJUcmFuc2NyaXB0JDogT2JzZXJ2YWJsZTxUcmFuc2NyaXB0RGF0YT4gPVxuICAgIHRoaXMudXNlclRyYW5zY3JpcHRTdWJqZWN0LmFzT2JzZXJ2YWJsZSgpO1xuICBib3RUcmFuc2NyaXB0JDogT2JzZXJ2YWJsZTxzdHJpbmc+ID0gdGhpcy5ib3RUcmFuc2NyaXB0U3ViamVjdC5hc09ic2VydmFibGUoKTtcblxuICBjb25zdHJ1Y3RvcihcbiAgICBwcml2YXRlIGF1ZGlvQW5hbHl6ZXI6IEF1ZGlvQW5hbHl6ZXJTZXJ2aWNlLFxuICAgIHByaXZhdGUgd3NDbGllbnQ6IFdlYlNvY2tldFZvaWNlQ2xpZW50U2VydmljZSxcbiAgICBwcml2YXRlIHBsYXRmb3JtVG9rZW5SZWZyZXNoOiBQbGF0Zm9ybVRva2VuUmVmcmVzaFNlcnZpY2UsXG4gICAgLyoqIGBPYmplY3RgIG5vdCBgb2JqZWN0YCDigJQgbmdjIG1ldGFkYXRhIGNvbGxlY3Rpb24gcmVqZWN0cyB0aGUgYG9iamVjdGAgdHlwZSBpbiBESSBwYXJhbXMuICovXG4gICAgQEluamVjdChQTEFURk9STV9JRCkgcHJpdmF0ZSBwbGF0Zm9ybUlkOiBPYmplY3QsXG4gICkge1xuICAgIHRoaXMuc3Vic2NyaXB0aW9ucy5hZGQoXG4gICAgICB0aGlzLmF1ZGlvQW5hbHl6ZXIuYXVkaW9MZXZlbHMkLnN1YnNjcmliZSgobGV2ZWxzKSA9PlxuICAgICAgICB0aGlzLmF1ZGlvTGV2ZWxzU3ViamVjdC5uZXh0KGxldmVscyksXG4gICAgICApLFxuICAgICk7XG4gICAgdGhpcy5zdWJzY3JpcHRpb25zLmFkZChcbiAgICAgIHRoaXMud3NDbGllbnQucmVtb3RlQ2xvc2UkXG4gICAgICAgIC5waXBlKHRha2VVbnRpbCh0aGlzLmRlc3Ryb3kkKSlcbiAgICAgICAgLnN1YnNjcmliZSgoKSA9PiB2b2lkIHRoaXMuaGFuZGxlUmVtb3RlQ2xvc2UoKSksXG4gICAgKTtcbiAgfVxuXG4gIG5nT25EZXN0cm95KCk6IHZvaWQge1xuICAgIHRoaXMuZGVzdHJveSQubmV4dCgpO1xuICAgIHRoaXMuc3Vic2NyaXB0aW9ucy51bnN1YnNjcmliZSgpO1xuICAgIHRoaXMuZGlzY29ubmVjdCgpO1xuICB9XG5cbiAgLyoqIFJlc2V0IHRvIGlkbGUgc3RhdGUgKGUuZy4gd2hlbiBtb2RhbCBvcGVucyBzbyB1c2VyIGNhbiBjbGljayBTdGFydCBDYWxsKS4gKi9cbiAgcmVzZXRUb0lkbGUoKTogdm9pZCB7XG4gICAgaWYgKHRoaXMuY2FsbFN0YXRlU3ViamVjdC52YWx1ZSA9PT0gJ2lkbGUnKSByZXR1cm47XG4gICAgdGhpcy5lbmRDYWxsJC5uZXh0KCk7XG4gICAgdGhpcy5zdG9wRHVyYXRpb25UaW1lcigpO1xuICAgIHRoaXMuY2FsbFN0YXJ0VGltZSA9IDA7XG4gICAgdGhpcy5hdWRpb0FuYWx5emVyLnN0b3AoKTtcbiAgICB0aGlzLnN0b3BMb2NhbE1pYygpO1xuICAgIHRoaXMud3NDbGllbnQuZGlzY29ubmVjdCgpO1xuICAgIHRoaXMuY2FsbFN0YXRlU3ViamVjdC5uZXh0KCdpZGxlJyk7XG4gICAgdGhpcy5zdGF0dXNUZXh0U3ViamVjdC5uZXh0KCcnKTtcbiAgICB0aGlzLmR1cmF0aW9uU3ViamVjdC5uZXh0KCcwOjAwJyk7XG4gIH1cblxuICBhc3luYyBjb25uZWN0KFxuICAgIGFwaVVybDogc3RyaW5nLFxuICAgIHRva2VuOiBzdHJpbmcsXG4gICAgYm90SWQ6IHN0cmluZyxcbiAgICBjb252ZXJzYXRpb25JZDogc3RyaW5nLFxuICAgIGFwaUtleTogc3RyaW5nLFxuICAgIGV2ZW50VG9rZW46IHN0cmluZyxcbiAgICBldmVudElkOiBzdHJpbmcsXG4gICAgZXZlbnRVcmw6IHN0cmluZyxcbiAgICBkb21haW5BdXRob3JpdHk6IHN0cmluZyxcbiAgICB1c2Vyc0FwaVVybD86IHN0cmluZyxcbiAgKTogUHJvbWlzZTx2b2lkPiB7XG4gICAgaWYgKHRoaXMuY2FsbFN0YXRlU3ViamVjdC52YWx1ZSAhPT0gJ2lkbGUnKSB7XG4gICAgICBjb25zb2xlLndhcm4oJ0NhbGwgYWxyZWFkeSBpbiBwcm9ncmVzcycpO1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIHRyeSB7XG4gICAgICB0aGlzLmNhbGxTdGF0ZVN1YmplY3QubmV4dCgnY29ubmVjdGluZycpO1xuICAgICAgdGhpcy5zdGF0dXNUZXh0U3ViamVjdC5uZXh0KCdDb25uZWN0aW5nLi4uJyk7XG5cbiAgICAgIGxldCBhY2Nlc3NUb2tlbiA9IHRva2VuO1xuICAgICAgaWYgKHVzZXJzQXBpVXJsICYmIGlzUGxhdGZvcm1Ccm93c2VyKHRoaXMucGxhdGZvcm1JZCkpIHtcbiAgICAgICAgdHJ5IHtcbiAgICAgICAgICBjb25zdCBlbnN1cmVkID0gYXdhaXQgdGhpcy5wbGF0Zm9ybVRva2VuUmVmcmVzaFxuICAgICAgICAgICAgLmVuc3VyZVZhbGlkQWNjZXNzVG9rZW4odG9rZW4sIHVzZXJzQXBpVXJsKVxuICAgICAgICAgICAgLnBpcGUodGFrZSgxKSlcbiAgICAgICAgICAgIC50b1Byb21pc2UoKTtcbiAgICAgICAgICBpZiAoZW5zdXJlZD8uYWNjZXNzVG9rZW4pIHtcbiAgICAgICAgICAgIGFjY2Vzc1Rva2VuID0gZW5zdXJlZC5hY2Nlc3NUb2tlbjtcbiAgICAgICAgICB9XG4gICAgICAgIH0gY2F0Y2ggKGUpIHtcbiAgICAgICAgICBjb25zb2xlLndhcm4oXG4gICAgICAgICAgICAnW0hpdmVHcHQgVm9pY2VdIFRva2VuIHJlZnJlc2ggYmVmb3JlIGNvbm5lY3QgZmFpbGVkJyxcbiAgICAgICAgICAgIGUsXG4gICAgICAgICAgKTtcbiAgICAgICAgfVxuICAgICAgfVxuXG4gICAgICBjb25zdCBiYXNlVXJsID0gYXBpVXJsLnJlcGxhY2UoL1xcLyQvLCAnJyk7XG4gICAgICBjb25zdCBwb3N0VXJsID0gYCR7YmFzZVVybH0vYWkvYXNrLXZvaWNlLXNvY2tldGA7XG5cbiAgICAgIGNvbnN0IGhlYWRlcnM6IFJlY29yZDxzdHJpbmcsIHN0cmluZz4gPSB7XG4gICAgICAgICdDb250ZW50LVR5cGUnOiAnYXBwbGljYXRpb24vanNvbicsXG4gICAgICAgIEF1dGhvcml6YXRpb246IGBCZWFyZXIgJHthY2Nlc3NUb2tlbn1gLFxuICAgICAgICAneC1hcGkta2V5JzogYXBpS2V5LFxuICAgICAgICAnaGl2ZS1ib3QtaWQnOiBib3RJZCxcbiAgICAgICAgJ2RvbWFpbi1hdXRob3JpdHknOiBkb21haW5BdXRob3JpdHksXG4gICAgICAgIGV2ZW50VXJsLFxuICAgICAgICBldmVudElkLFxuICAgICAgICBldmVudFRva2VuLFxuICAgICAgICAnbmdyb2stc2tpcC1icm93c2VyLXdhcm5pbmcnOiAndHJ1ZScsXG4gICAgICB9O1xuXG4gICAgICBjb25zdCByZXMgPSBhd2FpdCBmZXRjaChwb3N0VXJsLCB7XG4gICAgICAgIG1ldGhvZDogJ1BPU1QnLFxuICAgICAgICBoZWFkZXJzLFxuICAgICAgICBib2R5OiBKU09OLnN0cmluZ2lmeSh7XG4gICAgICAgICAgYm90X2lkOiBib3RJZCxcbiAgICAgICAgICBjb252ZXJzYXRpb25faWQ6IGNvbnZlcnNhdGlvbklkLFxuICAgICAgICAgIHZvaWNlOiAnYWxsb3knLFxuICAgICAgICB9KSxcbiAgICAgIH0pO1xuXG4gICAgICBpZiAoIXJlcy5vaykge1xuICAgICAgICB0aHJvdyBuZXcgRXJyb3IoYEhUVFAgJHtyZXMuc3RhdHVzfWApO1xuICAgICAgfVxuXG4gICAgICBjb25zdCBqc29uID0gYXdhaXQgcmVzLmpzb24oKTtcbiAgICAgIGNvbnN0IHdzVXJsID1cbiAgICAgICAgKHR5cGVvZiBqc29uPy53c191cmwgPT09ICdzdHJpbmcnICYmIGpzb24ud3NfdXJsKSB8fFxuICAgICAgICAodHlwZW9mIGpzb24/LnJuX3dzX3VybCA9PT0gJ3N0cmluZycgJiYganNvbi5ybl93c191cmwpO1xuICAgICAgaWYgKCF3c1VybCkge1xuICAgICAgICB0aHJvdyBuZXcgRXJyb3IoJ05vIHdzX3VybCBpbiByZXNwb25zZScpO1xuICAgICAgfVxuXG4gICAgICBjb25zdCB1bnRpbENhbGxFbmRzJCA9IG1lcmdlKHRoaXMuZGVzdHJveSQsIHRoaXMuZW5kQ2FsbCQpO1xuXG4gICAgICB0aGlzLnN1YnNjcmlwdGlvbnMuYWRkKFxuICAgICAgICB0aGlzLndzQ2xpZW50LnVzZXJUcmFuc2NyaXB0JFxuICAgICAgICAgIC5waXBlKHRha2VVbnRpbCh1bnRpbENhbGxFbmRzJCkpXG4gICAgICAgICAgLnN1YnNjcmliZSgodCkgPT4gdGhpcy51c2VyVHJhbnNjcmlwdFN1YmplY3QubmV4dCh0KSksXG4gICAgICApO1xuICAgICAgdGhpcy5zdWJzY3JpcHRpb25zLmFkZChcbiAgICAgICAgdGhpcy53c0NsaWVudC5ib3RUcmFuc2NyaXB0JFxuICAgICAgICAgIC5waXBlKHRha2VVbnRpbCh1bnRpbENhbGxFbmRzJCkpXG4gICAgICAgICAgLnN1YnNjcmliZSgodCkgPT4gdGhpcy5ib3RUcmFuc2NyaXB0U3ViamVjdC5uZXh0KHQpKSxcbiAgICAgICk7XG5cbiAgICAgIHRoaXMuc3Vic2NyaXB0aW9ucy5hZGQoXG4gICAgICAgIHRoaXMud3NDbGllbnQub3BlbmVkJFxuICAgICAgICAgIC5waXBlKHRha2VVbnRpbCh1bnRpbENhbGxFbmRzJCksIHRha2UoMSkpXG4gICAgICAgICAgLnN1YnNjcmliZSgoKSA9PiB2b2lkIHRoaXMub25XZWJzb2NrZXRPcGVuZWQoKSksXG4gICAgICApO1xuXG4gICAgICB0aGlzLndzQ2xpZW50LmNvbm5lY3Qod3NVcmwpO1xuICAgIH0gY2F0Y2ggKGVycm9yKSB7XG4gICAgICBjb25zb2xlLmVycm9yKCdFcnJvciBjb25uZWN0aW5nIHZvaWNlIGFnZW50OicsIGVycm9yKTtcbiAgICAgIHRoaXMuY2FsbFN0YXRlU3ViamVjdC5uZXh0KCdlbmRlZCcpO1xuICAgICAgYXdhaXQgdGhpcy5kaXNjb25uZWN0KCk7XG4gICAgICB0aGlzLnN0YXR1c1RleHRTdWJqZWN0Lm5leHQoJ0Nvbm5lY3Rpb24gZmFpbGVkJyk7XG4gICAgICB0aHJvdyBlcnJvcjtcbiAgICB9XG4gIH1cblxuICBwcml2YXRlIGFzeW5jIG9uV2Vic29ja2V0T3BlbmVkKCk6IFByb21pc2U8dm9pZD4ge1xuICAgIGlmICh0aGlzLmNhbGxTdGF0ZVN1YmplY3QudmFsdWUgIT09ICdjb25uZWN0aW5nJykge1xuICAgICAgcmV0dXJuO1xuICAgIH1cbiAgICB0cnkge1xuICAgICAgYXdhaXQgdGhpcy5zdGFydExvY2FsTWljKCk7XG4gICAgICB0aGlzLnN0YXR1c1RleHRTdWJqZWN0Lm5leHQoJ0Nvbm5lY3RlZCcpO1xuICAgICAgdGhpcy5jYWxsU3RhdGVTdWJqZWN0Lm5leHQoJ2Nvbm5lY3RlZCcpO1xuICAgICAgdGhpcy53aXJlU3BlYWtpbmdTdGF0ZSgpO1xuICAgIH0gY2F0Y2ggKGVycikge1xuICAgICAgY29uc29sZS5lcnJvcignW0hpdmVHcHQgVm9pY2VdIE1pYyBvciBzZXNzaW9uIHNldHVwIGZhaWxlZCcsIGVycik7XG4gICAgICB0aGlzLmNhbGxTdGF0ZVN1YmplY3QubmV4dCgnZW5kZWQnKTtcbiAgICAgIHRoaXMuc3RhdHVzVGV4dFN1YmplY3QubmV4dCgnTWljcm9waG9uZSB1bmF2YWlsYWJsZScpO1xuICAgICAgYXdhaXQgdGhpcy5kaXNjb25uZWN0KCk7XG4gICAgfVxuICB9XG5cbiAgcHJpdmF0ZSB3aXJlU3BlYWtpbmdTdGF0ZSgpOiB2b2lkIHtcbiAgICBjb25zdCB1bnRpbENhbGxFbmRzJCA9IG1lcmdlKHRoaXMuZGVzdHJveSQsIHRoaXMuZW5kQ2FsbCQpO1xuXG4gICAgY29uc3QgdHJhbnNjcmlwdERyaXZlbkFzc2lzdGFudCQgPSB0aGlzLndzQ2xpZW50LmJvdFRyYW5zY3JpcHQkLnBpcGUoXG4gICAgICBzd2l0Y2hNYXAoKCkgPT4gY29uY2F0KG9mKHRydWUpLCB0aW1lcig4MDApLnBpcGUobWFwKCgpID0+IGZhbHNlKSkpKSxcbiAgICAgIGRpc3RpbmN0VW50aWxDaGFuZ2VkKCksXG4gICAgKTtcblxuICAgIGNvbnN0IGFzc2lzdGFudFRhbGtpbmckID0gbWVyZ2UoXG4gICAgICB0aGlzLndzQ2xpZW50LmFzc2lzdGFudFNwZWFraW5nJCxcbiAgICAgIHRyYW5zY3JpcHREcml2ZW5Bc3Npc3RhbnQkLFxuICAgICkucGlwZShkaXN0aW5jdFVudGlsQ2hhbmdlZCgpLCBzdGFydFdpdGgoZmFsc2UpKTtcblxuICAgIGNvbnN0IHVzZXJUYWxraW5nJCA9IGNvbWJpbmVMYXRlc3QoW1xuICAgICAgdGhpcy5hdWRpb0FuYWx5emVyLmlzVXNlclNwZWFraW5nJCxcbiAgICAgIHRoaXMud3NDbGllbnQuc2VydmVyVXNlclNwZWFraW5nJC5waXBlKHN0YXJ0V2l0aChmYWxzZSkpLFxuICAgIF0pLnBpcGUoXG4gICAgICBtYXAoKFtsb2NhbCwgc2VydmVyXSkgPT4gbG9jYWwgfHwgc2VydmVyKSxcbiAgICAgIGRpc3RpbmN0VW50aWxDaGFuZ2VkKCksXG4gICAgICBzdGFydFdpdGgoZmFsc2UpLFxuICAgICk7XG5cbiAgICB0aGlzLnN1YnNjcmlwdGlvbnMuYWRkKFxuICAgICAgY29tYmluZUxhdGVzdChbYXNzaXN0YW50VGFsa2luZyQsIHVzZXJUYWxraW5nJF0pXG4gICAgICAgIC5waXBlKHRha2VVbnRpbCh1bnRpbENhbGxFbmRzJCkpXG4gICAgICAgIC5zdWJzY3JpYmUoKFtib3QsIHVzZXJdKSA9PiB7XG4gICAgICAgICAgY29uc3QgY3VycmVudCA9IHRoaXMuY2FsbFN0YXRlU3ViamVjdC52YWx1ZTtcbiAgICAgICAgICBpZiAodXNlcikge1xuICAgICAgICAgICAgdGhpcy5pc1VzZXJTcGVha2luZ1N1YmplY3QubmV4dCh0cnVlKTtcbiAgICAgICAgICAgIHRoaXMuY2FsbFN0YXRlU3ViamVjdC5uZXh0KCdsaXN0ZW5pbmcnKTtcbiAgICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgdGhpcy5pc1VzZXJTcGVha2luZ1N1YmplY3QubmV4dChmYWxzZSk7XG4gICAgICAgICAgfVxuICAgICAgICAgIGlmICh1c2VyKSB7XG4gICAgICAgICAgICByZXR1cm47XG4gICAgICAgICAgfVxuICAgICAgICAgIGlmIChib3QpIHtcbiAgICAgICAgICAgIGlmICh0aGlzLmNhbGxTdGFydFRpbWUgPT09IDApIHtcbiAgICAgICAgICAgICAgdGhpcy5jYWxsU3RhcnRUaW1lID0gRGF0ZS5ub3coKTtcbiAgICAgICAgICAgICAgdGhpcy5zdGFydER1cmF0aW9uVGltZXIoKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICAgIHRoaXMuY2FsbFN0YXRlU3ViamVjdC5uZXh0KCd0YWxraW5nJyk7XG4gICAgICAgICAgfSBlbHNlIGlmIChjdXJyZW50ID09PSAndGFsa2luZycgfHwgY3VycmVudCA9PT0gJ2xpc3RlbmluZycpIHtcbiAgICAgICAgICAgIHRoaXMuY2FsbFN0YXRlU3ViamVjdC5uZXh0KCdjb25uZWN0ZWQnKTtcbiAgICAgICAgICB9XG4gICAgICAgIH0pLFxuICAgICk7XG4gIH1cblxuICBwcml2YXRlIGFzeW5jIHN0YXJ0TG9jYWxNaWMoKTogUHJvbWlzZTx2b2lkPiB7XG4gICAgdGhpcy5zdG9wTG9jYWxNaWMoKTtcbiAgICBjb25zdCBzdHJlYW0gPSBhd2FpdCBuYXZpZ2F0b3IubWVkaWFEZXZpY2VzLmdldFVzZXJNZWRpYSh7IGF1ZGlvOiB0cnVlIH0pO1xuICAgIGNvbnN0IHRyYWNrID0gc3RyZWFtLmdldEF1ZGlvVHJhY2tzKClbMF07XG4gICAgaWYgKCF0cmFjaykge1xuICAgICAgc3RyZWFtLmdldFRyYWNrcygpLmZvckVhY2goKHQpID0+IHQuc3RvcCgpKTtcbiAgICAgIHRocm93IG5ldyBFcnJvcignTm8gYXVkaW8gdHJhY2snKTtcbiAgICB9XG4gICAgdGhpcy5sb2NhbE1pY1N0cmVhbSA9IHN0cmVhbTtcbiAgICB0aGlzLmlzTWljTXV0ZWRTdWJqZWN0Lm5leHQoIXRyYWNrLmVuYWJsZWQpO1xuICAgIHRoaXMuYXVkaW9BbmFseXplci5zdGFydChzdHJlYW0pO1xuICB9XG5cbiAgcHJpdmF0ZSBzdG9wTG9jYWxNaWMoKTogdm9pZCB7XG4gICAgaWYgKHRoaXMubG9jYWxNaWNTdHJlYW0pIHtcbiAgICAgIHRoaXMubG9jYWxNaWNTdHJlYW0uZ2V0VHJhY2tzKCkuZm9yRWFjaCgodCkgPT4gdC5zdG9wKCkpO1xuICAgICAgdGhpcy5sb2NhbE1pY1N0cmVhbSA9IG51bGw7XG4gICAgfVxuICB9XG5cbiAgcHJpdmF0ZSBhc3luYyBoYW5kbGVSZW1vdGVDbG9zZSgpOiBQcm9taXNlPHZvaWQ+IHtcbiAgICBjb25zdCBzdGF0ZSA9IHRoaXMuY2FsbFN0YXRlU3ViamVjdC52YWx1ZTtcbiAgICBpZiAoc3RhdGUgPT09ICdpZGxlJyB8fCBzdGF0ZSA9PT0gJ2VuZGVkJykgcmV0dXJuO1xuICAgIHRoaXMuZW5kQ2FsbCQubmV4dCgpO1xuICAgIHRoaXMuc3RvcER1cmF0aW9uVGltZXIoKTtcbiAgICB0aGlzLmNhbGxTdGFydFRpbWUgPSAwO1xuICAgIHRoaXMuYXVkaW9BbmFseXplci5zdG9wKCk7XG4gICAgdGhpcy5zdG9wTG9jYWxNaWMoKTtcbiAgICB0aGlzLmNhbGxTdGF0ZVN1YmplY3QubmV4dCgnZW5kZWQnKTtcbiAgICB0aGlzLnN0YXR1c1RleHRTdWJqZWN0Lm5leHQoJ0Nvbm5lY3Rpb24gbG9zdCcpO1xuICB9XG5cbiAgYXN5bmMgZGlzY29ubmVjdCgpOiBQcm9taXNlPHZvaWQ+IHtcbiAgICB0aGlzLmVuZENhbGwkLm5leHQoKTtcbiAgICB0aGlzLnN0b3BEdXJhdGlvblRpbWVyKCk7XG4gICAgdGhpcy5jYWxsU3RhcnRUaW1lID0gMDtcbiAgICB0aGlzLmF1ZGlvQW5hbHl6ZXIuc3RvcCgpO1xuICAgIHRoaXMuc3RvcExvY2FsTWljKCk7XG4gICAgdGhpcy53c0NsaWVudC5kaXNjb25uZWN0KCk7XG5cbiAgICB0aGlzLmNhbGxTdGF0ZVN1YmplY3QubmV4dCgnZW5kZWQnKTtcbiAgICB0aGlzLnN0YXR1c1RleHRTdWJqZWN0Lm5leHQoJ0NhbGwgRW5kZWQnKTtcbiAgfVxuXG4gIHRvZ2dsZU1pYygpOiB2b2lkIHtcbiAgICBjb25zdCBuZXh0TXV0ZWQgPSAhdGhpcy5pc01pY011dGVkU3ViamVjdC52YWx1ZTtcbiAgICBjb25zdCB0cmFjayA9IHRoaXMubG9jYWxNaWNTdHJlYW0/LmdldEF1ZGlvVHJhY2tzKClbMF07XG4gICAgaWYgKHRyYWNrKSB7XG4gICAgICB0cmFjay5lbmFibGVkID0gIW5leHRNdXRlZDtcbiAgICB9XG4gICAgdGhpcy5pc01pY011dGVkU3ViamVjdC5uZXh0KG5leHRNdXRlZCk7XG4gIH1cblxuICBwcml2YXRlIHN0YXJ0RHVyYXRpb25UaW1lcigpOiB2b2lkIHtcbiAgICBjb25zdCB1cGRhdGVEdXJhdGlvbiA9ICgpID0+IHtcbiAgICAgIGlmICh0aGlzLmNhbGxTdGFydFRpbWUgPiAwKSB7XG4gICAgICAgIGNvbnN0IGVsYXBzZWQgPSBNYXRoLmZsb29yKChEYXRlLm5vdygpIC0gdGhpcy5jYWxsU3RhcnRUaW1lKSAvIDEwMDApO1xuICAgICAgICBjb25zdCBtaW51dGVzID0gTWF0aC5mbG9vcihlbGFwc2VkIC8gNjApO1xuICAgICAgICBjb25zdCBzZWNvbmRzID0gZWxhcHNlZCAlIDYwO1xuICAgICAgICB0aGlzLmR1cmF0aW9uU3ViamVjdC5uZXh0KFxuICAgICAgICAgIGAke21pbnV0ZXN9OiR7U3RyaW5nKHNlY29uZHMpLnBhZFN0YXJ0KDIsICcwJyl9YCxcbiAgICAgICAgKTtcbiAgICAgIH1cbiAgICB9O1xuICAgIHVwZGF0ZUR1cmF0aW9uKCk7XG4gICAgdGhpcy5kdXJhdGlvbkludGVydmFsID0gc2V0SW50ZXJ2YWwodXBkYXRlRHVyYXRpb24sIDEwMDApO1xuICB9XG5cbiAgcHJpdmF0ZSBzdG9wRHVyYXRpb25UaW1lcigpOiB2b2lkIHtcbiAgICBpZiAodGhpcy5kdXJhdGlvbkludGVydmFsKSB7XG4gICAgICBjbGVhckludGVydmFsKHRoaXMuZHVyYXRpb25JbnRlcnZhbCk7XG4gICAgICB0aGlzLmR1cmF0aW9uSW50ZXJ2YWwgPSBudWxsO1xuICAgIH1cbiAgfVxufVxuIl19
|
|
296
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoidm9pY2UtYWdlbnQuc2VydmljZS5qcyIsInNvdXJjZVJvb3QiOiIvVXNlcnMvcm9oaXR0aGFrdXIvaGl2ZS1ncHQvSGl2ZUFJLVBhY2thZ2VzL0FuZ3VsYXIvcHJvamVjdHMvaGl2ZWdwdC9ldmVudHNncHQtYW5ndWxhci9zcmMvIiwic291cmNlcyI6WyJsaWIvY29tcG9uZW50cy92b2ljZS1hZ2VudC9zZXJ2aWNlcy92b2ljZS1hZ2VudC5zZXJ2aWNlLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7QUFBQSxPQUFPLEVBQUUsaUJBQWlCLEVBQUUsTUFBTSxpQkFBaUIsQ0FBQztBQUNwRCxPQUFPLEVBQUUsTUFBTSxFQUFFLFVBQVUsRUFBRSxNQUFNLEVBQWEsV0FBVyxFQUFFLE1BQU0sZUFBZSxDQUFDO0FBQ25GLE9BQU8sRUFBRSxlQUFlLEVBQWMsT0FBTyxFQUFFLFlBQVksRUFBRSxNQUFNLE1BQU0sQ0FBQztBQUMxRSxPQUFPLEVBQUUsSUFBSSxFQUFFLE1BQU0sZ0JBQWdCLENBQUM7QUFDdEMsT0FBTyxFQUFFLGFBQWEsRUFBRSxTQUFTLEVBQUUsTUFBTSx1QkFBdUIsQ0FBQztBQUNqRSxPQUFPLEVBQUUsa0JBQWtCLEVBQUUsTUFBTSxpQ0FBaUMsQ0FBQztBQUNyRSxPQUFPLEVBQUUsMkJBQTJCLEVBQUUsTUFBTSxrREFBa0QsQ0FBQztBQUMvRixPQUFPLEVBQUUsb0JBQW9CLEVBQUUsTUFBTSwwQkFBMEIsQ0FBQzs7OztBQWVoRTs7Ozs7Ozs7OztHQVVHO0FBSUgsTUFBTSxPQUFPLGlCQUFpQjtJQTRCNUIsWUFDVSxhQUFtQyxFQUNuQyxvQkFBaUQsRUFDakQsTUFBYztJQUN0Qiw4RkFBOEY7SUFDakUsVUFBa0I7UUFKdkMsa0JBQWEsR0FBYixhQUFhLENBQXNCO1FBQ25DLHlCQUFvQixHQUFwQixvQkFBb0IsQ0FBNkI7UUFDakQsV0FBTSxHQUFOLE1BQU0sQ0FBUTtRQUVPLGVBQVUsR0FBVixVQUFVLENBQVE7UUFoQ3pDLHFCQUFnQixHQUFHLElB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R0FBRyxDQUFDLElBQUksTUFBTSxDQUFDLENBQUMsQ0FBQyxDQUFDLFFBQVEsQ0FBQyxDQUFDLEVBQUUsR0FBRyxDQUFDLEVBQUUsQ0FBQyxDQUFDO2FBQ2pFO1FBQ0gsQ0FBQyxDQUFDO1FBQ0YsSUFBSSxFQUFFLENBQUM7UUFDUCxJQUFJLENBQUMsZ0JBQWdCLEdBQUcsV0FBVyxDQUFDLElBQUksRUFBRSxJQUFJLENBQUMsQ0FBQztJQUNsRCxDQUFDO0lBRU8saUJBQWlCO1FBQ3ZCLElBQUksSUFBSSxDQUFDLGdCQUFnQixFQUFFO1lBQ3pCLGFBQWEsQ0FBQyxJQUFJLENBQUMsZ0JBQWdCLENBQUMsQ0FBQztZQUNyQyxJQUFJLENBQUMsZ0JBQWdCLEdBQUcsSUFBSSxDQUFDO1NBQzlCO0lBQ0gsQ0FBQzs7OztZQXRURixVQUFVLFNBQUM7Z0JBQ1YsVUFBVSxFQUFFLE1BQU07YUFDbkI7OztZQTVCUSxvQkFBb0I7WUFEcEIsMkJBQTJCO1lBTFAsTUFBTTtZQW9FVSxNQUFNLHVCQUE5QyxNQUFNLFNBQUMsV0FBVyIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IGlzUGxhdGZvcm1Ccm93c2VyIH0gZnJvbSAnQGFuZ3VsYXIvY29tbW9uJztcbmltcG9ydCB7IEluamVjdCwgSW5qZWN0YWJsZSwgTmdab25lLCBPbkRlc3Ryb3ksIFBMQVRGT1JNX0lEIH0gZnJvbSAnQGFuZ3VsYXIvY29yZSc7XG5pbXBvcnQgeyBCZWhhdmlvclN1YmplY3QsIE9ic2VydmFibGUsIFN1YmplY3QsIFN1YnNjcmlwdGlvbiB9IGZyb20gJ3J4anMnO1xuaW1wb3J0IHsgdGFrZSB9IGZyb20gJ3J4anMvb3BlcmF0b3JzJztcbmltcG9ydCB7IFBpcGVjYXRDbGllbnQsIFJUVklFdmVudCB9IGZyb20gJ0BwaXBlY2F0LWFpL2NsaWVudC1qcyc7XG5pbXBvcnQgeyBXZWJTb2NrZXRUcmFuc3BvcnQgfSBmcm9tICdAcGlwZWNhdC1haS93ZWJzb2NrZXQtdHJhbnNwb3J0JztcbmltcG9ydCB7IFBsYXRmb3JtVG9rZW5SZWZyZXNoU2VydmljZSB9IGZyb20gJy4uLy4uLy4uL3NlcnZpY2VzL3BsYXRmb3JtLXRva2VuLXJlZnJlc2guc2VydmljZSc7XG5pbXBvcnQgeyBBdWRpb0FuYWx5emVyU2VydmljZSB9IGZyb20gJy4vYXVkaW8tYW5hbHl6ZXIuc2VydmljZSc7XG5cbmV4cG9ydCB0eXBlIENhbGxTdGF0ZSA9XG4gIHwgJ2lkbGUnXG4gIHwgJ2Nvbm5lY3RpbmcnXG4gIHwgJ2Nvbm5lY3RlZCdcbiAgfCAnbGlzdGVuaW5nJ1xuICB8ICd0YWxraW5nJ1xuICB8ICdlbmRlZCc7XG5cbmV4cG9ydCBpbnRlcmZhY2UgVHJhbnNjcmlwdERhdGEge1xuICB0ZXh0OiBzdHJpbmc7XG4gIGZpbmFsOiBib29sZWFuO1xufVxuXG4vKipcbiAqIFZvaWNlIGFnZW50IG9yY2hlc3RyYXRvciB1c2luZyB0aGUgb2ZmaWNpYWwgUGlwZWNhdENsaWVudCBTREsuXG4gKlxuICogQXVkaW8gZmxvdyAobWlycm9ycyB0aGUgUmVhY3QgcmVmZXJlbmNlIGltcGxlbWVudGF0aW9uKTpcbiAqICAtIExvY2FsIG1pYzogYWNxdWlyZWQgYnkgUGlwZWNhdENsaWVudC5pbml0RGV2aWNlcygpOyBsb2NhbCB0cmFjayBmZWQgdG9cbiAqICAgIEF1ZGlvQW5hbHl6ZXJTZXJ2aWNlIGZvciB3YXZlZm9ybSB2aXN1YWxpc2F0aW9uLlxuICogIC0gQm90IGF1ZGlvOiByZWNlaXZlZCBhcyBhIE1lZGlhU3RyZWFtVHJhY2sgdmlhIFJUVklFdmVudC5UcmFja1N0YXJ0ZWQsXG4gKiAgICBwbGF5ZWQgdGhyb3VnaCBhIGhpZGRlbiA8YXVkaW8+IGVsZW1lbnQuXG4gKiAgLSBBbGwgYmluYXJ5IHByb3RvYnVmIGZyYW1pbmcgLyBSVFZJIHByb3RvY29sIGhhbmRsZWQgYnlcbiAqICAgIEBwaXBlY2F0LWFpL2NsaWVudC1qcyArIEBwaXBlY2F0LWFpL3dlYnNvY2tldC10cmFuc3BvcnQuXG4gKi9cbkBJbmplY3RhYmxlKHtcbiAgcHJvdmlkZWRJbjogJ3Jvb3QnLFxufSlcbmV4cG9ydCBjbGFzcyBWb2ljZUFnZW50U2VydmljZSBpbXBsZW1lbnRzIE9uRGVzdHJveSB7XG4gIHByaXZhdGUgY2FsbFN0YXRlU3ViamVjdCA9IG5ldyBCZWhhdmlvclN1YmplY3Q8Q2FsbFN0YXRlPignaWRsZScpO1xuICBwcml2YXRlIHN0YXR1c1RleHRTdWJqZWN0ID0gbmV3IEJlaGF2aW9yU3ViamVjdDxzdHJpbmc+KCcnKTtcbiAgcHJpdmF0ZSBkdXJhdGlvblN1YmplY3QgPSBuZXcgQmVoYXZpb3JTdWJqZWN0PHN0cmluZz4oJzAwOjAwJyk7XG4gIHByaXZhdGUgaXNNaWNNdXRlZFN1YmplY3QgPSBuZXcgQmVoYXZpb3JTdWJqZWN0PGJvb2xlYW4+KGZhbHNlKTtcbiAgcHJpdmF0ZSBpc1VzZXJTcGVha2luZ1N1YmplY3QgPSBuZXcgQmVoYXZpb3JTdWJqZWN0PGJvb2xlYW4+KGZhbHNlKTtcbiAgcHJpdmF0ZSBhdWRpb0xldmVsc1N1YmplY3QgPSBuZXcgQmVoYXZpb3JTdWJqZWN0PG51bWJlcltdPihbXSk7XG4gIHByaXZhdGUgdXNlclRyYW5zY3JpcHRTdWJqZWN0ID0gbmV3IFN1YmplY3Q8VHJhbnNjcmlwdERhdGE+KCk7XG4gIHByaXZhdGUgYm90VHJhbnNjcmlwdFN1YmplY3QgPSBuZXcgU3ViamVjdDxzdHJpbmc+KCk7XG5cbiAgcHJpdmF0ZSBjYWxsU3RhcnRUaW1lID0gMDtcbiAgcHJpdmF0ZSBkdXJhdGlvbkludGVydmFsOiBSZXR1cm5UeXBlPHR5cGVvZiBzZXRJbnRlcnZhbD4gfCBudWxsID0gbnVsbDtcblxuICBwcml2YXRlIHBjQ2xpZW50OiBQaXBlY2F0Q2xpZW50IHwgbnVsbCA9IG51bGw7XG4gIHByaXZhdGUgYm90QXVkaW9FbGVtZW50OiBIVE1MQXVkaW9FbGVtZW50IHwgbnVsbCA9IG51bGw7XG5cbiAgcHJpdmF0ZSBzdWJzY3JpcHRpb25zID0gbmV3IFN1YnNjcmlwdGlvbigpO1xuICBwcml2YXRlIGRlc3Ryb3kkID0gbmV3IFN1YmplY3Q8dm9pZD4oKTtcblxuICBjYWxsU3RhdGUkOiBPYnNlcnZhYmxlPENhbGxTdGF0ZT4gPSB0aGlzLmNhbGxTdGF0ZVN1YmplY3QuYXNPYnNlcnZhYmxlKCk7XG4gIHN0YXR1c1RleHQkOiBPYnNlcnZhYmxlPHN0cmluZz4gPSB0aGlzLnN0YXR1c1RleHRTdWJqZWN0LmFzT2JzZXJ2YWJsZSgpO1xuICBkdXJhdGlvbiQ6IE9ic2VydmFibGU8c3RyaW5nPiA9IHRoaXMuZHVyYXRpb25TdWJqZWN0LmFzT2JzZXJ2YWJsZSgpO1xuICBpc01pY011dGVkJDogT2JzZXJ2YWJsZTxib29sZWFuPiA9IHRoaXMuaXNNaWNNdXRlZFN1YmplY3QuYXNPYnNlcnZhYmxlKCk7XG4gIGlzVXNlclNwZWFraW5nJDogT2JzZXJ2YWJsZTxib29sZWFuPiA9IHRoaXMuaXNVc2VyU3BlYWtpbmdTdWJqZWN0LmFzT2JzZXJ2YWJsZSgpO1xuICBhdWRpb0xldmVscyQ6IE9ic2VydmFibGU8bnVtYmVyW10+ID0gdGhpcy5hdWRpb0xldmVsc1N1YmplY3QuYXNPYnNlcnZhYmxlKCk7XG4gIHVzZXJUcmFuc2NyaXB0JDogT2JzZXJ2YWJsZTxUcmFuc2NyaXB0RGF0YT4gPSB0aGlzLnVzZXJUcmFuc2NyaXB0U3ViamVjdC5hc09ic2VydmFibGUoKTtcbiAgYm90VHJhbnNjcmlwdCQ6IE9ic2VydmFibGU8c3RyaW5nPiA9IHRoaXMuYm90VHJhbnNjcmlwdFN1YmplY3QuYXNPYnNlcnZhYmxlKCk7XG5cbiAgY29uc3RydWN0b3IoXG4gICAgcHJpdmF0ZSBhdWRpb0FuYWx5emVyOiBBdWRpb0FuYWx5emVyU2VydmljZSxcbiAgICBwcml2YXRlIHBsYXRmb3JtVG9rZW5SZWZyZXNoOiBQbGF0Zm9ybVRva2VuUmVmcmVzaFNlcnZpY2UsXG4gICAgcHJpdmF0ZSBuZ1pvbmU6IE5nWm9uZSxcbiAgICAvKiogYE9iamVjdGAgbm90IGBvYmplY3RgIOKAlCBuZ2MgbWV0YWRhdGEgY29sbGVjdGlvbiByZWplY3RzIHRoZSBgb2JqZWN0YCB0eXBlIGluIERJIHBhcmFtcy4gKi9cbiAgICBASW5qZWN0KFBMQVRGT1JNX0lEKSBwcml2YXRlIHBsYXRmb3JtSWQ6IE9iamVjdCxcbiAgKSB7XG4gICAgdGhpcy5zdWJzY3JpcHRpb25zLmFkZChcbiAgICAgIHRoaXMuYXVkaW9BbmFseXplci5hdWRpb0xldmVscyQuc3Vic2NyaWJlKChsZXZlbHMpID0+XG4gICAgICAgIHRoaXMuYXVkaW9MZXZlbHNTdWJqZWN0Lm5leHQobGV2ZWxzKSxcbiAgICAgICksXG4gICAgKTtcbiAgfVxuXG4gIG5nT25EZXN0cm95KCk6IHZvaWQge1xuICAgIHRoaXMuZGVzdHJveSQubmV4dCgpO1xuICAgIHRoaXMuc3Vic2NyaXB0aW9ucy51bnN1YnNjcmliZSgpO1xuICAgIHZvaWQgdGhpcy5kaXNjb25uZWN0KCk7XG4gIH1cblxuICAvKiogUmVzZXQgdG8gaWRsZSAoZS5nLiB3aGVuIG1vZGFsIHJlLW9wZW5zIHNvIHVzZXIgY2FuIGNsaWNrIFN0YXJ0IENhbGwpLiAqL1xuICByZXNldFRvSWRsZSgpOiB2b2lkIHtcbiAgICBpZiAodGhpcy5jYWxsU3RhdGVTdWJqZWN0LnZhbHVlID09PSAnaWRsZScpIHJldHVybjtcbiAgICB2b2lkIHRoaXMuZGlzY29ubmVjdCgpO1xuICAgIHRoaXMuY2FsbFN0YXRlU3ViamVjdC5uZXh0KCdpZGxlJyk7XG4gICAgdGhpcy5zdGF0dXNUZXh0U3ViamVjdC5uZXh0KCcnKTtcbiAgICB0aGlzLmR1cmF0aW9uU3ViamVjdC5uZXh0KCcwOjAwJyk7XG4gIH1cblxuICBhc3luYyBjb25uZWN0KFxuICAgIGFwaVVybDogc3RyaW5nLFxuICAgIHRva2VuOiBzdHJpbmcsXG4gICAgYm90SWQ6IHN0cmluZyxcbiAgICBjb252ZXJzYXRpb25JZDogc3RyaW5nLFxuICAgIGFwaUtleTogc3RyaW5nLFxuICAgIGV2ZW50VG9rZW46IHN0cmluZyxcbiAgICBldmVudElkOiBzdHJpbmcsXG4gICAgZXZlbnRVcmw6IHN0cmluZyxcbiAgICBkb21haW5BdXRob3JpdHk6IHN0cmluZyxcbiAgICB1c2Vyc0FwaVVybD86IHN0cmluZyxcbiAgKTogUHJvbWlzZTx2b2lkPiB7XG4gICAgaWYgKHRoaXMuY2FsbFN0YXRlU3ViamVjdC52YWx1ZSAhPT0gJ2lkbGUnKSB7XG4gICAgICBjb25zb2xlLndhcm4oJ1tIaXZlR3B0IFZvaWNlXSBDYWxsIGFscmVhZHkgaW4gcHJvZ3Jlc3MnKTtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICB0cnkge1xuICAgICAgdGhpcy5jYWxsU3RhdGVTdWJqZWN0Lm5leHQoJ2Nvbm5lY3RpbmcnKTtcbiAgICAgIHRoaXMuc3RhdHVzVGV4dFN1YmplY3QubmV4dCgnQ29ubmVjdGluZy4uLicpO1xuXG4gICAgICBsZXQgYWNjZXNzVG9rZW4gPSB0b2tlbjtcbiAgICAgIGlmICh1c2Vyc0FwaVVybCAmJiBpc1BsYXRmb3JtQnJvd3Nlcih0aGlzLnBsYXRmb3JtSWQpKSB7XG4gICAgICAgIHRyeSB7XG4gICAgICAgICAgY29uc3QgZW5zdXJlZCA9IGF3YWl0IHRoaXMucGxhdGZvcm1Ub2tlblJlZnJlc2hcbiAgICAgICAgICAgIC5lbnN1cmVWYWxpZEFjY2Vzc1Rva2VuKHRva2VuLCB1c2Vyc0FwaVVybClcbiAgICAgICAgICAgIC5waXBlKHRha2UoMSkpXG4gICAgICAgICAgICAudG9Qcm9taXNlKCk7XG4gICAgICAgICAgaWYgKGVuc3VyZWQ/LmFjY2Vzc1Rva2VuKSBhY2Nlc3NUb2tlbiA9IGVuc3VyZWQuYWNjZXNzVG9rZW47XG4gICAgICAgIH0gY2F0Y2ggKGUpIHtcbiAgICAgICAgICBjb25zb2xlLndhcm4oJ1tIaXZlR3B0IFZvaWNlXSBUb2tlbiByZWZyZXNoIGZhaWxlZCcsIGUpO1xuICAgICAgICB9XG4gICAgICB9XG5cbiAgICAgIGNvbnN0IGJhc2VVcmwgPSBhcGlVcmwucmVwbGFjZSgvXFwvJC8sICcnKTtcblxuICAgICAgY29uc3QgcGNDbGllbnQgPSBuZXcgUGlwZWNhdENsaWVudCh7XG4gICAgICAgIHRyYW5zcG9ydDogbmV3IFdlYlNvY2tldFRyYW5zcG9ydCgpLFxuICAgICAgICBlbmFibGVNaWM6IHRydWUsXG4gICAgICAgIGVuYWJsZUNhbTogZmFsc2UsXG4gICAgICAgIGNhbGxiYWNrczoge1xuICAgICAgICAgIG9uQ29ubmVjdGVkOiAoKSA9PiB0aGlzLm5nWm9uZS5ydW4oKCkgPT4gdGhpcy5vblBpcGVjYXRDb25uZWN0ZWQoKSksXG4gICAgICAgICAgb25EaXNjb25uZWN0ZWQ6ICgpID0+IHRoaXMubmdab25lLnJ1bigoKSA9PiB0aGlzLm9uUGlwZWNhdERpc2Nvbm5lY3RlZCgpKSxcbiAgICAgICAgICBvbkJvdFJlYWR5OiAoKSA9PiB0aGlzLm5nWm9uZS5ydW4oKCkgPT4gdGhpcy5vbkJvdFJlYWR5KCkpLFxuICAgICAgICAgIG9uVXNlclRyYW5zY3JpcHQ6IChkYXRhKSA9PlxuICAgICAgICAgICAgdGhpcy5uZ1pvbmUucnVuKCgpID0+XG4gICAgICAgICAgICAgIHRoaXMudXNlclRyYW5zY3JpcHRTdWJqZWN0Lm5leHQoeyB0ZXh0OiBkYXRhLnRleHQsIGZpbmFsOiAhIWRhdGEuZmluYWwgfSksXG4gICAgICAgICAgICApLFxuICAgICAgICAgIG9uQm90VHJhbnNjcmlwdDogKGRhdGEpID0+XG4gICAgICAgICAgICB0aGlzLm5nWm9uZS5ydW4oKCkgPT4gdGhpcy5ib3RUcmFuc2NyaXB0U3ViamVjdC5uZXh0KGRhdGEudGV4dCkpLFxuICAgICAgICAgIG9uRXJyb3I6IChlcnIpID0+IHtcbiAgICAgICAgICAgIHRoaXMubmdab25lLnJ1bigoKSA9PiB7XG4gICAgICAgICAgICAgIGNvbnNvbGUuZXJyb3IoJ1tIaXZlR3B0IFZvaWNlXSBQaXBlY2F0Q2xpZW50IGVycm9yJywgZXJyKTtcbiAgICAgICAgICAgICAgdGhpcy5jYWxsU3RhdGVTdWJqZWN0Lm5leHQoJ2VuZGVkJyk7XG4gICAgICAgICAgICAgIHRoaXMuc3RhdHVzVGV4dFN1YmplY3QubmV4dCgnQ29ubmVjdGlvbiBmYWlsZWQnKTtcbiAgICAgICAgICAgIH0pO1xuICAgICAgICAgIH0sXG4gICAgICAgIH0sXG4gICAgICB9KTtcblxuICAgICAgdGhpcy5wY0NsaWVudCA9IHBjQ2xpZW50O1xuXG4gICAgICAvLyBCb3QgYXVkaW8gYXJyaXZlcyBhcyBhIE1lZGlhU3RyZWFtVHJhY2sg4oCUIHdpcmUgdG8gYSBoaWRkZW4gPGF1ZGlvPiBlbGVtZW50XG4gICAgICBwY0NsaWVudC5vbihcbiAgICAgICAgUlRWSUV2ZW50LlRyYWNrU3RhcnRlZCxcbiAgICAgICAgKHRyYWNrOiBNZWRpYVN0cmVhbVRyYWNrLCBwYXJ0aWNpcGFudD86IHsgbG9jYWw/OiBib29sZWFuIH0pID0+IHtcbiAgICAgICAgICBpZiAoIXBhcnRpY2lwYW50Py5sb2NhbCAmJiB0cmFjay5raW5kID09PSAnYXVkaW8nKSB7XG4gICAgICAgICAgICB0aGlzLm5nWm9uZS5ydW4oKCkgPT4gdGhpcy5zZXR1cEJvdEF1ZGlvVHJhY2sodHJhY2spKTtcbiAgICAgICAgICB9XG4gICAgICAgIH0sXG4gICAgICApO1xuXG4gICAgICAvLyBTcGVha2luZyBzdGF0ZSBjb21lcyBzdHJhaWdodCBmcm9tIFJUVkkgZXZlbnRzXG4gICAgICBwY0NsaWVudC5vbihSVFZJRXZlbnQuQm90U3RhcnRlZFNwZWFraW5nLCAoKSA9PlxuICAgICAgICB0aGlzLm5nWm9uZS5ydW4oKCkgPT4gdGhpcy5vbkJvdFN0YXJ0ZWRTcGVha2luZygpKSxcbiAgICAgICk7XG4gICAgICBwY0NsaWVudC5vbihSVFZJRXZlbnQuQm90U3RvcHBlZFNwZWFraW5nLCAoKSA9PlxuICAgICAgICB0aGlzLm5nWm9uZS5ydW4oKCkgPT4gdGhpcy5vbkJvdFN0b3BwZWRTcGVha2luZygpKSxcbiAgICAgICk7XG4gICAgICBwY0NsaWVudC5vbihSVFZJRXZlbnQuVXNlclN0YXJ0ZWRTcGVha2luZywgKCkgPT5cbiAgICAgICAgdGhpcy5uZ1pvbmUucnVuKCgpID0+IHtcbiAgICAgICAgICB0aGlzLmlzVXNlclNwZWFraW5nU3ViamVjdC5uZXh0KHRydWUpO1xuICAgICAgICAgIHRoaXMuY2FsbFN0YXRlU3ViamVjdC5uZXh0KCdsaXN0ZW5pbmcnKTtcbiAgICAgICAgfSksXG4gICAgICApO1xuICAgICAgcGNDbGllbnQub24oUlRWSUV2ZW50LlVzZXJTdG9wcGVkU3BlYWtpbmcsICgpID0+XG4gICAgICAgIHRoaXMubmdab25lLnJ1bigoKSA9PiB7XG4gICAgICAgICAgdGhpcy5pc1VzZXJTcGVha2luZ1N1YmplY3QubmV4dChmYWxzZSk7XG4gICAgICAgICAgaWYgKHRoaXMuY2FsbFN0YXRlU3ViamVjdC52YWx1ZSA9PT0gJ2xpc3RlbmluZycpIHtcbiAgICAgICAgICAgIHRoaXMuY2FsbFN0YXRlU3ViamVjdC5uZXh0KCdjb25uZWN0ZWQnKTtcbiAgICAgICAgICB9XG4gICAgICAgIH0pLFxuICAgICAgKTtcblxuICAgICAgLy8gQWNxdWlyZSBtaWMgKHRyaWdnZXJzIGJyb3dzZXIgcGVybWlzc2lvbiBwcm9tcHQpXG4gICAgICBhd2FpdCBwY0NsaWVudC5pbml0RGV2aWNlcygpO1xuXG4gICAgICAvLyBCdWlsZCBoZWFkZXJzIHVzaW5nIHRoZSBicm93c2VyIEhlYWRlcnMgQVBJIChyZXF1aXJlZCBieSBwaXBlY2F0J3MgQVBJUmVxdWVzdCB0eXBlKVxuICAgICAgY29uc3QgcmVxdWVzdEhlYWRlcnMgPSBuZXcgSGVhZGVycygpO1xuICAgICAgcmVxdWVzdEhlYWRlcnMuYXBwZW5kKCdBdXRob3JpemF0aW9uJywgYEJlYXJlciAke2FjY2Vzc1Rva2VufWApO1xuICAgICAgcmVxdWVzdEhlYWRlcnMuYXBwZW5kKCd4LWFwaS1rZXknLCBhcGlLZXkpO1xuICAgICAgcmVxdWVzdEhlYWRlcnMuYXBwZW5kKCdoaXZlLWJvdC1pZCcsIGJvdElkKTtcbiAgICAgIHJlcXVlc3RIZWFkZXJzLmFwcGVuZCgnZG9tYWluLWF1dGhvcml0eScsIGRvbWFpbkF1dGhvcml0eSk7XG4gICAgICByZXF1ZXN0SGVhZGVycy5hcHBlbmQoJ2V2ZW50VXJsJywgZXZlbnRVcmwpO1xuICAgICAgcmVxdWVzdEhlYWRlcnMuYXBwZW5kKCdldmVudElkJywgZXZlbnRJZCk7XG4gICAgICByZXF1ZXN0SGVhZGVycy5hcHBlbmQoJ2V2ZW50VG9rZW4nLCBldmVudFRva2VuKTtcbiAgICAgIHJlcXVlc3RIZWFkZXJzLmFwcGVuZCgnbmdyb2stc2tpcC1icm93c2VyLXdhcm5pbmcnLCAndHJ1ZScpO1xuXG4gICAgICAvLyBQT1NUIHRvIC9haS9hc2stdm9pY2Utc29ja2V0IOKGkiByZWNlaXZlcyB7IHdzX3VybCB9IOKGkiBXZWJTb2NrZXRUcmFuc3BvcnQgY29ubmVjdHNcbiAgICAgIGF3YWl0IHBjQ2xpZW50LnN0YXJ0Qm90QW5kQ29ubmVjdCh7XG4gICAgICAgIGVuZHBvaW50OiBgJHtiYXNlVXJsfS9haS9hc2stdm9pY2Utc29ja2V0YCxcbiAgICAgICAgaGVhZGVyczogcmVxdWVzdEhlYWRlcnMsXG4gICAgICAgIHJlcXVlc3REYXRhOiB7XG4gICAgICAgICAgYm90X2lkOiBib3RJZCxcbiAgICAgICAgICBjb252ZXJzYXRpb25faWQ6IGNvbnZlcnNhdGlvbklkLFxuICAgICAgICAgIHZvaWNlOiAnYWxsb3knLFxuICAgICAgICB9LFxuICAgICAgfSk7XG4gICAgfSBjYXRjaCAoZXJyb3IpIHtcbiAgICAgIGNvbnNvbGUuZXJyb3IoJ1tIaXZlR3B0IFZvaWNlXSBjb25uZWN0IGZhaWxlZCcsIGVycm9yKTtcbiAgICAgIHRoaXMuY2FsbFN0YXRlU3ViamVjdC5uZXh0KCdlbmRlZCcpO1xuICAgICAgYXdhaXQgdGhpcy5jbGVhbnVwUGlwZWNhdENsaWVudCgpO1xuICAgICAgdGhpcy5zdGF0dXNUZXh0U3ViamVjdC5uZXh0KCdDb25uZWN0aW9uIGZhaWxlZCcpO1xuICAgICAgdGhyb3cgZXJyb3I7XG4gICAgfVxuICB9XG5cbiAgcHJpdmF0ZSBvblBpcGVjYXRDb25uZWN0ZWQoKTogdm9pZCB7XG4gICAgdGhpcy5jYWxsU3RhdGVTdWJqZWN0Lm5leHQoJ2Nvbm5lY3RlZCcpO1xuICAgIHRoaXMuc3RhdHVzVGV4dFN1YmplY3QubmV4dCgnQ29ubmVjdGVkJyk7XG4gICAgdGhpcy5pc01pY011dGVkU3ViamVjdC5uZXh0KGZhbHNlKTtcbiAgICB0aGlzLnN0YXJ0TG9jYWxNaWNBbmFseXplcigpO1xuICB9XG5cbiAgcHJpdmF0ZSBvblBpcGVjYXREaXNjb25uZWN0ZWQoKTogdm9pZCB7XG4gICAgdGhpcy5zdG9wRHVyYXRpb25UaW1lcigpO1xuICAgIHRoaXMuY2FsbFN0YXJ0VGltZSA9IDA7XG4gICAgdGhpcy5hdWRpb0FuYWx5emVyLnN0b3AoKTtcbiAgICB0aGlzLnN0b3BCb3RBdWRpbygpO1xuICAgIHRoaXMuY2FsbFN0YXRlU3ViamVjdC5uZXh0KCdlbmRlZCcpO1xuICAgIHRoaXMuc3RhdHVzVGV4dFN1YmplY3QubmV4dCgnQ2FsbCBFbmRlZCcpO1xuICB9XG5cbiAgcHJpdmF0ZSBvbkJvdFJlYWR5KCk6IHZvaWQge1xuICAgIC8vIFJldHJ5IHRyYWNrIHdpcmluZyBpbiBjYXNlIHRyYWNrcyB3ZXJlbid0IHJlYWR5IGF0IG9uQ29ubmVjdGVkXG4gICAgdGhpcy5zdGFydExvY2FsTWljQW5hbHl6ZXIoKTtcbiAgICBjb25zdCBib3RUcmFjayA9ICh0aGlzLnBjQ2xpZW50Py50cmFja3MoKSBhcyB7IGJvdD86IHsgYXVkaW8/OiBNZWRpYVN0cmVhbVRyYWNrIH0gfSlcbiAgICAgID8uYm90Py5hdWRpbztcbiAgICBpZiAoYm90VHJhY2spIHRoaXMuc2V0dXBCb3RBdWRpb1RyYWNrKGJvdFRyYWNrKTtcbiAgfVxuXG4gIHByaXZhdGUgc3RhcnRMb2NhbE1pY0FuYWx5emVyKCk6IHZvaWQge1xuICAgIGNvbnN0IGxvY2FsVHJhY2sgPSAodGhpcy5wY0NsaWVudD8udHJhY2tzKCkgYXMgeyBsb2NhbD86IHsgYXVkaW8/OiBNZWRpYVN0cmVhbVRyYWNrIH0gfSlcbiAgICAgID8ubG9jYWw/LmF1ZGlvO1xuICAgIGlmIChsb2NhbFRyYWNrKSB7XG4gICAgICB0aGlzLmF1ZGlvQW5hbHl6ZXIuc3RhcnQobmV3IE1lZGlhU3RyZWFtKFtsb2NhbFRyYWNrXSkpO1xuICAgIH1cbiAgfVxuXG4gIHByaXZhdGUgb25Cb3RTdGFydGVkU3BlYWtpbmcoKTogdm9pZCB7XG4gICAgaWYgKHRoaXMuY2FsbFN0YXJ0VGltZSA9PT0gMCkge1xuICAgICAgdGhpcy5jYWxsU3RhcnRUaW1lID0gRGF0ZS5ub3coKTtcbiAgICAgIHRoaXMuc3RhcnREdXJhdGlvblRpbWVyKCk7XG4gICAgfVxuICAgIHRoaXMuY2FsbFN0YXRlU3ViamVjdC5uZXh0KCd0YWxraW5nJyk7XG4gIH1cblxuICBwcml2YXRlIG9uQm90U3RvcHBlZFNwZWFraW5nKCk6IHZvaWQge1xuICAgIGlmICh0aGlzLmNhbGxTdGF0ZVN1YmplY3QudmFsdWUgPT09ICd0YWxraW5nJykge1xuICAgICAgdGhpcy5jYWxsU3RhdGVTdWJqZWN0Lm5leHQoJ2Nvbm5lY3RlZCcpO1xuICAgIH1cbiAgfVxuXG4gIHByaXZhdGUgc2V0dXBCb3RBdWRpb1RyYWNrKHRyYWNrOiBNZWRpYVN0cmVhbVRyYWNrKTogdm9pZCB7XG4gICAgaWYgKCF0aGlzLmJvdEF1ZGlvRWxlbWVudCkge1xuICAgICAgdGhpcy5ib3RBdWRpb0VsZW1lbnQgPSBuZXcgQXVkaW8oKTtcbiAgICAgIHRoaXMuYm90QXVkaW9FbGVtZW50LmF1dG9wbGF5ID0gdHJ1ZTtcbiAgICB9XG4gICAgY29uc3QgZXhpc3RpbmcgPSAodGhpcy5ib3RBdWRpb0VsZW1lbnQuc3JjT2JqZWN0IGFzIE1lZGlhU3RyZWFtIHwgbnVsbClcbiAgICAgID8uZ2V0QXVkaW9UcmFja3MoKVswXTtcbiAgICBpZiAoZXhpc3Rpbmc/LmlkID09PSB0cmFjay5pZCkgcmV0dXJuO1xuXG4gICAgdGhpcy5ib3RBdWRpb0VsZW1lbnQuc3JjT2JqZWN0ID0gbmV3IE1lZGlhU3RyZWFtKFt0cmFja10pO1xuICAgIHRoaXMuYm90QXVkaW9FbGVtZW50LnBsYXkoKS5jYXRjaCgoZXJyKSA9PlxuICAgICAgY29uc29sZS53YXJuKCdbSGl2ZUdwdCBWb2ljZV0gQm90IGF1ZGlvIHBsYXkgYmxvY2tlZCcsIGVyciksXG4gICAgKTtcbiAgfVxuXG4gIHByaXZhdGUgc3RvcEJvdEF1ZGlvKCk6IHZvaWQge1xuICAgIGlmICh0aGlzLmJvdEF1ZGlvRWxlbWVudCkge1xuICAgICAgdHJ5IHtcbiAgICAgICAgdGhpcy5ib3RBdWRpb0VsZW1lbnQucGF1c2UoKTtcbiAgICAgICAgKHRoaXMuYm90QXVkaW9FbGVtZW50LnNyY09iamVjdCBhcyBNZWRpYVN0cmVhbSB8IG51bGwpXG4gICAgICAgICAgPy5nZXRBdWRpb1RyYWNrcygpXG4gICAgICAgICAgLmZvckVhY2goKHQpID0+IHQuc3RvcCgpKTtcbiAgICAgICAgdGhpcy5ib3RBdWRpb0VsZW1lbnQuc3JjT2JqZWN0ID0gbnVsbDtcbiAgICAgIH0gY2F0Y2gge1xuICAgICAgICAvLyBpZ25vcmVcbiAgICAgIH1cbiAgICAgIHRoaXMuYm90QXVkaW9FbGVtZW50ID0gbnVsbDtcbiAgICB9XG4gIH1cblxuICBhc3luYyBkaXNjb25uZWN0KCk6IFByb21pc2U8dm9pZD4ge1xuICAgIHRoaXMuc3RvcER1cmF0aW9uVGltZXIoKTtcbiAgICB0aGlzLmNhbGxTdGFydFRpbWUgPSAwO1xuICAgIHRoaXMuYXVkaW9BbmFseXplci5zdG9wKCk7XG4gICAgdGhpcy5zdG9wQm90QXVkaW8oKTtcbiAgICBhd2FpdCB0aGlzLmNsZWFudXBQaXBlY2F0Q2xpZW50KCk7XG4gICAgdGhpcy5jYWxsU3RhdGVTdWJqZWN0Lm5leHQoJ2VuZGVkJyk7XG4gICAgdGhpcy5zdGF0dXNUZXh0U3ViamVjdC5uZXh0KCdDYWxsIEVuZGVkJyk7XG4gIH1cblxuICBwcml2YXRlIGFzeW5jIGNsZWFudXBQaXBlY2F0Q2xpZW50KCk6IFByb21pc2U8dm9pZD4ge1xuICAgIGlmICh0aGlzLnBjQ2xpZW50KSB7XG4gICAgICB0cnkge1xuICAgICAgICBhd2FpdCB0aGlzLnBjQ2xpZW50LmRpc2Nvbm5lY3QoKTtcbiAgICAgIH0gY2F0Y2gge1xuICAgICAgICAvLyBpZ25vcmVcbiAgICAgIH1cbiAgICAgIHRoaXMucGNDbGllbnQgPSBudWxsO1xuICAgIH1cbiAgfVxuXG4gIHRvZ2dsZU1pYygpOiB2b2lkIHtcbiAgICBpZiAoIXRoaXMucGNDbGllbnQpIHJldHVybjtcbiAgICBjb25zdCBuZXh0TXV0ZWQgPSAhdGhpcy5pc01pY011dGVkU3ViamVjdC52YWx1ZTtcbiAgICB0aGlzLnBjQ2xpZW50LmVuYWJsZU1pYyghbmV4dE11dGVkKTtcbiAgICB0aGlzLmlzTWljTXV0ZWRTdWJqZWN0Lm5leHQobmV4dE11dGVkKTtcbiAgICBpZiAobmV4dE11dGVkKSB0aGlzLmlzVXNlclNwZWFraW5nU3ViamVjdC5uZXh0KGZhbHNlKTtcbiAgfVxuXG4gIHByaXZhdGUgc3RhcnREdXJhdGlvblRpbWVyKCk6IHZvaWQge1xuICAgIGNvbnN0IHRpY2sgPSAoKSA9PiB7XG4gICAgICBpZiAodGhpcy5jYWxsU3RhcnRUaW1lID4gMCkge1xuICAgICAgICBjb25zdCBlbGFwc2VkID0gTWF0aC5mbG9vcigoRGF0ZS5ub3coKSAtIHRoaXMuY2FsbFN0YXJ0VGltZSkgLyAxMDAwKTtcbiAgICAgICAgY29uc3QgbSA9IE1hdGguZmxvb3IoZWxhcHNlZCAvIDYwKTtcbiAgICAgICAgY29uc3QgcyA9IGVsYXBzZWQgJSA2MDtcbiAgICAgICAgdGhpcy5kdXJhdGlvblN1YmplY3QubmV4dChgJHttfToke1N0cmluZyhzKS5wYWRTdGFydCgyLCAnMCcpfWApO1xuICAgICAgfVxuICAgIH07XG4gICAgdGljaygpO1xuICAgIHRoaXMuZHVyYXRpb25JbnRlcnZhbCA9IHNldEludGVydmFsKHRpY2ssIDEwMDApO1xuICB9XG5cbiAgcHJpdmF0ZSBzdG9wRHVyYXRpb25UaW1lcigpOiB2b2lkIHtcbiAgICBpZiAodGhpcy5kdXJhdGlvbkludGVydmFsKSB7XG4gICAgICBjbGVhckludGVydmFsKHRoaXMuZHVyYXRpb25JbnRlcnZhbCk7XG4gICAgICB0aGlzLmR1cmF0aW9uSW50ZXJ2YWwgPSBudWxsO1xuICAgIH1cbiAgfVxufVxuIl19
|