MAATRIX / Блог / Сколько RAM нужно для Navidrome

Сколько RAM нужно для Navidrome

MAATRIX

Navidrome — самый лёгкий способ поднять личный аналог Spotify из собственной музыки: один Go-бинарник, встроенная SQLite, без отдельной базы данных и без видео-транскодирования, которое обычно и раздувает требования у Jellyfin или Plex. В покое сервис укладывается в считаные сотни мегабайт, но два момента всё же дают заметный пик — первое сканирование библиотеки и одновременное транскодирование при стриминге на несколько устройств. Ниже — из чего складывается память Navidrome, сколько закладывать под свою коллекцию и как настроить лимиты, чтобы сервис не мешал остальным сервисам на том же VPS.

Обсудить статью, задать вопрос или начать новую тему

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

Перейти в сообщество →

Из чего складывается память Navidrome

Navidrome спроектирован иначе, чем большинство self-hosted медиасерверов, и это прямо влияет на требования к RAM:

  • Один процесс, один бинарник. В отличие от Jellyfin (несколько подсистем плюс FFmpeg-транскодер для видео) или Immich (четыре контейнера с ML и векторной базой), Navidrome — это единственный Go-процесс, который сам обслуживает и веб-интерфейс, и Subsonic API, и сканер библиотеки.
  • SQLite вместо внешней СУБД. База метаданных (треки, альбомы, плейлисты, история прослушиваний, полнотекстовый индекс поиска) хранится в одном файле SQLite прямо в томе /data. Не нужно поднимать и держать в памяти отдельный процесс MariaDB или PostgreSQL, как для Nextcloud или PhotoPrism — это одна из главных причин, почему Navidrome ощутимо легче своих аналогов.
  • Индексация тегов. При сканировании библиотеки Navidrome читает метаданные (ID3, Vorbis Comments, FLAC-теги) через встроенный парсер, извлекает обложки — встроенные в файл или лежащие рядом как cover.jpg — и пишет всё это в базу.
  • Транскодирование по требованию. Если клиент запрашивает поток не в исходном формате (например, мобильное приложение просит битрейт 128 kbps вместо оригинального FLAC, чтобы сэкономить трафик), Navidrome на лету запускает внешний процесс ffmpeg. Это отдельный процесс на каждый активный транскодируемый поток, а не встроенная функция самого Go-бинарника.
  • Кеш транскодированных файлов. Результат транскодирования по умолчанию кешируется на диске, чтобы повторный запрос того же трека в том же формате не гонял ffmpeg заново — экономит CPU при повторных прослушиваниях, но не сам факт разового транскодирования.

Совокупность этого объясняет, почему Navidrome спокойно живёт на 512 МБ – 1 ГБ для личной коллекции, но требует явного запаса, если библиотека большая или слушателей несколько.

Сканирование библиотеки — где сервер проседает

Первое подключение папки с музыкой — момент, когда Navidrome делает больше всего работы за раз. Sканер обходит файловую систему, читает теги каждого трека, извлекает обложки и пишет записи в SQLite с построением полнотекстового индекса для поиска по названию, исполнителю и альбому.

Что определяет размер пика:

  1. Количество файлов, а не их объём на диске. Сканирование 50 000 файлов по 3 МБ каждый нагружает сервер сильнее, чем 5 000 файлов по 40 МБ (lossless-альбомы) — потому что операция идёт по каждому файлу отдельно: открыть, прочитать теги, записать в БД.
  2. Плотность метаданных. Файлы с богатыми тегами (расширенные ID3v2 с обложками высокого разрешения, лирикой, множественными жанрами) требуют больше памяти на разбор, чем минимально размеченные MP3 из старых рипов.
  3. Параллелизм сканера. Navidrome сканирует несколько файлов одновременно; чем больше ядер видит контейнер, тем выше параллелизм и тем заметнее кратковременный пик RAM во время самого сканирования.
  4. Первый полный скан против последующих. Начиная с версий с файловым наблюдателем (fsnotify), Navidrome отслеживает изменения в папке с музыкой и досканирует только новые или изменённые файлы — тяжёлый импорт всей коллекции происходит по сути один раз, при первом запуске или при полном пересканировании (ND_SCANSCHEDULE/принудительный full scan).

На практике для личной коллекции пик сканирования редко превышает 400–600 МБ сверх состояния покоя, даже на библиотеках в десятки тысяч треков — SQLite и текстовые метаданные заметно легче, чем фото или видео с их бинарными индексами.

Нужен сервер под эту задачу?

Разверните VPS MAATRIX за пару минут: NVMe, AMD EPYC, root-доступ, локации UK, США, Франция и РФ. Оплата картой РФ и по СБП.

Арендовать сервер

Транскодирование потоков — вторая точка нагрузки

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

Когда транскодирование включается на практике:

  • Мобильное приложение на мобильной сети. Клиенты вроде Symfonium, DSub, Substreamer или Amperfy по умолчанию просят пониженный битрейт для экономии трафика — это заставляет Navidrome транскодировать даже небольшие MP3, если исходный битрейт выше запрошенного.
  • Формат, который не поддерживает клиент. Не все Subsonic-клиенты одинаково хорошо работают с FLAC или Opus — часть настроена запрашивать MP3 или AAC вне зависимости от исходника.
  • Веб-плеер в браузере на медленном канале. Встроенный веб-интерфейс Navidrome тоже может запрашивать транскодированный поток при соответствующей настройке качества.

Каждый активный запрос на транскодирование — это отдельный процесс ffmpeg, живущий, пока идёт передача потока. По памяти аудио-транскодирование значительно легче видео: один поток обычно укладывается в 30–80 МБ в зависимости от формата и битрейта, но при пяти-шести одновременных слушателях с включённым транскодированием это уже добавляет несколько сотен мегабайт к базовому потреблению — и именно этот сценарий, а не размер коллекции, чаще всего роняет сервер с минимальным тарифом.

Если все клиенты в сети настроены забирать оригинальный файл без изменения битрейта (например, домашняя сеть с хорошим Wi-Fi), транскодирование почти не происходит, и профиль нагрузки Navidrome остаётся близким к состоянию покоя даже при нескольких активных слушателях.

Сколько RAM закладывать по размеру коллекции

Ориентировочные цифры для Navidrome в Docker на Ubuntu 24.04, с учётом одновременного сканирования и до нескольких параллельных транскодируемых потоков. Точные значения зависят от плотности метаданных, формата файлов и настроек клиентов — это ориентир для выбора тарифа, а не гарантированный потолок.

Размер коллекцииRAM в покоеRAM при сканированииRAM с 2–4 транскодируемыми потоками
до 5 000 треков150–250 МБ300–400 МБ400–550 МБ
5 000–30 000 треков200–350 МБ400–700 МБ550–850 МБ
30 000–100 000 треков300–500 МБ700 МБ–1,2 ГБ800 МБ–1,3 ГБ
100 000+ треков / несколько библиотек500 МБ–1 ГБ1,2–2 ГБ1,3–2,5 ГБ

Для сравнения: даже крупная личная коллекция в 100 000+ треков по требованиям к памяти сопоставима с небольшой фотобиблиотекой в PhotoPrism на 20 000 фото — потому что Navidrome не работает с тяжёлыми бинарными данными вроде RAW-фото или видеокадров, только с текстовыми метаданными и звуковым потоком при транскодировании.

Диск считайте отдельно от RAM: сама музыка занимает место пропорционально формату (FLAC против MP3 — разница в разы), а кеш транскодированных файлов и база SQLite добавляют сверху обычно не больше нескольких процентов от объёма коллекции.

Docker-compose с лимитами памяти

Конфигурация для личной коллекции среднего размера с явными лимитами на контейнер — чтобы при скачке нагрузки (одновременное полное пересканирование и несколько активных слушателей) Navidrome упёрся в свой собственный лимит, а не забрал память у соседних сервисов на сервере:

services:
  navidrome:
    image: deluan/navidrome:latest
    container_name: navidrome
    restart: unless-stopped
    ports:
      - "4533:4533"
    environment:
      ND_SCANSCHEDULE: "1h"
      ND_LOGLEVEL: "info"
      ND_SESSIONTIMEOUT: "24h"
      ND_ENABLETRANSCODINGCONFIG: "true"
      ND_TRANSCODINGCACHESIZE: "1GB"
      ND_BASEURL: ""
    volumes:
      - "./data:/data"
      - "/path/to/music:/music:ro"
    deploy:
      resources:
        limits:
          memory: 768m
        reservations:
          memory: 128m

Музыкальную папку стоит монтировать в режиме :ro (только чтение) — Navidrome не изменяет исходные файлы, только читает теги. ND_TRANSCODINGCACHESIZE ограничивает размер дискового кеша транскодированных файлов: чем реже кеш промахивается, тем реже запускается новый процесс ffmpeg и тем реже случаются пики RAM. Названия переменных окружения у Navidrome со временем менялись между релизами, поэтому перед обновлением на новую версию стоит свериться с актуальным разделом конфигурации в документации проекта.

Общие принципы работы с лимитами памяти контейнеров — что происходит с сервисом при достижении лимита и как выбрать разумный запас — разобраны в статье про ресурсы и лимиты CPU и памяти в Docker.

Navidrome против Jellyfin и Plex: почему нужно меньше

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

NavidromeJellyfin / Plex
Тип контентаТолько аудиоВидео, аудио, фото
ТранскодированиеАудиопоток, лёгкий процесс ffmpegВидеотранскодирование — тяжёлый CPU/RAM-процесс, особенно без аппаратного ускорения
База данныхВстроенная SQLiteВстроенная база + собственный медиасканер с превью-кадрами для видео
Типичный минимум RAM512 МБ – 1 ГБ2–4 ГБ, больше при активном видеотранскодировании
Число процессов в поставкеОдин бинарникОдин процесс, но с более тяжёлым внутренним стеком под видео

Главный источник разницы — видео. Генерация превью-кадров, транскодирование под разные разрешения и битрейты — всё это у Jellyfin и Plex может съедать гигабайты RAM на один активный поток, особенно без GPU. Если нужна именно музыка, а не фильмы и сериалы, ставить ради этого полноценный медиасервер избыточно — разница в требованиях к серверу может быть пятикратной и больше. Сравнение по функциям и требованиям для видео есть в статье Jellyfin или Plex: что выбрать для сервера; а если кроме музыки хочется поднять на том же VPS личный фотоархив, по нагрузке на память это ближе к разбору в статье сколько RAM нужно для Immich — там своя фоновая нагрузка, но уже от машинного обучения, а не от видео.

Нужен сервер под эту задачу?

Разверните VPS MAATRIX за пару минут: NVMe, AMD EPYC, root-доступ, локации UK, США, Франция и РФ. Оплата картой РФ и по СБП.

Арендовать сервер

Нужны сами нейросети для контента?

Генерируйте изображения, видео и озвучку нейросетями на falapi.io — десятки моделей в одном окне. Оплата картой РФ и по СБП.

Частые вопросы

Хватит ли 512 МБ RAM для Navidrome?

Для небольшой личной коллекции (до нескольких тысяч треков) и одного слушателя без активного транскодирования — да, этого достаточно с небольшим запасом. Как только появляется параллельное транскодирование для нескольких устройств или библиотека вырастает до десятков тысяч треков, лучше закладывать от 1 ГБ.

Нужна ли отдельная база данных вроде PostgreSQL?

Нет, Navidrome использует встроенную SQLite и не поддерживает подключение внешней СУБД как основной вариант — это осознанное архитектурное решение разработчиков ради простоты развёртывания, и как раз то, что делает сервис заметно легче по памяти, чем аналоги на MariaDB или Postgres.

Растёт ли память пропорционально числу треков в библиотеке?

В состоянии покоя — незначительно: SQLite-файл растёт линейно с числом записей, но сам по себе не требует держать весь индекс в оперативной памяти. Заметный рост потребления даёт не число треков, а активность — сканирование новых файлов и число одновременных транскодируемых потоков.

Транскодирование обязательно, или можно всегда отдавать оригинал?

Транскодирование включается по запросу клиента или по настройке качества потока — если все ваши приложения настроены забирать оригинальный файл, ffmpeg почти не будет запускаться, и требования к RAM останутся близки к состоянию покоя.

Что будет, если контейнеру не хватит памяти при сканировании большой библиотеки?

Процесс Navidrome будет остановлен OOM-killer'ом (или Docker перезапустит его по restart policy), сканирование прервётся на середине и продолжится с точки останова при следующем запуске сканера — потери данных в базе обычно нет, но пересканирование всей библиотеки заново займёт время.

Обсудить статью, задать вопрос или начать новую тему

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

Перейти в сообщество →