UNPKG

cubex-multiselect-dropdown

Version:
404 lines (403 loc) 53.4 kB
/** * @fileoverview added by tsickle * @suppress {checkTypes,extraRequire,uselessCode} checked by tsc */ import { Component, Input, Output, EventEmitter, HostListener, ElementRef } from '@angular/core'; var MultiselectDropdownComponent = /** @class */ (function () { function MultiselectDropdownComponent(eRef) { this.eRef = eRef; this.filterText = ''; this.selectionLabel = 'Select'; this.optionList = []; this.open = false; this.selectedOptions = []; this.displayNameKey = ''; this.toggleSelectionKey = ''; this.selectionTextWidth = 11; this.componentWidth = 250; this.componentHeight = 400; this.selectedOptionsSet = []; this.selectionChange = new EventEmitter(); this.selectedAll = false; this.isSelectedOptionsArayString = false; this.isoptionListArayString = false; this.tooltipBoxWidth = 150; this.searchError = false; this.listOptionColorKey = ''; } /** * @return {?} */ MultiselectDropdownComponent.prototype.ngOnInit = /** * @return {?} */ function () { if (!this.selectedOptions) { this.selectedOptions = []; } this.currentStyles = { width: this.componentWidth < 250 ? '250px' : (this.componentWidth + 'px'), "max-height": this.componentHeight + 'px', }; this.noOption = { "padding-left": (this.componentWidth / 2) - 75 + 'px', "color": "gainsboro" }; this.tooltipTextWidth = { width: this.tooltipBoxWidth <= 150 ? '150px' : (this.tooltipBoxWidth + 'px'), }; this.tooltipTopUnshift = { top: this.selectionLabel !== '' ? '25px' : '7px', }; this.errorAlert = { border: this.searchError == true ? '1px solid red' : '1px solid #dfdfdf' }; }; /** * @param {?} changes * @return {?} */ MultiselectDropdownComponent.prototype.ngOnChanges = /** * @param {?} changes * @return {?} */ function (changes) { var _this = this; this.errorAlert = { border: this.searchError == true ? '1px solid red' : '1px solid #dfdfdf' }; for (var propName in changes) { if (propName === 'selectionSet') { // if((changes[propName].previousValue === undefined || changes[propName].firstChange === true) && this.toggleSelectionKey !=='build'){ // return; // } this.isoptionListArayString = typeof this.optionList[0] === 'string'; this.selectedOptions = changes[propName].currentValue; //console.log("Is this string -->", this.isoptionListArayString, this.selectedOptions); if (this.isoptionListArayString) { this.selectedOptionsSet = []; this.optionList.filter(function (item) { /** @type {?} */ var itemKey = _this.selectedOptions.indexOf(/** @type {?} */ (item)); if (itemKey > -1) { _this.selectedOptionsSet[itemKey] = item; return true; } else { return false; } }); this.filterText = this.selectedOptions.length > 0 && this.open === false ? (this.selectedOptions[0].length < (this.selectionTextWidth + 1) ? this.selectedOptions[0] : this.selectedOptions[0].substring(0, this.selectionTextWidth) + '..') : ''; } else { this.selectedOptionsSet = []; this.optionList.filter(function (item) { /** @type {?} */ var index = _this.selectedOptions.findIndex(function (x) { return x[_this.displayNameKey] === (/** @type {?} */ (item))[_this.toggleSelectionKey]; }); //console.log("selectedOptions --> ", this.selectedOptions, index,(<any>item)[this.toggleSelectionKey]) if (index > -1) { _this.selectedOptionsSet[index] = item; return true; } else { return false; } }); console.log("selectedOptionsSet -->", this.selectedOptionsSet); this.filterText = this.selectedOptions.length > 0 && this.open === false ? (this.selectedOptions[0][this.toggleSelectionKey].length < (this.selectionTextWidth + 1) ? this.selectedOptions[0][this.toggleSelectionKey] : this.selectedOptions[0][this.toggleSelectionKey].substring(0, this.selectionTextWidth) + '..') : ''; } this.selectedAll = this.optionList.length === this.selectedOptionsSet.length ? true : false; } } }; /** * @param {?} option * @return {?} */ MultiselectDropdownComponent.prototype.toggleOption = /** * @param {?} option * @return {?} */ function (option) { var _this = this; this.filterText = ''; /** @type {?} */ var index = 0; if (this.isoptionListArayString) { index = this.selectedOptions.indexOf(option); if (index < 0) { this.selectedOptions.push(option); this.selectedOptionsSet.push(option); } else { this.selectedOptions.splice(index, 1); this.selectedOptionsSet.splice(index, 1); } } else { index = this.selectedOptions.findIndex(function (x) { return x[_this.toggleSelectionKey] === option[_this.toggleSelectionKey]; }); //console.log("selectedOptions --> ", this.selectedOptions, index, option[this.toggleSelectionKey]); if (index < 0) { this.selectedOptions.push(option); this.selectedOptionsSet.push(option); } else { this.selectedOptions.splice(index, 1); this.selectedOptionsSet.splice(index, 1); } } if (this.optionList.length === this.selectedOptions.length) { this.selectedAll = true; } else { this.selectedAll = false; } // console.log(this.selectedOptions); // console.log(this.selectedOptionsSet); //this.selectedOptionsSet = this.getSelectedOptionSet(this.selectedOptionsSet); // console.log("After Modified -->", this.selectedOptionsSet); this.selectionChange.emit(this.selectedOptionsSet); }; // getSelectedOptionSet(selectedOptionsSet) { // if(this.isSelectedOptionsArayString){ // let selectedOptionListStringArray: any = []; // this.selectedOptionsSet.forEach(item => { // selectedOptionListStringArray.push(item[this.displayNameKey]); // }); // return selectedOptionListStringArray; // } else { // return selectedOptionsSet; // } // } /** * @param {?} event * @return {?} */ MultiselectDropdownComponent.prototype.selectAll = /** * @param {?} event * @return {?} */ function (event) { event.stopPropagation(); this.filterText = ''; this.selectedAll = true; /** @type {?} */ var toggleSelectionKey = this.toggleSelectionKey; if (this.isoptionListArayString) { this.selectedOptions = this.optionList.map(function (item) { return item[toggleSelectionKey]; }); } else { this.selectedOptions = this.optionList.map(function (item) { return item; }); } this.selectedOptionsSet = this.optionList; //this.selectedOptionsSet = this.getSelectedOptionSet(this.selectedOptionsSet); this.selectionChange.emit(this.selectedOptionsSet); }; /** * @param {?} event * @return {?} */ MultiselectDropdownComponent.prototype.reset = /** * @param {?} event * @return {?} */ function (event) { event.stopPropagation(); this.selectedAll = false; this.selectedOptions = []; this.selectedOptionsSet = []; this.filterText = ''; this.selectionChange.emit(this.selectedOptionsSet); }; /** * @param {?} option * @return {?} */ MultiselectDropdownComponent.prototype.isOptionSelected = /** * @param {?} option * @return {?} */ function (option) { var _this = this; /** @type {?} */ var selectedFlag; if (this.isoptionListArayString) { selectedFlag = this.selectedOptions.indexOf(option) > -1; } else { /** @type {?} */ var index = this.selectedOptions.findIndex(function (x) { return x[_this.toggleSelectionKey] === option[_this.toggleSelectionKey]; }); selectedFlag = index > -1; } return selectedFlag; }; /** * @return {?} */ MultiselectDropdownComponent.prototype.closeDropdown = /** * @return {?} */ function () { this.open = false; if (this.isoptionListArayString) { this.filterText = this.selectedOptions[0] ? (this.selectedOptions[0].length < (this.selectionTextWidth + 1) ? this.selectedOptions[0] : this.selectedOptions[0].substring(0, this.selectionTextWidth) + '..') : ''; } else { this.filterText = this.selectedOptions.length > 0 && this.open === false ? (this.selectedOptions[0][this.toggleSelectionKey].length < (this.selectionTextWidth + 1) ? this.selectedOptions[0][this.toggleSelectionKey] : this.selectedOptions[0][this.toggleSelectionKey].substring(0, this.selectionTextWidth) + '..') : ''; } }; /** * @return {?} */ MultiselectDropdownComponent.prototype.toggleDropdown = /** * @return {?} */ function () { this.open = !this.open; if (this.open) { this.filterText = ''; } else { if (this.isoptionListArayString) { this.filterText = this.selectedOptions[0] ? (this.selectedOptions[0].length < (this.selectionTextWidth + 1) ? this.selectedOptions[0] : this.selectedOptions[0].substring(0, this.selectionTextWidth) + '..') : ''; } else { this.filterText = this.selectedOptions.length > 0 && this.open === false ? (this.selectedOptions[0][this.toggleSelectionKey].length < (this.selectionTextWidth + 1) ? this.selectedOptions[0][this.toggleSelectionKey] : this.selectedOptions[0][this.toggleSelectionKey].substring(0, this.selectionTextWidth) + '..') : ''; } } }; /** * @return {?} */ MultiselectDropdownComponent.prototype.openDropdown = /** * @return {?} */ function () { this.open = true; this.filterText = ''; }; /** * @param {?} event * @return {?} */ MultiselectDropdownComponent.prototype.clickout = /** * @param {?} event * @return {?} */ function (event) { if (!this.eRef.nativeElement.contains(event.target)) { this.open = false; if (this.isoptionListArayString) { this.filterText = this.selectedOptions[0] ? (this.selectedOptions[0].length < (this.selectionTextWidth + 1) ? this.selectedOptions[0] : this.selectedOptions[0].substring(0, this.selectionTextWidth) + '..') : ''; } else { this.filterText = this.selectedOptions.length > 0 && this.open === false ? (this.selectedOptions[0][this.toggleSelectionKey].length < (this.selectionTextWidth + 1) ? this.selectedOptions[0][this.toggleSelectionKey] : this.selectedOptions[0][this.toggleSelectionKey].substring(0, this.selectionTextWidth) + '..') : ''; } } }; MultiselectDropdownComponent.decorators = [ { type: Component, args: [{ selector: 'cubex-multiselect-dropdown', template: "<div *ngIf=\"!isoptionListArayString\" style=\"position: relative !important;\">\n <span class=\"tooltip\" *ngIf=\"!open\" [ngStyle]=\"tooltipTopUnshift\">\n <small *ngIf=\"selectedOptions.length>1\">+{{selectedOptions.length-1}} selected</small>\n <span class=\"tooltiptextparent\">\n <span class=\"tooltiptext\" [ngStyle]=\"tooltipTextWidth\">\n <ng-template ngFor let-selectedOption let-index=\"index\" [ngForOf]=\"selectedOptions.slice(1)\">\n <span class=\"bullet\"></span>\n <span>{{selectedOption[displayNameKey]}}</span>\n <br>\n </ng-template>\n </span>\n </span>\n </span>\n\n <div class=\"form-group proto-select\" (clickOutside)=\"closeDropdown()\">\n <div class=\"form-group__text\">\n <input class=\"text-small text-vibrant\" type=\"text\" (click)=\"openDropdown()\" [(ngModel)]=\"filterText\"\n placeholder=\"{{selectedOptions.length <1?selectionPlaceholder: ''}}\" [ngStyle]=\"errorAlert\" />\n <label>{{selectionLabel}}</label>\n <i class=\"proto-select-chevron\" [ngClass]=\"[ open ? 'icon-chevron-up' : 'icon-chevron-down' ]\"\n (click)=\"toggleDropdown()\"></i>\n </div>\n\n <div class=\"panel panel--raised proto-select-dropdown\" *ngIf=\"open\">\n <div class=\"text-small text-muted text-noselect qtr-padding\" *ngIf=\"optionList.length == 0\">\n No option available\n </div>\n <!-- Select All & Clear -->\n <div class=\"flex flex-center-vertical dropdown-header clearfix\" *ngIf=\"optionList.length > 0\">\n <div class=\"form-group\">\n <label class=\"checkbox\">\n <input type=\"checkbox\" *ngIf=\"!selectedAll\" (click)=\"selectAll($event)\">\n <input type=\"checkbox\" *ngIf=\"selectedAll\" checked (click)=\"reset($event)\">\n <span class=\"checkbox__input\"></span>\n <span class=\"checkbox__label text-small text-blue\"> &nbsp;All</span>\n </label>\n </div>\n <span class=\"flex-fluid\"></span>\n <span class=\"text-small text-warning qtr-padding half-padding-right clickable pull-right\"\n (click)=\"reset($event)\">Clear</span>\n </div>\n\n <!-- <div class=\"panel no-padding\" *ngFor=\"let item of optionList | filterObjectsByKey : displayNameKey : filterText | arraySort: displayNameKey\"> -->\n <div class=\"panel no-padding\" *ngFor=\"let item of optionList | filterObjectsByKey : displayNameKey : filterText\">\n\n <div class=\"form-group\">\n <label class=\"checkbox\">\n <input type=\"checkbox\" (click)=\"toggleOption(item)\" name=item[displayNameKey]\n value=item[displayNameKey] [checked]=\"isOptionSelected(item)\">\n <span class=\"checkbox__input\"></span>\n <span class=\"checkbox__label text-small\"\n [ngStyle]=\"{'color': ((item[listOptionColorKey] !== '')?item[listOptionColorKey]: '#58585b')}\">\n &nbsp;{{item[displayNameKey]|uppercase }}</span>\n </label>\n </div>\n </div>\n\n </div>\n </div>\n</div>\n\n<div *ngIf=\"isoptionListArayString\" style=\"position: relative !important;\">\n <span class=\"tooltip\" *ngIf=\"!open\" [ngStyle]=\"tooltipTopUnshift\">\n <small *ngIf=\"selectedOptions.length>1\">+{{selectedOptions.length-1}} selected</small>\n <span class=\"tooltiptextparent\">\n <span class=\"tooltiptext\" [ngStyle]=\"tooltipTextWidth\">\n <ng-template ngFor let-selectedOption let-index=\"index\" [ngForOf]=\"selectedOptions.slice(1)\">\n <span class=\"bullet\"></span>\n <span>{{selectedOption}}</span>\n <br>\n </ng-template>\n </span>\n </span>\n </span>\n\n <div class=\"form-group proto-select\" (clickOutside)=\"closeDropdown()\">\n <div class=\"form-group__text\">\n <input class=\"text-small text-vibrant\" type=\"text\" (click)=\"openDropdown()\" [(ngModel)]=\"filterText\"\n placeholder=\"{{selectedOptions.length <1?selectionPlaceholder: ''}}\" [ngStyle]=\"errorAlert\" />\n <label>{{selectionLabel}}</label>\n <i class=\"proto-select-chevron\" [ngClass]=\"[ open ? 'icon-chevron-up' : 'icon-chevron-down' ]\"\n (click)=\"toggleDropdown()\"></i>\n </div>\n\n <div class=\"panel panel--raised proto-select-dropdown\" *ngIf=\"open\">\n <div class=\"text-small text-muted text-noselect qtr-padding\" *ngIf=\"optionList.length == 0\">\n No option available\n </div>\n <!-- Select All & Clear -->\n <div class=\"flex flex-center-vertical dropdown-header clearfix\" *ngIf=\"optionList.length > 0\">\n <div class=\"form-group\">\n <label class=\"checkbox\">\n <input type=\"checkbox\" *ngIf=\"!selectedAll\" (click)=\"selectAll($event)\">\n <input type=\"checkbox\" *ngIf=\"selectedAll\" checked (click)=\"reset($event)\">\n <span class=\"checkbox__input\"></span>\n <span class=\"checkbox__label text-small text-blue\"> &nbsp;All</span>\n </label>\n </div>\n <span class=\"flex-fluid\"></span>\n <span class=\"text-small text-warning qtr-padding half-padding-right clickable pull-right\"\n (click)=\"reset($event)\">Clear</span>\n </div>\n\n <div class=\"panel no-padding\" *ngFor=\"let item of optionList | filterStrings : filterText\">\n <div class=\"form-group\">\n <label class=\"checkbox\">\n <input type=\"checkbox\" (click)=\"toggleOption(item)\" name=item value=item\n [checked]=\"isOptionSelected(item)\">\n <span class=\"checkbox__input\"></span>\n <span class=\"checkbox__label text-small\" [ngStyle]=\"{'color': ((item !== '')?item: '#58585b')}\">\n &nbsp;{{item|uppercase }}</span>\n </label>\n </div>\n </div>\n\n </div>\n </div>\n</div>", styles: [".overlayAnchor{display:inline-block;min-width:250px}.link{text-decoration:underline;cursor:pointer;color:#007493;padding-left:8px}.noOption{padding-top:5px}.tooltip{position:absolute;right:40px;top:25px;z-index:1;display:inline-block}.tooltip .tooltiptext{visibility:hidden;min-width:120px;background-color:#555;color:#fff;text-align:center;padding:5px 0;border-radius:6px;max-height:460px;overflow:scroll;position:absolute;z-index:1;top:125%;left:50%;margin-left:-60px;opacity:0;transition:opacity .3s}.tooltip .tooltiptextparent{visibility:hidden;opacity:0;transition:opacity .3s}.tooltip .tooltiptextparent::after{content:\"\";position:absolute;top:15px;left:15px;margin-left:-5px;border-width:5px;border-style:solid;border-color:transparent transparent #555}.tooltip:hover .tooltiptext,.tooltip:hover .tooltiptextparent{visibility:visible;opacity:1}.bullet{height:5px;width:5px;background-color:#fff;border-radius:50%;display:inline-block;margin-bottom:3px}.inputBox{border-bottom:1px solid #ddd;border-top:none;border-left:none;border-right:none;width:-webkit-fill-available;width:-moz-available;width:stretch}.dropdown-expanded{border:1px solid #d3d3d3;padding-left:9px;min-width:171px;width:-webkit-fit-content;width:-moz-fit-content;width:fit-content;height:-webkit-fit-content;height:-moz-fit-content;height:fit-content;overflow:scroll;float:left}.customInput{outline:0;padding-left:6px;padding-top:3px}.customInput:hover{outline:#ccc solid 1px}.inlineBox{display:block;cursor:pointer;position:relative;padding-left:28px;padding-bottom:6px;-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;margin:5px 0;border-bottom:1px solid #ccc;word-wrap:break-word}.inlineBox input[type=checkbox]{position:absolute;opacity:0;cursor:pointer;height:0;width:0}.checkmark{position:absolute;top:0;left:0;height:22px;width:22px;background-color:#eee;border-radius:5px}.checkmarkText{position:relative;top:3px}.inlineBox:hover input~.checkmark{background-color:#ccc}.inlineBox input:checked~.checkmark{background-color:#ddd}.checkmark:after{content:\"\";position:absolute;display:none}.inlineBox input:checked~.checkmark:after{display:block}.inlineBox .checkmark:after{left:4px;top:4px;width:14px;height:14px;background:#00beed;border-radius:5px}::-webkit-scrollbar{width:6px}::-webkit-scrollbar:horizontal{height:6px}::-webkit-scrollbar-track{background:#f1f1f1}::-webkit-scrollbar-thumb{background:#888;border-radius:5px}::-webkit-scrollbar-thumb:hover{background:#666}.proto-select .proto-select-backdrop{position:fixed;top:0;bottom:0;right:0;left:0;z-index:99}.proto-select .proto-select-chevron{position:absolute;bottom:0;right:0;padding:5px 8px;color:gray}.proto-select .proto-select-dropdown{position:absolute;z-index:999;border:1px solid #f1f1f1;overflow-y:auto;padding:0;top:100%;left:0;right:0;max-height:215px}.proto-select .proto-select-dropdown .dropdown-header{position:-webkit-sticky;position:sticky;top:0;z-index:99;width:100%;background-color:#fff;border-bottom:1px solid #f1f1f1}.proto-select .proto-select-dropdown .form-group{padding:6px 10px;margin:0}.proto-select .proto-select-dropdown .form-group .checkbox__label{padding-top:2px}.proto-select .proto-select-dropdown .form-group.selected,.proto-select .proto-select-dropdown .form-group.selected:hover{background-color:#00bceb!important;color:#fff}.proto-select .proto-select-dropdown .form-group.selected .checkbox__label,.proto-select .proto-select-dropdown .form-group.selected:hover .checkbox__label{color:#fff!important}.proto-select .proto-select-dropdown .form-group:hover{background-color:#f1f1f1}"] }] } ]; /** @nocollapse */ MultiselectDropdownComponent.ctorParameters = function () { return [ { type: ElementRef } ]; }; MultiselectDropdownComponent.propDecorators = { selectionLabel: [{ type: Input, args: ['label',] }], optionList: [{ type: Input, args: ['data',] }], selectionSet: [{ type: Input, args: ['checkedOptions',] }], open: [{ type: Input, args: ['isOpen',] }], displayNameKey: [{ type: Input, args: ['displayKey',] }], toggleSelectionKey: [{ type: Input, args: ['toggleKey',] }], selectionPlaceholder: [{ type: Input, args: ['placeholder',] }], selectionTextWidth: [{ type: Input, args: ['selectionWidth',] }], componentWidth: [{ type: Input, args: ['width',] }], componentHeight: [{ type: Input, args: ['height',] }], selectionChange: [{ type: Output, args: ['onChange',] }], tooltipBoxWidth: [{ type: Input, args: ['tooltipWidth',] }], searchError: [{ type: Input, args: ['error',] }], listOptionColorKey: [{ type: Input, args: ['optionColorKey',] }], clickout: [{ type: HostListener, args: ['document:click', ['$event'],] }] }; return MultiselectDropdownComponent; }()); export { MultiselectDropdownComponent }; if (false) { /** @type {?} */ MultiselectDropdownComponent.prototype.filterText; /** @type {?} */ MultiselectDropdownComponent.prototype.selectionLabel; /** @type {?} */ MultiselectDropdownComponent.prototype.optionList; /** @type {?} */ MultiselectDropdownComponent.prototype.selectionSet; /** @type {?} */ MultiselectDropdownComponent.prototype.open; /** @type {?} */ MultiselectDropdownComponent.prototype.selectedOptions; /** @type {?} */ MultiselectDropdownComponent.prototype.displayNameKey; /** @type {?} */ MultiselectDropdownComponent.prototype.toggleSelectionKey; /** @type {?} */ MultiselectDropdownComponent.prototype.selectionPlaceholder; /** @type {?} */ MultiselectDropdownComponent.prototype.selectionTextWidth; /** @type {?} */ MultiselectDropdownComponent.prototype.componentWidth; /** @type {?} */ MultiselectDropdownComponent.prototype.componentHeight; /** @type {?} */ MultiselectDropdownComponent.prototype.selectedOptionsSet; /** @type {?} */ MultiselectDropdownComponent.prototype.selectionChange; /** @type {?} */ MultiselectDropdownComponent.prototype.currentStyles; /** @type {?} */ MultiselectDropdownComponent.prototype.noOption; /** @type {?} */ MultiselectDropdownComponent.prototype.tooltipTextWidth; /** @type {?} */ MultiselectDropdownComponent.prototype.errorAlert; /** @type {?} */ MultiselectDropdownComponent.prototype.tooltipTopUnshift; /** @type {?} */ MultiselectDropdownComponent.prototype.selectedAll; /** @type {?} */ MultiselectDropdownComponent.prototype.isSelectedOptionsArayString; /** @type {?} */ MultiselectDropdownComponent.prototype.isoptionListArayString; /** @type {?} */ MultiselectDropdownComponent.prototype.tooltipBoxWidth; /** @type {?} */ MultiselectDropdownComponent.prototype.searchError; /** @type {?} */ MultiselectDropdownComponent.prototype.listOptionColorKey; /** @type {?} */ MultiselectDropdownComponent.prototype.eRef; } //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoibXVsdGlzZWxlY3QtZHJvcGRvd24uY29tcG9uZW50LmpzIiwic291cmNlUm9vdCI6Im5nOi8vY3ViZXgtbXVsdGlzZWxlY3QtZHJvcGRvd24vIiwic291cmNlcyI6WyJsaWIvbXVsdGlzZWxlY3QtZHJvcGRvd24uY29tcG9uZW50LnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7Ozs7QUFBQSxPQUFPLEVBQUUsU0FBUyxFQUFVLEtBQUssRUFBRSxNQUFNLEVBQUUsWUFBWSxFQUE0QixZQUFZLEVBQUUsVUFBVSxFQUFDLE1BQU0sZUFBZSxDQUFDOztJQW1DaEksc0NBQW9CLElBQWdCO1FBQWhCLFNBQUksR0FBSixJQUFJLENBQVk7MEJBMUJmLEVBQUU7OEJBQ2tCLFFBQVE7MEJBQ04sRUFBRTtvQkFFWixLQUFLOytCQUNMLEVBQUU7OEJBQ0csRUFBRTtrQ0FDQyxFQUFFO2tDQUVXLEVBQUU7OEJBQ2YsR0FBRzsrQkFDRCxHQUFHO2tDQUNWLEVBQUU7K0JBQ0EsSUFBSSxZQUFZLEVBQU87MkJBTXRDLEtBQUs7MkNBQ1csS0FBSztzQ0FDVixLQUFLOytCQUNVLEdBQUc7MkJBQ2IsS0FBSztrQ0FDVSxFQUFFO0tBR3ZEOzs7O0lBRUQsK0NBQVE7OztJQUFSO1FBQ0UsSUFBSSxDQUFDLElBQUksQ0FBQyxlQUFlLEVBQUU7WUFDekIsSUFBSSxDQUFDLGVBQWUsR0FBRyxFQUFFLENBQUM7U0FDM0I7UUFDRCxJQUFJLENBQUMsYUFBYSxHQUFHO1lBQ25CLEtBQUssRUFBRSxJQUFJLENBQUMsY0FBYyxHQUFHLEdBQUcsQ0FBQyxDQUFDLENBQUMsT0FBTyxDQUFDLENBQUMsQ0FBQyxDQUFDLElBQUksQ0FBQyxjQUFjLEdBQUcsSUFBSSxDQUFDO1lBQ3pFLFlBQVksRUFBRSxJQUFJLENBQUMsZUFBZSxHQUFHLElBQUk7U0FDMUMsQ0FBQztRQUNGLElBQUksQ0FBQyxRQUFRLEdBQUc7WUFDZCxjQUFjLEVBQUUsQ0FBQyxJQUFJLENBQUMsY0FBYyxHQUFHLENBQUMsQ0FBQyxH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QUMsQ0FBQyxJQUFJLENBQUMsa0JBQWtCLENBQUMsQ0FBQyxTQUFTLENBQUMsQ0FBQyxFQUFFLElBQUksQ0FBQyxrQkFBa0IsQ0FBQztvQkFDM0ssSUFBSSxDQUFDLENBQUMsQ0FBQyxDQUFDLEVBQUUsQ0FBQzthQUNkO1NBQ0Y7S0FDRjs7Z0JBcFBGLFNBQVMsU0FBQztvQkFDVCxRQUFRLEVBQUUsNEJBQTRCO29CQUN0Qyxna05BQXVDOztpQkFFeEM7Ozs7Z0JBTmdHLFVBQVU7OztpQ0FVeEcsS0FBSyxTQUFDLE9BQU87NkJBQ2IsS0FBSyxTQUFDLE1BQU07K0JBQ1osS0FBSyxTQUFDLGdCQUFnQjt1QkFDdEIsS0FBSyxTQUFDLFFBQVE7aUNBRWQsS0FBSyxTQUFDLFlBQVk7cUNBQ2xCLEtBQUssU0FBQyxXQUFXO3VDQUNqQixLQUFLLFNBQUMsYUFBYTtxQ0FDbkIsS0FBSyxTQUFDLGdCQUFnQjtpQ0FDdEIsS0FBSyxTQUFDLE9BQU87a0NBQ2IsS0FBSyxTQUFDLFFBQVE7a0NBRWQsTUFBTSxTQUFDLFVBQVU7a0NBU2pCLEtBQUssU0FBQyxjQUFjOzhCQUNwQixLQUFLLFNBQUMsT0FBTztxQ0FDYixLQUFLLFNBQUMsZ0JBQWdCOzJCQXVNdEIsWUFBWSxTQUFDLGdCQUFnQixFQUFFLENBQUMsUUFBUSxDQUFDOzt1Q0F4TzVDOztTQU9hLDRCQUE0QiIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IENvbXBvbmVudCwgT25Jbml0LCBJbnB1dCwgT3V0cHV0LCBFdmVudEVtaXR0ZXIsIE9uQ2hhbmdlcywgU2ltcGxlQ2hhbmdlcywgSG9zdExpc3RlbmVyLCBFbGVtZW50UmVmfSBmcm9tICdAYW5ndWxhci9jb3JlJztcblxuQENvbXBvbmVudCh7XG4gIHNlbGVjdG9yOiAnY3ViZXgtbXVsdGlzZWxlY3QtZHJvcGRvd24nLFxuICB0ZW1wbGF0ZVVybDonbXVsdGlzZWxlY3QtZHJvcGRvd24uaHRtbCcsXG4gIHN0eWxlVXJsczogWydtdWx0aXNlbGVjdC1kcm9wZG93bi5jc3MnXVxufSlcbmV4cG9ydCBjbGFzcyBNdWx0aXNlbGVjdERyb3Bkb3duQ29tcG9uZW50IGltcGxlbWVudHMgT25Jbml0LCBPbkNoYW5nZXMge1xuXG4gIGZpbHRlclRleHQ6IHN0cmluZyA9ICcnO1xuICBASW5wdXQoJ2xhYmVsJykgc2VsZWN0aW9uTGFiZWw6IHN0cmluZyA9ICdTZWxlY3QnO1xuICBASW5wdXQoJ2RhdGEnKSBvcHRpb25MaXN0OiBBcnJheTxPYmplY3Q+ID0gW107XG4gIEBJbnB1dCgnY2hlY2tlZE9wdGlvbnMnKSBzZWxlY3Rpb25TZXQ6IEFycmF5PHN0cmluZz47XG4gIEBJbnB1dCgnaXNPcGVuJykgb3BlbjogYm9vbGVhbiA9IGZhbHNlO1xuICBzZWxlY3RlZE9wdGlvbnM6IEFycmF5PHN0cmluZz4gPSBbXTtcbiAgQElucHV0KCdkaXNwbGF5S2V5JykgZGlzcGxheU5hbWVLZXkgPSAnJztcbiAgQElucHV0KCd0b2dnbGVLZXknKSB0b2dnbGVTZWxlY3Rpb25LZXkgPSAnJztcbiAgQElucHV0KCdwbGFjZWhvbGRlcicpIHNlbGVjdGlvblBsYWNlaG9sZGVyOiBzdHJpbmc7XG4gIEBJbnB1dCgnc2VsZWN0aW9uV2lkdGgnKSBzZWxlY3Rpb25UZXh0V2lkdGg6IG51bWJlciA9IDExO1xuICBASW5wdXQoJ3dpZHRoJykgY29tcG9uZW50V2lkdGg6IG51bWJlciA9IDI1MDtcbiAgQElucHV0KCdoZWlnaHQnKSBjb21wb25lbnRIZWlnaHQ6IG51bWJlciA9IDQwMDtcbiAgc2VsZWN0ZWRPcHRpb25zU2V0OiBBcnJheTxPYmplY3Q+ID0gW107XG4gIEBPdXRwdXQoJ29uQ2hhbmdlJykgc2VsZWN0aW9uQ2hhbmdlID0gbmV3IEV2ZW50RW1pdHRlcjxhbnk+KCk7XG4gIGN1cnJlbnRTdHlsZXM6IHt9O1xuICBub09wdGlvbjoge307XG4gIHRvb2x0aXBUZXh0V2lkdGg6IHt9O1xuICBlcnJvckFsZXJ0OiB7fTtcbiAgdG9vbHRpcFRvcFVuc2hpZnQ6IHt9O1xuICBzZWxlY3RlZEFsbDogQm9vbGVhbiA9IGZhbHNlO1xuICBpc1NlbGVjdGVkT3B0aW9uc0FyYXlTdHJpbmc6IGJvb2xlYW4gPSBmYWxzZTtcbiAgaXNvcHRpb25MaXN0QXJheVN0cmluZzogYm9vbGVhbiA9IGZhbHNlO1xuICBASW5wdXQoJ3Rvb2x0aXBXaWR0aCcpIHRvb2x0aXBCb3hXaWR0aDogbnVtYmVyID0gMTUwO1xuICBASW5wdXQoJ2Vycm9yJykgc2VhcmNoRXJyb3I6IGJvb2xlYW4gPSBmYWxzZTtcbiAgQElucHV0KCdvcHRpb25Db2xvcktleScpIGxpc3RPcHRpb25Db2xvcktleTogc3RyaW5nID0gJyc7XG5cbiAgY29uc3RydWN0b3IocHJpdmF0ZSBlUmVmOiBFbGVtZW50UmVmKSB7XG4gIH1cblxuICBuZ09uSW5pdCgpIHtcbiAgICBpZiAoIXRoaXMuc2VsZWN0ZWRPcHRpb25zKSB7XG4gICAgICB0aGlzLnNlbGVjdGVkT3B0aW9ucyA9IFtdO1xuICAgIH1cbiAgICB0aGlzLmN1cnJlbnRTdHlsZXMgPSB7XG4gICAgICB3aWR0aDogdGhpcy5jb21wb25lbnRXaWR0aCA8IDI1MCA/ICcyNTBweCcgOiAodGhpcy5jb21wb25lbnRXaWR0aCArICdweCcpLFxuICAgICAgXCJtYXgtaGVpZ2h0XCI6IHRoaXMuY29tcG9uZW50SGVpZ2h0ICsgJ3B4JyxcbiAgICB9O1xuICAgIHRoaXMubm9PcHRpb24gPSB7XG4gICAgICBcInBhZGRpbmctbGVmdFwiOiAodGhpcy5jb21wb25lbnRXaWR0aCAvIDIpIC0gNzUgKyAncHgnLFxuICAgICAgXCJjb2xvclwiOiBcImdhaW5zYm9yb1wiXG4gICAgfTtcbiAgICB0aGlzLnRvb2x0aXBUZXh0V2lkdGggPSB7XG4gICAgICB3aWR0aDogdGhpcy50b29sdGlwQm94V2lkdGggPD0gMTUwID8gJzE1MHB4JyA6ICh0aGlzLnRvb2x0aXBCb3hXaWR0aCArICdweCcpLFxuICAgIH1cbiAgICB0aGlzLnRvb2x0aXBUb3BVbnNoaWZ0ID0ge1xuICAgICAgdG9wOiB0aGlzLnNlbGVjdGlvbkxhYmVsICE9PSAnJyA/ICcyNXB4JyA6ICc3cHgnLFxuICAgIH1cbiAgICB0aGlzLmVycm9yQWxlcnQgPSB7XG4gICAgICBib3JkZXI6IHRoaXMuc2VhcmNoRXJyb3IgPT0gdHJ1ZSA/ICcxcHggc29saWQgcmVkJyA6ICcxcHggc29saWQgI2RmZGZkZidcbiAgICB9O1xuICB9XG5cbiAgbmdPbkNoYW5nZXMoY2hhbmdlczogU2ltcGxlQ2hhbmdlcykge1xuICAgIHRoaXMuZXJyb3JBbGVydCA9IHtcbiAgICAgIGJvcmRlcjogdGhpcy5zZWFyY2hFcnJvciA9PSB0cnVlID8gJzFweCBzb2xpZCByZWQnIDogJzFweCBzb2xpZCAjZGZkZmRmJ1xuICAgIH07XG4gICAgZm9yIChsZXQgcHJvcE5hbWUgaW4gY2hhbmdlcykge1xuICAgICAgaWYgKHByb3BOYW1lID09PSAnc2VsZWN0aW9uU2V0Jykge1xuICAgICAgICAvLyBpZigoY2hhbmdlc1twcm9wTmFtZV0ucHJldmlvdXNWYWx1ZSA9PT0gdW5kZWZpbmVkIHx8IGNoYW5nZXNbcHJvcE5hbWVdLmZpcnN0Q2hhbmdlID09PSB0cnVlKSAmJiB0aGlzLnRvZ2dsZVNlbGVjdGlvbktleSAhPT0nYnVpbGQnKXtcbiAgICAgICAgLy8gICByZXR1cm47XG4gICAgICAgIC8vIH1cbiAgICAgICAgdGhpcy5pc29wdGlvbkxpc3RBcmF5U3RyaW5nID0gdHlwZW9mIHRoaXMub3B0aW9uTGlzdFswXSA9PT0gJ3N0cmluZyc7XG4gICAgICAgIHRoaXMuc2VsZWN0ZWRPcHRpb25zID0gY2hhbmdlc1twcm9wTmFtZV0uY3VycmVudFZhbHVlO1xuICAgICAgICAvL2NvbnNvbGUubG9nKFwiSXMgdGhpcyBzdHJpbmcgLS0+XCIsIHRoaXMuaXNvcHRpb25MaXN0QXJheVN0cmluZywgdGhpcy5zZWxlY3RlZE9wdGlvbnMpO1xuICAgICAgICBpZiAodGhpcy5pc29wdGlvbkxpc3RBcmF5U3RyaW5nKSB7XG4gICAgICAgICAgdGhpcy5zZWxlY3RlZE9wdGlvbnNTZXQgPSBbXTtcbiAgICAgICAgICB0aGlzLm9wdGlvbkxpc3QuZmlsdGVyKChpdGVtKSA9PiB7XG4gICAgICAgICAgICBsZXQgaXRlbUtleSA9IHRoaXMuc2VsZWN0ZWRPcHRpb25zLmluZGV4T2YoPGFueT5pdGVtKTtcbiAgICAgICAgICAgIGlmIChpdGVtS2V5ID4gLTEpIHtcbiAgICAgICAgICAgICAgdGhpcy5zZWxlY3RlZE9wdGlvbnNTZXRbaXRlbUtleV0gPSBpdGVtO1xuICAgICAgICAgICAgICByZXR1cm4gdHJ1ZTtcbiAgICAgICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgICAgIHJldHVybiBmYWxzZTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICB9KTtcbiAgICAgICAgICB0aGlzLmZpbHRlclRleHQgPSB0aGlzLnNlbGVjdGVkT3B0aW9ucy5sZW5ndGggPiAwICYmIHRoaXMub3BlbiA9PT0gZmFsc2UgPyAodGhpcy5zZWxlY3RlZE9wdGlvbnNbMF0ubGVuZ3RoXG4gICAgICAgICAgICA8ICh0aGlzLnNlbGVjdGlvblRleHRXaWR0aCArIDEpID8gdGhpcy5zZWxlY3RlZE9wdGlvbnNbMF0gOiB0aGlzLnNlbGVjdGVkT3B0aW9uc1swXS5zdWJzdHJpbmcoMCwgdGhpcy5zZWxlY3Rpb25UZXh0V2lkdGgpICtcbiAgICAgICAgICAgICcuLicpIDogJyc7XG4gICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgdGhpcy5zZWxlY3RlZE9wdGlvbnNTZXQgPSBbXTtcbiAgICAgICAgICB0aGlzLm9wdGlvbkxpc3QuZmlsdGVyKChpdGVtKSA9PiB7XG4gICAgICAgICAgICAvL2NvbnNvbGUubG9nKFwiVGVzdCBPYmplY3QgLS0+XCIsdGhpcy5zZWxlY3RlZE9wdGlvbnMuZmluZEluZGV4KHggPT4geFt0aGlzLmRpc3BsYXlOYW1lS2V5XSA9PT0gKDxhbnk+aXRlbSlbdGhpcy50b2dnbGVTZWxlY3Rpb25LZXldKSk7XG4gICAgICAgICAgICBsZXQgaW5kZXggPSB0aGlzLnNlbGVjdGVkT3B0aW9ucy5maW5kSW5kZXgoeCA9PiB4W3RoaXMuZGlzcGxheU5hbWVLZXldID09PSAoPGFueT5pdGVtKVt0aGlzLnRvZ2dsZVNlbGVjdGlvbktleV0pO1xuICAgICAgICAgICAgLy9jb25zb2xlLmxvZyhcInNlbGVjdGVkT3B0aW9ucyAtLT4gXCIsIHRoaXMuc2VsZWN0ZWRPcHRpb25zLCBpbmRleCwoPGFueT5pdGVtKVt0aGlzLnRvZ2dsZVNlbGVjdGlvbktleV0pXG4gICAgICAgICAgICBpZiAoaW5kZXggPiAtMSkge1xuICAgICAgICAgICAgICB0aGlzLnNlbGVjdGVkT3B0aW9uc1NldFtpbmRleF0gPSBpdGVtO1xuICAgICAgICAgICAgICByZXR1cm4gdHJ1ZTtcbiAgICAgICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgICAgIHJldHVybiBmYWxzZTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICB9KTtcbiAgICAgICAgICBjb25zb2xlLmxvZyhcInNlbGVjdGVkT3B0aW9uc1NldCAtLT5cIiwgdGhpcy5zZWxlY3RlZE9wdGlvbnNTZXQpO1xuICAgICAgICAgIHRoaXMuZmlsdGVyVGV4dCA9IHRoaXMuc2VsZWN0ZWRPcHRpb25zLmxlbmd0aCA+IDAgJiYgdGhpcy5vcGVuID09PSBmYWxzZSA/ICh0aGlzLnNlbGVjdGVkT3B0aW9uc1swXVt0aGlzLnRvZ2dsZVNlbGVjdGlvbktleV0ubGVuZ3RoXG4gICAgICAgICAgICA8ICh0aGlzLnNlbGVjdGlvblRleHRXaWR0aCArIDEpID8gdGhpcy5zZWxlY3RlZE9wdGlvbnNbMF1bdGhpcy50b2dnbGVTZWxlY3Rpb25LZXldIDogdGhpcy5zZWxlY3RlZE9wdGlvbnNbMF1bdGhpcy50b2dnbGVTZWxlY3Rpb25LZXldLnN1YnN0cmluZygwLCB0aGlzLnNlbGVjdGlvblRleHRXaWR0aCkgK1xuICAgICAgICAgICAgJy4uJykgOiAnJztcbiAgICAgICAgfVxuXG5cbiAgICAgICAgdGhpcy5zZWxlY3RlZEFsbCA9IHRoaXMub3B0aW9uTGlzdC5sZW5ndGggPT09IHRoaXMuc2VsZWN0ZWRPcHRpb25zU2V0Lmxlbmd0aCA/IHRydWUgOiBmYWxzZTtcbiAgICAgIH1cbiAgICB9XG4gIH1cblxuICB0b2dnbGVPcHRpb24ob3B0aW9uKSB7XG4gICAgdGhpcy5maWx0ZXJUZXh0ID0gJyc7XG4gICAgbGV0IGluZGV4ID0gMDtcbiAgICBpZiAodGhpcy5pc29wdGlvbkxpc3RBcmF5U3RyaW5nKSB7XG4gICAgICBpbmRleCA9IHRoaXMuc2VsZWN0ZWRPcHRpb25zLmluZGV4T2Yob3B0aW9uKTtcbiAgICAgIGlmIChpbmRleCA8IDApIHtcbiAgICAgICAgdGhpcy5zZWxlY3RlZE9wdGlvbnMucHVzaChvcHRpb24pO1xuICAgICAgICB0aGlzLnNlbGVjdGVkT3B0aW9uc1NldC5wdXNoKG9wdGlvbik7XG4gICAgICB9IGVsc2Uge1xuICAgICAgICB0aGlzLnNlbGVjdGVkT3B0aW9ucy5zcGxpY2UoaW5kZXgsIDEpO1xuICAgICAgICB0aGlzLnNlbGVjdGVkT3B0aW9uc1NldC5zcGxpY2UoaW5kZXgsIDEpO1xuICAgICAgfVxuICAgIH0gZWxzZSB7XG4gICAgICBpbmRleCA9IHRoaXMuc2VsZWN0ZWRPcHRpb25zLmZpbmRJbmRleCh4ID0+IHhbdGhpcy50b2dnbGVTZWxlY3Rpb25LZXldID09PSBvcHRpb25bdGhpcy50b2dnbGVTZWxlY3Rpb25LZXldKTtcbiAgICAgIC8vY29uc29sZS5sb2coXCJzZWxlY3RlZE9wdGlvbnMgLS0+IFwiLCB0aGlzLnNlbGVjdGVkT3B0aW9ucywgaW5kZXgsIG9wdGlvblt0aGlzLnRvZ2dsZVNlbGVjdGlvbktleV0pO1xuICAgICAgaWYgKGluZGV4IDwgMCkge1xuICAgICAgICB0aGlzLnNlbGVjdGVkT3B0aW9ucy5wdXNoKG9wdGlvbik7XG4gICAgICAgIHRoaXMuc2VsZWN0ZWRPcHRpb25zU2V0LnB1c2gob3B0aW9uKTtcbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIHRoaXMuc2VsZWN0ZWRPcHRpb25zLnNwbGljZShpbmRleCwgMSk7XG4gICAgICAgIHRoaXMuc2VsZWN0ZWRPcHRpb25zU2V0LnNwbGljZShpbmRleCwgMSk7XG4gICAgICB9XG4gICAgfVxuXG4gICAgaWYgKHRoaXMub3B0aW9uTGlzdC5sZW5ndGggPT09IHRoaXMuc2VsZWN0ZWRPcHRpb25zLmxlbmd0aCkge1xuICAgICAgdGhpcy5zZWxlY3RlZEFsbCA9IHRydWU7XG4gICAgfSBlbHNlIHtcbiAgICAgIHRoaXMuc2VsZWN0ZWRBbGwgPSBmYWxzZTtcbiAgICB9XG5cbiAgICAvLyBjb25zb2xlLmxvZyh0aGlzLnNlbGVjdGVkT3B0aW9ucyk7XG4gICAgLy8gY29uc29sZS5sb2codGhpcy5zZWxlY3RlZE9wdGlvbnNTZXQpO1xuICAgIC8vdGhpcy5zZWxlY3RlZE9wdGlvbnNTZXQgPSB0aGlzLmdldFNlbGVjdGVkT3B0aW9uU2V0KHRoaXMuc2VsZWN0ZWRPcHRpb25zU2V0KTtcbiAgICAvLyBjb25zb2xlLmxvZyhcIkFmdGVyIE1vZGlmaWVkIC0tPlwiLCB0aGlzLnNlbGVjdGVkT3B0aW9uc1NldCk7XG4gICAgdGhpcy5zZWxlY3Rpb25DaGFuZ2UuZW1pdCh0aGlzLnNlbGVjdGVkT3B0aW9uc1NldCk7XG4gIH1cblxuICAvLyBnZXRTZWxlY3RlZE9wdGlvblNldChzZWxlY3RlZE9wdGlvbnNTZXQpIHtcbiAgLy8gICBpZih0aGlzLmlzU2VsZWN0ZWRPcHRpb25zQXJheVN0cmluZyl7XG4gIC8vICAgICAgIGxldCBzZWxlY3RlZE9wdGlvbkxpc3RTdHJpbmdBcnJheTogYW55ID0gW107XG4gIC8vICAgICAgIHRoaXMuc2VsZWN0ZWRPcHRpb25zU2V0LmZvckVhY2goaXRlbSA9PiB7XG4gIC8vICAgICAgICAgc2VsZWN0ZWRPcHRpb25MaXN0U3RyaW5nQXJyYXkucHVzaChpdGVtW3RoaXMuZGlzcGxheU5hbWVLZXldKTtcbiAgLy8gICAgICAgIH0pO1xuICAvLyAgICAgICByZXR1cm4gc2VsZWN0ZWRPcHRpb25MaXN0U3RyaW5nQXJyYXk7XG4gIC8vICAgfSBlbHNlIHtcbiAgLy8gICAgIHJldHVybiBzZWxlY3RlZE9wdGlvbnNTZXQ7XG4gIC8vICAgfVxuXG4gIC8vIH1cbiAgc2VsZWN0QWxsKGV2ZW50KSB7XG4gICAgZXZlbnQuc3RvcFByb3BhZ2F0aW9uKCk7XG4gICAgdGhpcy5maWx0ZXJUZXh0ID0gJyc7XG4gICAgdGhpcy5zZWxlY3RlZEFsbCA9IHRydWU7XG4gICAgbGV0IHRvZ2dsZVNlbGVjdGlvbktleSA9IHRoaXMudG9nZ2xlU2VsZWN0aW9uS2V5O1xuICAgIGlmICh0aGlzLmlzb3B0aW9uTGlzdEFyYXlTdHJpbmcpIHtcbiAgICAgIHRoaXMuc2VsZWN0ZWRPcHRpb25zID0gdGhpcy5vcHRpb25MaXN0Lm1hcChmdW5jdGlvbiAoaXRlbTogYW55KSB7XG4gICAgICAgIHJldHVybiBpdGVtW3RvZ2dsZVNlbGVjdGlvbktleV1cbiAgICAgIH0pO1xuICAgIH0gZWxzZSB7XG4gICAgICB0aGlzLnNlbGVjdGVkT3B0aW9ucyA9IHRoaXMub3B0aW9uTGlzdC5tYXAoZnVuY3Rpb24gKGl0ZW06IGFueSkge1xuICAgICAgICByZXR1cm4gaXRlbVxuICAgICAgfSk7XG4gICAgfVxuICAgIHRoaXMuc2VsZWN0ZWRPcHRpb25zU2V0ID0gdGhpcy5vcHRpb25MaXN0O1xuICAgIC8vdGhpcy5zZWxlY3RlZE9wdGlvbnNTZXQgPSB0aGlzLmdldFNlbGVjdGVkT3B0aW9uU2V0KHRoaXMuc2VsZWN0ZWRPcHRpb25zU2V0KTtcbiAgICB0aGlzLnNlbGVjdGlvbkNoYW5nZS5lbWl0KHRoaXMuc2VsZWN0ZWRPcHRpb25zU2V0KTtcbiAgfVxuICByZXNldChldmVudCkge1xuICAgIGV2ZW50LnN0b3BQcm9wYWdhdGlvbigpO1xuICAgIHRoaXMuc2VsZWN0ZWRBbGwgPSBmYWxzZTtcbiAgICB0aGlzLnNlbGVjdGVkT3B0aW9ucyA9IFtdO1xuICAgIHRoaXMuc2VsZWN0ZWRPcHRpb25zU2V0ID0gW107XG4gICAgdGhpcy5maWx0ZXJUZXh0ID0gJyc7XG4gICAgdGhpcy5zZWxlY3Rpb25DaGFuZ2UuZW1pdCh0aGlzLnNlbGVjdGVkT3B0aW9uc1NldCk7XG4gIH1cblxuICBpc09wdGlvblNlbGVjdGVkKG9wdGlvbikge1xuICAgIGxldCBzZWxlY3RlZEZsYWc6IGJvb2xlYW47XG4gICAgaWYgKHRoaXMuaXNvcHRpb25MaXN0QXJheVN0cmluZykge1xuICAgICAgc2VsZWN0ZWRGbGFnID0gdGhpcy5zZWxlY3RlZE9wdGlvbnMuaW5kZXhPZihvcHRpb24pID4gLTE7XG4gICAgfSBlbHNlIHtcbiAgICAgIGxldCBpbmRleCA9IHRoaXMuc2VsZWN