Если вам нужно добавить на свой сайт видео, то может возникнуть вопрос, где его хостить и как потом раздавать. В этом посте разберем варианты и рассмотрим примеры использования Yandex Object Storage. Формат MP4 знаком, наверное, всем. Но если мы хотим показывать видео на сайте эффективно, то стоит задуматься: лучшее ли это решение для нашей задачи — просто выложить все видео одним файлом MP4? Протокол HLS (HTTP Live Streaming) был предложен в 2009 году и к настоящему времени де-факто стал стандартом в области адаптивного видеостриминга. HLS был разработан Apple как замена их собственной разработки QuickTime Streaming Server, а также как альтернатива другому популярному на тот момент протоколу — Real-Time Messaging Protocol (RTMP). Этот протокол, выпущенный Adobe в 2002 году, использовал технологию Flash, чтобы передавать видео с низкой задержкой через интернет. Не смотря на то, что Flash давно «умер», RTMP до сих пор остается популярным протоколом для видеотрансляций. Хотя HLS не так широко известен, но он, наряду с MPEG-DASH и SRT, остается одним из главных протоколов, которые обеспечивают доставку видео- и аудиоконтента в современном интернете. Велики шансы, что вы пользуетесь им каждый день, даже не задумываясь об этом. Особенно если вы — пользователь экосистемы Apple. Хотя HLS и был разработан в Apple, он широко поддерживается и на других платформах: Linux, Windows, смартфонах с Android и iOS, OTT-устройствах, Smart TV, а также в браузерах Google Chrome, Safari, Android Browser, Microsoft Edge, Chrome for Android и Opera Mobile. На части платформ поддержка нативная, в других же она реализована через JS-плееры. Тот факт, что потоковая передача HLS обычно осуществляется через видеоплеер HTML5, делает HLS универсальным и широко совместимым. Его часто называют «HTML5-видео», что не совсем точно. Видеоплеер HTML5 просто совместим с HLS. HLS — это протокол потоковой передачи видео. Но что это означает? Возможно, вы слышали термин «кодек», но важно отметить, что потоковый протокол — это не кодек. Протокол — это более широкая категория. Потоковый протокол — это стандартизированный метод передачи видеоконтента между устройствами. Протокол может предполагать использование определенного кодека (или кодеков), который будет использоваться для сжатия и распаковки видео- и аудиоконтента. Например, HLS поддерживает множество популярных кодеков: Audio: AAC-LC, HE-AAC+ v1 & v2, xHE-AAC, Apple Lossless, FLAC Video: H.265, H.264 HLS предназначен для обеспечения надежности и динамической адаптации к сетевым условиям путем оптимизации (т. е. ухудшения или улучшения) воспроизведения видео для доступных скоростей интернета. Кроме того, он «заботится» о разных аспектах, которые связаны с доставкой видеоконтента зрителям: Стриминг с адаптивным битрейтом (Adaptive Bitrate Streaming) — HLS подстраивает качество видео под текущую скорость интернет-канала. Это позволяет авторам предлагать несколько видеопотоков в разном качестве, а плееру переключаться между ними незаметно. Пример среднего битрейта видео (Кбит/с), источник: Apple Совместимость со многими устройствами — HLS гарантирует, что ваш видеоконтент будет воспроизводиться на любом устройстве, которое может запустить совместимый плеер (например, HTML5). Субтитры — HLS поддерживает скрытые субтитры. Это позволяет авторам встроить несколько потоков субтитров (например, на разных языках). Возможность менять аудио дорожку — HLS поддерживает несколько потоков аудио, между которыми можно переключаться. Возможность вставлять рекламу — HLS использует для этого технологии VPAID и VAST. Масштабирование — HLS обладает высокой масштабируемостью для доставки видеофайлов и потокового контента через глобальные сети доставки контента (CDN). В отличие от протокола RTMP, который работает совместно с Flash Player, HLS может легко масштабироваться для доставки с помощью обычных веб-серверов через CDN. Распределяя рабочую нагрузку по сети серверов, CDN приспосабливаются к всплескам вирусной аудитории и гораздо большим, чем ожидалось, живым аудиториям. CDN также помогают улучшить качество просмотра, кешируя аудио- и видеосегменты. Для сравнения, поддержка CDN для RTMP быстро снижается. RTMP также требует использования выделенного сервера потоковой передачи, что делает его более ресурсоемким для развертывания. Защита от пиратства — реализуется через поддержку большого количества технологий DRM. Вот более подробный пост про то, как можно ограничить доступ к видео при помощи шифрования AES-128. HLS имеет некоторые ограничения, но они связаны с конкретными проектными решениями, которые были приняты при разработке протокола. Часть этих ограничений связана с задержкой. HLS ставит во главу угла комфорт пользователя, а не низкую задержку, поэтому live-контент, который транслируется с использованием протокола HLS, не является достаточно «живым». Зритель увидит его с задержкой до 30 секунд. Таким образом, HLS — не лучший выбор для таких приложений, как веб-конференции или управление устройствами, где необходимо видео в реальном времени (камеры и дроны). В этом случае лучше использовать более быстрый потоковый протокол, например WebRTC (Web Real-Time Communications). Задержка в HLS возникает из-за того, что протокол разбивает видео на множество многосекундных фрагментов (сегментов), которые обычно имеют длительность 2–6 секунд. И поскольку протокол HLS также должен буферизировать несколько таких небольших сегментов одновременно, задержка может составлять десятки секунд. Однако если задержка или плохие сетевые условия не являются проблемой, то HLS — это протокол, который вам нужен. С HLS создатели контента могут подготовить версии своего видео для нескольких различных интернет-каналов и условий воспроизведения: 3G, 4G, LTE, медленный публичный Wi‑Fi, быстрый домашний интернет. Различные поставщики CDN постепенно отказываются от поддержки RTMP, заявляя, что его развертывание становится слишком дорогим. Вместо этого набирают популярность такие протоколы, как HLS, SRT и MPEG-DASH. Adobe перестал поддерживать технологию, на которую опирается RTMP. Поэтому однажды ваш процесс потоковой передачи RTMP станет технологически устаревшим и потеряет поддержку со стороны производителя. Это лишь вопрос времени. HLS оптимизирует доставку аудио и видео на обширный спектр мобильных, настольных, планшетных и OTT-устройств. HLS позволяет доставлять видео по запросу с помощью шифрования и аутентификации. HLS значительно снижает затраты на CDN. При этом он обеспечивает только оптимальный битрейт для клиентской сети и избегает сценария «частичного воспроизведения и полной загрузки», который присущ прогрессивной потоковой передаче HTTP. Например, когда всё видео представлено одним файлом MP4. Apple App Store требует, чтобы приложения с десятиминутным (и более) видео использовали HLS. Надеюсь, я смог вас убедить, что сегодня для распространения видеоконтента через интернет стоит смотреть в сторону HLS. Давайте теперь на примере рассмотрим способ, как нам использовать объектное хранилище в Yandex.Cloud. Object Storage — это решение для хранения больших объемов данных за относительно небольшие деньги. Оно идеально подходит для чего-то вроде видеофайлов, которые, как правило, имеют довольно большой объем. Доступ к файлам (или объектам, как их часто называют) осуществляется через HTTP(S), что делает Object Storage отличным решением для хранения и обслуживания ваших HLS-видео. Для начала нам понадобится бакет в хранилище. Если у вас его нет, то вот инструкция, как его создать. Если у вас уже есть видео в формате HLS, то смело переходите к следующему разделу. Если же его нет, то вам понадобится утилита ffmpeg, при помощи которой вы сможете конвертировать видео и аудио во множество форматов, в том числе HLS. Установка ffmpeg Windows Скачайте последнюю версию отсюда. Разархивируйте. Откройте консоль в папке. Выполните команду ./ffmpeg — вы должны будете увидеть информацию о версии ffmpeg. Mac OS X Установите homebrew. Выполните команду brew install ffmpeg Вызовите ffmpeg — вы должны будете увидеть информацию о версии ffmpeg. Ubuntu Выполните команды:  CentOS или Fedora Выполните команду: Видео для примера Возьмем какой-нибудь видеофайл и посмотрим информацию о нем: В консоли появится приблизительно следующее: Подготовим команду для конвертации видео: Теперь подробно разберем, что означают все эти ключи: -i sample.mp4 — задает sample.mp4 в качестве входного файла. -vf "scale=w=1280:h=720:force_original_aspect_ratio=decrease" — масштабирует видео до максимальных размеров в пределах заданного разрешения 1280x720 с сохранением соотношения сторон. -c:a:0 aac -ar 48000 -ac:a:0 2 -b:a:0 128k — задает аудиокодек AAC с частотой дискретизации 48кГц и битрейтом 128K. -ac:a:0 2 — указывает, что если в первом аудиопотоке (a:0) больше двух каналов, нужно смиксовать их в стереосигнал. -c:v h264 — устанавливает видеокодек H.264, который является стандартным кодеком для HLS. Это кодек без аппаратного ускорения. Если вы будете конвертировать видео на MacOS X, то можете попробовать использовать значение h264_videotoolbox. Для других платформ также есть кодеки с поддержкой аппаратного ускорения. -profile:v main — устанавливает профиль кодека H.264 в main (это означает включение поддержки всех современных устройств). Подробнее в статье. -crf 20 — Constant Rate Factor, высокоуровневая настройка качества. -g 48 -keyint_min 48 — указывает, что нужно создавать ключевой кадр (I-frame) через каждые 48 кадров (~2 сек) — это важно, влияет на корректную нарезку на сегменты. -sc_threshold 0 — не создавать ключевые кадры при смене сцены. -b:v:0 2500k -maxrate 2675k -bufsize 3750k — ограничить битрейт видео. Конкретные значения стоит подбирать исходя из особенностей вашего видео. Подробнее в разделе «Как правильно выбрать битрейт». -hls_time 4 — указывает длину сегмента в секундах. Реальная длина будет зависеть от ключевых кадров. -hls_playlist_type vod — добавляет тег #EXT-X-PLAYLIST-TYPE:VOD и сохраняет все сегменты в плейлист. -hls_segment_filename sample/720p_%03d.ts — явным образом задает имена файлов для сегментов. sample/720p.m3u8 — указывает путь до плейлиста, также говорит ffmpeg выводить его в формате HLS (файл .m3u8). Эта команда сгенерирует HLS-плейлист и сегменты и сложит их в папку sample. Утилита ffmpeg поддерживает несколько входных и выходных файлов и все результаты могут быть сгенерированы параллельно одной длинной командой. Очень важно, чтобы помимо параметров разрешения и битрейта команды были идентичны, тогда результаты будут правильно выровнены, то есть ключевые кадры будут установлены в нужных местах, чтобы обеспечить плавное переключение между ними «на лету».  Мы создадим четыре версии с разрешениями: 1080p 1920x1080 (original) 720p 1280x720 480p 842x480 360p 640x360 HLS-плеер должен знать, что существует несколько версий нашего видео, поэтому мы создаем мастер-плейлист HLS, чтобы указать их и сохранить вместе с другими плейлистами и сегментами в файл playlist.m3u8. Битрейт зависит в основном от разрешения и типа контента. При установке слишком низкого битрейта пикселизация изображения будет особенно видна в тех областях, где происходит быстрое движение. Когда битрейт слишком высок, выходные файлы могут быть чрезмерно большими без дополнительного значения. Чтобы выбрать правильный битрейт, нужно понимать его содержимое. Видео с резкими движениями, например запись спортивных или новостных событий, потребует более высокого битрейта, чтобы избежать пикселизации. А для контента с плавными движениями в кадре, например, музыкального концерта или интервью, будет достаточно низкого битрейта без видимых изменений качества. Вот некоторые хорошие значения по умолчанию: Убедитесь, что тип контента списка воспроизведения и сегментов видео (файлов .ts) установлен в application/x-mpegURL и video/MP2T соответственно. Если вы загружаете файлы при помощи s3cmd, то он проставит корректные заголовок Content-type будет установлен корректно. Для того чтобы видеоплееры могли получить доступ к видеофайлам, необходимо указать настройки CORS в бакете. Это максимально широкое правило для примера. Если вы хотите ограничить круг сайтов, куда можно будет встраивать видео, то прочитайте этот пост. Теперь можно выкладывать видео на свой сайт. В пример я добавил минимальный контрол для переключения уровня качества. Вот использованный плеер и react-обертка. А вот альтернативный плеер. Итак, в чем же плюс? Если вы откроете консоль, то увидите, что после того как браузер загрузил несколько первых сегментов видео, загрузка приостанавливается. Это позволяет нам экономить трафик в тех случаях, когда пользователь открыл страницу с видео, начал просмотр видео и остановился. В этом случае нам не нужно загружать весь видеофайл целиком. Мы можем вовремя остановиться, а потом, если это понадобится (пользователь продолжит воспроизведение), загрузить остальное. Позже мы еще вернемся к теме HLS и вопросу использования сервисов Yandex.Cloud. А пока напомню, что Object Storage является одним из сервисов экосистемы serverless в Yandex.Cloud, и есть живое растущее serverless-комьюнити Yandex Serverless Ecosystem, где можно задавать вопросы и оперативно получать ответы от единомышленников и коллег. Присоединяйтесь! И еще в Yandex.Cloud действует программа free tier. Она позволяет реализовать массу проектов бесплатно, если не выходить за лимиты.