Уведомление об ИИ-переводе

Этот документ был переведён с помощью ИИ. Для получения точной информации обратитесь к английской версии.

JavaScript-скрипт

Workflow: Узел JavaScriptCommunity Edition+

Введение

Узел JavaScript-скрипт позволяет выполнять пользовательский серверный JavaScript-скрипт в рамках рабочего процесса. В скрипте можно использовать переменные из предыдущих этапов рабочего процесса в качестве параметров, а возвращаемое значение скрипта может быть передано последующим узлам.

Скрипт выполняется в рабочем потоке на сервере приложения NocoBase. По умолчанию используется безопасная песочница (isolated-vm), которая не поддерживает require и встроенные API Node.js. Подробнее см. в разделах Движок выполнения и Список возможностей.

Создание узла

В интерфейсе настройки рабочего процесса нажмите кнопку «Плюс» («+») в потоке, чтобы добавить узел «JavaScript»:

20241202203457

Настройка узла

20241202203655

Параметры

Используются для передачи переменных или статических значений из контекста рабочего процесса в скрипт, где они будут использоваться в логике кода. name — это имя параметра, которое после передачи в скрипт становится именем переменной. value — это значение параметра, которое может быть переменной или константой.

Содержимое скрипта

Содержимое скрипта можно рассматривать как функцию. Вы можете написать любой JavaScript-код, поддерживаемый средой Node.js, и использовать оператор return для возврата значения в качестве результата выполнения узла, которое затем может быть использовано последующими узлами как переменная.

После написания кода вы можете нажать кнопку «Тест» под полем редактора, чтобы открыть диалоговое окно тестового выполнения. Там вы сможете ввести статические значения для параметров и выполнить симуляцию. После выполнения в диалоговом окне будут отображены возвращаемое значение и содержимое вывода (журнала).

20241202203833

Настройка таймаута

Единица измерения — миллисекунды. Значение 0 означает, что таймаут не установлен.

Продолжить при ошибке

Если этот параметр отмечен, последующие узлы будут выполнены, даже если скрипт завершится с ошибкой или превысит время ожидания.

Примечание

Если скрипт завершится с ошибкой, он не вернет никакого значения, и результат узла будет заполнен сообщением об ошибке. Если последующие узлы используют переменную результата из узла скрипта, к этому следует относиться с осторожностью.

Движок выполнения

Узел JavaScript-скрипта поддерживает два движка выполнения, которые автоматически выбираются в зависимости от наличия переменной среды WORKFLOW_SCRIPT_MODULES:

Безопасный режим (по умолчанию)

Когда WORKFLOW_SCRIPT_MODULES не настроена, скрипты выполняются с использованием движка isolated-vm. Этот движок выполняет код в изолированной среде V8 со следующими характеристиками:

  • Не поддерживает require — импорт модулей невозможен
  • Не поддерживает встроенные API Node.js (такие как process, Buffer, global и др.)
  • Доступны только встроенные объекты стандарта ECMAScript (такие как JSON, Math, Promise, Date и др.)
  • Поддерживает передачу данных через параметры, console для логирования и async/await

Это рекомендуемый режим по умолчанию, подходящий для чистых вычислений и логики обработки данных, обеспечивающий наивысший уровень изоляции безопасности.

Небезопасный режим (поддержка модулей)

Когда WORKFLOW_SCRIPT_MODULES настроена, скрипты переключаются на встроенный движок vm Node.js для обеспечения возможности использования require.

Предупреждение безопасности

В небезопасном режиме, хотя скрипты выполняются в песочнице vm с ограниченным списком разрешённых модулей, модуль vm Node.js не является безопасным механизмом песочницы. Включение этого режима подразумевает доверие ко всем пользователям, имеющим права на редактирование скриптов рабочих процессов. Администраторы должны самостоятельно оценить риски безопасности и строго контролировать список разрешённых модулей и права на редактирование рабочих процессов.

В скрипте можно использовать модули в соответствии со стандартом CommonJS, используя директиву require() для импорта модулей.

Поддерживаются нативные модули Node.js и модули, установленные в node_modules (включая зависимости, уже используемые NocoBase). Модули, которые должны быть доступны для использования в коде, необходимо объявить в переменной среды приложения WORKFLOW_SCRIPT_MODULES. Несколько имен пакетов разделяются запятыми, например:

WORKFLOW_SCRIPT_MODULES=crypto,timers,lodash,dayjs
Примечание

Модули, не объявленные в переменной среды WORKFLOW_SCRIPT_MODULES, не могут быть использованы в скрипте, даже если они являются нативными для Node.js или уже установлены в node_modules. Эта политика позволяет на уровне эксплуатации контролировать список модулей, доступных пользователям, и в некоторых сценариях предотвращать чрезмерные права доступа скриптов.

В среде, где развертывание выполнено не из исходного кода, если какой-либо модуль не установлен в node_modules, вы можете вручную установить необходимый пакет в каталог storage. Например, для использования пакета exceljs выполните следующие действия:

cd storage
npm i --no-save --no-package-lock --prefix . exceljs

Затем добавьте относительный (или абсолютный) путь к этому пакету, основанный на текущем рабочем каталоге приложения (CWD), в переменную среды WORKFLOW_SCRIPT_MODULES:

WORKFLOW_SCRIPT_MODULES=./storage/node_modules/exceljs

После этого вы сможете использовать пакет exceljs в своем скрипте (имя, используемое в require, должно точно совпадать с указанным в переменной среды):

const ExcelJS = require('./storage/node_modules/exceljs');
// ...

Список возможностей

Версия Node.js

Соответствует версии Node.js, на которой работает основное приложение.

Глобальные переменные

Не поддерживаются глобальные переменные, такие как global, process, __dirname и __filename.

console.log(global); // will throw error: "global is not defined"

Входные параметры

Параметры, настроенные в узле, становятся глобальными переменными в скрипте и могут быть использованы напрямую. Параметры, передаваемые в скрипт, поддерживают только примитивные типы, такие как boolean, number, string, object и массивы. Объект Date при передаче будет преобразован в строку формата ISO. Другие сложные типы, например, экземпляры пользовательских классов, не могут быть переданы напрямую.

Возвращаемое значение

С помощью оператора return можно вернуть данные примитивных типов (по тем же правилам, что и для параметров) в узел в качестве его результата. Если оператор return не вызывается в коде, выполнение узла не будет иметь возвращаемого значения.

return 123;

Вывод (Лог)

Поддерживается использование console для вывода логов.

console.log('hello world!');

При выполнении рабочего процесса вывод узла скрипта также записывается в файл логов соответствующего рабочего процесса.

Асинхронность

Поддерживается использование async для определения асинхронных функций и await для их вызова. Поддерживается использование глобального объекта Promise.

async function test() {
  return Promise.resolve(1);
}

const value = await test();
return value;

Таймеры

Если вам необходимо использовать такие методы, как setTimeout, setInterval или setImmediate, их нужно импортировать из пакета timers Node.js (доступно только в небезопасном режиме).

const { setTimeout, setInterval, setImmediate, clearTimeout, clearInterval, clearImmediate } = require('timers');

async function sleep(time) {
  return new Promise((resolve) => setTimeout(resolve, time));
}

await sleep(1000);

return 123;