@bnsights/bbsf-controls 1.0.181 → 1.0.183

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.
@@ -1,16 +1,14 @@
1
- import { Component, Input, Optional, Output, EventEmitter } from '@angular/core';
1
+ import { Component, Input, Optional, Output, EventEmitter, SkipSelf } from '@angular/core';
2
2
  import { FormControl, Validators } from '@angular/forms';
3
3
  import * as i0 from "@angular/core";
4
- import * as i1 from "../../Shared/services/ControlUtility";
4
+ import * as i1 from "../../Shared/services";
5
5
  import * as i2 from "@angular/forms";
6
6
  import * as i3 from "@bnsights/bbsf-utilities";
7
- import * as i4 from "../../Shared/services/GlobalSettings.service";
8
- import * as i5 from "@angular/common";
9
- import * as i6 from "@angular/cdk/bidi";
10
- import * as i7 from "ngx-intl-tel-input";
11
- import * as i8 from "ng-inline-svg-2";
7
+ import * as i4 from "@angular/common";
8
+ import * as i5 from "@angular/cdk/bidi";
9
+ import * as i6 from "ngx-intl-tel-input";
10
+ import * as i7 from "ng-inline-svg-2";
12
11
  export class TextAreaComponent {
13
- static { this.controlContainerstatic = null; }
14
12
  constructor(controlUtility, controlContainer, textAreaControlHost, utilityService, controlValidationService, globalSettings, speechRecognitionService, languageService) {
15
13
  this.controlUtility = controlUtility;
16
14
  this.controlContainer = controlContainer;
@@ -34,6 +32,12 @@ export class TextAreaComponent {
34
32
  this.minCharsLimit = -1; //To disable chars limit feature by default
35
33
  this.maxLimitWarningMsg = '';
36
34
  this.isMicOn = false;
35
+ this.selectedSpeechLanguageDisplayText = '';
36
+ // Accessibility properties
37
+ this.ariaDescribedBy = '';
38
+ this.errorMessageId = '';
39
+ this.characterCountId = '';
40
+ this.wordCountId = '';
37
41
  this.resetError = () => {
38
42
  this.controlValidationService.removeGlobalError();
39
43
  };
@@ -57,10 +61,23 @@ export class TextAreaComponent {
57
61
  this.isValid = () => {
58
62
  this.controlUtility.isValid(this.textAreaFormControl);
59
63
  };
60
- TextAreaComponent.controlContainerstatic = this.controlContainer;
61
64
  this.currentLanguage = localStorage.getItem('language');
62
65
  }
63
66
  ngOnInit() {
67
+ // Initialize accessibility IDs
68
+ this.errorMessageId = `${this.options.name}-error`;
69
+ this.characterCountId = `${this.options.name}-char-count`;
70
+ this.wordCountId = `${this.options.name}-word-count`;
71
+ this.updateAriaDescribedBy();
72
+ // Initialize speech recognition properties only if enabled
73
+ if (this.options.enableSpeechRecognition) {
74
+ this.isMicOn = false;
75
+ this.selectedSpeechLanguageDisplayText = '';
76
+ }
77
+ else {
78
+ // Reset speech-related properties when disabled
79
+ this.resetSpeechProperties();
80
+ }
64
81
  if (this.options.isReadonly && !this.options.value)
65
82
  this.options.value = this.utilityService.getResourceValue('NA');
66
83
  if (this.options.forceDirection)
@@ -116,9 +133,24 @@ export class TextAreaComponent {
116
133
  if (this.options.isDisabled) {
117
134
  this.textAreaFormControl.disable();
118
135
  }
119
- this.textAreaControlHost.ngSubmit.subscribe((value) => {
120
- this.group.markAllAsTouched();
121
- this.markAllAsTouched = true;
136
+ // Only subscribe to ngSubmit if FormGroupDirective is available
137
+ if (this.textAreaControlHost) {
138
+ this.textAreaControlHost.ngSubmit.subscribe((value) => {
139
+ this.group.markAllAsTouched();
140
+ this.markAllAsTouched = true;
141
+ });
142
+ }
143
+ // Subscribe to value changes to ensure warning messages are properly reset
144
+ this.valueChangesSubscription = this.textAreaFormControl.valueChanges.subscribe((value) => {
145
+ // Reset warning message when control is empty or null
146
+ if (!value || value.trim().length === 0) {
147
+ this.showCharsLimitMsg = false;
148
+ this.hasCharsLimitValidationError = false;
149
+ this.maxLimitWarningMsg = '';
150
+ this.currentCharsCount = 0;
151
+ this.wordCount = 0;
152
+ this.wordCountArray = 0;
153
+ }
122
154
  });
123
155
  }
124
156
  ngAfterViewInit() {
@@ -137,6 +169,55 @@ export class TextAreaComponent {
137
169
  getInputType(type) {
138
170
  return this.controlUtility.getInputType(type);
139
171
  }
172
+ // Accessibility helper methods
173
+ updateAriaDescribedBy() {
174
+ const describedByIds = [];
175
+ if (this.options.labelDescription) {
176
+ describedByIds.push(`${this.options.name}-description`);
177
+ }
178
+ if (this.options.maxWordCount > 0) {
179
+ describedByIds.push(this.wordCountId);
180
+ }
181
+ if (this.showCharsLimitMsg) {
182
+ describedByIds.push(this.characterCountId);
183
+ }
184
+ if (this.textAreaFormControl?.invalid && this.textAreaFormControl?.touched) {
185
+ describedByIds.push(this.errorMessageId);
186
+ }
187
+ // Only add speech-related descriptions if speech recognition is enabled
188
+ if (this.options.enableSpeechRecognition && this.selectedSpeechLanguageDisplayText) {
189
+ describedByIds.push(`${this.options.name}-language-display`);
190
+ }
191
+ this.ariaDescribedBy = describedByIds.join(' ');
192
+ }
193
+ announceToScreenReader(message) {
194
+ // Create temporary element for screen reader announcement
195
+ const announcement = document.createElement('div');
196
+ announcement.setAttribute('aria-live', 'polite');
197
+ announcement.setAttribute('aria-atomic', 'true');
198
+ announcement.className = 'sr-only';
199
+ announcement.textContent = message;
200
+ document.body.appendChild(announcement);
201
+ // Remove after announcement
202
+ setTimeout(() => {
203
+ document.body.removeChild(announcement);
204
+ }, 1000);
205
+ }
206
+ resetSpeechProperties() {
207
+ // Reset all speech-related properties when speech recognition is disabled
208
+ this.isMicOn = false;
209
+ this.selectedSpeechLanguageDisplayText = '';
210
+ // Clean up any active speech recognition subscriptions
211
+ if (this.subscription) {
212
+ this.subscription.unsubscribe();
213
+ this.subscription = null;
214
+ }
215
+ // Remove speech language form control if it exists
216
+ const languageControlName = 'Language_' + this.options.name;
217
+ if (this.group?.get(languageControlName)) {
218
+ this.group.removeControl(languageControlName);
219
+ }
220
+ }
140
221
  trimControlValue() {
141
222
  let originalValue = this.controlUtility.trimControlValue(this.textAreaFormControl.value);
142
223
  this.textAreaFormControl.patchValue(originalValue);
@@ -144,8 +225,53 @@ export class TextAreaComponent {
144
225
  this.controlUtility.patchControlValue(originalValue, this.options.patchFunction, this.options.patchPath);
145
226
  }
146
227
  }
228
+ onKeyDown(event) {
229
+ const textarea = event.target;
230
+ const currentValue = textarea.value || '';
231
+ const key = event.key;
232
+ // Allow navigation keys (arrows, home, end, etc.)
233
+ const allowedKeys = ['Backspace', 'Delete', 'Tab', 'Escape', 'Enter', 'Home', 'End', 'ArrowLeft', 'ArrowRight', 'ArrowUp', 'ArrowDown'];
234
+ // Allow Ctrl/Cmd + keys (copy, paste, select all, etc.)
235
+ if (event.ctrlKey || event.metaKey) {
236
+ return; // Allow all Ctrl/Cmd combinations
237
+ }
238
+ // If it's a navigation key, allow it
239
+ if (allowedKeys.includes(key)) {
240
+ // Special handling for word count on Backspace
241
+ if (key === 'Backspace' && this.options.maxWordCount > 0) {
242
+ return; // Always allow backspace for word count correction
243
+ }
244
+ return;
245
+ }
246
+ // Check word count limit
247
+ if (this.options.maxWordCount > 0) {
248
+ const currentWordCount = currentValue.trim() ? currentValue.trim().split(/\s+/).length : 0;
249
+ if (currentWordCount >= this.options.maxWordCount && key !== 'Backspace' && key !== 'Delete') {
250
+ // Check if adding this character would create a new word
251
+ const cursorPosition = textarea.selectionStart;
252
+ const charBefore = cursorPosition > 0 ? currentValue[cursorPosition - 1] : '';
253
+ const charAfter = cursorPosition < currentValue.length ? currentValue[cursorPosition] : '';
254
+ // If we're typing a space or the character before/after is a space, this might create a new word
255
+ if (key === ' ' || (/\s/.test(charBefore) && !(/\s/.test(key)))) {
256
+ event.preventDefault();
257
+ return;
258
+ }
259
+ }
260
+ }
261
+ // Check character count limit
262
+ if (this.options.maxLength && currentValue.length >= this.options.maxLength) {
263
+ // Only allow if we have selected text (which will be replaced) or navigation keys
264
+ const hasSelection = textarea.selectionStart !== textarea.selectionEnd;
265
+ if (!hasSelection && !allowedKeys.includes(key)) {
266
+ event.preventDefault();
267
+ return;
268
+ }
269
+ }
270
+ }
147
271
  copyInputMessage(inputElement) {
148
272
  this.controlUtility.CopyInputMessage(inputElement);
273
+ // Announce to screen readers
274
+ this.announceToScreenReader('Text copied to clipboard');
149
275
  }
150
276
  onTextChange() {
151
277
  if (this.textAreaFormControl.value == '') {
@@ -158,7 +284,7 @@ export class TextAreaComponent {
158
284
  if (this.wordCountArray > this.options.maxWordCount) {
159
285
  this.wordCount = this.options.maxWordCount;
160
286
  this.textAreaFormControl.setErrors({
161
- errorMassage: ` Word count must be less then or equal ${this.options.maxWordCount}`
287
+ errorMessage: `Word count must be less than or equal to ${this.options.maxWordCount}`
162
288
  });
163
289
  this.textAreaFormControl.markAsTouched();
164
290
  this.textAreaFormControl.invalid;
@@ -169,30 +295,47 @@ export class TextAreaComponent {
169
295
  }
170
296
  }
171
297
  //Check for maxlength limit count
172
- //MaxLength should be gretaer than or equals chars limit so that minCharsLimit would be >= 0
298
+ //MaxLength should be greater than or equals chars limit so that minCharsLimit would be >= 0
173
299
  if (this.options.maxLength && this.minCharsLimit >= 0) {
174
- this.currentCharsCount = this.textAreaFormControl.value.length;
175
- if (this.currentCharsCount > this.minCharsLimit) {
176
- this.showCharsLimitMsg = true;
177
- this.hasCharsLimitValidationError = true;
178
- if (this.currentCharsCount == this.options.maxLength)
179
- this.charsLimitMsgClass = 'danger';
180
- else
181
- this.charsLimitMsgClass = 'warning';
300
+ // Check if value exists and is not empty
301
+ const controlValue = this.textAreaFormControl.value;
302
+ if (controlValue && controlValue.trim().length > 0) {
303
+ this.currentCharsCount = controlValue.length;
304
+ if (this.currentCharsCount > this.minCharsLimit) {
305
+ this.showCharsLimitMsg = true;
306
+ this.hasCharsLimitValidationError = true;
307
+ if (this.currentCharsCount == this.options.maxLength)
308
+ this.charsLimitMsgClass = 'danger';
309
+ else
310
+ this.charsLimitMsgClass = 'warning';
311
+ // Only generate warning message when we actually want to show it
312
+ let max = this.options.maxLength;
313
+ let current = this.currentCharsCount;
314
+ let msg = this.utilityService.getResourceValue('MaxLengthLimitWarning');
315
+ this.maxLimitWarningMsg = msg
316
+ .replace('${max}', max.toString())
317
+ .replace('${current}', current.toString());
318
+ }
319
+ else {
320
+ this.showCharsLimitMsg = false;
321
+ this.hasCharsLimitValidationError = false;
322
+ }
182
323
  }
183
324
  else {
325
+ // Reset everything when value is empty
326
+ this.currentCharsCount = 0;
184
327
  this.showCharsLimitMsg = false;
185
328
  this.hasCharsLimitValidationError = false;
329
+ this.maxLimitWarningMsg = '';
186
330
  }
187
- let max = this.options.maxLength;
188
- let current = this.currentCharsCount;
189
- let msg = this.utilityService.getResourceValue('MaxLengthLimitWarning');
190
- // Replace placeholders with actual values
191
- this.maxLimitWarningMsg = msg
192
- .replace('${max}', max.toString())
193
- .replace('${current}', current.toString());
194
331
  }
195
332
  this.onChange.emit(this.textAreaFormControl.value);
333
+ // Update accessibility attributes
334
+ this.updateAriaDescribedBy();
335
+ // Announce character limit warnings to screen readers
336
+ if (this.showCharsLimitMsg && this.charsLimitMsgClass === 'danger') {
337
+ this.announceToScreenReader(`Character limit reached: ${this.maxLimitWarningMsg}`);
338
+ }
196
339
  }
197
340
  onFocus(isFocus) {
198
341
  this.isShowWordCount = isFocus;
@@ -207,6 +350,10 @@ export class TextAreaComponent {
207
350
  }
208
351
  //region Speech Recognition
209
352
  setSpeechLanguage() {
353
+ // Guard: Only execute if speech recognition is enabled
354
+ if (!this.options.enableSpeechRecognition) {
355
+ return;
356
+ }
210
357
  const languageControlName = 'Language_' + this.options.name;
211
358
  if (this.options.autoSaveSpeechLanguagetoLocalStorage) {
212
359
  let savedLanguage = localStorage.getItem('speechLanguage');
@@ -222,9 +369,14 @@ export class TextAreaComponent {
222
369
  this.loadSelectedSpeechLanguage();
223
370
  }
224
371
  this.group.get(languageControlName).setValue(this.options.selectedSpeechLanguage);
225
- this.selectedSpeechLanguageDisplayText = this.options.speechLanguages.find((l) => l.dialect == this.options.selectedSpeechLanguage).prefix;
372
+ const language = this.options.speechLanguages?.find((l) => l.dialect == this.options.selectedSpeechLanguage);
373
+ this.selectedSpeechLanguageDisplayText = language?.prefix || '';
226
374
  }
227
375
  loadSelectedSpeechLanguage() {
376
+ // Guard: Only execute if speech recognition is enabled
377
+ if (!this.options.enableSpeechRecognition) {
378
+ return;
379
+ }
228
380
  if (!this.options.selectedSpeechLanguage) {
229
381
  if (this.currentLanguage == 'en' &&
230
382
  this.options.speechLanguages.some((language) => language.englishName === 'English')) {
@@ -240,13 +392,21 @@ export class TextAreaComponent {
240
392
  }
241
393
  }
242
394
  startSpeechRecognition() {
395
+ // Guard: Only execute if speech recognition is enabled
396
+ if (!this.options.enableSpeechRecognition) {
397
+ return;
398
+ }
243
399
  if (!this.speechRecognitionService.isSupported) {
244
- this.utilityService.notifyErrorMessage(this.utilityService.getResourceValue('BrowserNotSupportSpeechRecognition'));
400
+ const errorMessage = this.utilityService.getResourceValue('BrowserNotSupportSpeechRecognition');
401
+ this.utilityService.notifyErrorMessage(errorMessage);
402
+ this.announceToScreenReader(errorMessage);
245
403
  return;
246
404
  }
247
405
  //Disable Select Language
248
406
  this.enableOrDisableLanguageSelect(false);
249
407
  this.isMicOn = true;
408
+ // Announce to screen readers
409
+ this.announceToScreenReader('Speech recognition started. Speak now.');
250
410
  this.subscription = this.speechRecognitionService
251
411
  .startListening(this.options.selectedSpeechLanguage)
252
412
  .subscribe({
@@ -275,10 +435,15 @@ export class TextAreaComponent {
275
435
  //Enable Select Language
276
436
  this.enableOrDisableLanguageSelect();
277
437
  this.isMicOn = false;
438
+ this.announceToScreenReader('Speech recognition stopped.');
278
439
  }
279
440
  });
280
441
  }
281
442
  stopSpeechRecognition() {
443
+ // Guard: Only execute if speech recognition is enabled
444
+ if (!this.options.enableSpeechRecognition) {
445
+ return;
446
+ }
282
447
  this.enableOrDisableLanguageSelect();
283
448
  if (!this.speechRecognitionService.isSupported) {
284
449
  return;
@@ -288,6 +453,8 @@ export class TextAreaComponent {
288
453
  if (this.subscription) {
289
454
  this.subscription.unsubscribe();
290
455
  }
456
+ // Announce to screen readers
457
+ this.announceToScreenReader('Speech recognition stopped.');
291
458
  }
292
459
  fireOnChange(text) {
293
460
  if (this.onChange) {
@@ -295,13 +462,48 @@ export class TextAreaComponent {
295
462
  }
296
463
  }
297
464
  ngOnDestroy() {
465
+ // Always clean up subscriptions
466
+ if (this.subscription) {
467
+ this.subscription.unsubscribe();
468
+ }
469
+ if (this.valueChangesSubscription) {
470
+ this.valueChangesSubscription.unsubscribe();
471
+ }
472
+ // Only call speech recognition cleanup if it was enabled
298
473
  if (this.options.enableSpeechRecognition) {
299
474
  this.stopSpeechRecognition();
300
475
  }
301
476
  }
477
+ // Keyboard accessibility for speech recognition controls
478
+ onMicKeydown(event, action) {
479
+ // Guard: Only execute if speech recognition is enabled
480
+ if (!this.options.enableSpeechRecognition) {
481
+ return;
482
+ }
483
+ if (event.key === 'Enter' || event.key === ' ') {
484
+ event.preventDefault();
485
+ if (action === 'start') {
486
+ this.startSpeechRecognition();
487
+ }
488
+ else {
489
+ this.stopSpeechRecognition();
490
+ }
491
+ }
492
+ }
493
+ onCopyKeydown(event, inputElement) {
494
+ if (event.key === 'Enter' || event.key === ' ') {
495
+ event.preventDefault();
496
+ this.copyInputMessage(inputElement);
497
+ }
498
+ }
302
499
  onSpeechLanguageChange(event) {
500
+ // Guard: Only execute if speech recognition is enabled
501
+ if (!this.options.enableSpeechRecognition) {
502
+ return;
503
+ }
303
504
  let selectedLang_Dialect = event.target.value;
304
- this.selectedSpeechLanguageDisplayText = this.options.speechLanguages.find((l) => l.dialect == selectedLang_Dialect).prefix;
505
+ const language = this.options.speechLanguages?.find((l) => l.dialect == selectedLang_Dialect);
506
+ this.selectedSpeechLanguageDisplayText = language?.prefix || '';
305
507
  this.options.selectedSpeechLanguage = selectedLang_Dialect;
306
508
  const languageControlName = 'Language_' + this.options.name;
307
509
  let select = this.group.get(languageControlName);
@@ -309,8 +511,14 @@ export class TextAreaComponent {
309
511
  if (this.options.autoSaveSpeechLanguagetoLocalStorage) {
310
512
  localStorage.setItem('speechLanguage', selectedLang_Dialect);
311
513
  }
514
+ // Announce language change to screen readers
515
+ this.announceToScreenReader(`Speech recognition language changed to ${language?.name || selectedLang_Dialect}`);
312
516
  }
313
517
  enableOrDisableLanguageSelect(isEnabled = true) {
518
+ // Guard: Only execute if speech recognition is enabled
519
+ if (!this.options.enableSpeechRecognition) {
520
+ return;
521
+ }
314
522
  const languageControlName = 'Language_' + this.options.name;
315
523
  let select = this.group.get(languageControlName);
316
524
  if (isEnabled) {
@@ -320,19 +528,23 @@ export class TextAreaComponent {
320
528
  select.disable();
321
529
  }
322
530
  }
323
- static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "17.3.12", ngImport: i0, type: TextAreaComponent, deps: [{ token: i1.ControlUtility }, { token: i2.ControlContainer, optional: true }, { token: i2.FormGroupDirective }, { token: i3.UtilityService }, { token: i3.ControlValidationService }, { token: i4.GlobalSettings }, { token: i3.SpeechRecognitionService }, { token: i3.LanguageService }], target: i0.ɵɵFactoryTarget.Component }); }
324
- static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "17.3.12", type: TextAreaComponent, selector: "BBSF-TextArea", inputs: { group: "group", options: "options" }, outputs: { onChange: "onChange" }, ngImport: i0, template: "<div class=\"form-group bbsf-control bbsf-textarea\" [formGroup]=\"group\">\r\n <div [ngClass]=\"(options.viewType==1)?'bbsf-vertical':'bbsf-horizontal'\">\r\n <!--label-->\r\n <label *ngIf=\"!options.hideLabel\" class=\"bbsf-label {{options.labelExtraClasses}}\">\r\n {{options.labelValue}}\r\n <!--Asterisk-->\r\n <span *ngIf=\"((options.showAsterisk&&options.isRequired)||(options.isRequired))&&!options.isReadonly\"\r\n class=\"text-danger\">*</span>\r\n </label>\r\n <div *ngIf=\"!options.isReadonly\" class=\"bbsf-input-container\" [ngClass]=\"{\r\n 'p-120px': options.enableSpeechRecognition && options.enableCopyToClipboard,\r\n 'p-80px': options.enableSpeechRecognition && !options.enableCopyToClipboard,\r\n 'p-40px': !options.enableSpeechRecognition && options.enableCopyToClipboard\r\n }\">\r\n <!--input-->\r\n <textarea class=\"form-control {{options.extraClasses}}\" (focus)=\"onFocus(true)\" (focusout)=\"onFocus(false)\"\r\n [dir]=\"textDir\" aria-describedby=\"email-error\" aria-invalid=\"true\" formControlName=\"{{options.name}}\"\r\n [class.is-invalid]=\"textAreaFormControl.invalid && textAreaFormControl.touched\"\r\n placeholder=\"{{options.placeholder}}\" id=\"{{options.name}}\" autocomplete=\"{{options.autoComplete}}\"\r\n (change)=\"trimControlValue()\" rows=\"{{options.rows}}\" (keyup)=\"onTextChange()\" cols=\"{{options.cols}}\"\r\n maxlength=\"{{options.maxLength}}\" minlength=\"{{options.minLength}}\" [(ngModel)]=\"options.value\"\r\n (keydown)=\"wordCountArray>options.maxWordCount&&$event.keyCode !=8?$event.preventDefault():null\"\r\n #TextAreainput></textarea>\r\n <!--CopyToClipboard-->\r\n <div class=\"copy-clipboard\" *ngIf=\"options.enableCopyToClipboard\" (click)=\"copyInputMessage(TextAreainput)\">\r\n <i class=\"fas fa-copy\"></i>\r\n </div>\r\n <div [ngClass]=\"{'expanded': isFocused}\" class=\"language-container {{options.extraClassMicLanguage}}\" *ngIf=\"options.enableSpeechRecognition\">\r\n <span class=\"svg-icon svg-icon-5\" [inlineSVG]=\"options.iconMic? options.iconMic : './src/assets/images/mic.svg'\" (click)=\"startSpeechRecognition()\"\r\n *ngIf=\"!isMicOn\">\r\n </span>\r\n <span class=\"svg-icon svg-icon-5\" [inlineSVG]=\"options.iconMicOff? options.iconMicOff : './src/assets/images/mic-off.svg'\" (click)=\"stopSpeechRecognition()\"\r\n *ngIf=\"isMicOn\">\r\n </span>\r\n <div>\r\n <span class=\"language-text\">{{ selectedSpeechLanguageDisplayText }}</span>\r\n <select class=\"language-select\" [formControlName]=\"'Language_'+options.name\" (change)=\"onSpeechLanguageChange($event)\">\r\n <option *ngFor=\"let language of options.speechLanguages\" [value]=\"language.dialect\">\r\n {{language.name}}\r\n </option>\r\n </select>\r\n\r\n </div>\r\n\r\n\r\n </div>\r\n </div>\r\n <!-- readonly -->\r\n <div *ngIf=\"options.isReadonly\"><span class=\"readonly-view\">{{options.value}}</span>\r\n </div>\r\n <div class=\"subtext-container\">\r\n <!--wordCount-->\r\n <div class=\"bbsf-word-count\" *ngIf=\"options.maxWordCount>0&&isShowWordCount\">\r\n {{wordCount}}/{{options.maxWordCount}} Words</div>\r\n <!-- CharsLimitMsg-->\r\n <div class=\"bbsf-character-count\" *ngIf=\"showCharsLimitMsg\"\r\n [ngClass]=\"{'badge-light-warning': charsLimitMsgClass === 'warning', 'badge-light-danger' : charsLimitMsgClass === 'danger' }\">\r\n {{maxLimitWarningMsg}}\r\n </div>\r\n <!-- LabelDescription-->\r\n <div class=\"bbsf-control-desc\" *ngIf=\"options.labelDescription!=null\">{{options.labelDescription}}</div>\r\n <!-- requiredText-->\r\n <div class=\"bbsf-validation\" [dir]=\"textDir\" *ngIf=\"(textAreaFormControl.invalid && textAreaFormControl.touched)\">\r\n {{getErrorValidation(textAreaFormControl.errors|keyvalue)}}\r\n </div>\r\n </div>\r\n <div *ngIf=\"(group.valid&&group.dirty&&group.touched )||(group.untouched&&group.invalid&&group.dirty) \">\r\n {{resetError()}}</div>\r\n </div>\r\n", dependencies: [{ kind: "directive", type: i5.NgClass, selector: "[ngClass]", inputs: ["class", "ngClass"] }, { kind: "directive", type: i5.NgForOf, selector: "[ngFor][ngForOf]", inputs: ["ngForOf", "ngForTrackBy", "ngForTemplate"] }, { kind: "directive", type: i5.NgIf, selector: "[ngIf]", inputs: ["ngIf", "ngIfThen", "ngIfElse"] }, { kind: "directive", type: i6.Dir, selector: "[dir]", inputs: ["dir"], outputs: ["dirChange"], exportAs: ["dir"] }, { kind: "directive", type: i7.NativeElementInjectorDirective, selector: "[ngModel], [formControl], [formControlName]" }, { kind: "directive", type: i2.NgSelectOption, selector: "option", inputs: ["ngValue", "value"] }, { kind: "directive", type: i2.ɵNgSelectMultipleOption, selector: "option", inputs: ["ngValue", "value"] }, { kind: "directive", type: i2.DefaultValueAccessor, selector: "input:not([type=checkbox])[formControlName],textarea[formControlName],input:not([type=checkbox])[formControl],textarea[formControl],input:not([type=checkbox])[ngModel],textarea[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i2.SelectControlValueAccessor, selector: "select:not([multiple])[formControlName],select:not([multiple])[formControl],select:not([multiple])[ngModel]", inputs: ["compareWith"] }, { kind: "directive", type: i2.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i2.NgControlStatusGroup, selector: "[formGroupName],[formArrayName],[ngModelGroup],[formGroup],form:not([ngNoForm]),[ngForm]" }, { kind: "directive", type: i2.MinLengthValidator, selector: "[minlength][formControlName],[minlength][formControl],[minlength][ngModel]", inputs: ["minlength"] }, { kind: "directive", type: i2.MaxLengthValidator, selector: "[maxlength][formControlName],[maxlength][formControl],[maxlength][ngModel]", inputs: ["maxlength"] }, { kind: "directive", type: i2.FormGroupDirective, selector: "[formGroup]", inputs: ["formGroup"], outputs: ["ngSubmit"], exportAs: ["ngForm"] }, { kind: "directive", type: i2.FormControlName, selector: "[formControlName]", inputs: ["formControlName", "disabled", "ngModel"], outputs: ["ngModelChange"] }, { kind: "directive", type: i8.InlineSVGDirective, selector: "[inlineSVG]", inputs: ["inlineSVG", "resolveSVGUrl", "replaceContents", "prepend", "injectComponent", "cacheSVG", "setSVGAttributes", "removeSVGAttributes", "forceEvalStyles", "evalScripts", "fallbackImgUrl", "fallbackSVG", "onSVGLoaded"], outputs: ["onSVGInserted", "onSVGFailed"] }, { kind: "pipe", type: i5.KeyValuePipe, name: "keyvalue" }] }); }
531
+ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "17.3.12", ngImport: i0, type: TextAreaComponent, deps: [{ token: i1.ControlUtility }, { token: i2.ControlContainer, optional: true, skipSelf: true }, { token: i2.FormGroupDirective, optional: true }, { token: i3.UtilityService }, { token: i3.ControlValidationService }, { token: i1.GlobalSettings }, { token: i3.SpeechRecognitionService }, { token: i3.LanguageService }], target: i0.ɵɵFactoryTarget.Component }); }
532
+ static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "17.3.12", type: TextAreaComponent, selector: "BBSF-TextArea", inputs: { group: "group", options: "options" }, outputs: { onChange: "onChange" }, ngImport: i0, template: "<div class=\"form-group bbsf-control bbsf-textarea\" [formGroup]=\"group\">\r\n <div [ngClass]=\"(options.viewType==1)?'bbsf-vertical':'bbsf-horizontal'\">\r\n <!--label-->\r\n <label *ngIf=\"!options.hideLabel\" class=\"bbsf-label {{options.labelExtraClasses}}\">\r\n {{options.labelValue}}\r\n <!--Asterisk-->\r\n <span *ngIf=\"((options.showAsterisk&&options.isRequired)||(options.isRequired))&&!options.isReadonly\"\r\n class=\"text-danger\">*</span>\r\n </label>\r\n <div *ngIf=\"!options.isReadonly\" class=\"bbsf-input-container\" [ngClass]=\"{\r\n 'p-120px': options.enableSpeechRecognition && options.enableCopyToClipboard,\r\n 'p-80px': options.enableSpeechRecognition && !options.enableCopyToClipboard,\r\n 'p-40px': !options.enableSpeechRecognition && options.enableCopyToClipboard\r\n }\">\r\n <!--input-->\r\n <textarea class=\"form-control {{options.extraClasses}}\" (focus)=\"onFocus(true)\" (focusout)=\"onFocus(false)\"\r\n [dir]=\"textDir\" [attr.aria-invalid]=\"textAreaFormControl.invalid && textAreaFormControl.touched\"\r\n [attr.aria-describedby]=\"ariaDescribedBy\" [attr.aria-label]=\"options.labelValue || options.placeholder\"\r\n formControlName=\"{{options.name}}\"\r\n [class.is-invalid]=\"textAreaFormControl.invalid && textAreaFormControl.touched\"\r\n placeholder=\"{{options.placeholder}}\" id=\"{{options.name}}\" autocomplete=\"{{options.autoComplete}}\"\r\n (change)=\"trimControlValue()\" rows=\"{{options.rows}}\" (keyup)=\"onTextChange()\" cols=\"{{options.cols}}\"\r\n [attr.minlength]=\"options.minLength\" [(ngModel)]=\"options.value\" (keydown)=\"onKeyDown($event)\"\r\n [attr.maxlength]=\"options.maxLength\" role=\"textbox\" [attr.aria-multiline]=\"true\" #TextAreainput></textarea>\r\n <!--CopyToClipboard-->\r\n <button type=\"button\" class=\"copy-clipboard\" *ngIf=\"options.enableCopyToClipboard\"\r\n (click)=\"copyInputMessage(TextAreainput)\" (keydown)=\"onCopyKeydown($event, TextAreainput)\"\r\n [attr.aria-label]=\"'Copy text to clipboard'\" title=\"Copy text to clipboard\" tabindex=\"0\">\r\n <i class=\"fas fa-copy\" aria-hidden=\"true\"></i>\r\n </button>\r\n <div [ngClass]=\"{'expanded': isFocused}\" class=\"language-container {{options.extraClassMicLanguage}}\"\r\n *ngIf=\"options.enableSpeechRecognition\" role=\"region\" [attr.aria-label]=\"'Speech recognition controls'\">\r\n\r\n <!-- Start Speech Recognition Button -->\r\n <button type=\"button\" class=\"svg-icon svg-icon-5 speech-control-btn\"\r\n [inlineSVG]=\"options.iconMic || 'assets/bbsf-controls/images/mic.svg'\" (click)=\"startSpeechRecognition()\"\r\n (keydown)=\"onMicKeydown($event, 'start')\" *ngIf=\"options.enableSpeechRecognition && !isMicOn\"\r\n [attr.aria-label]=\"'Start speech recognition'\" title=\"Start speech recognition\" tabindex=\"0\"\r\n [attr.aria-pressed]=\"false\">\r\n </button>\r\n\r\n <!-- Stop Speech Recognition Button -->\r\n <button type=\"button\" class=\"svg-icon svg-icon-5 speech-control-btn\"\r\n [inlineSVG]=\"options.iconMicOff || 'assets/bbsf-controls/images/mic-off.svg'\"\r\n (click)=\"stopSpeechRecognition()\" (keydown)=\"onMicKeydown($event, 'stop')\"\r\n *ngIf=\"options.enableSpeechRecognition && isMicOn\" [attr.aria-label]=\"'Stop speech recognition'\"\r\n title=\"Stop speech recognition\" tabindex=\"0\" [attr.aria-pressed]=\"true\">\r\n </button>\r\n\r\n <div class=\"language-controls\">\r\n <span class=\"language-text\" [attr.id]=\"options.name + '-language-display'\"\r\n aria-live=\"polite\">{{ options.enableSpeechRecognition ? selectedSpeechLanguageDisplayText : '' }}</span>\r\n\r\n <label [for]=\"'Language_'+options.name\" class=\"sr-only\">\r\n Select speech recognition language\r\n </label>\r\n <select class=\"language-select\" [formControlName]=\"'Language_'+options.name\" [id]=\"'Language_'+options.name\"\r\n (change)=\"onSpeechLanguageChange($event)\" [attr.aria-describedby]=\"options.name + '-language-display'\">\r\n <option *ngFor=\"let language of options.speechLanguages\" [value]=\"language.dialect\">\r\n {{language.name}}\r\n </option>\r\n </select>\r\n </div>\r\n </div>\r\n </div>\r\n <!-- readonly -->\r\n <div *ngIf=\"options.isReadonly\"><span class=\"readonly-view\">{{options.value}}</span>\r\n </div>\r\n <div class=\"subtext-container\">\r\n <!--wordCount-->\r\n <div class=\"bbsf-word-count\" *ngIf=\"options.maxWordCount>0&&isShowWordCount\" [attr.id]=\"wordCountId\"\r\n aria-live=\"polite\" [attr.aria-label]=\"'Word count: ' + wordCount + ' of ' + options.maxWordCount + ' words'\">\r\n {{wordCount}}/{{options.maxWordCount}} Words\r\n </div>\r\n\r\n <!-- CharsLimitMsg-->\r\n <div class=\"bbsf-character-count\" *ngIf=\"showCharsLimitMsg\" [attr.id]=\"characterCountId\" aria-live=\"polite\"\r\n [attr.aria-atomic]=\"true\"\r\n [ngClass]=\"{'badge-light-warning': charsLimitMsgClass === 'warning', 'badge-light-danger' : charsLimitMsgClass === 'danger' }\">\r\n {{maxLimitWarningMsg}}\r\n </div>\r\n\r\n <!-- LabelDescription-->\r\n <div class=\"bbsf-control-desc\" *ngIf=\"options.labelDescription!=null\" [attr.id]=\"options.name + '-description'\">\r\n {{options.labelDescription}}\r\n </div>\r\n\r\n <!-- requiredText-->\r\n <div class=\"bbsf-validation\" [dir]=\"textDir\" *ngIf=\"(textAreaFormControl.invalid && textAreaFormControl.touched)\"\r\n [attr.id]=\"errorMessageId\" role=\"alert\" aria-live=\"assertive\" [attr.aria-atomic]=\"true\">\r\n {{getErrorValidation(textAreaFormControl.errors|keyvalue)}}\r\n </div>\r\n </div>\r\n <div *ngIf=\"(group.valid&&group.dirty&&group.touched )||(group.untouched&&group.invalid&&group.dirty) \">\r\n {{resetError()}}</div>\r\n </div>", dependencies: [{ kind: "directive", type: i4.NgClass, selector: "[ngClass]", inputs: ["class", "ngClass"] }, { kind: "directive", type: i4.NgForOf, selector: "[ngFor][ngForOf]", inputs: ["ngForOf", "ngForTrackBy", "ngForTemplate"] }, { kind: "directive", type: i4.NgIf, selector: "[ngIf]", inputs: ["ngIf", "ngIfThen", "ngIfElse"] }, { kind: "directive", type: i5.Dir, selector: "[dir]", inputs: ["dir"], outputs: ["dirChange"], exportAs: ["dir"] }, { kind: "directive", type: i6.NativeElementInjectorDirective, selector: "[ngModel], [formControl], [formControlName]" }, { kind: "directive", type: i2.NgSelectOption, selector: "option", inputs: ["ngValue", "value"] }, { kind: "directive", type: i2.ɵNgSelectMultipleOption, selector: "option", inputs: ["ngValue", "value"] }, { kind: "directive", type: i2.DefaultValueAccessor, selector: "input:not([type=checkbox])[formControlName],textarea[formControlName],input:not([type=checkbox])[formControl],textarea[formControl],input:not([type=checkbox])[ngModel],textarea[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i2.SelectControlValueAccessor, selector: "select:not([multiple])[formControlName],select:not([multiple])[formControl],select:not([multiple])[ngModel]", inputs: ["compareWith"] }, { kind: "directive", type: i2.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i2.NgControlStatusGroup, selector: "[formGroupName],[formArrayName],[ngModelGroup],[formGroup],form:not([ngNoForm]),[ngForm]" }, { kind: "directive", type: i2.FormGroupDirective, selector: "[formGroup]", inputs: ["formGroup"], outputs: ["ngSubmit"], exportAs: ["ngForm"] }, { kind: "directive", type: i2.FormControlName, selector: "[formControlName]", inputs: ["formControlName", "disabled", "ngModel"], outputs: ["ngModelChange"] }, { kind: "directive", type: i7.InlineSVGDirective, selector: "[inlineSVG]", inputs: ["inlineSVG", "resolveSVGUrl", "replaceContents", "prepend", "injectComponent", "cacheSVG", "setSVGAttributes", "removeSVGAttributes", "forceEvalStyles", "evalScripts", "fallbackImgUrl", "fallbackSVG", "onSVGLoaded"], outputs: ["onSVGInserted", "onSVGFailed"] }, { kind: "pipe", type: i4.KeyValuePipe, name: "keyvalue" }] }); }
325
533
  }
326
534
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "17.3.12", ngImport: i0, type: TextAreaComponent, decorators: [{
327
535
  type: Component,
328
- args: [{ selector: 'BBSF-TextArea', template: "<div class=\"form-group bbsf-control bbsf-textarea\" [formGroup]=\"group\">\r\n <div [ngClass]=\"(options.viewType==1)?'bbsf-vertical':'bbsf-horizontal'\">\r\n <!--label-->\r\n <label *ngIf=\"!options.hideLabel\" class=\"bbsf-label {{options.labelExtraClasses}}\">\r\n {{options.labelValue}}\r\n <!--Asterisk-->\r\n <span *ngIf=\"((options.showAsterisk&&options.isRequired)||(options.isRequired))&&!options.isReadonly\"\r\n class=\"text-danger\">*</span>\r\n </label>\r\n <div *ngIf=\"!options.isReadonly\" class=\"bbsf-input-container\" [ngClass]=\"{\r\n 'p-120px': options.enableSpeechRecognition && options.enableCopyToClipboard,\r\n 'p-80px': options.enableSpeechRecognition && !options.enableCopyToClipboard,\r\n 'p-40px': !options.enableSpeechRecognition && options.enableCopyToClipboard\r\n }\">\r\n <!--input-->\r\n <textarea class=\"form-control {{options.extraClasses}}\" (focus)=\"onFocus(true)\" (focusout)=\"onFocus(false)\"\r\n [dir]=\"textDir\" aria-describedby=\"email-error\" aria-invalid=\"true\" formControlName=\"{{options.name}}\"\r\n [class.is-invalid]=\"textAreaFormControl.invalid && textAreaFormControl.touched\"\r\n placeholder=\"{{options.placeholder}}\" id=\"{{options.name}}\" autocomplete=\"{{options.autoComplete}}\"\r\n (change)=\"trimControlValue()\" rows=\"{{options.rows}}\" (keyup)=\"onTextChange()\" cols=\"{{options.cols}}\"\r\n maxlength=\"{{options.maxLength}}\" minlength=\"{{options.minLength}}\" [(ngModel)]=\"options.value\"\r\n (keydown)=\"wordCountArray>options.maxWordCount&&$event.keyCode !=8?$event.preventDefault():null\"\r\n #TextAreainput></textarea>\r\n <!--CopyToClipboard-->\r\n <div class=\"copy-clipboard\" *ngIf=\"options.enableCopyToClipboard\" (click)=\"copyInputMessage(TextAreainput)\">\r\n <i class=\"fas fa-copy\"></i>\r\n </div>\r\n <div [ngClass]=\"{'expanded': isFocused}\" class=\"language-container {{options.extraClassMicLanguage}}\" *ngIf=\"options.enableSpeechRecognition\">\r\n <span class=\"svg-icon svg-icon-5\" [inlineSVG]=\"options.iconMic? options.iconMic : './src/assets/images/mic.svg'\" (click)=\"startSpeechRecognition()\"\r\n *ngIf=\"!isMicOn\">\r\n </span>\r\n <span class=\"svg-icon svg-icon-5\" [inlineSVG]=\"options.iconMicOff? options.iconMicOff : './src/assets/images/mic-off.svg'\" (click)=\"stopSpeechRecognition()\"\r\n *ngIf=\"isMicOn\">\r\n </span>\r\n <div>\r\n <span class=\"language-text\">{{ selectedSpeechLanguageDisplayText }}</span>\r\n <select class=\"language-select\" [formControlName]=\"'Language_'+options.name\" (change)=\"onSpeechLanguageChange($event)\">\r\n <option *ngFor=\"let language of options.speechLanguages\" [value]=\"language.dialect\">\r\n {{language.name}}\r\n </option>\r\n </select>\r\n\r\n </div>\r\n\r\n\r\n </div>\r\n </div>\r\n <!-- readonly -->\r\n <div *ngIf=\"options.isReadonly\"><span class=\"readonly-view\">{{options.value}}</span>\r\n </div>\r\n <div class=\"subtext-container\">\r\n <!--wordCount-->\r\n <div class=\"bbsf-word-count\" *ngIf=\"options.maxWordCount>0&&isShowWordCount\">\r\n {{wordCount}}/{{options.maxWordCount}} Words</div>\r\n <!-- CharsLimitMsg-->\r\n <div class=\"bbsf-character-count\" *ngIf=\"showCharsLimitMsg\"\r\n [ngClass]=\"{'badge-light-warning': charsLimitMsgClass === 'warning', 'badge-light-danger' : charsLimitMsgClass === 'danger' }\">\r\n {{maxLimitWarningMsg}}\r\n </div>\r\n <!-- LabelDescription-->\r\n <div class=\"bbsf-control-desc\" *ngIf=\"options.labelDescription!=null\">{{options.labelDescription}}</div>\r\n <!-- requiredText-->\r\n <div class=\"bbsf-validation\" [dir]=\"textDir\" *ngIf=\"(textAreaFormControl.invalid && textAreaFormControl.touched)\">\r\n {{getErrorValidation(textAreaFormControl.errors|keyvalue)}}\r\n </div>\r\n </div>\r\n <div *ngIf=\"(group.valid&&group.dirty&&group.touched )||(group.untouched&&group.invalid&&group.dirty) \">\r\n {{resetError()}}</div>\r\n </div>\r\n" }]
536
+ args: [{ selector: 'BBSF-TextArea', template: "<div class=\"form-group bbsf-control bbsf-textarea\" [formGroup]=\"group\">\r\n <div [ngClass]=\"(options.viewType==1)?'bbsf-vertical':'bbsf-horizontal'\">\r\n <!--label-->\r\n <label *ngIf=\"!options.hideLabel\" class=\"bbsf-label {{options.labelExtraClasses}}\">\r\n {{options.labelValue}}\r\n <!--Asterisk-->\r\n <span *ngIf=\"((options.showAsterisk&&options.isRequired)||(options.isRequired))&&!options.isReadonly\"\r\n class=\"text-danger\">*</span>\r\n </label>\r\n <div *ngIf=\"!options.isReadonly\" class=\"bbsf-input-container\" [ngClass]=\"{\r\n 'p-120px': options.enableSpeechRecognition && options.enableCopyToClipboard,\r\n 'p-80px': options.enableSpeechRecognition && !options.enableCopyToClipboard,\r\n 'p-40px': !options.enableSpeechRecognition && options.enableCopyToClipboard\r\n }\">\r\n <!--input-->\r\n <textarea class=\"form-control {{options.extraClasses}}\" (focus)=\"onFocus(true)\" (focusout)=\"onFocus(false)\"\r\n [dir]=\"textDir\" [attr.aria-invalid]=\"textAreaFormControl.invalid && textAreaFormControl.touched\"\r\n [attr.aria-describedby]=\"ariaDescribedBy\" [attr.aria-label]=\"options.labelValue || options.placeholder\"\r\n formControlName=\"{{options.name}}\"\r\n [class.is-invalid]=\"textAreaFormControl.invalid && textAreaFormControl.touched\"\r\n placeholder=\"{{options.placeholder}}\" id=\"{{options.name}}\" autocomplete=\"{{options.autoComplete}}\"\r\n (change)=\"trimControlValue()\" rows=\"{{options.rows}}\" (keyup)=\"onTextChange()\" cols=\"{{options.cols}}\"\r\n [attr.minlength]=\"options.minLength\" [(ngModel)]=\"options.value\" (keydown)=\"onKeyDown($event)\"\r\n [attr.maxlength]=\"options.maxLength\" role=\"textbox\" [attr.aria-multiline]=\"true\" #TextAreainput></textarea>\r\n <!--CopyToClipboard-->\r\n <button type=\"button\" class=\"copy-clipboard\" *ngIf=\"options.enableCopyToClipboard\"\r\n (click)=\"copyInputMessage(TextAreainput)\" (keydown)=\"onCopyKeydown($event, TextAreainput)\"\r\n [attr.aria-label]=\"'Copy text to clipboard'\" title=\"Copy text to clipboard\" tabindex=\"0\">\r\n <i class=\"fas fa-copy\" aria-hidden=\"true\"></i>\r\n </button>\r\n <div [ngClass]=\"{'expanded': isFocused}\" class=\"language-container {{options.extraClassMicLanguage}}\"\r\n *ngIf=\"options.enableSpeechRecognition\" role=\"region\" [attr.aria-label]=\"'Speech recognition controls'\">\r\n\r\n <!-- Start Speech Recognition Button -->\r\n <button type=\"button\" class=\"svg-icon svg-icon-5 speech-control-btn\"\r\n [inlineSVG]=\"options.iconMic || 'assets/bbsf-controls/images/mic.svg'\" (click)=\"startSpeechRecognition()\"\r\n (keydown)=\"onMicKeydown($event, 'start')\" *ngIf=\"options.enableSpeechRecognition && !isMicOn\"\r\n [attr.aria-label]=\"'Start speech recognition'\" title=\"Start speech recognition\" tabindex=\"0\"\r\n [attr.aria-pressed]=\"false\">\r\n </button>\r\n\r\n <!-- Stop Speech Recognition Button -->\r\n <button type=\"button\" class=\"svg-icon svg-icon-5 speech-control-btn\"\r\n [inlineSVG]=\"options.iconMicOff || 'assets/bbsf-controls/images/mic-off.svg'\"\r\n (click)=\"stopSpeechRecognition()\" (keydown)=\"onMicKeydown($event, 'stop')\"\r\n *ngIf=\"options.enableSpeechRecognition && isMicOn\" [attr.aria-label]=\"'Stop speech recognition'\"\r\n title=\"Stop speech recognition\" tabindex=\"0\" [attr.aria-pressed]=\"true\">\r\n </button>\r\n\r\n <div class=\"language-controls\">\r\n <span class=\"language-text\" [attr.id]=\"options.name + '-language-display'\"\r\n aria-live=\"polite\">{{ options.enableSpeechRecognition ? selectedSpeechLanguageDisplayText : '' }}</span>\r\n\r\n <label [for]=\"'Language_'+options.name\" class=\"sr-only\">\r\n Select speech recognition language\r\n </label>\r\n <select class=\"language-select\" [formControlName]=\"'Language_'+options.name\" [id]=\"'Language_'+options.name\"\r\n (change)=\"onSpeechLanguageChange($event)\" [attr.aria-describedby]=\"options.name + '-language-display'\">\r\n <option *ngFor=\"let language of options.speechLanguages\" [value]=\"language.dialect\">\r\n {{language.name}}\r\n </option>\r\n </select>\r\n </div>\r\n </div>\r\n </div>\r\n <!-- readonly -->\r\n <div *ngIf=\"options.isReadonly\"><span class=\"readonly-view\">{{options.value}}</span>\r\n </div>\r\n <div class=\"subtext-container\">\r\n <!--wordCount-->\r\n <div class=\"bbsf-word-count\" *ngIf=\"options.maxWordCount>0&&isShowWordCount\" [attr.id]=\"wordCountId\"\r\n aria-live=\"polite\" [attr.aria-label]=\"'Word count: ' + wordCount + ' of ' + options.maxWordCount + ' words'\">\r\n {{wordCount}}/{{options.maxWordCount}} Words\r\n </div>\r\n\r\n <!-- CharsLimitMsg-->\r\n <div class=\"bbsf-character-count\" *ngIf=\"showCharsLimitMsg\" [attr.id]=\"characterCountId\" aria-live=\"polite\"\r\n [attr.aria-atomic]=\"true\"\r\n [ngClass]=\"{'badge-light-warning': charsLimitMsgClass === 'warning', 'badge-light-danger' : charsLimitMsgClass === 'danger' }\">\r\n {{maxLimitWarningMsg}}\r\n </div>\r\n\r\n <!-- LabelDescription-->\r\n <div class=\"bbsf-control-desc\" *ngIf=\"options.labelDescription!=null\" [attr.id]=\"options.name + '-description'\">\r\n {{options.labelDescription}}\r\n </div>\r\n\r\n <!-- requiredText-->\r\n <div class=\"bbsf-validation\" [dir]=\"textDir\" *ngIf=\"(textAreaFormControl.invalid && textAreaFormControl.touched)\"\r\n [attr.id]=\"errorMessageId\" role=\"alert\" aria-live=\"assertive\" [attr.aria-atomic]=\"true\">\r\n {{getErrorValidation(textAreaFormControl.errors|keyvalue)}}\r\n </div>\r\n </div>\r\n <div *ngIf=\"(group.valid&&group.dirty&&group.touched )||(group.untouched&&group.invalid&&group.dirty) \">\r\n {{resetError()}}</div>\r\n </div>" }]
329
537
  }], ctorParameters: () => [{ type: i1.ControlUtility }, { type: i2.ControlContainer, decorators: [{
330
538
  type: Optional
331
- }] }, { type: i2.FormGroupDirective }, { type: i3.UtilityService }, { type: i3.ControlValidationService }, { type: i4.GlobalSettings }, { type: i3.SpeechRecognitionService }, { type: i3.LanguageService }], propDecorators: { group: [{
539
+ }, {
540
+ type: SkipSelf
541
+ }] }, { type: i2.FormGroupDirective, decorators: [{
542
+ type: Optional
543
+ }] }, { type: i3.UtilityService }, { type: i3.ControlValidationService }, { type: i1.GlobalSettings }, { type: i3.SpeechRecognitionService }, { type: i3.LanguageService }], propDecorators: { group: [{
332
544
  type: Input
333
545
  }], options: [{
334
546
  type: Input
335
547
  }], onChange: [{
336
548
  type: Output
337
549
  }] } });
338
- //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiVGV4dEFyZWEuY29tcG9uZW50LmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vLi4vLi4vcHJvamVjdHMvYmJzZi1jb250cm9scy9zcmMvbGliL2NvbnRyb2xzL1RleHRBcmVhL1RleHRBcmVhLmNvbXBvbmVudC50cyIsIi4uLy4uLy4uLy4uLy4uLy4uL3Byb2plY3RzL2Jic2YtY29udHJvbHMvc3JjL2xpYi9jb250cm9scy9UZXh0QXJlYS9UZXh0QXJlYS5jb21wb25lbnQuaHRtbCJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiQUFBQSxPQUFPLEVBQUUsU0FBUyxFQUFVLEtBQUssRUFBRSxRQUFRLEVBQUUsTUFBTSxFQUFFLFlBQVksRUFBMEQsTUFBTSxlQUFlLENBQUM7QUFDakosT0FBTyxFQUFFLFdBQVcsRUFBRSxVQUFVLEVBQW9FLE1BQU0sZ0JBQWdCLENBQUM7Ozs7Ozs7Ozs7QUFXM0gsTUFBTSxPQUFPLGlCQUFpQjthQUNyQiwyQkFBc0IsR0FBRyxJQUFJLEFBQVAsQ0FBUTtJQUNyQyxZQUNVLGNBQThCLEVBQ2xCLGdCQUFrQyxFQUMvQyxtQkFBdUMsRUFDdEMsY0FBOEIsRUFDOUIsd0JBQWtELEVBQ2xELGNBQThCLEVBQzlCLHdCQUFrRCxFQUNsRCxlQUFnQztRQVBoQyxtQkFBYyxHQUFkLGNBQWMsQ0FBZ0I7UUFDbEIscUJBQWdCLEdBQWhCLGdCQUFnQixDQUFrQjtRQUMvQyx3QkFBbUIsR0FBbkIsbUJBQW1CLENBQW9CO1FBQ3RDLG1CQUFjLEdBQWQsY0FBYyxDQUFnQjtRQUM5Qiw2QkFBd0IsR0FBeEIsd0JBQXdCLENBQTBCO1FBQ2xELG1CQUFjLEdBQWQsY0FBYyxDQUFnQjtRQUM5Qiw2QkFBd0IsR0FBeEIsd0JBQXdCLENBQTBCO1FBQ2xELG9CQUFlLEdBQWYsZUFBZSxDQUFpQjtRQU9oQyxhQUFRLEdBQUcsSUFBSSxZQUFZLEVBQUUsQ0FBQztRQUd4QyxjQUFTLEdBQVcsQ0FBQyxDQUFDO1FBQ3RCLG1CQUFjLEdB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Z0IsRUFBRSxvQkFBb0IsQ0FBQyxDQUFDO1NBQzlEO0lBQ0gsQ0FBQztJQUNELDZCQUE2QixDQUFDLFlBQXFCLElBQUk7UUFDckQsTUFBTSxtQkFBbUIsR0FBRyxXQUFXLEdBQUcsSUFBSSxDQUFDLE9BQU8sQ0FBQyxJQUFJLENBQUM7UUFDNUQsSUFBSSxNQUFNLEdBQUcsSUFBSSxDQUFDLEtBQUssQ0FBQyxHQUFHLENBQUMsbUJBQW1CLENBQUMsQ0FBQztRQUNqRCxJQUFJLFNBQVMsRUFBRTtZQUNiLE1BQU0sQ0FBQyxNQUFNLEVBQUUsQ0FBQztTQUNqQjthQUFNO1lBQ0wsTUFBTSxDQUFDLE9BQU8sRUFBRSxDQUFDO1NBQ2xCO0lBQ0gsQ0FBQzsrR0F0WFUsaUJBQWlCO21HQUFqQixpQkFBaUIsd0lDWjlCLCtwSUFxRUE7OzRGRHpEYSxpQkFBaUI7a0JBSjdCLFNBQVM7K0JBQ0UsZUFBZTs7MEJBT3RCLFFBQVE7Z1BBV0YsS0FBSztzQkFBYixLQUFLO2dCQUNHLE9BQU87c0JBQWYsS0FBSztnQkFDSSxRQUFRO3NCQUFqQixNQUFNIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgQ29tcG9uZW50LCBPbkluaXQsIElucHV0LCBPcHRpb25hbCwgT3V0cHV0LCBFdmVudEVtaXR0ZXIsIENoYW5nZURldGVjdG9yUmVmLCBIb3N0TGlzdGVuZXIsIFZpZXdDaGlsZCwgRWxlbWVudFJlZiB9IGZyb20gJ0Bhbmd1bGFyL2NvcmUnO1xyXG5pbXBvcnQgeyBGb3JtQ29udHJvbCwgVmFsaWRhdG9ycywgRm9ybUdyb3VwLCBBYnN0cmFjdENvbnRyb2wsIENvbnRyb2xDb250YWluZXIsIEZvcm1Hcm91cERpcmVjdGl2ZSB9IGZyb20gJ0Bhbmd1bGFyL2Zvcm1zJztcclxuaW1wb3J0IHsgQ29udHJvbFZhbGlkYXRpb25TZXJ2aWNlLCBMYW5ndWFnZVNlcnZpY2UsIFV0aWxpdHlTZXJ2aWNlLCBTcGVlY2hSZWNvZ25pdGlvblNlcnZpY2UgfSBmcm9tICdAYm5zaWdodHMvYmJzZi11dGlsaXRpZXMnO1xyXG5pbXBvcnQgeyBDb250cm9sVXRpbGl0eSB9IGZyb20gJy4uLy4uL1NoYXJlZC9zZXJ2aWNlcy9Db250cm9sVXRpbGl0eSc7XHJcbmltcG9ydCB7IFRleHRBcmVhT3B0aW9ucyB9IGZyb20gJy4uLy4uL1NoYXJlZC9Nb2RlbHMvVGV4dEFyZWFPcHRpb25zJztcclxuaW1wb3J0IHsgR2xvYmFsU2V0dGluZ3MgfSBmcm9tICcuLi8uLi9TaGFyZWQvc2VydmljZXMvR2xvYmFsU2V0dGluZ3Muc2VydmljZSc7XHJcbmltcG9ydCB7IE9ic2VydmFibGUsIFN1YnNjcmlwdGlvbiB9IGZyb20gJ3J4anMnO1xyXG5cclxuQENvbXBvbmVudCh7XHJcbiAgc2VsZWN0b3I6ICdCQlNGLVRleHRBcmVhJyxcclxuICB0ZW1wbGF0ZVVybDogJy4vVGV4dEFyZWEuY29tcG9uZW50Lmh0bWwnXHJcbn0pXHJcbmV4cG9ydCBjbGFzcyBUZXh0QXJlYUNvbXBvbmVudCBpbXBsZW1lbnRzIE9uSW5pdCB7XHJcbiAgc3RhdGljIGNvbnRyb2xDb250YWluZXJzdGF0aWMgPSBudWxsO1xyXG4gIGNvbnN0cnVjdG9yKFxyXG4gICAgcHJpdmF0ZSBjb250cm9sVXRpbGl0eTogQ29udHJvbFV0aWxpdHksXHJcbiAgICBAT3B0aW9uYWwoKSBwcml2YXRlIGNvbnRyb2xDb250YWluZXI6IENvbnRyb2xDb250YWluZXIsXHJcbiAgICBwdWJsaWMgdGV4dEFyZWFDb250cm9sSG9zdDogRm9ybUdyb3VwRGlyZWN0aXZlLFxyXG4gICAgcHJpdmF0ZSB1dGlsaXR5U2VydmljZTogVXRpbGl0eVNlcnZpY2UsXHJcbiAgICBwcml2YXRlIGNvbnRyb2xWYWxpZGF0aW9uU2VydmljZTogQ29udHJvbFZhbGlkYXRpb25TZXJ2aWNlLFxyXG4gICAgcHJpdmF0ZSBnbG9iYWxTZXR0aW5nczogR2xvYmFsU2V0dGluZ3MsXHJcbiAgICBwcml2YXRlIHNwZWVjaFJlY29nbml0aW9uU2VydmljZTogU3BlZWNoUmVjb2duaXRpb25TZXJ2aWNlLFxyXG4gICAgcHJpdmF0ZSBsYW5ndWFnZVNlcnZpY2U6IExhbmd1YWdlU2VydmljZVxyXG4gICkge1xyXG4gICAgVGV4dEFyZWFDb21wb25lbnQuY29udHJvbENvbnRhaW5lcnN0YXRpYyA9IHRoaXMuY29udHJvbENvbnRhaW5lcjtcclxuICAgIHRoaXMuY3VycmVudExhbmd1YWdlID0gbG9jYWxTdG9yYWdlLmdldEl0ZW0oJ2xhbmd1YWdlJyk7XHJcbiAgfVxyXG4gIEBJbnB1dCgpIGdyb3VwOiBGb3JtR3JvdXA7XHJcbiAgQElucHV0KCkgb3B0aW9uczogVGV4dEFyZWFPcHRpb25zO1xyXG4gIEBPdXRwdXQoKSBvbkNoYW5nZSA9IG5ldyBFdmVudEVtaXR0ZXIoKTtcclxuXHJcbiAgdGV4dEFyZWFGb3JtQ29udHJvbDogQWJzdHJhY3RDb250cm9sO1xyXG4gIHdvcmRDb3VudDogbnVtYmVyID0gMDtcclxuICB3b3JkQ291bnRBcnJheTogbnVtYmVyID0gMDtcclxuICBpc1Nob3dXb3JkQ291bnQ6IGJvb2xlYW4gPSBmYWxzZTtcclxuICBtYXJrQWxsQXNUb3VjaGVkOiBib29sZWFuID0gZmFsc2U7XHJcbiAgdmFsaWRhdGlvblJ1bGVzID0gW107XHJcbiAgdmFsaWRhdGlvblJ1bGVzYXN5bmMgPSBbXTtcclxuICAvL0ZvciBTaG93IHdhcm5pbmcgbWVzc2FnZSBvZiBtYXggbGVuZ3RoIGxpbWl0XHJcbiAgY3VycmVudENoYXJzQ291bnQ6IG51bWJlciA9IDA7XHJcbiAgc2hvd0NoYXJzTGltaXRNc2c6IGJvb2xlYW4gPSBmYWxzZTtcclxuICBoYXNDaGFyc0xpbWl0VmFsaWRhdGlvbkVycm9yOiBib29sZWFuID0gZmFsc2U7XHJcbiAgY2hhcnNMaW1pdE1zZ0NsYXNzOiBzdHJpbmc7XHJcbiAgbWluQ2hhcnNMaW1pdDogbnVtYmVyID0gLTE7IC8vVG8gZGlzYWJsZSBjaGFycyBsaW1pdCBmZWF0dXJlIGJ5IGRlZmF1bHRcclxuICBtYXhMaW1pdFdhcm5pbmdNc2c6IHN0cmluZyA9ICcnO1xyXG4gIGlzTWljT246IGJvb2xlYW4gPSBmYWxzZTtcclxuICBwdWJsaWMgdGV4dERpcjtcclxuICBpc0ZvY3VzZWQ6IGJvb2xlYW47XHJcbiAgY3VycmVudExhbmd1YWdlOiBTdHJpbmc7XHJcbiAgc3Vic2NyaXB0aW9uOiBTdWJzY3JpcHRpb247XHJcbiAgc2VsZWN0ZWRTcGVlY2hMYW5ndWFnZURpc3BsYXlUZXh0OiBzdHJpbmc7XHJcblxyXG4gIG5nT25Jbml0KCkge1xyXG4gICAgaWYgKHRoaXMub3B0aW9ucy5pc1JlYWRvbmx5ICYmICF0aGlzLm9wdGlvbnMudmFsdWUpXHJcbiAgICAgIHRoaXMub3B0aW9ucy52YWx1ZSA9IHRoaXMudXRpbGl0eVNlcnZpY2UuZ2V0UmVzb3VyY2VWYWx1ZSgnTkEnKTtcclxuXHJcbiAgICBpZiAodGhpcy5vcHRpb25zLmZvcmNlRGlyZWN0aW9uKVxyXG4gICAgICB0aGlzLnRleHREaXIgPSB0aGlzLm9wdGlvbnMuZm9yY2VEaXJlY3Rpb24gPT0gMiA/ICdydGwnIDogJ2x0cic7XHJcbiAgICBlbHNlIHRoaXMudGV4dERpciA9IGxvY2FsU3RvcmFnZS5nZXRJdGVtKCdsYW5ndWFnZScpID09ICdhcicgPyAncnRsJyA6ICdsdHInO1xyXG5cclxuICAgIHRoaXMuY29udHJvbFZhbGlkYXRpb25TZXJ2aWNlLmlzQ3JlYXRlZEJlZm9yID0gZmFsc2U7XHJcblxyXG4gICAgdGhpcy5ncm91cC5hZGRDb250cm9sKHRoaXMub3B0aW9ucy5uYW1lLCBuZXcgRm9ybUNvbnRyb2woJycpKTtcclxuICAgIHRoaXMudGV4dEFyZWFGb3JtQ29udHJvbCA9IHRoaXMuZ3JvdXAuY29udHJvbHNbdGhpcy5vcHRpb25zLm5hbWVdOyAvLyAgbmV3IEZvcm1Db250cm9sKCcnLHZhbGlkYXRpb25SdWxlcyk7XHJcblxyXG4gICAgaWYgKCF0aGlzLm9wdGlvbnMubWF4TGVuZ3RoKSB0aGlzLm9wdGlvbnMubWF4TGVuZ3RoID0gdGhpcy5nbG9iYWxTZXR0aW5ncy5tYXhMZW5ndGhUZXh0QXJlYTtcclxuXHJcbiAgICBpZiAoIXRoaXMub3B0aW9ucy52aWV3VHlwZSkgdGhpcy5vcHRpb25zLnZpZXdUeXBlID0gdGhpcy5nbG9iYWxTZXR0aW5ncy52aWV3VHlwZTtcclxuXHJcbiAgICBpZiAodGhpcy5vcHRpb25zLmxhYmVsS2V5ICE9IG51bGwgJiYgdGhpcy5vcHRpb25zLmxhYmVsS2V5ICE9ICcnKVxyXG4gICAgICB0aGlzLm9wdGlvbnMubGFiZWxWYWx1ZSA9IHRoaXMudXRpbGl0eVNlcnZpY2UuZ2V0UmVzb3VyY2VWYWx1ZSh0aGlzLm9wdGlvbnMubGFiZWxLZXkpO1xyXG5cclxuICAgIGlmICh0aGlzLm9wdGlvbnMuZW5hYmxlU3BlZWNoUmVjb2duaXRpb24pIHtcclxuICAgICAgLy8gSW5pdGlhbGl6ZSBsYW5ndWFnZSBmb3JtIGNvbnRyb2xcclxuICAgICAgY29uc3QgbGFuZ3VhZ2VDb250cm9sTmFtZSA9ICdMYW5ndWFnZV8nICsgdGhpcy5vcHRpb25zLm5hbWU7XHJcbiAgICAgIHRoaXMuZ3JvdXAuYWRkQ29udHJvbChcclxuICAgICAgICBsYW5ndWFnZUNvbnRyb2xOYW1lLFxyXG4gICAgICAgIG5ldyBGb3JtQ29udHJvbCh0aGlzLm9wdGlvbnMuc2VsZWN0ZWRTcGVlY2hMYW5ndWFnZSB8fCAnJylcclxuICAgICAgKTtcclxuICAgICAgLy9HZXQgYWxsIGxhbmd1YWdlcyBpZiBub3Qgc2V0XHJcbiAgICAgIGlmICghdGhpcy5vcHRpb25zLnNwZWVjaExhbmd1YWdlcykge1xyXG4gICAgICAgIHRoaXMubGFuZ3VhZ2VTZXJ2aWNlLmdldExhbmd1YWdlcygpLnN1YnNjcmliZSgocmVzdWx0KSA9PiB7XHJcbiAgICAgICAgICB0aGlzLm9wdGlvbnMuc3BlZWNoTGFuZ3VhZ2VzID0gcmVzdWx0O1xyXG4gICAgICAgICAgdGhpcy5zZXRTcGVlY2hMYW5ndWFnZSgpO1xyXG4gICAgICAgIH0pO1xyXG4gICAgICB9IGVsc2Uge1xyXG4gICAgICAgIHRoaXMuc2V0U3BlZWNoTGFuZ3VhZ2UoKTtcclxuICAgICAgfVxyXG4gICAgfVxyXG4gICAgdGhpcy50ZXh0QXJlYUZvcm1Db250cm9sLnNldFZhbHVlKHRoaXMub3B0aW9ucy52YWx1ZSk7XHJcbiAgICBpZiAodGhpcy5vcHRpb25zLmN1c3RvbVZhbGlkYXRpb24ubGVuZ3RoID4gMCkge1xyXG4gICAgICBsZXQgVmFsaWRhdGlvbnMgPSB0aGlzLm9wdGlvbnMuY3VzdG9tVmFsaWRhdGlvbjtcclxuICAgICAgZm9yIChsZXQgaW5kZXggPSAwOyBpbmRleCA8IFZhbGlkYXRpb25zLmxlbmd0aDsgaW5kZXgrKykge1xyXG4gICAgICAgIGNvbnN0IFZhbGlkYXRpb24gPSBWYWxpZGF0aW9uc1tpbmRleF07XHJcbiAgICAgICAgdGhpcy52YWxpZGF0aW9uUnVsZXMucHVzaChWYWxpZGF0aW9uLmZ1bmN0aW9uQm9keSk7XHJcbiAgICAgIH1cclxuICAgIH1cclxuICAgIGlmICh0aGlzLm9wdGlvbnMubWluTGVuZ3RoID4gMCkge1xyXG4gICAgICB0aGlzLnZhbGlkYXRpb25SdWxlcy5wdXNoKFZhbGlkYXRvcnMubWluTGVuZ3RoKHRoaXMub3B0aW9ucy5taW5MZW5ndGgpKTtcclxuICAgIH1cclxuICAgIGlmICh0aGlzLm9wdGlvbnMubWF4TGVuZ3RoID4gMCkge1xyXG4gICAgICB0aGlzLnZhbGlkYXRpb25SdWxlcy5wdXNoKFZhbGlkYXRvcnMubWF4TGVuZ3RoKHRoaXMub3B0aW9ucy5tYXhMZW5ndGgpKTtcclxuXHJcbiAgICAgIGlmICghdGhpcy5vcHRpb25zLm1heExlbmd0aFdhcm5pbmdMaW1pdClcclxuICAgICAgICB0aGlzLm9wdGlvbnMubWF4TGVuZ3RoV2FybmluZ0xpbWl0ID0gdGhpcy5nbG9iYWxTZXR0aW5ncy5tYXhMZW5ndGhXYXJuaW5nTGltaXQ7XHJcblxyXG4gICAgICB0aGlzLm1pbkNoYXJzTGltaXQgPSB0aGlzLm9wdGlvbnMubWF4TGVuZ3RoIC0gdGhpcy5vcHRpb25zLm1heExlbmd0aFdhcm5pbmdMaW1pdDtcclxuICAgIH1cclxuICAgIGlmICh0aGlzLm9wdGlvbnMuaXNSZXF1aXJlZCkge1xyXG4gICAgICB0aGlzLnZhbGlkYXRpb25SdWxlcy5wdXNoKFZhbGlkYXRvcnMucmVxdWlyZWQpO1xyXG4gICAgfVxyXG4gICAgdGhpcy50ZXh0QXJlYUZvcm1Db250cm9sLnNldFZhbGlkYXRvcnModGhpcy52YWxpZGF0aW9uUnVsZXMpO1xyXG4gICAgdGhpcy50ZXh0QXJlYUZvcm1Db250cm9sLnNldEFzeW5jVmFsaWRhdG9ycyh0aGlzLnZhbGlkYXRpb25SdWxlc2FzeW5jKTtcclxuICAgIGlmICh0aGlzLm9wdGlvbnMuaXNEaXNhYmxlZCkge1xyXG4gICAgICB0aGlzLnRleHRBcmVhRm9ybUNvbnRyb2wuZGlzYWJsZSgpO1xyXG4gICAgfVxyXG5cclxuICAgIHRoaXMudGV4dEFyZWFDb250cm9sSG9zdC5uZ1N1Ym1pdC5zdWJzY3JpYmUoKHZhbHVlKSA9PiB7XHJcbiAgICAgIHRoaXMuZ3JvdXAubWFya0FsbEFzVG91Y2hlZCgpO1xyXG4gICAgICB0aGlzLm1hcmtBbGxBc1RvdWNoZWQgPSB0cnVlO1xyXG4gICAgfSk7XHJcbiAgfVxyXG5cclxuICBuZ0FmdGVyVmlld0luaXQoKTogdm9pZCB7XHJcbiAgICB0aGlzLmNvbnRyb2xVdGlsaXR5LnNldEF0dHJpYnV0ZUZvckNvbnRyb2wodGhpcy5vcHRpb25zKTtcclxuICB9XHJcblxyXG4gIHJlc2V0RXJyb3IgPSAoKSA9PiB7XHJcbiAgICB0aGlzLmNvbnRyb2xWYWxpZGF0aW9uU2VydmljZS5yZW1vdmVHbG9iYWxFcnJvcigpO1xyXG4gIH07XHJcblxyXG4gIHNob3dHbG9iYWxFcnJvcigpIHtcclxuICAgIHRoaXMuY29udHJvbFV0aWxpdHkuc2hvd0dsb2JhbEVycm9yKCk7XHJcbiAgfVxyXG5cclxuICBnZXRFcnJvclZhbGlkYXRpb24oRXJyb3JMaXN0KSB7XHJcbiAgICBpZiAodGhpcy5tYXJrQWxsQXNUb3VjaGVkICYmIHRoaXMuZ3JvdXAuaW52YWxpZCkge1xyXG4gICAgICB0aGlzLnNob3dHbG9iYWxFcnJvcigpO1xyXG4gICAgICB0aGlzLm1hcmtBbGxBc1RvdWNoZWQgPSBmYWxzZTtcclxuICAgIH1cclxuICAgIHJldHVybiB0aGlzLmNvbnRyb2xVdGlsaXR5LmdldEVycm9yVmFsaWRhdGlvbk1hc3NhZ2UoRXJyb3JMaXN0LCB0aGlzLmdyb3VwLCB0aGlzLm9wdGlvbnMpO1xyXG4gIH1cclxuICBnZXRJbnB1dFR5cGUodHlwZTogbnVtYmVyKSB7XHJcbiAgICByZXR1cm4gdGhpcy5jb250cm9sVXRpbGl0eS5nZXRJbnB1dFR5cGUodHlwZSk7XHJcbiAgfVxyXG5cclxuICB0cmltQ29udHJvbFZhbHVlKCkge1xyXG4gICAgbGV0IG9yaWdpbmFsVmFsdWUgPSB0aGlzLmNvbnRyb2xVdGlsaXR5LnRyaW1Db250cm9sVmFsdWUodGhpcy50ZXh0QXJlYUZvcm1Db250cm9sLnZhbHVlKTtcclxuICAgIHRoaXMudGV4dEFyZWFGb3JtQ29udHJvbC5wYXRjaFZhbHVlKG9yaWdpbmFsVmFsdWUpO1xyXG4gICAgaWYgKHRoaXMub3B0aW9ucy5wYXRjaEZ1bmN0aW9uICYmIHRoaXMub3B0aW9ucy5wYXRjaFBhdGggJiYgdGhpcy50ZXh0QXJlYUZvcm1Db250cm9sLnZhbGlkKSB7XHJcbiAgICAgIHRoaXMuY29udHJvbFV0aWxpdHkucGF0Y2hDb250cm9sVmFsdWUoXHJcbiAgICAgICAgb3JpZ2luYWxWYWx1ZSxcclxuICAgICAgICB0aGlzLm9wdGlvbnMucGF0Y2hGdW5jdGlvbixcclxuICAgICAgICB0aGlzLm9wdGlvbnMucGF0Y2hQYXRoXHJcbiAgICAgICk7XHJcbiAgICB9XHJcbiAgfVxyXG5cclxuICBjb3B5SW5wdXRNZXNzYWdlKGlucHV0RWxlbWVudCkge1xyXG4gICAgdGhpcy5jb250cm9sVXRpbGl0eS5Db3B5SW5wdXRNZXNzYWdlKGlucHV0RWxlbWVudCk7XHJcbiAgfVxyXG5cclxuICBvblRleHRDaGFuZ2UoKSB7XHJcbiAgICBpZiAodGhpcy50ZXh0QXJlYUZvcm1Db250cm9sLnZhbHVlID09ICcnKSB7XHJcbiAgICAgIHRoaXMud29yZENvdW50QXJyYXkgPSAwO1xyXG4gICAgICB0aGlzLndvcmRDb3VudCA9IDA7XHJcbiAgICB9IGVsc2Uge1xyXG4gICAgICB0aGlzLndvcmRDb3VudEFycmF5ID0gdGhpcy50ZXh0QXJlYUZvcm1Db250cm9sLnZhbHVlLnNwbGl0KCcgJykubGVuZ3RoO1xyXG4gICAgICBpZiAodGhpcy53b3JkQ291bnRBcnJheSA+IDApIHtcclxuICAgICAgICBpZiAodGhpcy53b3JkQ291bnRBcnJheSA+IHRoaXMub3B0aW9ucy5tYXhXb3JkQ291bnQpIHtcclxuICAgICAgICAgIHRoaXMud29yZENvdW50ID0gdGhpcy5vcHRpb25zLm1heFdvcmRDb3VudDtcclxuICAgICAgICAgIHRoaXMudGV4dEFyZWFGb3JtQ29udHJvbC5zZXRFcnJvcnMoe1xyXG4gICAgICAgICAgICBlcnJvck1hc3NhZ2U6IGAgIFdvcmQgY291bnQgbXVzdCBiZSBsZXNzIHRoZW4gb3IgZXF1YWwgICR7dGhpcy5vcHRpb25zLm1heFdvcmRDb3VudH1gXHJcbiAgICAgICAgICB9KTtcclxuICAgICAgICAgIHRoaXMudGV4dEFyZWFGb3JtQ29udHJvbC5tYXJrQXNUb3VjaGVkKCk7XHJcbiAgICAgICAgICB0aGlzLnRleHRBcmVhRm9ybUNvbnRyb2wuaW52YWxpZDtcclxuICAgICAgICB9IGVsc2Uge1xyXG4gICAgICAgICAgdGhpcy53b3JkQ291bnQgPSB0aGlzLndvcmRDb3VudEFycmF5O1xyXG4gICAgICAgIH1cclxuICAgICAgfVxyXG4gICAgfVxyXG4gICAgLy9DaGVjayBmb3IgbWF4bGVuZ3RoIGxpbWl0IGNvdW50XHJcbiAgICAvL01heExlbmd0aCBzaG91bGQgYmUgZ3JldGFlciB0aGFuIG9yIGVxdWFscyBjaGFycyBsaW1pdCBzbyB0aGF0IG1pbkNoYXJzTGltaXQgd291bGQgYmUgPj0gMFxyXG4gICAgaWYgKHRoaXMub3B0aW9ucy5tYXhMZW5ndGggJiYgdGhpcy5taW5DaGFyc0xpbWl0ID49IDApIHtcclxuICAgICAgdGhpcy5jdXJyZW50Q2hhcnNDb3VudCA9IHRoaXMudGV4dEFyZWFGb3JtQ29udHJvbC52YWx1ZS5sZW5ndGg7XHJcbiAgICAgIGlmICh0aGlzLmN1cnJlbnRDaGFyc0NvdW50ID4gdGhpcy5taW5DaGFyc0xpbWl0KSB7XHJcbiAgICAgICAgdGhpcy5zaG93Q2hhcnNMaW1pdE1zZyA9IHRydWU7XHJcbiAgICAgICAgdGhpcy5oYXNDaGFyc0xpbWl0VmFsaWRhdGlvbkVycm9yID0gdHJ1ZTtcclxuXHJcbiAgICAgICAgaWYgKHRoaXMuY3VycmVudENoYXJzQ291bnQgPT0gdGhpcy5vcHRpb25zLm1heExlbmd0aCkgdGhpcy5jaGFyc0xpbWl0TXNnQ2xhc3MgPSAnZGFuZ2VyJztcclxuICAgICAgICBlbHNlIHRoaXMuY2hhcnNMaW1pdE1zZ0NsYXNzID0gJ3dhcm5pbmcnO1xyXG4gICAgICB9IGVsc2Uge1xyXG4gICAgICAgIHRoaXMuc2hvd0NoYXJzTGltaXRNc2cgPSBmYWxzZTtcclxuICAgICAgICB0aGlzLmhhc0NoYXJzTGltaXRWYWxpZGF0aW9uRXJyb3IgPSBmYWxzZTtcclxuICAgICAgfVxyXG5cclxuICAgICAgbGV0IG1heDogbnVtYmVyID0gdGhpcy5vcHRpb25zLm1heExlbmd0aDtcclxuICAgICAgbGV0IGN1cnJlbnQ6IG51bWJlciA9IHRoaXMuY3VycmVudENoYXJzQ291bnQ7XHJcbiAgICAgIGxldCBtc2c6IHN0cmluZyA9IHRoaXMudXRpbGl0eVNlcnZpY2UuZ2V0UmVzb3VyY2VWYWx1ZSgnTWF4TGVuZ3RoTGltaXRXYXJuaW5nJyk7XHJcblxyXG4gICAgICAvLyBSZXBsYWNlIHBsYWNlaG9sZGVycyB3aXRoIGFjdHVhbCB2YWx1ZXNcclxuICAgICAgdGhpcy5tYXhMaW1pdFdhcm5pbmdNc2cgPSBtc2dcclxuICAgICAgICAucmVwbGFjZSgnJHttYXh9JywgbWF4LnRvU3RyaW5nKCkpXHJcbiAgICAgICAgLnJlcGxhY2UoJyR7Y3VycmVudH0nLCBjdXJyZW50LnRvU3RyaW5nKCkpO1xyXG4gICAgfVxyXG4gICAgdGhpcy5vbkNoYW5nZS5lbWl0KHRoaXMudGV4dEFyZWFGb3JtQ29udHJvbC52YWx1ZSk7XHJcbiAgfVxyXG5cclxuICBvbkZvY3VzKGlzRm9jdXM6IGJvb2xlYW4pIHtcclxuICAgIHRoaXMuaXNTaG93V29yZENvdW50ID0gaXNGb2N1cztcclxuXHJcbiAgICAvL29uRm9jdXNcclxuICAgIGlmIChpc0ZvY3VzKSB7XHJcbiAgICAgIGlmICh0aGlzLmhhc0NoYXJzTGltaXRWYWxpZGF0aW9uRXJyb3IpXHJcbiAgICAgICAgLy9jaGVjayBpZiB0aGVyZSB3YXMgcHJldmlvdXMgdmFsaWRhdGlvbiBlcnJvclxyXG4gICAgICAgIHRoaXMuc2hvd0NoYXJzTGltaXRNc2cgPSB0cnVlO1xyXG4gICAgfSAvL29uRm9jdXNPdXRcclxuICAgIGVsc2UgdGhpcy5zaG93Q2hhcnNMaW1pdE1zZyA9IGZhbHNlO1xyXG4gIH1cclxuXHJcbiAgLy9FeHRlcm5hbCBNZXRob2RcclxuICByZW1vdmVSZXF1aXJlZFZhbGlkYXRpb24gPSAoKSA9PiB7XHJcbiAgICB0aGlzLmNvbnRyb2xVdGlsaXR5LnJlbW92ZVJlcXVpcmVkVmFsaWRhdGlvbihcclxuICAgICAgdGhpcy50ZXh0QXJlYUZvcm1Db250cm9sLFxyXG4gICAgICB0aGlzLnZhbGlkYXRpb25SdWxlcyxcclxuICAgICAgdGhpcy5vcHRpb25zXHJcbiAgICApO1xyXG4gIH07XHJcbiAgLy9FeHRlcm5hbCBNZXRob2RcclxuICBhZGRSZXF1aXJlZFZhbGlkYXRpb24gPSAoKSA9PiB7XHJcbiAgICB0aGlzLmNvbnRyb2xVdGlsaXR5LmFkZFJlcXVpcmVkVmFsaWRhdGlvbihcclxuICAgICAgdGhpcy50ZXh0QXJlYUZvcm1Db250cm9sLFxyXG4gICAgICB0aGlzLnZhbGlkYXRpb25SdWxlcyxcclxuICAgICAgdGhpcy5vcHRpb25zXHJcbiAgICApO1xyXG4gIH07XHJcblxyXG4gIC8vRXh0ZXJuYWwgTWV0aG9kXHJcbiAgcmVtb3ZlQ3VzdG9tVmFsaWRhdGlvbiA9IChjdXN0b21WYWxpZGF0aW9uKSA9PiB7XHJcbiAgICB0aGlzLmNvbnRyb2xVdGlsaXR5LnJlbW92ZUN1c3RvbVZhbGlkYXRpb24oXHJcbiAgICAgIHRoaXMudGV4dEFyZWFGb3JtQ29udHJvbCxcclxuICAgICAgdGhpcy52YWxpZGF0aW9uUnVsZXMsXHJcbiAgICAgIGN1c3RvbVZhbGlkYXRpb25cclxuICAgICk7XHJcbiAgfTtcclxuICAvL0V4dGVybmFsIE1ldGhvZFxyXG4gIGFkZEN1c3RvbVZhbGlkYXRpb24gPSAoY3VzdG9tVmFsaWRhdGlvbikgPT4ge1xyXG4gICAgdGhpcy5jb250cm9sVXRpbGl0eS5hZGRDdXN0b21WYWxpZGF0aW9uKFxyXG4gICAgICB0aGlzLnRleHRBcmVhRm9ybUNvbnRyb2wsXHJcbiAgICAgIHRoaXMudmFsaWRhdGlvblJ1bGVzLFxyXG4gICAgICBjdXN0b21WYWxpZGF0aW9uXHJcbiAgICApO1xyXG4gIH07XHJcbiAgLy9FeHRlcm5hbCBNZXRob2RcclxuICBpc1ZhbGlkID0gKCkgPT4ge1xyXG4gICAgdGhpcy5jb250cm9sVXRpbGl0eS5pc1ZhbGlkKHRoaXMudGV4dEFyZWFGb3JtQ29udHJvbCk7XHJcbiAgfTtcclxuICAvL3JlZ2lvbiBTcGVlY2ggUmVjb2duaXRpb25cclxuICBzZXRTcGVlY2hMYW5ndWFnZSgpIHtcclxuICAgIGNvbnN0IGxhbmd1YWdlQ29udHJvbE5hbWUgPSAnTGFuZ3VhZ2VfJyArIHRoaXMub3B0aW9ucy5uYW1lO1xyXG5cclxuICAgIGlmICh0aGlzLm9wdGlvbnMuYXV0b1NhdmVTcGVlY2hMYW5ndWFnZXRvTG9jYWxTdG9yYWdlKSB7XHJcbiAgICAgIGxldCBzYXZlZExhbmd1YWdlID0gbG9jYWxTdG9yYWdlLmdldEl0ZW0oJ3NwZWVjaExhbmd1YWdlJyk7XHJcbiAgICAgIGlmIChzYXZlZExhbmd1YWdlKSB7XHJcbiAgICAgICAgdGhpcy5vcHRpb25zLnNlbGVjdGVkU3BlZWNoTGFuZ3VhZ2UgPSBzYXZlZExhbmd1YWdlO1xyXG4gICAgICB9IGVsc2Uge1xyXG4gICAgICAgIHRoaXMubG9hZFNlbGVjdGVkU3BlZWNoTGFuZ3VhZ2UoKTtcclxuICAgICAgICBsb2NhbFN0b3JhZ2Uuc2V0SXRlbSgnc3BlZWNoTGFuZ3VhZ2UnLCB0aGlzLm9wdGlvbnMuc2VsZWN0ZWRTcGVlY2hMYW5ndWFnZSk7XHJcbiAgICAgIH1cclxuICAgIH0gZWxzZSB7XHJcbiAgICAgIHRoaXMubG9hZFNlbGVjdGVkU3BlZWNoTGFuZ3VhZ2UoKTtcclxuICAgIH1cclxuICAgIHRoaXMuZ3JvdXAuZ2V0KGxhbmd1YWdlQ29udHJvbE5hbWUpLnNldFZhbHVlKHRoaXMub3B0aW9ucy5zZWxlY3RlZFNwZWVjaExhbmd1YWdlKTtcclxuXHJcbiAgICB0aGlzLnNlbGVjdGVkU3BlZWNoTGFuZ3VhZ2VEaXNwbGF5VGV4dCA9IHRoaXMub3B0aW9ucy5zcGVlY2hMYW5ndWFnZXMuZmluZChcclxuICAgICAgKGwpID0+IGwuZGlhbGVjdCA9PSB0aGlzLm9wdGlvbnMuc2VsZWN0ZWRTcGVlY2hMYW5ndWFnZVxyXG4gICAgKS5wcmVmaXg7XHJcbiAgfVxyXG4gIGxvYWRTZWxlY3RlZFNwZWVjaExhbmd1YWdlKCkge1xyXG4gICAgaWYgKCF0aGlzLm9wdGlvbnMuc2VsZWN0ZWRTcGVlY2hMYW5ndWFnZSkge1xyXG4gICAgICBpZiAoXHJcbiAgICAgICAgdGhpcy5jdXJyZW50TGFuZ3VhZ2UgPT0gJ2VuJyAmJlxyXG4gICAgICAgIHRoaXMub3B0aW9ucy5zcGVlY2hMYW5ndWFnZXMuc29tZSgobGFuZ3VhZ2UpID0+IGxhbmd1YWdlLmVuZ2xpc2hOYW1lID09PSAnRW5nbGlzaCcpXHJcbiAgICAgICkge1xyXG4gICAgICAgIHRoaXMub3B0aW9ucy5zZWxlY3RlZFNwZWVjaExhbmd1YWdlID0gdGhpcy5vcHRpb25zLnNwZWVjaExhbmd1YWdlcy5maW5kKFxyXG4gICAgICAgICAgKGxhbmd1YWdlKSA9PiBsYW5ndWFnZS5lbmdsaXNoTmFtZSA9PT0gJ0VuZ2xpc2gnXHJcbiAgICAgICAgKS5kaWFsZWN0O1xyXG4gICAgICB9IGVsc2UgaWYgKFxyXG4gICAgICAgIHRoaXMuY3VycmVudExhbmd1YWdlID09ICdhcicgJiZcclxuICAgICAgICB0aGlzLm9wdGlvbnMuc3BlZWNoTGFuZ3VhZ2VzLnNvbWUoKGxhbmd1YWdlKSA9PiBsYW5ndWFnZS5lbmdsaXNoTmFtZSA9PT0gJ0FyYWJpYycpXHJcbiAgICAgICkge1xyXG4gICAgICAgIHRoaXMub3B0aW9ucy5zZWxlY3RlZFNwZWVjaExhbmd1YWdlID0gdGhpcy5vcHRpb25zLnNwZWVjaExhbmd1YWdlcy5maW5kKFxyXG4gICAgICAgICAgKGxhbmd1YWdlKSA9PiBsYW5ndWFnZS5lbmdsaXNoTmFtZSA9PT0gJ0FyYWJpYydcclxuICAgICAgICApLmRpYWxlY3Q7XHJcbiAgICAgIH0gZWxzZSB7XHJcbiAgICAgICAgdGhpcy5vcHRpb25zLnNlbGVjdGVkU3BlZWNoTGFuZ3VhZ2UgPSB0aGlzLm9wdGlvbnMuc3BlZWNoTGFuZ3VhZ2VzWzBdLmRpYWxlY3Q7XHJcbiAgICAgIH1cclxuICAgIH1cclxuICB9XHJcbiAgc3RhcnRTcGVlY2hSZWNvZ25pdGlvbigpOiB2b2lkIHtcclxuICAgIGlmICghdGhpcy5zcGVlY2hSZWNvZ25pdGlvblNlcnZpY2UuaXNTdXBwb3J0ZWQpIHtcclxuICAgICAgdGhpcy51dGlsaXR5U2VydmljZS5ub3RpZnlFcnJvck1lc3NhZ2UoXHJcbiAgICAgICAgdGhpcy51dGlsaXR5U2VydmljZS5nZXRSZXNvdXJjZVZhbHVlKCdCcm93c2VyTm90U3VwcG9ydFNwZWVjaFJlY29nbml0aW9uJylcclxuICAgICAgKTtcclxuICAgICAgcmV0dXJuO1xyXG4gICAgfVxyXG4gICAgLy9EaXNhYmxlIFNlbGVjdCBMYW5ndWFnZVxyXG4gICAgdGhpcy5lbmFibGVPckRpc2FibGVMYW5ndWFnZVNlbGVjdChmYWxzZSk7XHJcbiAgICB0aGlzLmlzTWljT24gPSB0cnVlO1xyXG4gICAgdGhpcy5zdWJzY3JpcHRpb24gPSB0aGlzLnNwZWVjaFJlY29nbml0aW9uU2VydmljZVxyXG4gICAgICAuc3RhcnRMaXN0ZW5pbmcodGhpcy5vcHRpb25zLnNlbGVjdGVkU3BlZWNoTGFuZ3VhZ2UpXHJcbiAgICAgIC5zdWJzY3JpYmUoe1xyXG4gICAgICAgIG5leHQ6ICh0cmFuc2NyaXB0OiBzdHJpbmcpID0+IHtcclxuICAgICAgICAgIGlmICh0cmFuc2NyaXB0KSB7XHJcbiAgICAgICAgICAgIGlmICh0aGlzLm9wdGlvbnMudmFsdWUpIHtcclxuICAgICAgICAgICAgICB0aGlzLm9wdGlvbnMudmFsdWUgKz0gJyAnO1xyXG4gICAgICAgICAgICAgIHRoaXMuZmlyZU9uQ2hhbmdlKHRoaXMub3B0aW9ucy52YWx1ZSk7XHJcbiAgICAgICAgICAgIH1cclxuICAgICAgICAgICAgbGV0IGNoYXJJbmRleCA9IDA7XHJcbiAgICAgICAgICAgIGNvbnN0IGludGVydmFsID0gc2V0SW50ZXJ2YWwoKCkgPT4ge1xyXG4gICAgICAgICAgICAgIHRoaXMub3B0aW9ucy52YWx1ZSArPSB0cmFuc2NyaXB0W2NoYXJJbmRleF07XHJcbiAgICAgICAgICAgICAgdGhpcy5maXJlT25DaGFuZ2UodGhpcy5vcHRpb25zLnZhbHVlKTtcclxuICAgICAgICAgICAgICBjaGFySW5kZXgrKztcclxuICAgICAgICAgICAgICBpZiAoY2hhckluZGV4ID09PSB0cmFuc2NyaXB0Lmxlbmd0aCkge1xyXG4gICAgICAgICAgICAgICAgY2xlYXJJbnRlcnZhbChpbnRlcnZhbCk7XHJcbiAgICAgICAgICAgICAgfVxyXG4gICAgICAgICAgICB9LCAxMCk7XHJcbiAgICAgICAgICB9XHJcbiAgICAgICAgfSxcclxuICAgICAgICBlcnJvcjogKGVycm9yOiBhbnkpID0+IHtcclxuICAgICAgICAgIGNvbnNvbGUuZXJyb3IoZXJyb3IpO1xyXG4gICAgICAgICAgdGhpcy5zdG9wU3BlZWNoUmVjb2duaXRpb24oKTtcclxuICAgICAgICB9LFxyXG4gICAgICAgIGNvbXBsZXRlOiAoKSA9PiB7XHJcbiAgICAgICAgICAvL0VuYWJsZSBTZWxlY3QgTGFuZ3VhZ2VcclxuICAgICAgICAgIHRoaXMuZW5hYmxlT3JEaXNhYmxlTGFuZ3VhZ2VTZWxlY3QoKTtcclxuICAgICAgICAgIHRoaXMuaXNNaWNPbiA9IGZhbHNlO1xyXG4gICAgICAgIH1cclxuICAgICAgfSk7XHJcbiAgfVxyXG5cclxuICBzdG9wU3BlZWNoUmVjb2duaXRpb24oKTogdm9pZCB7XHJcbiAgICB0aGlzLmVuYWJsZU9yRGlzYWJsZUxhbmd1YWdlU2VsZWN0KCk7XHJcbiAgICBpZiAoIXRoaXMuc3BlZWNoUmVjb2duaXRpb25TZXJ2aWNlLmlzU3VwcG9ydGVkKSB7XHJcbiAgICAgIHJldHVybjtcclxuICAgIH1cclxuICAgIHRoaXMuaXNNaWNPbiA9IGZhbHNlO1xyXG4gICAgdGhpcy5zcGVlY2hSZWNvZ25pdGlvblNlcnZpY2Uuc3RvcExpc3RlbmluZygpO1xyXG4gICAgaWYgKHRoaXMuc3Vic2NyaXB0aW9uKSB7XHJcbiAgICAgIHRoaXMuc3Vic2NyaXB0aW9uLnVuc3Vic2NyaWJlKCk7XHJcbiAgICB9XHJcbiAgfVxyXG4gIGZpcmVPbkNoYW5nZSh0ZXh0KTogdm9pZCB7XHJcbiAgICBpZiAodGhpcy5vbkNoYW5nZSkge1xyXG4gICAgICB0aGlzLm9uQ2hhbmdlLmVtaXQodGV4dCk7XHJcbiAgICB9XHJcbiAgfVxyXG4gIG5nT25EZXN0cm95KCk6IHZvaWQge1xyXG4gICAgaWYgKHRoaXMub3B0aW9ucy5lbmFibGVTcGVlY2hSZWNvZ25pdGlvbikge1xyXG4gICAgICB0aGlzLnN0b3BTcGVlY2hSZWNvZ25pdGlvbigpO1xyXG4gICAgfVxyXG4gIH1cclxuXHJcbiAgb25TcGVlY2hMYW5ndWFnZUNoYW5nZShldmVudCkge1xyXG4gICAgbGV0IHNlbGVjdGVkTGFuZ19EaWFsZWN0ID0gZXZlbnQudGFyZ2V0LnZhbHVlO1xyXG4gICAgdGhpcy5zZWxlY3RlZFNwZWVjaExhbmd1YWdlRGlzcGxheVRleHQgPSB0aGlzLm9wdGlvbnMuc3BlZWNoTGFuZ3VhZ2VzLmZpbmQoXHJcbiAgICAgIChsKSA9PiBsLmRpYWxlY3QgPT0gc2VsZWN0ZWRMYW5nX0RpYWxlY3RcclxuICAgICkucHJlZml4O1xyXG4gICAgdGhpcy5vcHRpb25zLnNlbGVjdGVkU3BlZWNoTGFuZ3VhZ2UgPSBzZWxlY3RlZExhbmdfRGlhbGVjdDtcclxuXHJcbiAgICBjb25zdCBsYW5ndWFnZUNvbnRyb2xOYW1lID0gJ0xhbmd1YWdlXycgKyB0aGlzLm9wdGlvbnMubmFtZTtcclxuICAgIGxldCBzZWxlY3QgPSB0aGlzLmdyb3VwLmdldChsYW5ndWFnZUNvbnRyb2xOYW1lKTtcclxuICAgIHNlbGVjdC5zZXRWYWx1ZShzZWxlY3RlZExhbmdfRGlhbGVjdCk7XHJcblxyXG4gICAgaWYgKHRoaXMub3B0aW9ucy5hdXRvU2F2ZVNwZWVjaExhbmd1YWdldG9Mb2NhbFN0b3JhZ2UpIHtcclxuICAgICAgbG9jYWxTdG9yYWdlLnNldEl0ZW0oJ3NwZWVjaExhbmd1YWdlJywgc2VsZWN0ZWRMYW5nX0RpYWxlY3QpO1xyXG4gICAgfVxyXG4gIH1cclxuICBlbmFibGVPckRpc2FibGVMYW5ndWFnZVNlbGVjdChpc0VuYWJsZWQ6IGJvb2xlYW4gPSB0cnVlKSB7XHJcbiAgICBjb25zdCBsYW5ndWFnZUNvbnRyb2xOYW1lID0gJ0xhbmd1YWdlXycgKyB0aGlzLm9wdGlvbnMubmFtZTtcclxuICAgIGxldCBzZWxlY3QgPSB0aGlzLmdyb3VwLmdldChsYW5ndWFnZUNvbnRyb2xOYW1lKTtcclxuICAgIGlmIChpc0VuYWJsZWQpIHtcclxuICAgICAgc2VsZWN0LmVuYWJsZSgpO1xyXG4gICAgfSBlbHNlIHtcclxuICAgICAgc2VsZWN0LmRpc2FibGUoKTtcclxuICAgIH1cclxuICB9XHJcbiAgLy8jZW5kUmVnaW9uXHJcbn1cclxuXHJcblxyXG4iLCI8ZGl2IGNsYXNzPVwiZm9ybS1ncm91cCBiYnNmLWNvbnRyb2wgYmJzZi10ZXh0YXJlYVwiIFtmb3JtR3JvdXBdPVwiZ3JvdXBcIj5cclxuICA8ZGl2IFtuZ0NsYXNzXT1cIihvcHRpb25zLnZpZXdUeXBlPT0xKT8nYmJzZi12ZXJ0aWNhbCc6J2Jic2YtaG9yaXpvbnRhbCdcIj5cclxuICAgIDwhLS1sYWJlbC0tPlxyXG4gICAgPGxhYmVsICpuZ0lmPVwiIW9wdGlvbnMuaGlkZUxhYmVsXCIgY2xhc3M9XCJiYnNmLWxhYmVsIHt7b3B0aW9ucy5sYWJlbEV4dHJhQ2xhc3Nlc319XCI+XHJcbiAgICAgIHt7b3B0aW9ucy5sYWJlbFZhbHVlfX1cclxuICAgICAgPCEtLUFzdGVyaXNrLS0+XHJcbiAgICAgIDxzcGFuICpuZ0lmPVwiKChvcHRpb25zLnNob3dBc3RlcmlzayYmb3B0aW9ucy5pc1JlcXVpcmVkKXx8KG9wdGlvbnMuaXNSZXF1aXJlZCkpJiYhb3B0aW9ucy5pc1JlYWRvbmx5XCJcclxuICAgICAgICBjbGFzcz1cInRleHQtZGFuZ2VyXCI+Kjwvc3Bhbj5cclxuICAgIDwvbGFiZWw+XHJcbiAgICA8ZGl2ICpuZ0lmPVwiIW9wdGlvbnMuaXNSZWFkb25seVwiIGNsYXNzPVwiYmJzZi1pbnB1dC1jb250YWluZXJcIiBbbmdDbGFzc109XCJ7XHJcbiAgICAgICdwLTEyMHB4Jzogb3B0aW9ucy5lbmFibGVTcGVlY2hSZWNvZ25pdGlvbiAmJiBvcHRpb25zLmVuYWJsZUNvcHlUb0NsaXBib2FyZCxcclxuICAgICAgJ3AtODBweCc6IG9wdGlvbnMuZW5hYmxlU3BlZWNoUmVjb2duaXRpb24gJiYgIW9wdGlvbnMuZW5hYmxlQ29weVRvQ2xpcGJvYXJkLFxyXG4gICAgICAncC00MHB4JzogIW9wdGlvbnMuZW5hYmxlU3BlZWNoUmVjb2duaXRpb24gJiYgb3B0aW9ucy5lbmFibGVDb3B5VG9DbGlwYm9hcmRcclxuICAgIH1cIj5cclxuICAgICAgPCEtLWlucHV0LS0+XHJcbiAgICAgIDx0ZXh0YXJlYSBjbGFzcz1cImZvcm0tY29udHJvbCB7e29wdGlvbnMuZXh0cmFDbGFzc2VzfX1cIiAoZm9jdXMpPVwib25Gb2N1cyh0cnVlKVwiIChmb2N1c291dCk9XCJvbkZvY3VzKGZhbHNlKVwiXHJcbiAgICAgICAgW2Rpcl09XCJ0ZXh0RGlyXCIgYXJpYS1kZXNjcmliZWRieT1cImVtYWlsLWVycm9yXCIgYXJpYS1pbnZhbGlkPVwidHJ1ZVwiIGZvcm1Db250cm9sTmFtZT1cInt7b3B0aW9ucy5uYW1lfX1cIlxyXG4gICAgICAgIFtjbGFzcy5pcy1pbnZhbGlkXT1cInRleHRBcmVhRm9ybUNvbnRyb2wuaW52YWxpZCAmJiB0ZXh0QXJlYUZvcm1Db250cm9sLnRvdWNoZWRcIlxyXG4gICAgICAgIHBsYWNlaG9sZGVyPVwie3tvcHRpb25zLnBsYWNlaG9sZGVyfX1cIiBpZD1cInt7b3B0aW9ucy5uYW1lfX1cIiBhdXRvY29tcGxldGU9XCJ7e29wdGlvbnMuYXV0b0NvbXBsZXRlfX1cIlxyXG4gICAgICAgIChjaGFuZ2UpPVwidHJpbUNvbnRyb2xWYWx1ZSgpXCIgcm93cz1cInt7b3B0aW9ucy5yb3dzfX1cIiAoa2V5dXApPVwib25UZXh0Q2hhbmdlKClcIiBjb2xzPVwie3tvcHRpb25zLmNvbHN9fVwiXHJcbiAgICAgICAgbWF4bGVuZ3RoPVwie3tvcHRpb25zLm1heExlbmd0aH19XCIgbWlubGVuZ3RoPVwie3tvcHRpb25zLm1pbkxlbmd0aH19XCIgWyhuZ01vZGVsKV09XCJvcHRpb25zLnZhbHVlXCJcclxuICAgICAgICAoa2V5ZG93bik9XCJ3b3JkQ291bnRBcnJheT5vcHRpb25zLm1heFdvcmRDb3VudCYmJGV2ZW50LmtleUNvZGUgIT04PyRldmVudC5wcmV2ZW50RGVmYXVsdCgpOm51bGxcIlxyXG4gICAgICAgICNUZXh0QXJlYWlucHV0PjwvdGV4dGFyZWE+XHJcbiAgICAgIDwhLS1Db3B5VG9DbGlwYm9hcmQtLT5cclxuICAgICAgPGRpdiBjbGFzcz1cImNvcHktY2xpcGJvYXJkXCIgKm5nSWY9XCJvcHRpb25zLmVuYWJsZUNvcHlUb0NsaXBib2FyZFwiIChjbGljayk9XCJjb3B5SW5wdXRNZXNzYWdlKFRleHRBcmVhaW5wdXQpXCI+XHJcbiAgICAgICAgPGkgY2xhc3M9XCJmYXMgZmEtY29weVwiPjwvaT5cclxuICAgICAgPC9kaXY+XHJcbiAgICAgIDxkaXYgW25nQ2xhc3NdPVwieydleHBhbmRlZCc6IGlzRm9jdXNlZH1cIiBjbGFzcz1cImxhbmd1YWdlLWNvbnRhaW5lciB7e29wdGlvbnMuZXh0cmFDbGFzc01pY0xhbmd1YWdlfX1cIiAqbmdJZj1cIm9wdGlvbnMuZW5hYmxlU3BlZWNoUmVjb2duaXRpb25cIj5cclxuICAgICAgICA8c3BhbiBjbGFzcz1cInN2Zy1pY29uIHN2Zy1pY29uLTVcIiBbaW5saW5lU1ZHXT1cIm9wdGlvbnMuaWNvbk1pYz8gb3B0aW9ucy5pY29uTWljIDogJy4vc3JjL2Fzc2V0cy9pbWFnZXMvbWljLnN2ZydcIiAoY2xpY2spPVwic3RhcnRTcGVlY2hSZWNvZ25pdGlvbigpXCJcclxuICAgICAgICAgICAgICAqbmdJZj1cIiFpc01pY09uXCI+XHJcbiAgICAgICAgPC9zcGFuPlxyXG4gICAgICAgIDxzcGFuIGNsYXNzPVwic3ZnLWljb24gc3ZnLWljb24tNVwiIFtpbmxpbmVTVkddPVwib3B0aW9ucy5pY29uTWljT2ZmPyBvcHRpb25zLmljb25NaWNPZmYgOiAnLi9zcmMvYXNzZXRzL2ltYWdlcy9taWMtb2ZmLnN2ZydcIiAoY2xpY2spPVwic3RvcFNwZWVjaFJlY29nbml0aW9uKClcIlxyXG4gICAgICAgICAgICAgICpuZ0lmPVwiaXNNaWNPblwiPlxyXG4gICAgICAgIDwvc3Bhbj5cclxuICAgICAgICA8ZGl2PlxyXG4gICAgICAgICAgPHNwYW4gY2xhc3M9XCJsYW5ndWFnZS10ZXh0XCI+e3sgc2VsZWN0ZWRTcGVlY2hMYW5ndWFnZURpc3BsYXlUZXh0IH19PC9zcGFuPlxyXG4gICAgICAgICAgPHNlbGVjdCBjbGFzcz1cImxhbmd1YWdlLXNlbGVjdFwiIFtmb3JtQ29udHJvbE5hbWVdPVwiJ0xhbmd1YWdlXycrb3B0aW9ucy5uYW1lXCIgKGNoYW5nZSk9XCJvblNwZWVjaExhbmd1YWdlQ2hhbmdlKCRldmVudClcIj5cclxuICAgICAgICAgICAgPG9wdGlvbiAqbmdGb3I9XCJsZXQgbGFuZ3VhZ2Ugb2Ygb3B0aW9ucy5zcGVlY2hMYW5ndWFnZXNcIiBbdmFsdWVdPVwibGFuZ3VhZ2UuZGlhbGVjdFwiPlxyXG4gICAgICAgICAgICAgIHt7bGFuZ3VhZ2UubmFtZX19XHJcbiAgICAgICAgICAgIDwvb3B0aW9uPlxyXG4gICAgICAgICAgPC9zZWxlY3Q+XHJcblxyXG4gICAgICAgIDwvZGl2PlxyXG5cclxuXHJcbiAgICAgIDwvZGl2PlxyXG4gICAgPC9kaXY+XHJcbiAgICA8IS0tIHJlYWRvbmx5IC0tPlxyXG4gICAgPGRpdiAqbmdJZj1cIm9wdGlvbnMuaXNSZWFkb25seVwiPjxzcGFuIGNsYXNzPVwicmVhZG9ubHktdmlld1wiPnt7b3B0aW9ucy52YWx1ZX19PC9zcGFuPlxyXG4gICAgPC9kaXY+XHJcbiAgICA8ZGl2IGNsYXNzPVwic3VidGV4dC1jb250YWluZXJcIj5cclxuICAgICAgPCEtLXdvcmRDb3VudC0tPlxyXG4gICAgICA8ZGl2IGNsYXNzPVwiYmJzZi13b3JkLWNvdW50XCIgKm5nSWY9XCJvcHRpb25zLm1heFdvcmRDb3VudD4wJiZpc1Nob3dXb3JkQ291bnRcIj5cclxuICAgICAgICB7e3dvcmRDb3VudH19L3t7b3B0aW9ucy5tYXhXb3JkQ291bnR9fSBXb3JkczwvZGl2PlxyXG4gICAgICA8IS0tIENoYXJzTGltaXRNc2ctLT5cclxuICAgICAgPGRpdiBjbGFzcz1cImJic2YtY2hhcmFjdGVyLWNvdW50XCIgKm5nSWY9XCJzaG93Q2hhcnNMaW1pdE1zZ1wiXHJcbiAgICAgICAgW25nQ2xhc3NdPVwieydiYWRnZS1saWdodC13YXJuaW5nJzogY2hhcnNMaW1pdE1zZ0NsYXNzID09PSAnd2FybmluZycsICdiYWRnZS1saWdodC1kYW5nZXInIDogY2hhcnNMaW1pdE1zZ0NsYXNzID09PSAnZGFuZ2VyJyB9XCI+XHJcbiAgICAgICAge3ttYXhMaW1pdFdhcm5pbmdNc2d9fVxyXG4gICAgICA8L2Rpdj5cclxuICAgICAgPCEtLSBMYWJlbERlc2NyaXB0aW9uLS0+XHJcbiAgICAgIDxkaXYgY2xhc3M9XCJiYnNmLWNvbnRyb2wtZGVzY1wiICpuZ0lmPVwib3B0aW9ucy5sYWJlbERlc2NyaXB0aW9uIT1udWxsXCI+e3tvcHRpb25zLmxhYmVsRGVzY3JpcHRpb259fTwvZGl2PlxyXG4gICAgICA8IS0tIHJlcXVpcmVkVGV4dC0tPlxyXG4gICAgICA8ZGl2IGNsYXNzPVwiYmJzZi12YWxpZGF0aW9uXCIgW2Rpcl09XCJ0ZXh0RGlyXCIgKm5nSWY9XCIodGV4dEFyZWFGb3JtQ29udHJvbC5pbnZhbGlkICYmIHRleHRBcmVhRm9ybUNvbnRyb2wudG91Y2hlZClcIj5cclxuICAgICAgICB7e2dldEVycm9yVmFsaWRhdGlvbih0ZXh0QXJlYUZvcm1Db250cm9sLmVycm9yc3xrZXl2YWx1ZSl9fVxyXG4gICAgICA8L2Rpdj5cclxuICAgIDwvZGl2PlxyXG4gICAgPGRpdiAqbmdJZj1cIihncm91cC52YWxpZCYmZ3JvdXAuZGlydHkmJmdyb3VwLnRvdWNoZWQgKXx8KGdyb3VwLnVudG91Y2hlZCYmZ3JvdXAuaW52YWxpZCYmZ3JvdXAuZGlydHkpIFwiPlxyXG4gICAgICB7e3Jlc2V0RXJyb3IoKX19PC9kaXY+XHJcbiAgPC9kaXY+XHJcbiJdfQ==
550
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiVGV4dEFyZWEuY29tcG9uZW50LmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vLi4vLi4vcHJvamVjdHMvYmJzZi1jb250cm9scy9zcmMvbGliL2NvbnRyb2xzL1RleHRBcmVhL1RleHRBcmVhLmNvbXBvbmVudC50cyIsIi4uLy4uLy4uLy4uLy4uLy4uL3Byb2plY3RzL2Jic2YtY29udHJvbHMvc3JjL2xpYi9jb250cm9scy9UZXh0QXJlYS9UZXh0QXJlYS5jb21wb25lbnQuaHRtbCJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiQUFBQSxPQUFPLEVBQUUsU0FBUyxFQUFxQixLQUFLLEVBQUUsUUFBUSxFQUFFLE1BQU0sRUFBRSxZQUFZLEVBQUUsUUFBUSxFQUFFLE1BQU0sZUFBZSxDQUFDO0FBQzlHLE9BQU8sRUFBRSxXQUFXLEVBQUUsVUFBVSxFQUFvRSxNQUFNLGdCQUFnQixDQUFDOzs7Ozs7Ozs7QUFVM0gsTUFBTSxPQUFPLGlCQUFpQjtJQUM1QixZQUNVLGNBQThCLEVBQ04sZ0JBQWtDLEVBQy9DLG1CQUF1QyxFQUNsRCxjQUE4QixFQUM5Qix3QkFBa0QsRUFDbEQsY0FBOEIsRUFDOUIsd0JBQWtELEVBQ2xELGVBQWdDO1FBUGhDLG1CQUFjLEdBQWQsY0FBYyxDQUFnQjtRQUNOLHFCQUFnQixHQUFoQixnQkFBZ0IsQ0FBa0I7UUFDL0Msd0JBQW1CLEdBQW5CLG1CQUFtQixDQUFvQjtRQUNsRCxtQkFBYyxHQUFkLGNBQWMsQ0FBZ0I7UUFDOUIsNkJBQXdCLEdBQXhCLHdCQUF3QixDQUEwQjtRQUNsRCxtQkFBYyxHQUFkLGNBQWMsQ0FBZ0I7UUFDOUIsNkJBQXdCLEdBQXhCLHdCQUF3QixDQUEwQjtRQUNsRCxvQkFBZSxHQUFmLGVBQWUsQ0FBaUI7UUFNaEMsYUFBUSxHQUFHLElBQUksWUFBWSxFQUFFLENBQUM7UUFHeEMsY0FBUyxHQUFXLENBQUMsQ0FBQztRQUN0QixtQkFBYyxHQUFXLENBQUMsQ0FBQztRQUMzQixvQkFBZSxH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QztRQUM3QyxJQUFJLENBQUMsc0JBQXNCLENBQUMsMENBQTBDLFFBQVEsRUFBRSxJQUFJLElBQUksb0JBQW9CLEVBQUUsQ0FBQyxDQUFDO0lBQ2xILENBQUM7SUFDRCw2QkFBNkIsQ0FBQyxZQUFxQixJQUFJO1FBQ3JELHVEQUF1RDtRQUN2RCxJQUFJLENBQUMsSUFBSSxDQUFDLE9BQU8sQ0FBQyx1QkFBdUIsRUFBRTtZQUN6QyxPQUFPO1NBQ1I7UUFFRCxNQUFNLG1CQUFtQixHQUFHLFdBQVcsR0FBRyxJQUFJLENBQUMsT0FBTyxDQUFDLElBQUksQ0FBQztRQUM1RCxJQUFJLE1BQU0sR0FBRyxJQUFJLENBQUMsS0FBSyxDQUFDLEdBQUcsQ0FBQyxtQkFBbUIsQ0FBQyxDQUFDO1FBQ2pELElBQUksU0FBUyxFQUFFO1lBQ2IsTUFBTSxDQUFDLE1BQU0sRUFBRSxDQUFDO1NBQ2pCO2FBQU07WUFDTCxNQUFNLENBQUMsT0FBTyxFQUFFLENBQUM7U0FDbEI7SUFDSCxDQUFDOytHQXhtQlUsaUJBQWlCO21HQUFqQixpQkFBaUIsd0lDWDlCLHloTUErRlE7OzRGRHBGSyxpQkFBaUI7a0JBSjdCLFNBQVM7K0JBQ0UsZUFBZTs7MEJBTXRCLFFBQVE7OzBCQUFJLFFBQVE7OzBCQUNwQixRQUFROytNQVNGLEtBQUs7c0JBQWIsS0FBSztnQkFDRyxPQUFPO3NCQUFmLEtBQUs7Z0JBQ0ksUUFBUTtzQkFBakIsTUFBTSIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IENvbXBvbmVudCwgT25Jbml0LCBPbkRlc3Ryb3ksIElucHV0LCBPcHRpb25hbCwgT3V0cHV0LCBFdmVudEVtaXR0ZXIsIFNraXBTZWxmIH0gZnJvbSAnQGFuZ3VsYXIvY29yZSc7XHJcbmltcG9ydCB7IEZvcm1Db250cm9sLCBWYWxpZGF0b3JzLCBGb3JtR3JvdXAsIEFic3RyYWN0Q29udHJvbCwgQ29udHJvbENvbnRhaW5lciwgRm9ybUdyb3VwRGlyZWN0aXZlIH0gZnJvbSAnQGFuZ3VsYXIvZm9ybXMnO1xyXG5pbXBvcnQgeyBDb250cm9sVmFsaWRhdGlvblNlcnZpY2UsIExhbmd1YWdlU2VydmljZSwgVXRpbGl0eVNlcnZpY2UsIFNwZWVjaFJlY29nbml0aW9uU2VydmljZSB9IGZyb20gJ0BibnNpZ2h0cy9iYnNmLXV0aWxpdGllcyc7XHJcbmltcG9ydCB7IFN1YnNjcmlwdGlvbiB9IGZyb20gJ3J4anMnO1xyXG5pbXBvcnQgeyBDb250cm9sVXRpbGl0eSwgR2xvYmFsU2V0dGluZ3MgfSBmcm9tICcuLi8uLi9TaGFyZWQvc2VydmljZXMnO1xyXG5pbXBvcnQgeyBUZXh0QXJlYU9wdGlvbnMgfSBmcm9tICcuLi8uLi9TaGFyZWQvTW9kZWxzJztcclxuXHJcbkBDb21wb25lbnQoe1xyXG4gIHNlbGVjdG9yOiAnQkJTRi1UZXh0QXJlYScsXHJcbiAgdGVtcGxhdGVVcmw6ICcuL1RleHRBcmVhLmNvbXBvbmVudC5odG1sJ1xyXG59KVxyXG5leHBvcnQgY2xhc3MgVGV4dEFyZWFDb21wb25lbnQgaW1wbGVtZW50cyBPbkluaXQsIE9uRGVzdHJveSB7XHJcbiAgY29uc3RydWN0b3IoXHJcbiAgICBwcml2YXRlIGNvbnRyb2xVdGlsaXR5OiBDb250cm9sVXRpbGl0eSxcclxuICAgIEBPcHRpb25hbCgpIEBTa2lwU2VsZigpIHByaXZhdGUgY29udHJvbENvbnRhaW5lcjogQ29udHJvbENvbnRhaW5lcixcclxuICAgIEBPcHRpb25hbCgpIHB1YmxpYyB0ZXh0QXJlYUNvbnRyb2xIb3N0OiBGb3JtR3JvdXBEaXJlY3RpdmUsXHJcbiAgICBwcml2YXRlIHV0aWxpdHlTZXJ2aWNlOiBVdGlsaXR5U2VydmljZSxcclxuICAgIHByaXZhdGUgY29udHJvbFZhbGlkYXRpb25TZXJ2aWNlOiBDb250cm9sVmFsaWRhdGlvblNlcnZpY2UsXHJcbiAgICBwcml2YXRlIGdsb2JhbFNldHRpbmdzOiBHbG9iYWxTZXR0aW5ncyxcclxuICAgIHByaXZhdGUgc3BlZWNoUmVjb2duaXRpb25TZXJ2aWNlOiBTcGVlY2hSZWNvZ25pdGlvblNlcnZpY2UsXHJcbiAgICBwcml2YXRlIGxhbmd1YWdlU2VydmljZTogTGFuZ3VhZ2VTZXJ2aWNlXHJcbiAgKSB7XHJcbiAgICB0aGlzLmN1cnJlbnRMYW5ndWFnZSA9IGxvY2FsU3RvcmFnZS5nZXRJdGVtKCdsYW5ndWFnZScpO1xyXG4gIH1cclxuICBASW5wdXQoKSBncm91cDogRm9ybUdyb3VwO1xyXG4gIEBJbnB1dCgpIG9wdGlvbnM6IFRleHRBcmVhT3B0aW9ucztcclxuICBAT3V0cHV0KCkgb25DaGFuZ2UgPSBuZXcgRXZlbnRFbWl0dGVyKCk7XHJcblxyXG4gIHRleHRBcmVhRm9ybUNvbnRyb2w6IEFic3RyYWN0Q29udHJvbDtcclxuICB3b3JkQ291bnQ6IG51bWJlciA9IDA7XHJcbiAgd29yZENvdW50QXJyYXk6IG51bWJlciA9IDA7XHJcbiAgaXNTaG93V29yZENvdW50OiBib29sZWFuID0gZmFsc2U7XHJcbiAgbWFya0FsbEFzVG91Y2hlZDogYm9vbGVhbiA9IGZhbHNlO1xyXG4gIHZhbGlkYXRpb25SdWxlcyA9IFtdO1xyXG4gIHZhbGlkYXRpb25SdWxlc2FzeW5jID0gW107XHJcbiAgLy9Gb3IgU2hvdyB3YXJuaW5nIG1lc3NhZ2Ugb2YgbWF4IGxlbmd0aCBsaW1pdFxyXG4gIGN1cnJlbnRDaGFyc0NvdW50OiBudW1iZXIgPSAwO1xyXG4gIHNob3dDaGFyc0xpbWl0TXNnOiBib29sZWFuID0gZmFsc2U7XHJcbiAgaGFzQ2hhcnNMaW1pdFZhbGlkYXRpb25FcnJvcjogYm9vbGVhbiA9IGZhbHNlO1xyXG4gIGNoYXJzTGltaXRNc2dDbGFzczogc3RyaW5nO1xyXG4gIG1pbkNoYXJzTGltaXQ6IG51bWJlciA9IC0xOyAvL1RvIGRpc2FibGUgY2hhcnMgbGltaXQgZmVhdHVyZSBieSBkZWZhdWx0XHJcbiAgbWF4TGltaXRXYXJuaW5nTXNnOiBzdHJpbmcgPSAnJztcclxuICBpc01pY09uOiBib29sZWFuID0gZmFsc2U7XHJcbiAgcHVibGljIHRleHREaXI7XHJcbiAgaXNGb2N1c2VkOiBib29sZWFuO1xyXG4gIGN1cnJlbnRMYW5ndWFnZTogU3RyaW5nO1xyXG4gIHN1YnNjcmlwdGlvbjogU3Vic2NyaXB0aW9uO1xyXG4gIHZhbHVlQ2hhbmdlc1N1YnNjcmlwdGlvbjogU3Vic2NyaXB0aW9uO1xyXG4gIHNlbGVjdGVkU3BlZWNoTGFuZ3VhZ2VEaXNwbGF5VGV4dDogc3RyaW5nID0gJyc7XHJcblxyXG4gIC8vIEFjY2Vzc2liaWxpdHkgcHJvcGVydGllc1xyXG4gIGFyaWFEZXNjcmliZWRCeTogc3RyaW5nID0gJyc7XHJcbiAgZXJyb3JNZXNzYWdlSWQ6IHN0cmluZyA9ICcnO1xyXG4gIGNoYXJhY3RlckNvdW50SWQ6IHN0cmluZyA9ICcnO1xyXG4gIHdvcmRDb3VudElkOiBzdHJpbmcgPSAnJztcclxuXHJcbiAgbmdPbkluaXQoKSB7XHJcbiAgICAvLyBJbml0aWFsaXplIGFjY2Vzc2liaWxpdHkgSURzXHJcbiAgICB0aGlzLmVycm9yTWVzc2FnZUlkID0gYCR7dGhpcy5vcHRpb25zLm5hbWV9LWVycm9yYDtcclxuICAgIHRoaXMuY2hhcmFjdGVyQ291bnRJZCA9IGAke3RoaXMub3B0aW9ucy5uYW1lfS1jaGFyLWNvdW50YDtcclxuICAgIHRoaXMud29yZENvdW50SWQgPSBgJHt0aGlzLm9wdGlvbnMubmFtZX0td29yZC1jb3VudGA7XHJcbiAgICB0aGlzLnVwZGF0ZUFyaWFEZXNjcmliZWRCeSgpO1xyXG5cclxuICAgIC8vIEluaXRpYWxpemUgc3BlZWNoIHJlY29nbml0aW9uIHByb3BlcnRpZXMgb25seSBpZiBlbmFibGVkXHJcbiAgICBpZiAodGhpcy5vcHRpb25zLmVuYWJsZVNwZWVjaFJlY29nbml0aW9uKSB7XHJcbiAgICAgIHRoaXMuaXNNaWNPbiA9IGZhbHNlO1xyXG4gICAgICB0aGlzLnNlbGVjdGVkU3BlZWNoTGFuZ3VhZ2VEaXNwbGF5VGV4dCA9ICcnO1xyXG4gICAgfSBlbHNlIHtcclxuICAgICAgLy8gUmVzZXQgc3BlZWNoLXJlbGF0ZWQgcHJvcGVydGllcyB3aGVuIGRpc2FibGVkXHJcbiAgICAgIHRoaXMucmVzZXRTcGVlY2hQcm9wZXJ0aWVzKCk7XHJcbiAgICB9XHJcbiAgICBpZiAodGhpcy5vcHRpb25zLmlzUmVhZG9ubHkgJiYgIXRoaXMub3B0aW9ucy52YWx1ZSlcclxuICAgICAgdGhpcy5vcHRpb25zLnZhbHVlID0gdGhpcy51dGlsaXR5U2VydmljZS5nZXRSZXNvdXJjZVZhbHVlKCdOQScpO1xyXG5cclxuICAgIGlmICh0aGlzLm9wdGlvbnMuZm9yY2VEaXJlY3Rpb24pXHJcbiAgICAgIHRoaXMudGV4dERpciA9IHRoaXMub3B0aW9ucy5mb3JjZURpcmVjdGlvbiA9PSAyID8gJ3J0bCcgOiAnbHRyJztcclxuICAgIGVsc2UgdGhpcy50ZXh0RGlyID0gbG9jYWxTdG9yYWdlLmdldEl0ZW0oJ2xhbmd1YWdlJykgPT0gJ2FyJyA/ICdydGwnIDogJ2x0cic7XHJcblxyXG4gICAgdGhpcy5jb250cm9sVmFsaWRhdGlvblNlcnZpY2UuaXNDcmVhdGVkQmVmb3IgPSBmYWxzZTtcclxuXHJcbiAgICB0aGlzLmdyb3VwLmFkZENvbnRyb2wodGhpcy5vcHRpb25zLm5hbWUsIG5ldyBGb3JtQ29udHJvbCgnJykpO1xyXG4gICAgdGhpcy50ZXh0QXJlYUZvcm1Db250cm9sID0gdGhpcy5ncm91cC5jb250cm9sc1t0aGlzLm9wdGlvbnMubmFtZV07IC8vICBuZXcgRm9ybUNvbnRyb2woJycsdmFsaWRhdGlvblJ1bGVzKTtcclxuXHJcbiAgICBpZiAoIXRoaXMub3B0aW9ucy5tYXhMZW5ndGgpIHRoaXMub3B0aW9ucy5tYXhMZW5ndGggPSB0aGlzLmdsb2JhbFNldHRpbmdzLm1heExlbmd0aFRleHRBcmVhO1xyXG5cclxuICAgIGlmICghdGhpcy5vcHRpb25zLnZpZXdUeXBlKSB0aGlzLm9wdGlvbnMudmlld1R5cGUgPSB0aGlzLmdsb2JhbFNldHRpbmdzLnZpZXdUeXBlO1xyXG5cclxuICAgIGlmICh0aGlzLm9wdGlvbnMubGFiZWxLZXkgIT0gbnVsbCAmJiB0aGlzLm9wdGlvbnMubGFiZWxLZXkgIT0gJycpXHJcbiAgICAgIHRoaXMub3B0aW9ucy5sYWJlbFZhbHVlID0gdGhpcy51dGlsaXR5U2VydmljZS5nZXRSZXNvdXJjZVZhbHVlKHRoaXMub3B0aW9ucy5sYWJlbEtleSk7XHJcblxyXG4gICAgaWYgKHRoaXMub3B0aW9ucy5lbmFibGVTcGVlY2hSZWNvZ25pdGlvbikge1xyXG4gICAgICAvLyBJbml0aWFsaXplIGxhbmd1YWdlIGZvcm0gY29udHJvbFxyXG4gICAgICBjb25zdCBsYW5ndWFnZUNvbnRyb2xOYW1lID0gJ0xhbmd1YWdlXycgKyB0aGlzLm9wdGlvbnMubmFtZTtcclxuICAgICAgdGhpcy5ncm91cC5hZGRDb250cm9sKFxyXG4gICAgICAgIGxhbmd1YWdlQ29udHJvbE5hbWUsXHJcbiAgICAgICAgbmV3IEZvcm1Db250cm9sKHRoaXMub3B0aW9ucy5zZWxlY3RlZFNwZWVjaExhbmd1YWdlIHx8ICcnKVxyXG4gICAgICApO1xyXG4gICAgICAvL0dldCBhbGwgbGFuZ3VhZ2VzIGlmIG5vdCBzZXRcclxuICAgICAgaWYgKCF0aGlzLm9wdGlvbnMuc3BlZWNoTGFuZ3VhZ2VzKSB7XHJcbiAgICAgICAgdGhpcy5sYW5ndWFnZVNlcnZpY2UuZ2V0TGFuZ3VhZ2VzKCkuc3Vic2NyaWJlKChyZXN1bHQpID0+IHtcclxuICAgICAgICAgIHRoaXMub3B0aW9ucy5zcGVlY2hMYW5ndWFnZXMgPSByZXN1bHQ7XHJcbiAgICAgICAgICB0aGlzLnNldFNwZWVjaExhbmd1YWdlKCk7XHJcbiAgICAgICAgfSk7XHJcbiAgICAgIH0gZWxzZSB7XHJcbiAgICAgICAgdGhpcy5zZXRTcGVlY2hMYW5ndWFnZSgpO1xyXG4gICAgICB9XHJcbiAgICB9XHJcbiAgICB0aGlzLnRleHRBcmVhRm9ybUNvbnRyb2wuc2V0VmFsdWUodGhpcy5vcHRpb25zLnZhbHVlKTtcclxuICAgIGlmICh0aGlzLm9wdGlvbnMuY3VzdG9tVmFsaWRhdGlvbi5sZW5ndGggPiAwKSB7XHJcbiAgICAgIGxldCBWYWxpZGF0aW9ucyA9IHRoaXMub3B0aW9ucy5jdXN0b21WYWxpZGF0aW9uO1xyXG4gICAgICBmb3IgKGxldCBpbmRleCA9IDA7IGluZGV4IDwgVmFsaWRhdGlvbnMubGVuZ3RoOyBpbmRleCsrKSB7XHJcbiAgICAgICAgY29uc3QgVmFsaWRhdGlvbiA9IFZhbGlkYXRpb25zW2luZGV4XTtcclxuICAgICAgICB0aGlzLnZhbGlkYXRpb25SdWxlcy5wdXNoKFZhbGlkYXRpb24uZnVuY3Rpb25Cb2R5KTtcclxuICAgICAgfVxyXG4gICAgfVxyXG4gICAgaWYgKHRoaXMub3B0aW9ucy5taW5MZW5ndGggPiAwKSB7XHJcbiAgICAgIHRoaXMudmFsaWRhdGlvblJ1bGVzLnB1c2goVmFsaWRhdG9ycy5taW5MZW5ndGgodGhpcy5vcHRpb25zLm1pbkxlbmd0aCkpO1xyXG4gICAgfVxyXG4gICAgaWYgKHRoaXMub3B0aW9ucy5tYXhMZW5ndGggPiAwKSB7XHJcbiAgICAgIHRoaXMudmFsaWRhdGlvblJ1bGVzLnB1c2goVmFsaWRhdG9ycy5tYXhMZW5ndGgodGhpcy5vcHRpb25zLm1heExlbmd0aCkpO1xyXG5cclxuICAgICAgaWYgKCF0aGlzLm9wdGlvbnMubWF4TGVuZ3RoV2FybmluZ0xpbWl0KVxyXG4gICAgICAgIHRoaXMub3B0aW9ucy5tYXhMZW5ndGhXYXJuaW5nTGltaXQgPSB0aGlzLmdsb2JhbFNldHRpbmdzLm1heExlbmd0aFdhcm5pbmdMaW1pdDtcclxuXHJcbiAgICAgIHRoaXMubWluQ2hhcnNMaW1pdCA9IHRoaXMub3B0aW9ucy5tYXhMZW5ndGggLSB0aGlzLm9wdGlvbnMubWF4TGVuZ3RoV2FybmluZ0xpbWl0O1xyXG4gICAgfVxyXG4gICAgaWYgKHRoaXMub3B0aW9ucy5pc1JlcXVpcmVkKSB7XHJcbiAgICAgIHRoaXMudmFsaWRhdGlvblJ1bGVzLnB1c2goVmFsaWRhdG9ycy5yZXF1aXJlZCk7XHJcbiAgICB9XHJcbiAgICB0aGlzLnRleHRBcmVhRm9ybUNvbnRyb2wuc2V0VmFsaWRhdG9ycyh0aGlzLnZhbGlkYXRpb25SdWxlcyk7XHJcbiAgICB0aGlzLnRleHRBcmVhRm9ybUNvbnRyb2wuc2V0QXN5bmNWYWxpZGF0b3JzKHRoaXMudmFsaWRhdGlvblJ1bGVzYXN5bmMpO1xyXG4gICAgaWYgKHRoaXMub3B0aW9ucy5pc0Rpc2FibGVkKSB7XHJcbiAgICAgIHRoaXMudGV4dEFyZWFGb3JtQ29udHJvbC5kaXNhYmxlKCk7XHJcbiAgICB9XHJcblxyXG4gICAgLy8gT25seSBzdWJzY3JpYmUgdG8gbmdTdWJtaXQgaWYgRm9ybUdyb3VwRGlyZWN0aXZlIGlzIGF2YWlsYWJsZVxyXG4gICAgaWYgKHRoaXMudGV4dEFyZWFDb250cm9sSG9zdCkge1xyXG4gICAgICB0aGlzLnRleHRBcmVhQ29udHJvbEhvc3QubmdTdWJtaXQuc3Vic2NyaWJlKCh2YWx1ZSkgPT4ge1xyXG4gICAgICAgIHRoaXMuZ3JvdXAubWFya0FsbEFzVG91Y2hlZCgpO1xyXG4gICAgICAgIHRoaXMubWFya0FsbEFzVG91Y2hlZCA9IHRydWU7XHJcbiAgICAgIH0pO1xyXG4gICAgfVxyXG5cclxuICAgIC8vIFN1YnNjcmliZSB0byB2YWx1ZSBjaGFuZ2VzIHRvIGVuc3VyZSB3YXJuaW5nIG1lc3NhZ2VzIGFyZSBwcm9wZXJseSByZXNldFxyXG4gICAgdGhpcy52YWx1ZUNoYW5nZXNTdWJzY3JpcHRpb24gPSB0aGlzLnRleHRBcmVhRm9ybUNvbnRyb2wudmFsdWVDaGFuZ2VzLnN1YnNjcmliZSgodmFsdWUpID0+IHtcclxuICAgICAgLy8gUmVzZXQgd2FybmluZyBtZXNzYWdlIHdoZW4gY29udHJvbCBpcyBlbXB0eSBvciBudWxsXHJcbiAgICAgIGlmICghdmFsdWUgfHwgdmFsdWUudHJpbSgpLmxlbmd0aCA9PT0gMCkge1xyXG4gICAgICAgIHRoaXMuc2hvd0NoYXJzTGltaXRNc2cgPSBmYWxzZTtcclxuICAgICAgICB0aGlzLmhhc0NoYXJzTGltaXRWYWxpZGF0aW9uRXJyb3IgPSBmYWxzZTtcclxuICAgICAgICB0aGlzLm1heExpbWl0V2FybmluZ01zZyA9ICcnO1xyXG4gICAgICAgIHRoaXMuY3VycmVudENoYXJzQ291bnQgPSAwO1xyXG4gICAgICAgIHRoaXMud29yZENvdW50ID0gMDtcclxuICAgICAgICB0aGlzLndvcmRDb3VudEFycmF5ID0gMDtcclxuICAgICAgfVxyXG4gICAgfSk7XHJcbiAgfVxyXG5cclxuICBuZ0FmdGVyVmlld0luaXQoKTogdm9pZCB7XHJcbiAgICB0aGlzLmNvbnRyb2xVdGlsaXR5LnNldEF0dHJpYnV0ZUZvckNvbnRyb2wodGhpcy5vcHRpb25zKTtcclxuICB9XHJcblxyXG4gIHJlc2V0RXJyb3IgPSAoKSA9PiB7XHJcbiAgICB0aGlzLmNvbnRyb2xWYWxpZGF0aW9uU2VydmljZS5yZW1vdmVHbG9iYWxFcnJvcigpO1xyXG4gIH07XHJcblxyXG4gIHNob3dHbG9iYWxFcnJvcigpIHtcclxuICAgIHRoaXMuY29udHJvbFV0aWxpdHkuc2hvd0dsb2JhbEVycm9yKCk7XHJcbiAgfVxyXG5cclxuICBnZXRFcnJvclZhbGlkYXRpb24oRXJyb3JMaXN0KSB7XHJcbiAgICBpZiAodGhpcy5tYXJrQWxsQXNUb3VjaGVkICYmIHRoaXMuZ3JvdXAuaW52YWxpZCkge1xyXG4gICAgICB0aGlzLnNob3dHbG9iYWxFcnJvcigpO1xyXG4gICAgICB0aGlzLm1hcmtBbGxBc1RvdWNoZWQgPSBmYWxzZTtcclxuICAgIH1cclxuICAgIHJldHVybiB0aGlzLmNvbnRyb2xVdGlsaXR5LmdldEVycm9yVmFsaWRhdGlvbk1hc3NhZ2UoRXJyb3JMaXN0LCB0aGlzLmdyb3VwLCB0aGlzLm9wdGlvbnMpO1xyXG4gIH1cclxuICBnZXRJbnB1dFR5cGUodHlwZTogbnVtYmVyKSB7XHJcbiAgICByZXR1cm4gdGhpcy5jb250cm9sVXRpbGl0eS5nZXRJbnB1dFR5cGUodHlwZSk7XHJcbiAgfVxyXG5cclxuICAvLyBBY2Nlc3NpYmlsaXR5IGhlbHBlciBtZXRob2RzXHJcbiAgdXBkYXRlQXJpYURlc2NyaWJlZEJ5KCkge1xyXG4gICAgY29uc3QgZGVzY3JpYmVkQnlJZHMgPSBbXTtcclxuXHJcbiAgICBpZiAodGhpcy5vcHRpb25zLmxhYmVsRGVzY3JpcHRpb24pIHtcclxuICAgICAgZGVzY3JpYmVkQnlJZHMucHVzaChgJHt0aGlzLm9wdGlvbnMubmFtZX0tZGVzY3JpcHRpb25gKTtcclxuICAgIH1cclxuXHJcbiAgICBpZiAodGhpcy5vcHRpb25zLm1heFdvcmRDb3VudCA+IDApIHtcclxuICAgICAgZGVzY3JpYmVkQnlJZHMucHVzaCh0aGlzLndvcmRDb3VudElkKTtcclxuICAgIH1cclxuXHJcbiAgICBpZiAodGhpcy5zaG93Q2hhcnNMaW1pdE1zZykge1xyXG4gICAgICBkZXNjcmliZWRCeUlkcy5wdXNoKHRoaXMuY2hhcmFjdGVyQ291bnRJZCk7XHJcbiAgICB9XHJcblxyXG4gICAgaWYgKHRoaXMudGV4dEFyZWFGb3JtQ29udHJvbD8uaW52YWxpZCAmJiB0aGlzLnRleHRBcmVhRm9ybUNvbnRyb2w/LnRvdWNoZWQpIHtcclxuICAgICAgZGVzY3JpYmVkQnlJZHMucHVzaCh0aGlzLmVycm9yTWVzc2FnZUlkKTtcclxuICAgIH1cclxuXHJcbiAgICAvLyBPbmx5IGFkZCBzcGVlY2gtcmVsYXRlZCBkZXNjcmlwdGlvbnMgaWYgc3BlZWNoIHJlY29nbml0aW9uIGlzIGVuYWJsZWRcclxuICAgIGlmICh0aGlzLm9wdGlvbnMuZW5hYmxlU3BlZWNoUmVjb2duaXRpb24gJiYgdGhpcy5zZWxlY3RlZFNwZWVjaExhbmd1YWdlRGlzcGxheVRleHQpIHtcclxuICAgICAgZGVzY3JpYmVkQnlJZHMucHVzaChgJHt0aGlzLm9wdGlvbnMubmFtZX0tbGFuZ3VhZ2UtZGlzcGxheWApO1xyXG4gICAgfVxyXG5cclxuICAgIHRoaXMuYXJpYURlc2NyaWJlZEJ5ID0gZGVzY3JpYmVkQnlJZHMuam9pbignICcpO1xyXG4gIH1cclxuXHJcbiAgYW5ub3VuY2VUb1NjcmVlblJlYWRlcihtZXNzYWdlOiBzdHJpbmcpIHtcclxuICAgIC8vIENyZWF0ZSB0ZW1wb3JhcnkgZWxlbWVudCBmb3Igc2NyZWVuIHJlYWRlciBhbm5vdW5jZW1lbnRcclxuICAgIGNvbnN0IGFubm91bmNlbWVudCA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ2RpdicpO1xyXG4gICAgYW5ub3VuY2VtZW50LnNldEF0dHJpYnV0ZSgnYXJpYS1saXZlJywgJ3BvbGl0ZScpO1xyXG4gICAgYW5ub3VuY2VtZW50LnNldEF0dHJpYnV0ZSgnYXJpYS1hdG9taWMnLCAndHJ1ZScpO1xyXG4gICAgYW5ub3VuY2VtZW50LmNsYXNzTmFtZSA9ICdzci1vbmx5JztcclxuICAgIGFubm91bmNlbWVudC50ZXh0Q29udGVudCA9IG1lc3NhZ2U7XHJcblxyXG4gICAgZG9jdW1lbnQuYm9keS5hcHBlbmRDaGlsZChhbm5vdW5jZW1lbnQpO1xyXG5cclxuICAgIC8vIFJlbW92ZSBhZnRlciBhbm5vdW5jZW1lbnRcclxuICAgIHNldFRpbWVvdXQoKCkgPT4ge1xyXG4gICAgICBkb2N1bWVudC5ib2R5LnJlbW92ZUNoaWxkKGFubm91bmNlbWVudCk7XHJcbiAgICB9LCAxMDAwKTtcclxuICB9XHJcblxyXG4gIHJlc2V0U3BlZWNoUHJvcGVydGllcygpIHtcclxuICAgIC8vIFJlc2V0IGFsbCBzcGVlY2gtcmVsYXRlZCBwcm9wZXJ0aWVzIHdoZW4gc3BlZWNoIHJlY29nbml0aW9uIGlzIGRpc2FibGVkXHJcbiAgICB0aGlzLmlzTWljT24gPSBmYWxzZTtcclxuICAgIHRoaXMuc2VsZWN0ZWRTcGVlY2hMYW5ndWFnZURpc3BsYXlUZXh0ID0gJyc7XHJcblxyXG4gICAgLy8gQ2xlYW4gdXAgYW55IGFjdGl2ZSBzcGVlY2ggcmVjb2duaXRpb24gc3Vic2NyaXB0aW9uc1xyXG4gICAgaWYgKHRoaXMuc3Vic2NyaXB0aW9uKSB7XHJcbiAgICAgIHRoaXMuc3Vic2NyaXB0aW9uLnVuc3Vic2NyaWJlKCk7XHJcbiAgICAgIHRoaXMuc3Vic2NyaXB0aW9uID0gbnVsbDtcclxuICAgIH1cclxuXHJcbiAgICAvLyBSZW1vdmUgc3BlZWNoIGxhbmd1YWdlIGZvcm0gY29udHJvbCBpZiBpdCBleGlzdHNcclxuICAgIGNvbnN0IGxhbmd1YWdlQ29udHJvbE5hbWUgPSAnTGFuZ3VhZ2VfJyArIHRoaXMub3B0aW9ucy5uYW1lO1xyXG4gICAgaWYgKHRoaXMuZ3JvdXA/LmdldChsYW5ndWFnZUNvbnRyb2xOYW1lKSkge1xyXG4gICAgICB0aGlzLmdyb3VwLnJlbW92ZUNvbnRyb2wobGFuZ3VhZ2VDb250cm9sTmFtZSk7XHJcbiAgICB9XHJcbiAgfVxyXG5cclxuICB0cmltQ29udHJvbFZhbHVlKCkge1xyXG4gICAgbGV0IG9yaWdpbmFsVmFsdWUgPSB0aGlzLmNvbnRyb2xVdGlsaXR5LnRyaW1Db250cm9sVmFsdWUodGhpcy50ZXh0QXJlYUZvcm1Db250cm9sLnZhbHVlKTtcclxuICAgIHRoaXMudGV4dEFyZWFGb3JtQ29udHJvbC5wYXRjaFZhbHVlKG9yaWdpbmFsVmFsdWUpO1xyXG4gICAgaWYgKHRoaXMub3B0aW9ucy5wYXRjaEZ1bmN0aW9uICYmIHRoaXMub3B0aW9ucy5wYXRjaFBhdGggJiYgdGhpcy50ZXh0QXJlYUZvcm1Db250cm9sLnZhbGlkKSB7XHJcbiAgICAgIHRoaXMuY29udHJvbFV0aWxpdHkucGF0Y2hDb250cm9sVmFsdWUoXHJcbiAgICAgICAgb3JpZ2luYWxWYWx1ZSxcclxuICAgICAgICB0aGlzLm9wdGlvbnMucGF0Y2hGdW5jdGlvbixcclxuICAgICAgICB0aGlzLm9wdGlvbnMucGF0Y2hQYXRoXHJcbiAgICAgICk7XHJcbiAgICB9XHJcbiAgfVxyXG5cclxuICBvbktleURvd24oZXZlbnQ6IEtleWJvYXJkRXZlbnQpIHtcclxuICAgIGNvbnN0IHRleHRhcmVhID0gZXZlbnQudGFyZ2V0IGFzIEhUTUxUZXh0QXJlYUVsZW1lbnQ7XHJcbiAgICBjb25zdCBjdXJyZW50VmFsdWUgPSB0ZXh0YXJlYS52YWx1ZSB8fCAnJztcclxuICAgIGNvbnN0IGtleSA9IGV2ZW50LmtleTtcclxuXHJcbiAgICAvLyBBbGxvdyBuYXZpZ2F0aW9uIGtleXMgKGFycm93cywgaG9tZSwgZW5kLCBldGMuKVxyXG4gICAgY29uc3QgYWxsb3dlZEtleXMgPSBbJ0JhY2tzcGFjZScsICdEZWxldGUnLCAnVGFiJywgJ0VzY2FwZScsICdFbnRlcicsICdIb21lJywgJ0VuZCcsICdBcnJvd0xlZnQnLCAnQXJyb3dSaWdodCcsICdBcnJvd1VwJywgJ0Fycm93RG93biddO1xyXG5cclxuICAgIC8vIEFsbG93IEN0cmwvQ21kICsga2V5cyAoY29weSwgcGFzdGUsIHNlbGVjdCBhbGwsIGV0Yy4pXHJcbiAgICBpZiAoZXZlbnQuY3RybEtleSB8fCBldmVudC5tZXRhS2V5KSB7XHJcbiAgICAgIHJldHVybjsgLy8gQWxsb3cgYWxsIEN0cmwvQ21kIGNvbWJpbmF0aW9uc1xyXG4gICAgfVxyXG5cclxuICAgIC8vIElmIGl0J3MgYSBuYXZpZ2F0aW9uIGtleSwgYWxsb3cgaXRcclxuICAgIGlmIChhbGxvd2VkS2V5cy5pbmNsdWRlcyhrZXkpKSB7XHJcbiAgICAgIC8vIFNwZWNpYWwgaGFuZGxpbmcgZm9yIHdvcmQgY291bnQgb24gQmFja3NwYWNlXHJcbiAgICAgIGlmIChrZXkgPT09ICdCYWNrc3BhY2UnICYmIHRoaXMub3B0aW9ucy5tYXhXb3JkQ291bnQgPiAwKSB7XHJcbiAgICAgICAgcmV0dXJuOyAvLyBBbHdheXMgYWxsb3cgYmFja3NwYWNlIGZvciB3b3JkIGNvdW50IGNvcnJlY3Rpb25cclxuICAgICAgfVxyXG4gICAgICByZXR1cm47XHJcbiAgICB9XHJcblxyXG4gICAgLy8gQ2hlY2sgd29yZCBjb3VudCBsaW1pdFxyXG4gICAgaWYgKHRoaXMub3B0aW9ucy5tYXhXb3JkQ291bnQgPiAwKSB7XHJcbiAgICAgIGNvbnN0IGN1cnJlbnRXb3JkQ291bnQgPSBjdXJyZW50VmFsdWUudHJpbSgpID8gY3VycmVudFZhbHVlLnRyaW0oKS5zcGxpdCgvXFxzKy8pLmxlbmd0aCA6IDA7XHJcbiAgICAgIGlmIChjdXJyZW50V29yZENvdW50ID49IHRoaXMub3B0aW9ucy5tYXhXb3JkQ291bnQgJiYga2V5ICE9PSAnQmFja3NwYWNlJyAmJiBrZXkgIT09ICdEZWxldGUnKSB7XHJcbiAgICAgICAgLy8gQ2hlY2sgaWYgYWRkaW5nIHRoaXMgY2hhcmFjdGVyIHdvdWxkIGNyZWF0ZSBhIG5ldyB3b3JkXHJcbiAgICAgICAgY29uc3QgY3Vyc29yUG9zaXRpb24gPSB0ZXh0YXJlYS5zZWxlY3Rpb25TdGFydDtcclxuICAgICAgICBjb25zdCBjaGFyQmVmb3JlID0gY3Vyc29yUG9zaXRpb24gPiAwID8gY3VycmVudFZhbHVlW2N1cnNvclBvc2l0aW9uIC0gMV0gOiAnJztcclxuICAgICAgICBjb25zdCBjaGFyQWZ0ZXIgPSBjdXJzb3JQb3NpdGlvbiA8IGN1cnJlbnRWYWx1ZS5sZW5ndGggPyBjdXJyZW50VmFsdWVbY3Vyc29yUG9zaXRpb25dIDogJyc7XHJcblxyXG4gICAgICAgIC8vIElmIHdlJ3JlIHR5cGluZyBhIHNwYWNlIG9yIHRoZSBjaGFyYWN0ZXIgYmVmb3JlL2FmdGVyIGlzIGEgc3BhY2UsIHRoaXMgbWlnaHQgY3JlYXRlIGEgbmV3IHdvcmRcclxuICAgICAgICBpZiAoa2V5ID09PSAnICcgfHwgKC9cXHMvLnRlc3QoY2hhckJlZm9yZSkgJiYgISgvXFxzLy50ZXN0KGtleSkpKSkge1xyXG4gICAgICAgICAgZXZlbnQucHJldmVudERlZmF1bHQoKTtcclxuICAgICAgICAgIHJldHVybjtcclxuICAgICAgICB9XHJcbiAgICAgIH1cclxuICAgIH1cclxuXHJcbiAgICAvLyBDaGVjayBjaGFyYWN0ZXIgY291bnQgbGltaXRcclxuICAgIGlmICh0aGlzLm9wdGlvbnMubWF4TGVuZ3RoICYmIGN1cnJlbnRWYWx1ZS5sZW5ndGggPj0gdGhpcy5vcHRpb25zLm1heExlbmd0aCkge1xyXG4gICAgICAvLyBPbmx5IGFsbG93IGlmIHdlIGhhdmUgc2VsZWN0ZWQgdGV4dCAod2hpY2ggd2lsbCBiZSByZXBsYWNlZCkgb3IgbmF2aWdhdGlvbiBrZXlzXHJcbiAgICAgIGNvbnN0IGhhc1NlbGVjdGlvbiA9IHRleHRhcmVhLnNlbGVjdGlvblN0YXJ0ICE9PSB0ZXh0YXJlYS5zZWxlY3Rpb25FbmQ7XHJcbiAgICAgIGlmICghaGFzU2VsZWN0aW9uICYmICFhbGxvd2VkS2V5cy5pbmNsdWRlcyhrZXkpKSB7XHJcbiAgICAgICAgZXZlbnQucHJldmVudERlZmF1bHQoKTtcclxuICAgICAgICByZXR1cm47XHJcbiAgICAgIH1cclxuICAgIH1cclxuICB9XHJcblxyXG4gIGNvcHlJbnB1dE1lc3NhZ2UoaW5wdXRFbGVtZW50KSB7XHJcbiAgICB0aGlzLmNvbnRyb2xVdGlsaXR5LkNvcHlJbnB1dE1lc3NhZ2UoaW5wdXRFbGVtZW50KTtcclxuICAgIC8vIEFubm91bmNlIHRvIHNjcmVlbiByZWFkZXJzXHJcbiAgICB0aGlzLmFubm91bmNlVG9TY3JlZW5SZWFkZXIoJ1RleHQgY29waWVkIHRvIGNsaXBib2FyZCcpO1xyXG4gIH1cclxuXHJcbiAgb25UZXh0Q2hhbmdlKCkge1xyXG4gICAgaWYgKHRoaXMudGV4dEFyZWFGb3JtQ29udHJvbC52YWx1ZSA9PSAnJykge1xyXG4gICAgICB0aGlzLndvcmRDb3VudEFycmF5ID0gMDtcclxuICAgICAgdGhpcy53b3JkQ291bnQgPSAwO1xyXG4gICAgfSBlbHNlIHtcclxuICAgICAgdGhpcy53b3JkQ291bnRBcnJheSA9IHRoaXMudGV4dEFyZWFGb3JtQ29udHJvbC52YWx1ZS5zcGxpdCgnICcpLmxlbmd0aDtcclxuICAgICAgaWYgKHRoaXMud29yZENvdW50QXJyYXkgPiAwKSB7XHJcbiAgICAgICAgaWYgKHRoaXMud29yZENvdW50QXJyYXkgPiB0aGlzLm9wdGlvbnMubWF4V29yZENvdW50KSB7XHJcbiAgICAgICAgICB0aGlzLndvcmRDb3VudCA9IHRoaXMub3B0aW9ucy5tYXhXb3JkQ291bnQ7XHJcbiAgICAgICAgICB0aGlzLnRleHRBcmVhRm9ybUNvbnRyb2wuc2V0RXJyb3JzKHtcclxuICAgICAgICAgICAgZXJyb3JNZXNzYWdlOiBgV29yZCBjb3VudCBtdXN0IGJlIGxlc3MgdGhhbiBvciBlcXVhbCB0byAke3RoaXMub3B0aW9ucy5tYXhXb3JkQ291bnR9YFxyXG4gICAgICAgICAgfSk7XHJcbiAgICAgICAgICB0aGlzLnRleHRBcmVhRm9ybUNvbnRyb2wubWFya0FzVG91Y2hlZCgpO1xyXG4gICAgICAgICAgdGhpcy50ZXh0QXJlYUZvcm1Db250cm9sLmludmFsaWQ7XHJcbiAgICAgICAgfSBlbHNlIHtcclxuICAgICAgICAgIHRoaXMud29yZENvdW50ID0gdGhpcy53b3JkQ291bnRBcnJheTtcclxuICAgICAgICB9XHJcbiAgICAgIH1cclxuICAgIH1cclxuICAgIC8vQ2hlY2sgZm9yIG1heGxlbmd0aCBsaW1pdCBjb3VudFxyXG4gICAgLy9NYXhMZW5ndGggc2hvdWxkIGJlIGdyZWF0ZXIgdGhhbiBvciBlcXVhbHMgY2hhcnMgbGltaXQgc28gdGhhdCBtaW5DaGFyc0xpbWl0IHdvdWxkIGJlID49IDBcclxuICAgIGlmICh0aGlzLm9wdGlvbnMubWF4TGVuZ3RoICYmIHRoaXMubWluQ2hhcnNMaW1pdCA+PSAwKSB7XHJcbiAgICAgIC8vIENoZWNrIGlmIHZhbHVlIGV4aXN0cyBhbmQgaXMgbm90IGVtcHR5XHJcbiAgICAgIGNvbnN0IGNvbnRyb2xWYWx1ZSA9IHRoaXMudGV4dEFyZWFGb3JtQ29udHJvbC52YWx1ZTtcclxuICAgICAgaWYgKGNvbnRyb2xWYWx1ZSAmJiBjb250cm9sVmFsdWUudHJpbSgpLmxlbmd0aCA+IDApIHtcclxuICAgICAgICB0aGlzLmN1cnJlbnRDaGFyc0NvdW50ID0gY29udHJvbFZhbHVlLmxlbmd0aDtcclxuICAgICAgICBpZiAodGhpcy5jdXJyZW50Q2hhcnNDb3VudCA+IHRoaXMubWluQ2hhcnNMaW1pdCkge1xyXG4gICAgICAgICAgdGhpcy5zaG93Q2hhcnNMaW1pdE1zZyA9IHRydWU7XHJcbiAgICAgICAgICB0aGlzLmhhc0NoYXJzTGltaXRWYWxpZGF0aW9uRXJyb3IgPSB0cnVlO1xyXG5cclxuICAgICAgICAgIGlmICh0aGlzLmN1cnJlbnRDaGFyc0NvdW50ID09IHRoaXMub3B0aW9ucy5tYXhMZW5ndGgpIHRoaXMuY2hhcnNMaW1pdE1zZ0NsYXNzID0gJ2Rhbmdlcic7XHJcbiAgICAgICAgICBlbHNlIHRoaXMuY2hhcnNMaW1pdE1zZ0NsYXNzID0gJ3dhcm5pbmcnO1xyXG5cclxuICAgICAgICAgIC8vIE9ubHkgZ2VuZXJhdGUgd2FybmluZyBtZXNzYWdlIHdoZW4gd2UgYWN0dWFsbHkgd2FudCB0byBzaG93IGl0XHJcbiAgICAgICAgICBsZXQgbWF4OiBudW1iZXIgPSB0aGlzLm9wdGlvbnMubWF4TGVuZ3RoO1xyXG4gICAgICAgICAgbGV0IGN1cnJlbnQ6IG51bWJlciA9IHRoaXMuY3VycmVudENoYXJzQ291bnQ7XHJcbiAgICAgICAgICBsZXQgbXNnOiBzdHJpbmcgPSB0aGlzLnV0aWxpdHlTZXJ2aWNlLmdldFJlc291cmNlVmFsdWUoJ01heExlbmd0aExpbWl0V2FybmluZycpO1xyXG5cclxuICAgICAgICAgIHRoaXMubWF4TGltaXRXYXJuaW5nTXNnID0gbXNnXHJcbiAgICAgICAgICAgIC5yZXBsYWNlKCcke21heH0nLCBtYXgudG9TdHJpbmcoKSlcclxuICAgICAgICAgICAgLnJlcGxhY2UoJyR7Y3VycmVudH0nLCBjdXJyZW50LnRvU3RyaW5nKCkpO1xyXG4gICAgICAgIH0gZWxzZSB7XHJcbiAgICAgICAgICB0aGlzLnNob3dDaGFyc0xpbWl0TXNnID0gZmFsc2U7XHJcbiAgICAgICAgICB0aGlzLmhhc0NoYXJzTGltaXRWYWxpZGF0aW9uRXJyb3IgPSBmYWxzZTtcclxuICAgICAgICB9XHJcbiAgICAgIH0gZWxzZSB7XHJcbiAgICAgICAgLy8gUmVzZXQgZXZlcnl0aGluZyB3aGVuIHZhbHVlIGlzIGVtcHR5XHJcbiAgICAgICAgdGhpcy5jdXJyZW50Q2hhcnNDb3VudCA9IDA7XHJcbiAgICAgICAgdGhpcy5zaG93Q2hhcnNMaW1pdE1zZyA9IGZhbHNlO1xyXG4gICAgICAgIHRoaXMuaGFzQ2hhcnNMaW1pdFZhbGlkYXRpb25FcnJvciA9IGZhbHNlO1xyXG4gICAgICAgIHRoaXMubWF4TGltaXRXYXJuaW5nTXNnID0gJyc7XHJcbiAgICAgIH1cclxuICAgIH1cclxuICAgIHRoaXMub25DaGFuZ2UuZW1pdCh0aGlzLnRleHRBcmVhRm9ybUNvbnRyb2wudmFsdWUpO1xyXG5cclxuICAgIC8vIFVwZGF0ZSBhY2Nlc3NpYmlsaXR5IGF0dHJpYnV0ZXNcclxuICAgIHRoaXMudXBkYXRlQXJpYURlc2NyaWJlZEJ5KCk7XHJcblxyXG4gICAgLy8gQW5ub3VuY2UgY2hhcmFjdGVyIGxpbWl0IHdhcm5pbmdzIHRvIHNjcmVlbiByZWFkZXJzXHJcbiAgICBpZiAodGhpcy5zaG93Q2hhcnNMaW1pdE1zZyAmJiB0aGlzLmNoYXJzTGltaXRNc2dDbGFzcyA9PT0gJ2RhbmdlcicpIHtcclxuICAgICAgdGhpcy5hbm5vdW5jZVRvU2NyZWVuUmVhZGVyKGBDaGFyYWN0ZXIgbGltaXQgcmVhY2hlZDogJHt0aGlzLm1heExpbWl0V2FybmluZ01zZ31gKTtcclxuICAgIH1cclxuICB9XHJcblxyXG4gIG9uRm9jdXMoaXNGb2N1czogYm9vbGVhbikge1xyXG4gICAgdGhpcy5pc1Nob3dXb3JkQ291bnQgPSBpc0ZvY3VzO1xyXG5cclxuICAgIC8vb25Gb2N1c1xyXG4gICAgaWYgKGlzRm9jdXMpIHtcclxuICAgICAgaWYgKHRoaXMuaGFzQ2hhcnNMaW1pdFZhbGlkYXRpb25FcnJvcilcclxuICAgICAgICAvL2NoZWNrIGlmIHRoZXJlIHdhcyBwcmV2aW91cyB2YWxpZGF0aW9uIGVycm9yXHJcbiAgICAgICAgdGhpcy5zaG93Q2hhcnNMaW1pdE1zZyA9IHRydWU7XHJcbiAgICB9IC8vb25Gb2N1c091dFxyXG4gICAgZWxzZSB0aGlzLnNob3dDaGFyc0xpbWl0TXNnID0gZmFsc2U7XHJcbiAgfVxyXG5cclxuICAvL0V4dGVybmFsIE1ldGhvZFxyXG4gIHJlbW92ZVJlcXVpcmVkVmFsaWRhdGlvbiA9ICgpID0+IHtcclxuICAgIHRoaXMuY29udHJvbFV0aWxpdHkucmVtb3ZlUmVxdWlyZWRWYWxpZGF0aW9uKFxyXG4gICAgICB0aGlzLnRleHRBcmVhRm9ybUNvbnRyb2wsXHJcbiAgICAgIHRoaXMudmFsaWRhdGlvblJ1bGVzLFxyXG4gICAgICB0aGlzLm9wdGlvbnNcclxuICAgICk7XHJcbiAgfTtcclxuICAvL0V4dGVybmFsIE1ldGhvZFxyXG4gIGFkZFJlcXVpcmVkVmFsaWRhdGlvbiA9ICgpID0+IHtcclxuICAgIHRoaXMuY29udHJvbFV0aWxpdHkuYWRkUmVxdWlyZWRWYWxpZGF0aW9uKFxyXG4gICAgICB0aGlzLnRleHRBcmVhRm9ybUNvbnRyb2wsXHJcbiAgICAgIHRoaXMudmFsaWRhdGlvblJ1bGVzLFxyXG4gICAgICB0aGlzLm9wdGlvbnNcclxuICAgICk7XHJcbiAgfTtcclxuXHJcbiAgLy9FeHRlcm5hbCBNZXRob2RcclxuICByZW1vdmVDdXN0b21WYWxpZGF0aW9uID0gKGN1c3RvbVZhbGlkYXRpb24pID0+IHtcclxuICAgIHRoaXMuY29udHJvbFV0aWxpdHkucmVtb3ZlQ3VzdG9tVmFsaWRhdGlvbihcclxuICAgICAgdGhpcy50ZXh0QXJlYUZvcm1Db250cm9sLFxyXG4gICAgICB0aGlzLnZhbGlkYXRpb25SdWxlcyxcclxuICAgICAgY3VzdG9tVmFsaWRhdGlvblxyXG4gICAgKTtcclxuICB9O1xyXG4gIC8vRXh0ZXJuYWwgTWV0aG9kXHJcbiAgYWRkQ3VzdG9tVmFsaWRhdGlvbiA9IChjdXN0b21WYWxpZGF0aW9uKSA9PiB7XHJcbiAgICB0aGlzLmNvbnRyb2xVdGlsaXR5LmFkZEN1c3RvbVZhbGlkYXRpb24oXHJcbiAgICAgIHRoaXMudGV4dEFyZWFGb3JtQ29udHJvbCxcclxuICAgICAgdGhpcy52YWxpZGF0aW9uUnVsZXMsXHJcbiAgICAgIGN1c3RvbVZhbGlkYXRpb25cclxuICAgICk7XHJcbiAgfTtcclxuICAvL0V4dGVybmFsIE1ldGhvZFxyXG4gIGlzVmFsaWQgPSAoKSA9PiB7XHJcbiAgICB0aGlzLmNvbnRyb2xVdGlsaXR5LmlzVmFsaWQodGhpcy50ZXh0QXJlYUZvcm1Db250cm9sKTtcclxuICB9O1xyXG4gIC8vcmVnaW9uIFNwZWVjaCBSZWNvZ25pdGlvblxyXG4gIHNldFNwZWVjaExhbmd1YWdlKCkge1xyXG4gICAgLy8gR3VhcmQ6IE9ubHkgZXhlY3V0ZSBpZiBzcGVlY2ggcmVjb2duaXRpb24gaXMgZW5hYmxlZFxyXG4gICAgaWYgKCF0aGlzLm9wdGlvbnMuZW5hYmxlU3BlZWNoUmVjb2duaXRpb24pIHtcclxuICAgICAgcmV0dXJuO1xyXG4gICAgfVxyXG5cclxuICAgIGNvbnN0IGxhbmd1YWdlQ29udHJvbE5hbWUgPSAnTGFuZ3VhZ2VfJyArIHRoaXMub3B0aW9ucy5uYW1lO1xyXG5cclxuICAgIGlmICh0aGlzLm9wdGlvbnMuYXV0b1NhdmVTcGVlY2hMYW5ndWFnZXRvTG9jYWxTdG9yYWdlKSB7XHJcbiAgICAgIGxldCBzYXZlZExhbmd1YWdlID0gbG9jYWxTdG9yYWdlLmdldEl0ZW0oJ3NwZWVjaExhbmd1YWdlJyk7XHJcbiAgICAgIGlmIChzYXZlZExhbmd1YWdlKSB7XHJcbiAgICAgICAgdGhpcy5vcHRpb25zLnNlbGVjdGVkU3BlZWNoTGFuZ3VhZ2UgPSBzYXZlZExhbmd1YWdlO1xyXG4gICAgICB9IGVsc2Uge1xyXG4gICAgICAgIHRoaXMubG9hZFNlbGVjdGVkU3BlZWNoTGFuZ3VhZ2UoKTtcclxuICAgICAgICBsb2NhbFN0b3JhZ2Uuc2V0SXRlbSgnc3BlZWNoTGFuZ3VhZ2UnLCB0aGlzLm9wdGlvbnMuc2VsZWN0ZWRTcGVlY2hMYW5ndWFnZSk7XHJcbiAgICAgIH1cclxuICAgIH0gZWxzZSB7XHJcbiAgICAgIHRoaXMubG9hZFNlbGVjdGVkU3BlZWNoTGFuZ3VhZ2UoKTtcclxuICAgIH1cclxuICAgIHRoaXMuZ3JvdXAuZ2V0KGxhbmd1YWdlQ29udHJvbE5hbWUpLnNldFZhbHVlKHRoaXMub3B0aW9ucy5zZWxlY3RlZFNwZWVjaExhbmd1YWdlKTtcclxuXHJcbiAgICBjb25zdCBsYW5ndWFnZSA9IHRoaXMub3B0aW9ucy5zcGVlY2hMYW5ndWFnZXM/LmZpbmQoXHJcbiAgICAgIChsKSA9PiBsLmRpYWxlY3QgPT0gdGhpcy5vcHRpb25zLnNlbGVjdGVkU3BlZWNoTGFuZ3VhZ2VcclxuICAgICk7XHJcbiAgICB0aGlzLnNlbGVjdGVkU3BlZWNoTGFuZ3VhZ2VEaXNwbGF5VGV4dCA9IGxhbmd1YWdlPy5wcmVmaXggfHwgJyc7XHJcbiAgfVxyXG4gIGxvYWRTZWxlY3RlZFNwZWVjaExhbmd1YWdlKCkge1xyXG4gICAgLy8gR3VhcmQ6IE9ubHkgZXhlY3V0ZSBpZiBzcGVlY2ggcmVjb2duaXRpb24gaXMgZW5hYmxlZFxyXG4gICAgaWYgKCF0aGlzLm9wdGlvbnMuZW5hYmxlU3BlZWNoUmVjb2duaXRpb24pIHtcclxuICAgICAgcmV0dXJuO1xyXG4gICAgfVxyXG5cclxuICAgIGlmICghdGhpcy5vcHRpb25zLnNlbGVjdGVkU3BlZWNoTGFuZ3VhZ2UpIHtcclxuICAgICAgaWYgKFxyXG4gICAgICAgIHRoaXMuY3VycmVudExhbmd1YWdlID09ICdlbicgJiZcclxuICAgICAgICB0aGlzLm9wdGlvbnMuc3BlZWNoTGFuZ3VhZ2VzLnNvbWUoKGxhbmd1YWdlKSA9PiBsYW5ndWFnZS5lbmdsaXNoTmFtZSA9PT0gJ0VuZ2xpc2gnKVxyXG4gICAgICApIHtcclxuICAgICAgICB0aGlzLm9wdGlvbnMuc2VsZWN0ZWRTcGVlY2hMYW5ndWFnZSA9IHRoaXMub3B0aW9ucy5zcGVlY2hMYW5ndWFnZXMuZmluZChcclxuICAgICAgICAgIChsYW5ndWFnZSkgPT4gbGFuZ3VhZ2UuZW5nbGlzaE5hbWUgPT09ICdFbmdsaXNoJ1xyXG4gICAgICAgICkuZGlhbGVjdDtcclxuICAgICAgfSBlbHNlIGlmIChcclxuICAgICAgICB0aGlzLmN1cnJlbnRMYW5ndWFnZSA9PSAnYXInICYmXHJcbiAgICAgICAgdGhpcy5vcHRpb25zLnNwZWVjaExhbmd1YWdlcy5zb21lKChsYW5ndWFnZSkgPT4gbGFuZ3VhZ2UuZW5nbGlzaE5hbWUgPT09ICdBcmFiaWMnKVxyXG4gICAgICApIHtcclxuICAgICAgICB0aGlzLm9wdGlvbnMuc2VsZWN0ZWRTcGVlY2hMYW5ndWFnZSA9IHRoaXMub3B0aW9ucy5zcGVlY2hMYW5ndWFnZXMuZmluZChcclxuICAgICAgICAgIChsYW5ndWFnZSkgPT4gbGFuZ3VhZ2UuZW5nbGlzaE5hbWUgPT09ICdBcmFiaWMnXHJcbiAgICAgICAgKS5kaWFsZWN0O1xyXG4gICAgICB9IGVsc2Uge1xyXG4gICAgICAgIHRoaXMub3B0aW9ucy5zZWxlY3RlZFNwZWVjaExhbmd1YWdlID0gdGhpcy5vcHRpb25zLnNwZWVjaExhbmd1YWdlc1swXS5kaWFsZWN0O1xyXG4gICAgICB9XHJcbiAgICB9XHJcbiAgfVxyXG4gIHN0YXJ0U3BlZWNoUmVjb2duaXRpb24oKTogdm9pZCB7XHJcbiAgICAvLyBHdWFyZDogT25seSBleGVjdXRlIGlmIHNwZWVjaCByZWNvZ25pdGlvbiBpcyBlbmFibGVkXHJcbiAgICBpZiAoIXRoaXMub3B0aW9ucy5lbmFibGVTcGVlY2hSZWNvZ25pdGlvbikge1xyXG4gICAgICByZXR1cm47XHJcbiAgICB9XHJcblxyXG4gICAgaWYgKCF0aGlzLnNwZWVjaFJlY29nbml0aW9uU2VydmljZS5pc1N1cHBvcnRlZCkge1xyXG4gICAgICBjb25zdCBlcnJvck1lc3NhZ2UgPSB0aGlzLnV0aWxpdHlTZXJ2aWNlLmdldFJlc291cmNlVmFsdWUoJ0Jyb3dzZXJOb3RTdXBwb3J0U3BlZWNoUmVjb2duaXRpb24nKTtcclxuICAgICAgdGhpcy51dGlsaXR5U2VydmljZS5ub3RpZnlFcnJvck1lc3NhZ2UoZXJyb3JNZXNzYWdlKTtcclxuICAgICAgdGhpcy5hbm5vdW5jZVRvU2NyZWVuUmVhZGVyKGVycm9yTWVzc2FnZSk7XHJcbiAgICAgIHJldHVybjtcclxuICAgIH1cclxuICAgIC8vRGlzYWJsZSBTZWxlY3QgTGFuZ3VhZ2VcclxuICAgIHRoaXMuZW5hYmxlT3JEaXNhYmxlTGFuZ3VhZ2VTZWxlY3QoZmFsc2UpO1xyXG4gICAgdGhpcy5pc01pY09uID0gdHJ1ZTtcclxuXHJcbiAgICAvLyBBbm5vdW5jZSB0byBzY3JlZW4gcmVhZGVyc1xyXG4gICAgdGhpcy5hbm5vdW5jZVRvU2NyZWVuUmVhZGVyKCdTcGVlY2ggcmVjb2duaXRpb24gc3RhcnRlZC4gU3BlYWsgbm93LicpO1xyXG4gICAgdGhpcy5zdWJzY3JpcHRpb24gPSB0aGlzLnNwZWVjaFJlY29nbml0aW9uU2VydmljZVxyXG4gICAgICAuc3RhcnRMaXN0ZW5pbmcodGhpcy5vcHRpb25zLnNlbGVjdGVkU3BlZWNoTGFuZ3VhZ2UpXHJcbiAgICAgIC5zdWJzY3JpYmUoe1xyXG4gICAgICAgIG5leHQ6ICh0cmFuc2NyaXB0OiBzdHJpbmcpID0+IHtcclxuICAgICAgICAgIGlmICh0cmFuc2NyaXB0KSB7XHJcbiAgICAgICAgICAgIGlmICh0aGlzLm9wdGlvbnMudmFsdWUpIHtcclxuICAgICAgICAgICAgICB0aGlzLm9wdGlvbnMudmFsdWUgKz0gJyAnO1xyXG4gICAgICAgICAgICAgIHRoaXMuZmlyZU9uQ2hhbmdlKHRoaXMub3B0aW9ucy52YWx1ZSk7XHJcbiAgICAgICAgICAgIH1cclxuICAgICAgICAgICAgbGV0IGNoYXJJbmRleCA9IDA7XHJcbiAgICAgICAgICAgIGNvbnN0IGludGVydmFsID0gc2V0SW50ZXJ2YWwoKCkgPT4ge1xyXG4gICAgICAgICAgICAgIHRoaXMub3B0aW9ucy52YWx1ZSArPSB0cmFuc2NyaXB0W2NoYXJJbmRleF07XHJcbiAgICAgICAgICAgICAgdGhpcy5maXJlT25DaGFuZ2UodGhpcy5vcHRpb25zLnZhbHVlKTtcclxuICAgICAgICAgICAgICBjaGFySW5kZXgrKztcclxuICAgICAgICAgICAgICBpZiAoY2hhckluZGV4ID09PSB0cmFuc2NyaXB0Lmxlbmd0aCkge1xyXG4gICAgICAgICAgICAgICAgY2xlYXJJbnRlcnZhbChpbnRlcnZhbCk7XHJcbiAgICAgICAgICAgICAgfVxyXG4gICAgICAgICAgICB9LCAxMCk7XHJcbiAgICAgICAgICB9XHJcbiAgICAgICAgfSxcclxuICAgICAgICBlcnJvcjogKGVycm9yOiBhbnkpID0+IHtcclxuICAgICAgICAgIGNvbnNvbGUuZXJyb3IoZXJyb3IpO1xyXG4gICAgICAgICAgdGhpcy5zdG9wU3BlZWNoUmVjb2duaXRpb24oKTtcclxuICAgICAgICB9LFxyXG4gICAgICAgIGNvbXBsZXRlOiAoKSA9PiB7XHJcbiAgICAgICAgICAvL0VuYWJsZSBTZWxlY3QgTGFuZ3VhZ2VcclxuICAgICAgICAgIHRoaXMuZW5hYmxlT3JEaXNhYmxlTGFuZ3VhZ2VTZWxlY3QoKTtcclxuICAgICAgICAgIHRoaXMuaXNNaWNPbiA9IGZhbHNlO1xyXG4gICAgICAgICAgdGhpcy5hbm5vdW5jZVRvU2NyZWVuUmVhZGVyKCdTcGVlY2ggcmVjb2duaXRpb24gc3RvcHBlZC4nKTtcclxuICAgICAgICB9XHJcbiAgICAgIH0pO1xyXG4gIH1cclxuXHJcbiAgc3RvcFNwZWVjaFJlY29nbml0aW9uKCk6IHZvaWQge1xyXG4gICAgLy8gR3VhcmQ6IE9ubHkgZXhlY3V0ZSBpZiBzcGVlY2ggcmVjb2duaXRpb24gaXMgZW5hYmxlZFxyXG4gICAgaWYgKCF0aGlzLm9wdGlvbnMuZW5hYmxlU3BlZWNoUmVjb2duaXRpb24pIHtcclxuICAgICAgcmV0dXJuO1xyXG4gICAgfVxyXG5cclxuICAgIHRoaXMuZW5hYmxlT3JEaXNhYmxlTGFuZ3VhZ2VTZWxlY3QoKTtcclxuICAgIGlmICghdGhpcy5zcGVlY2hSZWNvZ25pdGlvblNlcnZpY2UuaXNTdXBwb3J0ZWQpIHtcclxuICAgICAgcmV0dXJuO1xyXG4gICAgfVxyXG4gICAgdGhpcy5pc01pY09uID0gZmFsc2U7XHJcbiAgICB0aGlzLnNwZWVjaFJlY29nbml0aW9uU2VydmljZS5zdG9wTGlzdGVuaW5nKCk7XHJcbiAgICBpZiAodGhpcy5zdWJzY3JpcHRpb24pIHtcclxuICAgICAgdGhpcy5zdWJzY3JpcHRpb24udW5zdWJzY3JpYmUoKTtcclxuICAgIH1cclxuXHJcbiAgICAvLyBBbm5vdW5jZSB0byBzY3JlZW4gcmVhZGVyc1xyXG4gICAgdGhpcy5hbm5vdW5jZVRvU2NyZWVuUmVhZGVyKCdTcGVlY2ggcmVjb2duaXRpb24gc3RvcHBlZC4nKTtcclxuICB9XHJcbiAgZmlyZU9uQ2hhbmdlKHRleHQpOiB2b2lkIHtcclxuICAgIGlmICh0aGlzLm9uQ2hhbmdlKSB7XHJcbiAgICAgIHRoaXMub25DaGFuZ2UuZW1pdCh0ZXh0KTtcclxuICAgIH1cclxuICB9XHJcbiAgbmdPbkRlc3Ryb3koKTogdm9pZCB7XHJcbiAgICAvLyBBbHdheXMgY2xlYW4gdXAgc3Vic2NyaXB0aW9uc1xyXG4gICAgaWYgKHRoaXMuc3Vic2NyaXB0aW9uKSB7XHJcbiAgICAgIHRoaXMuc3Vic2NyaXB0aW9uLnVuc3Vic2NyaWJlKCk7XHJcbiAgICB9XHJcbiAgICBpZiAodGhpcy52YWx1ZUNoYW5nZXNTdWJzY3JpcHRpb24pIHtcclxuICAgICAgdGhpcy52YWx1ZUNoYW5nZXNTdWJzY3JpcHRpb24udW5zdWJzY3JpYmUoKTtcclxuICAgIH1cclxuXHJcbiAgICAvLyBPbmx5IGNhbGwgc3BlZWNoIHJlY29nbml0aW9uIGNsZWFudXAgaWYgaXQgd2FzIGVuYWJsZWRcclxuICAgIGlmICh0aGlzLm9wdGlvbnMuZW5hYmxlU3BlZWNoUmVjb2duaXRpb24pIHtcclxuICAgICAgdGhpcy5zdG9wU3BlZWNoUmVjb2duaXRpb24oKTtcclxuICAgIH1cclxuICB9XHJcblxyXG4gIC8vIEtleWJvYXJkIGFjY2Vzc2liaWxpdHkgZm9yIHNwZWVjaCByZWNvZ25pdGlvbiBjb250cm9sc1xyXG4gIG9uTWljS2V5ZG93bihldmVudDogS2V5Ym9hcmRFdmVudCwgYWN0aW9uOiAnc3RhcnQnIHwgJ3N0b3AnKTogdm9pZCB7XHJcbiAgICAvLyBHdWFyZDogT25seSBleGVjdXRlIGlmIHNwZWVjaCByZWNvZ25pdGlvbiBpcyBlbmFibGVkXHJcbiAgICBpZiAoIXRoaXMub3B0aW9ucy5lbmFibGVTcGVlY2hSZWNvZ25pdGlvbikge1xyXG4gICAgICByZXR1cm47XHJcbiAgICB9XHJcblxyXG4gICAgaWYgKGV2ZW50LmtleSA9PT0gJ0VudGVyJyB8fCBldmVudC5rZXkgPT09ICcgJykge1xyXG4gICAgICBldmVudC5wcmV2ZW50RGVmYXVsdCgpO1xyXG4gICAgICBpZiAoYWN0aW9uID09PSAnc3RhcnQnKSB7XHJcbiAgICAgICAgdGhpcy5zdGFydFNwZWVjaFJlY29nbml0aW9uKCk7XHJcbiAgICAgIH0gZWxzZSB7XHJcbiAgICAgICAgdGhpcy5zdG9wU3BlZWNoUmVjb2duaXRpb24oKTtcclxuICAgICAgfVxyXG4gICAgfVxyXG4gIH1cclxuXHJcbiAgb25Db3B5S2V5ZG93bihldmVudDogS2V5Ym9hcmRFdmVudCwgaW5wdXRFbGVtZW50OiBIVE1MVGV4dEFyZWFFbGVtZW50KTogdm9pZCB7XHJcbiAgICBpZiAoZXZlbnQua2V5ID09PSAnRW50ZXInIHx8IGV2ZW50LmtleSA9PT0gJyAnKSB7XHJcbiAgICAgIGV2ZW50LnByZXZlbnREZWZhdWx0KCk7XHJcbiAgICAgIHRoaXMuY29weUlucHV0TWVzc2FnZShpbnB1dEVsZW1lbnQpO1xyXG4gICAgfVxyXG4gIH1cclxuXHJcbiAgb25TcGVlY2hMYW5ndWFnZUNoYW5nZShldmVudDogRXZlbnQpIHtcclxuICAgIC8vIEd1YXJkOiBPbmx5IGV4ZWN1dGUgaWYgc3BlZWNoIHJlY29nbml0aW9uIGlzIGVuYWJsZWRcclxuICAgIGlmICghdGhpcy5vcHRpb25zLmVuYWJsZVNwZWVjaFJlY29nbml0aW9uKSB7XHJcbiAgICAgIHJldHVybjtcclxuICAgIH1cclxuXHJcbiAgICBsZXQgc2VsZWN0ZWRMYW5nX0RpYWxlY3QgPSAoZXZlbnQudGFyZ2V0IGFzIEhUTUxTZWxlY3RFbGVtZW50KS52YWx1ZTtcclxuICAgIGNvbnN0IGxhbmd1YWdlID0gdGhpcy5vcHRpb25zLnNwZWVjaExhbmd1YWdlcz8uZmluZChcclxuICAgICAgKGwpID0+IGwuZGlhbGVjdCA9PSBzZWxlY3RlZExhbmdfRGlhbGVjdFxyXG4gICAgKTtcclxuICAgIHRoaXMuc2VsZWN0ZWRTcGVlY2hMYW5ndWFnZURpc3BsYXlUZXh0ID0gbGFuZ3VhZ2U/LnByZWZpeCB8fCAnJztcclxuICAgIHRoaXMub3B0aW9ucy5zZWxlY3RlZFNwZWVjaExhbmd1YWdlID0gc2VsZWN0ZWRMYW5nX0RpYWxlY3Q7XHJcblxyXG4gICAgY29uc3QgbGFuZ3VhZ2VDb250cm9sTmFtZSA9ICdMYW5ndWFnZV8nICsgdGhpcy5vcHRpb25zLm5hbWU7XHJcbiAgICBsZXQgc2VsZWN0ID0gdGhpcy5ncm91cC5nZXQobGFuZ3VhZ2VDb250cm9sTmFtZSk7XHJcbiAgICBzZWxlY3Quc2V0VmFsdWUoc2VsZWN0ZWRMYW5nX0RpYWxlY3QpO1xyXG5cclxuICAgIGlmICh0aGlzLm9wdGlvbnMuYXV0b1NhdmVTcGVlY2hMYW5ndWFnZXRvTG9jYWxTdG9yYWdlKSB7XHJcbiAgICAgIGxvY2FsU3RvcmFnZS5zZXRJdGVtKCdzcGVlY2hMYW5ndWFnZScsIHNlbGVjdGVkTGFuZ19EaWFsZWN0KTtcclxuICAgIH1cclxuXHJcbiAgICAvLyBBbm5vdW5jZSBsYW5ndWFnZSBjaGFuZ2UgdG8gc2NyZWVuIHJlYWRlcnNcclxuICAgIHRoaXMuYW5ub3VuY2VUb1NjcmVlblJlYWRlcihgU3BlZWNoIHJlY29nbml0aW9uIGxhbmd1YWdlIGNoYW5nZWQgdG8gJHtsYW5ndWFnZT8ubmFtZSB8fCBzZWxlY3RlZExhbmdfRGlhbGVjdH1gKTtcclxuICB9XHJcbiAgZW5hYmxlT3JEaXNhYmxlTGFuZ3VhZ2VTZWxlY3QoaXNFbmFibGVkOiBib29sZWFuID0gdHJ1ZSkge1xyXG4gICAgLy8gR3VhcmQ6IE9ubHkgZXhlY3V0ZSBpZiBzcGVlY2ggcmVjb2duaXRpb24gaXMgZW5hYmxlZFxyXG4gICAgaWYgKCF0aGlzLm9wdGlvbnMuZW5hYmxlU3BlZWNoUmVjb2duaXRpb24pIHtcclxuICAgICAgcmV0dXJuO1xyXG4gICAgfVxyXG5cclxuICAgIGNvbnN0IGxhbmd1YWdlQ29udHJvbE5hbWUgPSAnTGFuZ3VhZ2VfJyArIHRoaXMub3B0aW9ucy5uYW1lO1xyXG4gICAgbGV0IHNlbGVjdCA9IHRoaXMuZ3JvdXAuZ2V0KGxhbmd1YWdlQ29udHJvbE5hbWUpO1xyXG4gICAgaWYgKGlzRW5hYmxlZCkge1xyXG4gICAgICBzZWxlY3QuZW5hYmxlKCk7XHJcbiAgICB9IGVsc2Uge1xyXG4gICAgICBzZWxlY3QuZGlzYWJsZSgpO1xyXG4gICAgfVxyXG4gIH1cclxuICAvLyNlbmRSZWdpb25cclxufVxyXG5cclxuXHJcbiIsIjxkaXYgY2xhc3M9XCJmb3JtLWdyb3VwIGJic2YtY29udHJvbCBiYnNmLXRleHRhcmVhXCIgW2Zvcm1Hcm91cF09XCJncm91cFwiPlxyXG4gIDxkaXYgW25nQ2xhc3NdPVwiKG9wdGlvbnMudmlld1R5cGU9PTEpPydiYnNmLXZlcnRpY2FsJzonYmJzZi1ob3Jpem9udGFsJ1wiPlxyXG4gICAgPCEtLWxhYmVsLS0+XHJcbiAgICA8bGFiZWwgKm5nSWY9XCIhb3B0aW9ucy5oaWRlTGFiZWxcIiBjbGFzcz1cImJic2YtbGFiZWwge3tvcHRpb25zLmxhYmVsRXh0cmFDbGFzc2VzfX1cIj5cclxuICAgICAge3tvcHRpb25zLmxhYmVsVmFsdWV9fVxyXG4gICAgICA8IS0tQXN0ZXJpc2stLT5cclxuICAgICAgPHNwYW4gKm5nSWY9XCIoKG9wdGlvbnMuc2hvd0FzdGVyaXNrJiZvcHRpb25zLmlzUmVxdWlyZWQpfHwob3B0aW9ucy5pc1JlcXVpcmVkKSkmJiFvcHRpb25zLmlzUmVhZG9ubHlcIlxyXG4gICAgICAgIGNsYXNzPVwidGV4dC1kYW5nZXJcIj4qPC9zcGFuPlxyXG4gICAgPC9sYWJlbD5cclxuICAgIDxkaXYgKm5nSWY9XCIhb3B0aW9ucy5pc1JlYWRvbmx5XCIgY2xhc3M9XCJiYnNmLWlucHV0LWNvbnRhaW5lclwiIFtuZ0NsYXNzXT1cIntcclxuICAgICAgJ3AtMTIwcHgnOiBvcHRpb25zLmVuYWJsZVNwZWVjaFJlY29nbml0aW9uICYmIG9wdGlvbnMuZW5hYmxlQ29weVRvQ2xpcGJvYXJkLFxyXG4gICAgICAncC04MHB4Jzogb3B0aW9ucy5lbmFibGVTcGVlY2hSZWNvZ25pdGlvbiAmJiAhb3B0aW9ucy5lbmFibGVDb3B5VG9DbGlwYm9hcmQsXHJcbiAgICAgICdwLTQwcHgnOiAhb3B0aW9ucy5lbmFibGVTcGVlY2hSZWNvZ25pdGlvbiAmJiBvcHRpb25zLmVuYWJsZUNvcHlUb0NsaXBib2FyZFxyXG4gICAgfVwiPlxyXG4gICAgICA8IS0taW5wdXQtLT5cclxuICAgICAgPHRleHRhcmVhIGNsYXNzPVwiZm9ybS1jb250cm9sIHt7b3B0aW9ucy5leHRyYUNsYXNzZXN9fVwiIChmb2N1cyk9XCJvbkZvY3VzKHRydWUpXCIgKGZvY3Vzb3V0KT1cIm9uRm9jdXMoZmFsc2UpXCJcclxuICAgICAgICBbZGlyXT1cInRleHREaXJcIiBbYXR0ci5hcmlhLWludmFsaWRdPVwidGV4dEFyZWFGb3JtQ29udHJvbC5pbnZhbGlkICYmIHRleHRBcmVhRm9ybUNvbnRyb2wudG91Y2hlZFwiXHJcbiAgICAgICAgW2F0dHIuYXJpYS1kZXNjcmliZWRieV09XCJhcmlhRGVzY3JpYmVkQnlcIiBbYXR0ci5hcmlhLWxhYmVsXT1cIm9wdGlvbnMubGFiZWxWYWx1ZSB8fCBvcHRpb25zLnBsYWNlaG9sZGVyXCJcclxuICAgICAgICBmb3JtQ29udHJvbE5hbWU9XCJ7e29wdGlvbnMubmFtZX19XCJcclxuICAgICAgICBbY2xhc3MuaXMtaW52YWxpZF09XCJ0ZXh0QXJlYUZvcm1Db250cm9sLmludmFsaWQgJiYgdGV4dEFyZWFGb3JtQ29udHJvbC50b3VjaGVkXCJcclxuICAgICAgICBwbGFjZWhvbGRlcj1cInt7b3B0aW9ucy5wbGFjZWhvbGRlcn19XCIgaWQ9XCJ7e29wdGlvbnMubmFtZX19XCIgYXV0b2NvbXBsZXRlPVwie3tvcHRpb25zLmF1dG9Db21wbGV0ZX19XCJcclxuICAgICAgICAoY2hhbmdlKT1cInRyaW1Db250cm9sVmFsdWUoKVwiIHJvd3M9XCJ7e29wdGlvbnMucm93c319XCIgKGtleXVwKT1cIm9uVGV4dENoYW5nZSgpXCIgY29scz1cInt7b3B0aW9ucy5jb2xzfX1cIlxyXG4gICAgICAgIFthdHRyLm1pbmxlbmd0aF09XCJvcHRpb25zLm1pbkxlbmd0aFwiIFsobmdNb2RlbCldPVwib3B0aW9ucy52YWx1ZVwiIChrZXlkb3duKT1cIm9uS2V5RG93bigkZXZlbnQpXCJcclxuICAgICAgICBbYXR0ci5tYXhsZW5ndGhdPVwib3B0aW9ucy5tYXhMZW5ndGhcIiByb2xlPVwidGV4dGJveFwiIFthdHRyLmFyaWEtbXVsdGlsaW5lXT1cInRydWVcIiAjVGV4dEFyZWFpbnB1dD48L3RleHRhcmVhPlxyXG4gICAgICA8IS0tQ29weVRvQ2xpcGJvYXJkLS0+XHJcbiAgICAgIDxidXR0b24gdHlwZT1cImJ1dHRvblwiIGNsYXNzPVwiY29weS1jbGlwYm9hcmRcIiAqbmdJZj1cIm9wdGlvbnMuZW5hYmxlQ29weVRvQ2xpcGJvYXJkXCJcclxuICAgICAgICAoY2xpY2spPVwiY29weUlucHV0TWVzc2FnZShUZXh0QXJlYWlucHV0KVwiIChrZXlkb3duKT1cIm9uQ29weUtleWRvd24oJGV2ZW50LCBUZXh0QXJlYWlucHV0KVwiXHJcbiAgICAgICAgW2F0dHIuYXJpYS1sYWJlbF09XCInQ29weSB0ZXh0IHRvIGNsaXBib2FyZCdcIiB0aXRsZT1cIkNvcHkgdGV4dCB0byBjbGlwYm9hcmRcIiB0YWJpbmRleD1cIjBcIj5cclxuICAgICAgICA8aSBjbGFzcz1cImZhcyBmYS1jb3B5XCIgYXJpYS1oaWRkZW49XCJ0cnVlXCI+PC9pPlxyXG4gICAgICA8L2J1dHRvbj5cclxuICAgICAgPGRpdiBbbmdDbGFzc109XCJ7J2V4cGFuZGVkJzogaXNGb2N1c2VkfVwiIGNsYXNzPVwibGFuZ3VhZ2UtY29udGFpbmVyIHt7b3B0aW9ucy5leHRyYUNsYXNzTWljTGFuZ3VhZ2V9fVwiXHJcbiAgICAgICAgKm5nSWY9XCJvcHRpb25zLmVuYWJsZVNwZWVjaFJlY29nbml0aW9uXCIgcm9sZT1cInJlZ2lvblwiIFthdHRyLmFyaWEtbGFiZWxdPVwiJ1NwZWVjaCByZWNvZ25pdGlvbiBjb250cm9scydcIj5cclxuXHJcbiAgICAgICAgPCEtLSBTdGFydCBTcGVlY2ggUmVjb2duaXRpb24gQnV0dG9uIC0tPlxyXG4gICAgICAgIDxidXR0b24gdHlwZT1cImJ1dHRvblwiIGNsYXNzPVwic3ZnLWljb24gc3ZnLWljb24tNSBzcGVlY2gtY29udHJvbC1idG5cIlxyXG4gICAgICAgICAgW2lubGluZVNWR109XCJvcHRpb25zLmljb25NaWMgfHwgJ2Fzc2V0cy9iYnNmLWNvbnRyb2xzL2ltYWdlcy9taWMuc3ZnJ1wiIChjbGljayk9XCJzdGFydFNwZWVjaFJlY29nbml0aW9uKClcIlxyXG4gICAgICAgICAgKGtleWRvd24pPVwib25NaWNLZXlkb3duKCRldmVudCwgJ3N0YXJ0JylcIiAqbmdJZj1cIm9wdGlvbnMuZW5hYmxlU3BlZWNoUmVjb2duaXRpb24gJiYgIWlzTWljT25cIlxyXG4gICAgICAgICAgW2F0dHIuYXJpYS1sYWJlbF09XCInU3RhcnQgc3BlZWNoIHJlY29nbml0aW9uJ1wiIHRpdGxlPVwiU3RhcnQgc3BlZWNoIHJlY29nbml0aW9uXCIgdGFiaW5kZXg9XCIwXCJcclxuICAgICAgICAgIFthdHRyLmFyaWEtcHJlc3NlZF09XCJmYWxzZVwiPlxyXG4gICAgICAgIDwvYnV0dG9uPlxyXG5cclxuICAgICAgICA8IS0tIFN0b3AgU3BlZWNoIFJlY29nbml0aW9uIEJ1dHRvbiAtLT5cclxuICAgICAgICA8YnV0dG9uIHR5cGU9XCJidXR0b25cIiBjbGFzcz1cInN2Zy1pY29uIHN2Zy1pY29uLTUgc3BlZWNoLWNvbnRyb2wtYnRuXCJcclxuICAgICAgICAgIFtpbmxpbmVTVkddPVwib3B0aW9ucy5pY29uTWljT2ZmIHx8ICdhc3NldHMvYmJzZi1jb250cm9scy9pbWFnZXMvbWljLW9mZi5zdmcnXCJcclxuICAgICAgICAgIChjbGljayk9XCJzdG9wU3BlZWNoUmVjb2duaXRpb24oKVwiIChrZXlkb3duKT1cIm9uTWljS2V5ZG93bigkZXZlbnQsICdzdG9wJylcIlxyXG4gICAgICAgICAgKm5nSWY9XCJvcHRpb25zLmVuYWJsZVNwZWVjaFJlY29nbml0aW9uICYmIGlzTWljT25cIiBbYXR0ci5hcmlhLWxhYmVsXT1cIidTdG9wIHNwZWVjaCByZWNvZ25pdGlvbidcIlxyXG4gICAgICAgICAgdGl0bGU9XCJTdG9wIHNwZWVjaCByZWNvZ25pdGlvblwiIHRhYmluZGV4PVwiMFwiIFthdHRyLmFyaWEtcHJlc3NlZF09XCJ0cnVlXCI+XHJcbiAgICAgICAgPC9idXR0b24+XHJcblxyXG4gICAgICAgIDxkaXYgY2xhc3M9XCJsYW5ndWFnZS1jb250cm9sc1wiPlxyXG4gICAgICAgICAgPHNwYW4gY2xhc3M9XCJsYW5ndWFnZS10ZXh0XCIgW2F0dHIuaWRdPVwib3B0aW9ucy5uYW1lICsgJy1sYW5ndWFnZS1kaXNwbGF5J1wiXHJcbiAgICAgICAgICAgIGFyaWEtbGl2ZT1cInBvbGl0ZVwiPnt7IG9wdGlvbnMuZW5hYmxlU3BlZWNoUmVjb2duaXRpb24gPyBzZWxlY3RlZFNwZWVjaExhbmd1YWdlRGlzcGxheVRleHQgOiAnJyB9fTwvc3Bhbj5cclxuXHJcbiAgICAgICAgICA8bGFiZWwgW2Zvcl09XCInTGFuZ3VhZ2VfJytvcHRpb25zLm5hbWVcIiBjbGFzcz1cInNyLW9ubHlcIj5cclxuICAgICAgICAgICAgU2VsZWN0IHNwZWVjaCByZWNvZ25pdGlvbiBsYW5ndWFnZVxyXG4gICAgICAgICAgPC9sYWJlbD5cclxuICAgICAgICAgIDxzZWxlY3QgY2xhc3M9XCJsYW5ndWFnZS1zZWxlY3RcIiBbZm9ybUNvbnRyb2xOYW1lXT1cIidMYW5ndWFnZV8nK29wdGlvbnMubmFtZVwiIFtpZF09XCInTGFuZ3VhZ2VfJytvcHRpb25zLm5hbWVcIlxyXG4gICAgICAgICAgICAoY2hhbmdlKT1cIm9uU3BlZWNoTGFuZ3VhZ2VDaGFuZ2UoJGV2ZW50KVwiIFthdHRyLmFyaWEtZGVzY3JpYmVkYnldPVwib3B0aW9ucy5uYW1lICsgJy1sYW5ndWFnZS1kaXNwbGF5J1wiPlxyXG4gICAgICAgICAgICA8b3B0aW9uICpuZ0Zvcj1cImxldCBsYW5ndWFnZSBvZiBvcHRpb25zLnNwZWVjaExhbmd1YWdlc1wiIFt2YWx1ZV09XCJsYW5ndWFnZS5kaWFsZWN0XCI+XHJcbiAgICAgICAgICAgICAge3tsYW5ndWFnZS5uYW1lfX1cclxuICAgICAgICAgICAgPC9vcHRpb24+XHJcbiAgICAgICAgICA8L3NlbGVjdD5cclxuICAgICAgICA8L2Rpdj5cclxuICAgICAgPC9kaXY+XHJcbiAgICA8L2Rpdj5cclxuICAgIDwhLS0gcmVhZG9ubHkgLS0+XHJcbiAgICA8ZGl2ICpuZ0lmPVwib3B0aW9ucy5pc1JlYWRvbmx5XCI+PHNwYW4gY2xhc3M9XCJyZWFkb25seS12aWV3XCI+e3tvcHRpb25zLnZhbHVlfX08L3NwYW4+XHJcbiAgICA8L2Rpdj5cclxuICAgIDxkaXYgY2xhc3M9XCJzdWJ0ZXh0LWNvbnRhaW5lclwiPlxyXG4gICAgICA8IS0td29yZENvdW50LS0+XHJcbiAgICAgIDxkaXYgY2xhc3M9XCJiYnNmLXdvcmQtY291bnRcIiAqbmdJZj1cIm9wdGlvbnMubWF4V29yZENvdW50PjAmJmlzU2hvd1dvcmRDb3VudFwiIFthdHRyLmlkXT1cIndvcmRDb3VudElkXCJcclxuICAgICAgICBhcmlhLWxpdmU9XCJwb2xpdGVcIiBbYXR0ci5hcmlhLWxhYmVsXT1cIidXb3JkIGNvdW50OiAnICsgd29yZENvdW50ICsgJyBvZiAnICsgb3B0aW9ucy5tYXhXb3JkQ291bnQgKyAnIHdvcmRzJ1wiPlxyXG4gICAgICAgIHt7d29yZENvdW50fX0ve3tvcHRpb25zLm1heFdvcmRDb3VudH19IFdvcmRzXHJcbiAgICAgIDwvZGl2PlxyXG5cclxuICAgICAgPCEtLSBDaGFyc0xpbWl0TXNnLS0+XHJcbiAgICAgIDxkaXYgY2xhc3M9XCJiYnNmLWNoYXJhY3Rlci1jb3VudFwiICpuZ0lmPVwic2hvd0NoYXJzTGltaXRNc2dcIiBbYXR0ci5pZF09XCJjaGFyYWN0ZXJDb3VudElkXCIgYXJpYS1saXZlPVwicG9saXRlXCJcclxuICAgICAgICBbYXR0ci5hcmlhLWF0b21pY109XCJ0cnVlXCJcclxuICAgICAgICBbbmdDbGFzc109XCJ7J2JhZGdlLWxpZ2h0LXdhcm5pbmcnOiBjaGFyc0xpbWl0TXNnQ2xhc3MgPT09ICd3YXJuaW5nJywgJ2JhZGdlLWxpZ2h0LWRhbmdlcicgOiBjaGFyc0xpbWl0TXNnQ2xhc3MgPT09ICdkYW5nZXInIH1cIj5cclxuICAgICAgICB7e21heExpbWl0V2FybmluZ01zZ319XHJcbiAgICAgIDwvZGl2PlxyXG5cclxuICAgICAgPCEtLSBMYWJlbERlc2NyaXB0aW9uLS0+XHJcbiAgICAgIDxkaXYgY2xhc3M9XCJiYnNmLWNvbnRyb2wtZGVzY1wiICpuZ0lmPVwib3B0aW9ucy5sYWJlbERlc2NyaXB0aW9uIT1udWxsXCIgW2F0dHIuaWRdPVwib3B0aW9ucy5uYW1lICsgJy1kZXNjcmlwdGlvbidcIj5cclxuICAgICAgICB7e29wdGlvbnMubGFiZWxEZXNjcmlwdGlvbn19XHJcbiAgICAgIDwvZGl2PlxyXG5cclxuICAgICAgPCEtLSByZXF1aXJlZFRleHQtLT5cclxuICAgICAgPGRpdiBjbGFzcz1cImJic2YtdmFsaWRhdGlvblwiIFtkaXJdPVwidGV4dERpclwiICpuZ0lmPVwiKHRleHRBcmVhRm9ybUNvbnRyb2wuaW52YWxpZCAmJiB0ZXh0QXJlYUZvcm1Db250cm9sLnRvdWNoZWQpXCJcclxuICAgICAgICBbYXR0ci5pZF09XCJlcnJvck1lc3NhZ2VJZFwiIHJvbGU9XCJhbGVydFwiIGFyaWEtbGl2ZT1cImFzc2VydGl2ZVwiIFthdHRyLmFyaWEtYXRvbWljXT1cInRydWVcIj5cclxuICAgICAgICB7e2dldEVycm9yVmFsaWRhdGlvbih0ZXh0QXJlYUZvcm1Db250cm9sLmVycm9yc3xrZXl2YWx1ZSl9fVxyXG4gICAgICA8L2Rpdj5cclxuICAgIDwvZGl2PlxyXG4gICAgPGRpdiAqbmdJZj1cIihncm91cC52YWxpZCYmZ3JvdXAuZGlydHkmJmdyb3VwLnRvdWNoZWQgKXx8KGdyb3VwLnVudG91Y2hlZCYmZ3JvdXAuaW52YWxpZCYmZ3JvdXAuZGlydHkpIFwiPlxyXG4gICAgICB7e3Jlc2V0RXJyb3IoKX19PC9kaXY+XHJcbiAgPC9kaXY+Il19