UNPKG

ngx-diagrams

Version:

> Light Weight, Modular, Typed Diagram Engine for Angular

230 lines 27.8 kB
import { BaseEntity } from '../base.entity'; import { createEntityState, createValueState } from '../state/state'; import { coerceArray, isEmptyArray, unique } from '../utils'; import { LinkModel } from './link.model'; import { NodeModel } from './node.model'; export class DiagramModel extends BaseEntity { constructor(diagramEngine, id, logPrefix = '[Diagram]') { super(id, logPrefix); this.diagramEngine = diagramEngine; this.nodes$ = createEntityState([], this.entityPipe('nodes')); this.links$ = createEntityState([], this.entityPipe('links')); this.offsetX$ = createValueState(0, this.entityPipe('offsetX')); this.offsetY$ = createValueState(0, this.entityPipe('offsetY')); this.zoom$ = createValueState(100, this.entityPipe('zoom')); this.maxZoomOut$ = createValueState(null); this.maxZoomIn$ = createValueState(null); this.gridSize$ = createValueState(0); } // TODO: support the following events for links and nodes // removed, updated<positionChanged/dataChanged>, added getNodes() { return this.nodes$.value; } getNodesArray() { return this.nodes$.array(); } getNode(id) { return this.nodes$.get(id); } getLink(id) { return this.links$.get(id); } getLinks() { return this.links$.value; } getLinksArray() { return this.links$.array(); } getAllPorts(options = {}) { const result = new Map(); this.getNodes().forEach((node) => { const ports = options.filter ? node.getPortsArray().filter(options.filter) : node.getPortsArray(); ports.forEach((port) => result.set(port.id, port)); }); return result; } /** * Add a node to the diagram * @returns Inserted Node */ addNode(node) { this.nodes$.add(node).emit(); return node; } /** * Delete a node from the diagram */ deleteNode(nodeOrId) { const nodeId = typeof nodeOrId === 'string' ? nodeOrId : nodeOrId.id; const node = this.getNode(nodeId); for (const port of node.getPorts().values()) { for (const link of port.getLinks().values()) { this.deleteLink(link); } } this.nodes$.remove(nodeId).emit(); } /** * Get nodes as observable, use `.getValue()` for snapshot */ selectNodes() { return this.nodes$.value$; } /** * Add link * @returns Newly created link */ addLink(link) { this.links$.add(link).emit(); return link; } /** * Delete link */ deleteLink(linkOrId) { const linkId = typeof linkOrId === 'string' ? linkOrId : linkOrId.id; this.links$.remove(linkId).emit(); } reset() { this.nodes$.clear().emit(); this.links$.clear().emit(); } /** * Get links behaviour subject, use `.getValue()` for snapshot */ selectLinks() { return this.links$.value$; } // /** // * Serialize the diagram model to JSON // * @returns diagram model as a string // */ serialize() { const serializedNodes = this.nodes$.map((node) => node.serialize()); const serializedLinks = this.links$.map((link) => link.serialize()); return Object.assign(Object.assign({}, super.serialize()), { nodes: serializedNodes, links: serializedLinks }); } setMaxZoomOut(maxZoomOut) { this.maxZoomOut$.set(maxZoomOut).emit(); } setMaxZoomIn(maxZoomIn) { this.maxZoomIn$.set(maxZoomIn).emit(); } getMaxZoomOut() { return this.maxZoomOut$.value; } getMaxZoomIn() { return this.maxZoomIn$.value; } setOffset(x, y) { this.offsetX$.set(x).emit(); this.offsetY$.set(y).emit(); } setOffsetX(x) { this.offsetX$.set(x).emit(); } getOffsetX() { return this.offsetX$.value; } selectOffsetX() { return this.offsetX$.value$; } setOffsetY(y) { this.offsetY$.set(y).emit(); } getOffsetY() { return this.offsetY$.value; } selectOffsetY() { return this.offsetY$.value$; } setZoomLevel(z) { const maxZoomIn = this.getMaxZoomIn(); const maxZoomOut = this.getMaxZoomOut(); // check if zoom levels exceeded defined boundaries if ((maxZoomIn && z > maxZoomIn) || (maxZoomOut && z < maxZoomOut)) { return; } this.zoom$.set(z).emit(); } getZoomLevel() { return this.zoom$.value; } selectZoomLevel() { return this.zoom$.value$; } getDiagramEngine() { return this.diagramEngine; } clearSelection(ignore = null) { this.getSelectedItems().forEach((element) => { if ((ignore === null || ignore === void 0 ? void 0 : ignore.id) === element.id) { return; } element.setSelected(false); }); } getGridPosition({ x, y }) { const gridSize = this.gridSize$.value; if (gridSize === 0) { return { x, y }; } return { x: gridSize * Math.floor((x + gridSize / 2) / gridSize), y: gridSize * Math.floor((y + gridSize / 2) / gridSize) }; } getSelectedItems(...filters) { filters = coerceArray(filters); const items = []; const nodes = this.nodes$.array(); const links = this.links$.array(); const selectedNodes = () => nodes.flatMap((node) => node.getSelectedEntities()); const selectedPorts = () => nodes.flatMap((node) => node.getPortsArray().flatMap((port) => port.getSelectedEntities())); const selectedLinks = () => links.flatMap((link) => link.getSelectedEntities()); const selectedPoints = () => links.flatMap((link) => link.getPoints().flatMap((point) => point.getSelectedEntities())); if (isEmptyArray(filters)) { items.push(...selectedNodes(), ...selectedPorts(), ...selectedLinks(), ...selectedPoints()); } else { const byType = { node: selectedNodes, port: selectedPorts, link: selectedLinks, point: selectedPoints }; for (const type of filters) { items.push(...byType[type]()); } } return unique(items); } addAll(...models) { const links = []; const nodes = []; for (const model of models) { if (model instanceof LinkModel) { links.push(model); } else if (model instanceof NodeModel) { nodes.push(model); } } this.addLinks(links); this.addNodes(nodes); return models; } addLinks(links) { this.links$.addMany(links).emit(); } addNodes(nodes) { this.nodes$.addMany(nodes).emit(); } destroy() { super.destroy(); this.nodes$.destroy(); this.links$.destroy(); } } //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZGlhZ3JhbS5tb2RlbC5qcyIsInNvdXJjZVJvb3QiOiIuLi8uLi8uLi8uLi9saWJzL25neC1kaWFncmFtcy9zcmMvIiwic291cmNlcyI6WyJsaWIvbW9kZWxzL2RpYWdyYW0ubW9kZWwudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQ0EsT0FBTyxFQUFFLFVBQVUsRUFBa0IsTUFBTSxnQkFBZ0IsQ0FBQztBQUs1RCxPQUFPLEVBQUUsaUJBQWlCLEVBQUUsZ0JBQWdCLEVBQUUsTUFBTSxnQkFBZ0IsQ0FBQztBQUNyRSxPQUFPLEVBQUUsV0FBVyxFQUFNLFlBQVksRUFBRSxNQUFNLEVBQUUsTUFBTSxVQUFVLENBQUM7QUFHakUsT0FBTyxFQUFFLFNBQVMsRUFBRSxNQUFNLGNBQWMsQ0FBQztBQUN6QyxPQUFPLEVBQUUsU0FBUyxFQUFFLE1BQU0sY0FBYyxDQUFDO0FBR3pDLE1BQU0sT0FBTyxZQUFhLFNBQVEsVUFBVTtJQVUxQyxZQUFzQixhQUE0QixFQUFFLEVBQVcsRUFBRSxTQUFTLEdBQUcsV0FBVztRQUN0RixLQUFLLENBQUMsRUFBRSxFQUFFLFNBQVMsQ0FBQyxDQUFDO1FBREQsa0JBQWEsR0FBYixhQUFhLENBQWU7UUFUeEMsV0FBTSxHQUFHLGlCQUFpQixDQUFZLEVBQUUsRUFBRSxJQUFJLENBQUMsVUFBVSxDQUFDLE9BQU8sQ0FBQyxDQUFDLENBQUM7UUFDcEUsV0FBTSxHQUFHLGlCQUFpQixDQUFZLEVBQUUsRUFBRSxJQUFJLENBQUMsVUFBVSxDQUFDLE9BQU8sQ0FBQyxDQUFDLENBQUM7UUFDcEUsYUFBUSxHQUFHLGdCQUFnQixDQUFDLENBQUMsRUFBRSxJQUFJLENBQUMsVUFBVSxDQUFDLFNBQVMsQ0FBQyxDQUFDLENBQUM7UUFDM0QsYUFBUSxHQUFHLGdCQUFnQixDQUFDLENBQUMsRUFBRSxJQUFJLENBQUMsVUFBVSxDQUFDLFNBQVMsQ0FBQyxDQUFDLENBQUM7UUFDM0QsVUFBSyxHQUFHLGdCQUFnQixDQUFDLEdBQUcsRUFBRSxJQUFJLENB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LFFBQVEsQ0FBQyxLQUFrQjtRQUN6QixJQUFJLENBQUMsTUFBTSxDQUFDLE9BQU8sQ0FBQyxLQUFLLENBQUMsQ0FBQyxJQUFJLEVBQUUsQ0FBQztJQUNwQyxDQUFDO0lBRUQsUUFBUSxDQUFDLEtBQWtCO1FBQ3pCLElBQUksQ0FBQyxNQUFNLENBQUMsT0FBTyxDQUFDLEtBQUssQ0FBQyxDQUFDLElBQUksRUFBRSxDQUFDO0lBQ3BDLENBQUM7SUFFRCxPQUFPO1FBQ0wsS0FBSyxDQUFDLE9BQU8sRUFBRSxDQUFDO1FBQ2hCLElBQUksQ0FBQyxNQUFNLENBQUMsT0FBTyxFQUFFLENBQUM7UUFDdEIsSUFBSSxDQUFDLE1BQU0sQ0FBQyxPQUFPLEVBQUUsQ0FBQztJQUN4QixDQUFDO0NBQ0YiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBPYnNlcnZhYmxlIH0gZnJvbSAncnhqcyc7XG5pbXBvcnQgeyBCYXNlRW50aXR5LCBCYXNlRW50aXR5VHlwZSB9IGZyb20gJy4uL2Jhc2UuZW50aXR5JztcbmltcG9ydCB7IENvb3JkcyB9IGZyb20gJy4uL2ludGVyZmFjZXMvY29vcmRzLmludGVyZmFjZSc7XG5pbXBvcnQgeyBTZWxlY3RPcHRpb25zIH0gZnJvbSAnLi4vaW50ZXJmYWNlcy9zZWxlY3Qtb3B0aW9ucy5pbnRlcmZhY2UnO1xuaW1wb3J0IHsgU2VyaWFsaXplZERpYWdyYW1Nb2RlbCB9IGZyb20gJy4uL2ludGVyZmFjZXMvc2VyaWFsaXphdGlvbi5pbnRlcmZhY2UnO1xuaW1wb3J0IHsgRGlhZ3JhbUVuZ2luZSB9IGZyb20gJy4uL3NlcnZpY2VzL2VuZ2luZS5zZXJ2aWNlJztcbmltcG9ydCB7IGNyZWF0ZUVudGl0eVN0YXRlLCBjcmVhdGVWYWx1ZVN0YXRlIH0gZnJvbSAnLi4vc3RhdGUvc3RhdGUnO1xuaW1wb3J0IHsgY29lcmNlQXJyYXksIElELCBpc0VtcHR5QXJyYXksIHVuaXF1ZSB9IGZyb20gJy4uL3V0aWxzJztcbmltcG9ydCB7IEVudGl0eU1hcCB9IGZyb20gJy4uL3V0aWxzL3R5cGVzJztcbmltcG9ydCB7IEJhc2VNb2RlbCB9IGZyb20gJy4vYmFzZS5tb2RlbCc7XG5pbXBvcnQgeyBMaW5rTW9kZWwgfSBmcm9tICcuL2xpbmsubW9kZWwnO1xuaW1wb3J0IHsgTm9kZU1vZGVsIH0gZnJvbSAnLi9ub2RlLm1vZGVsJztcbmltcG9ydCB7IFBvcnRNb2RlbCB9IGZyb20gJy4vcG9ydC5tb2RlbCc7XG5cbmV4cG9ydCBjbGFzcyBEaWFncmFtTW9kZWwgZXh0ZW5kcyBCYXNlRW50aXR5IHtcbiAgcHJvdGVjdGVkIG5vZGVzJCA9IGNyZWF0ZUVudGl0eVN0YXRlPE5vZGVNb2RlbD4oW10sIHRoaXMuZW50aXR5UGlwZSgnbm9kZXMnKSk7XG4gIHByb3RlY3RlZCBsaW5rcyQgPSBjcmVhdGVFbnRpdHlTdGF0ZTxMaW5rTW9kZWw+KFtdLCB0aGlzLmVudGl0eVBpcGUoJ2xpbmtzJykpO1xuICBwcm90ZWN0ZWQgb2Zmc2V0WCQgPSBjcmVhdGVWYWx1ZVN0YXRlKDAsIHRoaXMuZW50aXR5UGlwZSgnb2Zmc2V0WCcpKTtcbiAgcHJvdGVjdGVkIG9mZnNldFkkID0gY3JlYXRlVmFsdWVTdGF0ZSgwLCB0aGlzLmVudGl0eVBpcGUoJ29mZnNldFknKSk7XG4gIHByb3RlY3RlZCB6b29tJCA9IGNyZWF0ZVZhbHVlU3RhdGUoMTAwLCB0aGlzLmVudGl0eVBpcGUoJ3pvb20nKSk7XG4gIHByb3RlY3RlZCBtYXhab29tT3V0JCA9IGNyZWF0ZVZhbHVlU3RhdGUobnVsbCk7XG4gIHByb3RlY3RlZCBtYXhab29tSW4kID0gY3JlYXRlVmFsdWVTdGF0ZShudWxsKTtcbiAgcHJvdGVjdGVkIGdyaWRTaXplJCA9IGNyZWF0ZVZhbHVlU3RhdGUoMCk7XG5cbiAgY29uc3RydWN0b3IocHJvdGVjdGVkIGRpYWdyYW1FbmdpbmU6IERpYWdyYW1FbmdpbmUsIGlkPzogc3RyaW5nLCBsb2dQcmVmaXggPSAnW0RpYWdyYW1dJykge1xuICAgIHN1cGVyKGlkLCBsb2dQcmVmaXgpO1xuICB9XG5cbiAgLy8gVE9ETzogc3VwcG9ydCB0aGUgZm9sbG93aW5nIGV2ZW50cyBmb3IgbGlua3MgYW5kIG5vZGVzXG4gIC8vIHJlbW92ZWQsIHVwZGF0ZWQ8cG9zaXRpb25DaGFuZ2VkL2RhdGFDaGFuZ2VkPiwgYWRkZWRcbiAgZ2V0Tm9kZXMoKTogRW50aXR5TWFwPE5vZGVNb2RlbD4ge1xuICAgIHJldHVybiB0aGlzLm5vZGVzJC52YWx1ZTtcbiAgfVxuXG4gIGdldE5vZGVzQXJyYXkoKTogTm9kZU1vZGVsW10ge1xuICAgIHJldHVybiB0aGlzLm5vZGVzJC5hcnJheSgpO1xuICB9XG5cbiAgZ2V0Tm9kZShpZDogSUQpOiBOb2RlTW9kZWwgfCB1bmRlZmluZWQge1xuICAgIHJldHVybiB0aGlzLm5vZGVzJC5nZXQoaWQpO1xuICB9XG5cbiAgZ2V0TGluayhpZDogSUQpOiBMaW5rTW9kZWwgfCB1bmRlZmluZWQge1xuICAgIHJldHVybiB0aGlzLmxpbmtzJC5nZXQoaWQpO1xuICB9XG5cbiAgZ2V0TGlua3MoKTogRW50aXR5TWFwPExpbmtNb2RlbD4ge1xuICAgIHJldHVybiB0aGlzLmxpbmtzJC52YWx1ZTtcbiAgfVxuXG4gIGdldExpbmtzQXJyYXkoKTogTGlua01vZGVsW10ge1xuICAgIHJldHVybiB0aGlzLmxpbmtzJC5hcnJheSgpO1xuICB9XG5cbiAgZ2V0QWxsUG9ydHMob3B0aW9uczogU2VsZWN0T3B0aW9uczxQb3J0TW9kZWw+ID0ge30pOiBNYXA8c3RyaW5nLCBQb3J0TW9kZWw+IHtcbiAgICBjb25zdCByZXN1bHQgPSBuZXcgTWFwPElELCBQb3J0TW9kZWw+KCk7XG5cbiAgICB0aGlzLmdldE5vZGVzKCkuZm9yRWFjaCgobm9kZSkgPT4ge1xuICAgICAgY29uc3QgcG9ydHMgPSBvcHRpb25zLmZpbHRlciA/IG5vZGUuZ2V0UG9ydHNBcnJheSgpLmZpbHRlcihvcHRpb25zLmZpbHRlcikgOiBub2RlLmdldFBvcnRzQXJyYXkoKTtcbiAgICAgIHBvcnRzLmZvckVhY2goKHBvcnQpID0+IHJlc3VsdC5zZXQocG9ydC5pZCwgcG9ydCkpO1xuICAgIH0pO1xuXG4gICAgcmV0dXJuIHJlc3VsdDtcbiAgfVxuXG4gIC8qKlxuICAgKiBBZGQgYSBub2RlIHRvIHRoZSBkaWFncmFtXG4gICAqIEByZXR1cm5zIEluc2VydGVkIE5vZGVcbiAgICovXG4gIGFkZE5vZGUobm9kZTogTm9kZU1vZGVsKTogTm9kZU1vZGVsIHtcbiAgICB0aGlzLm5vZGVzJC5hZGQobm9kZSkuZW1pdCgpO1xuICAgIHJldHVybiBub2RlO1xuICB9XG5cbiAgLyoqXG4gICAqIERlbGV0ZSBhIG5vZGUgZnJvbSB0aGUgZGlhZ3JhbVxuICAgKi9cbiAgZGVsZXRlTm9kZShub2RlT3JJZDogTm9kZU1vZGVsIHwgc3RyaW5nKTogdm9pZCB7XG4gICAgY29uc3Qgbm9kZUlkOiBJRCA9IHR5cGVvZiBub2RlT3JJZCA9PT0gJ3N0cmluZycgPyBub2RlT3JJZCA6IG5vZGVPcklkLmlkO1xuICAgIGNvbnN0IG5vZGUgPSB0aGlzLmdldE5vZGUobm9kZUlkKTtcblxuICAgIGZvciAoY29uc3QgcG9ydCBvZiBub2RlLmdldFBvcnRzKCkudmFsdWVzKCkpIHtcbiAgICAgIGZvciAoY29uc3QgbGluayBvZiBwb3J0LmdldExpbmtzKCkudmFsdWVzKCkpIHtcbiAgICAgICAgdGhpcy5kZWxldGVMaW5rKGxpbmspO1xuICAgICAgfVxuICAgIH1cblxuICAgIHRoaXMubm9kZXMkLnJlbW92ZShub2RlSWQpLmVtaXQoKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBHZXQgbm9kZXMgYXMgb2JzZXJ2YWJsZSwgdXNlIGAuZ2V0VmFsdWUoKWAgZm9yIHNuYXBzaG90XG4gICAqL1xuICBzZWxlY3ROb2RlcygpOiBPYnNlcnZhYmxlPEVudGl0eU1hcDxOb2RlTW9kZWw+PiB7XG4gICAgcmV0dXJuIHRoaXMubm9kZXMkLnZhbHVlJDtcbiAgfVxuXG4gIC8qKlxuICAgKiBBZGQgbGlua1xuICAgKiBAcmV0dXJucyBOZXdseSBjcmVhdGVkIGxpbmtcbiAgICovXG4gIGFkZExpbmsobGluazogTGlua01vZGVsKTogTGlua01vZGVsIHtcbiAgICB0aGlzLmxpbmtzJC5hZGQobGluaykuZW1pdCgpO1xuICAgIHJldHVybiBsaW5rO1xuICB9XG5cbiAgLyoqXG4gICAqIERlbGV0ZSBsaW5rXG4gICAqL1xuICBkZWxldGVMaW5rKGxpbmtPcklkOiBMaW5rTW9kZWwgfCBzdHJpbmcpIHtcbiAgICBjb25zdCBsaW5rSWQ6IElEID0gdHlwZW9mIGxpbmtPcklkID09PSAnc3RyaW5nJyA/IGxpbmtPcklkIDogbGlua09ySWQuaWQ7XG4gICAgdGhpcy5saW5rcyQucmVtb3ZlKGxpbmtJZCkuZW1pdCgpO1xuICB9XG5cbiAgcmVzZXQoKSB7XG4gICAgdGhpcy5ub2RlcyQuY2xlYXIoKS5lbWl0KCk7XG4gICAgdGhpcy5saW5rcyQuY2xlYXIoKS5lbWl0KCk7XG4gIH1cblxuICAvKipcbiAgICogR2V0IGxpbmtzIGJlaGF2aW91ciBzdWJqZWN0LCB1c2UgYC5nZXRWYWx1ZSgpYCBmb3Igc25hcHNob3RcbiAgICovXG4gIHNlbGVjdExpbmtzKCk6IE9ic2VydmFibGU8RW50aXR5TWFwPExpbmtNb2RlbD4+IHtcbiAgICByZXR1cm4gdGhpcy5saW5rcyQudmFsdWUkO1xuICB9XG5cbiAgLy8gLyoqXG4gIC8vICAqIFNlcmlhbGl6ZSB0aGUgZGlhZ3JhbSBtb2RlbCB0byBKU09OXG4gIC8vICAqIEByZXR1cm5zIGRpYWdyYW0gbW9kZWwgYXMgYSBzdHJpbmdcbiAgLy8gICovXG4gIHNlcmlhbGl6ZSgpOiBTZXJpYWxpemVkRGlhZ3JhbU1vZGVsIHtcbiAgICBjb25zdCBzZXJpYWxpemVkTm9kZXMgPSB0aGlzLm5vZGVzJC5tYXAoKG5vZGUpID0+IG5vZGUuc2VyaWFsaXplKCkpO1xuICAgIGNvbnN0IHNlcmlhbGl6ZWRMaW5rcyA9IHRoaXMubGlua3MkLm1hcCgobGluaykgPT4gbGluay5zZXJpYWxpemUoKSk7XG5cbiAgICByZXR1cm4geyAuLi5zdXBlci5zZXJpYWxpemUoKSwgbm9kZXM6IHNlcmlhbGl6ZWROb2RlcywgbGlua3M6IHNlcmlhbGl6ZWRMaW5rcyB9O1xuICB9XG5cbiAgc2V0TWF4Wm9vbU91dChtYXhab29tT3V0OiBudW1iZXIpIHtcbiAgICB0aGlzLm1heFpvb21PdXQkLnNldChtYXhab29tT3V0KS5lbWl0KCk7XG4gIH1cblxuICBzZXRNYXhab29tSW4obWF4Wm9vbUluOiBudW1iZXIpIHtcbiAgICB0aGlzLm1heFpvb21JbiQuc2V0KG1heFpvb21JbikuZW1pdCgpO1xuICB9XG5cbiAgZ2V0TWF4Wm9vbU91dCgpIHtcbiAgICByZXR1cm4gdGhpcy5tYXhab29tT3V0JC52YWx1ZTtcbiAgfVxuXG4gIGdldE1heFpvb21JbigpIHtcbiAgICByZXR1cm4gdGhpcy5tYXhab29tSW4kLnZhbHVlO1xuICB9XG5cbiAgc2V0T2Zmc2V0KHg6IG51bWJlciwgeTogbnVtYmVyKSB7XG4gICAgdGhpcy5vZmZzZXRYJC5zZXQoeCkuZW1pdCgpO1xuICAgIHRoaXMub2Zmc2V0WSQuc2V0KHkpLmVtaXQoKTtcbiAgfVxuXG4gIHNldE9mZnNldFgoeDogbnVtYmVyKSB7XG4gICAgdGhpcy5vZmZzZXRYJC5zZXQoeCkuZW1pdCgpO1xuICB9XG5cbiAgZ2V0T2Zmc2V0WCgpOiBudW1iZXIge1xuICAgIHJldHVybiB0aGlzLm9mZnNldFgkLnZhbHVlO1xuICB9XG5cbiAgc2VsZWN0T2Zmc2V0WCgpOiBPYnNlcnZhYmxlPG51bWJlcj4ge1xuICAgIHJldHVybiB0aGlzLm9mZnNldFgkLnZhbHVlJDtcbiAgfVxuXG4gIHNldE9mZnNldFkoeTogbnVtYmVyKSB7XG4gICAgdGhpcy5vZmZzZXRZJC5zZXQoeSkuZW1pdCgpO1xuICB9XG5cbiAgZ2V0T2Zmc2V0WSgpOiBudW1iZXIge1xuICAgIHJldHVybiB0aGlzLm9mZnNldFkkLnZhbHVlO1xuICB9XG5cbiAgc2VsZWN0T2Zmc2V0WSgpOiBPYnNlcnZhYmxlPG51bWJlcj4ge1xuICAgIHJldHVybiB0aGlzLm9mZnNldFkkLnZhbHVlJDtcbiAgfVxuXG4gIHNldFpvb21MZXZlbCh6OiBudW1iZXIpIHtcbiAgICBjb25zdCBtYXhab29tSW4gPSB0aGlzLmdldE1heFpvb21JbigpO1xuICAgIGNvbnN0IG1heFpvb21PdXQgPSB0aGlzLmdldE1heFpvb21PdXQoKTtcblxuICAgIC8vIGNoZWNrIGlmIHpvb20gbGV2ZWxzIGV4Y2VlZGVkIGRlZmluZWQgYm91bmRhcmllc1xuICAgIGlmICgobWF4Wm9vbUluICYmIHogPiBtYXhab29tSW4pIHx8IChtYXhab29tT3V0ICYmIHogPCBtYXhab29tT3V0KSkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIHRoaXMuem9vbSQuc2V0KHopLmVtaXQoKTtcbiAgfVxuXG4gIGdldFpvb21MZXZlbCgpOiBudW1iZXIge1xuICAgIHJldHVybiB0aGlzLnpvb20kLnZhbHVlO1xuICB9XG5cbiAgc2VsZWN0Wm9vbUxldmVsKCk6IE9ic2VydmFibGU8bnVtYmVyPiB7XG4gICAgcmV0dXJuIHRoaXMuem9vbSQudmFsdWUkO1xuICB9XG5cbiAgZ2V0RGlhZ3JhbUVuZ2luZSgpOiBEaWFncmFtRW5naW5lIHtcbiAgICByZXR1cm4gdGhpcy5kaWFncmFtRW5naW5lO1xuICB9XG5cbiAgY2xlYXJTZWxlY3Rpb24oaWdub3JlOiBCYXNlTW9kZWwgfCBudWxsID0gbnVsbCkge1xuICAgIHRoaXMuZ2V0U2VsZWN0ZWRJdGVtcygpLmZvckVhY2goKGVsZW1lbnQpID0+IHtcbiAgICAgIGlmIChpZ25vcmU/LmlkID09PSBlbGVtZW50LmlkKSB7XG4gICAgICAgIHJldHVybjtcbiAgICAgIH1cbiAgICAgIGVsZW1lbnQuc2V0U2VsZWN0ZWQoZmFsc2UpO1xuICAgIH0pO1xuICB9XG5cbiAgZ2V0R3JpZFBvc2l0aW9uKHsgeCwgeSB9OiBDb29yZHMpOiBDb29yZHMge1xuICAgIGNvbnN0IGdyaWRTaXplID0gdGhpcy5ncmlkU2l6ZSQudmFsdWU7XG4gICAgaWYgKGdyaWRTaXplID09PSAwKSB7XG4gICAgICByZXR1cm4geyB4LCB5IH07XG4gICAgfVxuXG4gICAgcmV0dXJuIHtcbiAgICAgIHg6IGdyaWRTaXplICogTWF0aC5mbG9vcigoeCArIGdyaWRTaXplIC8gMikgLyBncmlkU2l6ZSksXG4gICAgICB5OiBncmlkU2l6ZSAqIE1hdGguZmxvb3IoKHkgKyBncmlkU2l6ZSAvIDIpIC8gZ3JpZFNpemUpXG4gICAgfTtcbiAgfVxuXG4gIGdldFNlbGVjdGVkSXRlbXMoLi4uZmlsdGVyczogQmFzZUVudGl0eVR5cGVbXSk6IEJhc2VNb2RlbFtdIHtcbiAgICBmaWx0ZXJzID0gY29lcmNlQXJyYXkoZmlsdGVycyk7XG5cbiAgICBjb25zdCBpdGVtczogQmFzZU1vZGVsW10gPSBbXTtcbiAgICBjb25zdCBub2RlcyA9IHRoaXMubm9kZXMkLmFycmF5KCk7XG4gICAgY29uc3QgbGlua3MgPSB0aGlzLmxpbmtzJC5hcnJheSgpO1xuXG4gICAgY29uc3Qgc2VsZWN0ZWROb2RlcyA9ICgpID0+IG5vZGVzLmZsYXRNYXAoKG5vZGUpID0+IG5vZGUuZ2V0U2VsZWN0ZWRFbnRpdGllcygpKTtcbiAgICBjb25zdCBzZWxlY3RlZFBvcnRzID0gKCkgPT5cbiAgICAgIG5vZGVzLmZsYXRNYXAoKG5vZGUpID0+IG5vZGUuZ2V0UG9ydHNBcnJheSgpLmZsYXRNYXAoKHBvcnQ6IFBvcnRNb2RlbCkgPT4gcG9ydC5nZXRTZWxlY3RlZEVudGl0aWVzKCkpKTtcbiAgICBjb25zdCBzZWxlY3RlZExpbmtzID0gKCkgPT4gbGlua3MuZmxhdE1hcCgobGluaykgPT4gbGluay5nZXRTZWxlY3RlZEVudGl0aWVzKCkpO1xuICAgIGNvbnN0IHNlbGVjdGVkUG9pbnRzID0gKCkgPT5cbiAgICAgIGxpbmtzLmZsYXRNYXAoKGxpbmspID0+IGxpbmsuZ2V0UG9pbnRzKCkuZmxhdE1hcCgocG9pbnQpID0+IHBvaW50LmdldFNlbGVjdGVkRW50aXRpZXMoKSkpO1xuXG4gICAgaWYgKGlzRW1wdHlBcnJheShmaWx0ZXJzKSkge1xuICAgICAgaXRlbXMucHVzaCguLi5zZWxlY3RlZE5vZGVzKCksIC4uLnNlbGVjdGVkUG9ydHMoKSwgLi4uc2VsZWN0ZWRMaW5rcygpLCAuLi5zZWxlY3RlZFBvaW50cygpKTtcbiAgICB9IGVsc2Uge1xuICAgICAgY29uc3QgYnlUeXBlOiBSZWNvcmQ8QmFzZUVudGl0eVR5cGUsICgpID0+IEJhc2VNb2RlbFtdPiA9IHtcbiAgICAgICAgbm9kZTogc2VsZWN0ZWROb2RlcyxcbiAgICAgICAgcG9ydDogc2VsZWN0ZWRQb3J0cyxcbiAgICAgICAgbGluazogc2VsZWN0ZWRMaW5rcyxcbiAgICAgICAgcG9pbnQ6IHNlbGVjdGVkUG9pbnRzXG4gICAgICB9O1xuXG4gICAgICBmb3IgKGNvbnN0IHR5cGUgb2YgZmlsdGVycykge1xuICAgICAgICBpdGVtcy5wdXNoKC4uLmJ5VHlwZVt0eXBlXSgpKTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICByZXR1cm4gdW5pcXVlKGl0ZW1zKTtcbiAgfVxuXG4gIGFkZEFsbCguLi5tb2RlbHM6IEJhc2VNb2RlbFtdKSB7XG4gICAgY29uc3QgbGlua3M6IExpbmtNb2RlbFtdID0gW107XG4gICAgY29uc3Qgbm9kZXM6IE5vZGVNb2RlbFtdID0gW107XG5cbiAgICBmb3IgKGNvbnN0IG1vZGVsIG9mIG1vZGVscykge1xuICAgICAgaWYgKG1vZGVsIGluc3RhbmNlb2YgTGlua01vZGVsKSB7XG4gICAgICAgIGxpbmtzLnB1c2gobW9kZWwpO1xuICAgICAgfSBlbHNlIGlmIChtb2RlbCBpbnN0YW5jZW9mIE5vZGVNb2RlbCkge1xuICAgICAgICBub2Rlcy5wdXNoKG1vZGVsKTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICB0aGlzLmFkZExpbmtzKGxpbmtzKTtcbiAgICB0aGlzLmFkZE5vZGVzKG5vZGVzKTtcblxuICAgIHJldHVybiBtb2RlbHM7XG4gIH1cblxuICBhZGRMaW5rcyhsaW5rczogTGlua01vZGVsW10pIHtcbiAgICB0aGlzLmxpbmtzJC5hZGRNYW55KGxpbmtzKS5lbWl0KCk7XG4gIH1cblxuICBhZGROb2Rlcyhub2RlczogTm9kZU1vZGVsW10pIHtcbiAgICB0aGlzLm5vZGVzJC5hZGRNYW55KG5vZGVzKS5lbWl0KCk7XG4gIH1cblxuICBkZXN0cm95KCkge1xuICAgIHN1cGVyLmRlc3Ryb3koKTtcbiAgICB0aGlzLm5vZGVzJC5kZXN0cm95KCk7XG4gICAgdGhpcy5saW5rcyQuZGVzdHJveSgpO1xuICB9XG59XG4iXX0=