@c8y/ngx-components
Version:
Angular modules for Cumulocity IoT applications
47 lines • 20.4 kB
JavaScript
import { DiagnosticsService } from './diagnostics.service';
import { ActivatedRoute } from '@angular/router';
import { Component } from '@angular/core';
import { BehaviorSubject, pipe } from 'rxjs';
import { map } from 'rxjs/operators';
import { operationStatusClasses, operationStatusIcons, OperationRealtimeService } from '@c8y/ngx-components';
import * as i0 from "@angular/core";
import * as i1 from "@angular/router";
import * as i2 from "./diagnostics.service";
import * as i3 from "@c8y/ngx-components";
import * as i4 from "@angular/common";
import * as i5 from "@c8y/ngx-components/repository/shared";
import * as i6 from "ngx-bootstrap/tooltip";
export class DiagnosticsComponent {
constructor(route, diagnosticService, operationRealtime) {
this.route = route;
this.diagnosticService = diagnosticService;
this.operationRealtime = operationRealtime;
this.statusIcons = operationStatusIcons;
this.statusClasses = operationStatusClasses;
this.deviceId = this.route.snapshot.parent.data.contextData.id;
this.device$ = new BehaviorSubject(this.route.snapshot.parent.data.contextData);
this.operations$ = this.diagnosticService.getOperations$(this.device$);
this.operationsPipe = pipe(map(ops => ops.filter(op => op[this.diagnosticService.fragment])));
this.realtimeOptions = {
entityOrId: this.deviceId,
removeOnUpdate: true,
insertOnUpdate: true
};
}
onDiagnosticRequest() {
this.diagnosticService.createOperation(this.deviceId);
}
onDelete(operation) {
this.diagnosticService.deleteOperation(operation);
}
onCancel(operation) {
this.diagnosticService.cancelOperation(operation);
}
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.13", ngImport: i0, type: DiagnosticsComponent, deps: [{ token: i1.ActivatedRoute }, { token: i2.DiagnosticsService }, { token: i3.OperationRealtimeService }], target: i0.ɵɵFactoryTarget.Component }); }
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "18.2.13", type: DiagnosticsComponent, selector: "c8y-diagnostics", ngImport: i0, template: "<c8y-action-bar-item [placement]=\"'right'\">\n <button\n class=\"btn btn-link\"\n type=\"button\"\n title=\"{{ 'Request diagnostic file' | translate }}\"\n (click)=\"onDiagnosticRequest()\"\n >\n <i c8yIcon=\"stethoscope\"></i>\n <span translate>Request diagnostic file</span>\n </button>\n</c8y-action-bar-item>\n\n<div\n class=\"page-sticky-header hidden-xs c8y-list__item c8y-list--timeline\"\n *ngIf=\"operationCount > 0\"\n>\n <div class=\"d-flex\">\n <div class=\"c8y-list--timeline__item__date a-s-center\">\n <label>{{ 'Date' | translate }}</label>\n </div>\n <div class=\"c8y-list__item__block flex-grow\">\n <div class=\"c8y-list__item__icon\">\n <i class=\"p-l-24\"></i>\n </div>\n <div class=\"c8y-list__item__body\">\n <div class=\"content-flex-40\">\n <div class=\"col-4\">{{ 'Event' | translate }}</div>\n <div class=\"col-5 m-l-8\">{{ 'File' | translate }}</div>\n </div>\n </div>\n </div>\n </div>\n</div>\n\n<c8y-list-group>\n <ng-template\n c8yFor\n let-operation\n [c8yForOf]=\"operations$\"\n [c8yForPipe]=\"operationsPipe\"\n [c8yForRealtime]=\"operationRealtime\"\n [c8yForRealtimeOptions]=\"realtimeOptions\"\n (c8yForCount)=\"operationCount = $event\"\n >\n <c8y-li-timeline>\n {{ operation.creationTime | c8yDate }}\n <c8y-li>\n <c8y-li-icon>\n <i\n [c8yIcon]=\"statusIcons[operation.status]\"\n [ngClass]=\"statusClasses[operation.status]\"\n [tooltip]=\"operation.status?.toString() | translate\"\n ></i>\n </c8y-li-icon>\n <c8y-li-body class=\"content-flex-40\">\n <div class=\"col-4\">\n <p class=\"text-truncate-wrap\" title=\"{{ operation.description | translate }}\">\n {{ operation.description | translate }}\n </p>\n </div>\n <div class=\"col-5\" *ngIf=\"operation.c8y_DiagnosticReport?.file\">\n <div class=\"text-truncate-wrap m-t-xs-8\">\n <span class=\"text-label-small visible-xs\" translate>File</span>\n <span title=\"{{ operation.c8y_DiagnosticReport.file }}\">\n <c8y-file-download\n url=\"{{ operation.c8y_DiagnosticReport.file }}\"\n ></c8y-file-download>\n </span>\n </div>\n </div>\n </c8y-li-body>\n <c8y-li-action\n (click)=\"onCancel(operation)\"\n *ngIf=\"operation.status === 'PENDING'\"\n icon=\"times\"\n label=\"{{ 'Cancel' | translate }}\"\n ></c8y-li-action>\n <c8y-li-action\n (click)=\"onDelete(operation)\"\n *ngIf=\"operation.status === 'SUCCESSFUL'\"\n icon=\"delete\"\n label=\"{{ 'Delete' | translate }}\"\n ></c8y-li-action>\n </c8y-li>\n </c8y-li-timeline>\n </ng-template>\n</c8y-list-group>\n\n<!-- EMPTY STATE -->\n\n<c8y-ui-empty-state\n *ngIf=\"operationCount === 0\"\n [icon]=\"'stethoscope'\"\n [title]=\"'No diagnostic files available.' | translate\"\n></c8y-ui-empty-state>\n", dependencies: [{ kind: "component", type: i3.ActionBarItemComponent, selector: "c8y-action-bar-item", inputs: ["placement", "priority", "itemClass", "injector", "groupId", "inGroupPriority"] }, { kind: "component", type: i3.EmptyStateComponent, selector: "c8y-ui-empty-state", inputs: ["icon", "title", "subtitle", "horizontal"] }, { kind: "directive", type: i3.IconDirective, selector: "[c8yIcon]", inputs: ["c8yIcon"] }, { kind: "directive", type: i3.C8yTranslateDirective, selector: "[translate],[ngx-translate]" }, { kind: "directive", type: i4.NgClass, selector: "[ngClass]", inputs: ["class", "ngClass"] }, { kind: "directive", type: i4.NgIf, selector: "[ngIf]", inputs: ["ngIf", "ngIfThen", "ngIfElse"] }, { kind: "directive", type: i3.ForOfDirective, selector: "[c8yFor]", inputs: ["c8yForOf", "c8yForLoadMore", "c8yForPipe", "c8yForNotFound", "c8yForMaxIterations", "c8yForLoadingTemplate", "c8yForLoadNextLabel", "c8yForLoadingLabel", "c8yForRealtime", "c8yForRealtimeOptions", "c8yForComparator", "c8yForEnableVirtualScroll", "c8yForVirtualScrollElementSize", "c8yForVirtualScrollStrategy", "c8yForVirtualScrollContainerHeight"], outputs: ["c8yForCount", "c8yForChange", "c8yForLoadMoreComponent"] }, { kind: "component", type: i3.ListGroupComponent, selector: "c8y-list-group" }, { kind: "component", type: i3.ListItemComponent, selector: "c8y-list-item, c8y-li", inputs: ["active", "highlighted", "emptyActions", "dense", "collapsed", "selectable"], outputs: ["collapsedChange"] }, { kind: "component", type: i3.ListItemIconComponent, selector: "c8y-list-item-icon, c8y-li-icon", inputs: ["icon", "status"] }, { kind: "component", type: i3.ListItemBodyComponent, selector: "c8y-list-item-body, c8y-li-body", inputs: ["body"] }, { kind: "component", type: i3.ListItemActionComponent, selector: "c8y-list-item-action, c8y-li-action", inputs: ["label", "icon", "disabled"], outputs: ["click"] }, { kind: "component", type: i3.ListItemTimelineComponent, selector: "c8y-list-item-timeline, c8y-li-timeline" }, { kind: "component", type: i5.FileDownloadComponent, selector: "c8y-file-download", inputs: ["url"] }, { kind: "directive", type: i6.TooltipDirective, selector: "[tooltip], [tooltipHtml]", inputs: ["adaptivePosition", "tooltip", "placement", "triggers", "container", "containerClass", "boundariesElement", "isOpen", "isDisabled", "delay", "tooltipHtml", "tooltipPlacement", "tooltipIsOpen", "tooltipEnable", "tooltipAppendToBody", "tooltipAnimation", "tooltipClass", "tooltipContext", "tooltipPopupDelay", "tooltipFadeDuration", "tooltipTrigger"], outputs: ["tooltipChange", "onShown", "onHidden", "tooltipStateChanged"], exportAs: ["bs-tooltip"] }, { kind: "pipe", type: i3.C8yTranslatePipe, name: "translate" }, { kind: "pipe", type: i3.DatePipe, name: "c8yDate" }] }); }
}
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.13", ngImport: i0, type: DiagnosticsComponent, decorators: [{
type: Component,
args: [{ selector: 'c8y-diagnostics', template: "<c8y-action-bar-item [placement]=\"'right'\">\n <button\n class=\"btn btn-link\"\n type=\"button\"\n title=\"{{ 'Request diagnostic file' | translate }}\"\n (click)=\"onDiagnosticRequest()\"\n >\n <i c8yIcon=\"stethoscope\"></i>\n <span translate>Request diagnostic file</span>\n </button>\n</c8y-action-bar-item>\n\n<div\n class=\"page-sticky-header hidden-xs c8y-list__item c8y-list--timeline\"\n *ngIf=\"operationCount > 0\"\n>\n <div class=\"d-flex\">\n <div class=\"c8y-list--timeline__item__date a-s-center\">\n <label>{{ 'Date' | translate }}</label>\n </div>\n <div class=\"c8y-list__item__block flex-grow\">\n <div class=\"c8y-list__item__icon\">\n <i class=\"p-l-24\"></i>\n </div>\n <div class=\"c8y-list__item__body\">\n <div class=\"content-flex-40\">\n <div class=\"col-4\">{{ 'Event' | translate }}</div>\n <div class=\"col-5 m-l-8\">{{ 'File' | translate }}</div>\n </div>\n </div>\n </div>\n </div>\n</div>\n\n<c8y-list-group>\n <ng-template\n c8yFor\n let-operation\n [c8yForOf]=\"operations$\"\n [c8yForPipe]=\"operationsPipe\"\n [c8yForRealtime]=\"operationRealtime\"\n [c8yForRealtimeOptions]=\"realtimeOptions\"\n (c8yForCount)=\"operationCount = $event\"\n >\n <c8y-li-timeline>\n {{ operation.creationTime | c8yDate }}\n <c8y-li>\n <c8y-li-icon>\n <i\n [c8yIcon]=\"statusIcons[operation.status]\"\n [ngClass]=\"statusClasses[operation.status]\"\n [tooltip]=\"operation.status?.toString() | translate\"\n ></i>\n </c8y-li-icon>\n <c8y-li-body class=\"content-flex-40\">\n <div class=\"col-4\">\n <p class=\"text-truncate-wrap\" title=\"{{ operation.description | translate }}\">\n {{ operation.description | translate }}\n </p>\n </div>\n <div class=\"col-5\" *ngIf=\"operation.c8y_DiagnosticReport?.file\">\n <div class=\"text-truncate-wrap m-t-xs-8\">\n <span class=\"text-label-small visible-xs\" translate>File</span>\n <span title=\"{{ operation.c8y_DiagnosticReport.file }}\">\n <c8y-file-download\n url=\"{{ operation.c8y_DiagnosticReport.file }}\"\n ></c8y-file-download>\n </span>\n </div>\n </div>\n </c8y-li-body>\n <c8y-li-action\n (click)=\"onCancel(operation)\"\n *ngIf=\"operation.status === 'PENDING'\"\n icon=\"times\"\n label=\"{{ 'Cancel' | translate }}\"\n ></c8y-li-action>\n <c8y-li-action\n (click)=\"onDelete(operation)\"\n *ngIf=\"operation.status === 'SUCCESSFUL'\"\n icon=\"delete\"\n label=\"{{ 'Delete' | translate }}\"\n ></c8y-li-action>\n </c8y-li>\n </c8y-li-timeline>\n </ng-template>\n</c8y-list-group>\n\n<!-- EMPTY STATE -->\n\n<c8y-ui-empty-state\n *ngIf=\"operationCount === 0\"\n [icon]=\"'stethoscope'\"\n [title]=\"'No diagnostic files available.' | translate\"\n></c8y-ui-empty-state>\n" }]
}], ctorParameters: () => [{ type: i1.ActivatedRoute }, { type: i2.DiagnosticsService }, { type: i3.OperationRealtimeService }] });
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZGlhZ25vc3RpY3MuY29tcG9uZW50LmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vZGlhZ25vc3RpY3MvZGlhZ25vc3RpY3MuY29tcG9uZW50LnRzIiwiLi4vLi4vLi4vZGlhZ25vc3RpY3MvZGlhZ25vc3RpY3MuY29tcG9uZW50Lmh0bWwiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUFFLGtCQUFrQixFQUFFLE1BQU0sdUJBQXVCLENBQUM7QUFDM0QsT0FBTyxFQUFFLGNBQWMsRUFBRSxNQUFNLGlCQUFpQixDQUFDO0FBQ2pELE9BQU8sRUFBRSxTQUFTLEVBQUUsTUFBTSxlQUFlLENBQUM7QUFDMUMsT0FBTyxFQUFFLGVBQWUsRUFBRSxJQUFJLEVBQUUsTUFBTSxNQUFNLENBQUM7QUFDN0MsT0FBTyxFQUFFLEdBQUcsRUFBRSxNQUFNLGdCQUFnQixDQUFDO0FBQ3JDLE9BQU8sRUFFTCxzQkFBc0IsRUFDdEIsb0JBQW9CLEVBQ3BCLHdCQUF3QixFQUV6QixNQUFNLHFCQUFxQixDQUFDOzs7Ozs7OztBQU03QixNQUFNLE9BQU8sb0JBQW9CO0lBZ0IvQixZQUNVLEtBQXFCLEVBQ3JCLGlCQUFxQyxFQUN0QyxpQkFBMkM7UUFGMUMsVUFBSyxHQUFMLEtBQUssQ0FBZ0I7UUFDckIsc0JBQWlCLEdBQWpCLGlCQUFpQixDQUFvQjtRQUN0QyxzQkFBaUIsR0FBakIsaUJBQWlCLENBQTBCO1FBbEJwRCxnQkFBVyxHQUFHLG9CQUFvQixDQUFDO1FBQ25DLGtCQUFhLEdBQUcsc0JBQXNCLENBQUM7UUFDdkMsYUFBUSxHQUFXLElBQUksQ0FBQyxLQUFLLENBQUMsUUFBUSxDQUFDLE1BQU0sQ0FBQyxJQUFJLENBQUMsV0FBVyxDQUFDLEVBQUUsQ0FBQztRQUNsRSxZQUFPLEdBQUcsSUFBSSxlQUFlLENBQWlCLElBQUksQ0FBQyxLQUFLLENBQUMsUUFBUSxDQUFDLE1BQU0sQ0FBQyxJQUFJLENBQUMsV0FBVyxDQUFDLENBQUM7UUFDM0YsZ0JBQVcsR0FBRyxJQUFJLENBQUMsaUJBQWlCLENBQUMsY0FBYyxDQUFDLElBQUksQ0FBQyxPQUFPLENBQUMsQ0FBQztRQUNsRSxtQkFBYyxHQUFnQyxJQUFJLENBQ2hELEdBQUcsQ0FBQyxHQUFHLENBQUMsRUFBRSxDQUFDLEdBQUcsQ0FBQyxNQUFNLENBQUMsRUFBRSxDQUFDLEVBQUUsQ0FBQyxFQUFFLENBQUMsSUFBSSxDQUFDLGlCQUFpQixDQUFDLFFBQVEsQ0FBQyxDQUFDLENBQUMsQ0FDbEUsQ0FBQztRQUNGLG9CQUFlLEdBQXlCO1lBQ3RDLFVBQVUsRUFBRSxJQUFJLENBQUMsUUFBUTtZQUN6QixjQUFjLEVBQUUsSUFBSTtZQUNwQixjQUFjLEVBQUUsSUFBSTtTQUNHLENBQUM7SUFPdkIsQ0FBQztJQUVKLG1CQUFtQjtRQUNqQixJQUFJLENBQUMsaUJBQWlCLENBQUMsZUFBZSxDQUFDLElBQUksQ0FBQyxRQUFRLENBQUMsQ0FBQztJQUN4RCxDQUFDO0lBRUQsUUFBUSxDQUFDLFNBQXFCO1FBQzVCLElBQUksQ0FBQyxpQkFBaUIsQ0FBQyxlQUFlLENBQUMsU0FBUyxDQUFDLENBQUM7SUFDcEQsQ0FBQztJQUVELFFBQVEsQ0FBQyxTQUFxQjtRQUM1QixJQUFJLENBQUMsaUJBQWlCLENBQUMsZUFBZSxDQUFDLFNBQVMsQ0FBQyxDQUFDO0lBQ3BELENBQUM7K0dBaENVLG9CQUFvQjttR0FBcEIsb0JBQW9CLHVEQ2pCakMseWxHQStGQTs7NEZEOUVhLG9CQUFvQjtrQkFKaEMsU0FBUzsrQkFFRSxpQkFBaUIiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBEaWFnbm9zdGljc1NlcnZpY2UgfSBmcm9tICcuL2RpYWdub3N0aWNzLnNlcnZpY2UnO1xuaW1wb3J0IHsgQWN0aXZhdGVkUm91dGUgfSBmcm9tICdAYW5ndWxhci9yb3V0ZXInO1xuaW1wb3J0IHsgQ29tcG9uZW50IH0gZnJvbSAnQGFuZ3VsYXIvY29yZSc7XG5pbXBvcnQgeyBCZWhhdmlvclN1YmplY3QsIHBpcGUgfSBmcm9tICdyeGpzJztcbmltcG9ydCB7IG1hcCB9IGZyb20gJ3J4anMvb3BlcmF0b3JzJztcbmltcG9ydCB7XG4gIEZvck9mUmVhbHRpbWVPcHRpb25zLFxuICBvcGVyYXRpb25TdGF0dXNDbGFzc2VzLFxuICBvcGVyYXRpb25TdGF0dXNJY29ucyxcbiAgT3BlcmF0aW9uUmVhbHRpbWVTZXJ2aWNlLFxuICBGb3JPZkZpbHRlclBpcGVcbn0gZnJvbSAnQGM4eS9uZ3gtY29tcG9uZW50cyc7XG5pbXBvcnQgeyBJTWFuYWdlZE9iamVjdCwgSU9wZXJhdGlvbiB9IGZyb20gJ0BjOHkvY2xpZW50JztcbkBDb21wb25lbnQoe1xuICB0ZW1wbGF0ZVVybDogJy4vZGlhZ25vc3RpY3MuY29tcG9uZW50Lmh0bWwnLFxuICBzZWxlY3RvcjogJ2M4eS1kaWFnbm9zdGljcydcbn0pXG5leHBvcnQgY2xhc3MgRGlhZ25vc3RpY3NDb21wb25lbnQge1xuICBzdGF0dXNJY29ucyA9IG9wZXJhdGlvblN0YXR1c0ljb25zO1xuICBzdGF0dXNDbGFzc2VzID0gb3BlcmF0aW9uU3RhdHVzQ2xhc3NlcztcbiAgZGV2aWNlSWQ6IHN0cmluZyA9IHRoaXMucm91dGUuc25hcHNob3QucGFyZW50LmRhdGEuY29udGV4dERhdGEuaWQ7XG4gIGRldmljZSQgPSBuZXcgQmVoYXZpb3JTdWJqZWN0PElNYW5hZ2VkT2JqZWN0Pih0aGlzLnJvdXRlLnNuYXBzaG90LnBhcmVudC5kYXRhLmNvbnRleHREYXRhKTtcbiAgb3BlcmF0aW9ucyQgPSB0aGlzLmRpYWdub3N0aWNTZXJ2aWNlLmdldE9wZXJhdGlvbnMkKHRoaXMuZGV2aWNlJCk7XG4gIG9wZXJhdGlvbnNQaXBlOiBGb3JPZkZpbHRlclBpcGU8SU9wZXJhdGlvbj4gPSBwaXBlKFxuICAgIG1hcChvcHMgPT4gb3BzLmZpbHRlcihvcCA9PiBvcFt0aGlzLmRpYWdub3N0aWNTZXJ2aWNlLmZyYWdtZW50XSkpXG4gICk7XG4gIHJlYWx0aW1lT3B0aW9uczogRm9yT2ZSZWFsdGltZU9wdGlvbnMgPSB7XG4gICAgZW50aXR5T3JJZDogdGhpcy5kZXZpY2VJZCxcbiAgICByZW1vdmVPblVwZGF0ZTogdHJ1ZSxcbiAgICBpbnNlcnRPblVwZGF0ZTogdHJ1ZVxuICB9IGFzIEZvck9mUmVhbHRpbWVPcHRpb25zO1xuICBvcGVyYXRpb25Db3VudDogbnVtYmVyO1xuXG4gIGNvbnN0cnVjdG9yKFxuICAgIHByaXZhdGUgcm91dGU6IEFjdGl2YXRlZFJvdXRlLFxuICAgIHByaXZhdGUgZGlhZ25vc3RpY1NlcnZpY2U6IERpYWdub3N0aWNzU2VydmljZSxcbiAgICBwdWJsaWMgb3BlcmF0aW9uUmVhbHRpbWU6IE9wZXJhdGlvblJlYWx0aW1lU2VydmljZVxuICApIHt9XG5cbiAgb25EaWFnbm9zdGljUmVxdWVzdCgpIHtcbiAgICB0aGlzLmRpYWdub3N0aWNTZXJ2aWNlLmNyZWF0ZU9wZXJhdGlvbih0aGlzLmRldmljZUlkKTtcbiAgfVxuXG4gIG9uRGVsZXRlKG9wZXJhdGlvbjogSU9wZXJhdGlvbikge1xuICAgIHRoaXMuZGlhZ25vc3RpY1NlcnZpY2UuZGVsZXRlT3BlcmF0aW9uKG9wZXJhdGlvbik7XG4gIH1cblxuICBvbkNhbmNlbChvcGVyYXRpb246IElPcGVyYXRpb24pIHtcbiAgICB0aGlzLmRpYWdub3N0aWNTZXJ2aWNlLmNhbmNlbE9wZXJhdGlvbihvcGVyYXRpb24pO1xuICB9XG59XG4iLCI8Yzh5LWFjdGlvbi1iYXItaXRlbSBbcGxhY2VtZW50XT1cIidyaWdodCdcIj5cbiAgPGJ1dHRvblxuICAgIGNsYXNzPVwiYnRuIGJ0bi1saW5rXCJcbiAgICB0eXBlPVwiYnV0dG9uXCJcbiAgICB0aXRsZT1cInt7ICdSZXF1ZXN0IGRpYWdub3N0aWMgZmlsZScgfCB0cmFuc2xhdGUgfX1cIlxuICAgIChjbGljayk9XCJvbkRpYWdub3N0aWNSZXF1ZXN0KClcIlxuICA+XG4gICAgPGkgYzh5SWNvbj1cInN0ZXRob3Njb3BlXCI+PC9pPlxuICAgIDxzcGFuIHRyYW5zbGF0ZT5SZXF1ZXN0IGRpYWdub3N0aWMgZmlsZTwvc3Bhbj5cbiAgPC9idXR0b24+XG48L2M4eS1hY3Rpb24tYmFyLWl0ZW0+XG5cbjxkaXZcbiAgY2xhc3M9XCJwYWdlLXN0aWNreS1oZWFkZXIgaGlkZGVuLXhzIGM4eS1saXN0X19pdGVtIGM4eS1saXN0LS10aW1lbGluZVwiXG4gICpuZ0lmPVwib3BlcmF0aW9uQ291bnQgPiAwXCJcbj5cbiAgPGRpdiBjbGFzcz1cImQtZmxleFwiPlxuICAgIDxkaXYgY2xhc3M9XCJjOHktbGlzdC0tdGltZWxpbmVfX2l0ZW1fX2RhdGUgYS1zLWNlbnRlclwiPlxuICAgICAgPGxhYmVsPnt7ICdEYXRlJyB8IHRyYW5zbGF0ZSB9fTwvbGFiZWw+XG4gICAgPC9kaXY+XG4gICAgPGRpdiBjbGFzcz1cImM4eS1saXN0X19pdGVtX19ibG9jayBmbGV4LWdyb3dcIj5cbiAgICAgIDxkaXYgY2xhc3M9XCJjOHktbGlzdF9faXRlbV9faWNvblwiPlxuICAgICAgICA8aSBjbGFzcz1cInAtbC0yNFwiPjwvaT5cbiAgICAgIDwvZGl2PlxuICAgICAgPGRpdiBjbGFzcz1cImM4eS1saXN0X19pdGVtX19ib2R5XCI+XG4gICAgICAgIDxkaXYgY2xhc3M9XCJjb250ZW50LWZsZXgtNDBcIj5cbiAgICAgICAgICA8ZGl2IGNsYXNzPVwiY29sLTRcIj57eyAnRXZlbnQnIHwgdHJhbnNsYXRlIH19PC9kaXY+XG4gICAgICAgICAgPGRpdiBjbGFzcz1cImNvbC01IG0tbC04XCI+e3sgJ0ZpbGUnIHwgdHJhbnNsYXRlIH19PC9kaXY+XG4gICAgICAgIDwvZGl2PlxuICAgICAgPC9kaXY+XG4gICAgPC9kaXY+XG4gIDwvZGl2PlxuPC9kaXY+XG5cbjxjOHktbGlzdC1ncm91cD5cbiAgPG5nLXRlbXBsYXRlXG4gICAgYzh5Rm9yXG4gICAgbGV0LW9wZXJhdGlvblxuICAgIFtjOHlGb3JPZl09XCJvcGVyYXRpb25zJFwiXG4gICAgW2M4eUZvclBpcGVdPVwib3BlcmF0aW9uc1BpcGVcIlxuICAgIFtjOHlGb3JSZWFsdGltZV09XCJvcGVyYXRpb25SZWFsdGltZVwiXG4gICAgW2M4eUZvclJlYWx0aW1lT3B0aW9uc109XCJyZWFsdGltZU9wdGlvbnNcIlxuICAgIChjOHlGb3JDb3VudCk9XCJvcGVyYXRpb25Db3VudCA9ICRldmVudFwiXG4gID5cbiAgICA8Yzh5LWxpLXRpbWVsaW5lPlxuICAgICAge3sgb3BlcmF0aW9uLmNyZWF0aW9uVGltZSB8IGM4eURhdGUgfX1cbiAgICAgIDxjOHktbGk+XG4gICAgICAgIDxjOHktbGktaWNvbj5cbiAgICAgICAgICA8aVxuICAgICAgICAgICAgW2M4eUljb25dPVwic3RhdHVzSWNvbnNbb3BlcmF0aW9uLnN0YXR1c11cIlxuICAgICAgICAgICAgW25nQ2xhc3NdPVwic3RhdHVzQ2xhc3Nlc1tvcGVyYXRpb24uc3RhdHVzXVwiXG4gICAgICAgICAgICBbdG9vbHRpcF09XCJvcGVyYXRpb24uc3RhdHVzPy50b1N0cmluZygpIHwgdHJhbnNsYXRlXCJcbiAgICAgICAgICA+PC9pPlxuICAgICAgICA8L2M4eS1saS1pY29uPlxuICAgICAgICA8Yzh5LWxpLWJvZHkgY2xhc3M9XCJjb250ZW50LWZsZXgtNDBcIj5cbiAgICAgICAgICA8ZGl2IGNsYXNzPVwiY29sLTRcIj5cbiAgICAgICAgICAgIDxwIGNsYXNzPVwidGV4dC10cnVuY2F0ZS13cmFwXCIgdGl0bGU9XCJ7eyBvcGVyYXRpb24uZGVzY3JpcHRpb24gfCB0cmFuc2xhdGUgfX1cIj5cbiAgICAgICAgICAgICAge3sgb3BlcmF0aW9uLmRlc2NyaXB0aW9uIHwgdHJhbnNsYXRlIH19XG4gICAgICAgICAgICA8L3A+XG4gICAgICAgICAgPC9kaXY+XG4gICAgICAgICAgPGRpdiBjbGFzcz1cImNvbC01XCIgKm5nSWY9XCJvcGVyYXRpb24uYzh5X0RpYWdub3N0aWNSZXBvcnQ/LmZpbGVcIj5cbiAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJ0ZXh0LXRydW5jYXRlLXdyYXAgbS10LXhzLThcIj5cbiAgICAgICAgICAgICAgPHNwYW4gY2xhc3M9XCJ0ZXh0LWxhYmVsLXNtYWxsIHZpc2libGUteHNcIiB0cmFuc2xhdGU+RmlsZTwvc3Bhbj5cbiAgICAgICAgICAgICAgPHNwYW4gdGl0bGU9XCJ7eyBvcGVyYXRpb24uYzh5X0RpYWdub3N0aWNSZXBvcnQuZmlsZSB9fVwiPlxuICAgICAgICAgICAgICAgIDxjOHktZmlsZS1kb3dubG9hZFxuICAgICAgICAgICAgICAgICAgdXJsPVwie3sgb3BlcmF0aW9uLmM4eV9EaWFnbm9zdGljUmVwb3J0LmZpbGUgfX1cIlxuICAgICAgICAgICAgICAgID48L2M4eS1maWxlLWRvd25sb2FkPlxuICAgICAgICAgICAgICA8L3NwYW4+XG4gICAgICAgICAgICA8L2Rpdj5cbiAgICAgICAgICA8L2Rpdj5cbiAgICAgICAgPC9jOHktbGktYm9keT5cbiAgICAgICAgPGM4eS1saS1hY3Rpb25cbiAgICAgICAgICAoY2xpY2spPVwib25DYW5jZWwob3BlcmF0aW9uKVwiXG4gICAgICAgICAgKm5nSWY9XCJvcGVyYXRpb24uc3RhdHVzID09PSAnUEVORElORydcIlxuICAgICAgICAgIGljb249XCJ0aW1lc1wiXG4gICAgICAgICAgbGFiZWw9XCJ7eyAnQ2FuY2VsJyB8IHRyYW5zbGF0ZSB9fVwiXG4gICAgICAgID48L2M4eS1saS1hY3Rpb24+XG4gICAgICAgIDxjOHktbGktYWN0aW9uXG4gICAgICAgICAgKGNsaWNrKT1cIm9uRGVsZXRlKG9wZXJhdGlvbilcIlxuICAgICAgICAgICpuZ0lmPVwib3BlcmF0aW9uLnN0YXR1cyA9PT0gJ1NVQ0NFU1NGVUwnXCJcbiAgICAgICAgICBpY29uPVwiZGVsZXRlXCJcbiAgICAgICAgICBsYWJlbD1cInt7ICdEZWxldGUnIHwgdHJhbnNsYXRlIH19XCJcbiAgICAgICAgPjwvYzh5LWxpLWFjdGlvbj5cbiAgICAgIDwvYzh5LWxpPlxuICAgIDwvYzh5LWxpLXRpbWVsaW5lPlxuICA8L25nLXRlbXBsYXRlPlxuPC9jOHktbGlzdC1ncm91cD5cblxuPCEtLSBFTVBUWSBTVEFURSAtLT5cblxuPGM4eS11aS1lbXB0eS1zdGF0ZVxuICAqbmdJZj1cIm9wZXJhdGlvbkNvdW50ID09PSAwXCJcbiAgW2ljb25dPVwiJ3N0ZXRob3Njb3BlJ1wiXG4gIFt0aXRsZV09XCInTm8gZGlhZ25vc3RpYyBmaWxlcyBhdmFpbGFibGUuJyB8IHRyYW5zbGF0ZVwiXG4+PC9jOHktdWktZW1wdHktc3RhdGU+XG4iXX0=