Недавно я столкнулся с неожиданной проблемой - у меня появились задублированные медиатеки в Emby. Нет, конечно, они появились не сами по себе, я приложил к этому руку, проще говоря, сам создал их, но то, как это все получилось, должно снять с меня "обвинения", хотя бы частично. Итак, обо всем по порядку.

Я довольно давно использую Emby в качестве основного медиасервиса. Весь контент у меня разбит на несколько медиатек - есть медиатека с сериалами, зарубежными и нашими фильмами, мультфильмами и так далее. Решил я создать еще одну медиатеку - для документальных и научно-популярных фильмов, и, заодно, добавить дополнительный каталог в медиатеку отечественного кино.

С первой задачей я справился быстро и без каких-либо проблем - создал медиатеку, привязал к ней каталоги, в которых и содержался нужный контент, задал вспомогательные параметры - тип контента, scraper, в общем, сделал все необходимое. А вот со вторым пунктом случилась незадача - при добавлении нужного каталога возникала ошибка.

Сейчас я уже не помню точный текст сообщения, но его суть сводилась к тому, что я не могу добавить выбранный каталог, возможно потому, что не хватает прав. Каких прав может не хватать? Я только что создал медиатеку и добавил в нее каталоги, один из которых - непосредственный сосед нужного мне сейчас каталога. Ну да ладно. Такие сообщения время от времени возникают и, чаще всего, проблема кроется в чем-то другом, а не в правах.

Правда вот разобраться в истинных причинах бывает иногда сложно и работа эта может потребовать много времени и усилий. Но, частенько, рядом может лежать решение, лёгкое и простое, позволяющее обойти возникшие трудности без существенных затрат. Для таких решений даже существует специальный термин - workaround, переводится, как обходной путь, хотя есть и такой вариант: временное решение. Ну да, конечно, самое что ни на есть временное 😏.

Так было и в этот раз, и я смалодушничал - выбрал простой путь (знал бы я, к чему это может привести 😉). Что это был за обходной путь? Всё очень просто - я решил создать новую медиатеку для отечественных фильмов, включив в нее как старые каталоги, так и новый, а старую - просто удалить. Да, я понимал, что такой подход потребует пересканировать содержимое каталогов для обновления базы, но фильмов в этой категории у меня не так много, так что мне казалось, что с этим неудобством можно и смириться.

Начал я свой обходной манёвр с удаления старой медиатеки:

  • зашел в панель управления сервером
    Выбраем нужный пункт меню
  • выбрал работу с медиатеками
    И снова нужный пункт меню
  • дал команду удалить нужную медиатеку
    Хотим удалить

Казалось бы, что может пойти не так? Сейчас расскажу. После выполнения приведенной выше последовательности действий ничего не произошло: ни сообщений об ошибках, ни удаления медиатеки. Ни-че-го. Вот тут бы мне насторожиться и начать по-настоящему разбираться с проблемами, ведь второй сбой - это уже более серьёзный повод задуматься о том, что они есть. Но... лезть в журнал, включать (возможно) отладочную информацию и вот это вот всё, по-прежнему, не хотелось. И я переключился на создание новой медиатеки.

  • Выбрал нужный элемент интерфейса:
    Добавляем медиатеку
  • Конечно, указал тип содержимого:
    Тип содержимого медиатеки
  • Добавил каталоги (они у меня примонтированы с различных устройств):
    Указываем каталоги
  • Повключал все, какие возможны, загрузчики метаданных:
    Включил scraper-ы
  • Установил еще кое-какие параметры:
    Различные настройки
  • И в конце, как водится, нажал Ok для сохранения:
    Сохранение медиатеки

Как вы думаете, что произошло потом? Правильно - ничего. Именно так, ничего. То есть экран не сменился, ошибок не появилось. И я еще раз нажал Ок. И еще. В общей сложности, я успел нажать шесть раз на эту самую кнопку Ok. И экран сменился. Теперь, в списке медиатек я мог наблюдать три элемента с отечественными фильмами - один старый, который не удалился, и два новых. Но это еще не все! На главном экране Emby у меня красовалось целых семь элементов - один старый и шесть новых! Жаль, screenshot-ов я не сделал 🙁.

Ладно, думаю, удалю-ка я ненужные дубликаты. И что вы думаете, получилось у меня? Правильно, нет! Правда, на этот раз мне выдалось сообщение, что удалить медиатеку нельзя из-за ошибки. Я, конечно, повторил попытку, но не смотря на то, что я пробовал разные элементы (речь, конечно, про вновь созданные) результат был один и тот же.

В общей сложности, это был сбой номер четыре, и я полез в журнал. А там, на каждую мою попытку удаления медиатеки, было по соощению об ошибке:

System.NullReferenceException: Object reference not set to an instance of an object

Поиск в Гугле не особо прояснил ситуацию, я лишь понял, что такие ошибки случаются и причины возникновения могут быть весьма разнообразны. Кстати, поиск по "emby duplicate media folders" оказался чуть более полезным, и практически вывел меня на нужный ответ. Проблема заключалась лишь в том, что там предлагалось медиатеки удалить, а это именно то действие (удаление медиатеки), которое и приводило меня к получению ошибки System.NullReferenceException. На самом деле, становилось понятно, что надо что-то делать с самой медиатекой, то есть, с ее представлением в Emby.

Где может храниться информация о медиатеках? Первой моей мыслью было - в базе данных. Ну я бы поступил именно так. Я знал, что у Emby есть БД, построенная на SQLite, и, на мой взгляд, логичнее всего было бы все, что касается библиотеки контента, хранить именно в ней. Файлы БД размещены в подкаталоге data каталога config:
Содержимое каталога config/data
который, в свою очередь, примонтирован в контейнер - вот соответствующий фрагмент файла docker-compose.yml:

...
  volumes:
    - /home/emby/vol/config:/config
...

Само собой, после того, как в этом каталоге (config/data) я обнаружил файл library.db, сомнений по поводу того, что я нахожусь на правильном пути, у меня практически не осталось.

Я скачал и установил программу для работы с БД SQLite SQLite Studio, остановил сервер Emby, сделал резервную копию файла library.db (на всякий случай) и стал его исследовать. Что сказать. Уже в который раз я убеждаюсь в том, что мои представления о том, как должен писаться софт и как должны быть организовываны данные, не вполне совпадают с представлениями авторов ПО[1]. Проведя пару часов за исследованием БД - чтобы быть уверенным, что ничего не упустил - я окончательно понял, что ищу не там.

После такого (неутешительного для себя) вывода, я стал внимательнее изучать структуру каталогов. И вот что мне удалось найти:
Каталог с медиатеками
Это было то, что нужно - каталог, содержащий подкаталоги, описывающие медиатеки. Содержимое на тот момент было немного другим - там, например, было два новых каталога для отечественных фильмов, названия которых несколько отличались - один назывался Наши фильмы, другой - Наши фильмы1. При этом, в интерфейсе Emby названия не отличались, что говорило о том, что какие-то метаданные, все-таки, лежат где-то еще[2].

После такой находки оставалось совсем немного. Я удалил (на самом деле, переместил) старый и один (лишний) новый (из двух) каталог и произвел сканирование библиотеки:
Сканирование медиатек
После завершения процесса сканирования у меня в списке медиатек осталась одна медиатека с отечественными фильмами, и три элемента Наши фильмы на главном экране. Дополнительные пересканирования не смогли убрать это затроение, поэтому я переместил оставшийся каталог в безопасное место и снова пересканировал медиатеки, после чего в интерфейсе Emby не осталось никаких упоминаний о некогда существоваших медиатеках с отечественными фильмами. Затем я, уже в интерфейсе Emby, добавил новую медиатеку и отсканировал контент. После чего все, наконец-то, встало на свои места.

Что же все-таки произошло у меня? Я так думаю, что в работе сервера была какая-то нестабильнось, вызванная, возможно, какими-то проблемами в моей инфраструктуре - может, место в очередной раз заканчивалось, может, "отвалились" какие-нибудь подмонтированные каталоги, или процессор планшета-трансформара (читай, сервера) был загружен из-за антивируса - сейчас, задним числом, можно только гадать. Из-за этой нестабильности диалог создания новой медиатеки "подвис", что позволили мне несколько раз (а точнее, шесть) попытаться его закрыть с сохранением. Так как авторам Emby уже поступала жалоба на появление дубликатов, они, как и обещали, провели работу над ошибками. Но, видимо, у меня создались, как это часто бывает, какие-то особенные условия, из-за которых код отработал как-то не так. В результате этого, в списке медиатек создались-таки дублирующиеся записи, а на главном экране появились все шесть элементов, причем, три из них оказались привязанными к одной медиатеке, а три других - к другой. Из-за такой кривой привязки при удалении возникала ошикба System.NullReferenceException. Как результат, мне пришлось углубляться во "внутренности" Emby.

В любом случае, история закончилась благопоолучно, что не может не радовать. На этом пока всё.


  1. Был еще опыт, связанный с БД Kodi, и, в конце концов, я решил, что для авторов такого ПО вовсе не важно, как организована база данных, главное для них, что данные как-то хранятся. ↩︎

  2. Потом я нашел, где - в самом каталоге медиатеки есть файл options.xml, в котором хранятся настройки данной конкретной медиатеки, в том числе и название (в теге Name) ↩︎