UNPKG

@senx/discovery-widgets

Version:

Discovery Widgets Elements

917 lines (916 loc) 36.4 kB
/* * Copyright 2022-2025 SenX S.A.S. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ import { h } from "@stencil/core"; import { Utils } from "../../utils/utils"; import { Param } from "../../model/param"; import { Logger } from "../../utils/logger"; import { GTSLib } from "../../utils/gts.lib"; import { LangUtils } from "../../utils/lang-utils"; import { v4 } from "uuid"; export class DiscoveryTileComponent { constructor() { this.options = new Param(); this.language = 'warpscript'; this.debug = false; this.unit = ''; this.autoRefresh = -1; this.vars = '{}'; this.loaded = false; this.result = '[]'; this.showLoader = false; this.hasError = false; this.errorMessage = ''; this.statusMessage = ''; this.hiddenByWs = false; this.innerVars = {}; this.innerOptions = new Param(); this.firstExec = false; } async optionsUpdate(newValue, oldValue) { var _a, _b, _c, _d; (_a = this.LOG) === null || _a === void 0 ? void 0 : _a.debug(['optionsUpdate'], newValue, oldValue); let opts = newValue; if (!!newValue && typeof newValue === 'string') { opts = JSON.parse(newValue); } if (!Utils.deepEqual(opts, this.innerOptions)) { this.innerOptions = Utils.clone(opts); if (Utils.deepEqual((_b = opts.httpHeaders) !== null && _b !== void 0 ? _b : {}, (_c = this.innerOptions.httpHeaders) !== null && _c !== void 0 ? _c : {})) { await this.exec(true); } (_d = this.LOG) === null || _d === void 0 ? void 0 : _d.debug(['optionsUpdate 2'], this.type, { options: this.innerOptions, newValue, oldValue }); } } async scriptUpdate(newValue, oldValue) { var _a; (_a = this.LOG) === null || _a === void 0 ? void 0 : _a.debug(['scriptUpdate'], newValue, oldValue); await this.exec(true); } async varsUpdate(newValue, oldValue) { var _a; let vars = this.vars; if (!!this.vars && typeof this.vars === 'string') { vars = JSON.parse(this.vars); } if (!Utils.deepEqual(vars, this.innerVars)) { this.innerVars = Utils.clone(vars); await this.exec(true); } if (this.LOG) { (_a = this.LOG) === null || _a === void 0 ? void 0 : _a.debug(['varsUpdate'], { vars: this.vars, newValue, oldValue }); } } async discoveryEventHandler(event) { var _a, _b, _c, _d, _e; const res = Utils.parseEventData(event.detail, this.innerOptions.eventHandler, this.componentId); if (res.vars) { this.innerVars = Utils.clone(Object.assign(Object.assign({}, ((_a = this.innerVars) !== null && _a !== void 0 ? _a : {})), res.vars)); if (!((_b = this.innerOptions.mutedVars) !== null && _b !== void 0 ? _b : []).includes(event.detail.selector)) { await this.exec(true); } } if (res.selected) { const vars = Utils.clone(Object.assign(Object.assign({}, ((_c = this.innerVars) !== null && _c !== void 0 ? _c : {})), res.selected)); if (!Utils.deepEqual((_d = this.innerVars) !== null && _d !== void 0 ? _d : {}, vars)) { this.innerVars = Utils.clone(vars); if (!((_e = this.innerOptions.mutedVars) !== null && _e !== void 0 ? _e : []).includes(event.detail.selector)) { await this.exec(true); } } } } async resize() { var _a; const dims = Utils.getContentBounds(this.el.parentElement); this.height = dims.h; (_a = this.LOG) === null || _a === void 0 ? void 0 : _a.debug(['componentDidLoad'], 'Tile - resize', this.tileResult); if (this.tileResult && this.width !== (dims.w - 2)) { this.width = dims.w - 2; return this.tileResult.resize(); } } async show(regexp) { if (this.tileResult) { await this.tileResult.show(regexp); } } async showById(id) { if (this.tileResult) { await this.tileResult.showById(id); } } async hide(regexp) { if (this.tileResult) { await this.tileResult.hide(regexp); } } async hideById(id) { if (this.tileResult) { await this.tileResult.hideById(id); } } async setFocus(regexp, ts, value) { if (this.tileResult) { await this.tileResult.setFocus(regexp, ts, value); } } async unFocus() { if (this.tileResult) { await this.tileResult.unFocus(); } } // noinspection JSUnusedGlobalSymbols componentWillLoad() { var _a, _b, _c; this.LOG = new Logger(DiscoveryTileComponent, this.debug); this.componentId = v4(); (_a = this.LOG) === null || _a === void 0 ? void 0 : _a.debug(['componentWillLoad'], { url: this.url, type: this.type, options: this.options, language: this.language, innerVars: this.innerVars, }); if (!!this.options && typeof this.options === 'string' && this.options !== 'undefined') { this.innerOptions = JSON.parse(this.options); } else { this.innerOptions = Object.assign({}, (_b = this.options) !== null && _b !== void 0 ? _b : new Param()); } this.innerVars = JSON.parse((_c = this.vars) !== null && _c !== void 0 ? _c : '{}'); const dims = Utils.getContentBounds(this.el.parentElement); this.width = dims.w - 2; this.height = dims.h; } async componentDidLoad() { if (!this.firstExec) { await this.exec(); } } // noinspection JSUnusedGlobalSymbols disconnectedCallback() { var _a; (_a = this.LOG) === null || _a === void 0 ? void 0 : _a.debug(['disconnectedCallback'], 'disconnected'); if (this.timer) { window.clearInterval(this.timer); window.clearInterval(this.timerFadeOut); } if (this.socket) { this.socket.close(); } } async export(type = 'png') { if (this.tileResult) { return this.tileResult.export(type); } else { return undefined; } } async exec(refresh = false) { return new Promise(resolve => { var _a, _b, _c, _d, _e, _f; const script = (_a = this.script) !== null && _a !== void 0 ? _a : (_b = this.el) === null || _b === void 0 ? void 0 : _b.innerHTML; if (script !== undefined) { if (!refresh) { setTimeout(() => this.loaded = false); } this.ws = LangUtils.prepare(Utils.unsescape(script), (_c = this.innerVars) !== null && _c !== void 0 ? _c : {}, (_e = (_d = this.innerOptions) === null || _d === void 0 ? void 0 : _d.skippedVars) !== null && _e !== void 0 ? _e : [], this.type, this.language); if (window) { const win = window; let registry = win.DiscoveryPluginRegistry; registry = registry !== null && registry !== void 0 ? registry : {}; if (!!(registry !== null && registry !== void 0 ? registry : {})[this.type] && !!registry[this.type].scriptWrapper && typeof registry[this.type].scriptWrapper === 'function') { this.ws = registry[this.type].scriptWrapper(this.ws); } } (_f = this.LOG) === null || _f === void 0 ? void 0 : _f.debug(['exec'], this.chartTitle, this.ws, this.type); this.url = Utils.getUrl(this.url); if (this.url.toLowerCase().startsWith('http')) { const thisRequestTs = Date.now(); this.latestRequestTs = thisRequestTs; setTimeout(() => { this.hasError = false; this.errorMessage = ''; this.statusMessage = undefined; this.showLoader = !!this.innerOptions.showLoader; }); Utils.httpPost(this.url, this.ws, this.innerOptions.httpHeaders) .then((res) => { var _a, _b, _c, _d, _e, _f, _g, _h; if (this.latestRequestTs !== thisRequestTs) { // When requests pile up, the oldests must be ignored. (_a = this.LOG) === null || _a === void 0 ? void 0 : _a.debug(['exec', 'liloControl'], 'This request result arrived later than the latest request, discard result'); resolve(true); } else { this.hiddenByWs = false; if (((_b = this.type) !== null && _b !== void 0 ? _b : '').startsWith('input') || ((_c = this.type) !== null && _c !== void 0 ? _c : '').startsWith('svg')) { this.result = ''; } this.headers = (_d = res === null || res === void 0 ? void 0 : res.headers) !== null && _d !== void 0 ? _d : {}; this.headers.statusText = `Your script execution took ${GTSLib.formatElapsedTime(res.status.elapsed)} serverside, fetched ${res.status.fetched} datapoints and performed ${res.status.ops} WarpLib operations.`; (_e = this.LOG) === null || _e === void 0 ? void 0 : _e.debug(['exec', 'headers'], this.headers); this.statusHeaders.emit(this.headers); if (this.innerOptions.showStatus) { this.statusMessage = this.headers.statusText; } this.start = window.performance.now(); const rws = GTSLib.getData(res.data); let autoRefreshFeedBack = (_g = (_f = rws.globalParams) === null || _f === void 0 ? void 0 : _f.autoRefresh) !== null && _g !== void 0 ? _g : -1; const fadeOutAfter = (_h = rws.globalParams) === null || _h === void 0 ? void 0 : _h.fadeOutAfter; if (rws.localvars) { Utils.mergeDeep(this.innerVars, rws.localvars); } if (autoRefreshFeedBack < 0) { autoRefreshFeedBack = undefined; } if (this.autoRefresh !== this.innerOptions.autoRefresh || autoRefreshFeedBack) { this.autoRefresh = autoRefreshFeedBack ? autoRefreshFeedBack : this.innerOptions.autoRefresh; if (this.timer) { window.clearInterval(this.timer); } if (this.autoRefresh && this.autoRefresh > 0) { this.timer = window.setInterval(() => void this.exec(true), this.autoRefresh * 1000); } } if (fadeOutAfter) { if (this.timerFadeOut) { window.clearInterval(this.timerFadeOut); } if (fadeOutAfter > 0) { this.timerFadeOut = window.setInterval(() => { this.hiddenByWs = true; window.clearInterval(this.timerFadeOut); }, fadeOutAfter * 1000); } } requestAnimationFrame(() => { var _a; this.loaded = true; this.showLoader = false; (_a = this.LOG) === null || _a === void 0 ? void 0 : _a.debug(['exec', 'result'], this.chartTitle, this.result); this.result = res.data; this.execResult.emit(this.result); this.hasError = false; resolve(true); }); } }) .catch(e => { this.displayError(e); this.loaded = true; this.showLoader = false; resolve(true); }); } else if (this.url.toLowerCase().startsWith('ws')) { // Web Socket if (this.socket) { this.socket.close(); } this.socket = new WebSocket(this.url); this.socket.onopen = () => { this.socket.onmessage = event => { var _a; const res = event.data; setTimeout(() => { this.loaded = true; this.showLoader = false; }); if (res.startsWith('["Exception at \'EVERY')) { this.hasError = this.innerOptions.showErrors; this.errorMessage = JSON.parse(res)[0] || 'Error'; this.statusError.emit(this.errorMessage); } else { this.result = res; this.hasError = false; this.errorMessage = ''; (_a = this.LOG) === null || _a === void 0 ? void 0 : _a.debug(['exec', 'result'], this.result); this.execResult.emit(this.result); } }; this.socket.send(`<% ${this.ws} %> ${(this.innerOptions.autoRefresh || 1000)} EVERY`); resolve(true); }; } } }); } async setZoom(dataZoom) { await this.tileResult.setZoom(dataZoom); } handleSelfType(type) { this.selfType.emit(type); } displayError(e) { setTimeout(() => { var _a, _b; this.statusError.emit(e); this.hasError = !!this.innerOptions.showErrors; this.errorMessage = (_a = e.message) !== null && _a !== void 0 ? _a : e.statusText; (_b = this.LOG) === null || _b === void 0 ? void 0 : _b.error(['exec'], e, this.innerOptions.showErrors, this.errorMessage); }); } render() { return h("div", { key: 'b54c7d5deb688e7cb4c48048276886caebc62615' }, this.loaded ? h("div", { style: { width: '100%', height: '100%', display: 'flex', flexDirection: 'column' }, class: this.hiddenByWs ? 'hidden-by-ws' : '' }, this.hasError ? h("div", { class: "discovery-tile-error" }, this.errorMessage) : '', h("discovery-tile-result", { url: this.url, start: this.start, result: this.result, type: this.type, options: JSON.stringify(this.innerOptions), unit: this.unit, debug: this.debug, height: this.height, width: this.width, language: this.language, "chart-title": this.chartTitle, "chart-description": this.chartDescription, onSelfType: type => this.handleSelfType(type), onExecError: (e) => this.displayError(e.detail), onDraw: () => this.draw.emit(), vars: JSON.stringify(this.innerVars), ref: (el) => this.tileResult = el, id: this.componentId, standalone: true }), this.statusMessage ? h("div", { class: "discovery-tile-status" }, this.statusMessage) : '') : h("div", { class: "discovery-tile-spinner" }, this.showLoader ? h("discovery-spinner", { backdrop: true }, "Requesting data...") : ''), this.showLoader ? h("div", { class: "discovery-tile-spinner" }, h("discovery-spinner", { backdrop: true }, "Requesting data...")) : '', h("pre", { key: '4244123b48c8a9e272e1dc03c21d5feef232a466', id: "ws" }, h("slot", { key: 'a5ce3e880a9f65a64f48470d09d656d6ea9cece2' }))); } static get is() { return "discovery-tile"; } static get encapsulation() { return "shadow"; } static get originalStyleUrls() { return { "$": ["discovery-tile.scss"] }; } static get styleUrls() { return { "$": ["discovery-tile.css"] }; } static get properties() { return { "url": { "type": "string", "mutable": true, "complexType": { "original": "string", "resolved": "string", "references": {} }, "required": false, "optional": false, "docs": { "tags": [], "text": "" }, "getter": false, "setter": false, "attribute": "url", "reflect": false }, "chartTitle": { "type": "string", "mutable": false, "complexType": { "original": "string", "resolved": "string", "references": {} }, "required": false, "optional": false, "docs": { "tags": [], "text": "" }, "getter": false, "setter": false, "attribute": "chart-title", "reflect": false }, "chartDescription": { "type": "string", "mutable": false, "complexType": { "original": "string", "resolved": "string", "references": {} }, "required": false, "optional": false, "docs": { "tags": [], "text": "" }, "getter": false, "setter": false, "attribute": "chart-description", "reflect": false }, "script": { "type": "string", "mutable": false, "complexType": { "original": "string", "resolved": "string", "references": {} }, "required": false, "optional": false, "docs": { "tags": [], "text": "" }, "getter": false, "setter": false, "attribute": "script", "reflect": false }, "type": { "type": "string", "mutable": false, "complexType": { "original": "ChartType", "resolved": "string", "references": { "ChartType": { "location": "import", "path": "../../model/types", "id": "src/model/types.ts::ChartType" } } }, "required": false, "optional": false, "docs": { "tags": [], "text": "" }, "getter": false, "setter": false, "attribute": "type", "reflect": false }, "options": { "type": "string", "mutable": true, "complexType": { "original": "Param | string", "resolved": "Param | string", "references": { "Param": { "location": "import", "path": "../../model/param", "id": "src/model/param.ts::Param" } } }, "required": false, "optional": false, "docs": { "tags": [], "text": "" }, "getter": false, "setter": false, "attribute": "options", "reflect": true, "defaultValue": "new Param()" }, "language": { "type": "string", "mutable": false, "complexType": { "original": "'warpscript' | 'flows'", "resolved": "\"flows\" | \"warpscript\"", "references": {} }, "required": false, "optional": false, "docs": { "tags": [], "text": "" }, "getter": false, "setter": false, "attribute": "language", "reflect": false, "defaultValue": "'warpscript'" }, "debug": { "type": "boolean", "mutable": false, "complexType": { "original": "boolean", "resolved": "boolean", "references": {} }, "required": false, "optional": false, "docs": { "tags": [], "text": "" }, "getter": false, "setter": false, "attribute": "debug", "reflect": false, "defaultValue": "false" }, "unit": { "type": "string", "mutable": false, "complexType": { "original": "string", "resolved": "string", "references": {} }, "required": false, "optional": false, "docs": { "tags": [], "text": "" }, "getter": false, "setter": false, "attribute": "unit", "reflect": false, "defaultValue": "''" }, "autoRefresh": { "type": "number", "mutable": true, "complexType": { "original": "number", "resolved": "number", "references": {} }, "required": false, "optional": false, "docs": { "tags": [], "text": "" }, "getter": false, "setter": false, "attribute": "auto-refresh", "reflect": false, "defaultValue": "-1" }, "vars": { "type": "any", "mutable": false, "complexType": { "original": "any", "resolved": "any", "references": {} }, "required": false, "optional": false, "docs": { "tags": [], "text": "" }, "getter": false, "setter": false, "attribute": "vars", "reflect": false, "defaultValue": "'{}'" } }; } static get states() { return { "loaded": {}, "result": {}, "width": {}, "height": {}, "showLoader": {}, "hasError": {}, "errorMessage": {}, "statusMessage": {}, "hiddenByWs": {} }; } static get events() { return [{ "method": "statusHeaders", "name": "statusHeaders", "bubbles": true, "cancelable": true, "composed": true, "docs": { "tags": [], "text": "" }, "complexType": { "original": "string[]", "resolved": "string[]", "references": {} } }, { "method": "statusError", "name": "statusError", "bubbles": true, "cancelable": true, "composed": true, "docs": { "tags": [], "text": "" }, "complexType": { "original": "any", "resolved": "any", "references": {} } }, { "method": "execResult", "name": "execResult", "bubbles": true, "cancelable": true, "composed": true, "docs": { "tags": [], "text": "" }, "complexType": { "original": "string", "resolved": "string", "references": {} } }, { "method": "selfType", "name": "selfType", "bubbles": true, "cancelable": true, "composed": true, "docs": { "tags": [], "text": "" }, "complexType": { "original": "ChartType", "resolved": "string", "references": { "ChartType": { "location": "import", "path": "../../model/types", "id": "src/model/types.ts::ChartType" } } } }, { "method": "draw", "name": "draw", "bubbles": true, "cancelable": true, "composed": true, "docs": { "tags": [], "text": "" }, "complexType": { "original": "void", "resolved": "void", "references": {} } }]; } static get methods() { return { "resize": { "complexType": { "signature": "() => Promise<void>", "parameters": [], "references": { "Promise": { "location": "global", "id": "global::Promise" } }, "return": "Promise<void>" }, "docs": { "text": "", "tags": [] } }, "show": { "complexType": { "signature": "(regexp: string) => Promise<void>", "parameters": [{ "name": "regexp", "type": "string", "docs": "" }], "references": { "Promise": { "location": "global", "id": "global::Promise" } }, "return": "Promise<void>" }, "docs": { "text": "", "tags": [] } }, "showById": { "complexType": { "signature": "(id: number) => Promise<void>", "parameters": [{ "name": "id", "type": "number", "docs": "" }], "references": { "Promise": { "location": "global", "id": "global::Promise" } }, "return": "Promise<void>" }, "docs": { "text": "", "tags": [] } }, "hide": { "complexType": { "signature": "(regexp: string) => Promise<void>", "parameters": [{ "name": "regexp", "type": "string", "docs": "" }], "references": { "Promise": { "location": "global", "id": "global::Promise" } }, "return": "Promise<void>" }, "docs": { "text": "", "tags": [] } }, "hideById": { "complexType": { "signature": "(id: number) => Promise<void>", "parameters": [{ "name": "id", "type": "number", "docs": "" }], "references": { "Promise": { "location": "global", "id": "global::Promise" } }, "return": "Promise<void>" }, "docs": { "text": "", "tags": [] } }, "setFocus": { "complexType": { "signature": "(regexp: string, ts: number, value?: number) => Promise<void>", "parameters": [{ "name": "regexp", "type": "string", "docs": "" }, { "name": "ts", "type": "number", "docs": "" }, { "name": "value", "type": "number", "docs": "" }], "references": { "Promise": { "location": "global", "id": "global::Promise" } }, "return": "Promise<void>" }, "docs": { "text": "", "tags": [] } }, "unFocus": { "complexType": { "signature": "() => Promise<void>", "parameters": [], "references": { "Promise": { "location": "global", "id": "global::Promise" } }, "return": "Promise<void>" }, "docs": { "text": "", "tags": [] } }, "export": { "complexType": { "signature": "(type?: \"png\" | \"svg\") => Promise<{ dataUrl: string; bgColor: string; }>", "parameters": [{ "name": "type", "type": "\"svg\" | \"png\"", "docs": "" }], "references": { "Promise": { "location": "global", "id": "global::Promise" } }, "return": "Promise<{ dataUrl: string; bgColor: string; }>" }, "docs": { "text": "", "tags": [] } }, "exec": { "complexType": { "signature": "(refresh?: boolean) => Promise<unknown>", "parameters": [{ "name": "refresh", "type": "boolean", "docs": "" }], "references": { "Promise": { "location": "global", "id": "global::Promise" }, "DataModel": { "location": "import", "path": "../../model/types", "id": "src/model/types.ts::DataModel" } }, "return": "Promise<unknown>" }, "docs": { "text": "", "tags": [] } }, "setZoom": { "complexType": { "signature": "(dataZoom: { start: number; end: number; }) => Promise<void>", "parameters": [{ "name": "dataZoom", "type": "{ start: number; end: number; }", "docs": "" }], "references": { "Promise": { "location": "global", "id": "global::Promise" } }, "return": "Promise<void>" }, "docs": { "text": "", "tags": [] } } }; } static get elementRef() { return "el"; } static get watchers() { return [{ "propName": "options", "methodName": "optionsUpdate" }, { "propName": "script", "methodName": "scriptUpdate" }, { "propName": "vars", "methodName": "varsUpdate" }]; } static get listeners() { return [{ "name": "discoveryEvent", "method": "discoveryEventHandler", "target": "window", "capture": false, "passive": false }]; } } //# sourceMappingURL=discovery-tile.js.map