kre-form
Version:
本项目由 Angular8+ 编写的表单设计器和表单应用,所有的配置都是 JSON 结构体组成,PC 端是基于 ANT 组件库封装
642 lines • 53.7 kB
JavaScript
/**
* @fileoverview added by tsickle
* @suppress {checkTypes,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc
*/
import * as tslib_1 from "tslib";
import { Component, Input, Output, EventEmitter, } from "@angular/core";
import { Graph, Shape, Addon } from "@antv/x6";
import { NzMessageService } from "ng-zorro-antd/message";
var DataFlowComponent = /** @class */ (function () {
function DataFlowComponent(message) {
this.message = message;
this.drawerEvent = new EventEmitter();
this.modalEvent = new EventEmitter();
this.data = {
// 节点
nodes: [
{
id: "node1",
// String,可选,节点的唯一标识
x: 40,
// Number,必选,节点位置的 x 值
y: 40,
// Number,必选,节点位置的 y 值
width: 80,
// Number,可选,节点大小的 width 值
height: 40,
// Number,可选,节点大小的 height 值
label: "hello",
},
{
id: "node2",
// String,节点的唯一标识
x: 160,
// Number,必选,节点位置的 x 值
y: 180,
// Number,必选,节点位置的 y 值
width: 80,
// Number,可选,节点大小的 width 值
height: 40,
// Number,可选,节点大小的 height 值
label: "world",
},
],
// 边
edges: [
{
source: "node1",
// String,必须,起始节点 id
target: "node2",
},
],
};
this.title = "my-app";
}
/**
* @return {?}
*/
DataFlowComponent.prototype.ngOnInit = /**
* @return {?}
*/
function () {
this.graphShape();
this.grahpInit();
this.getHistoryGrahp();
this.graphEvent();
// console.log("节点", this.graph.getNodes());
// console.log("cell-----");
// console.log("节点和边", this.graph.getCells());
// console.log("根节点,即没有输入边的节点", this.graph.getRootNodes());
// console.log("叶子节点,即没有输出边的节点", this.graph.getLeafNodes());
// console.log("数量", this.graph.getCellCount());
// console.log(this.graph);
// console.log(this.stencil.graphs.group1.getNodes());
/** @type {?} */
var nodes = this.graph.getLeafNodes();
for (var i = 0; i < nodes.length; i++) {
/** @type {?} */
var node = nodes[i];
if (node["label"] !== "输出") {
this.message.error("界面必须包含输出");
break;
}
}
};
/**
* @return {?}
*/
DataFlowComponent.prototype.grahpInit = /**
* @return {?}
*/
function () {
var _this = this;
/** @type {?} */
var that = this;
// #region 初始化画布
this.graph = new Graph({
container: (/** @type {?} */ (document.getElementById("graph-container"))),
grid: true,
history: true,
minimap: {
enabled: true,
container: (/** @type {?} */ (document.getElementById("minimap"))),
width: 198,
height: 198,
padding: 10,
},
mousewheel: {
enabled: true,
zoomAtMousePosition: true,
modifiers: "ctrl",
minScale: 0.5,
maxScale: 3,
},
connecting: {
router: "manhattan",
connector: {
name: "rounded",
args: {
radius: 8,
},
},
anchor: "center",
connectionPoint: "anchor",
allowBlank: false,
snap: {
radius: 20,
},
createEdge: /**
* @return {?}
*/
function () {
return new Shape.Edge({
attrs: {
line: {
stroke: "#A2B1C3",
strokeWidth: 2,
targetMarker: {
name: "block",
width: 12,
height: 8,
},
},
},
zIndex: 0,
});
},
// 在移动边的时候判断连接是否有效
validateConnection:
// 在移动边的时候判断连接是否有效
/**
* @param {?} __0
* @return {?}
*/
function (_a) {
var sourceView = _a.sourceView, targetView = _a.targetView, sourceMagnet = _a.sourceMagnet, targetMagnet = _a.targetMagnet, sourceCell = _a.sourceCell, targetCell = _a.targetCell;
if (targetMagnet && targetCell) {
/** @type {?} */
var incomingEdges = (/** @type {?} */ (that.graph)).getIncomingEdges(targetCell) || [];
if (incomingEdges.length >= (/** @type {?} */ (targetView)).cell.getData().out) {
that.message.error("超出out数量");
return false;
}
}
// 不允许连接到自己
if (sourceView === targetView) {
// that.message.error("不允许连接到自己");
return false;
}
// 只能从输出链接桩创建连接
if (!sourceMagnet ||
sourceMagnet.getAttribute("port-group") === "left") {
// that.message.error("只能从输出链接桩创建连接");
return false;
}
// 只能连接到输入链接桩
if (!targetMagnet ||
targetMagnet.getAttribute("port-group") === "right") {
// that.message.error("只能连接到输入链接桩");
return false;
}
return !!targetMagnet;
},
},
highlighting: {
magnetAdsorbed: {
name: "stroke",
args: {
attrs: {
fill: "#5F95FF",
stroke: "#5F95FF",
},
},
},
},
resizing: true,
rotating: true,
selecting: {
enabled: true,
rubberband: true,
showNodeSelectionBox: true,
},
snapline: true,
keyboard: true,
clipboard: true,
});
this.stencil = new Addon.Stencil({
target: this.graph,
stencilGraphWidth: 200,
stencilGraphHeight: 180,
collapsable: true,
groups: [
{
title: "数据处理",
name: "group1",
},
{
title: "输入输出",
name: "group2",
},
],
layoutOptions: {
columns: 2,
columnWidth: 80,
rowHeight: 55,
},
validateNode: /**
* @param {?} currentnode
* @return {?}
*/
function (currentnode) {
/** @type {?} */
var nodes = that.graph.getNodes();
if (nodes.length > 0) {
for (var i = 0; i < nodes.length; i++) {
/** @type {?} */
var node = nodes[i];
if (currentnode["label"] === "输出" && node["label"] === "输出") {
return false;
}
}
}
return true;
},
getDropNode: /**
* @param {?} node
* @return {?}
*/
function (node) {
/** @type {?} */
var size = node.size();
if (node["label"] === "输入") {
that.getModal(node["label"]);
}
if (node["label"] === "输出") {
r2.attr("body/fill", "#ccc");
}
return node.clone().size(size.width * 1.1, size.height * 1.1);
},
});
(/** @type {?} */ (document.getElementById("stencil"))).appendChild(this.stencil.container);
// #region 初始化图形
// 常规左右两个桩
/** @type {?} */
var ports = {
groups: {
right: {
position: "right",
attrs: {
circle: {
r: 4,
magnet: true,
stroke: "#5F95FF",
strokeWidth: 1,
fill: "#fff",
style: {
visibility: "hidden",
},
},
},
},
left: {
position: "left",
attrs: {
circle: {
r: 4,
magnet: true,
stroke: "#5F95FF",
strokeWidth: 1,
fill: "#fff",
style: {
visibility: "hidden",
},
},
},
},
},
items: [
{
id: "port1",
group: "left",
},
{
id: "port2",
group: "right",
},
],
};
// 输入只有左侧一个桩
/** @type {?} */
var ports2 = {
groups: {
left: {
position: "left",
attrs: {
circle: {
r: 4,
magnet: true,
stroke: "#5F95FF",
strokeWidth: 1,
fill: "#fff",
style: {
visibility: "hidden",
},
},
},
},
},
items: [
{
id: "port1",
group: "left",
},
],
};
// 输出只有右侧一个桩
/** @type {?} */
var ports3 = {
groups: {
right: {
position: "right",
attrs: {
circle: {
r: 4,
magnet: true,
stroke: "#5F95FF",
strokeWidth: 1,
fill: "#fff",
style: {
visibility: "hidden",
},
},
},
},
},
items: [
{
id: "port2",
group: "right",
},
],
};
/** @type {?} */
var r1 = this.graph.createNode({
shape: "custom-rect",
id: "in",
label: "输入",
ports: tslib_1.__assign({}, ports3),
data: {
in: 0,
out: 3,
},
});
/** @type {?} */
var r2 = this.graph.createNode({
shape: "custom-rect",
id: "out",
label: "输出",
ports: tslib_1.__assign({}, ports2),
data: {
in: 2,
out: 2,
},
});
/** @type {?} */
var nodeArr = [];
this.menuList.forEach((/**
* @param {?} element
* @param {?} i
* @return {?}
*/
function (element, i) {
nodeArr.push(_this.graph.createNode({
shape: "custom-rect",
label: element.title,
ports: tslib_1.__assign({}, ports),
data: element.data,
}));
}));
this.stencil.load([r1, r2], "group1");
this.stencil.load(tslib_1.__spread(nodeArr), "group2");
};
/**
* @return {?}
*/
DataFlowComponent.prototype.graphEvent = /**
* @return {?}
*/
function () {
var _this = this;
// delete
this.graph.bindKey("backspace", (/**
* @return {?}
*/
function () {
/** @type {?} */
var cells = _this.graph.getSelectedCells();
if (cells.length) {
_this.graph.removeCells(cells);
}
}));
// 控制连接桩显示/隐藏
/** @type {?} */
var showPorts = (/**
* @param {?} ports
* @param {?} show
* @return {?}
*/
function (ports, show) {
for (var i = 0, len = ports.length; i < len; i = i + 1) {
ports[i].style.visibility = show ? "visible" : "hidden";
}
});
this.graph.on("node:mouseenter", (/**
* @return {?}
*/
function () {
/** @type {?} */
var container = (/** @type {?} */ (document.getElementById("graph-container")));
/** @type {?} */
var ports = (/** @type {?} */ (container.querySelectorAll(".x6-port-body")));
showPorts(ports, true);
}));
this.graph.on("node:mouseleave", (/**
* @return {?}
*/
function () {
/** @type {?} */
var container = (/** @type {?} */ (document.getElementById("graph-container")));
/** @type {?} */
var ports = (/** @type {?} */ (container.querySelectorAll(".x6-port-body")));
showPorts(ports, false);
}));
// this.graph.on(
// "edge:connected",
// ({ isNew, currentMagnet, currentCell }) => {}
// );
// this.graph.on("edge:added", ({ cell, index, options }) => {});
// this.graph.on(
// "edge:change:*",
// (args: {
// key: string; // 通过 key 来确定改变项
// current: any; // 当前值,类型根据 key 指代的类型确定
// previous: any; // 改变之前的值,类型根据 key 指代的类型确定
// options: any; // 透传的 options
// }) => {
// console.log("key:", args.key);
// }
// );
// this.graph.on("edge:changed", ({ edge, options }) => {});
this.graph.on("node:click", (/**
* @param {?} __0
* @return {?}
*/
function (_a) {
var cell = _a.cell, view = _a.view;
/** @type {?} */
var node = view.cell;
console.log(node.label);
if (node.label === "输入") {
_this.getModal(node.label);
}
else {
_this.getDrawer(node.label);
}
}));
};
/**
* @return {?}
*/
DataFlowComponent.prototype.getHistoryGrahp = /**
* @return {?}
*/
function () {
/** @type {?} */
var json = localStorage.getItem("graphJSON");
if (json) {
this.graph.fromJSON(JSON.parse(json));
}
};
/**
* @param {?} label
* @return {?}
*/
DataFlowComponent.prototype.getModal = /**
* @param {?} label
* @return {?}
*/
function (label) {
this.modalEvent.emit(label);
};
/**
* @param {?} label
* @return {?}
*/
DataFlowComponent.prototype.getDrawer = /**
* @param {?} label
* @return {?}
*/
function (label) {
this.drawerEvent.emit(label);
};
/**
* @return {?}
*/
DataFlowComponent.prototype.graphShape = /**
* @return {?}
*/
function () {
Graph.registerNode("custom-rect", {
inherit: "rect",
width: 66,
height: 30,
attrs: {
body: {
strokeWidth: 1,
stroke: "#eee",
fill: "#fff",
},
text: {
fontSize: 12,
color: "#262626",
},
},
}, true);
};
/**
* @return {?}
*/
DataFlowComponent.prototype.handleZoomIn = /**
* @return {?}
*/
function () {
this.graph.zoom(0.1);
console.log(this.graph.zoom());
};
/**
* @return {?}
*/
DataFlowComponent.prototype.handleZoomOut = /**
* @return {?}
*/
function () {
this.graph.zoom(-0.1);
};
/**
* @return {?}
*/
DataFlowComponent.prototype.handleUndo = /**
* @return {?}
*/
function () {
this.graph.history.undo();
};
/**
* @return {?}
*/
DataFlowComponent.prototype.handleRedo = /**
* @return {?}
*/
function () {
this.graph.history.redo();
};
/**
* @return {?}
*/
DataFlowComponent.prototype.handleReal = /**
* @return {?}
*/
function () {
this.graph.scale(1);
this.graph.centerContent();
};
/**
* @return {?}
*/
DataFlowComponent.prototype.handleFit = /**
* @return {?}
*/
function () {
this.graph.zoomToFit({ padding: 12 });
};
DataFlowComponent.decorators = [
{ type: Component, args: [{
selector: "data-flow",
template: "<div class=\"wrap\">\n <div class=\"main\">\n <div class=\"edit-container\">\n <div id=\"container\">\n <div id=\"stencil\"></div>\n <div class=\"graph-wrap\">\n <div class=\"toolbar-wrap\">\n <span (click)=\"handleZoomIn()\" class=\"toolbar-btn\">+</span>\n <span class=\"number\">{{ graph.zoom() | percent }}</span>\n <span (click)=\"handleZoomOut()\" class=\"toolbar-btn\">-</span>\n <span class=\"line\">|</span>\n <span\n (click)=\"handleUndo()\"\n [ngClass]=\"{ on: graph.history.canUndo() }\"\n class=\"toolbar-btn-off\"\n ><</span\n >\n <span\n (click)=\"handleRedo()\"\n [ngClass]=\"{ on: graph.history.canRedo() }\"\n class=\"toolbar-btn-off\"\n >></span\n >\n\n <span (click)=\"handleReal()\">\u5B9E\u9645\u5C3A\u5BF8</span>\n <span (click)=\"handleFit()\">\u9002\u5E94\u753B\u5E03</span>\n </div>\n <div id=\"graph-container\"></div>\n <div id=\"minimap\"></div>\n </div>\n </div>\n </div>\n <div class=\"board\"></div>\n </div>\n</div>\n",
styles: [":host #stencil{width:180px;height:100%;position:relative}:host .graph-wrap{width:calc(100% - 180px)}:host .graph-wrap .toolbar-wrap{height:42px;line-height:42px}:host .graph-wrap .toolbar-wrap span{color:#111;margin:0 10px}:host .graph-wrap .toolbar-wrap .number{display:inline-block;width:42px}:host .graph-wrap .toolbar-wrap .line{color:#eee}:host .graph-wrap .toolbar-wrap .toolbar-btn{cursor:pointer;font-weight:700;padding:0 10px}:host .graph-wrap .toolbar-wrap .toolbar-btn-off{font-weight:700;padding:0 10px;cursor:default;color:#eee}:host .graph-wrap .toolbar-wrap .on{cursor:pointer;color:#111}:host .graph-wrap #graph-container{width:100%;height:100%}:host .graph-wrap #minimap{position:absolute;right:1rem;top:1rem;background-color:#bc8f8f}:host #container{display:flex;height:500px}:host ::ng-deep .x6-widget-stencil-title{display:none}:host ::ng-deep .x6-widget-stencil.collapsable>.x6-widget-stencil-content{top:0}"]
}] }
];
/** @nocollapse */
DataFlowComponent.ctorParameters = function () { return [
{ type: NzMessageService }
]; };
DataFlowComponent.propDecorators = {
menuList: [{ type: Input }],
drawerEvent: [{ type: Output }],
modalEvent: [{ type: Output }]
};
return DataFlowComponent;
}());
export { DataFlowComponent };
if (false) {
/** @type {?} */
DataFlowComponent.prototype.menuList;
/** @type {?} */
DataFlowComponent.prototype.drawerEvent;
/** @type {?} */
DataFlowComponent.prototype.modalEvent;
/** @type {?} */
DataFlowComponent.prototype.data;
/** @type {?} */
DataFlowComponent.prototype.title;
/** @type {?} */
DataFlowComponent.prototype.graph;
/** @type {?} */
DataFlowComponent.prototype.stencil;
/**
* @type {?}
* @private
*/
DataFlowComponent.prototype.message;
}
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZGF0YS1mbG93LmNvbXBvbmVudC5qcyIsInNvdXJjZVJvb3QiOiJuZzovL0BrcmUtZm9ybS9hYmMvc3JjL2xpYi9kYXRhLWZsb3cvIiwic291cmNlcyI6WyJkYXRhLWZsb3cuY29tcG9uZW50LnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7Ozs7O0FBQUEsT0FBTyxFQUNMLFNBQVMsRUFJVCxLQUFLLEVBQ0wsTUFBTSxFQUNOLFlBQVksR0FDYixNQUFNLGVBQWUsQ0FBQztBQUN2QixPQUFPLEVBQUUsS0FBSyxFQUFFLEtBQUssRUFBRSxLQUFLLEVBQVEsTUFBTSxVQUFVLENBQUM7QUFFckQsT0FBTyxFQUFFLGdCQUFnQixFQUFFLE1BQU0sdUJBQXVCLENBQUM7QUFFekQ7SUF3Q0UsMkJBQW9CLE9BQXlCO1FBQXpCLFlBQU8sR0FBUCxPQUFPLENBQWtCO1FBakNuQyxnQkFBVyxHQUFHLElBQUksWUFBWSxFQUFPLENBQUM7UUFDdEMsZUFBVSxHQUFHLElBQUksWUFBWSxFQUFPLENBQUM7UUFDL0MsU0FBSSxHQUFHOztZQUVMLEtBQUssRUFBRTtnQkFDTDtvQkFDRSxFQUFFLEVBQUUsT0FBTzs7b0JBQ1gsQ0FBQyxFQUFFLEVBQUU7O29CQUNMLENBQUMsRUFBRSxFQUFFOztvQkFDTCxLQUFLLEVBQUUsRUFBRTs7b0JBQ1QsTUFBTSxFQUFFLEVBQUU7O29CQUNWLEtBQUssRUFBRSxPQUFPO2lCQUNmO2dCQUNEO29CQUNFLEVBQUUsRUFBRSxPQUFPOztvQkFDWCxDQUFDLEVBQUUsR0FBRzs7b0JBQ04sQ0FBQyxFQUFFLEdBQUc7O29CQUNOLEtBQUssRUFBRSxFQUFFOztvQkFDVCxNQUFNLEVBQUUsRUFBRTs7b0JBQ1YsS0FBSyxFQUFFLE9BQU87aUJBQ2Y7YUFDRjs7WUFFRCxLQUFLLEVBQUU7Z0JBQ0w7b0JBQ0UsTUFBTSxFQUFFLE9BQU87O29CQUNmLE1BQU0sRUFBRSxPQUFPO2lCQUNoQjthQUNGO1NBQ0YsQ0FBQztRQUNGLFVBQUssR0FBRyxRQUFRLENBQUM7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LDR1Q0FBeUM7O2lCQUUxQzs7OztnQkFOUSxnQkFBZ0I7OzsyQkFRdEIsS0FBSzs4QkFDTCxNQUFNOzZCQUNOLE1BQU07O0lBZ2VULHdCQUFDO0NBQUEsQUF4ZUQsSUF3ZUM7U0FuZVksaUJBQWlCOzs7SUFDNUIscUNBQXNCOztJQUN0Qix3Q0FBZ0Q7O0lBQ2hELHVDQUErQzs7SUFDL0MsaUNBMkJFOztJQUNGLGtDQUFpQjs7SUFDakIsa0NBQWE7O0lBQ2Isb0NBQXVCOzs7OztJQUNYLG9DQUFpQyIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7XG4gIENvbXBvbmVudCxcbiAgT25Jbml0LFxuICBWaWV3Q2hpbGQsXG4gIFRlbXBsYXRlUmVmLFxuICBJbnB1dCxcbiAgT3V0cHV0LFxuICBFdmVudEVtaXR0ZXIsXG59IGZyb20gXCJAYW5ndWxhci9jb3JlXCI7XG5pbXBvcnQgeyBHcmFwaCwgU2hhcGUsIEFkZG9uLCBOb2RlIH0gZnJvbSBcIkBhbnR2L3g2XCI7XG5pbXBvcnQgeyBub2RlQ2VudGVyIH0gZnJvbSBcIkBhbnR2L3g2L2xpYi9yZWdpc3RyeS9ub2RlLWFuY2hvci9ub2RlLWNlbnRlclwiO1xuaW1wb3J0IHsgTnpNZXNzYWdlU2VydmljZSB9IGZyb20gXCJuZy16b3Jyby1hbnRkL21lc3NhZ2VcIjtcblxuQENvbXBvbmVudCh7XG4gIHNlbGVjdG9yOiBcImRhdGEtZmxvd1wiLFxuICB0ZW1wbGF0ZVVybDogXCIuL2RhdGEtZmxvdy5jb21wb25lbnQuaHRtbFwiLFxuICBzdHlsZVVybHM6IFtcIi4vZGF0YS1mbG93LmNvbXBvbmVudC5sZXNzXCJdLFxufSlcbmV4cG9ydCBjbGFzcyBEYXRhRmxvd0NvbXBvbmVudCBpbXBsZW1lbnRzIE9uSW5pdCB7XG4gIEBJbnB1dCgpIG1lbnVMaXN0OiBbXTtcbiAgQE91dHB1dCgpIGRyYXdlckV2ZW50ID0gbmV3IEV2ZW50RW1pdHRlcjxhbnk+KCk7XG4gIEBPdXRwdXQoKSBtb2RhbEV2ZW50ID0gbmV3IEV2ZW50RW1pdHRlcjxhbnk+KCk7XG4gIGRhdGEgPSB7XG4gICAgLy8g6IqC54K5XG4gICAgbm9kZXM6IFtcbiAgICAgIHtcbiAgICAgICAgaWQ6IFwibm9kZTFcIiwgLy8gU3RyaW5n77yM5Y+v6YCJ77yM6IqC54K555qE5ZSv5LiA5qCH6K+GXG4gICAgICAgIHg6IDQwLCAvLyBOdW1iZXLvvIzlv4XpgInvvIzoioLngrnkvY3nva7nmoQgeCDlgLxcbiAgICAgICAgeTogNDAsIC8vIE51bWJlcu+8jOW/hemAie+8jOiKgueCueS9jee9rueahCB5IOWAvFxuICAgICAgICB3aWR0aDogODAsIC8vIE51bWJlcu+8jOWPr+mAie+8jOiKgueCueWkp+Wwj+eahCB3aWR0aCDlgLxcbiAgICAgICAgaGVpZ2h0OiA0MCwgLy8gTnVtYmVy77yM5Y+v6YCJ77yM6IqC54K55aSn5bCP55qEIGhlaWdodCDlgLxcbiAgICAgICAgbGFiZWw6IFwiaGVsbG9cIiwgLy8gU3RyaW5n77yM6IqC54K55qCH562+XG4gICAgICB9LFxuICAgICAge1xuICAgICAgICBpZDogXCJub2RlMlwiLCAvLyBTdHJpbmfvvIzoioLngrnnmoTllK/kuIDmoIfor4ZcbiAgICAgICAgeDogMTYwLCAvLyBOdW1iZXLvvIzlv4XpgInvvIzoioLngrnkvY3nva7nmoQgeCDlgLxcbiAgICAgICAgeTogMTgwLCAvLyBOdW1iZXLvvIzlv4XpgInvvIzoioLngrnkvY3nva7nmoQgeSDlgLxcbiAgICAgICAgd2lkdGg6IDgwLCAvLyBOdW1iZXLvvIzlj6/pgInvvIzoioLngrnlpKflsI/nmoQgd2lkdGgg5YC8XG4gICAgICAgIGhlaWdodDogNDAsIC8vIE51bWJlcu+8jOWPr+mAie+8jOiKgueCueWkp+Wwj+eahCBoZWlnaHQg5YC8XG4gICAgICAgIGxhYmVsOiBcIndvcmxkXCIsIC8vIFN0cmluZ++8jOiKgueCueagh+etvlxuICAgICAgfSxcbiAgICBdLFxuICAgIC8vIOi+uVxuICAgIGVkZ2VzOiBbXG4gICAgICB7XG4gICAgICAgIHNvdXJjZTogXCJub2RlMVwiLCAvLyBTdHJpbmfvvIzlv4XpobvvvIzotbflp4voioLngrkgaWRcbiAgICAgICAgdGFyZ2V0OiBcIm5vZGUyXCIsIC8vIFN0cmluZ++8jOW/hemhu++8jOebruagh+iKgueCuSBpZFxuICAgICAgfSxcbiAgICBdLFxuICB9O1xuICB0aXRsZSA9IFwibXktYXBwXCI7XG4gIGdyYXBoOiBHcmFwaDtcbiAgc3RlbmNpbDogQWRkb24uU3RlbmNpbDtcbiAgY29uc3RydWN0b3IocHJpdmF0ZSBtZXNzYWdlOiBOek1lc3NhZ2VTZXJ2aWNlKSB7fVxuXG4gIG5nT25Jbml0KCkge1xuICAgIHRoaXMuZ3JhcGhTaGFwZSgpO1xuICAgIHRoaXMuZ3JhaHBJbml0KCk7XG4gICAgdGhpcy5nZXRIaXN0b3J5R3JhaHAoKTtcbiAgICB0aGlzLmdyYXBoRXZlbnQoKTtcbiAgICAvLyBjb25zb2xlLmxvZyhcIuiKgueCuVwiLCB0aGlzLmdyYXBoLmdldE5vZGVzKCkpO1xuICAgIC8vIGNvbnNvbGUubG9nKFwiY2VsbC0tLS0tXCIpO1xuICAgIC8vIGNvbnNvbGUubG9nKFwi6IqC54K55ZKM6L65XCIsIHRoaXMuZ3JhcGguZ2V0Q2VsbHMoKSk7XG4gICAgLy8gY29uc29sZS5sb2coXCLmoLnoioLngrnvvIzljbPmsqHmnInovpPlhaXovrnnmoToioLngrlcIiwgdGhpcy5ncmFwaC5nZXRSb290Tm9kZXMoKSk7XG4gICAgLy8gY29uc29sZS5sb2coXCLlj7blrZDoioLngrnvvIzljbPmsqHmnInovpPlh7rovrnnmoToioLngrlcIiwgdGhpcy5ncmFwaC5nZXRMZWFmTm9kZXMoKSk7XG4gICAgLy8gY29uc29sZS5sb2coXCLmlbDph49cIiwgdGhpcy5ncmFwaC5nZXRDZWxsQ291bnQoKSk7XG4gICAgLy8gY29uc29sZS5sb2codGhpcy5ncmFwaCk7XG4gICAgLy8gY29uc29sZS5sb2codGhpcy5zdGVuY2lsLmdyYXBocy5ncm91cDEuZ2V0Tm9kZXMoKSk7XG4gICAgbGV0IG5vZGVzID0gdGhpcy5ncmFwaC5nZXRMZWFmTm9kZXMoKTtcbiAgICBmb3IgKGxldCBpID0gMDsgaSA8IG5vZGVzLmxlbmd0aDsgaSsrKSB7XG4gICAgICBsZXQgbm9kZTogYW55ID0gbm9kZXNbaV07XG4gICAgICBpZiAobm9kZVtcImxhYmVsXCJdICE9PSBcIui+k+WHulwiKSB7XG4gICAgICAgIHRoaXMubWVzc2FnZS5lcnJvcihcIueVjOmdouW/hemhu+WMheWQq+i+k+WHulwiKTtcbiAgICAgICAgYnJlYWs7XG4gICAgICB9XG4gICAgfVxuICB9XG5cbiAgZ3JhaHBJbml0KCkge1xuICAgIGNvbnN0IHRoYXQgPSB0aGlzO1xuICAgIC8vICNyZWdpb24g5Yid5aeL5YyW55S75biDXG4gICAgdGhpcy5ncmFwaCA9IG5ldyBHcmFwaCh7XG4gICAgICBjb250YWluZXI6IGRvY3VtZW50LmdldEVsZW1lbnRCeUlkKFwiZ3JhcGgtY29udGFpbmVyXCIpISxcbiAgICAgIGdyaWQ6IHRydWUsXG4gICAgICBoaXN0b3J5OiB0cnVlLFxuICAgICAgbWluaW1hcDoge1xuICAgICAgICBlbmFibGVkOiB0cnVlLFxuICAgICAgICBjb250YWluZXI6IGRvY3VtZW50LmdldEVsZW1lbnRCeUlkKFwibWluaW1hcFwiKSEsXG4gICAgICAgIHdpZHRoOiAxOTgsXG4gICAgICAgIGhlaWdodDogMTk4LFxuICAgICAgICBwYWRkaW5nOiAxMCxcbiAgICAgIH0sXG4gICAgICBtb3VzZXdoZWVsOiB7XG4gICAgICAgIGVuYWJsZWQ6IHRydWUsXG4gICAgICAgIHpvb21BdE1vdXNlUG9zaXRpb246IHRydWUsXG4gICAgICAgIG1vZGlmaWVyczogXCJjdHJsXCIsXG4gICAgICAgIG1pblNjYWxlOiAwLjUsXG4gICAgICAgIG1heFNjYWxlOiAzLFxuICAgICAgfSxcbiAgICAgIGNvbm5lY3Rpbmc6IHtcbiAgICAgICAgcm91dGVyOiBcIm1hbmhhdHRhblwiLFxuICAgICAgICBjb25uZWN0b3I6IHtcbiAgICAgICAgICBuYW1lOiBcInJvdW5kZWRcIixcbiAgICAgICAgICBhcmdzOiB7XG4gICAgICAgICAgICByYWRpdXM6IDgsXG4gICAgICAgICAgfSxcbiAgICAgICAgfSxcbiAgICAgICAgYW5jaG9yOiBcImNlbnRlclwiLFxuICAgICAgICBjb25uZWN0aW9uUG9pbnQ6IFwiYW5jaG9yXCIsXG4gICAgICAgIGFsbG93Qmxhbms6IGZhbHNlLFxuICAgICAgICBzbmFwOiB7XG4gICAgICAgICAgcmFkaXVzOiAyMCxcbiAgICAgICAgfSxcbiAgICAgICAgY3JlYXRlRWRnZSgpIHtcbiAgICAgICAgICByZXR1cm4gbmV3IFNoYXBlLkVkZ2Uoe1xuICAgICAgICAgICAgYXR0cnM6IHtcbiAgICAgICAgICAgICAgbGluZToge1xuICAgICAgICAgICAgICAgIHN0cm9rZTogXCIjQTJCMUMzXCIsXG4gICAgICAgICAgICAgICAgc3Ryb2tlV2lkdGg6IDIsXG4gICAgICAgICAgICAgICAgdGFyZ2V0TWFya2VyOiB7XG4gICAgICAgICAgICAgICAgICBuYW1lOiBcImJsb2NrXCIsXG4gICAgICAgICAgICAgICAgICB3aWR0aDogMTIsXG4gICAgICAgICAgICAgICAgICBoZWlnaHQ6IDgsXG4gICAgICAgICAgICAgICAgfSxcbiAgICAgICAgICAgICAgfSxcbiAgICAgICAgICAgIH0sXG4gICAgICAgICAgICB6SW5kZXg6IDAsXG4gICAgICAgICAgfSk7XG4gICAgICAgIH0sXG4gICAgICAgIC8vIOWcqOenu+WKqOi+ueeahOaXtuWAmeWIpOaWrei/nuaOpeaYr+WQpuacieaViFxuICAgICAgICB2YWxpZGF0ZUNvbm5lY3Rpb24oe1xuICAgICAgICAgIHNvdXJjZVZpZXcsXG4gICAgICAgICAgdGFyZ2V0VmlldyxcbiAgICAgICAgICBzb3VyY2VNYWduZXQsXG4gICAgICAgICAgdGFyZ2V0TWFnbmV0LFxuICAgICAgICAgIHNvdXJjZUNlbGwsXG4gICAgICAgICAgdGFyZ2V0Q2VsbCxcbiAgICAgICAgfSkge1xuICAgICAgICAgIGlmICh0YXJnZXRNYWduZXQgJiYgdGFyZ2V0Q2VsbCkge1xuICAgICAgICAgICAgY29uc3QgaW5jb21pbmdFZGdlcyA9XG4gICAgICAgICAgICAgIHRoYXQuZ3JhcGghLmdldEluY29taW5nRWRnZXModGFyZ2V0Q2VsbCkgfHwgW107XG4gICAgICAgICAgICBpZiAoaW5jb21pbmdFZGdlcy5sZW5ndGggPj0gdGFyZ2V0VmlldyEuY2VsbC5nZXREYXRhKCkub3V0KSB7XG4gICAgICAgICAgICAgIHRoYXQubWVzc2FnZS5lcnJvcihcIui2heWHum91dOaVsOmHj1wiKTtcbiAgICAgICAgICAgICAgcmV0dXJuIGZhbHNlO1xuICAgICAgICAgICAgfVxuICAgICAgICAgIH1cblxuICAgICAgICAgIC8vIOS4jeWFgeiuuOi/nuaOpeWIsOiHquW3sVxuICAgICAgICAgIGlmIChzb3VyY2VWaWV3ID09PSB0YXJnZXRWaWV3KSB7XG4gICAgICAgICAgICAvLyB0aGF0Lm1lc3NhZ2UuZXJyb3IoXCLkuI3lhYHorrjov57mjqXliLDoh6rlt7FcIik7XG4gICAgICAgICAgICByZXR1cm4gZmFsc2U7XG4gICAgICAgICAgfVxuXG4gICAgICAgICAgLy8g5Y+q6IO95LuO6L6T5Ye66ZO+5o6l5qGp5Yib5bu66L+e5o6lXG4gICAgICAgICAgaWYgKFxuICAgICAgICAgICAgIXNvdXJjZU1hZ25ldCB8fFxuICAgICAgICAgICAgc291cmNlTWFnbmV0LmdldEF0dHJpYnV0ZShcInBvcnQtZ3JvdXBcIikgPT09IFwibGVmdFwiXG4gICAgICAgICAgKSB7XG4gICAgICAgICAgICAvLyB0aGF0Lm1lc3NhZ2UuZXJyb3IoXCLlj6rog73ku47ovpPlh7rpk77mjqXmoanliJvlu7rov57mjqVcIik7XG4gICAgICAgICAgICByZXR1cm4gZmFsc2U7XG4gICAgICAgICAgfVxuXG4gICAgICAgICAgLy8g5Y+q6IO96L+e5o6l5Yiw6L6T5YWl6ZO+5o6l5qGpXG4gICAgICAgICAgaWYgKFxuICAgICAgICAgICAgIXRhcmdldE1hZ25ldCB8fFxuICAgICAgICAgICAgdGFyZ2V0TWFnbmV0LmdldEF0dHJpYnV0ZShcInBvcnQtZ3JvdXBcIikgPT09IFwicmlnaHRcIlxuICAgICAgICAgICkge1xuICAgICAgICAgICAgLy8gdGhhdC5tZXNzYWdlLmVycm9yKFwi5Y+q6IO96L+e5o6l5Yiw6L6T5YWl6ZO+5o6l5qGpXCIpO1xuICAgICAgICAgICAgcmV0dXJuIGZhbHNlO1xuICAgICAgICAgIH1cbiAgICAgICAgICByZXR1cm4gISF0YXJnZXRNYWduZXQ7XG4gICAgICAgIH0sXG4gICAgICB9LFxuICAgICAgaGlnaGxpZ2h0aW5nOiB7XG4gICAgICAgIG1hZ25ldEFkc29yYmVkOiB7XG4gICAgICAgICAgbmFtZTogXCJzdHJva2VcIixcbiAgICAgICAgICBhcmdzOiB7XG4gICAgICAgICAgICBhdHRyczoge1xuICAgICAgICAgICAgICBmaWxsOiBcIiM1Rjk1RkZcIixcbiAgICAgICAgICAgICAgc3Ryb2tlOiBcIiM1Rjk1RkZcIixcbiAgICAgICAgICAgIH0sXG4gICAgICAgICAgfSxcbiAgICAgICAgfSxcbiAgICAgIH0sXG4gICAgICByZXNpemluZzogdHJ1ZSxcbiAgICAgIHJvdGF0aW5nOiB0cnVlLFxuICAgICAgc2VsZWN0aW5nOiB7XG4gICAgICAgIGVuYWJsZWQ6IHRydWUsXG4gICAgICAgIHJ1YmJlcmJhbmQ6IHRydWUsXG4gICAgICAgIHNob3dOb2RlU2VsZWN0aW9uQm94OiB0cnVlLFxuICAgICAgfSxcbiAgICAgIHNuYXBsaW5lOiB0cnVlLFxuICAgICAga2V5Ym9hcmQ6IHRydWUsXG4gICAgICBjbGlwYm9hcmQ6IHRydWUsXG4gICAgfSk7XG5cbiAgICB0aGlzLnN0ZW5jaWwgPSBuZXcgQWRkb24uU3RlbmNpbCh7XG4gICAgICB0YXJnZXQ6IHRoaXMuZ3JhcGgsXG4gICAgICBzdGVuY2lsR3JhcGhXaWR0aDogMjAwLFxuICAgICAgc3RlbmNpbEdyYXBoSGVpZ2h0OiAxODAsXG4gICAgICBjb2xsYXBzYWJsZTogdHJ1ZSxcbiAgICAgIGdyb3VwczogW1xuICAgICAgICB7XG4gICAgICAgICAgdGl0bGU6IFwi5pWw5o2u5aSE55CGXCIsXG4gICAgICAgICAgbmFtZTogXCJncm91cDFcIixcbiAgICAgICAgfSxcbiAgICAgICAge1xuICAgICAgICAgIHRpdGxlOiBcIui+k+WFpei+k+WHulwiLFxuICAgICAgICAgIG5hbWU6IFwiZ3JvdXAyXCIsXG4gICAgICAgIH0sXG4gICAgICBdLFxuICAgICAgbGF5b3V0T3B0aW9uczoge1xuICAgICAgICBjb2x1bW5zOiAyLFxuICAgICAgICBjb2x1bW5XaWR0aDogODAsXG4gICAgICAgIHJvd0hlaWdodDogNTUsXG4gICAgICB9LFxuICAgICAgdmFsaWRhdGVOb2RlKGN1cnJlbnRub2RlOiBhbnkpIHtcbiAgICAgICAgY29uc3Qgbm9kZXMgPSB0aGF0LmdyYXBoLmdldE5vZGVzKCk7XG4gICAgICAgIGlmIChub2Rlcy5sZW5ndGggPiAwKSB7XG4gICAgICAgICAgZm9yIChsZXQgaSA9IDA7IGkgPCBub2Rlcy5sZW5ndGg7IGkrKykge1xuICAgICAgICAgICAgbGV0IG5vZGU6IGFueSA9IG5vZGVzW2ldO1xuICAgICAgICAgICAgaWYgKGN1cnJlbnRub2RlW1wibGFiZWxcIl0gPT09IFwi6L6T5Ye6XCIgJiYgbm9kZVtcImxhYmVsXCJdID09PSBcIui+k+WHulwiKSB7XG4gICAgICAgICAgICAgIHJldHVybiBmYWxzZTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICB9XG4gICAgICAgIH1cbiAgICAgICAgcmV0dXJuIHRydWU7XG4gICAgICB9LFxuICAgICAgZ2V0RHJvcE5vZGUobm9kZTogYW55KSB7XG4gICAgICAgIGNvbnN0IHNpemUgPSBub2RlLnNpemUoKTtcbiAgICAgICAgaWYgKG5vZGVbXCJsYWJlbFwiXSA9PT0gXCLovpPlhaVcIikge1xuICAgICAgICAgIHRoYXQuZ2V0TW9kYWwobm9kZVtcImxhYmVsXCJdKTtcbiAgICAgICAgfVxuICAgICAgICBpZiAobm9kZVtcImxhYmVsXCJdID09PSBcIui+k+WHulwiKSB7XG4gICAgICAgICAgcjIuYXR0cihcImJvZHkvZmlsbFwiLCBcIiNjY2NcIik7XG4gICAgICAgIH1cblxuICAgICAgICByZXR1cm4gbm9kZS5jbG9uZSgpLnNpemUoc2l6ZS53aWR0aCAqIDEuMSwgc2l6ZS5oZWlnaHQgKiAxLjEpO1xuICAgICAgfSxcbiAgICB9KTtcbiAgICBkb2N1bWVudC5nZXRFbGVtZW50QnlJZChcInN0ZW5jaWxcIikhLmFwcGVuZENoaWxkKHRoaXMuc3RlbmNpbC5jb250YWluZXIpO1xuXG4gICAgLy8gI3JlZ2lvbiDliJ3lp4vljJblm77lvaJcbiAgICAvLyDluLjop4Tlt6blj7PkuKTkuKrmoalcbiAgICBjb25zdCBwb3J0cyA9IHtcbiAgICAgIGdyb3Vwczoge1xuICAgICAgICByaWdodDoge1xuICAgICAgICAgIHBvc2l0aW9uOiBcInJpZ2h0XCIsXG4gICAgICAgICAgYXR0cnM6IHtcbiAgICAgICAgICAgIGNpcmNsZToge1xuICAgICAgICAgICAgICByOiA0LFxuICAgICAgICAgICAgICBtYWduZXQ6IHRydWUsXG4gICAgICAgICAgICAgIHN0cm9rZTogXCIjNUY5NUZGXCIsXG4gICAgICAgICAgICAgIHN0cm9rZVdpZHRoOiAxLFxuICAgICAgICAgICAgICBmaWxsOiBcIiNmZmZcIixcbiAgICAgICAgICAgICAgc3R5bGU6IHtcbiAgICAgICAgICAgICAgICB2aXNpYmlsaXR5OiBcImhpZGRlblwiLFxuICAgICAgICAgICAgICB9LFxuICAgICAgICAgICAgfSxcbiAgICAgICAgICB9LFxuICAgICAgICB9LFxuICAgICAgICBsZWZ0OiB7XG4gICAgICAgICAgcG9zaXRpb246IFwibGVmdFwiLFxuICAgICAgICAgIGF0dHJzOiB7XG4gICAgICAgICAgICBjaXJjbGU6IHtcbiAgICAgICAgICAgICAgcjogNCxcbiAgICAgICAgICAgICAgbWFnbmV0OiB0cnVlLFxuICAgICAgICAgICAgICBzdHJva2U6IFwiIzVGOTVGRlwiLFxuICAgICAgICAgICAgICBzdHJva2VXaWR0aDogMSxcbiAgICAgICAgICAgICAgZmlsbDogXCIjZmZmXCIsXG4gICAgICAgICAgICAgIHN0eWxlOiB7XG4gICAgICAgICAgICAgICAgdmlzaWJpbGl0eTogXCJoaWRkZW5cIixcbiAgICAgICAgICAgICAgfSxcbiAgICAgICAgICAgIH0sXG4gICAgICAgICAgfSxcbiAgICAgICAgfSxcbiAgICAgIH0sXG4gICAgICBpdGVtczogW1xuICAgICAgICB7XG4gICAgICAgICAgaWQ6IFwicG9ydDFcIixcbiAgICAgICAgICBncm91cDogXCJsZWZ0XCIsXG4gICAgICAgIH0sXG4gICAgICAgIHtcbiAgICAgICAgICBpZDogXCJwb3J0MlwiLFxuICAgICAgICAgIGdyb3VwOiBcInJpZ2h0XCIsXG4gICAgICAgIH0sXG4gICAgICBdLFxuICAgIH07XG5cbiAgICAvLyDovpPlhaXlj6rmnInlt6bkvqfkuIDkuKrmoalcbiAgICBjb25zdCBwb3J0czIgPSB7XG4gICAgICBncm91cHM6IHtcbiAgICAgICAgbGVmdDoge1xuICAgICAgICAgIHBvc2l0aW9uOiBcImxlZnRcIixcbiAgICAgICAgICBhdHRyczoge1xuICAgICAgICAgICAgY2lyY2xlOiB7XG4gICAgICAgICAgICAgIHI6IDQsXG4gICAgICAgICAgICAgIG1hZ25ldDogdHJ1ZSxcbiAgICAgICAgICAgICAgc3Ryb2tlOiBcIiM1Rjk1RkZcIixcbiAgICAgICAgICAgICAgc3Ryb2tlV2lkdGg6IDEsXG4gICAgICAgICAgICAgIGZpbGw6IFwiI2ZmZlwiLFxuICAgICAgICAgICAgICBzdHlsZToge1xuICAgICAgICAgICAgICAgIHZpc2liaWxpdHk6IFwiaGlkZGVuXCIsXG4gICAgICAgICAgICAgIH0sXG4gICAgICAgICAgICB9LFxuICAgICAgICAgIH0sXG4gICAgICAgIH0sXG4gICAgICB9LFxuICAgICAgaXRlbXM6IFtcbiAgICAgICAge1xuICAgICAgICAgIGlkOiBcInBvcnQxXCIsXG4gICAgICAgICAgZ3JvdXA6IFwibGVmdFwiLFxuICAgICAgICB9LFxuICAgICAgXSxcbiAgICB9O1xuXG4gICAgLy8g6L6T5Ye65Y+q5pyJ5Y+z5L6n5LiA5Liq5qGpXG4gICAgY29uc3QgcG9ydHMzID0ge1xuICAgICAgZ3JvdXBzOiB7XG4gICAgICAgIHJpZ2h0OiB7XG4gICAgICAgICAgcG9zaXRpb246IFwicmlnaHRcIixcbiAgICAgICAgICBhdHRyczoge1xuICAgICAgICAgICAgY2lyY2xlOiB7XG4gICAgICAgICAgICAgIHI6IDQsXG4gICAgICAgICAgICAgIG1hZ25ldDogdHJ1ZSxcbiAgICAgICAgICAgICAgc3Ryb2tlOiBcIiM1Rjk1RkZcIixcbiAgICAgICAgICAgICAgc3Ryb2tlV2lkdGg6IDEsXG4gICAgICAgICAgICAgIGZpbGw6IFwiI2ZmZlwiLFxuICAgICAgICAgICAgICBzdHlsZToge1xuICAgICAgICAgICAgICAgIHZpc2liaWxpdHk6IFwiaGlkZGVuXCIsXG4gICAgICAgICAgICAgIH0sXG4gICAgICAgICAgICB9LFxuICAgICAgICAgIH0sXG4gICAgICAgIH0sXG4gICAgICB9LFxuICAgICAgaXRlbXM6IFtcbiAgICAgICAge1xuICAgICAgICAgIGlkOiBcInBvcnQyXCIsXG4gICAgICAgICAgZ3JvdXA6IFwicmlnaHRcIixcbiAgICAgICAgfSxcbiAgICAgIF0sXG4gICAgfTtcblxuICAgIGNvbnN0IHIxID0gdGhpcy5ncmFwaC5jcmVhdGVOb2RlKHtcbiAgICAgIHNoYXBlOiBcImN1c3RvbS1yZWN0XCIsXG4gICAgICBpZDogXCJpblwiLFxuICAgICAgbGFiZWw6IFwi6L6T5YWlXCIsXG4gICAgICBwb3J0czogeyAuLi5wb3J0czMgfSxcbiAgICAgIGRhdGE6IHtcbiAgICAgICAgaW46IDAsXG4gICAgICAgIG91dDogMywgLy/lj6rog73lh7rljrsz5p2h57q/XG4gICAgICB9LFxuICAgIH0pO1xuICAgIGNvbnN0IHIyID0gdGhpcy5ncmFwaC5jcmVhdGVOb2RlKHtcbiAgICAgIHNoYXBlOiBcImN1c3RvbS1yZWN0XCIsXG4gICAgICBpZDogXCJvdXRcIixcbiAgICAgIGxhYmVsOiBcIui+k+WHulwiLFxuICAgICAgcG9ydHM6IHsgLi4ucG9ydHMyIH0sXG4gICAgICBkYXRhOiB7XG4gICAgICAgIGluOiAyLFxuICAgICAgICBvdXQ6IDIsXG4gICAgICB9LFxuICAgIH0pO1xuXG4gICAgY29uc3Qgbm9kZUFycjogYW55W10gPSBbXTtcbiAgICB0aGlzLm1lbnVMaXN0LmZvckVhY2goKGVsZW1lbnQ6IGFueSwgaSkgPT4ge1xuICAgICAgbm9kZUFyci5wdXNoKFxuICAgICAgICB0aGlzLmdyYXBoLmNyZWF0ZU5vZGUoe1xuICAgICAgICAgIHNoYXBlOiBcImN1c3RvbS1yZWN0XCIsXG4gICAgICAgICAgbGFiZWw6IGVsZW1lbnQudGl0bGUsXG4gICAgICAgICAgcG9ydHM6IHsgLi4ucG9ydHMgfSxcbiAgICAgICAgICBkYXRhOiBlbGVtZW50LmRhdGEsXG4gICAgICAgIH0pXG4gICAgICApO1xuICAgIH0pO1xuXG4gICAgdGhpcy5zdGVuY2lsLmxvYWQoW3IxLCByMl0sIFwiZ3JvdXAxXCIpO1xuICAgIHRoaXMuc3RlbmNpbC5sb2FkKFsuLi5ub2RlQXJyXSwgXCJncm91cDJcIik7XG4gIH1cblxuICBncmFwaEV2ZW50KCkge1xuICAgIC8vIGRlbGV0ZVxuICAgIHRoaXMuZ3JhcGguYmluZEtleShcImJhY2tzcGFjZVwiLCAoKSA9PiB7XG4gICAgICBjb25zdCBjZWxscyA9IHRoaXMuZ3JhcGguZ2V0U2VsZWN0ZWRDZWxscygpO1xuICAgICAgaWYgKGNlbGxzLmxlbmd0aCkge1xuICAgICAgICB0aGlzLmdyYXBoLnJlbW92ZUNlbGxzKGNlbGxzKTtcbiAgICAgIH1cbiAgICB9KTtcblxuICAgIC8vIOaOp+WItui/nuaOpeahqeaYvuekui/pmpDol49cbiAgICBjb25zdCBzaG93UG9ydHMgPSAocG9ydHM6IE5vZGVMaXN0T2Y8U1ZHRWxlbWVudD4sIHNob3c6IGJvb2xlYW4pID0+IHtcbiAgICAgIGZvciAobGV0IGkgPSAwLCBsZW4gPSBwb3J0cy5sZW5ndGg7IGkgPCBsZW47IGkgPSBpICsgMSkge1xuICAgICAgICBwb3J0c1tpXS5zdHlsZS52aXNpYmlsaXR5ID0gc2hvdyA/IFwidmlzaWJsZVwiIDogXCJoaWRkZW5cIjtcbiAgICAgIH1cbiAgICB9O1xuICAgIHRoaXMuZ3JhcGgub24oXCJub2RlOm1vdXNlZW50ZXJcIiwgKCkgPT4ge1xuICAgICAgY29uc3QgY29udGFpbmVyID0gZG9jdW1lbnQuZ2V0RWxlbWVudEJ5SWQoXCJncmFwaC1jb250YWluZXJcIikhO1xuICAgICAgY29uc3QgcG9ydHMgPSBjb250YWluZXIucXVlcnlTZWxlY3RvckFsbChcbiAgICAgICAgXCIueDYtcG9ydC1ib2R5XCJcbiAgICAgICkgYXMgTm9kZUxpc3RPZjxTVkdFbGVtZW50PjtcbiAgICAgIHNob3dQb3J0cyhwb3J0cywgdHJ1ZSk7XG4gICAgfSk7XG4gICAgdGhpcy5ncmFwaC5vbihcIm5vZGU6bW91c2VsZWF2ZVwiLCAoKSA9PiB7XG4gICAgICBjb25zdCBjb250YWluZXIgPSBkb2N1bWVudC5nZXRFbGVtZW50QnlJZChcImdyYXBoLWNvbnRhaW5lclwiKSE7XG4gICAgICBjb25zdCBwb3J0cyA9IGNvbnRhaW5lci5xdWVyeVNlbGVjdG9yQWxsKFxuICAgIC