📦
Хостинг

Next.js standalone build: меньше ресурсов и деплой на маленький сервер

10.11.2026
← Все статьи

Next.js-проект, развёрнутый обычным способом, требует на сервере всю папку node_modules. В ней сотни пакетов, нужных для сборки, но никогда не используемых во время работы: TypeScript, линтеры, тестовые библиотеки и прочее. На маленьком VPS это занимает место на диске, удлиняет деплой и утяжеляет Docker-образы. Режим standalone решает именно эту проблему: во время сборки Next.js отслеживает файлы, которые приложение действительно использует, и собирает их в отдельную папку.

Как работает standalone

При сборке Next.js анализирует, какие модули импортирует каждая страница и каждый API route. Если standalone включён, появляется папка .next/standalone. В ней лежит минимальный server.js и урезанный node_modules только с нужными пакетами. Эта папка не нуждается в команде next start и запускается обычным node server.js. Поэтому на сервер достаточно перенести только её, а не весь проект.

Включаем standalone

Настройка занимает одну строку. Добавьте параметр output в next.config.js или next.config.mjs и пересоберите проект.

// next.config.mjs
const nextConfig = {
  output: "standalone",
};

export default nextConfig;
npm ci
npm run build
ls .next/standalone

После сборки в .next/standalone окажутся server.js, package.json, node_modules и вложенная папка .next. Чтобы сравнить объём, выполните du -sh node_modules .next/standalone: разница зависит от проекта, но обычно заметна.

Самый забываемый шаг: public и static

Две вещи в папку standalone автоматически не попадают: папка public и CSS- и JavaScript-чанки из .next/static. Next.js оставляет их намеренно, считая, что отдавать такие файлы напрямую через Nginx или CDN эффективнее. Если их не скопировать, сайт откроется, но без стилей, без картинок и с неработающими кнопками. Именно здесь чаще всего ошибаются в первый раз.

cp -r public .next/standalone/
cp -r .next/static .next/standalone/.next/

Хорошая привычка — добавить эти команды в скрипт сборки, чтобы не забывать о них при следующих деплоях. В package.json это можно сделать так.

"scripts": {
  "build": "next build",
  "postbuild": "cp -r public .next/standalone/ && cp -r .next/static .next/standalone/.next/"
}

Запуск на сервере

Standalone-сервер берёт порт и адрес из переменных окружения. PORT задаёт порт, HOSTNAME — адрес, на котором слушать. За Nginx безопаснее указать 127.0.0.1, а внутри Docker нужен 0.0.0.0.

cd /var/www/misol-next/.next/standalone
PORT=3000 HOSTNAME=127.0.0.1 NODE_ENV=production node server.js

Для постоянной работы удобен ecosystem-файл PM2: приложение держится в фоне, поднимается после падения и перезапускается при превышении лимита памяти.

// ecosystem.config.js
module.exports = {
  apps: [{
    name: "misol-next",
    cwd: "/var/www/misol-next/.next/standalone",
    script: "server.js",
    max_memory_restart: "400M",
    env: { NODE_ENV: "production", PORT: 3000, HOSTNAME: "127.0.0.1" }
  }]
};

Сборка вне сервера

Главное преимущество standalone в том, что собрать проект можно на мощном компьютере или в CI, а на сервер отправить готовую папку. Маленький VPS больше не страдает от нехватки памяти при сборке и только запускает готовое приложение. Важное условие одно: операционная система и архитектура процессора сборочной машины должны совпадать с серверными, потому что в некоторых пакетах, например в sharp для обработки изображений, есть платформозависимые бинарники.

npm run build
tar -czf release.tar.gz -C .next/standalone .
scp release.tar.gz deploy@example.uz:/var/www/misol-next/releases/

Standalone и Docker

В Docker standalone особенно полезен: в финальном образе остаются только нужные для работы файлы. Ниже упрощённый многоэтапный Dockerfile: на первом этапе идёт сборка, на втором копируется только результат.

FROM node:20-alpine AS build
WORKDIR /app
COPY package*.json ./
RUN npm ci
COPY . .
RUN npm run build

FROM node:20-alpine
WORKDIR /app
ENV NODE_ENV=production PORT=3000 HOSTNAME=0.0.0.0
COPY --from=build /app/.next/standalone ./
COPY --from=build /app/.next/static ./.next/static
COPY --from=build /app/public ./public
EXPOSE 3000
CMD ["node", "server.js"]

Практический пример: мебельный магазин в Намангане

Мебельный магазин в Намангане держит сайт-каталог на Next.js на маленьком VPS с 1 ГБ памяти. Раньше сборка шла прямо на сервере, память каждый раз заканчивалась, и сайт на несколько минут переставал отвечать. После перехода на standalone проект собирается на компьютере разработчика, на сервер отправляется готовый архив, а PM2 перезагружает приложение. Вместо всего node_modules на сервере теперь лежат только нужные пакеты, а деплой занимает меньше минуты.

Частые проблемы

Если хотите запустить Next.js на сервере с небольшими ресурсами, хороший старт — маленький VPS в кабинете sayt.uz и режим standalone. Если ресурсов станет не хватать, тариф можно будет увеличить позже.

Похожие статьи

🚦 Ошибка «Too many connections» в MySQL: причины и решение 📁 Подключение к хостингу по SFTP через FileZilla и WinSCP 🗄️ Как создать базу данных и пользователя в ISPmanager 🔤 utf8mb4: как сохранить эмодзи и узбекские буквы в MySQL без искажений
🌐 Язык
🇺🇿 O'zbek 🇺🇿 Ўзбек 🇷🇺 Русский ✓ 🇬🇧 English