@iotize/ionic
Version:
Iotize specific building blocks on top of @ionic/angular.
262 lines • 31.4 kB
JavaScript
import { Component, ContentChild, Directive, ElementRef, EventEmitter, HostListener, Input, Output, } from '@angular/core';
import { TapError } from '@iotize/tap';
import { ResultCode } from '@iotize/tap/client/api';
import { TapClientError } from '@iotize/tap/client/impl';
import { debug } from '../logger';
import { TaskManagerService } from '../task-manager/task-manager.service';
import * as i0 from "@angular/core";
import * as i1 from "../task-manager/task-manager.service";
import * as i2 from "@angular/common";
const TAG = 'TaskManagerComponent';
export class TaskManagerActionCancelDirective {
elementRef;
onClick = new EventEmitter();
constructor(elementRef) {
this.elementRef = elementRef;
}
// disable(value: boolean) {
// // this.elementRef.
// }
onClickListener() {
debug('app-task-manager-action-cancel clicked');
this.onClick.emit();
}
/** @nocollapse */ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: TaskManagerActionCancelDirective, deps: [{ token: i0.ElementRef }], target: i0.ɵɵFactoryTarget.Directive });
/** @nocollapse */ static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "18.2.14", type: TaskManagerActionCancelDirective, selector: "[app-task-manager-action-cancel]", outputs: { onClick: "onClick" }, host: { listeners: { "click": "onClickListener()" } }, ngImport: i0 });
}
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: TaskManagerActionCancelDirective, decorators: [{
type: Directive,
args: [{
selector: '[app-task-manager-action-cancel]',
}]
}], ctorParameters: () => [{ type: i0.ElementRef }], propDecorators: { onClick: [{
type: Output
}], onClickListener: [{
type: HostListener,
args: ['click']
}] } });
export class TaskManagerActionExecDirective {
onClick = new EventEmitter();
constructor() { } // public tpl: TemplateRef<any>
onClickListener() {
this.onClick.emit();
}
/** @nocollapse */ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: TaskManagerActionExecDirective, deps: [], target: i0.ɵɵFactoryTarget.Directive });
/** @nocollapse */ static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "18.2.14", type: TaskManagerActionExecDirective, selector: "[app-task-manager-action-exec]", outputs: { onClick: "onClick" }, host: { listeners: { "click": "onClickListener()" } }, ngImport: i0 });
}
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: TaskManagerActionExecDirective, decorators: [{
type: Directive,
args: [{
selector: '[app-task-manager-action-exec]',
}]
}], ctorParameters: () => [], propDecorators: { onClick: [{
type: Output
}], onClickListener: [{
type: HostListener,
args: ['click']
}] } });
export class TaskManagerRunningComponent {
taskManager;
/** Template inside the MatTab view that contains an `<ng-content>`. */
// @ViewChild(TemplateRef, { static: true }) _implicitContent: TemplateRef<any>;
context;
constructor(taskManager) {
this.taskManager = taskManager;
}
/** @nocollapse */ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: TaskManagerRunningComponent, deps: [{ token: i1.TaskManagerService }], target: i0.ɵɵFactoryTarget.Component });
/** @nocollapse */ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "18.2.14", type: TaskManagerRunningComponent, selector: "app-task-manager-running", inputs: { context: "context" }, ngImport: i0, template: ' <ng-content></ng-content> ', isInline: true });
}
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: TaskManagerRunningComponent, decorators: [{
type: Component,
args: [{
selector: 'app-task-manager-running',
template: ' <ng-content></ng-content> ',
}]
}], ctorParameters: () => [{ type: i1.TaskManagerService }], propDecorators: { context: [{
type: Input
}] } });
export class TaskManagerDelayedComponent {
taskManager;
/** Template inside the MatTab view that contains an `<ng-content>`. */
// @ViewChild(TemplateRef, { static: true }) _implicitContent: TemplateRef<any>;
context;
constructor(taskManager) {
this.taskManager = taskManager;
}
cancelTask() {
debug(TAG, 'Cancel task click');
}
/** @nocollapse */ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: TaskManagerDelayedComponent, deps: [{ token: i1.TaskManagerService }], target: i0.ɵɵFactoryTarget.Component });
/** @nocollapse */ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "18.2.14", type: TaskManagerDelayedComponent, selector: "app-task-manager-delayed", inputs: { context: "context" }, ngImport: i0, template: ' <ng-content></ng-content> ', isInline: true });
}
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: TaskManagerDelayedComponent, decorators: [{
type: Component,
args: [{
selector: 'app-task-manager-delayed',
template: ' <ng-content></ng-content> ',
}]
}], ctorParameters: () => [{ type: i1.TaskManagerService }], propDecorators: { context: [{
type: Input
}] } });
export class TaskManagerActionComponent {
taskManager;
context;
/** Template inside the MatTab view that contains an `<ng-content>`. */
// @ViewChild(TemplateRef, { static: true }) _implicitContent: TemplateRef<any>;
// @ContentChildren(TaskManagerActionExecDirective) execButton!: TaskManagerActionExecDirective;
constructor(taskManager) {
this.taskManager = taskManager;
}
performTask() {
debug(TAG, 'Perform task click');
}
/** @nocollapse */ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: TaskManagerActionComponent, deps: [{ token: i1.TaskManagerService }], target: i0.ɵɵFactoryTarget.Component });
/** @nocollapse */ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "18.2.14", type: TaskManagerActionComponent, selector: "app-task-manager-action", inputs: { context: "context" }, ngImport: i0, template: ' <ng-content></ng-content> ', isInline: true });
}
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: TaskManagerActionComponent, decorators: [{
type: Component,
args: [{
selector: 'app-task-manager-action',
template: ' <ng-content></ng-content> ',
}]
}], ctorParameters: () => [{ type: i1.TaskManagerService }], propDecorators: { context: [{
type: Input
}] } });
export class TaskManagerComponent {
taskManager;
taskContainer;
set task(taskContainerOrString) {
let taskContainer;
taskContainer = taskContainerOrString;
debug(TAG, 'set task ', taskContainer?.task?.id);
this.taskContainer = taskContainer;
}
get taskId() {
return this.taskContainer?.task?.id;
}
cancelDirective;
execDirective;
// @ContentChild(TaskManagerActionComponent, {}) actionComponent: TaskManagerActionComponent;
constructor(taskManager) {
this.taskManager = taskManager;
}
get loading() {
return false;
}
get taskState() {
return this.taskContainer?.meta?.state;
}
get actionTemplateContext() {
const cont = this._createContext();
if ('execTask' in cont) {
cont['execTask'] = (...context) => {
this.execTask(context);
};
}
return { $implicit: cont };
}
get delayedTemplateContext() {
const context = this._createContext();
if ('execTask' in this) {
context['execTask'] = () => {
if (this.taskId && this.taskManager.hasTask(this.taskId)) {
this.taskManager.cancel(this.taskId);
}
};
}
return { $implicit: context };
}
_createContext() {
return this;
}
ngAfterViewInit() {
if (this.cancelDirective) {
this.cancelDirective.onClick.subscribe(() => {
this.cancelTask();
});
}
else {
debug(TAG, 'cancel button is not set yet');
}
if (this.execDirective) {
this.execDirective.onClick.subscribe(() => {
this.execTask();
});
}
}
ngOnDestroy() {
debug(TAG, 'Task', this.taskId, 'component ngOnDestroy');
this.cancelTask();
}
cancelTask() {
debug(TAG, 'cancelTask clicked!');
if (!this.taskId) {
return;
}
if (this.taskManager.hasTask(this.taskId)) {
this.taskManager.cancel(this.taskId);
}
else {
debug(TAG, 'cannot cancel task ', this.taskId, 'it does not exist');
}
}
explainDelayReason() {
const err = this.taskContainer?.meta.error;
if (err) {
const codeError = err;
switch (codeError.code) {
case TapError.Code.ResponseStatusError:
switch (err.response.status) {
case ResultCode.UNAUTHORIZED:
return 'Waiting for user login';
}
break;
case TapError.Code.ExecuteRequestError:
const cause = err.cause;
if (cause) {
switch (cause.code) {
case TapClientError.Code.NotConnectedError:
case 'NfcTagLostError':
case 'NfcNotConnectedError':
return 'Waiting for Tap reconnection';
}
}
}
return 'Unknown reason';
}
}
execTask(context) {
const container = this.taskContainer;
if (!container) {
return;
}
debug(TAG, 'execTask ', container.task.id);
this.taskManager.addTaskContainer(container);
// this.execDirective.disable(true);
this.taskManager.exec(container.task.id, context).subscribe({
error: (err) => {
debug(`Task ${container.task.id} error: ${err.message}`);
console.warn(err);
// this.execDirective.disable(false);
},
complete: () => {
debug(`Task ${container.task.id} COMPLETED`);
},
});
}
/** @nocollapse */ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: TaskManagerComponent, deps: [{ token: i1.TaskManagerService }], target: i0.ɵɵFactoryTarget.Component });
/** @nocollapse */ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "18.2.14", type: TaskManagerComponent, selector: "app-task-manager", inputs: { task: "task" }, queries: [{ propertyName: "cancelDirective", first: true, predicate: TaskManagerActionCancelDirective, descendants: true, static: true }, { propertyName: "execDirective", first: true, predicate: TaskManagerActionExecDirective, descendants: true, static: true }], ngImport: i0, template: "<ng-container [ngSwitch]=\"taskState\">\n <ng-content\n select=\"app-task-manager-delayed\"\n *ngSwitchCase=\"'delayed'\"\n ></ng-content>\n <ng-content\n select=\"app-task-manager-running\"\n *ngSwitchCase=\"'running'\"\n ></ng-content>\n <ng-content select=\"app-task-manager-action\" *ngSwitchDefault></ng-content>\n</ng-container>\n", styles: [""], dependencies: [{ kind: "directive", type: i2.NgSwitch, selector: "[ngSwitch]", inputs: ["ngSwitch"] }, { kind: "directive", type: i2.NgSwitchCase, selector: "[ngSwitchCase]", inputs: ["ngSwitchCase"] }, { kind: "directive", type: i2.NgSwitchDefault, selector: "[ngSwitchDefault]" }] });
}
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: TaskManagerComponent, decorators: [{
type: Component,
args: [{ selector: 'app-task-manager', template: "<ng-container [ngSwitch]=\"taskState\">\n <ng-content\n select=\"app-task-manager-delayed\"\n *ngSwitchCase=\"'delayed'\"\n ></ng-content>\n <ng-content\n select=\"app-task-manager-running\"\n *ngSwitchCase=\"'running'\"\n ></ng-content>\n <ng-content select=\"app-task-manager-action\" *ngSwitchDefault></ng-content>\n</ng-container>\n" }]
}], ctorParameters: () => [{ type: i1.TaskManagerService }], propDecorators: { task: [{
type: Input
}], cancelDirective: [{
type: ContentChild,
args: [TaskManagerActionCancelDirective, { static: true }]
}], execDirective: [{
type: ContentChild,
args: [TaskManagerActionExecDirective, { static: true }]
}] } });
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoidGFzay1tYW5hZ2VyLmNvbXBvbmVudC5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uLy4uLy4uLy4uLy4uL3Byb2plY3RzL2lvdGl6ZS1pb25pYy9zcmMvbGliL3Rhc2stbWFuYWdlci11aS90YXNrLW1hbmFnZXIuY29tcG9uZW50LnRzIiwiLi4vLi4vLi4vLi4vLi4vLi4vcHJvamVjdHMvaW90aXplLWlvbmljL3NyYy9saWIvdGFzay1tYW5hZ2VyLXVpL3Rhc2stbWFuYWdlci5jb21wb25lbnQuaHRtbCJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiQUFBQSxPQUFPLEVBRUwsU0FBUyxFQUNULFlBQVksRUFDWixTQUFTLEVBQ1QsVUFBVSxFQUNWLFlBQVksRUFDWixZQUFZLEVBQ1osS0FBSyxFQUVMLE1BQU0sR0FDUCxNQUFNLGVBQWUsQ0FBQztBQUV2QixPQUFPLEVBQUUsUUFBUSxFQUEwQixNQUFNLGFBQWEsQ0FBQztBQUMvRCxPQUFPLEVBQUUsVUFBVSxFQUFFLE1BQU0sd0JBQXdCLENBQUM7QUFDcEQsT0FBTyxFQUFFLGNBQWMsRUFBRSxNQUFNLHlCQUF5QixDQUFDO0FBQ3pELE9BQU8sRUFBRSxLQUFLLEVBQUUsTUFBTSxXQUFXLENBQUM7QUFFbEMsT0FBTyxFQUFFLGtCQUFrQixFQUFFLE1BQU0sc0NBQXNDLENBQUM7Ozs7QUFFMUUsTUFBTSxHQUFHLEdBQUcsc0JBQXNCLENBQUM7QUFLbkMsTUFBTSxPQUFPLGdDQUFnQztJQUd0QjtJQUZYLE9BQU8sR0FBRyxJQUFJLFlBQVksRUFBUSxDQUFDO0lBRTdDLFlBQXFCLFVBQXNCO1FBQXRCLGVBQVUsR0FBVixVQUFVLENBQVk7SUFBRyxDQUFDO0lBRS9DLDRCQUE0QjtJQUM1Qix3QkFBd0I7SUFDeEIsSUFBSTtJQUVtQixlQUFlO1FBQ3BDLEtBQUssQ0FBQyx3Q0FBd0MsQ0FBQyxDQUFDO1FBQ2hELElBQUksQ0FBQyxPQUFPLENBQUMsSUFBSSxFQUFFLENBQUM7SUFDdEIsQ0FBQzsySEFa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RSxFQUFFLE9BQU8sQ0FBQyxDQUFDLFNBQVMsQ0FBQztZQUMxRCxLQUFLLEVBQUUsQ0FBQyxHQUFHLEVBQUUsRUFBRTtnQkFDYixLQUFLLENBQUMsUUFBUSxTQUFTLENBQUMsSUFBSSxDQUFDLEVBQUUsV0FBVyxHQUFHLENBQUMsT0FBTyxFQUFFLENBQUMsQ0FBQztnQkFDekQsT0FBTyxDQUFDLElBQUksQ0FBQyxHQUFHLENBQUMsQ0FBQztnQkFDbEIscUNBQXFDO1lBQ3ZDLENBQUM7WUFDRCxRQUFRLEVBQUUsR0FBRyxFQUFFO2dCQUNiLEtBQUssQ0FBQyxRQUFRLFNBQVMsQ0FBQyxJQUFJLENBQUMsRUFBRSxZQUFZLENBQUMsQ0FBQztZQUMvQyxDQUFDO1NBQ0YsQ0FBQyxDQUFDO0lBQ0wsQ0FBQzsySEF2SVUsb0JBQW9COytHQUFwQixvQkFBb0IsK0hBZ0JqQixnQ0FBZ0MsOEZBRWhDLDhCQUE4Qiw4REM3SDlDLG1XQVdBOzs0RkRnR2Esb0JBQW9CO2tCQUxoQyxTQUFTOytCQUNFLGtCQUFrQjt1RkFPZixJQUFJO3NCQUFoQixLQUFLO2dCQWNOLGVBQWU7c0JBRGQsWUFBWTt1QkFBQyxnQ0FBZ0MsRUFBRSxFQUFFLE1BQU0sRUFBRSxJQUFJLEVBQUU7Z0JBR2hFLGFBQWE7c0JBRFosWUFBWTt1QkFBQyw4QkFBOEIsRUFBRSxFQUFFLE1BQU0sRUFBRSxJQUFJLEVBQUUiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQge1xuICBBZnRlclZpZXdJbml0LFxuICBDb21wb25lbnQsXG4gIENvbnRlbnRDaGlsZCxcbiAgRGlyZWN0aXZlLFxuICBFbGVtZW50UmVmLFxuICBFdmVudEVtaXR0ZXIsXG4gIEhvc3RMaXN0ZW5lcixcbiAgSW5wdXQsXG4gIE9uRGVzdHJveSxcbiAgT3V0cHV0LFxufSBmcm9tICdAYW5ndWxhci9jb3JlJztcbmltcG9ydCB7IENvZGVFcnJvciB9IGZyb20gJ0Bpb3RpemUvY29tbW9uL2Vycm9yJztcbmltcG9ydCB7IFRhcEVycm9yLCBUYXBSZXNwb25zZVN0YXR1c0Vycm9yIH0gZnJvbSAnQGlvdGl6ZS90YXAnO1xuaW1wb3J0IHsgUmVzdWx0Q29kZSB9IGZyb20gJ0Bpb3RpemUvdGFwL2NsaWVudC9hcGknO1xuaW1wb3J0IHsgVGFwQ2xpZW50RXJyb3IgfSBmcm9tICdAaW90aXplL3RhcC9jbGllbnQvaW1wbCc7XG5pbXBvcnQgeyBkZWJ1ZyB9IGZyb20gJy4uL2xvZ2dlcic7XG5pbXBvcnQgeyBUYXNrTWFuYWdlciB9IGZyb20gJy4uL3Rhc2stbWFuYWdlci9kZWZpbml0aW9ucyc7XG5pbXBvcnQgeyBUYXNrTWFuYWdlclNlcnZpY2UgfSBmcm9tICcuLi90YXNrLW1hbmFnZXIvdGFzay1tYW5hZ2VyLnNlcnZpY2UnO1xuXG5jb25zdCBUQUcgPSAnVGFza01hbmFnZXJDb21wb25lbnQnO1xuXG5ARGlyZWN0aXZlKHtcbiAgc2VsZWN0b3I6ICdbYXBwLXRhc2stbWFuYWdlci1hY3Rpb24tY2FuY2VsXScsXG59KVxuZXhwb3J0IGNsYXNzIFRhc2tNYW5hZ2VyQWN0aW9uQ2FuY2VsRGlyZWN0aXZlIHtcbiAgQE91dHB1dCgpIG9uQ2xpY2sgPSBuZXcgRXZlbnRFbWl0dGVyPHZvaWQ+KCk7XG5cbiAgY29uc3RydWN0b3IocmVhZG9ubHkgZWxlbWVudFJlZjogRWxlbWVudFJlZikge31cblxuICAvLyBkaXNhYmxlKHZhbHVlOiBib29sZWFuKSB7XG4gIC8vICAgLy8gdGhpcy5lbGVtZW50UmVmLlxuICAvLyB9XG5cbiAgQEhvc3RMaXN0ZW5lcignY2xpY2snKSBvbkNsaWNrTGlzdGVuZXIoKSB7XG4gICAgZGVidWcoJ2FwcC10YXNrLW1hbmFnZXItYWN0aW9uLWNhbmNlbCBjbGlja2VkJyk7XG4gICAgdGhpcy5vbkNsaWNrLmVtaXQoKTtcbiAgfVxufVxuXG5ARGlyZWN0aXZlKHtcbiAgc2VsZWN0b3I6ICdbYXBwLXRhc2stbWFuYWdlci1hY3Rpb24tZXhlY10nLFxufSlcbmV4cG9ydCBjbGFzcyBUYXNrTWFuYWdlckFjdGlvbkV4ZWNEaXJlY3RpdmUge1xuICBAT3V0cHV0KCkgb25DbGljayA9IG5ldyBFdmVudEVtaXR0ZXI8dm9pZD4oKTtcblxuICBjb25zdHJ1Y3RvcigpIHt9IC8vIHB1YmxpYyB0cGw6IFRlbXBsYXRlUmVmPGFueT5cblxuICBASG9zdExpc3RlbmVyKCdjbGljaycpIG9uQ2xpY2tMaXN0ZW5lcigpIHtcbiAgICB0aGlzLm9uQ2xpY2suZW1pdCgpO1xuICB9XG59XG5cbkBDb21wb25lbnQoe1xuICBzZWxlY3RvcjogJ2FwcC10YXNrLW1hbmFnZXItcnVubmluZycsXG4gIHRlbXBsYXRlOiAnIDxuZy1jb250ZW50PjwvbmctY29udGVudD4gJyxcbn0pXG5leHBvcnQgY2xhc3MgVGFza01hbmFnZXJSdW5uaW5nQ29tcG9uZW50IHtcbiAgLyoqIFRlbXBsYXRlIGluc2lkZSB0aGUgTWF0VGFiIHZpZXcgdGhhdCBjb250YWlucyBhbiBgPG5nLWNvbnRlbnQ+YC4gKi9cbiAgLy8gQFZpZXdDaGlsZChUZW1wbGF0ZVJlZiwgeyBzdGF0aWM6IHRydWUgfSkgX2ltcGxpY2l0Q29udGVudDogVGVtcGxhdGVSZWY8YW55PjtcblxuICBASW5wdXQoKSBjb250ZXh0OiBhbnk7XG5cbiAgY29uc3RydWN0b3IocHVibGljIHRhc2tNYW5hZ2VyOiBUYXNrTWFuYWdlclNlcnZpY2UpIHt9XG59XG5cbkBDb21wb25lbnQoe1xuICBzZWxlY3RvcjogJ2FwcC10YXNrLW1hbmFnZXItZGVsYXllZCcsXG4gIHRlbXBsYXRlOiAnIDxuZy1jb250ZW50PjwvbmctY29udGVudD4gJyxcbn0pXG5leHBvcnQgY2xhc3MgVGFza01hbmFnZXJEZWxheWVkQ29tcG9uZW50IHtcbiAgLyoqIFRlbXBsYXRlIGluc2lkZSB0aGUgTWF0VGFiIHZpZXcgdGhhdCBjb250YWlucyBhbiBgPG5nLWNvbnRlbnQ+YC4gKi9cbiAgLy8gQFZpZXdDaGlsZChUZW1wbGF0ZVJlZiwgeyBzdGF0aWM6IHRydWUgfSkgX2ltcGxpY2l0Q29udGVudDogVGVtcGxhdGVSZWY8YW55PjtcblxuICBASW5wdXQoKSBjb250ZXh0OiBhbnk7XG5cbiAgY29uc3RydWN0b3IocHVibGljIHRhc2tNYW5hZ2VyOiBUYXNrTWFuYWdlclNlcnZpY2UpIHt9XG5cbiAgY2FuY2VsVGFzaygpIHtcbiAgICBkZWJ1ZyhUQUcsICdDYW5jZWwgdGFzayBjbGljaycpO1xuICB9XG59XG5cbkBDb21wb25lbnQoe1xuICBzZWxlY3RvcjogJ2FwcC10YXNrLW1hbmFnZXItYWN0aW9uJyxcbiAgdGVtcGxhdGU6ICcgPG5nLWNvbnRlbnQ+PC9uZy1jb250ZW50PiAnLFxufSlcbmV4cG9ydCBjbGFzcyBUYXNrTWFuYWdlckFjdGlvbkNvbXBvbmVudCB7XG4gIEBJbnB1dCgpIGNvbnRleHQ6IGFueTtcblxuICAvKiogVGVtcGxhdGUgaW5zaWRlIHRoZSBNYXRUYWIgdmlldyB0aGF0IGNvbnRhaW5zIGFuIGA8bmctY29udGVudD5gLiAqL1xuICAvLyBAVmlld0NoaWxkKFRlbXBsYXRlUmVmLCB7IHN0YXRpYzogdHJ1ZSB9KSBfaW1wbGljaXRDb250ZW50OiBUZW1wbGF0ZVJlZjxhbnk+O1xuXG4gIC8vIEBDb250ZW50Q2hpbGRyZW4oVGFza01hbmFnZXJBY3Rpb25FeGVjRGlyZWN0aXZlKSBleGVjQnV0dG9uITogVGFza01hbmFnZXJBY3Rpb25FeGVjRGlyZWN0aXZlO1xuXG4gIGNvbnN0cnVjdG9yKHB1YmxpYyB0YXNrTWFuYWdlcjogVGFza01hbmFnZXJTZXJ2aWNlKSB7fVxuXG4gIHBlcmZvcm1UYXNrKCkge1xuICAgIGRlYnVnKFRBRywgJ1BlcmZvcm0gdGFzayBjbGljaycpO1xuICB9XG59XG5cbkBDb21wb25lbnQoe1xuICBzZWxlY3RvcjogJ2FwcC10YXNrLW1hbmFnZXInLFxuICB0ZW1wbGF0ZVVybDogJy4vdGFzay1tYW5hZ2VyLmNvbXBvbmVudC5odG1sJyxcbiAgc3R5bGVVcmxzOiBbJy4vdGFzay1tYW5hZ2VyLmNvbXBvbmVudC5zY3NzJ10sXG59KVxuZXhwb3J0IGNsYXNzIFRhc2tNYW5hZ2VyQ29tcG9uZW50IGltcGxlbWVudHMgQWZ0ZXJWaWV3SW5pdCwgT25EZXN0cm95IHtcbiAgdGFza0NvbnRhaW5lcj86IFRhc2tNYW5hZ2VyLlRhc2tDb250YWluZXI8dW5rbm93bj47XG5cbiAgQElucHV0KCkgc2V0IHRhc2soXG4gICAgdGFza0NvbnRhaW5lck9yU3RyaW5nOiBUYXNrTWFuYWdlci5UYXNrQ29udGFpbmVyPHVua25vd24+IHwgc3RyaW5nXG4gICkge1xuICAgIGxldCB0YXNrQ29udGFpbmVyOiBUYXNrTWFuYWdlci5UYXNrQ29udGFpbmVyPHVua25vd24+IHwgdW5kZWZpbmVkO1xuICAgIHRhc2tDb250YWluZXIgPSB0YXNrQ29udGFpbmVyT3JTdHJpbmcgYXMgVGFza01hbmFnZXIuVGFza0NvbnRhaW5lcjx1bmtub3duPjtcbiAgICBkZWJ1ZyhUQUcsICdzZXQgdGFzayAnLCB0YXNrQ29udGFpbmVyPy50YXNrPy5pZCk7XG4gICAgdGhpcy50YXNrQ29udGFpbmVyID0gdGFza0NvbnRhaW5lcjtcbiAgfVxuXG4gIGdldCB0YXNrSWQoKSB7XG4gICAgcmV0dXJuIHRoaXMudGFza0NvbnRhaW5lcj8udGFzaz8uaWQ7XG4gIH1cblxuICBAQ29udGVudENoaWxkKFRhc2tNYW5hZ2VyQWN0aW9uQ2FuY2VsRGlyZWN0aXZlLCB7IHN0YXRpYzogdHJ1ZSB9KVxuICBjYW5jZWxEaXJlY3RpdmU/OiBUYXNrTWFuYWdlckFjdGlvbkNhbmNlbERpcmVjdGl2ZTtcbiAgQENvbnRlbnRDaGlsZChUYXNrTWFuYWdlckFjdGlvbkV4ZWNEaXJlY3RpdmUsIHsgc3RhdGljOiB0cnVlIH0pXG4gIGV4ZWNEaXJlY3RpdmU/OiBUYXNrTWFuYWdlckFjdGlvbkNhbmNlbERpcmVjdGl2ZTtcblxuICAvLyBAQ29udGVudENoaWxkKFRhc2tNYW5hZ2VyQWN0aW9uQ29tcG9uZW50LCB7fSkgYWN0aW9uQ29tcG9uZW50OiBUYXNrTWFuYWdlckFjdGlvbkNvbXBvbmVudDtcblxuICBjb25zdHJ1Y3RvcihwdWJsaWMgdGFza01hbmFnZXI6IFRhc2tNYW5hZ2VyU2VydmljZSkge31cblxuICBnZXQgbG9hZGluZygpOiBib29sZWFuIHtcbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cblxuICBnZXQgdGFza1N0YXRlKCkge1xuICAgIHJldHVybiB0aGlzLnRhc2tDb250YWluZXI/Lm1ldGE/LnN0YXRlO1xuICB9XG5cbiAgZ2V0IGFjdGlvblRlbXBsYXRlQ29udGV4dCgpIHtcbiAgICBjb25zdCBjb250ID0gdGhpcy5fY3JlYXRlQ29udGV4dCgpO1xuICAgIGlmICgnZXhlY1Rhc2snIGluIGNvbnQpIHtcbiAgICAgIGNvbnRbJ2V4ZWNUYXNrJ10gPSAoLi4uY29udGV4dDogYW55W10pID0+IHtcbiAgICAgICAgdGhpcy5leGVjVGFzayhjb250ZXh0KTtcbiAgICAgIH07XG4gICAgfVxuICAgIHJldHVybiB7ICRpbXBsaWNpdDogY29udCB9O1xuICB9XG5cbiAgZ2V0IGRlbGF5ZWRUZW1wbGF0ZUNvbnRleHQoKSB7XG4gICAgY29uc3QgY29udGV4dCA9IHRoaXMuX2NyZWF0ZUNvbnRleHQoKTtcbiAgICBpZiAoJ2V4ZWNUYXNrJyBpbiB0aGlzKSB7XG4gICAgICBjb250ZXh0WydleGVjVGFzayddID0gKCkgPT4ge1xuICAgICAgICBpZiAodGhpcy50YXNrSWQgJiYgdGhpcy50YXNrTWFuYWdlci5oYXNUYXNrKHRoaXMudGFza0lkKSkge1xuICAgICAgICAgIHRoaXMudGFza01hbmFnZXIuY2FuY2VsKHRoaXMudGFza0lkKTtcbiAgICAgICAgfVxuICAgICAgfTtcbiAgICB9XG4gICAgcmV0dXJuIHsgJGltcGxpY2l0OiBjb250ZXh0IH07XG4gIH1cblxuICBwcml2YXRlIF9jcmVhdGVDb250ZXh0KCk6IGFueSB7XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICBuZ0FmdGVyVmlld0luaXQoKTogdm9pZCB7XG4gICAgaWYgKHRoaXMuY2FuY2VsRGlyZWN0aXZlKSB7XG4gICAgICB0aGlzLmNhbmNlbERpcmVjdGl2ZS5vbkNsaWNrLnN1YnNjcmliZSgoKSA9PiB7XG4gICAgICAgIHRoaXMuY2FuY2VsVGFzaygpO1xuICAgICAgfSk7XG4gICAgfSBlbHNlIHtcbiAgICAgIGRlYnVnKFRBRywgJ2NhbmNlbCBidXR0b24gaXMgbm90IHNldCB5ZXQnKTtcbiAgICB9XG4gICAgaWYgKHRoaXMuZXhlY0RpcmVjdGl2ZSkge1xuICAgICAgdGhpcy5leGVjRGlyZWN0aXZlLm9uQ2xpY2suc3Vic2NyaWJlKCgpID0+IHtcbiAgICAgICAgdGhpcy5leGVjVGFzaygpO1xuICAgICAgfSk7XG4gICAgfVxuICB9XG5cbiAgbmdPbkRlc3Ryb3koKSB7XG4gICAgZGVidWcoVEFHLCAnVGFzaycsIHRoaXMudGFza0lkLCAnY29tcG9uZW50IG5nT25EZXN0cm95Jyk7XG4gICAgdGhpcy5jYW5jZWxUYXNrKCk7XG4gIH1cblxuICBjYW5jZWxUYXNrKCkge1xuICAgIGRlYnVnKFRBRywgJ2NhbmNlbFRhc2sgY2xpY2tlZCEnKTtcbiAgICBpZiAoIXRoaXMudGFza0lkKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIGlmICh0aGlzLnRhc2tNYW5hZ2VyLmhhc1Rhc2sodGhpcy50YXNrSWQpKSB7XG4gICAgICB0aGlzLnRhc2tNYW5hZ2VyLmNhbmNlbCh0aGlzLnRhc2tJZCk7XG4gICAgfSBlbHNlIHtcbiAgICAgIGRlYnVnKFRBRywgJ2Nhbm5vdCBjYW5jZWwgdGFzayAnLCB0aGlzLnRhc2tJZCwgJ2l0IGRvZXMgbm90IGV4aXN0Jyk7XG4gICAgfVxuICB9XG5cbiAgZXhwbGFpbkRlbGF5UmVhc29uKCkge1xuICAgIGNvbnN0IGVyciA9IHRoaXMudGFza0NvbnRhaW5lcj8ubWV0YS5lcnJvcjtcbiAgICBpZiAoZXJyKSB7XG4gICAgICBjb25zdCBjb2RlRXJyb3IgPSBlcnIgYXMgQ29kZUVycm9yO1xuICAgICAgc3dpdGNoIChjb2RlRXJyb3IuY29kZSkge1xuICAgICAgICBjYXNlIFRhcEVycm9yLkNvZGUuUmVzcG9uc2VTdGF0dXNFcnJvcjpcbiAgICAgICAgICBzd2l0Y2ggKChlcnIgYXMgVGFwUmVzcG9uc2VTdGF0dXNFcnJvcikucmVzcG9uc2Uuc3RhdHVzKSB7XG4gICAgICAgICAgICBjYXNlIFJlc3VsdENvZGUuVU5BVVRIT1JJWkVEOlxuICAgICAgICAgICAgICByZXR1cm4gJ1dhaXRpbmcgZm9yIHVzZXIgbG9naW4nO1xuICAgICAgICAgIH1cbiAgICAgICAgICBicmVhaztcbiAgICAgICAgY2FzZSBUYXBFcnJvci5Db2RlLkV4ZWN1dGVSZXF1ZXN0RXJyb3I6XG4gICAgICAgICAgY29uc3QgY2F1c2UgPSAoZXJyIGFzIFRhcEVycm9yKS5jYXVzZSBhcyBDb2RlRXJyb3I7XG4gICAgICAgICAgaWYgKGNhdXNlKSB7XG4gICAgICAgICAgICBzd2l0Y2ggKGNhdXNlLmNvZGUpIHtcbiAgICAgICAgICAgICAgY2FzZSBUYXBDbGllbnRFcnJvci5Db2RlLk5vdENvbm5lY3RlZEVycm9yOlxuICAgICAgICAgICAgICBjYXNlICdOZmNUYWdMb3N0RXJyb3InOlxuICAgICAgICAgICAgICBjYXNlICdOZmNOb3RDb25uZWN0ZWRFcnJvcic6XG4gICAgICAgICAgICAgICAgcmV0dXJuICdXYWl0aW5nIGZvciBUYXAgcmVjb25uZWN0aW9uJztcbiAgICAgICAgICAgIH1cbiAgICAgICAgICB9XG4gICAgICB9XG4gICAgICByZXR1cm4gJ1Vua25vd24gcmVhc29uJztcbiAgICB9XG4gIH1cblxuICBleGVjVGFzayhjb250ZXh0PzogYW55KSB7XG4gICAgY29uc3QgY29udGFpbmVyID0gdGhpcy50YXNrQ29udGFpbmVyO1xuICAgIGlmICghY29udGFpbmVyKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIGRlYnVnKFRBRywgJ2V4ZWNUYXNrICcsIGNvbnRhaW5lci50YXNrLmlkKTtcbiAgICB0aGlzLnRhc2tNYW5hZ2VyLmFkZFRhc2tDb250YWluZXIoY29udGFpbmVyKTtcbiAgICAvLyB0aGlzLmV4ZWNEaXJlY3RpdmUuZGlzYWJsZSh0cnVlKTtcbiAgICB0aGlzLnRhc2tNYW5hZ2VyLmV4ZWMoY29udGFpbmVyLnRhc2suaWQsIGNvbnRleHQpLnN1YnNjcmliZSh7XG4gICAgICBlcnJvcjogKGVycikgPT4ge1xuICAgICAgICBkZWJ1ZyhgVGFzayAke2NvbnRhaW5lci50YXNrLmlkfSBlcnJvcjogJHtlcnIubWVzc2FnZX1gKTtcbiAgICAgICAgY29uc29sZS53YXJuKGVycik7XG4gICAgICAgIC8vIHRoaXMuZXhlY0RpcmVjdGl2ZS5kaXNhYmxlKGZhbHNlKTtcbiAgICAgIH0sXG4gICAgICBjb21wbGV0ZTogKCkgPT4ge1xuICAgICAgICBkZWJ1ZyhgVGFzayAke2NvbnRhaW5lci50YXNrLmlkfSBDT01QTEVURURgKTtcbiAgICAgIH0sXG4gICAgfSk7XG4gIH1cbn1cbiIsIjxuZy1jb250YWluZXIgW25nU3dpdGNoXT1cInRhc2tTdGF0ZVwiPlxuICA8bmctY29udGVudFxuICAgIHNlbGVjdD1cImFwcC10YXNrLW1hbmFnZXItZGVsYXllZFwiXG4gICAgKm5nU3dpdGNoQ2FzZT1cIidkZWxheWVkJ1wiXG4gID48L25nLWNvbnRlbnQ+XG4gIDxuZy1jb250ZW50XG4gICAgc2VsZWN0PVwiYXBwLXRhc2stbWFuYWdlci1ydW5uaW5nXCJcbiAgICAqbmdTd2l0Y2hDYXNlPVwiJ3J1bm5pbmcnXCJcbiAgPjwvbmctY29udGVudD5cbiAgPG5nLWNvbnRlbnQgc2VsZWN0PVwiYXBwLXRhc2stbWFuYWdlci1hY3Rpb25cIiAqbmdTd2l0Y2hEZWZhdWx0PjwvbmctY29udGVudD5cbjwvbmctY29udGFpbmVyPlxuIl19