UNPKG

@chart-plugins/superset-indicator-chart

Version:

Indicator chart plugin for Apache Superset

87 lines (82 loc) 4.14 kB
function _extends() { _extends = Object.assign || function (target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i]; for (var key in source) { if (Object.prototype.hasOwnProperty.call(source, key)) { target[key] = source[key]; } } } return target; }; return _extends.apply(this, arguments); } import React from 'react'; import vm from 'vm'; const GLOBAL_CONTEXT = { console }; export function sandboxedEval(code, context = {}, opts = {}) { const sandbox = {}; const resultKey = `SAFE_EVAL_${Math.floor(Math.random() * 1000000)}`; sandbox[resultKey] = {}; const codeToEval = `${resultKey}=${code}`; const sandboxContext = _extends({}, GLOBAL_CONTEXT, context); Object.keys(sandboxContext).forEach(key => { sandbox[key] = sandboxContext[key]; }); try { vm.runInNewContext(codeToEval, sandbox, opts); return sandbox[resultKey]; } catch (error) { console.error('Error evaluating code in sandbox:', error); return () => error; } } /** * Упрощенная безопасная функция для выполнения JavaScript кода * Без использования worker-javascript.js */ export function simpleSandboxedEval(code) { // Создаем функцию с ограниченным доступом к глобальным объектам // eslint-disable-next-line no-new-func const evaluator = new Function('data', ` 'use strict'; // Ограничиваем доступ к глобальным объектам const window = undefined; const document = undefined; const navigator = undefined; const localStorage = undefined; const sessionStorage = undefined; const fetch = undefined; const XMLHttpRequest = undefined; // Разрешаем только базовые JavaScript функции const console = { log: () => {} }; const Math = Object.freeze(global.Math); const Date = Object.freeze(global.Date); const Array = Object.freeze(global.Array); const String = Object.freeze(global.String); const Number = Object.freeze(global.Number); const Object = Object.freeze(global.Object); const JSON = Object.freeze(global.JSON); try { return (${code})(data); } catch (error) { console.log('Error executing JavaScript code:', error); return '#0BDA51'; // Возвращаем зеленый цвет по умолчанию в случае ошибки } `); // Возвращаем функцию, которая будет выполнять код return data => { try { return evaluator(data); } catch (error) { console.error('Error in simpleSandboxedEval:', error); return '#0BDA51'; // Возвращаем зеленый цвет по умолчанию в случае ошибки } }; } // Контрол для JavaScript функций export function jsFunctionControl(label, description, extraTooltip = null, height = 100, defaultCode = '') { return { type: 'TextAreaControl', language: 'sql', label, description, height, default: defaultCode, aboveEditorSection: /*#__PURE__*/React.createElement("div", null, /*#__PURE__*/React.createElement("p", null, "\u0414\u0430\u043D\u043D\u0430\u044F \u0444\u0443\u043D\u043A\u0446\u0438\u044F \u043F\u043E\u043B\u0443\u0447\u0430\u0435\u0442 \u043D\u0430 \u0432\u0445\u043E\u0434 ", /*#__PURE__*/React.createElement("code", null, "data"), " \u043E\u0431\u044A\u0435\u043A\u0442 \u0438 \u0434\u043E\u043B\u0436\u043D\u0430 \u0432\u0435\u0440\u043D\u0443\u0442\u044C \u0446\u0432\u0435\u0442 \u0432 \u0444\u043E\u0440\u043C\u0430\u0442\u0435 HEX, RGB \u0438\u043B\u0438 \u0438\u043C\u0435\u043D\u0438."), extraTooltip && /*#__PURE__*/React.createElement("p", null, extraTooltip), /*#__PURE__*/React.createElement("p", null, /*#__PURE__*/React.createElement("strong", null, "\u041F\u0440\u0438\u043C\u0435\u0440:")), /*#__PURE__*/React.createElement("pre", null, `function(data) { const value = data.value || 0; return value < 10 ? '#FF0000' : '#00FF00'; }`)), tooltipOnClick: () => {} }; }