Обновить

Приложение течёт, а утечки нет: как оптимизатор картинок Next.js съел 4-гигабайтный VPS

Уровень сложностиСредний
Время на прочтение7 мин
Охват и читатели7.9K
Всего голосов 3: ↑3 и ↓0+5
Комментарии2

Комментарии 2

жирная тема. а как лимиты настроили для процессов?

Двумя drop-in’ами к юниту, чтобы не трогать основной файл сервиса.

/etc/systemd/system/iwant-next.service.d/memory.conf:

[Service]
MemoryHigh=800M
MemoryMax=1G
Restart=always

/etc/systemd/system/iwant-next.service.d/perf.conf:

[Service]
Environment=MALLOC_ARENA_MAX=2
Environment=VIPS_CONCURRENCY=1

Разница между двумя лимитами тут принципиальна. MemoryHigh - мягкий: cgroup начинает давить на процесс и агрессивно отбирать память, но не убивает. MemoryMax - жёсткий потолок, за ним прилетает OOM внутри cgroup, и уже Restart=always поднимает сервис. То есть MemoryHigh стоит ниже намеренно: он тормозит рост до того, как дело дойдёт до убийства, и пользователь видит замедление, а не пятисотку.

Числа брал не из головы: под нагрузкой с правильными аренами RSS держится 300–430 МБ, так что 800 МБ - примерно двукратный запас, а 1 ГБ - граница, за которой на этой машине начинает страдать Postgres и соседние приложения (4 ГБ на всё).

Кстати, после перезапуска сервис под трафиком возвращается к самому MemoryHigh за пару минут и дальше живёт, упираясь в потолок. Это нормальное поведение cgroup - в лимит утрамбовывается в том числе то, что можно отдать под давлением. Поэтому «сидит на 800 МБ» здесь не означает «ему нужно 800 МБ».

И главное: лимиты - это страховка, а не лечение. Память перестала расти от MALLOC_ARENA_MAX=2, а не от них. Если поставить только лимиты, получите бесконечный цикл «раздулся - убили - поднялся».

Проверить, что применилось:

systemctl show iwant-next -p MemoryHigh -p MemoryMax -p Environment
systemctl status iwant-next   # строка Memory: с пиком

А вы на чём сейчас упираетесь: в рост RSS или в OOM-килы?

Зарегистрируйтесь на Хабре, чтобы оставить комментарий

Публикации