Исполняемые файлы Node.js: от запуска до упаковки
node.exe: варианты использования и создание автономного исполняемого файла
Основной способ работы с Node.js – запуск скрипта через исполняемый файл node (на Windows node.exe). Команда
node myscript.jsNode js exe (node.js exe)
загружает и выполняет JavaScript-код из указанного файла. При этом Node.js инициализирует среду выполнения, подгружает встроенные модули и выполняет код в соответствии с циклом событий (event loop).Как выполнить простой скрипт с помощью node.exe?
Создайте файл hello.js с содержимым:
console.log('Привет из Node.js!');Затем в командной строке выполните:
node hello.jsПривет из Node.js!
Важно, чтобы утилита node была доступна в переменной PATH. Если после установки Node.js команда не найдена, проверьте путь установки и добавьте его вручную.
Типичная ошибка:
При запуске файла с расширением .js, но содержащего синтаксическую ошибку, Node.js выведет стек ошибки и завершит выполнение с ненулевым кодом. Например:
console.log('Hello'
)SyntaxError: Unexpected end of input
Решение – проверять код на наличие синтаксических ошибок перед запуском с помощью node --check.
Цель использования: стандартный запуск серверных, утилитных или CLI-приложений на Node.js. Подходит для большинства сценариев, когда на целевой машине уже установлена среда выполнения.
Как выполнять код Node.js в интерактивном режиме (REPL)?
Запустите node без аргументов, откроется REPL (Read-Eval-Print Loop):
nodeWelcome to Node.js v20.11.0. Type ".help" for more information. >
В этом режиме можно писать и сразу выполнять выражения:
> 2 + 2
4
> const fs = require('fs');
undefined
> fs.readdirSync('.').length
15Для выхода используйте .exit или Ctrl+C дважды.
Проблема:
В REPL нельзя использовать import (ES-модули) без дополнительных флагов. Вместо этого применяйте require или запускайте REPL с флагом --experimental-repl-await и используйте динамический импорт.
Цель: быстрое тестирование фрагментов кода, изучение API модулей, отладка небольших алгоритмов.
Как выполнить короткий скрипт без создания файла?
Флаг -e (eval) позволяет передать код прямо в командной строке:
node -e "console.log(process.version)"v20.11.0
Можно объединять несколько выражений в одну строку:
node -e "const os = require('os'); console.log(os.platform(), os.arch())"win32 x64
Для многострочного кода используйте обратный слэш для переноса строки (в bash) или пишите в одном абзаце.
Ошибка:
Кавычки внутри строки экранируются по-разному в зависимости от ОС. В Windows cmd рекомендуется использовать двойные кавычки снаружи, а внутри – одинарные или экранированные двойные. В PowerShell возможно потребуется обратный слэш. Например, в cmd:
node -e "console.log('hello \"world\"')"Если экранирование неверное, Node.js получит некорректный синтаксис.
Цель: запуск однострочных команд, проверка версий, быстрые вычисления, автоматизация CI/CD скриптов.
Как передать аргументы командной строки в скрипт?
После имени файла можно указать произвольные аргументы, которые попадут в process.argv. Создайте файл args.js:
console.log(process.argv);Запустите с аргументами:
node args.js --name=World --greet[ 'C:\\Program Files\\nodejs\\node.exe', 'C:\\project\\args.js', '--name=World', '--greet' ]
Первый элемент – путь к node.exe, второй – путь к скрипту, остальные – переданные аргументы. Для удобного разбора аргументов используйте пакет yargs или commander.
Типичная ошибка:
Попытка использовать process.argv для получения значений флагов без анализа. Ошибка – индекс 2 всегда считается первым аргументом, но порядок может быть нарушен, если скрипт вызывается с флагами самого node (например, --inspect). Рекомендуется использовать process.argv.slice(2).
Цель: создание командных утилит, настройка поведения скрипта при запуске, передача конфигураций.
Как отлаживать скрипт Node.js с помощью встроенного отладчика?
Node.js включает в себя встроенный отладчик на основе протокола Chrome DevTools. Запустите скрипт с флагом --inspect:
node --inspect mydebug.jsDebugger listening on ws://127.0.0.1:9229/... For help, see: https://nodejs.org/en/docs/inspector
Откройте в браузере Chrome страницу chrome://inspect и выберите удалённую цель. Появится полноценный отладчик с точками остановки, просмотром переменных и стека. Альтернативно можно использовать CLI-отладчик с флагом inspect (без двух дефисов):
node inspect mydebug.jsУстановите точку остановки в коде командой debugger;:
function compute(a, b) {
debugger;
return a + b;
}
console.log(compute(3, 4));Проблема:
Если порт 9229 занят, отладчик не запустится. Укажите другой порт: node --inspect=9230 app.js. Также при использовании контейнеров или удалённых машин может потребоваться разрешить подключения с других хостов: --inspect=0.0.0.0:9229.
Цель: глубокая отладка серверных приложений, анализ утечек памяти, профилирование.
Как упаковать Node.js приложение в один исполняемый exe файл?
Иногда требуется распространять приложение без необходимости устанавливать Node.js отдельно. Для этого используют инструменты, создающие standalone exe, включающие среду выполнения и код. Два популярных решения – pkg (от Vercel) и nexe.
Рассмотрим pkg. Установите его глобально:
npm install -g pkgСоздайте файл server.js:
const http = require('http');
http.createServer((req, res) => {
res.end('Hello from packaged app!');
}).listen(3000, () => console.log('Server running on port 3000'));Затем запустите сборку:
pkg server.js --targets win-x64 --output myserver.exeФлаг --targets задаёт платформу (win, linux, macos) и архитектуру. В результате будет создан файл myserver.exe размером около 60 МБ (включает полную среду Node.js).
Типичные ошибки pkg:
1. Dynamic require – pkg не может обработать строки с require, собираемые динамически (например, require(someVariable)). Решение – явно указать все необходимые модули в опции assets или использовать статические импорты. 2. Ошибка "Cannot find module" – если модуль не был загружен из main файла, его нужно добавить в конфигурацию pkg через pkg.assets в package.json. 3. Пути к файлам – после упаковки __dirname и __filename указывают внутрь виртуальной файловой системы. Для доступа к файлам, расположенным рядом с exe, используйте path.join(__dirname, 'resource').
Цель: распространение настольных приложений, CLI-утилит, серверов без установки runtime, развертывание на чистых серверах.
Расширенные примеры работы с node.exe и создания exe
Пример 1. Запуск HTTP-сервера с аргументами порта
Создайте файл server-args.js:
const http = require('http');
const port = parseInt(process.argv[2], 10) || 3000;
const server = http.createServer((req, res) => {
res.writeHead(200, {'Content-Type': 'text/plain'});
res.end('Server running on port ' + port);
});
server.listen(port, () => {
console.log('Listening on port', port);
});Запустите с указанием порта:
node server-args.js 4000Listening on port 4000
Откройте в браузере http://localhost:4000. Если аргумент не передан, сервер стартует на порту 3000.
Пример 2. Использование process.env для конфигурации
Создайте config-app.js:
const http = require('http');
const port = process.env.PORT || 8080;
const message = process.env.MESSAGE || 'Default message';
http.createServer((req, res) => {
res.end(message);
}).listen(port, () => console.log('Server on', port));Запустите с установленными переменными (в cmd):
set PORT=5000 && set MESSAGE=HelloFromEnv && node config-app.jsServer on 5000
В Windows PowerShell используйте $env:PORT=5000. Такой подход удобен для контейнеризации и CI/CD.
Пример 3. Упаковка приложения с помощью nexe
Установите nexe:
npm install -g nexeПодготовьте файл cli.js – простую CLI-утилиту:
#!/usr/bin/env node
const [,, ...args] = process.argv;
console.log('Arguments received:', args);Соберите исполняемый файл:
nexe cli.js -t windows-x64-20.11.0 -o mycli.exeПараметр -t задаёт целевую платформу и версию Node.js (можно опустить, nexe выберет подходящую). Проверьте сборку:
mycli.exe hello worldArguments received: [ 'hello', 'world' ]
Важно: nexe требует компилятор C++ (Visual Studio Build Tools на Windows), если не используется предварительно собранный бинарник. При возникновении ошибок установите windows-build-tools.
Пример 4. Запуск отладчика с точкой остановки в REPL
Можно войти в режим отладки прямо из REPL. Запустите node inspect и затем используйте команды:
node inspect
> .load test.js
> debugger
> contОднако чаще используют файл. Создайте debug-sample.js:
function factorial(n) {
if (n <= 1) return 1;
debugger;
return n * factorial(n - 1);
}
factorial(5);Запустите отладчик:
node inspect debug-sample.jsПошагово пройдите по рекурсии с командами next, step, watch.
Пример 5. Комбинация флагов: проверка синтаксиса и выполнение
Используйте --check, чтобы проверить файл без выполнения:
node --check app.jsЕсли ошибок нет, ничего не выводится. Если есть – покажет синтаксическую ошибку. Это удобно в pre-commit хуках.
node --check -e "console.log('valid')"Флаг --harmony включает экспериментальные возможности V8 (например, --harmony-array-flat).
Пример 6. Использование process.stdin в конвейере
Создайте transform.js – утилита, преобразующая текст в верхний регистр:
process.stdin.setEncoding('utf8');
let data = '';
process.stdin.on('readable', () => {
let chunk;
while ((chunk = process.stdin.read()) !== null) {
data += chunk;
}
});
process.stdin.on('end', () => {
process.stdout.write(data.toUpperCase());
});Запустите с перенаправлением ввода:
echo "hello node" | node transform.jsHELLO NODE
На Windows перенаправление работает в cmd, в PowerShell используйте Get-Content input.txt | node transform.js.
Пример 7. Упаковка приложения с помощью pkg и встроенных ресурсов
Создайте readme.txt рядом с скриптом. В скрипте resource-app.js:
const fs = require('fs');
const path = require('path');
const content = fs.readFileSync(path.join(__dirname, 'readme.txt'), 'utf8');
console.log(content);Обновите package.json, добавив секцию pkg:
{
"name": "resource-app",
"pkg": {
"assets": "readme.txt"
}
}Затем соберите:
pkg resource-app.js --targets win-x64 --output resource-app.exeТеперь exe содержит readme.txt внутри. При запуске он будет извлечён во временную папку (но для чтения это прозрачно).
Для более сложных случаев (загрузка динамических модулей) используйте pkg.scripts с перечислением всех JS-файлов.