@nauth-toolkit/client-angular 0.1.90 → 0.1.92
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/esm2022/lib/recaptcha.service.mjs +359 -0
- package/esm2022/lib/social-redirect-callback.guard.mjs +28 -21
- package/esm2022/ngmodule/auth.service.mjs +94 -12
- package/esm2022/ngmodule/tokens.mjs +1 -1
- package/esm2022/public-api.mjs +2 -1
- package/fesm2022/nauth-toolkit-client-angular.mjs +477 -33
- package/fesm2022/nauth-toolkit-client-angular.mjs.map +1 -1
- package/lib/recaptcha.service.d.ts +195 -0
- package/lib/social-redirect-callback.guard.d.ts +1 -0
- package/ngmodule/auth.service.d.ts +45 -10
- package/ngmodule/tokens.d.ts +97 -0
- package/package.json +2 -2
- package/public-api.d.ts +1 -0
|
@@ -0,0 +1,359 @@
|
|
|
1
|
+
import { Injectable, Inject, PLATFORM_ID, Optional, InjectionToken } from '@angular/core';
|
|
2
|
+
import { isPlatformBrowser } from '@angular/common';
|
|
3
|
+
import * as i0 from "@angular/core";
|
|
4
|
+
/**
|
|
5
|
+
* Injection token for reCAPTCHA configuration
|
|
6
|
+
*/
|
|
7
|
+
export const RECAPTCHA_CONFIG = new InjectionToken('RECAPTCHA_CONFIG');
|
|
8
|
+
/**
|
|
9
|
+
* Google reCAPTCHA service for Angular applications.
|
|
10
|
+
*
|
|
11
|
+
* Provides lazy loading of reCAPTCHA script and platform-aware token generation.
|
|
12
|
+
* Automatically detects platform (web, Capacitor WebView, Capacitor native, SSR)
|
|
13
|
+
* and skips reCAPTCHA in environments where it's not supported or needed.
|
|
14
|
+
*
|
|
15
|
+
* Features:
|
|
16
|
+
* - Lazy script loading (only loads when needed)
|
|
17
|
+
* - v2 (checkbox) and v3 (invisible) support
|
|
18
|
+
* - Platform detection (web, Capacitor, SSR)
|
|
19
|
+
* - Automatic skip for Capacitor native mode
|
|
20
|
+
* - Automatic skip for SSR
|
|
21
|
+
*
|
|
22
|
+
* @example v3 Automatic Mode
|
|
23
|
+
* ```typescript
|
|
24
|
+
* constructor(private recaptcha: RecaptchaService) {}
|
|
25
|
+
*
|
|
26
|
+
* async login() {
|
|
27
|
+
* const token = await this.recaptcha.execute('login');
|
|
28
|
+
* await this.auth.login(email, password, token);
|
|
29
|
+
* }
|
|
30
|
+
* ```
|
|
31
|
+
*
|
|
32
|
+
* @example v2 Manual Mode
|
|
33
|
+
* ```typescript
|
|
34
|
+
* ngOnInit() {
|
|
35
|
+
* this.recaptcha.render('recaptcha-container', (token) => {
|
|
36
|
+
* this.recaptchaToken = token;
|
|
37
|
+
* });
|
|
38
|
+
* }
|
|
39
|
+
* ```
|
|
40
|
+
*/
|
|
41
|
+
export class RecaptchaService {
|
|
42
|
+
platformId;
|
|
43
|
+
config;
|
|
44
|
+
scriptLoaded = false;
|
|
45
|
+
scriptLoading = null;
|
|
46
|
+
platform;
|
|
47
|
+
widgetId = null;
|
|
48
|
+
constructor(platformId, config) {
|
|
49
|
+
this.platformId = platformId;
|
|
50
|
+
this.config = config;
|
|
51
|
+
this.platform = this.detectPlatform();
|
|
52
|
+
}
|
|
53
|
+
// ============================================================================
|
|
54
|
+
// Platform Detection
|
|
55
|
+
// ============================================================================
|
|
56
|
+
/**
|
|
57
|
+
* Detect the current platform environment.
|
|
58
|
+
*
|
|
59
|
+
* Detection priority:
|
|
60
|
+
* 1. SSR (not in browser) → 'ssr'
|
|
61
|
+
* 2. Capacitor native (no web view) → 'capacitor-native'
|
|
62
|
+
* 3. Capacitor WebView → 'capacitor-webview'
|
|
63
|
+
* 4. Web browser → 'web'
|
|
64
|
+
*
|
|
65
|
+
* @returns Detected platform type
|
|
66
|
+
*
|
|
67
|
+
* @example
|
|
68
|
+
* ```typescript
|
|
69
|
+
* const platform = this.detectPlatform();
|
|
70
|
+
* if (platform === 'capacitor-native') {
|
|
71
|
+
* // Skip reCAPTCHA, use device attestation
|
|
72
|
+
* }
|
|
73
|
+
* ```
|
|
74
|
+
*/
|
|
75
|
+
detectPlatform() {
|
|
76
|
+
// SSR detection
|
|
77
|
+
if (!isPlatformBrowser(this.platformId)) {
|
|
78
|
+
return 'ssr';
|
|
79
|
+
}
|
|
80
|
+
// Capacitor detection (window.Capacitor exists)
|
|
81
|
+
const windowRef = window;
|
|
82
|
+
if (windowRef.Capacitor) {
|
|
83
|
+
// Capacitor native (iOS/Android app)
|
|
84
|
+
if (typeof windowRef.Capacitor.isNativePlatform === 'function' && windowRef.Capacitor.isNativePlatform()) {
|
|
85
|
+
return 'capacitor-native';
|
|
86
|
+
}
|
|
87
|
+
// Capacitor WebView
|
|
88
|
+
return 'capacitor-webview';
|
|
89
|
+
}
|
|
90
|
+
return 'web';
|
|
91
|
+
}
|
|
92
|
+
/**
|
|
93
|
+
* Get the current platform.
|
|
94
|
+
*
|
|
95
|
+
* @returns Current platform type
|
|
96
|
+
*/
|
|
97
|
+
getPlatform() {
|
|
98
|
+
return this.platform;
|
|
99
|
+
}
|
|
100
|
+
/**
|
|
101
|
+
* Check if reCAPTCHA should be skipped for current platform.
|
|
102
|
+
*
|
|
103
|
+
* Skips for:
|
|
104
|
+
* - SSR (no window object)
|
|
105
|
+
* - Capacitor native (use device attestation instead)
|
|
106
|
+
*
|
|
107
|
+
* @returns True if should skip reCAPTCHA
|
|
108
|
+
*/
|
|
109
|
+
shouldSkip() {
|
|
110
|
+
return this.platform === 'ssr' || this.platform === 'capacitor-native';
|
|
111
|
+
}
|
|
112
|
+
// ============================================================================
|
|
113
|
+
// Script Loading
|
|
114
|
+
// ============================================================================
|
|
115
|
+
/**
|
|
116
|
+
* Load Google reCAPTCHA script if not already loaded.
|
|
117
|
+
*
|
|
118
|
+
* Script URL format:
|
|
119
|
+
* - v2: https://www.google.com/recaptcha/api.js
|
|
120
|
+
* - v3: https://www.google.com/recaptcha/api.js?render={siteKey}
|
|
121
|
+
* - Enterprise: https://www.google.com/recaptcha/enterprise.js?render={siteKey}
|
|
122
|
+
*
|
|
123
|
+
* @returns Promise that resolves when script is loaded
|
|
124
|
+
*
|
|
125
|
+
* @throws Error if config is missing or script fails to load
|
|
126
|
+
*/
|
|
127
|
+
async loadScript() {
|
|
128
|
+
// Skip in SSR or Capacitor native
|
|
129
|
+
if (this.shouldSkip()) {
|
|
130
|
+
return;
|
|
131
|
+
}
|
|
132
|
+
// Skip if disabled
|
|
133
|
+
if (!this.config?.enabled) {
|
|
134
|
+
return;
|
|
135
|
+
}
|
|
136
|
+
// Already loaded
|
|
137
|
+
if (this.scriptLoaded) {
|
|
138
|
+
return;
|
|
139
|
+
}
|
|
140
|
+
// Already loading (return existing promise)
|
|
141
|
+
if (this.scriptLoading) {
|
|
142
|
+
return this.scriptLoading;
|
|
143
|
+
}
|
|
144
|
+
// Validate config
|
|
145
|
+
if (!this.config.siteKey) {
|
|
146
|
+
throw new Error('[RecaptchaService] Site key is required');
|
|
147
|
+
}
|
|
148
|
+
// Start loading
|
|
149
|
+
this.scriptLoading = this.injectScript();
|
|
150
|
+
try {
|
|
151
|
+
await this.scriptLoading;
|
|
152
|
+
this.scriptLoaded = true;
|
|
153
|
+
}
|
|
154
|
+
finally {
|
|
155
|
+
this.scriptLoading = null;
|
|
156
|
+
}
|
|
157
|
+
}
|
|
158
|
+
/**
|
|
159
|
+
* Inject the reCAPTCHA script into the DOM.
|
|
160
|
+
*
|
|
161
|
+
* @returns Promise that resolves when script loads
|
|
162
|
+
*/
|
|
163
|
+
injectScript() {
|
|
164
|
+
return new Promise((resolve, reject) => {
|
|
165
|
+
const script = document.createElement('script');
|
|
166
|
+
script.async = true;
|
|
167
|
+
script.defer = true;
|
|
168
|
+
// Set script URL based on version
|
|
169
|
+
if (this.config.version === 'enterprise') {
|
|
170
|
+
script.src = `https://www.google.com/recaptcha/enterprise.js?render=${this.config.siteKey}`;
|
|
171
|
+
}
|
|
172
|
+
else if (this.config.version === 'v3') {
|
|
173
|
+
script.src = `https://www.google.com/recaptcha/api.js?render=${this.config.siteKey}`;
|
|
174
|
+
}
|
|
175
|
+
else {
|
|
176
|
+
// v2 - load without render parameter
|
|
177
|
+
let url = 'https://www.google.com/recaptcha/api.js';
|
|
178
|
+
if (this.config.language) {
|
|
179
|
+
url += `?hl=${this.config.language}`;
|
|
180
|
+
}
|
|
181
|
+
script.src = url;
|
|
182
|
+
}
|
|
183
|
+
script.onload = () => resolve();
|
|
184
|
+
script.onerror = () => reject(new Error('[RecaptchaService] Failed to load reCAPTCHA script'));
|
|
185
|
+
document.head.appendChild(script);
|
|
186
|
+
});
|
|
187
|
+
}
|
|
188
|
+
// ============================================================================
|
|
189
|
+
// v3/Enterprise Methods (Invisible Challenge)
|
|
190
|
+
// ============================================================================
|
|
191
|
+
/**
|
|
192
|
+
* Execute reCAPTCHA v3/Enterprise challenge (invisible).
|
|
193
|
+
*
|
|
194
|
+
* Automatically loads script if needed and generates a token.
|
|
195
|
+
* Skips automatically for SSR and Capacitor native.
|
|
196
|
+
*
|
|
197
|
+
* @param action - Action name for v3 analytics (e.g., 'login', 'signup')
|
|
198
|
+
* @returns Promise resolving to reCAPTCHA token, or undefined if skipped
|
|
199
|
+
*
|
|
200
|
+
* @throws Error if version is v2, config missing, or execution fails
|
|
201
|
+
*
|
|
202
|
+
* @example
|
|
203
|
+
* ```typescript
|
|
204
|
+
* const token = await this.recaptcha.execute('login');
|
|
205
|
+
* if (token) {
|
|
206
|
+
* await this.auth.login(email, password, token);
|
|
207
|
+
* }
|
|
208
|
+
* ```
|
|
209
|
+
*/
|
|
210
|
+
async execute(action) {
|
|
211
|
+
// Skip for platforms that don't support reCAPTCHA
|
|
212
|
+
if (this.shouldSkip()) {
|
|
213
|
+
return undefined;
|
|
214
|
+
}
|
|
215
|
+
// Skip if disabled
|
|
216
|
+
if (!this.config?.enabled) {
|
|
217
|
+
return undefined;
|
|
218
|
+
}
|
|
219
|
+
// v2 requires manual render
|
|
220
|
+
if (this.config.version === 'v2') {
|
|
221
|
+
throw new Error('[RecaptchaService] execute() is only for v3/Enterprise. Use render() for v2.');
|
|
222
|
+
}
|
|
223
|
+
// Load script if needed
|
|
224
|
+
await this.loadScript();
|
|
225
|
+
// Get grecaptcha object
|
|
226
|
+
const grecaptcha = window.grecaptcha;
|
|
227
|
+
if (!grecaptcha) {
|
|
228
|
+
throw new Error('[RecaptchaService] grecaptcha is not loaded');
|
|
229
|
+
}
|
|
230
|
+
// Execute reCAPTCHA
|
|
231
|
+
const actionName = action || this.config.action || 'submit';
|
|
232
|
+
try {
|
|
233
|
+
if (this.config.version === 'enterprise' && grecaptcha.enterprise?.execute) {
|
|
234
|
+
return await grecaptcha.enterprise.execute(this.config.siteKey, { action: actionName });
|
|
235
|
+
}
|
|
236
|
+
else if (grecaptcha.execute) {
|
|
237
|
+
return await grecaptcha.execute(this.config.siteKey, { action: actionName });
|
|
238
|
+
}
|
|
239
|
+
else {
|
|
240
|
+
throw new Error('[RecaptchaService] grecaptcha.execute is not available');
|
|
241
|
+
}
|
|
242
|
+
}
|
|
243
|
+
catch (error) {
|
|
244
|
+
throw new Error(`[RecaptchaService] Failed to execute reCAPTCHA: ${error instanceof Error ? error.message : 'unknown error'}`);
|
|
245
|
+
}
|
|
246
|
+
}
|
|
247
|
+
// ============================================================================
|
|
248
|
+
// v2 Methods (Visible Checkbox)
|
|
249
|
+
// ============================================================================
|
|
250
|
+
/**
|
|
251
|
+
* Render reCAPTCHA v2 checkbox widget.
|
|
252
|
+
*
|
|
253
|
+
* @param containerId - DOM element ID or element to render in
|
|
254
|
+
* @param callback - Callback when user completes challenge
|
|
255
|
+
* @returns Promise resolving to widget ID
|
|
256
|
+
*
|
|
257
|
+
* @throws Error if version is not v2, config missing, or render fails
|
|
258
|
+
*
|
|
259
|
+
* @example
|
|
260
|
+
* ```typescript
|
|
261
|
+
* ngAfterViewInit() {
|
|
262
|
+
* this.recaptcha.render('recaptcha-container', (token) => {
|
|
263
|
+
* this.recaptchaToken = token;
|
|
264
|
+
* this.loginForm.patchValue({ recaptchaToken: token });
|
|
265
|
+
* });
|
|
266
|
+
* }
|
|
267
|
+
* ```
|
|
268
|
+
*/
|
|
269
|
+
async render(containerId, callback) {
|
|
270
|
+
// Skip for platforms that don't support reCAPTCHA
|
|
271
|
+
if (this.shouldSkip()) {
|
|
272
|
+
throw new Error('[RecaptchaService] reCAPTCHA v2 is not supported in SSR or Capacitor native');
|
|
273
|
+
}
|
|
274
|
+
// Skip if disabled
|
|
275
|
+
if (!this.config?.enabled) {
|
|
276
|
+
throw new Error('[RecaptchaService] reCAPTCHA is not enabled');
|
|
277
|
+
}
|
|
278
|
+
// Only for v2
|
|
279
|
+
if (this.config.version !== 'v2') {
|
|
280
|
+
throw new Error('[RecaptchaService] render() is only for v2. Use execute() for v3/Enterprise.');
|
|
281
|
+
}
|
|
282
|
+
// Load script if needed
|
|
283
|
+
await this.loadScript();
|
|
284
|
+
// Get grecaptcha object
|
|
285
|
+
const grecaptcha = window.grecaptcha;
|
|
286
|
+
if (!grecaptcha?.render) {
|
|
287
|
+
throw new Error('[RecaptchaService] grecaptcha.render is not available');
|
|
288
|
+
}
|
|
289
|
+
// Render widget
|
|
290
|
+
try {
|
|
291
|
+
this.widgetId = grecaptcha.render(containerId, {
|
|
292
|
+
sitekey: this.config.siteKey,
|
|
293
|
+
callback: callback,
|
|
294
|
+
});
|
|
295
|
+
return this.widgetId;
|
|
296
|
+
}
|
|
297
|
+
catch (error) {
|
|
298
|
+
throw new Error(`[RecaptchaService] Failed to render reCAPTCHA: ${error instanceof Error ? error.message : 'unknown error'}`);
|
|
299
|
+
}
|
|
300
|
+
}
|
|
301
|
+
/**
|
|
302
|
+
* Get response token from v2 widget.
|
|
303
|
+
*
|
|
304
|
+
* @param widgetId - Widget ID (optional, uses last rendered widget if not provided)
|
|
305
|
+
* @returns reCAPTCHA token or null if not completed
|
|
306
|
+
*
|
|
307
|
+
* @example
|
|
308
|
+
* ```typescript
|
|
309
|
+
* const token = this.recaptcha.getResponse();
|
|
310
|
+
* if (token) {
|
|
311
|
+
* await this.auth.login(email, password, token);
|
|
312
|
+
* }
|
|
313
|
+
* ```
|
|
314
|
+
*/
|
|
315
|
+
getResponse(widgetId) {
|
|
316
|
+
const grecaptcha = window.grecaptcha;
|
|
317
|
+
if (!grecaptcha?.getResponse) {
|
|
318
|
+
return null;
|
|
319
|
+
}
|
|
320
|
+
const id = widgetId !== undefined ? widgetId : this.widgetId ?? undefined;
|
|
321
|
+
return grecaptcha.getResponse(id) || null;
|
|
322
|
+
}
|
|
323
|
+
/**
|
|
324
|
+
* Reset v2 widget (clear response).
|
|
325
|
+
*
|
|
326
|
+
* @param widgetId - Widget ID (optional, uses last rendered widget if not provided)
|
|
327
|
+
*
|
|
328
|
+
* @example
|
|
329
|
+
* ```typescript
|
|
330
|
+
* // After failed login
|
|
331
|
+
* this.recaptcha.reset();
|
|
332
|
+
* ```
|
|
333
|
+
*/
|
|
334
|
+
reset(widgetId) {
|
|
335
|
+
const grecaptcha = window.grecaptcha;
|
|
336
|
+
if (!grecaptcha?.reset) {
|
|
337
|
+
return;
|
|
338
|
+
}
|
|
339
|
+
const id = widgetId !== undefined ? widgetId : this.widgetId ?? undefined;
|
|
340
|
+
grecaptcha.reset(id);
|
|
341
|
+
}
|
|
342
|
+
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "17.3.12", ngImport: i0, type: RecaptchaService, deps: [{ token: PLATFORM_ID }, { token: RECAPTCHA_CONFIG, optional: true }], target: i0.ɵɵFactoryTarget.Injectable });
|
|
343
|
+
static ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "17.3.12", ngImport: i0, type: RecaptchaService, providedIn: 'root' });
|
|
344
|
+
}
|
|
345
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "17.3.12", ngImport: i0, type: RecaptchaService, decorators: [{
|
|
346
|
+
type: Injectable,
|
|
347
|
+
args: [{
|
|
348
|
+
providedIn: 'root',
|
|
349
|
+
}]
|
|
350
|
+
}], ctorParameters: () => [{ type: undefined, decorators: [{
|
|
351
|
+
type: Inject,
|
|
352
|
+
args: [PLATFORM_ID]
|
|
353
|
+
}] }, { type: undefined, decorators: [{
|
|
354
|
+
type: Optional
|
|
355
|
+
}, {
|
|
356
|
+
type: Inject,
|
|
357
|
+
args: [RECAPTCHA_CONFIG]
|
|
358
|
+
}] }] });
|
|
359
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoicmVjYXB0Y2hhLnNlcnZpY2UuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi9zcmMvbGliL3JlY2FwdGNoYS5zZXJ2aWNlLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBLE9BQU8sRUFBRSxVQUFVLEVBQUUsTUFBTSxFQUFFLFdBQVcsRUFBRSxRQUFRLEVBQUUsY0FBYyxFQUFFLE1BQU0sZUFBZSxDQUFDO0FBQzFGLE9BQU8sRUFBRSxpQkFBaUIsRUFBRSxNQUFNLGlCQUFpQixDQUFDOztBQTJCcEQ7O0dBRUc7QUFDSCxNQUFNLENBQUMsTUFBTSxnQkFBZ0IsR0FBRyxJQUFJLGNBQWMsQ0FBeUIsa0JBQWtCLENBQUMsQ0FBQztBQUUvRjs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7R0FnQ0c7QUFJSCxNQUFNLE9BQU8sZ0JBQWdCO0lBT0k7SUFDaUI7SUFQeEMsWUFBWSxHQUFHLEtBQUssQ0FBQztJQUNyQixhQUFhLEdBQXlCLElBQUksQ0FBQztJQUMzQyxRQUFRLENBQVc7SUFDbkIsUUFBUSxHQUFrQixJQUFJLENBQUM7SUFFdkMsWUFDK0IsVUFBa0IsRUFDRCxNQUErQjtRQURoRCxlQUFVLEdBQVYsVUFBVSxDQUFRO1FBQ0QsV0FBTSxHQUFOLE1BQU0sQ0FBeUI7UUFFN0UsSUFBSSxDQUFDLFFBQVEsR0FBRyxJQUFJLENBQUMsY0FBYyxFQUFFLENBQUM7SUFDeEMsQ0FBQztJQUVELCtFQUErRTtJQUMvRSxxQkFBcUI7SUFDckIsK0VBQStFO0lBRS9FOzs7Ozs7Ozs7Ozs7Ozs7Ozs7T0FrQkc7SUFDSyxjQUFjO1FBQ3BCLGdCQUFnQjtRQUNoQixJQUFJLENBQUMsaUJBQWlCLENBQUMsSUFBSSxDQUFDLFVBQVUsQ0FBQyxFQUFFLENBQUM7WUFDeEMsT0FBTyxLQUFLLENBQUM7UUFDZixDQUFDO1FBRUQsZ0RBQWdEO1FBQ2hELE1BQU0sU0FBUyxHQUFHLE1BQThELENBQUM7UUFFakYsSUFBSSxTQUFTLENBQUMsU0FB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QztZQUM3QixPQUFPLElBQUksQ0FBQztRQUNkLENBQUM7UUFFRCxNQUFNLEVBQUUsR0FBRyxRQUFRLEtBQUssU0FBUyxDQUFDLENBQUMsQ0FBQyxRQUFRLENBQUMsQ0FBQyxDQUFDLElBQUksQ0FBQyxRQUFRLElBQUksU0FBUyxDQUFDO1FBQzFFLE9BQU8sVUFBVSxDQUFDLFdBQVcsQ0FBQyxFQUFFLENBQUMsSUFBSSxJQUFJLENBQUM7SUFDNUMsQ0FBQztJQUVEOzs7Ozs7Ozs7O09BVUc7SUFDSCxLQUFLLENBQUMsUUFBaUI7UUFDckIsTUFBTSxVQUFVLEdBQUksTUFBbUUsQ0FBQyxVQUFVLENBQUM7UUFFbkcsSUFBSSxDQUFDLFVBQVUsRUFBRSxLQUFLLEVBQUUsQ0FBQztZQUN2QixPQUFPO1FBQ1QsQ0FBQztRQUVELE1BQU0sRUFBRSxHQUFHLFFBQVEsS0FBSyxTQUFTLENBQUMsQ0FBQyxDQUFDLFFBQVEsQ0FBQyxDQUFDLENBQUMsSUFBSSxDQUFDLFFBQVEsSUFBSSxTQUFTLENBQUM7UUFDMUUsVUFBVSxDQUFDLEtBQUssQ0FBQyxFQUFFLENBQUMsQ0FBQztJQUN2QixDQUFDO3dHQS9VVSxnQkFBZ0Isa0JBT2pCLFdBQVcsYUFDQyxnQkFBZ0I7NEdBUjNCLGdCQUFnQixjQUZmLE1BQU07OzRGQUVQLGdCQUFnQjtrQkFINUIsVUFBVTttQkFBQztvQkFDVixVQUFVLEVBQUUsTUFBTTtpQkFDbkI7OzBCQVFJLE1BQU07MkJBQUMsV0FBVzs7MEJBQ2xCLFFBQVE7OzBCQUFJLE1BQU07MkJBQUMsZ0JBQWdCIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgSW5qZWN0YWJsZSwgSW5qZWN0LCBQTEFURk9STV9JRCwgT3B0aW9uYWwsIEluamVjdGlvblRva2VuIH0gZnJvbSAnQGFuZ3VsYXIvY29yZSc7XG5pbXBvcnQgeyBpc1BsYXRmb3JtQnJvd3NlciB9IGZyb20gJ0Bhbmd1bGFyL2NvbW1vbic7XG5cbi8qKlxuICogRGV0ZWN0cyB0aGUgY3VycmVudCBwbGF0Zm9ybSBlbnZpcm9ubWVudFxuICovXG50eXBlIFBsYXRmb3JtID0gJ3dlYicgfCAnY2FwYWNpdG9yLXdlYnZpZXcnIHwgJ2NhcGFjaXRvci1uYXRpdmUnIHwgJ3Nzcic7XG5cbi8qKlxuICogcmVDQVBUQ0hBIHZlcnNpb24gdHlwZVxuICovXG50eXBlIFJlY2FwdGNoYVZlcnNpb24gPSAndjInIHwgJ3YzJyB8ICdlbnRlcnByaXNlJztcblxuLyoqXG4gKiByZUNBUFRDSEEgY29uZmlndXJhdGlvbiBmb3IgUmVjYXB0Y2hhU2VydmljZVxuICogXG4gKiBJbnRlcm5hbCBjb25maWd1cmF0aW9uIGludGVyZmFjZSB1c2VkIGJ5IFJlY2FwdGNoYVNlcnZpY2UuXG4gKiBVc2UgUmVjYXB0Y2hhQW5ndWxhckNvbmZpZyBmcm9tIHRva2Vucy50cyBmb3IgYXBwIGNvbmZpZ3VyYXRpb24uXG4gKi9cbmV4cG9ydCBpbnRlcmZhY2UgUmVjYXB0Y2hhU2VydmljZUNvbmZpZyB7XG4gIGVuYWJsZWQ6IGJvb2xlYW47XG4gIHZlcnNpb246IFJlY2FwdGNoYVZlcnNpb247XG4gIHNpdGVLZXk6IHN0cmluZztcbiAgYWN0aW9uPzogc3RyaW5nO1xuICBhdXRvTG9hZFNjcmlwdD86IGJvb2xlYW47XG4gIGxhbmd1YWdlPzogc3RyaW5nO1xufVxuXG4vKipcbiAqIEluamVjdGlvbiB0b2tlbiBmb3IgcmVDQVBUQ0hBIGNvbmZpZ3VyYXRpb25cbiAqL1xuZXhwb3J0IGNvbnN0IFJFQ0FQVENIQV9DT05GSUcgPSBuZXcgSW5qZWN0aW9uVG9rZW48UmVjYXB0Y2hhU2VydmljZUNvbmZpZz4oJ1JFQ0FQVENIQV9DT05GSUcnKTtcblxuLyoqXG4gKiBHb29nbGUgcmVDQVBUQ0hBIHNlcnZpY2UgZm9yIEFuZ3VsYXIgYXBwbGljYXRpb25zLlxuICpcbiAqIFByb3ZpZGVzIGxhenkgbG9hZGluZyBvZiByZUNBUFRDSEEgc2NyaXB0IGFuZCBwbGF0Zm9ybS1hd2FyZSB0b2tlbiBnZW5lcmF0aW9uLlxuICogQXV0b21hdGljYWxseSBkZXRlY3RzIHBsYXRmb3JtICh3ZWIsIENhcGFjaXRvciBXZWJWaWV3LCBDYXBhY2l0b3IgbmF0aXZlLCBTU1IpXG4gKiBhbmQgc2tpcHMgcmVDQVBUQ0hBIGluIGVudmlyb25tZW50cyB3aGVyZSBpdCdzIG5vdCBzdXBwb3J0ZWQgb3IgbmVlZGVkLlxuICpcbiAqIEZlYXR1cmVzOlxuICogLSBMYXp5IHNjcmlwdCBsb2FkaW5nIChvbmx5IGxvYWRzIHdoZW4gbmVlZGVkKVxuICogLSB2MiAoY2hlY2tib3gpIGFuZCB2MyAoaW52aXNpYmxlKSBzdXBwb3J0XG4gKiAtIFBsYXRmb3JtIGRldGVjdGlvbiAod2ViLCBDYXBhY2l0b3IsIFNTUilcbiAqIC0gQXV0b21hdGljIHNraXAgZm9yIENhcGFjaXRvciBuYXRpdmUgbW9kZVxuICogLSBBdXRvbWF0aWMgc2tpcCBmb3IgU1NSXG4gKlxuICogQGV4YW1wbGUgdjMgQXV0b21hdGljIE1vZGVcbiAqIGBgYHR5cGVzY3JpcHRcbiAqIGNvbnN0cnVjdG9yKHByaXZhdGUgcmVjYXB0Y2hhOiBSZWNhcHRjaGFTZXJ2aWNlKSB7fVxuICpcbiAqIGFzeW5jIGxvZ2luKCkge1xuICogICBjb25zdCB0b2tlbiA9IGF3YWl0IHRoaXMucmVjYXB0Y2hhLmV4ZWN1dGUoJ2xvZ2luJyk7XG4gKiAgIGF3YWl0IHRoaXMuYXV0aC5sb2dpbihlbWFpbCwgcGFzc3dvcmQsIHRva2VuKTtcbiAqIH1cbiAqIGBgYFxuICpcbiAqIEBleGFtcGxlIHYyIE1hbnVhbCBNb2RlXG4gKiBgYGB0eXBlc2NyaXB0XG4gKiBuZ09uSW5pdCgpIHtcbiAqICAgdGhpcy5yZWNhcHRjaGEucmVuZGVyKCdyZWNhcHRjaGEtY29udGFpbmVyJywgKHRva2VuKSA9PiB7XG4gKiAgICAgdGhpcy5yZWNhcHRjaGFUb2tlbiA9IHRva2VuO1xuICogICB9KTtcbiAqIH1cbiAqIGBgYFxuICovXG5ASW5qZWN0YWJsZSh7XG4gIHByb3ZpZGVkSW46ICdyb290Jyxcbn0pXG5leHBvcnQgY2xhc3MgUmVjYXB0Y2hhU2VydmljZSB7XG4gIHByaXZhdGUgc2NyaXB0TG9hZGVkID0gZmFsc2U7XG4gIHByaXZhdGUgc2NyaXB0TG9hZGluZzogUHJvbWlzZTx2b2lkPiB8IG51bGwgPSBudWxsO1xuICBwcml2YXRlIHBsYXRmb3JtOiBQbGF0Zm9ybTtcbiAgcHJpdmF0ZSB3aWRnZXRJZDogbnVtYmVyIHwgbnVsbCA9IG51bGw7XG5cbiAgY29uc3RydWN0b3IoXG4gICAgQEluamVjdChQTEFURk9STV9JRCkgcHJpdmF0ZSBwbGF0Zm9ybUlkOiBzdHJpbmcsXG4gICAgQE9wdGlvbmFsKCkgQEluamVjdChSRUNBUFRDSEFfQ09ORklHKSBwcml2YXRlIGNvbmZpZz86IFJlY2FwdGNoYVNlcnZpY2VDb25maWcsXG4gICkge1xuICAgIHRoaXMucGxhdGZvcm0gPSB0aGlzLmRldGVjdFBsYXRmb3JtKCk7XG4gIH1cblxuICAvLyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09XG4gIC8vIFBsYXRmb3JtIERldGVjdGlvblxuICAvLyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09XG5cbiAgLyoqXG4gICAqIERldGVjdCB0aGUgY3VycmVudCBwbGF0Zm9ybSBlbnZpcm9ubWVudC5cbiAgICpcbiAgICogRGV0ZWN0aW9uIHByaW9yaXR5OlxuICAgKiAxLiBTU1IgKG5vdCBpbiBicm93c2VyKSDihpIgJ3NzcidcbiAgICogMi4gQ2FwYWNpdG9yIG5hdGl2ZSAobm8gd2ViIHZpZXcpIOKGkiAnY2FwYWNpdG9yLW5hdGl2ZSdcbiAgICogMy4gQ2FwYWNpdG9yIFdlYlZpZXcg4oaSICdjYXBhY2l0b3Itd2VidmlldydcbiAgICogNC4gV2ViIGJyb3dzZXIg4oaSICd3ZWInXG4gICAqXG4gICAqIEByZXR1cm5zIERldGVjdGVkIHBsYXRmb3JtIHR5cGVcbiAgICpcbiAgICogQGV4YW1wbGVcbiAgICogYGBgdHlwZXNjcmlwdFxuICAgKiBjb25zdCBwbGF0Zm9ybSA9IHRoaXMuZGV0ZWN0UGxhdGZvcm0oKTtcbiAgICogaWYgKHBsYXRmb3JtID09PSAnY2FwYWNpdG9yLW5hdGl2ZScpIHtcbiAgICogICAvLyBTa2lwIHJlQ0FQVENIQSwgdXNlIGRldmljZSBhdHRlc3RhdGlvblxuICAgKiB9XG4gICAqIGBgYFxuICAgKi9cbiAgcHJpdmF0ZSBkZXRlY3RQbGF0Zm9ybSgpOiBQbGF0Zm9ybSB7XG4gICAgLy8gU1NSIGRldGVjdGlvblxuICAgIGlmICghaXNQbGF0Zm9ybUJyb3dzZXIodGhpcy5wbGF0Zm9ybUlkKSkge1xuICAgICAgcmV0dXJuICdzc3InO1xuICAgIH1cblxuICAgIC8vIENhcGFjaXRvciBkZXRlY3Rpb24gKHdpbmRvdy5DYXBhY2l0b3IgZXhpc3RzKVxuICAgIGNvbnN0IHdpbmRvd1JlZiA9IHdpbmRvdyBhcyB7IENhcGFjaXRvcj86IHsgaXNOYXRpdmVQbGF0Zm9ybT86ICgpID0+IGJvb2xlYW4gfSB9O1xuXG4gICAgaWYgKHdpbmRvd1JlZi5DYXBhY2l0b3IpIHtcbiAgICAgIC8vIENhcGFjaXRvciBuYXRpdmUgKGlPUy9BbmRyb2lkIGFwcClcbiAgICAgIGlmICh0eXBlb2Ygd2luZG93UmVmLkNhcGFjaXRvci5pc05hdGl2ZVBsYXRmb3JtID09PSAnZnVuY3Rpb24nICYmIHdpbmRvd1JlZi5DYXBhY2l0b3IuaXNOYXRpdmVQbGF0Zm9ybSgpKSB7XG4gICAgICAgIHJldHVybiAnY2FwYWNpdG9yLW5hdGl2ZSc7XG4gICAgICB9XG4gICAgICAvLyBDYXBhY2l0b3IgV2ViVmlld1xuICAgICAgcmV0dXJuICdjYXBhY2l0b3Itd2Vidmlldyc7XG4gICAgfVxuXG4gICAgcmV0dXJuICd3ZWInO1xuICB9XG5cbiAgLyoqXG4gICAqIEdldCB0aGUgY3VycmVudCBwbGF0Zm9ybS5cbiAgICpcbiAgICogQHJldHVybnMgQ3VycmVudCBwbGF0Zm9ybSB0eXBlXG4gICAqL1xuICBnZXRQbGF0Zm9ybSgpOiBQbGF0Zm9ybSB7XG4gICAgcmV0dXJuIHRoaXMucGxhdGZvcm07XG4gIH1cblxuICAvKipcbiAgICogQ2hlY2sgaWYgcmVDQVBUQ0hBIHNob3VsZCBiZSBza2lwcGVkIGZvciBjdXJyZW50IHBsYXRmb3JtLlxuICAgKlxuICAgKiBTa2lwcyBmb3I6XG4gICAqIC0gU1NSIChubyB3aW5kb3cgb2JqZWN0KVxuICAgKiAtIENhcGFjaXRvciBuYXRpdmUgKHVzZSBkZXZpY2UgYXR0ZXN0YXRpb24gaW5zdGVhZClcbiAgICpcbiAgICogQHJldHVybnMgVHJ1ZSBpZiBzaG91bGQgc2tpcCByZUNBUFRDSEFcbiAgICovXG4gIHNob3VsZFNraXAoKTogYm9vbGVhbiB7XG4gICAgcmV0dXJuIHRoaXMucGxhdGZvcm0gPT09ICdzc3InIHx8IHRoaXMucGxhdGZvcm0gPT09ICdjYXBhY2l0b3ItbmF0aXZlJztcbiAgfVxuXG4gIC8vID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT1cbiAgLy8gU2NyaXB0IExvYWRpbmdcbiAgLy8gPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PVxuXG4gIC8qKlxuICAgKiBMb2FkIEdvb2dsZSByZUNBUFRDSEEgc2NyaXB0IGlmIG5vdCBhbHJlYWR5IGxvYWRlZC5cbiAgICpcbiAgICogU2NyaXB0IFVSTCBmb3JtYXQ6XG4gICAqIC0gdjI6IGh0dHBzOi8vd3d3Lmdvb2dsZS5jb20vcmVjYXB0Y2hhL2FwaS5qc1xuICAgKiAtIHYzOiBodHRwczovL3d3dy5nb29nbGUuY29tL3JlY2FwdGNoYS9hcGkuanM/cmVuZGVyPXtzaXRlS2V5fVxuICAgKiAtIEVudGVycHJpc2U6IGh0dHBzOi8vd3d3Lmdvb2dsZS5jb20vcmVjYXB0Y2hhL2VudGVycHJpc2UuanM/cmVuZGVyPXtzaXRlS2V5fVxuICAgKlxuICAgKiBAcmV0dXJucyBQcm9taXNlIHRoYXQgcmVzb2x2ZXMgd2hlbiBzY3JpcHQgaXMgbG9hZGVkXG4gICAqXG4gICAqIEB0aHJvd3MgRXJyb3IgaWYgY29uZmlnIGlzIG1pc3Npbmcgb3Igc2NyaXB0IGZhaWxzIHRvIGxvYWRcbiAgICovXG4gIGFzeW5jIGxvYWRTY3JpcHQoKTogUHJvbWlzZTx2b2lkPiB7XG4gICAgLy8gU2tpcCBpbiBTU1Igb3IgQ2FwYWNpdG9yIG5hdGl2ZVxuICAgIGlmICh0aGlzLnNob3VsZFNraXAoKSkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIC8vIFNraXAgaWYgZGlzYWJsZWRcbiAgICBpZiAoIXRoaXMuY29uZmlnPy5lbmFibGVkKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgLy8gQWxyZWFkeSBsb2FkZWRcbiAgICBpZiAodGhpcy5zY3JpcHRMb2FkZWQpIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICAvLyBBbHJlYWR5IGxvYWRpbmcgKHJldHVybiBleGlzdGluZyBwcm9taXNlKVxuICAgIGlmICh0aGlzLnNjcmlwdExvYWRpbmcpIHtcbiAgICAgIHJldHVybiB0aGlzLnNjcmlwdExvYWRpbmc7XG4gICAgfVxuXG4gICAgLy8gVmFsaWRhdGUgY29uZmlnXG4gICAgaWYgKCF0aGlzLmNvbmZpZy5zaXRlS2V5KSB7XG4gICAgICB0aHJvdyBuZXcgRXJyb3IoJ1tSZWNhcHRjaGFTZXJ2aWNlXSBTaXRlIGtleSBpcyByZXF1aXJlZCcpO1xuICAgIH1cblxuICAgIC8vIFN0YXJ0IGxvYWRpbmdcbiAgICB0aGlzLnNjcmlwdExvYWRpbmcgPSB0aGlzLmluamVjdFNjcmlwdCgpO1xuXG4gICAgdHJ5IHtcbiAgICAgIGF3YWl0IHRoaXMuc2NyaXB0TG9hZGluZztcbiAgICAgIHRoaXMuc2NyaXB0TG9hZGVkID0gdHJ1ZTtcbiAgICB9IGZpbmFsbHkge1xuICAgICAgdGhpcy5zY3JpcHRMb2FkaW5nID0gbnVsbDtcbiAgICB9XG4gIH1cblxuICAvKipcbiAgICogSW5qZWN0IHRoZSByZUNBUFRDSEEgc2NyaXB0IGludG8gdGhlIERPTS5cbiAgICpcbiAgICogQHJldHVybnMgUHJvbWlzZSB0aGF0IHJlc29sdmVzIHdoZW4gc2NyaXB0IGxvYWRzXG4gICAqL1xuICBwcml2YXRlIGluamVjdFNjcmlwdCgpOiBQcm9taXNlPHZvaWQ+IHtcbiAgICByZXR1cm4gbmV3IFByb21pc2UoKHJlc29sdmUsIHJlamVjdCkgPT4ge1xuICAgICAgY29uc3Qgc2NyaXB0ID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnc2NyaXB0Jyk7XG4gICAgICBzY3JpcHQuYXN5bmMgPSB0cnVlO1xuICAgICAgc2NyaXB0LmRlZmVyID0gdHJ1ZTtcblxuICAgICAgLy8gU2V0IHNjcmlwdCBVUkwgYmFzZWQgb24gdmVyc2lvblxuICAgICAgaWYgKHRoaXMuY29uZmlnIS52ZXJzaW9uID09PSAnZW50ZXJwcmlzZScpIHtcbiAgICAgICAgc2NyaXB0LnNyYyA9IGBodHRwczovL3d3dy5nb29nbGUuY29tL3JlY2FwdGNoYS9lbnRlcnByaXNlLmpzP3JlbmRlcj0ke3RoaXMuY29uZmlnIS5zaXRlS2V5fWA7XG4gICAgICB9IGVsc2UgaWYgKHRoaXMuY29uZmlnIS52ZXJzaW9uID09PSAndjMnKSB7XG4gICAgICAgIHNjcmlwdC5zcmMgPSBgaHR0cHM6Ly93d3cuZ29vZ2xlLmNvbS9yZWNhcHRjaGEvYXBpLmpzP3JlbmRlcj0ke3RoaXMuY29uZmlnIS5zaXRlS2V5fWA7XG4gICAgICB9IGVsc2Uge1xuICAgICAgICAvLyB2MiAtIGxvYWQgd2l0aG91dCByZW5kZXIgcGFyYW1ldGVyXG4gICAgICAgIGxldCB1cmwgPSAnaHR0cHM6Ly93d3cuZ29vZ2xlLmNvbS9yZWNhcHRjaGEvYXBpLmpzJztcbiAgICAgICAgaWYgKHRoaXMuY29uZmlnIS5sYW5ndWFnZSkge1xuICAgICAgICAgIHVybCArPSBgP2hsPSR7dGhpcy5jb25maWchLmxhbmd1YWdlfWA7XG4gICAgICAgIH1cbiAgICAgICAgc2NyaXB0LnNyYyA9IHVybDtcbiAgICAgIH1cblxuICAgICAgc2NyaXB0Lm9ubG9hZCA9ICgpID0+IHJlc29sdmUoKTtcbiAgICAgIHNjcmlwdC5vbmVycm9yID0gKCkgPT4gcmVqZWN0KG5ldyBFcnJvcignW1JlY2FwdGNoYVNlcnZpY2VdIEZhaWxlZCB0byBsb2FkIHJlQ0FQVENIQSBzY3JpcHQnKSk7XG5cbiAgICAgIGRvY3VtZW50LmhlYWQuYXBwZW5kQ2hpbGQoc2NyaXB0KTtcbiAgICB9KTtcbiAgfVxuXG4gIC8vID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT1cbiAgLy8gdjMvRW50ZXJwcmlzZSBNZXRob2RzIChJbnZpc2libGUgQ2hhbGxlbmdlKVxuICAvLyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09XG5cbiAgLyoqXG4gICAqIEV4ZWN1dGUgcmVDQVBUQ0hBIHYzL0VudGVycHJpc2UgY2hhbGxlbmdlIChpbnZpc2libGUpLlxuICAgKlxuICAgKiBBdXRvbWF0aWNhbGx5IGxvYWRzIHNjcmlwdCBpZiBuZWVkZWQgYW5kIGdlbmVyYXRlcyBhIHRva2VuLlxuICAgKiBTa2lwcyBhdXRvbWF0aWNhbGx5IGZvciBTU1IgYW5kIENhcGFjaXRvciBuYXRpdmUuXG4gICAqXG4gICAqIEBwYXJhbSBhY3Rpb24gLSBBY3Rpb24gbmFtZSBmb3IgdjMgYW5hbHl0aWNzIChlLmcuLCAnbG9naW4nLCAnc2lnbnVwJylcbiAgICogQHJldHVybnMgUHJvbWlzZSByZXNvbHZpbmcgdG8gcmVDQVBUQ0hBIHRva2VuLCBvciB1bmRlZmluZWQgaWYgc2tpcHBlZFxuICAgKlxuICAgKiBAdGhyb3dzIEVycm9yIGlmIHZlcnNpb24gaXMgdjIsIGNvbmZpZyBtaXNzaW5nLCBvciBleGVjdXRpb24gZmFpbHNcbiAgICpcbiAgICogQGV4YW1wbGVcbiAgICogYGBgdHlwZXNjcmlwdFxuICAgKiBjb25zdCB0b2tlbiA9IGF3YWl0IHRoaXMucmVjYXB0Y2hhLmV4ZWN1dGUoJ2xvZ2luJyk7XG4gICAqIGlmICh0b2tlbikge1xuICAgKiAgIGF3YWl0IHRoaXMuYXV0aC5sb2dpbihlbWFpbCwgcGFzc3dvcmQsIHRva2VuKTtcbiAgICogfVxuICAgKiBgYGBcbiAgICovXG4gIGFzeW5jIGV4ZWN1dGUoYWN0aW9uPzogc3RyaW5nKTogUHJvbWlzZTxzdHJpbmcgfCB1bmRlZmluZWQ+IHtcbiAgICAvLyBTa2lwIGZvciBwbGF0Zm9ybXMgdGhhdCBkb24ndCBzdXBwb3J0IHJlQ0FQVENIQVxuICAgIGlmICh0aGlzLnNob3VsZFNraXAoKSkge1xuICAgICAgcmV0dXJuIHVuZGVmaW5lZDtcbiAgICB9XG5cbiAgICAvLyBTa2lwIGlmIGRpc2FibGVkXG4gICAgaWYgKCF0aGlzLmNvbmZpZz8uZW5hYmxlZCkge1xuICAgICAgcmV0dXJuIHVuZGVmaW5lZDtcbiAgICB9XG5cbiAgICAvLyB2MiByZXF1aXJlcyBtYW51YWwgcmVuZGVyXG4gICAgaWYgKHRoaXMuY29uZmlnLnZlcnNpb24gPT09ICd2MicpIHtcbiAgICAgIHRocm93IG5ldyBFcnJvcignW1JlY2FwdGNoYVNlcnZpY2VdIGV4ZWN1dGUoKSBpcyBvbmx5IGZvciB2My9FbnRlcnByaXNlLiBVc2UgcmVuZGVyKCkgZm9yIHYyLicpO1xuICAgIH1cblxuICAgIC8vIExvYWQgc2NyaXB0IGlmIG5lZWRlZFxuICAgIGF3YWl0IHRoaXMubG9hZFNjcmlwdCgpO1xuXG4gICAgLy8gR2V0IGdyZWNhcHRjaGEgb2JqZWN0XG4gICAgY29uc3QgZ3JlY2FwdGNoYSA9ICh3aW5kb3cgYXMgeyBncmVjYXB0Y2hhPzogeyBleGVjdXRlPzogKHNpdGVLZXk6IHN0cmluZywgb3B0aW9uczogeyBhY3Rpb246IHN0cmluZyB9KSA9PiBQcm9taXNlPHN0cmluZz47IGVudGVycHJpc2U/OiB7IGV4ZWN1dGU/OiAoc2l0ZUtleTogc3RyaW5nLCBvcHRpb25zOiB7IGFjdGlvbjogc3RyaW5nIH0pID0+IFByb21pc2U8c3RyaW5nPiB9IH0gfSkuZ3JlY2FwdGNoYTtcblxuICAgIGlmICghZ3JlY2FwdGNoYSkge1xuICAgICAgdGhyb3cgbmV3IEVycm9yKCdbUmVjYXB0Y2hhU2VydmljZV0gZ3JlY2FwdGNoYSBpcyBub3QgbG9hZGVkJyk7XG4gICAgfVxuXG4gICAgLy8gRXhlY3V0ZSByZUNBUFRDSEFcbiAgICBjb25zdCBhY3Rpb25OYW1lID0gYWN0aW9uIHx8IHRoaXMuY29uZmlnLmFjdGlvbiB8fCAnc3VibWl0JztcblxuICAgIHRyeSB7XG4gICAgICBpZiAodGhpcy5jb25maWcudmVyc2lvbiA9PT0gJ2VudGVycHJpc2UnICYmIGdyZWNhcHRjaGEuZW50ZXJwcmlzZT8uZXhlY3V0ZSkge1xuICAgICAgICByZXR1cm4gYXdhaXQgZ3JlY2FwdGNoYS5lbnRlcnByaXNlLmV4ZWN1dGUodGhpcy5jb25maWcuc2l0ZUtleSwgeyBhY3Rpb246IGFjdGlvbk5hbWUgfSk7XG4gICAgICB9IGVsc2UgaWYgKGdyZWNhcHRjaGEuZXhlY3V0ZSkge1xuICAgICAgICByZXR1cm4gYXdhaXQgZ3JlY2FwdGNoYS5leGVjdXRlKHRoaXMuY29uZmlnLnNpdGVLZXksIHsgYWN0aW9uOiBhY3Rpb25OYW1lIH0pO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgdGhyb3cgbmV3IEVycm9yKCdbUmVjYXB0Y2hhU2VydmljZV0gZ3JlY2FwdGNoYS5leGVjdXRlIGlzIG5vdCBhdmFpbGFibGUnKTtcbiAgICAgIH1cbiAgICB9IGNhdGNoIChlcnJvcjogdW5rbm93bikge1xuICAgICAgdGhyb3cgbmV3IEVycm9yKGBbUmVjYXB0Y2hhU2VydmljZV0gRmFpbGVkIHRvIGV4ZWN1dGUgcmVDQVBUQ0hBOiAke2Vycm9yIGluc3RhbmNlb2YgRXJyb3IgPyBlcnJvci5tZXNzYWdlIDogJ3Vua25vd24gZXJyb3InfWApO1xuICAgIH1cbiAgfVxuXG4gIC8vID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT1cbiAgLy8gdjIgTWV0aG9kcyAoVmlzaWJsZSBDaGVja2JveClcbiAgLy8gPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PVxuXG4gIC8qKlxuICAgKiBSZW5kZXIgcmVDQVBUQ0hBIHYyIGNoZWNrYm94IHdpZGdldC5cbiAgICpcbiAgICogQHBhcmFtIGNvbnRhaW5lcklkIC0gRE9NIGVsZW1lbnQgSUQgb3IgZWxlbWVudCB0byByZW5kZXIgaW5cbiAgICogQHBhcmFtIGNhbGxiYWNrIC0gQ2FsbGJhY2sgd2hlbiB1c2VyIGNvbXBsZXRlcyBjaGFsbGVuZ2VcbiAgICogQHJldHVybnMgUHJvbWlzZSByZXNvbHZpbmcgdG8gd2lkZ2V0IElEXG4gICAqXG4gICAqIEB0aHJvd3MgRXJyb3IgaWYgdmVyc2lvbiBpcyBub3QgdjIsIGNvbmZpZyBtaXNzaW5nLCBvciByZW5kZXIgZmFpbHNcbiAgICpcbiAgICogQGV4YW1wbGVcbiAgICogYGBgdHlwZXNjcmlwdFxuICAgKiBuZ0FmdGVyVmlld0luaXQoKSB7XG4gICAqICAgdGhpcy5yZWNhcHRjaGEucmVuZGVyKCdyZWNhcHRjaGEtY29udGFpbmVyJywgKHRva2VuKSA9PiB7XG4gICAqICAgICB0aGlzLnJlY2FwdGNoYVRva2VuID0gdG9rZW47XG4gICAqICAgICB0aGlzLmxvZ2luRm9ybS5wYXRjaFZhbHVlKHsgcmVjYXB0Y2hhVG9rZW46IHRva2VuIH0pO1xuICAgKiAgIH0pO1xuICAgKiB9XG4gICAqIGBgYFxuICAgKi9cbiAgYXN5bmMgcmVuZGVyKGNvbnRhaW5lcklkOiBzdHJpbmcsIGNhbGxiYWNrOiAodG9rZW46IHN0cmluZykgPT4gdm9pZCk6IFByb21pc2U8bnVtYmVyPiB7XG4gICAgLy8gU2tpcCBmb3IgcGxhdGZvcm1zIHRoYXQgZG9uJ3Qgc3VwcG9ydCByZUNBUFRDSEFcbiAgICBpZiAodGhpcy5zaG91bGRTa2lwKCkpIHtcbiAgICAgIHRocm93IG5ldyBFcnJvcignW1JlY2FwdGNoYVNlcnZpY2VdIHJlQ0FQVENIQSB2MiBpcyBub3Qgc3VwcG9ydGVkIGluIFNTUiBvciBDYXBhY2l0b3IgbmF0aXZlJyk7XG4gICAgfVxuXG4gICAgLy8gU2tpcCBpZiBkaXNhYmxlZFxuICAgIGlmICghdGhpcy5jb25maWc/LmVuYWJsZWQpIHtcbiAgICAgIHRocm93IG5ldyBFcnJvcignW1JlY2FwdGNoYVNlcnZpY2VdIHJlQ0FQVENIQSBpcyBub3QgZW5hYmxlZCcpO1xuICAgIH1cblxuICAgIC8vIE9ubHkgZm9yIHYyXG4gICAgaWYgKHRoaXMuY29uZmlnLnZlcnNpb24gIT09ICd2MicpIHtcbiAgICAgIHRocm93IG5ldyBFcnJvcignW1JlY2FwdGNoYVNlcnZpY2VdIHJlbmRlcigpIGlzIG9ubHkgZm9yIHYyLiBVc2UgZXhlY3V0ZSgpIGZvciB2My9FbnRlcnByaXNlLicpO1xuICAgIH1cblxuICAgIC8vIExvYWQgc2NyaXB0IGlmIG5lZWRlZFxuICAgIGF3YWl0IHRoaXMubG9hZFNjcmlwdCgpO1xuXG4gICAgLy8gR2V0IGdyZWNhcHRjaGEgb2JqZWN0XG4gICAgY29uc3QgZ3JlY2FwdGNoYSA9ICh3aW5kb3cgYXMgeyBncmVjYXB0Y2hhPzogeyByZW5kZXI/OiAoY29udGFpbmVyOiBzdHJpbmcsIG9wdGlvbnM6IHsgc2l0ZWtleTogc3RyaW5nOyBjYWxsYmFjazogKHRva2VuOiBzdHJpbmcpID0+IHZvaWQgfSkgPT4gbnVtYmVyIH0gfSkuZ3JlY2FwdGNoYTtcblxuICAgIGlmICghZ3JlY2FwdGNoYT8ucmVuZGVyKSB7XG4gICAgICB0aHJvdyBuZXcgRXJyb3IoJ1tSZWNhcHRjaGFTZXJ2aWNlXSBncmVjYXB0Y2hhLnJlbmRlciBpcyBub3QgYXZhaWxhYmxlJyk7XG4gICAgfVxuXG4gICAgLy8gUmVuZGVyIHdpZGdldFxuICAgIHRyeSB7XG4gICAgICB0aGlzLndpZGdldElkID0gZ3JlY2FwdGNoYS5yZW5kZXIoY29udGFpbmVySWQsIHtcbiAgICAgICAgc2l0ZWtleTogdGhpcy5jb25maWcuc2l0ZUtleSxcbiAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrLFxuICAgICAgfSk7XG4gICAgICByZXR1cm4gdGhpcy53aWRnZXRJZDtcbiAgICB9IGNhdGNoIChlcnJvcjogdW5rbm93bikge1xuICAgICAgdGhyb3cgbmV3IEVycm9yKGBbUmVjYXB0Y2hhU2VydmljZV0gRmFpbGVkIHRvIHJlbmRlciByZUNBUFRDSEE6ICR7ZXJyb3IgaW5zdGFuY2VvZiBFcnJvciA/IGVycm9yLm1lc3NhZ2UgOiAndW5rbm93biBlcnJvcid9YCk7XG4gICAgfVxuICB9XG5cbiAgLyoqXG4gICAqIEdldCByZXNwb25zZSB0b2tlbiBmcm9tIHYyIHdpZGdldC5cbiAgICpcbiAgICogQHBhcmFtIHdpZGdldElkIC0gV2lkZ2V0IElEIChvcHRpb25hbCwgdXNlcyBsYXN0IHJlbmRlcmVkIHdpZGdldCBpZiBub3QgcHJvdmlkZWQpXG4gICAqIEByZXR1cm5zIHJlQ0FQVENIQSB0b2tlbiBvciBudWxsIGlmIG5vdCBjb21wbGV0ZWRcbiAgICpcbiAgICogQGV4YW1wbGVcbiAgICogYGBgdHlwZXNjcmlwdFxuICAgKiBjb25zdCB0b2tlbiA9IHRoaXMucmVjYXB0Y2hhLmdldFJlc3BvbnNlKCk7XG4gICAqIGlmICh0b2tlbikge1xuICAgKiAgIGF3YWl0IHRoaXMuYXV0aC5sb2dpbihlbWFpbCwgcGFzc3dvcmQsIHRva2VuKTtcbiAgICogfVxuICAgKiBgYGBcbiAgICovXG4gIGdldFJlc3BvbnNlKHdpZGdldElkPzogbnVtYmVyKTogc3RyaW5nIHwgbnVsbCB7XG4gICAgY29uc3QgZ3JlY2FwdGNoYSA9ICh3aW5kb3cgYXMgeyBncmVjYXB0Y2hhPzogeyBnZXRSZXNwb25zZT86ICh3aWRnZXRJZD86IG51bWJlcikgPT4gc3RyaW5nIH0gfSkuZ3JlY2FwdGNoYTtcblxuICAgIGlmICghZ3JlY2FwdGNoYT8uZ2V0UmVzcG9uc2UpIHtcbiAgICAgIHJldHVybiBudWxsO1xuICAgIH1cblxuICAgIGNvbnN0IGlkID0gd2lkZ2V0SWQgIT09IHVuZGVmaW5lZCA/IHdpZGdldElkIDogdGhpcy53aWRnZXRJZCA/PyB1bmRlZmluZWQ7XG4gICAgcmV0dXJuIGdyZWNhcHRjaGEuZ2V0UmVzcG9uc2UoaWQpIHx8IG51bGw7XG4gIH1cblxuICAvKipcbiAgICogUmVzZXQgdjIgd2lkZ2V0IChjbGVhciByZXNwb25zZSkuXG4gICAqXG4gICAqIEBwYXJhbSB3aWRnZXRJZCAtIFdpZGdldCBJRCAob3B0aW9uYWwsIHVzZXMgbGFzdCByZW5kZXJlZCB3aWRnZXQgaWYgbm90IHByb3ZpZGVkKVxuICAgKlxuICAgKiBAZXhhbXBsZVxuICAgKiBgYGB0eXBlc2NyaXB0XG4gICAqIC8vIEFmdGVyIGZhaWxlZCBsb2dpblxuICAgKiB0aGlzLnJlY2FwdGNoYS5yZXNldCgpO1xuICAgKiBgYGBcbiAgICovXG4gIHJlc2V0KHdpZGdldElkPzogbnVtYmVyKTogdm9pZCB7XG4gICAgY29uc3QgZ3JlY2FwdGNoYSA9ICh3aW5kb3cgYXMgeyBncmVjYXB0Y2hhPzogeyByZXNldD86ICh3aWRnZXRJZD86IG51bWJlcikgPT4gdm9pZCB9IH0pLmdyZWNhcHRjaGE7XG5cbiAgICBpZiAoIWdyZWNhcHRjaGE/LnJlc2V0KSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgY29uc3QgaWQgPSB3aWRnZXRJZCAhPT0gdW5kZWZpbmVkID8gd2lkZ2V0SWQgOiB0aGlzLndpZGdldElkID8/IHVuZGVmaW5lZDtcbiAgICBncmVjYXB0Y2hhLnJlc2V0KGlkKTtcbiAgfVxufVxuIl19
|
|
@@ -15,6 +15,7 @@ import { NAuthClientError, NAuthErrorCode } from '@nauth-toolkit/client';
|
|
|
15
15
|
* - If `exchangeToken` exists: exchanges it via backend (SDK handles navigation automatically).
|
|
16
16
|
* - If no `exchangeToken`: treat as cookie-success path (SDK handles navigation automatically).
|
|
17
17
|
* - If `error` exists: redirects to oauthError route.
|
|
18
|
+
* - If auto-redirect is disabled (redirectUrls set to null): returns true to activate the route.
|
|
18
19
|
*
|
|
19
20
|
* @example
|
|
20
21
|
* ```typescript
|
|
@@ -45,14 +46,16 @@ export const socialRedirectCallbackGuard = async () => {
|
|
|
45
46
|
if (appState) {
|
|
46
47
|
await auth.getClient().storeOauthState(appState);
|
|
47
48
|
}
|
|
48
|
-
// Provider error: redirect to oauthError
|
|
49
|
+
// Provider error: redirect to oauthError (or activate route if auto-redirect disabled)
|
|
49
50
|
if (error) {
|
|
50
51
|
await router.navigateToError('oauth');
|
|
51
|
-
|
|
52
|
+
// Return true to activate route if oauthError redirect is disabled
|
|
53
|
+
return router.isErrorRedirectDisabled('oauth');
|
|
52
54
|
}
|
|
53
55
|
// No exchangeToken: cookie success path; hydrate then navigate to success.
|
|
54
56
|
//
|
|
55
|
-
// Note: we do not "activate" the callback route to avoid
|
|
57
|
+
// Note: When auto-redirect is enabled, we do not "activate" the callback route to avoid
|
|
58
|
+
// consumers needing to render a page. When disabled, we activate the route.
|
|
56
59
|
if (!exchangeToken) {
|
|
57
60
|
// ============================================================================
|
|
58
61
|
// Cookies mode: hydrate user state before redirecting
|
|
@@ -94,31 +97,35 @@ export const socialRedirectCallbackGuard = async () => {
|
|
|
94
97
|
appState: appState ?? undefined,
|
|
95
98
|
});
|
|
96
99
|
}
|
|
97
|
-
catch (
|
|
100
|
+
catch (error) {
|
|
98
101
|
// Only treat auth failures (401/403) as OAuth errors
|
|
99
102
|
// Network errors or other issues might be temporary - still try success route
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
// The auth guard will handle authentication state on the next route
|
|
113
|
-
await router.navigateToSuccess(appState ? { appState } : undefined);
|
|
103
|
+
// Type guard: check if error is NAuthClientError
|
|
104
|
+
if (error instanceof NAuthClientError) {
|
|
105
|
+
const isAuthError = error.statusCode === 401 ||
|
|
106
|
+
error.statusCode === 403 ||
|
|
107
|
+
error.code === NAuthErrorCode.AUTH_TOKEN_INVALID ||
|
|
108
|
+
error.code === NAuthErrorCode.AUTH_SESSION_EXPIRED ||
|
|
109
|
+
error.code === NAuthErrorCode.AUTH_SESSION_NOT_FOUND;
|
|
110
|
+
if (isAuthError) {
|
|
111
|
+
// Cookies weren't set properly - OAuth failed
|
|
112
|
+
await router.navigateToError('oauth');
|
|
113
|
+
return router.isErrorRedirectDisabled('oauth');
|
|
114
|
+
}
|
|
114
115
|
}
|
|
116
|
+
// For network errors or other non-auth issues, proceed to success route
|
|
117
|
+
// The auth guard will handle authentication state on the next route
|
|
118
|
+
await router.navigateToSuccess(appState ? { appState } : undefined);
|
|
115
119
|
}
|
|
116
|
-
|
|
120
|
+
// Return true if success redirect is disabled, allowing the callback component to render
|
|
121
|
+
return router.isSuccessRedirectDisabled({ source: 'social', appState: appState ?? undefined });
|
|
117
122
|
}
|
|
118
123
|
// Exchange token - SDK handles navigation automatically
|
|
119
124
|
// Note: appState will be passed via query params when navigateToSuccess is called
|
|
120
125
|
// by the challenge router after successful exchange
|
|
121
126
|
await auth.exchangeSocialRedirect(exchangeToken);
|
|
122
|
-
|
|
127
|
+
// Return true if success redirect is disabled, allowing the callback component to render
|
|
128
|
+
// We use 'social' as source since this is the social OAuth callback flow
|
|
129
|
+
return router.isSuccessRedirectDisabled({ source: 'social', appState: appState ?? undefined });
|
|
123
130
|
};
|
|
124
|
-
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoic29jaWFsLXJlZGlyZWN0LWNhbGxiYWNrLmd1YXJkLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vc3JjL2xpYi9zb2NpYWwtcmVkaXJlY3QtY2FsbGJhY2suZ3VhcmQudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUFFLE1BQU0sRUFBRSxXQUFXLEVBQUUsTUFBTSxlQUFlLENBQUM7QUFDcEQsT0FBTyxFQUFFLGlCQUFpQixFQUFFLE1BQU0saUJBQWlCLENBQUM7QUFFcEQsT0FBTyxFQUFFLFdBQVcsRUFBRSxNQUFNLDBCQUEwQixDQUFDO0FBQ3ZELE9BQU8sRUFBRSxnQkFBZ0IsRUFBRSxjQUFjLEVBQXFCLE1BQU0sdUJBQXVCLENBQUM7QUFFNUY7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7R0FzQkc7QUFDSCxNQUFNLENBQUMsTUFBTSwyQkFBMkIsR0FBa0IsS0FBSyxJQUFzQixFQUFFO0lBQ3JGLE1BQU0sSUFBSSxHQUFHLE1BQU0sQ0FBQyxXQUFXLENBQUMsQ0FBQztJQUNqQyxNQUFNLFVBQVUsR0FBRyxNQUFNLENBQUMsV0FBVyxDQUFDLENBQUM7SUFDdkMsTUFBTSxTQUFTLEdBQUcsaUJBQWlCLENBQUMsVUFBVSxDQUFDLENBQUM7SUFFaEQsSUFBSSxDQUFDLFNBQVMsRUFBRSxDQUFDO1FBQ2YsT0FBTyxLQUFLLENBQUM7SUFDZixDQUFDO0lBRUQsTUFBTSxNQUFNLEdBQUcsSUFBSSxlQUFlLENBQUMsTUFBTSxDQUFDLFFBQVEsQ0FBQyxNQUFNLENBQUMsQ0FBQztJQUMzRCxNQUFNLEtBQUssR0FBRyxNQUFNLENBQUMsR0FBRyxDQUFDLE9BQU8sQ0FBQyxDQUFDO0lBQ2xDLE1BQU0sYUFBYSxHQUFHLE1BQU0sQ0FBQyxHQUFHLENBQUMsZUFBZSxDQUFDLENBQUM7SUFDbEQsTUFBTSxRQUFRLEdBQUcsTUFBTSxDQUFDLEdBQUcsQ0FBQyxVQUFVLENBQUMsQ0FBQztJQUV4QyxNQUFNLE1BQU0sR0FBRyxJQUFJ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b0RBQW9EO0lBQ3BELE1BQU0sSUFBSSxDQUFDLHNCQUFzQixDQUFDLGFBQWEsQ0FBQyxDQUFDO0lBQ2pELE9BQU8sS0FBSyxDQUFDO0FBQ2YsQ0FBQyxDQUFDIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgaW5qZWN0LCBQTEFURk9STV9JRCB9IGZyb20gJ0Bhbmd1bGFyL2NvcmUnO1xuaW1wb3J0IHsgaXNQbGF0Zm9ybUJyb3dzZXIgfSBmcm9tICdAYW5ndWxhci9jb21tb24nO1xuaW1wb3J0IHsgdHlwZSBDYW5BY3RpdmF0ZUZuIH0gZnJvbSAnQGFuZ3VsYXIvcm91dGVyJztcbmltcG9ydCB7IEF1dGhTZXJ2aWNlIH0gZnJvbSAnLi4vbmdtb2R1bGUvYXV0aC5zZXJ2aWNlJztcbmltcG9ydCB7IE5BdXRoQ2xpZW50RXJyb3IsIE5BdXRoRXJyb3JDb2RlLCB0eXBlIEF1dGhSZXNwb25zZSB9IGZyb20gJ0BuYXV0aC10b29sa2l0L2NsaWVudCc7XG5cbi8qKlxuICogU29jaWFsIHJlZGlyZWN0IGNhbGxiYWNrIHJvdXRlIGd1YXJkLlxuICpcbiAqIFRoaXMgZ3VhcmQgc3VwcG9ydHMgdGhlIHJlZGlyZWN0LWZpcnN0IHNvY2lhbCBmbG93IHdoZXJlIHRoZSBiYWNrZW5kIHJlZGlyZWN0c1xuICogYmFjayB0byB0aGUgZnJvbnRlbmQgd2l0aDpcbiAqIC0gYGFwcFN0YXRlYCAoYWx3YXlzIG9wdGlvbmFsKVxuICogLSBgZXhjaGFuZ2VUb2tlbmAgKHByZXNlbnQgZm9yIGpzb24vaHlicmlkIGZsb3dzLCBhbmQgZm9yIGNvb2tpZSBmbG93cyB0aGF0IHJldHVybiBhIGNoYWxsZW5nZSlcbiAqIC0gYGVycm9yYCAvIGBlcnJvcl9kZXNjcmlwdGlvbmAgKHByb3ZpZGVyIGVycm9ycylcbiAqXG4gKiBCZWhhdmlvcjpcbiAqIC0gSWYgYGV4Y2hhbmdlVG9rZW5gIGV4aXN0czogZXhjaGFuZ2VzIGl0IHZpYSBiYWNrZW5kIChTREsgaGFuZGxlcyBuYXZpZ2F0aW9uIGF1dG9tYXRpY2FsbHkpLlxuICogLSBJZiBubyBgZXhjaGFuZ2VUb2tlbmA6IHRyZWF0IGFzIGNvb2tpZS1zdWNjZXNzIHBhdGggKFNESyBoYW5kbGVzIG5hdmlnYXRpb24gYXV0b21hdGljYWxseSkuXG4gKiAtIElmIGBlcnJvcmAgZXhpc3RzOiByZWRpcmVjdHMgdG8gb2F1dGhFcnJvciByb3V0ZS5cbiAqXG4gKiBAZXhhbXBsZVxuICogYGBgdHlwZXNjcmlwdFxuICogaW1wb3J0IHsgc29jaWFsUmVkaXJlY3RDYWxsYmFja0d1YXJkIH0gZnJvbSAnQG5hdXRoLXRvb2xraXQvY2xpZW50L2FuZ3VsYXInO1xuICpcbiAqIGV4cG9ydCBjb25zdCByb3V0ZXM6IFJvdXRlcyA9IFtcbiAqICAgeyBwYXRoOiAnYXV0aC9jYWxsYmFjaycsIGNhbkFjdGl2YXRlOiBbc29jaWFsUmVkaXJlY3RDYWxsYmFja0d1YXJkXSwgY29tcG9uZW50OiBDYWxsYmFja0NvbXBvbmVudCB9LFxuICogXTtcbiAqIGBgYFxuICovXG5leHBvcnQgY29uc3Qgc29jaWFsUmVkaXJlY3RDYWxsYmFja0d1YXJkOiBDYW5BY3RpdmF0ZUZuID0gYXN5bmMgKCk6IFByb21pc2U8Ym9vbGVhbj4gPT4ge1xuICBjb25zdCBhdXRoID0gaW5qZWN0KEF1dGhTZXJ2aWNlKTtcbiAgY29uc3QgcGxhdGZvcm1JZCA9IGluamVjdChQTEFURk9STV9JRCk7XG4gIGNvbnN0IGlzQnJvd3NlciA9IGlzUGxhdGZvcm1Ccm93c2VyKHBsYXRmb3JtSWQpO1xuXG4gIGlmICghaXNCcm93c2VyKSB7XG4gICAgcmV0dXJuIGZhbHNlO1xuICB9XG5cbiAgY29uc3QgcGFyYW1zID0gbmV3IFVSTFNlYXJjaFBhcmFtcyh3aW5kb3cubG9jYXRpb24uc2VhcmNoKTtcbiAgY29uc3QgZXJyb3IgPSBwYXJhbXMuZ2V0KCdlcnJvcicpO1xuICBjb25zdCBleGNoYW5nZVRva2VuID0gcGFyYW1zLmdldCgnZXhjaGFuZ2VUb2tlbicpO1xuICBjb25zdCBhcHBTdGF0ZSA9IHBhcmFtcy5nZXQoJ2FwcFN0YXRlJyk7XG5cbiAgY29uc3Qgcm91dGVyID0gYXV0aC5nZXRDaGFsbGVuZ2VSb3V0ZXIoKTtcblxuICAvLyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09XG4gIC8vIEV4dHJhY3QgYW5kIHN0b3JlIGFwcFN0YXRlIGlmIHByZXNlbnRcbiAgLy8gPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PVxuICAvLyBXSFk6IGFwcFN0YXRlIGlzIHJvdW5kLXRyaXBwZWQgZnJvbSB0aGUgT0F1dGggZmxvdyBhbmQgc2hvdWxkIGJlIHN0b3JlZFxuICAvLyBmb3IgcmV0cmlldmFsIHZpYSBnZXRMYXN0T2F1dGhTdGF0ZSgpIGFuZCBwYXNzZWQgdG8gdGhlIHN1Y2Nlc3Mgcm91dGUuXG4gIGlmIChhcHBTdGF0ZSkge1xuICAgIGF3YWl0IGF1dGguZ2V0Q2xpZW50KCkuc3RvcmVPYXV0aFN0YXRlKGFwcFN0YXRlKTtcbiAgfVxuXG4gIC8vIFByb3ZpZGVyIGVycm9yOiByZWRpcmVjdCB0byBvYXV0aEVycm9yXG4gIGlmIChlcnJvcikge1xuICAgIGF3YWl0IHJvdXRlci5uYXZpZ2F0ZVRvRXJyb3IoJ29hdXRoJyk7XG4gICAgcmV0dXJuIGZhbHNlO1xuICB9XG5cbiAgLy8gTm8gZXhjaGFuZ2VUb2tlbjogY29va2llIHN1Y2Nlc3MgcGF0aDsgaHlkcmF0ZSB0aGVuIG5hdmlnYXRlIHRvIHN1Y2Nlc3MuXG4gIC8vXG4gIC8vIE5vdGU6IHdlIGRvIG5vdCBcImFjdGl2YXRlXCIgdGhlIGNhbGxiYWNrIHJvdXRlIHRvIGF2b2lkIGNvbnN1bWVycyBuZWVkaW5nIHRvIHJlbmRlciBhIHBhZ2UuXG4gIGlmICghZXhjaGFuZ2VUb2tlbikge1xuICAgIC8vID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT1cbiAgICAvLyBDb29raWVzIG1vZGU6IGh5ZHJhdGUgdXNlciBzdGF0ZSBiZWZvcmUgcmVkaXJlY3RpbmdcbiAgICAvLyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09XG4gICAgLy8gV0hZOiBJbiBjb29raWUgZGVsaXZlcnksIHRoZSBPQXV0aCBjYWxsYmFjayBjb21wbGV0ZXMgdmlhIGJyb3dzZXIgcmVkaXJlY3RzLCBzbyB0aGUgZnJvbnRlbmRcbiAgICAvLyBkb2VzIG5vdCByZWNlaXZlIGEgSlNPTiBBdXRoUmVzcG9uc2UgdG8gcG9wdWxhdGUgdGhlIFNESydzIGNhY2hlZCBgY3VycmVudFVzZXJgLlxuICAgIC8vXG4gICAgLy8gV2l0aG91dCB0aGlzLCBzeW5jIGd1YXJkcyAoYGF1dGhHdWFyZGApIGNhbiBpbW1lZGlhdGVseSByZWRpcmVjdCB0byAvbG9naW4gYmVjYXVzZVxuICAgIC8vIGBjdXJyZW50VXNlcmAgaXMgc3RpbGwgbnVsbCBldmVuIHRob3VnaCBjb29raWVzIHdlcmUgc2V0IHN1Y2Nlc3NmdWxseS5cbiAgICB0cnkge1xuICAgICAgY29uc3QgdXNlciA9IGF3YWl0IGF1dGguZ2V0UHJvZmlsZSgpO1xuXG4gICAgICAvLyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09XG4gICAgICAvLyBSb3V0ZSB0aHJvdWdoIGhhbmRsZUF1dGhSZXNwb25zZSB0byBlbnN1cmUgb25BdXRoUmVzcG9uc2UgaXMgY2FsbGVkXG4gICAgICAvLyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09XG4gICAgICAvLyBXSFk6IG9uQXV0aFJlc3BvbnNlIHNob3VsZCBiZSBjYWxsZWQgY29uc2lzdGVudGx5IGZvciBhbGwgYXV0aCBjb21wbGV0aW9ucyxcbiAgICAgIC8vIHdoZXRoZXIgdmlhIGV4Y2hhbmdlIHRva2VuIG9yIGNvb2tpZSBzdWNjZXNzIHBhdGguIFRoaXMgYWxsb3dzIGFwcHMgdG8gaGF2ZVxuICAgICAgLy8gYSBzaW5nbGUgaGFuZGxlciBmb3IgYWxsIGF1dGhlbnRpY2F0aW9uIG91dGNvbWVzIChsb2dpbiwgc2lnbnVwLCBzb2NpYWwpLlxuICAgICAgLy9cbiAgICAgIC8vIFdlIGNvbnN0cnVjdCBhIHN5bnRoZXRpYyBBdXRoUmVzcG9uc2Ugd2l0aCB0aGUgdXNlciBkYXRhLiBUb2tlbnMgYXJlIG9taXR0ZWRcbiAgICAgIC8vIGJlY2F1c2UgdGhleSdyZSBpbiBodHRwT25seSBjb29raWVzLCBub3QgYWNjZXNzaWJsZSB0byB0aGUgY2xpZW50LlxuICAgICAgY29uc3Qgc3ludGhldGljUmVzcG9uc2U6IEF1dGhSZXNwb25zZSA9IHtcbiAgICAgICAgdXNlcjoge1xuICAgICAgICAgIHN1YjogdXNlci5zdWIsXG4gICAgICAgICAgZW1haWw6IHVzZXIuZW1haWwsXG4gICAgICAgICAgZmlyc3ROYW1lOiB1c2VyLmZpcnN0TmFtZSxcbiAgICAgICAgICBsYXN0TmFtZTogdXNlci5sYXN0TmFtZSxcbiAgICAgICAgICBwaG9uZTogdXNlci5waG9uZSxcbiAgICAgICAgICBpc0VtYWlsVmVyaWZpZWQ6IHVzZXIuaXNFbWFpbFZlcmlmaWVkLFxuICAgICAgICAgIGlzUGhvbmVWZXJpZmllZDogdXNlci5pc1Bob25lVmVyaWZpZWQsXG4gICAgICAgICAgc29jaWFsUHJvdmlkZXJzOiB1c2VyLnNvY2lhbFByb3ZpZGVycyxcbiAgICAgICAgICBoYXNQYXNzd29yZEhhc2g6IHVzZXIuaGFzUGFzc3dvcmRIYXNoLFxuICAgICAgICB9LFxuICAgICAgICBhdXRoTWV0aG9kOiB1c2VyLnNlc3Npb25BdXRoTWV0aG9kID8/IHVuZGVmaW5lZCxcbiAgICAgIH07XG5cbiAgICAgIC8vIENhbGwgaGFuZGxlQXV0aFJlc3BvbnNlIHdoaWNoIHJlc3BlY3RzIG9uQXV0aFJlc3BvbnNlIGNhbGxiYWNrXG4gICAgICAvLyBQYXNzIGFwcFN0YXRlIGluIGNvbnRleHQgc28gb25BdXRoUmVzcG9uc2UgY2FuIGFjY2VzcyBpdFxuICAgICAgYXdhaXQgcm91dGVyLmhhbmRsZUF1dGhSZXNwb25zZShzeW50aGV0aWNSZXNwb25zZSwge1xuICAgICAgICBzb3VyY2U6ICdzb2NpYWwnLFxuICAgICAgICBhcHBTdGF0ZTogYXBwU3RhdGUgPz8gdW5kZWZpbmVkLFxuICAgICAgfSk7XG4gICAgfSBjYXRjaCAoZXJyKSB7XG4gICAgICAvLyBPbmx5IHRyZWF0IGF1dGggZmFpbHVyZXMgKDQwMS80MDMpIGFzIE9BdXRoIGVycm9yc1xuICAgICAgLy8gTmV0d29yayBlcnJvcnMgb3Igb3RoZXIgaXNzdWVzIG1pZ2h0IGJlIHRlbXBvcmFyeSAtIHN0aWxsIHRyeSBzdWNjZXNzIHJvdXRlXG4gICAgICBjb25zdCBpc0F1dGhFcnJvciA9XG4gICAgICAgIGVyciBpbnN0YW5jZW9mIE5BdXRoQ2xpZW50RXJyb3IgJiZcbiAgICAgICAgKGVyci5zdGF0dXNDb2RlID09PSA0MDEgfHxcbiAgICAgICAgICBlcnIuc3RhdHVzQ29kZSA9PT0gNDAzIHx8XG4gICAgICAgICAgZXJyLmNvZGUgPT09IE5BdXRoRXJyb3JDb2RlLkFVVEhfVE9LRU5fSU5WQUxJRCB8fFxuICAgICAgICAgIGVyci5jb2RlID09PSBOQXV0aEVycm9yQ29kZS5BVVRIX1NFU1NJT05fRVhQSVJFRCB8fFxuICAgICAgICAgIGVyci5jb2RlID09PSBOQXV0aEVycm9yQ29kZS5BVVRIX1NFU1NJT05fTk9UX0ZPVU5EKTtcblxuICAgICAgaWYgKGlzQXV0aEVycm9yKSB7XG4gICAgICAgIC8vIENvb2tpZXMgd2VyZW4ndCBzZXQgcHJvcGVybHkgLSBPQXV0aCBmYWlsZWRcbiAgICAgICAgYXdhaXQgcm91dGVyLm5hdmlnYXRlVG9FcnJvcignb2F1dGgnKTtcbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIC8vIEZvciBuZXR3b3JrIGVycm9ycyBvciBvdGhlciBpc3N1ZXMsIHByb2NlZWQgdG8gc3VjY2VzcyByb3V0ZVxuICAgICAgICAvLyBUaGUgYXV0aCBndWFyZCB3aWxsIGhhbmRsZSBhdXRoZW50aWNhdGlvbiBzdGF0ZSBvbiB0aGUgbmV4dCByb3V0ZVxuICAgICAgICBhd2FpdCByb3V0ZXIubmF2aWdhdGVUb1N1Y2Nlc3MoYXBwU3RhdGUgPyB7IGFwcFN0YXRlIH0gOiB1bmRlZmluZWQpO1xuICAgICAgfVxuICAgIH1cbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cblxuICAvLyBFeGNoYW5nZSB0b2tlbiAtIFNESyBoYW5kbGVzIG5hdmlnYXRpb24gYXV0b21hdGljYWxseVxuICAvLyBOb3RlOiBhcHBTdGF0ZSB3aWxsIGJlIHBhc3NlZCB2aWEgcXVlcnkgcGFyYW1zIHdoZW4gbmF2aWdhdGVUb1N1Y2Nlc3MgaXMgY2FsbGVkXG4gIC8vIGJ5IHRoZSBjaGFsbGVuZ2Ugcm91dGVyIGFmdGVyIHN1Y2Nlc3NmdWwgZXhjaGFuZ2VcbiAgYXdhaXQgYXV0aC5leGNoYW5nZVNvY2lhbFJlZGlyZWN0KGV4Y2hhbmdlVG9rZW4pO1xuICByZXR1cm4gZmFsc2U7XG59O1xuIl19
|
|
131
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoic29jaWFsLXJlZGlyZWN0LWNhbGxiYWNrLmd1YXJkLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vc3JjL2xpYi9zb2NpYWwtcmVkaXJlY3QtY2FsbGJhY2suZ3VhcmQudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUFFLE1BQU0sRUFBRSxXQUFXLEVBQUUsTUFBTSxlQUFlLENBQUM7QUFDcEQsT0FBTyxFQUFFLGlCQUFpQixFQUFFLE1BQU0saUJBQWlCLENBQUM7QUFFcEQsT0FBTyxFQUFFLFdBQVcsRUFBRSxNQUFNLDBCQUEwQixDQUFDO0FBQ3ZELE9BQU8sRUFBRSxnQkFBZ0IsRUFBRSxjQUFjLEVBQXFCLE1BQU0sdUJBQXVCLENBQUM7QUFFNUY7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7O0dBdUJHO0FBQ0gsTUFBTSxDQUFDLE1BQU0sMkJBQTJCLEdBQWtCLEtBQUssSUFBc0IsRUFBRTtJQUNyRixNQUFNLElBQUksR0FBRyxNQUFNLENBQUMsV0FBVyxDQUFDLENBQUM7SUFDakMsTUFBTSxVQUFVLEdBQUcsTUFBTSxDQUFDLFdBQVcsQ0FBQyxDQUFDO0lBQ3ZDLE1BQU0sU0FBUyxHQUFHLGlCQUFpQixDQUFDLFVBQVUsQ0FBQyxDQUFDO0lBRWhELElBQUksQ0FBQyxTQUFTLEVBQUUsQ0FBQztRQUNmLE9BQU8sS0FBSyxDQUFDO0lBQ2YsQ0FBQztJQUVELE1BQU0sTUFBTSxHQUFHLElBQUksZUFBZSxDQUFDLE1BQU0sQ0FBQyxRQUFRLENBQUMsTUFBTSxDQUFDLENBQUM7SUFDM0QsTUFBTSxLQUFLLEdBQUcsTUFBTSxDQUFDLEdBQUcsQ0FBQyxPQUFPLENBQUMsQ0FBQztJQUNsQyxNQUFNLGFBQWEsR0FBRyxNQUFNLENBQUMsR0FBRyxDQUFDLGVBQWUsQ0FBQyxDQUFDO0lBQ2xELE1BQU0sUUFBUSxHQUFHLE1BQU0sQ0FBQyxHQUFHLENBQUMsVUFBVSxDQUFDLENBQUM7SUFFeEMsTUFBTSxNQUFNLEdBQUcsSUFB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QUFRLEVBQUUsQ0FBQyxDQUFDLENBQUMsU0FBUyxDQUFDLENBQUM7UUFDdEUsQ0FBQztRQUVELHlGQUF5RjtRQUN6RixPQUFPLE1BQU0sQ0FBQyx5QkFBeUIsQ0FBQyxFQUFFLE1BQU0sRUFBRSxRQUFRLEVBQUUsUUFBUSxFQUFFLFFBQVEsSUFBSSxTQUFTLEVBQUUsQ0FBQyxDQUFDO0lBQ2pHLENBQUM7SUFFRCx3REFBd0Q7SUFDeEQsa0ZBQWtGO0lBQ2xGLG9EQUFvRDtJQUNwRCxNQUFNLElBQUksQ0FBQyxzQkFBc0IsQ0FBQyxhQUFhLENBQUMsQ0FBQztJQUVqRCx5RkFBeUY7SUFDekYseUVBQXlFO0lBQ3pFLE9BQU8sTUFBTSxDQUFDLHlCQUF5QixDQUFDLEVBQUUsTUFBTSxFQUFFLFFBQVEsRUFBRSxRQUFRLEVBQUUsUUFBUSxJQUFJLFNBQVMsRUFBRSxDQUFDLENBQUM7QUFDakcsQ0FBQyxDQUFDIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgaW5qZWN0LCBQTEFURk9STV9JRCB9IGZyb20gJ0Bhbmd1bGFyL2NvcmUnO1xuaW1wb3J0IHsgaXNQbGF0Zm9ybUJyb3dzZXIgfSBmcm9tICdAYW5ndWxhci9jb21tb24nO1xuaW1wb3J0IHsgdHlwZSBDYW5BY3RpdmF0ZUZuIH0gZnJvbSAnQGFuZ3VsYXIvcm91dGVyJztcbmltcG9ydCB7IEF1dGhTZXJ2aWNlIH0gZnJvbSAnLi4vbmdtb2R1bGUvYXV0aC5zZXJ2aWNlJztcbmltcG9ydCB7IE5BdXRoQ2xpZW50RXJyb3IsIE5BdXRoRXJyb3JDb2RlLCB0eXBlIEF1dGhSZXNwb25zZSB9IGZyb20gJ0BuYXV0aC10b29sa2l0L2NsaWVudCc7XG5cbi8qKlxuICogU29jaWFsIHJlZGlyZWN0IGNhbGxiYWNrIHJvdXRlIGd1YXJkLlxuICpcbiAqIFRoaXMgZ3VhcmQgc3VwcG9ydHMgdGhlIHJlZGlyZWN0LWZpcnN0IHNvY2lhbCBmbG93IHdoZXJlIHRoZSBiYWNrZW5kIHJlZGlyZWN0c1xuICogYmFjayB0byB0aGUgZnJvbnRlbmQgd2l0aDpcbiAqIC0gYGFwcFN0YXRlYCAoYWx3YXlzIG9wdGlvbmFsKVxuICogLSBgZXhjaGFuZ2VUb2tlbmAgKHByZXNlbnQgZm9yIGpzb24vaHlicmlkIGZsb3dzLCBhbmQgZm9yIGNvb2tpZSBmbG93cyB0aGF0IHJldHVybiBhIGNoYWxsZW5nZSlcbiAqIC0gYGVycm9yYCAvIGBlcnJvcl9kZXNjcmlwdGlvbmAgKHByb3ZpZGVyIGVycm9ycylcbiAqXG4gKiBCZWhhdmlvcjpcbiAqIC0gSWYgYGV4Y2hhbmdlVG9rZW5gIGV4aXN0czogZXhjaGFuZ2VzIGl0IHZpYSBiYWNrZW5kIChTREsgaGFuZGxlcyBuYXZpZ2F0aW9uIGF1dG9tYXRpY2FsbHkpLlxuICogLSBJZiBubyBgZXhjaGFuZ2VUb2tlbmA6IHRyZWF0IGFzIGNvb2tpZS1zdWNjZXNzIHBhdGggKFNESyBoYW5kbGVzIG5hdmlnYXRpb24gYXV0b21hdGljYWxseSkuXG4gKiAtIElmIGBlcnJvcmAgZXhpc3RzOiByZWRpcmVjdHMgdG8gb2F1dGhFcnJvciByb3V0ZS5cbiAqIC0gSWYgYXV0by1yZWRpcmVjdCBpcyBkaXNhYmxlZCAocmVkaXJlY3RVcmxzIHNldCB0byBudWxsKTogcmV0dXJucyB0cnVlIHRvIGFjdGl2YXRlIHRoZSByb3V0ZS5cbiAqXG4gKiBAZXhhbXBsZVxuICogYGBgdHlwZXNjcmlwdFxuICogaW1wb3J0IHsgc29jaWFsUmVkaXJlY3RDYWxsYmFja0d1YXJkIH0gZnJvbSAnQG5hdXRoLXRvb2xraXQvY2xpZW50L2FuZ3VsYXInO1xuICpcbiAqIGV4cG9ydCBjb25zdCByb3V0ZXM6IFJvdXRlcyA9IFtcbiAqICAgeyBwYXRoOiAnYXV0aC9jYWxsYmFjaycsIGNhbkFjdGl2YXRlOiBbc29jaWFsUmVkaXJlY3RDYWxsYmFja0d1YXJkXSwgY29tcG9uZW50OiBDYWxsYmFja0NvbXBvbmVudCB9LFxuICogXTtcbiAqIGBgYFxuICovXG5leHBvcnQgY29uc3Qgc29jaWFsUmVkaXJlY3RDYWxsYmFja0d1YXJkOiBDYW5BY3RpdmF0ZUZuID0gYXN5bmMgKCk6IFByb21pc2U8Ym9vbGVhbj4gPT4ge1xuICBjb25zdCBhdXRoID0gaW5qZWN0KEF1dGhTZXJ2aWNlKTtcbiAgY29uc3QgcGxhdGZvcm1JZCA9IGluamVjdChQTEFURk9STV9JRCk7XG4gIGNvbnN0IGlzQnJvd3NlciA9IGlzUGxhdGZvcm1Ccm93c2VyKHBsYXRmb3JtSWQpO1xuXG4gIGlmICghaXNCcm93c2VyKSB7XG4gICAgcmV0dXJuIGZhbHNlO1xuICB9XG5cbiAgY29uc3QgcGFyYW1zID0gbmV3IFVSTFNlYXJjaFBhcmFtcyh3aW5kb3cubG9jYXRpb24uc2VhcmNoKTtcbiAgY29uc3QgZXJyb3IgPSBwYXJhbXMuZ2V0KCdlcnJvcicpO1xuICBjb25zdCBleGNoYW5nZVRva2VuID0gcGFyYW1zLmdldCgnZXhjaGFuZ2VUb2tlbicpO1xuICBjb25zdCBhcHBTdGF0ZSA9IHBhcmFtcy5nZXQoJ2FwcFN0YXRlJyk7XG5cbiAgY29uc3Qgcm91dGVyID0gYXV0aC5nZXRDaGFsbGVuZ2VSb3V0ZXIoKTtcblxuICAvLyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09XG4gIC8vIEV4dHJhY3QgYW5kIHN0b3JlIGFwcFN0YXRlIGlmIHByZXNlbnRcbiAgLy8gPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PVxuICAvLyBXSFk6IGFwcFN0YXRlIGlzIHJvdW5kLXRyaXBwZWQgZnJvbSB0aGUgT0F1dGggZmxvdyBhbmQgc2hvdWxkIGJlIHN0b3JlZFxuICAvLyBmb3IgcmV0cmlldmFsIHZpYSBnZXRMYXN0T2F1dGhTdGF0ZSgpIGFuZCBwYXNzZWQgdG8gdGhlIHN1Y2Nlc3Mgcm91dGUuXG4gIGlmIChhcHBTdGF0ZSkge1xuICAgIGF3YWl0IGF1dGguZ2V0Q2xpZW50KCkuc3RvcmVPYXV0aFN0YXRlKGFwcFN0YXRlKTtcbiAgfVxuXG4gIC8vIFByb3ZpZGVyIGVycm9yOiByZWRpcmVjdCB0byBvYXV0aEVycm9yIChvciBhY3RpdmF0ZSByb3V0ZSBpZiBhdXRvLXJlZGlyZWN0IGRpc2FibGVkKVxuICBpZiAoZXJyb3IpIHtcbiAgICBhd2FpdCByb3V0ZXIubmF2aWdhdGVUb0Vycm9yKCdvYXV0aCcpO1xuICAgIC8vIFJldHVybiB0cnVlIHRvIGFjdGl2YXRlIHJvdXRlIGlmIG9hdXRoRXJyb3IgcmVkaXJlY3QgaXMgZGlzYWJsZWRcbiAgICByZXR1cm4gcm91dGVyLmlzRXJyb3JSZWRpcmVjdERpc2FibGVkKCdvYXV0aCcpO1xuICB9XG5cbiAgLy8gTm8gZXhjaGFuZ2VUb2tlbjogY29va2llIHN1Y2Nlc3MgcGF0aDsgaHlkcmF0ZSB0aGVuIG5hdmlnYXRlIHRvIHN1Y2Nlc3MuXG4gIC8vXG4gIC8vIE5vdGU6IFdoZW4gYXV0by1yZWRpcmVjdCBpcyBlbmFibGVkLCB3ZSBkbyBub3QgXCJhY3RpdmF0ZVwiIHRoZSBjYWxsYmFjayByb3V0ZSB0byBhdm9pZFxuICAvLyBjb25zdW1lcnMgbmVlZGluZyB0byByZW5kZXIgYSBwYWdlLiBXaGVuIGRpc2FibGVkLCB3ZSBhY3RpdmF0ZSB0aGUgcm91dGUuXG4gIGlmICghZXhjaGFuZ2VUb2tlbikge1xuICAgIC8vID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT1cbiAgICAvLyBDb29raWVzIG1vZGU6IGh5ZHJhdGUgdXNlciBzdGF0ZSBiZWZvcmUgcmVkaXJlY3RpbmdcbiAgICAvLyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09XG4gICAgLy8gV0hZOiBJbiBjb29raWUgZGVsaXZlcnksIHRoZSBPQXV0aCBjYWxsYmFjayBjb21wbGV0ZXMgdmlhIGJyb3dzZXIgcmVkaXJlY3RzLCBzbyB0aGUgZnJvbnRlbmRcbiAgICAvLyBkb2VzIG5vdCByZWNlaXZlIGEgSlNPTiBBdXRoUmVzcG9uc2UgdG8gcG9wdWxhdGUgdGhlIFNESydzIGNhY2hlZCBgY3VycmVudFVzZXJgLlxuICAgIC8vXG4gICAgLy8gV2l0aG91dCB0aGlzLCBzeW5jIGd1YXJkcyAoYGF1dGhHdWFyZGApIGNhbiBpbW1lZGlhdGVseSByZWRpcmVjdCB0byAvbG9naW4gYmVjYXVzZVxuICAgIC8vIGBjdXJyZW50VXNlcmAgaXMgc3RpbGwgbnVsbCBldmVuIHRob3VnaCBjb29raWVzIHdlcmUgc2V0IHN1Y2Nlc3NmdWxseS5cbiAgICB0cnkge1xuICAgICAgY29uc3QgdXNlciA9IGF3YWl0IGF1dGguZ2V0UHJvZmlsZSgpO1xuXG4gICAgICAvLyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09XG4gICAgICAvLyBSb3V0ZSB0aHJvdWdoIGhhbmRsZUF1dGhSZXNwb25zZSB0byBlbnN1cmUgb25BdXRoUmVzcG9uc2UgaXMgY2FsbGVkXG4gICAgICAvLyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09XG4gICAgICAvLyBXSFk6IG9uQXV0aFJlc3BvbnNlIHNob3VsZCBiZSBjYWxsZWQgY29uc2lzdGVudGx5IGZvciBhbGwgYXV0aCBjb21wbGV0aW9ucyxcbiAgICAgIC8vIHdoZXRoZXIgdmlhIGV4Y2hhbmdlIHRva2VuIG9yIGNvb2tpZSBzdWNjZXNzIHBhdGguIFRoaXMgYWxsb3dzIGFwcHMgdG8gaGF2ZVxuICAgICAgLy8gYSBzaW5nbGUgaGFuZGxlciBmb3IgYWxsIGF1dGhlbnRpY2F0aW9uIG91dGNvbWVzIChsb2dpbiwgc2lnbnVwLCBzb2NpYWwpLlxuICAgICAgLy9cbiAgICAgIC8vIFdlIGNvbnN0cnVjdCBhIHN5bnRoZXRpYyBBdXRoUmVzcG9uc2Ugd2l0aCB0aGUgdXNlciBkYXRhLiBUb2tlbnMgYXJlIG9taXR0ZWRcbiAgICAgIC8vIGJlY2F1c2UgdGhleSdyZSBpbiBodHRwT25seSBjb29raWVzLCBub3QgYWNjZXNzaWJsZSB0byB0aGUgY2xpZW50LlxuICAgICAgY29uc3Qgc3ludGhldGljUmVzcG9uc2U6IEF1dGhSZXNwb25zZSA9IHtcbiAgICAgICAgdXNlcjoge1xuICAgICAgICAgIHN1YjogdXNlci5zdWIsXG4gICAgICAgICAgZW1haWw6IHVzZXIuZW1haWwsXG4gICAgICAgICAgZmlyc3ROYW1lOiB1c2VyLmZpcnN0TmFtZSxcbiAgICAgICAgICBsYXN0TmFtZTogdXNlci5sYXN0TmFtZSxcbiAgICAgICAgICBwaG9uZTogdXNlci5waG9uZSxcbiAgICAgICAgICBpc0VtYWlsVmVyaWZpZWQ6IHVzZXIuaXNFbWFpbFZlcmlmaWVkLFxuICAgICAgICAgIGlzUGhvbmVWZXJpZmllZDogdXNlci5pc1Bob25lVmVyaWZpZWQsXG4gICAgICAgICAgc29jaWFsUHJvdmlkZXJzOiB1c2VyLnNvY2lhbFByb3ZpZGVycyxcbiAgICAgICAgICBoYXNQYXNzd29yZEhhc2g6IHVzZXIuaGFzUGFzc3dvcmRIYXNoLFxuICAgICAgICB9LFxuICAgICAgICBhdXRoTWV0aG9kOiB1c2VyLnNlc3Npb25BdXRoTWV0aG9kID8/IHVuZGVmaW5lZCxcbiAgICAgIH07XG5cbiAgICAgIC8vIENhbGwgaGFuZGxlQXV0aFJlc3BvbnNlIHdoaWNoIHJlc3BlY3RzIG9uQXV0aFJlc3BvbnNlIGNhbGxiYWNrXG4gICAgICAvLyBQYXNzIGFwcFN0YXRlIGluIGNvbnRleHQgc28gb25BdXRoUmVzcG9uc2UgY2FuIGFjY2VzcyBpdFxuICAgICAgYXdhaXQgcm91dGVyLmhhbmRsZUF1dGhSZXNwb25zZShzeW50aGV0aWNSZXNwb25zZSwge1xuICAgICAgICBzb3VyY2U6ICdzb2NpYWwnLFxuICAgICAgICBhcHBTdGF0ZTogYXBwU3RhdGUgPz8gdW5kZWZpbmVkLFxuICAgICAgfSk7XG4gICAgfSBjYXRjaCAoZXJyb3I6IHVua25vd24pIHtcbiAgICAgIC8vIE9ubHkgdHJlYXQgYXV0aCBmYWlsdXJlcyAoNDAxLzQwMykgYXMgT0F1dGggZXJyb3JzXG4gICAgICAvLyBOZXR3b3JrIGVycm9ycyBvciBvdGhlciBpc3N1ZXMgbWlnaHQgYmUgdGVtcG9yYXJ5IC0gc3RpbGwgdHJ5IHN1Y2Nlc3Mgcm91dGVcblxuICAgICAgLy8gVHlwZSBndWFyZDogY2hlY2sgaWYgZXJyb3IgaXMgTkF1dGhDbGllbnRFcnJvclxuICAgICAgaWYgKGVycm9yIGluc3RhbmNlb2YgTkF1dGhDbGllbnRFcnJvcikge1xuICAgICAgICBjb25zdCBpc0F1dGhFcnJvciA9XG4gICAgICAgICAgZXJyb3Iuc3RhdHVzQ29kZSA9PT0gNDAxIHx8XG4gICAgICAgICAgZXJyb3Iuc3RhdHVzQ29kZSA9PT0gNDAzIHx8XG4gICAgICAgICAgZXJyb3IuY29kZSA9PT0gTkF1dGhFcnJvckNvZGUuQVVUSF9UT0tFTl9JTlZBTElEIHx8XG4gICAgICAgICAgZXJyb3IuY29kZSA9PT0gTkF1dGhFcnJvckNvZGUuQVVUSF9TRVNTSU9OX0VYUElSRUQgfHxcbiAgICAgICAgICBlcnJvci5jb2RlID09PSBOQXV0aEVycm9yQ29kZS5BVVRIX1NFU1NJT05fTk9UX0ZPVU5EO1xuXG4gICAgICAgIGlmIChpc0F1dGhFcnJvcikge1xuICAgICAgICAgIC8vIENvb2tpZXMgd2VyZW4ndCBzZXQgcHJvcGVybHkgLSBPQXV0aCBmYWlsZWRcbiAgICAgICAgICBhd2FpdCByb3V0ZXIubmF2aWdhdGVUb0Vycm9yKCdvYXV0aCcpO1xuICAgICAgICAgIHJldHVybiByb3V0ZXIuaXNFcnJvclJlZGlyZWN0RGlzYWJsZWQoJ29hdXRoJyk7XG4gICAgICAgIH1cbiAgICAgIH1cblxuICAgICAgLy8gRm9yIG5ldHdvcmsgZXJyb3JzIG9yIG90aGVyIG5vbi1hdXRoIGlzc3VlcywgcHJvY2VlZCB0byBzdWNjZXNzIHJvdXRlXG4gICAgICAvLyBUaGUgYXV0aCBndWFyZCB3aWxsIGhhbmRsZSBhdXRoZW50aWNhdGlvbiBzdGF0ZSBvbiB0aGUgbmV4dCByb3V0ZVxuICAgICAgYXdhaXQgcm91dGVyLm5hdmlnYXRlVG9TdWNjZXNzKGFwcFN0YXRlID8geyBhcHBTdGF0ZSB9IDogdW5kZWZpbmVkKTtcbiAgICB9XG5cbiAgICAvLyBSZXR1cm4gdHJ1ZSBpZiBzdWNjZXNzIHJlZGlyZWN0IGlzIGRpc2FibGVkLCBhbGxvd2luZyB0aGUgY2FsbGJhY2sgY29tcG9uZW50IHRvIHJlbmRlclxuICAgIHJldHVybiByb3V0ZXIuaXNTdWNjZXNzUmVkaXJlY3REaXNhYmxlZCh7IHNvdXJjZTogJ3NvY2lhbCcsIGFwcFN0YXRlOiBhcHBTdGF0ZSA/PyB1bmRlZmluZWQgfSk7XG4gIH1cblxuICAvLyBFeGNoYW5nZSB0b2tlbiAtIFNESyBoYW5kbGVzIG5hdmlnYXRpb24gYXV0b21hdGljYWxseVxuICAvLyBOb3RlOiBhcHBTdGF0ZSB3aWxsIGJlIHBhc3NlZCB2aWEgcXVlcnkgcGFyYW1zIHdoZW4gbmF2aWdhdGVUb1N1Y2Nlc3MgaXMgY2FsbGVkXG4gIC8vIGJ5IHRoZSBjaGFsbGVuZ2Ugcm91dGVyIGFmdGVyIHN1Y2Nlc3NmdWwgZXhjaGFuZ2VcbiAgYXdhaXQgYXV0aC5leGNoYW5nZVNvY2lhbFJlZGlyZWN0KGV4Y2hhbmdlVG9rZW4pO1xuXG4gIC8vIFJldHVybiB0cnVlIGlmIHN1Y2Nlc3MgcmVkaXJlY3QgaXMgZGlzYWJsZWQsIGFsbG93aW5nIHRoZSBjYWxsYmFjayBjb21wb25lbnQgdG8gcmVuZGVyXG4gIC8vIFdlIHVzZSAnc29jaWFsJyBhcyBzb3VyY2Ugc2luY2UgdGhpcyBpcyB0aGUgc29jaWFsIE9BdXRoIGNhbGxiYWNrIGZsb3dcbiAgcmV0dXJuIHJvdXRlci5pc1N1Y2Nlc3NSZWRpcmVjdERpc2FibGVkKHsgc291cmNlOiAnc29jaWFsJywgYXBwU3RhdGU6IGFwcFN0YXRlID8/IHVuZGVmaW5lZCB9KTtcbn07XG4iXX0=
|