Развёртывание на сервере
Развёртывание — перенос приложения на сервер, где оно работает круглосуточно и доступно по домену. Для Node.js-приложения нужны три вещи: режим production, менеджер процессов, который перезапустит сервер после сбоя, и обратный прокси — веб-сервер, который принимает запросы из интернета и передаёт их приложению.
Режим production
Переменная окружения NODE_ENV=production включает в Express рабочий режим: шаблоны кешируются, а стандартная страница ошибки не показывает стек вызовов. Её же читает наш src/config.js, чтобы включить безопасные cookie и подробный журнал.
Подготовка на сервере
На сервере должен быть установлен Node.js 22 или новее. Скопируйте проект через Git и установите только рабочие зависимости:
git clone https://github.com/anna/blog.git
cd blog
npm ci --omit=devnpm ci ставит точно те версии, что записаны в package-lock.json, а --omit=dev пропускает пакеты для разработки вроде supertest. Файл .env создайте на сервере вручную, с новыми длинными секретами.
Менеджер процессов pm2
Если запустить npm start в терминале, сервер остановится вместе с сессией SSH и не поднимется после сбоя. pm2 держит приложение запущенным:
npm install --global pm2
NODE_ENV=production pm2 start src/server.js --name blog --node-args="--env-file=.env"
pm2 save
pm2 startuppm2 save запоминает список приложений, а pm2 startup печатает команду, после выполнения которой pm2 будет запускаться вместе с сервером.
| Команда | Что делает |
|---|---|
pm2 status | Список приложений и их состояние |
pm2 logs blog | Журнал приложения в реальном времени |
pm2 restart blog | Перезапуск, например после обновления кода |
pm2 stop blog | Остановка |
Обратный прокси nginx
Приложение слушает порт 3000 только на самом сервере, а nginx принимает запросы на 80-м и 443-м портах, занимается HTTPS-сертификатами и передаёт запросы дальше. Файл сайта, например /etc/nginx/sites-available/blog:
server {
listen 80;
server_name example.com;
location / {
proxy_pass http://127.0.0.1:3000;
proxy_set_header Host $host;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
}
}После включения сайта и перезагрузки nginx блог откроется по адресу http://example.com. HTTPS-сертификат бесплатно выдаёт Let's Encrypt через утилиту certbot.
Доверие прокси
Теперь все запросы приходят в Express от nginx, и req.ip показывает 127.0.0.1. Скажите Express, что перед ним один прокси, которому можно верить:
// src/app.js
app.set('trust proxy', 1);Express начнёт брать адрес посетителя и протокол из заголовков X-Forwarded-For и X-Forwarded-Proto. Без этого не будут работать ограничение частоты по IP и cookie с флагом secure.
Обновление
git pull
npm ci --omit=dev
pm2 restart blogЧастая ошибка
Не запускайте Node.js-приложение от пользователя root и не открывайте порт 3000 наружу. Приложение должно быть доступно только через nginx: так весь трафик проходит через HTTPS, а ошибка в коде не даст злоумышленнику прав администратора на сервере.