Авторы Гуру Тахасильдар, Амир Зиаи, Джонатан Солорзано-Гамильтон, Келли Григгс, Ви Айенгар

Введение

Netflix использует машинное обучение, чтобы создавать лучшие медиафайлы для наших участников. Ранее мы поделились подробностями об одном из этих алгоритмов, представили, как наша команда разработчиков платформы развивает экосистему машинного обучения для конкретных медиа, и обсудили, как данные этих алгоритмов сохраняются в нашем сервисе аннотаций.

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

В частности, мы углубимся в архитектуру, обеспечивающую возможности поиска студийных приложений в Netflix. Мы обсуждаем конкретные проблемы, которые мы решили с помощью алгоритмов машинного обучения (ML), рассматриваем различные болевые точки, которые мы рассмотрели, и предоставляем технический обзор нашей новой платформы.

Обзор

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

Вот пример такого ассета, созданного для одной из наших игр:

Эти мультимедийные ресурсы или «дополнительные» ресурсы не возникают сами по себе. Их должны создавать художники и видеоредакторы. Мы создаем инструменты для авторов, чтобы эти коллеги могли сосредоточить свое время и энергию на творчестве. К сожалению, большая часть их энергии уходит на трудоемкую предварительную работу. Ключевой возможностью является автоматизация этих рутинных задач.

Случаи использования

Вариант использования №1: диалоговый поиск

Диалог является центральным аспектом повествования. Один из лучших способов рассказать увлекательную историю — это уста персонажей. Резкие или запоминающиеся реплики — главная цель редакторов трейлеров. Ручной метод выявления таких линий — наблюдение (также известное как пробой).

Редактор просматривает заголовок от начала до конца, расшифровывает запоминающиеся слова и фразы с временным кодом и извлекает фрагмент позже, если требуется цитата. Редактор может сделать это быстро и записать только самые запоминающиеся моменты, но ему придется пересмотреть контент, если он пропустит что-то, что понадобится ему позже. Или они могут сделать это тщательно и расшифровать весь контент заранее. По словам одного из наших редакторов:

Просмотры / поломки очень повторяются и тратят бесчисленные часы творческого времени!

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

В идеале мы хотим включить диалоговый поиск, поддерживающий следующие функции:

  • Поиск по одному названию, подмножеству названий (например, по всем драмам) или по всему каталогу.
  • Поиск по характеру или таланту
  • Многоязычный поиск

Вариант использования № 2: визуальный поиск

Одна картинка стоит тысячи слов. Визуальное повествование может помочь сделать сложные истории более понятными и, как следствие, донести более впечатляющее сообщение.

Художникам и видеоредакторам постоянно нужны определенные визуальные элементы для включения в иллюстрации и трейлеры. Они могут вычищать кадры, кадры или сцены с конкретными персонажами, местами, объектами, событиями (например, сцена погони за автомобилем в боевике) или атрибутами (например, крупным планом). Что, если бы мы могли позволить пользователям находить визуальные элементы с помощью естественного языка?

Вот пример желаемого результата, когда пользователь ищет «красный гоночный автомобиль» во всей библиотеке контента.

Пример использования № 3: Обратный поиск кадра

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

Предварительные инженерные работы

Подход № 1: пакетная обработка по запросу

Нашим первым подходом к раскрытию этих нововведений был инструмент для запуска этих алгоритмов по требованию и для каждого шоу. Мы внедрили систему пакетной обработки, чтобы пользователи могли отправлять свои запросы и ждать, пока система сгенерирует вывод. Обработка заняла несколько часов. Некоторые алгоритмы ML требуют больших вычислительных ресурсов. Многие из предоставленных образцов содержали значительное количество кадров для обработки. Типичное 1-часовое видео может содержать более 80 000 кадров!

После ожидания обработки пользователи загружали сгенерированные выходные данные алгоритма для использования в автономном режиме. Эта ограниченная экспериментальная система значительно сократила время, затрачиваемое нашими пользователями на ручной анализ контента. Вот визуализация этого потока.

Подход №2: включение онлайн-запроса с предварительным расчетом

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

Следующая цитата иллюстрирует положительный отклик наших пользователей:

Мы хотели найти все кадры столовой в сериале. За считанные секунды у нас было то, на что обычно ушло бы 1-2 человека часа/полный день, — просмотреть все кадры столовой из всех 10 эпизодов шоу. Невероятно!
Рассвет Шенетт, ведущий дизайнер

Этот подход имел несколько преимуществ для разработки продукта. Это позволило нам прозрачно обновлять данные алгоритма так, чтобы пользователи не знали об этом. Он также предоставил информацию о шаблонах запросов и алгоритмах, которые набирали популярность среди пользователей. Кроме того, мы смогли выполнить несколько A/B-тестов, чтобы подтвердить или опровергнуть наши гипотезы по настройке поиска.

Болевые точки

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

Поддержание разрозненных систем представляло собой проблему. Сначала они были созданы разными командами на разных стеках, поэтому обслуживание было дорогим. Всякий раз, когда исследователи машинного обучения заканчивали новый алгоритм, им приходилось интегрировать его отдельно в каждую систему. Мы были близки к пределу возможностей, имея всего две системы и несколько алгоритмов. Мы знали, что ситуация будет только ухудшаться по мере того, как мы расширяемся до большего количества вариантов использования и большего количества исследователей.

Онлайн-приложение открыло интерактивность для наших пользователей и утвердило наше направление. Однако он плохо масштабировался. Добавление новых алгоритмов и внедрение новых вариантов использования по-прежнему отнимало много времени и требовало усилий слишком многих инженеров. Эти инвестиции в индивидуальную интеграцию были непостоянными, а сроки реализации варьировались от нескольких недель до нескольких месяцев. Из-за индивидуального характера реализации нам не хватало поиска по всему каталогу для всех доступных источников машинного обучения.

Таким образом, эта модель представляла собой тесно связанную архитектуру приложения и данных, в которой алгоритмы машинного обучения были смешаны с бэкэндом и программным стеком UI/UX. Чтобы устранить разницу в сроках реализации, нам нужно было стандартизировать способы интеграции различных алгоритмов — начиная с того, как они выполнялись, и заканчивая обеспечением согласованного доступа к данным для всех потребителей. Поскольку мы разработали больше алгоритмов понимания мультимедиа и хотели расширить их до дополнительных вариантов использования, нам нужно было инвестировать в перепроектирование системной архитектуры, чтобы позволить исследователям и инженерам из разных команд внедрять инновации независимо и совместно. Media Search Platform (MSP) — это инициатива, направленная на удовлетворение этих требований.

Хотя мы только начали работать с медиа-поиском, поиск сам по себе не является чем-то новым для Netflix. У нас есть зрелая и надежная функция поиска и рекомендаций, доступная миллионам наших подписчиков. Мы знали, что можем использовать опыт наших коллег, которые отвечают за создание и внедрение инноваций в этой сфере. В соответствии с нашей строго согласованной, слабо связанной культурой мы хотели дать инженерам возможность быстро и независимо внедрять и улучшать алгоритмы, одновременно упрощая интеграцию приложений Studio и продуктов с возможностями алгоритмов понимания мультимедиа.

Создание модульной, подключаемой и настраиваемой платформы стало ключом к нашему успеху. Такой подход позволил нам сохранить распределенное владение платформой. Он одновременно предоставил различные специализированные группы для внесения соответствующих компонентов платформы. Мы использовали сервисы, уже доступные для других вариантов использования, и расширили их возможности для поддержки новых требований.

Далее мы обсудим архитектуру системы и опишем, как различные модули взаимодействуют друг с другом для сквозного потока.

Архитектура

Инженеры Netflix стремятся выполнять итерации быстро и предпочитают подход «MVP» (минимально жизнеспособный продукт), чтобы получить раннюю обратную связь и минимизировать первоначальные инвестиционные затраты. Таким образом, мы не построили все модули полностью. Мы расширили масштаб пилотной реализации, чтобы убедиться, что немедленные функции были разблокированы. В то же время мы оставили дизайн достаточно открытым, чтобы обеспечить возможность расширения в будущем. Мы выделим несколько примеров ниже, поскольку мы обсуждаем каждый компонент отдельно.

Интерфейсы — API и запросы

Начиная с верхней части диаграммы, платформа позволяет приложениям взаимодействовать с ней, используя интерфейсы gRPC или GraphQL. Наличие разнообразия в интерфейсах необходимо для удовлетворения потребностей разработчиков приложений там, где они есть. В Netflix gRPC в основном используется для межсерверной связи. Благодаря активным инструментам GraphQL, предоставляемым нашими командами разработчиков по повышению производительности, GraphQL стал де-факто выбором для пользовательского интерфейса — интеграции с серверной частью. Вы можете узнать больше о том, что создала команда и как она используется, в этих сообщениях в блоге. В частности, для этого проекта мы полагались на платформу Domain Graph Service.

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

Поисковый шлюз

Сгенерированный клиентом входной запрос сначала передается в систему обработки запросов. Поскольку большинство наших пользователей выполняют целевые запросы, такие как — поиск диалога «друзья не лгут» (из приведенного выше примера), сегодня этот этап выполняет облегченную обработку и предоставляет хук для интеграции A/B-тестирования. В будущем мы планируем превратить его в «систему понимания запросов» для поддержки поиска в свободной форме, чтобы уменьшить нагрузку на пользователей и упростить создание запросов на стороне клиента.

Обработка запросов изменяет запросы, чтобы они соответствовали целевому набору данных. Это включает в себя «встраивание» преобразования и перевода. Для запросов к источникам данных на основе встраивания он преобразует входные данные, такие как текст или изображение, в соответствующее векторное представление. Каждый источник данных или алгоритм может использовать другой метод кодирования, поэтому на этом этапе гарантируется, что соответствующее кодирование также применяется к предоставленному запросу. Одним из примеров того, почему нам нужны разные методы кодирования для каждого алгоритма, является разная обработка изображения, состоящего из одного кадра, и видео, которое содержит последовательность нескольких кадров.

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

Как только запрос преобразован и готов к выполнению, мы делегируем выполнение поиска одной или нескольким поисковым системам. Сначала нам нужно объединить, какой запрос должен быть направлен в какую систему. Это обрабатывается маршрутизатором запросов и модулем Searcher-proxy. Для первоначальной реализации мы полагались на один искатель для выполнения всех запросов. Наш расширяемый подход означал, что платформа может поддерживать дополнительные поисковые системы, которые уже использовались для создания прототипов новых алгоритмов и экспериментов.

Поиск может пересекаться или объединять данные из нескольких алгоритмов, поэтому этот уровень может разветвлять один запрос на несколько поисков. Мы внедрили «поисковик-прокси» внутри этого уровня для каждого поддерживаемого поисковика. Каждый прокси отвечает за сопоставление входного запроса с запросом, ожидаемым соответствующим искателем. Затем он использует необработанный ответ от искателя, прежде чем передать его компоненту постпроцессора результатов.

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

Для простоты координации и обслуживания мы абстрагировали обработку запросов и ответов в модуле под названием Search Gateway.

Искатели

Как упоминалось выше, выполнение запроса обрабатывается поисковой системой. Основной поисковик, используемый в текущей реализации, называется Marken — масштабируемый сервис аннотаций, созданный в Netflix. Он поддерживает различные категории поиска, включая полнотекстовый поиск и поиск по сходству на основе векторов. Он может хранить и извлекать как временные (метки времени), так и пространственные (координаты) данные. Этот сервис использует Cassandra и Elasticsearch для хранения и поиска данных. При внедрении векторных данных мы провели обширный бенчмаркинг для оценки доступных хранилищ данных. Одним из выводов здесь является то, что даже если существует хранилище данных, которое специализируется на конкретном шаблоне запроса, для простоты обслуживания и согласованности мы решили не вводить его.

Мы определили несколько общих типов схем и стандартизировали способ хранения данных из разных алгоритмов. Каждый алгоритм по-прежнему обладает гибкостью для определения пользовательского типа схемы. Мы активно внедряем инновации в этой области и недавно добавили возможность пересекать данные из разных алгоритмов. Это откроет творческие способы наложения данных из нескольких алгоритмов друг на друга, чтобы быстро получить желаемые результаты.

Алгоритм выполнения и загрузки

До сих пор мы сосредоточились на том, как запрашиваются данные, но существует не менее сложный механизм, обеспечивающий выполнение алгоритма и генерацию данных. Этим занимается наша специальная команда Media ML Platform. Команда специализируется на создании набора инструментов машинного обучения для конкретных медиа. Он обеспечивает беспрепятственный доступ к мультимедийным ресурсам (аудио, видео, изображения и текст) в дополнение к хранению мультимедийных функций и оркестровке вычислений.

Для этого проекта мы разработали собственный приемник, который индексирует сгенерированные данные в Marken в соответствии с предопределенными схемами. Особое внимание уделяется тому, когда данные заполняются в первый раз, чтобы не перегрузить систему огромным количеством операций записи.

И последнее, но не менее важное: наша команда по пользовательскому интерфейсу создала настраиваемую расширяемую библиотеку, чтобы упростить интеграцию этой платформы с приложениями для конечных пользователей. Настраиваемый пользовательский интерфейс упрощает настройку генерации запросов и обработки ответов в соответствии с потребностями отдельных приложений и алгоритмов. Будущая работа включает в себя создание собственных виджетов, чтобы еще больше минимизировать работу с пользовательским интерфейсом.

Краткое содержание

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

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

Благодарности

Особая благодарность Виноду Уддараю, Фернандо Амату Хилу, Бен Кляйну, Минакши Джиндал, Варун Сехри, Бураку Бачиоглу, Борису Чену, Джейсону Гэ, Тиффани Лоу, Виталий Кауханка, Суприя Вадламани, Абхишек Сони, Густаво Кармо, Эллиот Чоу, Прасанна Падманабхан, Акшай Моди, Нагендра Каматх, Венбин Бай, Джексон де Кампос, Juan Vimberg, Patrick Strawderman, Dawn Chenette, Yuchen Xie, Andy Yao и Chen Zheng за проектирование, разработку и участие в различных частях платформы.