@duoduo-oba/ng-devui
Version:
DevUI components based on Angular
680 lines • 52.6 kB
JavaScript
/**
* @fileoverview added by tsickle
* Generated from: auto-complete.directive.ts
* @suppress {checkTypes,constantProperty,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc
*/
import { ChangeDetectorRef, ComponentFactoryResolver, Directive, ElementRef, EventEmitter, forwardRef, HostListener, Injector, Input, Output, TemplateRef, ViewContainerRef, HostBinding, Renderer2 } from '@angular/core';
import { NG_VALUE_ACCESSOR } from '@angular/forms';
import { fromEvent, of } from 'rxjs';
import { map, filter, debounceTime, switchMap, tap } from 'rxjs/operators';
import { PositionService } from '@duoduo-oba/ng-devui/position';
import { AutoCompletePopupComponent } from './auto-complete-popup.component';
export class AutoCompleteDirective {
/**
* @param {?} elementRef
* @param {?} viewContainerRef
* @param {?} componentFactoryResolver
* @param {?} renderer
* @param {?} injector
* @param {?} positionService
* @param {?} changeDetectorRef
*/
constructor(elementRef, viewContainerRef, componentFactoryResolver, renderer, injector, positionService, changeDetectorRef) {
this.elementRef = elementRef;
this.viewContainerRef = viewContainerRef;
this.componentFactoryResolver = componentFactoryResolver;
this.renderer = renderer;
this.injector = injector;
this.positionService = positionService;
this.changeDetectorRef = changeDetectorRef;
this.autocomplete = 'off';
this.autocapitalize = 'off';
this.autocorrect = 'off';
this.sceneType = ''; // sceneType使用场景:select(下拉框) suggest(联想)
// sceneType使用场景:select(下拉框) suggest(联想)
this.tipsText = ''; // 提示文字
this.maxHeight = 300;
/**
* 【可选】启用数据懒加载,默认不启用
*/
this.enableLazyLoad = false;
this.loadMore = new EventEmitter();
this.selectValue = new EventEmitter();
this.transInputFocusEmit = new EventEmitter(); // input状态传给父组件函数
// input状态传给父组件函数
this.KEYBOARD_EVENT_NOT_REFRESH = ['escape', 'enter', 'arrowup', 'arrowdown',
/*ie 10 edge */ 'esc', 'up', 'down'];
this.popTipsText = '';
this.focus = false;
this.placement = 'bottom-left';
this.onChange = (/**
* @param {?} _
* @return {?}
*/
(_) => null);
this.onTouched = (/**
* @return {?}
*/
() => null);
this.delay = 300;
this.valueChanges = this.registerInputEvent(elementRef);
this.minLength = 1;
this.itemTemplate = null;
this.noResultItemTemplate = null;
this.formatter = (/**
* @param {?} item
* @return {?}
*/
(item) => item ? (item.label || item.toString()) : '');
this.valueParser = (/**
* @param {?} item
* @return {?}
*/
(item) => item);
}
/**
* @return {?}
*/
ngOnInit() {
// 调用时机:input keyup
this.subscription = this.valueChanges
.subscribe((/**
* @param {?} source
* @return {?}
*/
source => this.onSourceChange(source)));
// 动态的创建了popup组件,
/** @type {?} */
const factory = this.componentFactoryResolver.resolveComponentFactory(AutoCompletePopupComponent);
this.popupRef = this.viewContainerRef.createComponent(factory, this.viewContainerRef.length, this.injector);
this.fillPopup(this.source);
if (!this.searchFn) {
this.searchFn = (/**
* @param {?} term
* @return {?}
*/
(term) => {
return of(this.source.filter((/**
* @param {?} lang
* @return {?}
*/
lang => this.formatter(lang).toLowerCase().indexOf(term.toLowerCase()) !== -1)));
});
}
// 调用时机:选中回车或者鼠标单击下拉选项
this.popupRef.instance.registerOnChange((/**
* @param {?} item
* @return {?}
*/
item => {
if (item.type === 'loadMore') {
this.loadMore.emit(item.value);
return;
}
/** @type {?} */
const value = this.valueParser(item.value);
this.writeValue(value);
this.onChange(value);
this.hidePopup();
this.selectValue.emit(item.value);
if (this.overview && this.overview !== 'single') {
setTimeout((/**
* @return {?}
*/
() => {
this.restLatestSource();
}), 0);
}
}));
}
/**
* @param {?} changes
* @return {?}
*/
ngOnChanges(changes) {
if (changes && this.popupRef && changes.source) {
this.fillPopup(this.source);
}
}
/**
* @return {?}
*/
restLatestSource() {
if (this.latestSource && this.latestSource.length > 0) {
this.writeValue('');
this.clearInputValue();
this.showLatestSource();
}
}
// 调用时机:input keyup
/**
* @param {?} source
* @return {?}
*/
onSourceChange(source) {
if (!this.elementRef.nativeElement.value) {
if (this.sceneType !== 'select') { // 下拉场景不展示最近输入
this.showLatestSource();
}
else {
this.showSource(source, true, true);
}
}
else {
this.showSource(source, true, true);
}
}
/**
* @private
* @return {?}
*/
showLatestSource() {
/** @type {?} */
let tempSource = [];
if (this.latestSource && this.latestSource.length > 0) {
this.searchFn('').subscribe((/**
* @param {?} source
* @return {?}
*/
source => {
/** @type {?} */
const t = this.latestSource.slice(-5);
tempSource = t.filter((/**
* @param {?} data
* @return {?}
*/
data => {
if (!data.label) {
return source.find((/**
* @param {?} item
* @return {?}
*/
item => item === data));
}
else {
return source.find((/**
* @param {?} item
* @return {?}
*/
item => item.label === data.label));
}
}));
/** @type {?} */
const pop = this.popupRef.instance;
pop.reset();
this.popTipsText = '最近输入';
this.fillPopup(tempSource);
pop.isOpen = true;
this.changeDetectorRef.markForCheck();
}));
}
if (tempSource.length <= 0) {
this.hidePopup();
}
}
/**
* @private
* @param {?} source
* @param {?} setOpen
* @param {?} isReset
* @return {?}
*/
showSource(source, setOpen, isReset) {
if ((source && source.length) || this.noResultItemTemplate) {
/** @type {?} */
const pop = this.popupRef.instance;
if (isReset) {
pop.reset();
}
this.popTipsText = this.tipsText || '';
this.fillPopup(source, this.value);
if (setOpen) {
pop.isOpen = true;
}
this.changeDetectorRef.markForCheck();
}
else {
this.hidePopup();
}
}
/**
* @param {?} obj
* @return {?}
*/
writeValue(obj) {
this.value = this.formatter(obj) || '';
this.writeInputValue(this.value);
}
/**
* @param {?} fn
* @return {?}
*/
registerOnChange(fn) {
this.onChange = fn;
}
/**
* @param {?} fn
* @return {?}
*/
registerOnTouched(fn) {
this.onTouched = fn;
}
/**
* @param {?} isDisabled
* @return {?}
*/
setDisabledState(isDisabled) {
this.disabled = isDisabled;
this.renderer.setProperty(this.elementRef.nativeElement, 'disabled', isDisabled);
if (this.popupRef) {
this.popupRef.instance.setDisabledState(isDisabled);
}
}
/**
* @return {?}
*/
ngOnDestroy() {
this.unSubscription();
}
/**
* @param {?} $event
* @return {?}
*/
onFocus($event) {
this.focus = true;
this.transInputFocusEmit.emit({
focus: true,
popupRef: this.popupRef
});
/** @type {?} */
const isOpen = this.sceneType !== 'select';
if (this.sceneType === 'select') {
this.searchFn('').subscribe((/**
* @param {?} source
* @return {?}
*/
source => {
this.showSource(source, isOpen, false);
}));
}
else {
if (!this.elementRef.nativeElement.value) {
this.showLatestSource();
}
else {
this.searchFn(this.elementRef.nativeElement.value).subscribe((/**
* @param {?} source
* @return {?}
*/
source => {
this.showSource(source, true, false);
}));
}
}
}
/**
* @param {?} $event
* @return {?}
*/
onBlur($event) {
this.focus = false;
this.onTouched();
}
/**
* @param {?} $event
* @return {?}
*/
onEscKeyup($event) {
this.hidePopup();
}
/**
* @param {?} $event
* @return {?}
*/
onEnterKeyDown($event) {
if (!this.popupRef.instance.source || !this.popupRef.instance.isOpen) {
return;
}
if (this.popupRef) {
this.popupRef.instance.selectCurrentItem($event);
}
}
/**
* @param {?} $event
* @return {?}
*/
onArrowUpKeyDown($event) {
if (this.popupRef) {
$event.preventDefault();
$event.stopPropagation();
this.popupRef.instance.prev();
}
}
/**
* @param {?} $event
* @return {?}
*/
onArrowDownKeyDown($event) {
if (this.popupRef) {
$event.preventDefault();
$event.stopPropagation();
this.popupRef.instance.next();
}
}
/**
* @param {?} $event
* @return {?}
*/
onDocumentClick($event) {
if (this.focus) {
this.transInputFocusEmit.emit({
focus: this.focus,
popupRef: this.popupRef
});
}
if (this.popupRef && !this.popupRef.instance.isOpen) {
return;
}
/** @type {?} */
const hostElement = this.elementRef.nativeElement;
if (!hostElement.contains($event.target)) {
this.hidePopup();
this.transInputFocusEmit.emit({
focus: false,
popupRef: this.popupRef
});
}
}
/**
* @private
* @return {?}
*/
hidePopup() {
if (this.popupRef) {
this.popupRef.instance.isOpen = false;
}
}
/**
* @private
* @param {?=} source
* @param {?=} term
* @return {?}
*/
fillPopup(source, term) {
this.position = this.positionService.position(this.elementRef.nativeElement);
/** @type {?} */
const pop = this.popupRef.instance;
pop.source = source;
pop.maxHeight = this.maxHeight;
pop.term = term;
pop.disabledKey = this.disabledKey;
pop.enableLazyLoad = this.enableLazyLoad;
['formatter', 'itemTemplate', 'noResultItemTemplate', 'cssClass', 'dropdown', 'popTipsText', 'position', 'overview']
.forEach((/**
* @param {?} key
* @return {?}
*/
key => {
if (this[key] !== undefined) {
pop[key] = this[key];
}
}));
}
/**
* @private
* @param {?} value
* @return {?}
*/
writeInputValue(value) {
this.renderer.setProperty(this.elementRef.nativeElement, 'value', value);
}
/**
* @private
* @return {?}
*/
clearInputValue() {
this.renderer.setProperty(this.elementRef.nativeElement, 'value', '');
}
/**
* @private
* @return {?}
*/
unSubscription() {
if (this.subscription) {
this.subscription.unsubscribe();
this.subscription = null;
}
}
/**
* @param {?} term
* @return {?}
*/
onTermChange(term) {
this.value = term;
if (this.popupRef) {
this.popupRef.instance.term = term;
}
this.onChange(term);
}
/**
* @private
* @param {?} elementRef
* @return {?}
*/
registerInputEvent(elementRef) {
return fromEvent(elementRef.nativeElement, 'keyup')
.pipe(filter((/**
* @param {?} e
* @return {?}
*/
(e) => {
return this.KEYBOARD_EVENT_NOT_REFRESH.indexOf(e.key.toLocaleLowerCase()) === -1;
})), map((/**
* @param {?} e
* @return {?}
*/
(e) => e.target.value)), tap((/**
* @param {?} term
* @return {?}
*/
term => this.onTouched())), filter((/**
* @param {?} term
* @return {?}
*/
term => !this.disabled && this.searchFn && term.length >= 0)), debounceTime(this.delay), tap((/**
* @param {?} term
* @return {?}
*/
term => this.onTermChange(term))), switchMap((/**
* @param {?} term
* @return {?}
*/
term => this.searchFn(term, this))));
}
}
AutoCompleteDirective.decorators = [
{ type: Directive, args: [{
selector: '[dAutoComplete]',
exportAs: 'autoComplete',
providers: [{
provide: NG_VALUE_ACCESSOR,
useExisting: forwardRef((/**
* @return {?}
*/
() => AutoCompleteDirective)),
multi: true
}]
},] }
];
/** @nocollapse */
AutoCompleteDirective.ctorParameters = () => [
{ type: ElementRef },
{ type: ViewContainerRef },
{ type: ComponentFactoryResolver },
{ type: Renderer2 },
{ type: Injector },
{ type: PositionService },
{ type: ChangeDetectorRef }
];
AutoCompleteDirective.propDecorators = {
autocomplete: [{ type: HostBinding, args: ['attr.autocomplete',] }],
autocapitalize: [{ type: HostBinding, args: ['attr.autocapitalize',] }],
autocorrect: [{ type: HostBinding, args: ['attr.autocorrect',] }],
disabled: [{ type: Input }],
cssClass: [{ type: Input }],
delay: [{ type: Input }],
minLength: [{ type: Input }],
itemTemplate: [{ type: Input }],
noResultItemTemplate: [{ type: Input }],
formatter: [{ type: Input }],
sceneType: [{ type: Input }],
tipsText: [{ type: Input }],
overview: [{ type: Input }],
latestSource: [{ type: Input }],
source: [{ type: Input }],
valueParser: [{ type: Input }],
searchFn: [{ type: Input }],
dropdown: [{ type: Input }],
maxHeight: [{ type: Input }],
disabledKey: [{ type: Input }],
enableLazyLoad: [{ type: Input }],
loadMore: [{ type: Output }],
selectValue: [{ type: Output }],
transInputFocusEmit: [{ type: Output }],
onFocus: [{ type: HostListener, args: ['focus', ['$event'],] }],
onBlur: [{ type: HostListener, args: ['blur', ['$event'],] }],
onEscKeyup: [{ type: HostListener, args: ['keydown.esc', ['$event'],] }],
onEnterKeyDown: [{ type: HostListener, args: ['keydown.Enter', ['$event'],] }],
onArrowUpKeyDown: [{ type: HostListener, args: ['keydown.ArrowUp', ['$event'],] }],
onArrowDownKeyDown: [{ type: HostListener, args: ['keydown.ArrowDown', ['$event'],] }],
onDocumentClick: [{ type: HostListener, args: ['document:click', ['$event'],] }]
};
if (false) {
/** @type {?} */
AutoCompleteDirective.prototype.autocomplete;
/** @type {?} */
AutoCompleteDirective.prototype.autocapitalize;
/** @type {?} */
AutoCompleteDirective.prototype.autocorrect;
/** @type {?} */
AutoCompleteDirective.prototype.disabled;
/** @type {?} */
AutoCompleteDirective.prototype.cssClass;
/** @type {?} */
AutoCompleteDirective.prototype.delay;
/** @type {?} */
AutoCompleteDirective.prototype.minLength;
/** @type {?} */
AutoCompleteDirective.prototype.itemTemplate;
/** @type {?} */
AutoCompleteDirective.prototype.noResultItemTemplate;
/** @type {?} */
AutoCompleteDirective.prototype.formatter;
/** @type {?} */
AutoCompleteDirective.prototype.sceneType;
/** @type {?} */
AutoCompleteDirective.prototype.tipsText;
/** @type {?} */
AutoCompleteDirective.prototype.overview;
/** @type {?} */
AutoCompleteDirective.prototype.latestSource;
/** @type {?} */
AutoCompleteDirective.prototype.source;
/** @type {?} */
AutoCompleteDirective.prototype.valueParser;
/** @type {?} */
AutoCompleteDirective.prototype.searchFn;
/** @type {?} */
AutoCompleteDirective.prototype.dropdown;
/** @type {?} */
AutoCompleteDirective.prototype.maxHeight;
/** @type {?} */
AutoCompleteDirective.prototype.disabledKey;
/**
* 【可选】启用数据懒加载,默认不启用
* @type {?}
*/
AutoCompleteDirective.prototype.enableLazyLoad;
/** @type {?} */
AutoCompleteDirective.prototype.loadMore;
/** @type {?} */
AutoCompleteDirective.prototype.selectValue;
/** @type {?} */
AutoCompleteDirective.prototype.transInputFocusEmit;
/** @type {?} */
AutoCompleteDirective.prototype.KEYBOARD_EVENT_NOT_REFRESH;
/** @type {?} */
AutoCompleteDirective.prototype.popupRef;
/** @type {?} */
AutoCompleteDirective.prototype.popTipsText;
/** @type {?} */
AutoCompleteDirective.prototype.position;
/** @type {?} */
AutoCompleteDirective.prototype.focus;
/**
* @type {?}
* @private
*/
AutoCompleteDirective.prototype.valueChanges;
/**
* @type {?}
* @private
*/
AutoCompleteDirective.prototype.value;
/**
* @type {?}
* @private
*/
AutoCompleteDirective.prototype.placement;
/**
* @type {?}
* @private
*/
AutoCompleteDirective.prototype.subscription;
/**
* @type {?}
* @private
*/
AutoCompleteDirective.prototype.onChange;
/**
* @type {?}
* @private
*/
AutoCompleteDirective.prototype.onTouched;
/**
* @type {?}
* @private
*/
AutoCompleteDirective.prototype.elementRef;
/**
* @type {?}
* @private
*/
AutoCompleteDirective.prototype.viewContainerRef;
/**
* @type {?}
* @private
*/
AutoCompleteDirective.prototype.componentFactoryResolver;
/**
* @type {?}
* @private
*/
AutoCompleteDirective.prototype.renderer;
/**
* @type {?}
* @private
*/
AutoCompleteDirective.prototype.injector;
/**
* @type {?}
* @private
*/
AutoCompleteDirective.prototype.positionService;
/**
* @type {?}
* @private
*/
AutoCompleteDirective.prototype.changeDetectorRef;
}
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiYXV0by1jb21wbGV0ZS5kaXJlY3RpdmUuanMiLCJzb3VyY2VSb290Ijoibmc6Ly9uZy1kZXZ1aS9hdXRvLWNvbXBsZXRlLyIsInNvdXJjZXMiOlsiYXV0by1jb21wbGV0ZS5kaXJlY3RpdmUudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6Ijs7Ozs7QUFBQSxPQUFPLEVBQ0wsaUJBQWlCLEVBQ2pCLHdCQUF3QixFQUV4QixTQUFTLEVBQ1QsVUFBVSxFQUNWLFlBQVksRUFDWixVQUFVLEVBQ1YsWUFBWSxFQUNaLFFBQVEsRUFDUixLQUFLLEVBR0wsTUFBTSxFQUNOLFdBQVcsRUFDWCxnQkFBZ0IsRUFDaEIsV0FBVyxFQUdYLFNBQVMsRUFDVixNQUFNLGVBQWUsQ0FBQztBQUN2QixPQUFPLEVBQXdCLGlCQUFpQixFQUFFLE1BQU0sZ0JBQWdCLENBQUM7QUFDekUsT0FBTyxFQUFFLFNBQVMsRUFBNEIsRUFBRSxFQUFFLE1BQU0sTUFBTSxDQUFDO0FBQy9ELE9BQU8sRUFBRSxHQUFHLEVBQUUsTUFBTSxFQUFFLFlBQVksRUFBRSxTQUFTLEVBQUUsR0FBRyxFQUFFLE1BQU0sZ0JBQWdCLENBQUM7QUFDM0UsT0FBTyxFQUFFLGVBQWUsRUFBRSxNQUFNLG1CQUFtQixDQUFDO0FBQ3BELE9BQU8sRUFBRSwwQkFBMEIsRUFBRSxNQUFNLGlDQUFpQyxDQUFDO0FBVzdFLE1BQU0sT0FBTyxxQkFBcUI7Ozs7Ozs7Ozs7SUE4Q2hDLFlBQW9CLFVBQXNCLEVBQ2hDLGdCQUFrQyxFQUNsQyx3QkFBa0QsRUFDbEQsUUFBbUIsRUFDbkIsUUFBa0IsRUFDbEIsZUFBZ0MsRUFDaEMsaUJBQW9DO1FBTjFCLGVBQVUsR0FBVixVQUFVLENBQVk7UUFDaEMscUJBQWdCLEdBQWhCLGdCQUFnQixDQUFrQjtRQUNsQyw2QkFBd0IsR0FBeEIsd0JBQXdCLENBQTBCO1FBQ2xELGFBQVEsR0FBUixRQUFRLENBQVc7UUFDbkIsYUFBUSxHQUFSLFFBQVEsQ0FBVTtRQUNsQixvQkFBZSxHQUFmLGVBQWUsQ0FBaUI7UUFDaEMsc0JBQWlCLEdBQWpCLGlCQUFpQixDQUFtQjtRQW5EWixpQkFBWSxHQUFHLEtBQUssQ0FBQztRQUNuQixtQkFBYyxHQUFHLEtBQUssQ0FBQztRQUMxQixnQkFBVyxHQUFHLEtBQUssQ0FBQztRQVE1QyxjQUFTLEdBQUcsRUFBRSxDQUFDLENBQUMsd0NBQXdDOztRQUN4RCxhQUFRLEdBQUcsRUFBRSxDQUFDLENBQUMsT0FBTztRQVV0QixjQUFTLEdBQUcsR0FBRyxDQUFDOzs7O1FBS2hCLG1CQUFjLEdBQUcsS0FBSyxDQUFDO1FBQ3RCLGFBQVEsR0FBRyxJQUFJLFlBQVksRUFBTyxDQUFDO1FBQ25DLGdCQUFXLEdBQUcsSUFBSSxZQUFZLEVBQU8sQ0FBQztRQUN0Qyx3QkFBbUIsR0FBRyxJQUFJLFlBQVksRUFBTyxDQUFDLENBQUMsaUJBQWlCOztRQUMxRSwrQkFBMEIsR0FBRyxDQUFDLFFBQVEsRUFBRSxPQUFPLEVBQUUsU0FBUyxFQUFFLFdBQVc7WUFDckUsZUFBZSxDQUFDLEtBQUssRUFBRSxJQUFJLEVBQUUsTUFBTSxDQUFDLENBQUM7UUFHdkMsZ0JBQVcsR0FBRyxFQUFFLENBQUM7UUFFakIsVUFBSyxHQUFHLEtBQUssQ0FBQztRQUlOLGNBQVMsR0FBRyxhQUFhLENBQUM7UUFFMUIsYUFBUTs7OztRQUFHLENBQUMsQ0FBTSxFQUFFLEVBQUUsQ0FBQyxJQUFJLEVBQUM7UUFDNUIsY0FBUzs7O1FBQUcsR0FBRyxFQUFFLENBQUMsSUFBSSxFQUFDO1FBUzdCLElBQUksQ0FBQyxLQUFLLEdBQUcsR0FBRyxDQUFDO1FBQ2pCLElBQUksQ0FBQyxZQUFZLEdBQUcsSUFBSSxDQUFDLGtCQUFrQixDQUFDLFVBQVUsQ0FBQyxDQUFDO1FBQ3hELElBQUksQ0FBQyxTQUFTLEdBQUcsQ0FBQyxDQUFDO1FBQ25CLElBQUksQ0FBQyxZQUFZLEdBQUcsSUFBSSxDQUFDO1FBQ3pCLElBQUksQ0FBQyxvQkFBb0IsR0FBRyxJQUFJLENBQUM7UUFDakMsSUFBSSxDQUFDLFNBQVM7Ozs7UUFBRyxDQUFDLElBQVMsRUFBRSxFQUFFLENBQUMsSUFBSSxDQUFDLENBQUMsQ0FBQyxDQUFDLElBQUksQ0FBQyxLQUFLLElBQUksSUFBSSxDQUFDLFFBQVEsRUFBRSxDQUFDLENBQUMsQ0FBQyxDQUFDLEVBQUUsQ0FBQSxDQUFDO1FBQzVFLElBQUksQ0FBQyxXQUFXOzs7O1FBQUcsQ0FBQyxJQUFTLEVBQUUsRUFBRSxDQUFDLElBQUksQ0FBQSxDQUFDO0lBQ3pDLENBQUM7Ozs7SUFFRCxRQUFRO1FBQ04sbUJBQW1CO1FBQ25CLElBQUksQ0FBQyxZQUFZLEdBQUcsSUFBSSxDQUFDLFlBQVk7YUFDbEMsU0FBUzs7OztRQUFDLE1BQU0sQ0FBQyxFQUFFLENBQUMsSUFBSSxDQUFDLGNBQWMsQ0FBQyxNQUFNLENBQUMsRUFBQyxDQUFDOzs7Y0FHOUMsT0FBTyxHQUFHLElBQUksQ0FBQyx3QkFBd0IsQ0FBQyx1QkFBdUIsQ0FBQywwQkFBMEIsQ0FBQztRQUNqRyxJQUFJLENBQUMsUUFBUSxHQUFHLElBQUksQ0FBQyxnQkFBZ0IsQ0FBQyxlQUFlLENBQUMsT0FBTyxFQUFFLElBQUksQ0FBQyxnQkFBZ0IsQ0FBQyxNQUFNLEVBQUUsSUFBSSxDQUFDLFFBQVEsQ0FBQyxDQUFDO1FBRTVHLElBQUksQ0FBQyxTQUFTLENBQUMsSUFBSSxDQUFDLE1BQU0sQ0FBQyxDQUFDO1FBRTVCLElBQUksQ0FBQyxJQUFJLENBQUMsUUFBUSxFQUFFO1lBQ2xCLElBQUksQ0FBQyxRQUFROzs7O1lBQUcsQ0FBQyxJQUFJLEVBQUUsRUFBRTtnQkFDdkIsT0FBTyxFQUFFLENBQUMsSUFBSSxDQUFDLE1BQU0sQ0FBQyxNQUFNOzs7O2dCQUFDLElBQUksQ0FBQyxFQUFFLENBQUMsSUFBSSxDQUFDLFNBQVMsQ0FBQyxJQUFJLENBQUMsQ0FBQyxXQUFXLEVBQUUsQ0FBQyxPQUFPLENBQUMsSUFBSSxDQUFDLFdBQVcsRUFBRSxDQUFDLEtBQUssQ0FBQyxDQUFDLEVBQUMsQ0FBQyxDQUFDO1lBQy9HLENBQUMsQ0FBQSxDQUFDO1NBQ0g7UUFFRCxzQkFBc0I7UUFDdEIsSUFBSSxDQUFDLFFBQVEsQ0FBQyxRQUFRLENBQUMsZ0JBQWdCOzs7O1FBQUMsSUFBSSxDQUFDLEVBQUU7WUFDN0MsSUFBSSxJQUFJLENBQUMsSUFBSSxLQUFLLFVBQVUsRUFBRTtnQkFDNUIsSUFBSSxDQUFDLFFBQVEsQ0FBQyxJQUFJLENBQUMsSUFBSSxDQUFDLEtBQUssQ0FBQyxDQUFDO2dCQUMvQixPQUFPO2FBQ1I7O2tCQUNLLEtBQUssR0FBRyxJQUFJLENBQUMsV0FBVyxDQUFDLElBQUksQ0FBQyxLQUFLLENBQUM7WUFDMUMsSUFBSSxDQUFDLFVBQVUsQ0FBQyxLQUFLLENBQUMsQ0FBQztZQUN2QixJQUFJLENBQUMsUUFBUSxDQUFDLEtBQUssQ0FBQyxDQUFDO1lBQ3JCLElBQUksQ0FBQyxTQUFTLEVBQUUsQ0FBQztZQUNqQixJQUFJLENBQUMsV0FBVyxDQUFDLElBQUksQ0FBQyxJQUFJLENBQUMsS0FBSyxDQUFDLENBQUM7WUFDbEMsSUFBSSxJQUFJLENBQUMsUUFBUSxJQUFJLElBQUksQ0FBQyxRQUFRLEtBQUssUUFBUSxFQUFFO2dCQUMvQyxVQUFVOzs7Z0JBQUMsR0FBRyxFQUFFO29CQUNkLElBQUksQ0FBQyxnQkFBZ0IsRUFBRSxDQUFDO2dCQUMxQixDQUFDLEdBQUUsQ0FBQyxDQUFDLENBQUM7YUFDUDtRQUNILENBQUMsRUFBQyxDQUFDO0lBQ0wsQ0FBQzs7Ozs7SUFFRCxXQUFXLENBQUMsT0FBc0I7UUFDaEMsSUFBSSxPQUFPLElBQUksSUFBSSxDQUFDLFFBQVEsSUFBSSxPQUFPLENBQUMsTUFBTSxFQUFFO1lBQzlDLElBQUksQ0FBQyxTQUFTLENBQUMsSUFBSSxDQUFDLE1BQU0sQ0FBQyxDQUFDO1NBQzdCO0lBQ0gsQ0FBQzs7OztJQUVELGdCQUFnQjtRQUNkLElBQUksSUFBSSxDQUFDLFlBQVksSUFBSSxJQUFJLENBQUMsWUFBWSxDQUFDLE1BQU0sR0FBRyxDQUFDLEVBQUU7WUFDckQsSUFBSSxDQUFDLFVBQVUsQ0FBQyxFQUFFLENBQUMsQ0FBQztZQUNwQixJQUFJLENBQUMsZUFBZSxFQUFFLENBQUM7WUFDdkIsSUFBSSxDQUFDLGdCQUFnQixFQUFFLENBQUM7U0FDekI7SUFDSCxDQUFDOzs7Ozs7SUFHRCxjQUFjLENBQUMsTUFBVztRQUN4QixJQUFJLENBQUMsSUFBSSxDQUFDLFVBQVUsQ0FBQyxhQUFhLENBQUMsS0FBSyxFQUFFO1lBQ3hDLElBQUksSUFBSSxDQUFDLFNBQVMsS0FBSyxRQUFRLEVBQUUsRUFBRSxjQUFjO2dCQUMvQyxJQUFJLENBQUMsZ0JBQWdCLEVBQUUsQ0FBQzthQUN6QjtpQkFBTTtnQkFDTCxJQUFJLENBQUMsVUFBVSxDQUFDLE1BQU0sRUFBRSxJQUFJLEVBQUUsSUFBSSxDQUFDLENBQUM7YUFDckM7U0FDRjthQUFNO1lBQ0wsSUFBSSxDQUFDLFVBQVUsQ0FBQyxNQUFNLEVBQUUsSUFBSSxFQUFFLElBQUksQ0FBQyxDQUFDO1NBQ3JDO0lBQ0gsQ0FBQzs7Ozs7SUFFTyxnQkFBZ0I7O1lBQ2xCLFVBQVUsR0FBRyxFQUFFO1FBQ25CLElBQUksSUFBSSxDQUFDLFlBQVksSUFBSSxJQUFJLENBQUMsWUFBWSxDQUFDLE1BQU0sR0FBRyxDQUFDLEVBQUU7WUFDckQsSUFBSSxDQUFDLFFBQVEsQ0FBQyxFQUFFLENBQUMsQ0FBQyxTQUFTOzs7O1lBQUMsTUFBTSxDQUFDLEVBQUU7O3NCQUM3QixDQUFDLEdBQUcsSUFBSSxDQUFDLFlBQVksQ0FBQyxLQUFLLENBQUMsQ0FBQyxDQUFDLENBQUM7Z0JBQ3JDLFVBQVUsR0FBRyxDQUFDLENBQUMsTUFBTTs7OztnQkFBQyxJQUFJLENBQUMsRUFBRTtvQkFDM0IsSUFBSSxDQUFDLElBQUksQ0FBQyxLQUFLLEVBQUU7d0JBQ2YsT0FBTyxNQUFNLENBQUMsSUFBSTs7Ozt3QkFBQyxJQUFJLENBQUMsRUFBRSxDQUFDLElBQUksS0FBSyxJQUFJLEVBQUMsQ0FBQztxQkFDM0M7eUJBQU07d0JBQ0wsT0FBTyxNQUFNLENBQUMsSUFBSTs7Ozt3QkFBQyxJQUFJLENBQUMsRUFBRSxDQUFDLElBQUksQ0FBQyxLQUFLLEtBQUssSUFBSSxDQUFDLEtBQUssRUFBQyxDQUFDO3FCQUN2RDtnQkFDSCxDQUFDLEVBQUMsQ0FBQzs7c0JBRUcsR0FBRyxHQUFHLElBQUksQ0FBQyxRQUFRLENBQUMsUUFBUTtnQkFDbEMsR0FBRyxDQUFDLEtBQUssRUFBRSxDQUFDO2dCQUNaLElBQUksQ0FBQyxXQUFXLEdBQUcsTUFBTSxDQUFDO2dCQUMxQixJQUFJLENBQUMsU0FBUyxDQUFDLFVBQVUsQ0FBQyxDQUFDO2dCQUMzQixHQUFHLENBQUMsTUFBTSxHQUFHLElBQUksQ0FBQztnQkFDbEIsSUFBSSxDQUFDLGlCQUFpQixDQUFDLFlBQVksRUFBRSxDQUFDO1lBQ3hDLENBQUMsRUFBQyxDQUFDO1NBQ0o7UUFFRCxJQUFJLFVBQVUsQ0FBQyxNQUFNLElBQUksQ0FBQyxFQUFFO1lBQzFCLElBQUksQ0FBQyxTQUFTLEVBQUUsQ0FBQztTQUNsQjtJQUNILENBQUM7Ozs7Ozs7O0lBRU8sVUFBVSxDQUFDLE1BQVcsRUFBRSxPQUFZLEVBQUUsT0FBWTtRQUN4RCxJQUFJLENBQUMsTUFBTSxJQUFJLE1BQU0sQ0FBQyxNQUFNLENBQUMsSUFBSSxJQUFJLENBQUMsb0JBQW9CLEVBQUU7O2tCQUNwRCxHQUFHLEdBQUcsSUFBSSxDQUFDLFFBQVEsQ0FBQyxRQUFRO1lBQ2xDLElBQUksT0FBTyxFQUFFO2dCQUNYLEdBQUcsQ0FBQyxLQUFLLEVBQUUsQ0FBQzthQUNiO1lBQ0QsSUFBSSxDQUFDLFdBQVcsR0FBRyxJQUFJLENBQUMsUUFBUSxJQUFJLEVBQUUsQ0FBQztZQUN2QyxJQUFJLENBQUMsU0FBUyxDQUFDLE1BQU0sRUFBRSxJQUFJLENBQUMsS0FBSyxDQUFDLENBQUM7WUFDbkMsSUFBSSxPQUFPLEVBQUU7Z0JBQ1gsR0FBRyxDQUFDLE1BQU0sR0FBRyxJQUFJLENBQUM7YUFDbkI7WUFDRCxJQUFJLENBQUMsaUJBQWlCLENBQUMsWUFBWSxFQUFFLENBQUM7U0FDdkM7YUFBTTtZQUNMLElBQUksQ0FBQyxTQUFTLEVBQUUsQ0FBQztTQUNsQjtJQUNILENBQUM7Ozs7O0lBRUQsVUFBVSxDQUFDLEdBQVE7UUFDakIsSUFBSSxDQUFDLEtBQUssR0FBRyxJQUFJLENBQUMsU0FBUyxDQUFDLEdBQUcsQ0FBQyxJQUFJLEVBQUUsQ0FBQztRQUN2QyxJQUFJLENBQUMsZUFBZSxDQUFDLElBQUksQ0FBQyxLQUFLLENBQUMsQ0FBQztJQUNuQyxDQUFDOzs7OztJQUVELGdCQUFnQixDQUFDLEVBQU87UUFDdEIsSUFBSSxDQUFDLFFBQVEsR0FBRyxFQUFFLENBQUM7SUFDckIsQ0FBQzs7Ozs7SUFFRCxpQkFBaUIsQ0FBQyxFQUFPO1FBQ3ZCLElBQUksQ0FBQyxTQUFTLEdBQUcsRUFBRSxDQUFDO0lBQ3RCLENBQUM7Ozs7O0lBRUQsZ0JBQWdCLENBQUMsVUFBbUI7UUFDbEMsSUFBSSxDQUFDLFFBQVEsR0FBRyxVQUFVLENBQUM7UUFDM0IsSUFBSSxDQUFDLFFBQVEsQ0FBQyxXQUFXLENBQUMsSUFBSSxDQUFDLFVBQVUsQ0FBQyxhQUFhLEVBQUUsVUFBVSxFQUFFLFVBQVUsQ0FBQyxDQUFDO1FBQ2pGLElBQUksSUFBSSxDQUFDLFFBQVEsRUFBRTtZQUNqQixJQUFJLENBQUMsUUFBUSxDQUFDLFFBQVEsQ0FBQyxnQkFBZ0IsQ0FBQyxVQUFVLENBQUMsQ0FBQztTQUNyRDtJQUNILENBQUM7Ozs7SUFFRCxXQUFXO1FBQ1QsSUFBSSxDQUFDLGNBQWMsRUFBRSxDQUFDO0lBQ3hCLENBQUM7Ozs7O0lBR0QsT0FBTyxDQUFDLE1BQVc7UUFDakIsSUFBSSxDQUFDLEtBQUssR0FBRyxJQUFJLENBQUM7UUFDbEIsSUFBSSxDQUFDLG1CQUFtQixDQUFDLElBQUksQ0FBQztZQUM1QixLQUFLLEVBQUUsSUFBSTtZQUNYLFFBQVEsRUFBRSxJQUFJLENBQUMsUUFBUTtTQUN4QixDQUFDLENBQUM7O2NBQ0csTUFBTSxHQUFHLElBQUksQ0FBQyxTQUFTLEtBQUssUUFBUTtRQUMxQyxJQUFJLElBQUksQ0FBQyxTQUFTLEtBQUssUUFBUSxFQUFFO1lBQy9CLElBQUksQ0FBQyxRQUFRLENBQUMsRUFBRSxDQUFDLENBQUMsU0FBUzs7OztZQUFDLE1BQU0sQ0FBQyxFQUFFO2dCQUNuQyxJQUFJLENBQUMsVUFBVSxDQUFDLE1BQU0sRUFBRSxNQUFNLEVBQUUsS0FBSyxDQUFDLENBQUM7WUFDekMsQ0FBQyxFQUFDLENBQUM7U0FDSjthQUFNO1lBQ0wsSUFBSSxDQUFDLElBQUksQ0FBQyxVQUFVLENBQUMsYUFBYSxDQUFDLEtBQUssRUFBRTtnQkFDeEMsSUFBSSxDQUFDLGdCQUFnQixFQUFFLENBQUM7YUFDekI7aUJBQU07Z0JBQ0wsSUFBSSxDQUFDLFFBQVEsQ0FBQyxJQUFJLENBQUMsVUFBVSxDQUFDLGFBQWEsQ0FBQyxLQUFLLENBQUMsQ0FBQyxTQUFTOzs7O2dCQUFDLE1BQU0sQ0FBQyxFQUFFO29CQUNwRSxJQUFJLENBQUMsVUFBVSxDQUFDLE1BQU0sRUFBRSxJQUFJLEVBQUUsS0FBSyxDQUFDLENBQUM7Z0JBQ3ZDLENBQUMsRUFBQyxDQUFDO2FBQ0o7U0FDRjtJQUNILENBQUM7Ozs7O0lBR0QsTUFBTSxDQUFDLE1BQVc7UUFDaEIsSUFBSSxDQUFDLEtBQUssR0FBRyxLQUFLLENBQUM7UUFDbkIsSUFBSSxDQUFDLFNBQVMsRUFBRSxDQUFDO0lBQ25CLENBQUM7Ozs7O0lBR0QsVUFBVSxDQUFDLE1BQVc7UUFDcEIsSUFBSSxDQUFDLFNBQVMsRUFBRSxDQUFDO0lBQ25CLENBQUM7Ozs7O0lBR0QsY0FBYyxDQUFDLE1BQVc7UUFDeEIsSUFBSSxDQUFDLElBQUksQ0FBQyxRQUFRLENBQUMsUUFBUSxDQUFDLE1BQU0sSUFBSSxDQUFDLElBQUksQ0FBQyxRQUFRLENBQUMsUUFBUSxDQUFDLE1BQU0sRUFBRTtZQUNwRSxPQUFPO1NBQ1I7UUFDRCxJQUFJLElBQUksQ0FBQyxRQUFRLEVBQUU7WUFDakIsSUFBSSxDQUFDLFFBQVEsQ0FBQyxRQUFRLENBQUMsaUJBQWlCLENBQUMsTUFBTSxDQUFDLENBQUM7U0FDbEQ7SUFDSCxDQUFDOzs7OztJQUdELGdCQUFnQixDQUFDLE1BQVc7UUFDMUIsSUFBSSxJQUFJLENBQUMsUUFBUSxFQUFFO1lBQ2pCLE1BQU0sQ0FBQyxjQUFjLEVBQUUsQ0FBQztZQUN4QixNQUFNLENBQUMsZUFBZSxFQUFFLENBQUM7WUFDekIsSUFBSSxDQUFDLFFBQVEsQ0FBQyxRQUFRLENBQUMsSUFBSSxFQUFFLENBQUM7U0FDL0I7SUFDSCxDQUFDOzs7OztJQUdELGtCQUFrQixDQUFDLE1BQVc7UUFDNUIsSUFBSSxJQUFJLENBQUMsUUFBUSxFQUFFO1lBQ2pCLE1BQU0sQ0FBQyxjQUFjLEVBQUUsQ0FBQztZQUN4QixNQUFNLENBQUMsZUFBZSxFQUFFLENBQUM7WUFDekIsSUFBSSxDQUFDLFFBQVEsQ0FBQyxRQUFRLENBQUMsSUFBSSxFQUFFLENBQUM7U0FDL0I7SUFDSCxDQUFDOzs7OztJQUdELGVBQWUsQ0FBQyxNQUFhO1FBQzNCLElBQUksSUFBSSxDQUFDLEtBQUssRUFBRTtZQUNkLElBQUksQ0FBQyxtQkFBbUIsQ0FBQyxJQUFJLENBQUM7Z0JBQzVCLEtBQUssRUFBRSxJQUFJLENBQUMsS0FBSztnQkFDakIsUUFBUSxFQUFFLElBQUksQ0FBQyxRQUFRO2FBQ3hCLENBQUMsQ0FBQztTQUNKO1FBQ0QsSUFBSSxJQUFJLENBQUMsUUFBUSxJQUFJLENBQUMsSUFBSSxDQUFDLFFBQVEsQ0FBQyxRQUFRLENBQUMsTUFBTSxFQUFFO1lBQ25ELE9BQU87U0FDUjs7Y0FFSyxXQUFXLEdBQUcsSUFBSSxDQUFDLFVBQVUsQ0FBQyxhQUFhO1FBQ2pELElBQUksQ0FBQyxXQUFXLENBQUMsUUFBUSxDQUFDLE1BQU0sQ0FBQyxNQUFNLENBQUMsRUFBRTtZQUN4QyxJQUFJLENBQUMsU0FBUyxFQUFFLENBQUM7WUFDakIsSUFBSSxDQUFDLG1CQUFtQixDQUFDLElBQUksQ0FBQztnQkFDNUIsS0FBSyxFQUFFLEtBQUs7Z0JBQ1osUUFBUSxFQUFFLElBQUksQ0FBQyxRQUFRO2FBQ3hCLENBQUMsQ0FBQztTQUNKO0lBQ0gsQ0FBQzs7Ozs7SUFFTyxTQUFTO1FBQ2YsSUFBSSxJQUFJLENBQUMsUUFBUSxFQUFFO1lBQ2pCLElBQUksQ0FBQyxRQUFRLENBQUMsUUFBUSxDQUFDLE1BQU0sR0FBRyxLQUFLLENBQUM7U0FDdkM7SUFDSCxDQUFDOzs7Ozs7O0lBRU8sU0FBUyxDQUFDLE1BQVksRUFBRSxJQUFhO1FBQzNDLElBQUksQ0FBQyxRQUFRLEdBQUcsSUFBSSxDQUFDLGVBQWUsQ0FBQyxRQUFRLENBQUMsSUFBSSxDQUFDLFVBQVUsQ0FBQyxhQUFhLENBQUMsQ0FBQzs7Y0FDdkUsR0FBRyxHQUFHLElBQUksQ0FBQyxRQUFRLENBQUMsUUFBUTtRQUNsQyxHQUFHLENBQUMsTUFBTSxHQUFHLE1BQU0sQ0FBQztRQUNwQixHQUFHLENBQUMsU0FBUyxHQUFHLElBQUksQ0FBQyxTQUFTLENBQUM7UUFDL0IsR0FBRyxDQUFDLElBQUksR0FBRyxJQUFJLENBQUM7UUFDaEIsR0FBRyxDQUFDLFdBQVcsR0FBRyxJQUFJLENBQUMsV0FBVyxDQUFDO1FBQ25DLEdBQUcsQ0FBQyxjQUFjLEdBQUcsSUFBSSxDQUFDLGNBQWMsQ0FBQztRQUN6QyxDQUFDLFdBQVcsRUFBRSxjQUFjLEVBQUUsc0JBQXNCLEVBQUUsVUFBVSxFQUFFLFVBQVUsRUFBRSxhQUFhLEVBQUUsVUFBVSxFQUFFLFVBQVUsQ0FBQzthQUNqSCxPQUFPOzs7O1FBQUMsR0FBRyxDQUFDLEVBQUU7WUFDYixJQUFJLElBQUksQ0FBQyxHQUFHLENBQUMsS0FBSyxTQUFTLEVBQUU7Z0JBQzNCLEdBQUcsQ0FBQyxHQUFHLENBQUMsR0FBRyxJQUFJLENBQUMsR0FBRyxDQUFDLENBQUM7YUFDdEI7UUFDSCxDQUFDLEVBQUMsQ0FBQztJQUNQLENBQUM7Ozs7OztJQUVPLGVBQWUsQ0FBQyxLQUFVO1FBQ2hDLElBQUksQ0FBQyxRQUFRLENBQUMsV0FBVyxDQUFDLElBQUksQ0FBQyxVQUFVLENBQUMsYUFBYSxFQUFFLE9BQU8sRUFBRSxLQUFLLENBQUMsQ0FBQztJQUMzRSxDQUFDOzs7OztJQUVPLGVBQWU7UUFDckIsSUFBSSxDQUFDLFFBQVEsQ0FBQyxXQUFXLENBQUMsSUFBSSxDQUFDLFVBQVUsQ0FBQyxhQUFhLEVBQUUsT0FBTyxFQUFFLEVBQUUsQ0FBQyxDQUFDO0lBQ3hFLENBQUM7Ozs7O0lBRU8sY0FBYztRQUNwQixJQUFJLElBQUksQ0FBQyxZQUFZLEVBQUU7WUFDckIsSUFBSSxDQUFDLFlBQVksQ0FBQyxXQUFXLEVBQUUsQ0FBQztZQUNoQyxJQUFJLENBQUMsWUFBWSxHQUFHLElBQUksQ0FBQztTQUMxQjtJQUNILENBQUM7Ozs7O0lBRUQsWUFBWSxDQUFDLElBQVM7UUFDcEIsSUFBSSxDQUFDLEtBQUssR0FBRyxJQUFJLENBQUM7UUFDbEIsSUFBSSxJQUFJLENBQUMsUUFBUSxFQUFFO1lBQ2pCLElBQUksQ0FBQyxRQUFRLENBQUMsUUFBUSxDQUFDLElBQUksR0FBRyxJQUFJLENBQUM7U0FDcEM7UUFDRCxJQUFJLENBQUMsUUFBUSxDQUFDLElBQUksQ0FBQyxDQUFDO0lBQ3RCLENBQUM7Ozs7OztJQUVPLGtCQUFrQixDQUFDLFVBQXNCO1FBQy9DLE9BQU8sU0FBUyxDQUFDLFVBQVUsQ0FBQyxhQUFhLEVBQUUsT0FBTyxDQUFDO2FBQ2hELElBQUksQ0FDSCxNQUFNOzs7O1FBQUMsQ0FBQyxDQUFnQixFQUFFLEVBQUU7WUFDMUIsT0FBTyxJQUFJLENBQUMsMEJBQTBCLENBQUMsT0FBTyxDQUFDLENBQUMsQ0FBQyxHQUFHLENBQUMsaUJBQWlCLEVBQUUsQ0FBQyxLQUFLLENBQUMsQ0FBQyxDQUFDO1FBQ25GLENBQUMsRUFBQyxFQUNGLEdBQUc7Ozs7UUFBQyxDQUFDLENBQU0sRUFBRSxFQUFFLENBQUMsQ0FBQyxDQUFDLE1BQU0sQ0FBQyxLQUFLLEVBQUMsRUFDL0IsR0FBRzs7OztRQUFDLElBQUksQ0FBQyxFQUFFLENBQUMsSUFBSSxDQUFDLFNBQVMsRUFBRSxFQUFDLEVBQzdCLE1BQU07Ozs7UUFBQyxJQUFJLENBQUMsRUFBRSxDQUFDLENBQUMsSUFBSSxDQUFDLFFBQVEsSUFBSSxJQUFJLENBQUMsUUFBUSxJQUFJLElBQUksQ0FBQyxNQUFNLElBQUksQ0FBQyxFQUFDLEVBQ25FLFlBQVksQ0FBQyxJQUFJLENBQUMsS0FBSyxDQUFDLEVBQ3hCLEdBQUc7Ozs7UUFBQyxJQUFJLENBQUMsRUFBRSxDQUFDLElBQUksQ0FBQyxZQUFZLENBQUMsSUFBSSxDQUFDLEVBQUMsRUFDcEMsU0FBUzs7OztRQUFDLElBQUksQ0FBQyxFQUFFLENBQUMsSUFBSSxDQUFDLFFBQVEsQ0FBQyxJQUFJLEVBQUUsSUFBSSxDQUFDLEVBQUMsQ0FDN0MsQ0FBQztJQUNOLENBQUM7OztZQXpWRixTQUFTLFNBQUM7Z0JBQ1QsUUFBUSxFQUFFLGlCQUFpQjtnQkFDM0IsUUFBUSxFQUFFLGNBQWM7Z0JBQ3hCLFNBQVMsRUFBRSxDQUFDO3dCQUNWLE9BQU8sRUFBRSxpQkFBaUI7d0JBQzFCLFdBQVcsRUFBRSxVQUFVOzs7d0JBQUMsR0FBRyxFQUFFLENBQUMscUJBQXFCLEVBQUM7d0JBQ3BELEtBQUssRUFBRSxJQUFJO3FCQUNaLENBQUM7YUFDSDs7OztZQTlCQyxVQUFVO1lBVVYsZ0JBQWdCO1lBYmhCLHdCQUF3QjtZQWlCeEIsU0FBUztZQVZULFFBQVE7WUFlRCxlQUFlO1lBdkJ0QixpQkFBaUI7OzsyQkFvQ2hCLFdBQVcsU0FBQyxtQkFBbUI7NkJBQy9CLFdBQVcsU0FBQyxxQkFBcUI7MEJBQ2pDLFdBQVcsU0FBQyxrQkFBa0I7dUJBQzlCLEtBQUs7dUJBQ0wsS0FBSztvQkFDTCxLQUFLO3dCQUNMLEtBQUs7MkJBQ0wsS0FBSzttQ0FDTCxLQUFLO3dCQUNMLEtBQUs7d0JBQ0wsS0FBSzt1QkFDTCxLQUFLO3VCQUlMLEtBQUs7MkJBQ0wsS0FBSztxQkFDTCxLQUFLOzBCQUNMLEtBQUs7dUJBQ0wsS0FBSzt1QkFDTCxLQUFLO3dCQUNMLEtBQUs7MEJBQ0wsS0FBSzs2QkFJTCxLQUFLO3VCQUNMLE1BQU07MEJBQ04sTUFBTTtrQ0FDTixNQUFNO3NCQW9LTixZQUFZLFNBQUMsT0FBTyxFQUFFLENBQUMsUUFBUSxDQUFDO3FCQXVCaEMsWUFBWSxTQUFDLE1BQU0sRUFBRSxDQUFDLFFBQVEsQ0FBQzt5QkFNL0IsWUFBWSxTQUFDLGFBQWEsRUFBRSxDQUFDLFFBQVEsQ0FBQzs2QkFLdEMsWUFBWSxTQUFDLGVBQWUsRUFBRSxDQUFDLFFBQVEsQ0FBQzsrQkFVeEMsWUFBWSxTQUFDLGlCQUFpQixFQUFFLENBQUMsUUFBUSxDQUFDO2lDQVMxQyxZQUFZLFNBQUMsbUJBQW1CLEVBQUUsQ0FBQyxRQUFRLENBQUM7OEJBUzVDLFlBQVksU0FBQyxnQkFBZ0IsRUFBRSxDQUFDLFFBQVEsQ0FBQzs7OztJQS9QMUMsNkNBQXVEOztJQUN2RCwrQ0FBMkQ7O0lBQzNELDRDQUFxRDs7SUFDckQseUNBQTJCOztJQUMzQix5Q0FBMEI7O0lBQzFCLHNDQUF1Qjs7SUFDdkIsMENBQTJCOztJQUMzQiw2Q0FBd0M7O0lBQ3hDLHFEQUFnRDs7SUFDaEQsMENBQTBDOztJQUMxQywwQ0FBd0I7O0lBQ3hCLHlDQUF1Qjs7SUFJdkIseUNBQTBCOztJQUMxQiw2Q0FBNkI7O0lBQzdCLHVDQUF1Qjs7SUFDdkIsNENBQXlDOztJQUN6Qyx5Q0FBdUY7O0lBQ3ZGLHlDQUEyQjs7SUFDM0IsMENBQXlCOztJQUN6Qiw0Q0FBNkI7Ozs7O0lBSTdCLCtDQUFnQzs7SUFDaEMseUNBQTZDOztJQUM3Qyw0Q0FBZ0Q7O0lBQ2hELG9EQUF3RDs7SUFDeEQsMkRBQ3VDOztJQUN2Qyx5Q0FBbUQ7O0lBRW5ELDRDQUFpQjs7SUFDakIseUNBQWM7O0lBQ2Qsc0NBQWM7Ozs7O0lBRWQsNkNBQXdDOzs7OztJQUN4QyxzQ0FBbUI7Ozs7O0lBQ25CLDBDQUFrQzs7Ozs7SUFDbEMsNkNBQW1DOzs7OztJQUNuQyx5Q0FBb0M7Ozs7O0lBQ3BDLDBDQUErQjs7Ozs7SUFFbkIsMkNBQThCOzs7OztJQUN4QyxpREFBMEM7Ozs7O0lBQzFDLHlEQUEwRDs7Ozs7SUFDMUQseUNBQTJCOzs7OztJQUMzQix5Q0FBMEI7Ozs7O0lBQzFCLGdEQUF3Qzs7Ozs7SUFDeEMsa0RBQTRDIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHtcclxuICBDaGFuZ2VEZXRlY3RvclJlZixcclxuICBDb21wb25lbnRGYWN0b3J5UmVzb2x2ZXIsXHJcbiAgQ29tcG9uZW50UmVmLFxyXG4gIERpcmVjdGl2ZSxcclxuICBFbGVtZW50UmVmLFxyXG4gIEV2ZW50RW1pdHRlcixcclxuICBmb3J3YXJkUmVmLFxyXG4gIEhvc3RMaXN0ZW5lcixcclxuICBJbmplY3RvcixcclxuICBJbnB1dCxcclxuICBPbkRlc3Ryb3ksXHJcbiAgT25Jbml0LFxyXG4gIE91dHB1dCxcclxuICBUZW1wbGF0ZVJlZixcclxuICBWaWV3Q29udGFpbmVyUmVmLFxyXG4gIEhvc3RCaW5kaW5nLFxyXG4gIFNpbXBsZUNoYW5nZXMsXHJcbiAgT25DaGFuZ2VzLFxyXG4gIFJlbmRlcmVyMlxyXG59IGZyb20gJ0Bhbmd1bGFyL2NvcmUnO1xyXG5pbXBvcnQgeyBDb250cm9sVmFsdWVBY2Nlc3NvciwgTkdfVkFMVUVfQUNDRVNTT1IgfSBmcm9tICdAYW5ndWxhci9mb3Jtcyc7XHJcbmltcG9ydCB7IGZyb21FdmVudCwgT2JzZXJ2YWJsZSwgU3Vic2NyaXB0aW9uLCBvZiB9IGZyb20gJ3J4anMnO1xyXG5pbXBvcnQgeyBtYXAsIGZpbHRlciwgZGVib3VuY2VUaW1lLCBzd2l0Y2hNYXAsIHRhcCB9IGZyb20gJ3J4anMvb3BlcmF0b3JzJztcclxuaW1wb3J0IHsgUG9zaXRpb25TZXJ2aWNlIH0gZnJvbSAnbmctZGV2dWkvcG9zaXRpb24nO1xyXG5pbXBvcnQgeyBBdXRvQ29tcGxldGVQb3B1cENvbXBvbmVudCB9IGZyb20gJy4vYXV0by1jb21wbGV0ZS1wb3B1cC5jb21wb25lbnQnO1xyXG5cclxuQERpcmVjdGl2ZSh7XHJcbiAgc2VsZWN0b3I6ICdbZEF1dG9Db21wbGV0ZV0nLFxyXG4gIGV4cG9ydEFzOiAnYXV0b0NvbXBsZXRlJyxcclxuICBwcm92aWRlcnM6IFt7XHJcbiAgICBwcm92aWRlOiBOR19WQUxVRV9BQ0NFU1NPUixcclxuICAgIHVzZUV4aXN0aW5nOiBmb3J3YXJkUmVmKCgpID0+IEF1dG9Db21wbGV0ZURpcmVjdGl2ZSksXHJcbiAgICBtdWx0aTogdHJ1ZVxyXG4gIH1dXHJcbn0pXHJcbmV4cG9ydCBjbGFzcyBBdXRvQ29tcGxldGVEaXJlY3RpdmUgaW1wbGVtZW50cyBPbkluaXQsIE9uRGVzdHJveSwgT25DaGFuZ2VzLCBDb250cm9sVmFsdWVBY2Nlc3NvciB7XHJcbiAgQEhvc3RCaW5kaW5nKCdhdHRyLmF1dG9jb21wbGV0ZScpIGF1dG9jb21wbGV0ZSA9ICdvZmYnO1xyXG4gIEBIb3N0QmluZGluZygnYXR0ci5hdXRvY2FwaXRhbGl6ZScpIGF1dG9jYXBpdGFsaXplID0gJ29mZic7XHJcbiAgQEhvc3RCaW5kaW5nKCdhdHRyLmF1dG9jb3JyZWN0JykgYXV0b2NvcnJlY3QgPSAnb2ZmJztcclxuICBASW5wdXQoKSBkaXNhYmxlZDogYm9vbGVhbjtcclxuICBASW5wdXQoKSBjc3NDbGFzczogc3RyaW5nO1xyXG4gIEBJbnB1dCgpIGRlbGF5OiBudW1iZXI7XHJcbiAgQElucHV0KCkgbWluTGVuZ3RoOiBudW1iZXI7XHJcbiAgQElucHV0KCkgaXRlbVRlbXBsYXRlOiBUZW1wbGF0ZVJlZjxhbnk+O1xyXG4gIEBJbnB1dCgpIG5vUmVzdWx0SXRlbVRlbXBsYXRlOiBUZW1wbGF0ZVJlZjxhbnk+O1xyXG4gIEBJbnB1dCgpIGZvcm1hdHRlcjogKGl0ZW06IGFueSkgPT4gc3RyaW5nO1xyXG4gIEBJbnB1dCgpIHNjZW5lVHlwZSA9ICcnOyAvLyBzY2VuZVR5cGXkvb/nlKjlnLrmma/vvJpzZWxlY3Qo5LiL5ouJ5qGGKSBzdWdnZXN0KOiBlOaDsylcclxuICBASW5wdXQoKSB0aXBzVGV4dCA9ICcnOyAvLyDmj5DnpLrmloflrZdcclxuICAvKlxyXG4gb3ZlcnZpZXc6IGJvcmRlciBub25lIG11bHRpbGluZSBzaW5nbGVcclxuICovXHJcbiAgQElucHV0KCkgb3ZlcnZpZXc6IHN0cmluZztcclxuICBASW5wdXQoKSBsYXRlc3RTb3VyY2U6IGFueVtdOyAvLyDmnIDov5HovpPlhaVcclxuICBASW5wdXQoKSBzb3VyY2U6IGFueVtdO1xyXG4gIEBJbnB1dCgpIHZhbHVlUGFyc2VyOiAoaXRlbTogYW55KSA9PiBhbnk7XHJcbiAgQElucHV0KCkgc2VhcmNoRm46ICh0ZXJtOiBzdHJpbmcsIHRhcmdldD86IEF1dG9Db21wbGV0ZURpcmVjdGl2ZSkgPT4gT2JzZXJ2YWJsZTxhbnlbXT47XHJcbiAgQElucHV0KCkgZHJvcGRvd246IGJvb2xlYW47XHJcbiAgQElucHV0KCkgbWF4SGVpZ2h0ID0gMzAwO1xyXG4gIEBJbnB1dCgpIGRpc2FibGVkS2V5OiBzdHJpbmc7XHJcbiAgLyoqXHJcbiAgICogIOOAkOWPr+mAieOAkeWQr+eUqOaVsOaNruaHkuWKoOi9ve+8jOm7mOiupOS4jeWQr+eUqFxyXG4gICAqL1xyXG4gIEBJbnB1dCgpIGVuYWJsZUxhenlMb2FkID0gZmFsc2U7XHJcbiAgQE91dHB1dCgpIGxvYWRNb3JlID0gbmV3IEV2ZW50RW1pdHRlcjxhbnk+KCk7XHJcbiAgQE91dHB1dCgpIHNlbGVjdFZhbHVlID0gbmV3IEV2ZW50RW1pdHRlcjxhbnk+KCk7XHJcbiAgQE91dHB1dCgpIHRyYW5zSW5wdXRGb2N1c0VtaXQgPSBuZXcgRXZlbnRFbWl0dGVyPGFueT4oKTsgLy8gaW5wdXTnirbmgIHkvKDnu5nniLbnu4Tku7blh73mlbBcclxuICBLRVlCT0FSRF9FVkVOVF9OT1RfUkVGUkVTSCA9IFsnZXNjYXBlJywgJ2VudGVyJywgJ2Fycm93dXAnLCAnYXJyb3dkb3duJyxcclxuICAgIC8qaWUgMTAgZWRnZSAqLyAnZXNjJywgJ3VwJywgJ2Rvd24nXTtcclxuICBwb3B1cFJlZjogQ29tcG9uZW50UmVmPEF1dG9Db21wbGV0ZVBvcHVwQ29tcG9uZW50PjtcclxuXHJcbiAgcG9wVGlwc1RleHQgPSAnJztcclxuICBwb3NpdGlvbjogYW55O1xyXG4gIGZvY3VzID0gZmFsc2U7XHJcblxyXG4gIHByaXZhdGUgdmFsdWVDaGFuZ2VzOiBPYnNlcnZhYmxlPGFueVtdPjtcclxuICBwcml2YXRlIHZhbHVlOiBhbnk7XHJcbiAgcHJpdmF0ZSBwbGFjZW1lbnQgPSAnYm90dG9tLWxlZnQnO1xyXG4gIHByaXZhdGUgc3Vic2NyaXB0aW9uOiBTdWJzY3JpcHRpb247XHJcbiAgcHJpdmF0ZSBvbkNoYW5nZSA9IChfOiBhbnkpID0+IG51bGw7XHJcbiAgcHJpdmF0ZSBvblRvdWNoZWQgPSAoKSA9PiBudWxsO1xyXG5cclxuICBjb25zdHJ1Y3Rvcihwcml2YXRlIGVsZW1lbnRSZWY6IEVsZW1lbnRSZWYsXHJcbiAgICBwcml2YXRlIHZpZXdDb250YWluZXJSZWY6IFZpZXdDb250YWluZXJSZWYsXHJcbiAgICBwcml2YXRlIGNvbXBvbmVudEZhY3RvcnlSZXNvbHZlcjogQ29tcG9uZW50RmFjdG9yeVJlc29sdmVyLFxyXG4gICAgcHJpdmF0ZSByZW5kZXJlcjogUmVuZGVyZXIyLFxyXG4gICAgcHJpdmF0ZSBpbmplY3RvcjogSW5qZWN0b3IsXHJcbiAgICBwcml2YXRlIHBvc2l0aW9uU2VydmljZTogUG9zaXRpb25TZXJ2aWNlLFxyXG4gICAgcHJpdmF0ZSBjaGFuZ2VEZXRlY3RvclJlZjogQ2hhbmdlRGV0ZWN0b3JSZWYpIHtcclxuICAgIHRoaXMuZGVsYXkgPSAzMDA7XHJcbiAgICB0aGlzLnZhbHVlQ2hhbmdlcyA9IHRoaXMucmVnaXN0ZXJJbnB1dEV2ZW50KGVsZW1lbnRSZWYpO1xyXG4gICAgdGhpcy5taW5MZW5ndGggPSAxO1xyXG4gICAgdGhpcy5pdGVtVGVtcGxhdGUgPSBudWxsO1xyXG4gICAgdGhpcy5ub1Jlc3VsdEl0ZW1UZW1wbGF0ZSA9IG51bGw7XHJcbiAgICB0aGlzLmZvcm1hdHRlciA9IChpdGVtOiBhbnkpID0+IGl0ZW0gPyAoaXRlbS5sYWJlbCB8fCBpdGVtLnRvU3RyaW5nKCkpIDogJyc7XHJcbiAgICB0aGlzLnZhbHVlUGFyc2VyID0gKGl0ZW06IGFueSkgPT4gaXRlbTtcclxuICB9XHJcblxyXG4gIG5nT25Jbml0KCkge1xyXG4gICAgLy8g6LCD55So5pe25py677yaaW5wdXQga2V5dXBcclxuICAgIHRoaXMuc3Vic2NyaXB0aW9uID0gdGhpcy52YWx1ZUNoYW5nZXNcclxuICAgICAgLnN1YnNjcmliZShzb3VyY2UgPT4gdGhpcy5vblNvdXJjZUNoYW5nZShzb3VyY2UpKTtcclxuXHJcbiAgICAvLyDliqjmgIHnmoTliJvlu7rkuoZwb3B1cOe7hOS7tu+8jFxyXG4gICAgY29uc3QgZmFjdG9yeSA9IHRoaXMuY29tcG9uZW50RmFjdG9yeVJlc29sdmVyLnJlc29sdmVDb21wb25lbnRGYWN0b3J5KEF1dG9Db21wbGV0ZVBvcHVwQ29tcG9uZW50KTtcclxuICAgIHRoaXMucG9wdXBSZWYgPSB0aGlzLnZpZXdDb250YWluZXJSZWYuY3JlYXRlQ29tcG9uZW50KGZhY3RvcnksIHRoaXMudmlld0NvbnRhaW5lclJlZi5sZW5ndGgsIHRoaXMuaW5qZWN0b3IpO1xyXG5cclxuICAgIHRoaXMuZmlsbFBvcHVwKHRoaXMuc291cmNlKTtcclxuXHJcbiAgICBpZiAoIXRoaXMuc2VhcmNoRm4pIHtcclxuICAgICAgdGhpcy5zZWFyY2hGbiA9ICh0ZXJtKSA9PiB7XHJcbiAgICAgICAgcmV0dXJuIG9mKHRoaXMuc291cmNlLmZpbHRlcihsYW5nID0+IHRoaXMuZm9ybWF0dGVyKGxhbmcpLnRvTG93ZXJDYXNlKCkuaW5kZXhPZih0ZXJtLnRvTG93ZXJDYXNlKCkpICE9PSAtMSkpO1xyXG4gICAgICB9O1xyXG4gICAgfVxyXG5cclxuICAgIC8vIOiwg+eUqOaXtuacuu+8mumAieS4reWbnui9puaIluiAhem8oOagh+WNleWHu+S4i+aLiemAiemhuVxyXG4gICAgdGhpcy5wb3B1cFJlZi5pbnN0YW5jZS5yZWdpc3Rlck9uQ2hhbmdlKGl0ZW0gPT4ge1xyXG4gICAgICBpZiAoaXRlbS50eXBlID09PSAnbG9hZE1vcmUnKSB7XHJcbiAgICAgICAgdGhpcy5sb2FkTW9yZS5lbWl0KGl0ZW0udmFsdWUpO1xyXG4gICAgICAgIHJldHVybjtcclxuICAgICAgfVxyXG4gICAgICBjb25zdCB2YWx1ZSA9IHRoaXMudmFsdWVQYXJzZXIoaXRlbS52YWx1ZSk7XHJcbiAgICAgIHRoaXMud3JpdGVWYWx1ZSh2YWx1ZSk7XHJcbiAgICAgIHRoaXMub25DaGFuZ2UodmFsdWUpO1xyXG4gICAgICB0aGlzLmhpZGVQb3B1cCgpO1xyXG4gICAgICB0aGlzLnNlbGVjdFZhbHVlLmVtaXQoaXRlbS52YWx1ZSk7XHJcbiAgICAgIGlmICh0aGlzLm92ZXJ2aWV3ICYmIHRoaXMub3ZlcnZpZXcgIT09ICdzaW5nbGUnKSB7XHJcbiAgICAgICAgc2V0VGltZW91dCgoKSA9PiB7IC8vIOi/memHjOeojeW+ruW7tui/n+S4gOS4i++8jOetieW+heWFieagh+eahOS9jee9ruWPkeeUn+WPmOWMlu+8jOWlvemHjeaWsOiOt+WPluWFieagh+eahOS9jee9rlxyXG4gICAgICAgICAgdGhpcy5yZXN0TGF0ZXN0U291cmNlKCk7XHJcbiAgICAgICAgfSwgMCk7XHJcbiAgICAgIH1cclxuICAgIH0pO1xyXG4gIH1cclxuXHJcbiAgbmdPbkNoYW5nZXMoY2hhbmdlczogU2ltcGxlQ2hhbmdlcykge1xyXG4gICAgaWYgKGNoYW5nZXMgJiYgdGhpcy5wb3B1cFJlZiAmJiBjaGFuZ2VzLnNvdXJjZSkge1xyXG4gICAgICB0aGlzLmZpbGxQb3B1cCh0aGlzLnNvdXJjZSk7XHJcbiAgICB9XHJcbiAgfVxyXG5cclxuICByZXN0TGF0ZXN0U291cmNlKCkge1xyXG4gICAgaWYgKHRoaXMubGF0ZXN0U291cmNlICYmIHRoaXMubGF0ZXN0U291cmNlLmxlbmd0aCA+IDApIHtcclxuICAgICAgdGhpcy53cml0ZVZhbHVlKCcnKTtcclxuICAgICAgdGhpcy5jbGVhcklucHV0VmFsdWUoKTtcclxuICAgICAgdGhpcy5zaG93TGF0ZXN0U291cmNlKCk7XHJcbiAgICB9XHJcbiAgfVxyXG5cclxuICAvLyDosIPnlKjml7bmnLrvvJppbnB1dCBrZXl1cFxyXG4gIG9uU291cmNlQ2hhbmdlKHNvdXJjZTogYW55KSB7XHJcbiAgICBpZiAoIXRoaXMuZWxlbWVudFJlZi5uYXRpdmVFbGVtZW50LnZhbHVlKSB7XHJcbiAgICAgIGlmICh0aGlzLnNjZW5lVHlwZSAhPT0gJ3NlbGVjdCcpIHsgLy8g5LiL5ouJ5Zy65pmv5LiN5bGV56S65pyA6L+R6L6T5YWlXHJcbiAgICAgICAgdGhpcy5zaG93TGF0ZXN0U291cmNlKCk7XHJcbiAgICAgIH0gZWxzZSB7XHJcbiAgICAgICAgdGhpcy5zaG93U291cmNlKHNvdXJjZSwgdHJ1ZSwgdHJ1ZSk7XHJcbiAgICAgIH1cclxuICAgIH0gZWxzZSB7XHJcbiAgICAgIHRoaXMuc2hvd1NvdXJjZShzb3VyY2UsIHRydWUsIHRydWUpO1xyXG4gICAgfVxyXG4gIH1cclxuXHJcbiAgcHJpdmF0ZSBzaG93TGF0ZXN0U291cmNlKCkge1xyXG4gICAgbGV0IHRlbXBTb3VyY2UgPSBbXTtcclxuICAgIGlmICh0aGlzLmxhdGVzdFNvdXJjZSAmJiB0aGlzLmxhdGVzdFNvdXJjZS5sZW5ndGggPiAwKSB7XHJcbiAgICAgIHRoaXMuc2VhcmNoRm4oJycpLnN1YnNjcmliZShzb3VyY2UgPT4ge1xyXG4gICAgICAgIGNvbnN0IHQgPSB0aGlzLmxhdGVzdFNvdXJjZS5zbGljZSgtNSk7IC8vIOacgOi/kei+k+WFpeWPquaUr+aMgeacgOWkmjXkuKrvvIzmiKrlj5blkI416aG5XHJcbiAgICAgICAgdGVtcFNvdXJjZSA9IHQuZmlsdGVyKGRhdGEgPT4ge1xyXG4gICAgICAgICAgaWYgKCFkYXRhLmxhYmVsKSB7XHJcbiAgICAgICAgICAgIHJldHVybiBzb3VyY2UuZmluZChpdGVtID0+IGl0ZW0gPT09IGRhdGEpO1xyXG4gICAgICAgICAgfSBlbHNlIHtcclxuICAgICAgICAgICAgcmV0dXJuIHNvdXJjZS5maW5kKGl0ZW0gPT4gaXRlbS5sYWJlbCA9PT0gZGF0YS5sYWJlbCk7XHJcbiAgICAgICAgICB9XHJcbiAgICAgICAgfSk7XHJcblxyXG4gICAgICAgIGNvbnN0IHBvcCA9IHRoaXMucG9wdXBSZWYuaW5zdGFuY2U7XHJcbiAgICAgICAgcG9wLnJlc2V0KCk7XHJcbiAgICAgICAgdGhpcy5wb3BUaXBzVGV4dCA9ICfmnIDov5HovpPlhaUnO1xyXG4gICAgICAgIHRoaXMuZmlsbFBvcHVwKHRlbXBTb3VyY2UpO1xyXG4gICAgICAgIHBvcC5pc09wZW4gPSB0cnVlO1xyXG4gICAgICAgIHRoaXMuY2hhbmdlRGV0ZWN0b3JSZWYubWFya0ZvckNoZWNrKCk7XHJcbiAgICAgIH0pO1xyXG4gICAgfVxyXG5cclxuICAgIGlmICh0ZW1wU291cmNlLmxlbmd0aCA8PSAwKSB7XHJcbiAgICAgIHRoaXMuaGlkZVBvcHVwKCk7XHJcbiAgICB9XHJcbiAgfVxyXG5cclxuICBwcml2YXRlIHNob3dTb3VyY2Uoc291cmNlOiBhbnksIHNldE9wZW46IGFueSwgaXNSZXNldDogYW55KSB7XHJcbiAgICBpZiAoKHNvdXJjZSAmJiBzb3VyY2UubGVuZ3RoKSB8fCB0aGlzLm5vUmVzdWx0SXRlbVRlbXBsYXRlKSB7XHJcbiAgICAgIGNvbnN0IHBvcCA9IHRoaXMucG9wdXBSZWYuaW5zdGFuY2U7XHJcbiAgICAgIGlmIChpc1Jlc2V0KSB7XHJcbiAgICAgICAgcG9wLnJlc2V0KCk7XHJcbiAgICAgIH1cclxuICAgICAgdGhpcy5wb3BUaXBzVGV4dCA9IHRoaXMudGlwc1RleHQgfHwgJyc7XHJcbiAgICAgIHRoaXMuZmlsbFBvcHVwKHNvdXJjZSwgdGhpcy52YWx1ZSk7XHJcbiAgICAgIGlmIChzZXRPcGVuKSB7XHJcbiAgICAgICAgcG9wLmlzT3BlbiA9IHRydWU7XHJcbiAgICAgIH1cclxuICAgICAgdGhpcy5jaGFuZ2VEZXRlY3RvclJlZi5tYXJrRm9yQ2hlY2soKTtcclxuICAgIH0gZWxzZSB7XHJcbiAgICAgIHRoaXMuaGlkZVBvcHVwKCk7XHJcbiAgICB9XHJcbiAgfVxyXG5cclxuICB3cml0ZVZhbHVlKG9iajogYW55KTogdm9pZCB7XHJcbiAgICB0aGlzLnZhbHVlID0gdGhpcy5mb3JtYXR0ZXIob2JqKSB8fCAnJztcclxuICAgIHRoaXMud3JpdGVJbnB1dFZhbHVlKHRoaXMudmFsdWUpO1xyXG4gIH1cclxuXHJcbiAgcmVnaXN0ZXJPbkNoYW5nZShmbjogYW55KTogdm9pZCB7XHJcbiAgICB0aGlzLm9uQ2hhbmdlID0gZm47XHJcbiAgfVxyXG5cclxuICByZWdpc3Rlck9uVG91Y2hlZChmbjogYW55KTogdm9pZCB7XHJcbiAgICB0aGlzLm9uVG91Y2hlZCA9IGZuO1xyXG4gIH1cclxuXHJcbiAgc2V0RGlzYWJsZWRTdGF0ZShpc0Rpc2FibGVkOiBib29sZWFuKTogdm9pZCB7XHJcbiAgICB0aGlzLmRpc2FibGVkID0gaXNEaXNhYmxlZDtcclxuICAgIHRoaXMucmVuZGVyZXIuc2V0UHJvcGVydHkodGhpcy5lbGVtZW50UmVmLm5hdGl2ZUVsZW1lbnQsICdkaXNhYmxlZCcsIGlzRGlzYWJsZWQpO1xyXG4gICAgaWYgKHRoaXMucG9wdXBSZWYpIHtcclxuICAgICAgdGhpcy5wb3B1cFJlZi5pbnN0YW5jZS5zZXREaXNhYmxlZFN0YXRlKGlzRGlzYWJsZWQpO1xyXG4gICAgfVxyXG4gIH1cclxuXHJcbiAgbmdPbkRlc3Ryb3koKSB7XHJcbiAgICB0aGlzLnVuU3Vic2NyaXB0aW9uKCk7XHJcbiAgfVxyXG5cclxuICBASG9zdExpc3RlbmVyKCdmb2N1cycsIFsnJGV2ZW50J10pXHJcbiAgb25Gb2N1cygkZXZlbnQ6IGFueSkge1xyXG4gICAgdGhpcy5mb2N1cyA9IHRydWU7XHJcbiAgICB0aGlzLnRyYW5zSW5wdXRGb2N1c0VtaXQuZW1pdCh7XHJcbiAgICAgIGZvY3VzOiB0cnVlLFxyXG4gICAgICBwb3B1cFJlZjogdGhpcy5wb3B1cFJlZlxyXG4gICAgfSk7XHJcbiAgICBjb25zdCBpc09wZW4gPSB0aGlzLnNjZW5lVHlwZSAhPT0gJ3NlbGVjdCc7XHJcbiAgICBpZiAodGhpcy5zY2VuZVR5cGUgPT09ICdzZWxlY3QnKSB7XHJcbiAgICAgIHRoaXMuc2VhcmNoRm4oJycpLnN1YnNjcmliZShzb3VyY2UgPT4ge1xyXG4gICAgICAgIHRoaXMuc2hvd1NvdXJjZShzb3VyY2UsIGlzT3BlbiwgZmFsc2UpO1xyXG4gICAgICB9KTtcclxuICAgIH0gZWxzZSB7XHJcbiAgICAgIGlmICghdGhpcy5lbGVtZW50UmVmLm5hdGl2ZUVsZW1lbnQudmFsdWUpIHtcclxuICAgICAgICB0aGlzLnNob3dMYXRlc3RTb3VyY2UoKTtcclxuICAgICAgfSBlbHNlIHtcclxuICAgICAgICB0aGlzLnNlYXJjaEZuKHRoaXMuZWxlbWVudFJlZi5uYXRpdmVFbGVtZW50LnZhbHVlKS5zdWJzY3JpYmUoc291cmNlID0+IHtcclxuICAgICAgICAgIHRoaXMuc2hvd1NvdXJjZShzb3VyY2UsIHRydWUsIGZhbHNlKTtcclxuICAgICAgICB9KTtcclxuICAgICAgfVxyXG4gICAgfVxyXG4gIH1cclxuXHJcbiAgQEhvc3RMaXN0ZW5lcignYmx1cicsIFsnJGV2ZW50J10pXHJcbiAgb25CbHVyKCRldmVudDogYW55KSB7XHJcbiAgICB0aGlzLmZvY3VzID0gZmFsc2U7XHJcbiAgICB0aGlzLm9uVG91Y2hlZCgpO1xyXG4gIH1cclxuXHJcbiAgQEhvc3RMaXN0ZW5lcigna2V5ZG93bi5lc2MnLCBbJyRldmVudCddKVxyXG4gIG9uRXNjS2V5dXAoJGV2ZW50OiBhbnkpIHtcclxuICAgIHRoaXMuaGlkZVBvcHVwKCk7XHJcbiAgfVxyXG5cclxuICBASG9zdExpc3RlbmVyKCdrZXlkb3duLkVudGVyJywgWyckZXZlbnQnXSlcclxuICBvbkVudGVyS2V5RG93bigkZXZlbnQ6IGFueSkge1xyXG4gICAgaWYgKCF0aGlzLnBvcHVwUmVmLmluc3RhbmNlLnNvdXJjZSB8fCAhdGhpcy5wb3B1cFJlZi5pbnN0YW5jZS5pc09wZW4pIHtcclxuICAgICAgcmV0dXJuO1xyXG4gICAgfVxyXG4gICAgaWYgKHRoaXMucG9wdXBSZWYpIHtcclxuICAgICAgdGhpcy5wb3B1cFJlZi5pbnN0YW5jZS5zZWxlY3RDdXJyZW50SXRlbSgkZXZlbnQpO1xyXG4gICAgfVxyXG4gIH1cclxuXHJcbiAgQEhvc3RMaXN0ZW5lcigna2V5ZG93bi5BcnJvd1VwJywgWyckZXZlbnQnXSlcclxuICBvbkFycm93VXBLZXlEb3duKCRldmVudDogYW55KSB7XHJcbiAgICBpZiAodGhpcy5wb3B1cFJlZikge1xyXG4gICAgICAkZXZlbnQucHJldmVudERlZmF1bHQoKTtcclxuICAgICAgJGV2ZW50LnN0b3BQcm9wYWdhdGlvbigpO1xyXG4gICAgICB0aGlzLnBvcHVwUmVmLmluc3RhbmNlLnByZXYoKTtcclxuICAgIH1cclxuICB9XHJcblxyXG4gIEBIb3N0TGlzdGVuZXIoJ2tleWRvd24uQXJyb3dEb3duJywgWyckZXZlbnQnXSlcclxuICBvbkFycm93RG93bktleURvd24oJGV2ZW50OiBhbnkpIHtcclxuICAgIGlmICh0aGlzLnBvcHVwUmVmKSB7XHJcbiAgICAgICRldmVudC5wcmV2ZW50RGVmYXVsdCgpO1xyXG4gICAgICAkZXZlbnQuc3RvcFByb3BhZ2F0aW9uKCk7XHJcbiAgICAgIHRoaXMucG9wdXBSZWYuaW5zdGFuY2UubmV4dCgpO1xyXG4gICAgfVxyXG4gIH1cclxuXHJcbiAgQEhvc3RMaXN0ZW5lcignZG9jdW1lbnQ6Y2xpY2snLCBbJyRldmVudCddKVxyXG4gIG9uRG9jdW1lbnRDbGljaygkZXZlbnQ6IEV2ZW50KSB7XHJcbiAgICBpZiAodGhpcy5mb2N1cykge1xyXG4gICAgICB0aGlzLnRyYW5zSW5wdXRGb2N1c0VtaXQuZW1pdCh7XHJcbiAgICAgICAgZm9jdXM6IHRoaXMuZm9jdXMsXHJcbiAgICAgICAgcG9wdXBSZWY6IHRoaXMucG9wdXBSZWZcclxuICAgICAgfSk7XHJcbiAgICB9XHJcbiAgICBpZiAodGhpcy5wb3B1cFJlZiAmJiAhdGhpcy5wb3B1cFJlZi5pbnN0YW5jZS5pc09wZW4pIHtcclxuICAgICAgcmV0dXJuO1xyXG4gICAgfVxyXG5cclxuICAgIGNvbnN0IGhvc3RFbGVtZW50ID0gdGhpcy5lbGVtZW50UmVmLm5hdGl2ZUVsZW1lbnQ7XHJcbiAgICBpZiAoIWhvc3RFbGVtZW50LmNvbnRhaW5zKCRldmVudC50YXJnZXQpKSB7XHJcbiAgICAgIHRoaXMuaGlkZVBvcHVwKCk7XHJcbiAgICAgIHRoaXMudHJhbnNJbnB1dEZvY3VzRW1pdC5lbWl0KHtcclxuICAgICAgICBmb2N1czogZmFsc2UsXHJcbiAgICAgICAgcG9wdXBSZWY6IHRoaXMucG9wdXBSZWZcclxuICAgICAgfSk7XHJcbiAgICB9XHJcbiAgfVxyXG5cclxuICBwcml2YXRlIGhpZGVQb3B1cCgpIHtcclxuICAgIGlmICh0aGlzLnBvcHVwUmVmKSB7XHJcbiAgICAgIHRoaXMucG9wdXBSZWYuaW5zdGFuY2UuaXNPcGVuID0gZmFsc2U7XHJcbiAgICB9XHJcbiAgfVxyXG5cclxuICBwcml2YXRlIGZpbGxQb3B1cChzb3VyY2U/OiBhbnksIHRlcm0/OiBzdHJpbmcpIHtcclxuICAgIHRoaXMucG9zaXRpb24gPSB0aGlzLnBvc2l0aW9uU2VydmljZS5wb3NpdGlvbih0aGlzLmVsZW1lbnRSZWYu