Encrypted Media Extensions (EME) предоставляет API, который позволяет веб-приложениям взаимодействовать с системами защиты контента, обеспечивая воспроизведение зашифрованного аудио и видео.
EME разработан для того, чтобы одно и то же приложение и зашифрованные файлы можно было использовать в любом браузере, независимо от базовой системы защиты. Первое стало возможным благодаря стандартизированным API и потоку, а второе стало возможным благодаря концепции Common Encryption.
EME — это расширение спецификации HTMLMediaElement
, отсюда и название. Будучи «расширением», поддержка браузером EME необязательна: если браузер не поддерживает зашифрованные медиа, он не сможет воспроизводить зашифрованные медиа, но EME не требуется для соответствия спецификации HTML. Из спецификации EME :
Реализации EME используют следующие внешние компоненты:
- Система ключей: Механизм защиты контента (DRM). EME не определяет сами системы ключей, за исключением Clear Key (подробнее об этом ниже).
- Модуль дешифрования контента (CDM): клиентский программный или аппаратный механизм, который позволяет воспроизводить зашифрованные медиаданные. Как и в случае с Key Systems, EME не определяет никаких CDM, но предоставляет интерфейс для взаимодействия приложений с доступными CDM.
- Сервер лицензий (ключей): взаимодействует с CDM для предоставления ключей для расшифровки медиа. Согласование с сервером лицензий является обязанностью приложения.
- Услуга упаковки: кодирует и шифрует медиаданные для распространения/потребления.
Обратите внимание, что приложение, использующее EME, взаимодействует с сервером лицензий для получения ключей для включения дешифрования, но идентификация пользователя и аутентификация не являются частью EME. Извлечение ключей для включения воспроизведения мультимедиа происходит после (необязательной) аутентификации пользователя. Такие сервисы, как Netflix, должны аутентифицировать пользователей в своем веб-приложении: когда пользователь входит в приложение, приложение определяет личность и привилегии пользователя.
Как работает ЭМЕ?
Вот как взаимодействуют компоненты EME, что соответствует следующему примеру кода:
- Веб-приложение пытается воспроизвести аудио или видео, имеющее один или несколько зашифрованных потоков.
- Браузер распознает, что носитель зашифрован (см. врезку ниже, как это происходит), и запускает
encrypted
событие с метаданными (initData
), полученными от носителя о шифровании. - Приложение обрабатывает
encrypted
событие:- If no
MediaKeys
object has been associated with the media element, first select an available Key System by usingnavigator.requestMediaKeySystemAccess()
to check what Key Systems are available, then create aMediaKeys
object for an available Key System via aMediaKeySystemAccess
object. Note that initialization of the MediaKeys object should happen before the firstencrypted
event. Getting a license server URL is done by the app independently of selecting an available key system. AMediaKeys
object represents all the keys available to decrypt the media for an audio or video element. It represents a CDM instance and provides access to the CDM, specifically for creating key sessions, which are used to obtain keys from a license server. - После создания объекта
MediaKeys
назначьте его элементу мультимедиа:setMediaKeys()
связывает объектMediaKeys
с HTMLMediaElement, чтобы его ключи можно было использовать во время воспроизведения, т. е. во время декодирования.
- If no
- Приложение создает
MediaKeySession
, вызываяcreateSession()
наMediaKeys
. Это создаетMediaKeySession
, который представляет собой срок действия лицензии и ее ключей. - Приложение генерирует запрос лицензии, передавая медиаданные, полученные в
encrypted
обработчике, в CDM, вызываяgenerateRequest()
вMediaKeySession
. - CDM запускает событие
message
: запрос на получение ключа с сервера лицензий. - Объект
MediaKeySession
получает событиеmessage
, и приложение отправляет сообщение на сервер лицензий (например, через XHR). - The application receives a response from the license server and passes the data to the CDM using the
update()
method of theMediaKeySession
. - CDM расшифровывает медиа, используя ключи в лицензии. Действительный ключ может быть использован из любого сеанса в
MediaKey
s, связанного с элементом медиа. CDM получит доступ к ключу и политике, проиндексированным по Key ID. - Воспроизведение мультимедиа возобновляется.
Уф…
Обратите внимание, что между CDM и сервером лицензий может быть несколько сообщений, и вся коммуникация в этом процессе непрозрачна для браузера и приложения: сообщения понятны только CDM и серверу лицензий, хотя уровень приложения может видеть, какой тип сообщения отправляет CDM. Запрос лицензии содержит доказательство действительности CDM (и доверительных отношений), а также ключ для использования при шифровании ключа(ей) контента в результирующей лицензии.
…но чем на самом деле занимаются МЧР?
Реализация EME сама по себе не предоставляет способа расшифровки мультимедиа: она просто предоставляет API для веб-приложения для взаимодействия с модулями расшифровки контента.
Что CDM на самом деле делают, не определено спецификацией EME, и CDM может обрабатывать декодирование (распаковку) медиа, а также дешифрование. От наименее до наиболее надежного, есть несколько потенциальных вариантов функциональности CDM:
- Только расшифровка, позволяющая воспроизводить данные с использованием обычного медиаконвейера, например, через элемент
<video>
. - Расшифровка и декодирование, передача видеокадров в браузер для рендеринга.
- Расшифровка и декодирование, рендеринг непосредственно на аппаратном уровне (например, на графическом процессоре).
Существует несколько способов сделать CDM доступным для веб-приложения:
- Подключите CDM к браузеру.
- Распространите CDM отдельно.
- Встройте CDM в операционную систему.
- Включить CDM в прошивку.
- Встроить CDM в оборудование.
Спецификация EME не определяет, каким образом предоставляется доступ к CDM, но во всех случаях браузер несет ответственность за проверку и предоставление CDM.
EME не требует использования какой-либо конкретной системы ключей; среди текущих настольных и мобильных браузеров Chrome поддерживает Widevine, а IE11 поддерживает PlayReady.
Получение ключа с сервера лицензий
При типичном коммерческом использовании контент будет зашифрован и закодирован с использованием сервиса или инструмента упаковки. После того, как зашифрованный носитель станет доступен онлайн, веб-клиент может получить ключ (содержащийся в лицензии) с сервера лицензий и использовать этот ключ для включения расшифровки и воспроизведения контента.
Следующий код (адаптированный из примеров спецификации ) показывает, как приложение может выбрать подходящую систему ключей и получить ключ с сервера лицензий.
var video = document.querySelector('video');
var config = [{initDataTypes: ['webm'],
videoCapabilities: [{contentType: 'video/webm; codecs="vp9"'}]}];
if (!video.mediaKeys) {
navigator.requestMediaKeySystemAccess('org.w3.clearkey',
config).then(
function(keySystemAccess) {
var promise = keySystemAccess.createMediaKeys();
promise.catch(
console.error.bind(console, 'Unable to create MediaKeys')
);
promise.then(
function(createdMediaKeys) {
return video.setMediaKeys(createdMediaKeys);
}
).catch(
console.error.bind(console, 'Unable to set MediaKeys')
);
promise.then(
function(createdMediaKeys) {
var initData = new Uint8Array([...]);
var keySession = createdMediaKeys.createSession();
keySession.addEventListener('message', handleMessage,
false);
return keySession.generateRequest('webm', initData);
}
).catch(
console.error.bind(console,
'Unable to create or initialize key session')
);
}
);
}
function handleMessage(event) {
var keySession = event.target;
var license = new Uint8Array([...]);
keySession.update(license).catch(
console.error.bind(console, 'update() failed')
);
}
Обычное шифрование
Решения Common Encryption позволяют поставщикам контента шифровать и упаковывать свой контент один раз на контейнер/кодек и использовать его с различными Key Systems, CDM и клиентами: то есть любым CDM, который поддерживает Common Encryption. Например, видео, упакованное с помощью Playready, может воспроизводиться в браузере с помощью Widevine CDM, получающего ключ с сервера лицензий Widevine.
Это отличается от устаревших решений, которые работали только с полным вертикальным стеком, включая одного клиента, который часто также включал среду выполнения приложения.
Common Encryption (CENC) — стандарт ISO, определяющий схему защиты для ISO BMFF; аналогичная концепция применяется к WebM.
Очистить ключ
Хотя EME не определяет функциональность DRM, в настоящее время спецификация предписывает, чтобы все браузеры, поддерживающие EME, реализовали Clear Key. Используя эту систему, медиа можно шифровать с помощью ключа, а затем воспроизводить, просто указав этот ключ. Clear Key можно встроить в браузер: он не требует использования отдельного модуля дешифрования.
Хотя Clear Key вряд ли будет использоваться для многих типов коммерческого контента, он полностью совместим со всеми браузерами, поддерживающими EME. Он также удобен для тестирования реализаций EME и приложений, использующих EME, без необходимости запрашивать ключ контента с сервера лицензий. На сайте simpl.info/ck есть простой пример Clear Key. Ниже приведено пошаговое руководство по коду, которое соответствует описанным выше шагам, но без взаимодействия с сервером лицензий.
// Define a key: hardcoded in this example
// – this corresponds to the key used for encryption
var KEY = new Uint8Array([
0xeb, 0xdd, 0x62, 0xf1, 0x68, 0x14, 0xd2, 0x7b,
0x68, 0xef, 0x12, 0x2a, 0xfc, 0xe4, 0xae, 0x3c
]);
var config = [{
initDataTypes: ['webm'],
videoCapabilities: [{
contentType: 'video/webm; codecs="vp8"'
}]
}];
var video = document.querySelector('video');
video.addEventListener('encrypted', handleEncrypted, false);
navigator.requestMediaKeySystemAccess('org.w3.clearkey', config).then(
function(keySystemAccess) {
return keySystemAccess.createMediaKeys();
}
).then(
function(createdMediaKeys) {
return video.setMediaKeys(createdMediaKeys);
}
).catch(
function(error) {
console.error('Failed to set up MediaKeys', error);
}
);
function handleEncrypted(event) {
var session = video.mediaKeys.createSession();
session.addEventListener('message', handleMessage, false);
session.generateRequest(event.initDataType, event.initData).catch(
function(error) {
console.error('Failed to generate a license request', error);
}
);
}
function handleMessage(event) {
// If you had a license server, you would make an asynchronous XMLHttpRequest
// with event.message as the body. The response from the server, as a
// Uint8Array, would then be passed to session.update().
// Instead, we will generate the license synchronously on the client, using
// the hard-coded KEY at the top.
var license = generateLicense(event.message);
var session = event.target;
session.update(license).catch(
function(error) {
console.error('Failed to update the session', error);
}
);
}
// Convert Uint8Array into base64 using base64url alphabet, without padding.
function toBase64(u8arr) {
return btoa(String.fromCharCode.apply(null, u8arr)).
replace(/\+/g, '-').replace(/\//g, '_').replace(/=*$/, '');
}
// This takes the place of a license server.
// kids is an array of base64-encoded key IDs
// keys is an array of base64-encoded keys
function generateLicense(message) {
// Parse the clearkey license request.
var request = JSON.parse(new TextDecoder().decode(message));
// We only know one key, so there should only be one key ID.
// A real license server could easily serve multiple keys.
console.assert(request.kids.length === 1);
var keyObj = {
kty: 'oct',
alg: 'A128KW',
kid: request.kids[0],
k: toBase64(KEY)
};
return new TextEncoder().encode(JSON.stringify({
keys: [keyObj]
}));
}
Для проверки этого кода вам понадобится зашифрованное видео для воспроизведения. Шифрование видео для использования с Clear Key может быть выполнено для WebM согласно инструкциям webm_crypt . Также доступны коммерческие сервисы (по крайней мере для ISO BMFF/MP4), и разрабатываются другие решения.
Сопутствующая технология №1
Расширения медиа-источников (MSE)
HTMLMediaElement — творение простой красоты.
Мы можем загружать, декодировать и воспроизводить медиа, просто указав URL-адрес источника:
<video src='foo.webm'></video>
Media Source API — это расширение HTMLMediaElement, позволяющее более точно контролировать источник медиа, позволяя JavaScript создавать потоки для воспроизведения из «кусков» видео. Это, в свою очередь, позволяет использовать такие методы, как адаптивная потоковая передача и сдвиг во времени.
Почему MSE важен для EME? Потому что в дополнение к распространению защищенного контента поставщики коммерческого контента должны иметь возможность адаптировать доставку контента к условиям сети и другим требованиям. Например, Netflix динамически изменяет битрейт потока по мере изменения условий сети. EME работает с воспроизведением потоков мультимедиа, предоставляемых реализацией MSE, так же, как и с мультимедиа, предоставляемыми через атрибут src
.
Как разбить на части и воспроизвести медиа, закодированные с разным битрейтом? См. раздел DASH ниже.
Вы можете увидеть MSE в действии на simpl.info/mse ; для целей этого примера видео WebM разделено на пять частей с использованием API File. В производственном приложении части видео будут извлечены через Ajax.
Сначала создается SourceBuffer:
var sourceBuffer = mediaSource.addSourceBuffer('video/webm; codecs="vorbis,vp8"');
Затем весь фильм «транслируется» в видеоэлемент путем добавления каждого фрагмента с помощью метода appendBuffer():
reader.onload = function (e) {
sourceBuffer.appendBuffer(new Uint8Array(e.target.result));
if (i === NUM_CHUNKS - 1) {
mediaSource.endOfStream();
} else {
if (video.paused) {
// start playing after first chunk is appended
video.play();
}
readChunk_(++i);
}
};
Подробнее о MSE читайте в статье HTML5 Rocks .
Сопутствующая технология №2
Динамическая адаптивная потоковая передача по HTTP (DASH)
Мультиустройство, мультиплатформенность, мобильность — как бы вы это ни называли, веб часто работает в условиях изменчивой связности. Динамическая, адаптивная доставка имеет решающее значение для преодоления ограничений пропускной способности и изменчивости в мире мультиустройств.
DASH (он же MPEG-DASH) разработан для обеспечения наилучшей доставки медиа в нестабильном мире, как для потоковой передачи, так и для загрузки. Несколько других технологий делают что-то похожее, например, HTTP Live Streaming (HLS) от Apple и Smooth Streaming от Microsoft, но DASH — единственный метод адаптивной потоковой передачи битрейта через HTTP, основанный на открытом стандарте. DASH уже используется такими сайтами, как YouTube.
Какое отношение это имеет к EME и MSE? Реализации DASH на основе MSE могут анализировать манифест, загружать сегменты видео с соответствующим битрейтом и передавать их видеоэлементу, когда он в этом нуждается, используя существующую инфраструктуру HTTP.
Другими словами, DASH позволяет коммерческим поставщикам контента осуществлять адаптивную потоковую передачу защищенного контента.
DASH делает то, что заявлено в его описании:
- Динамичный: реагирует на меняющиеся условия.
- Адаптивный: адаптируется для обеспечения подходящего битрейта аудио или видео.
- Потоковая передача: позволяет осуществлять потоковую передачу и загрузку.
- HTTP: обеспечивает доставку контента с использованием преимуществ HTTP, но без недостатков традиционного потокового сервера.
BBC начала проводить тестовые трансляции с использованием DASH :
Подводя итог:
- Медиаданные кодируются с разной скоростью передачи данных.
- Файлы с разным битрейтом доступны с HTTP-сервера.
- Клиентское веб-приложение выбирает, какой битрейт извлекать и воспроизводить с помощью DASH.
В рамках процесса сегментации видео программно создается XML-манифест, известный как Media Presentation Description (MPD). Он описывает наборы адаптации и представления с указанием продолжительности и URL-адресов. MPD выглядит следующим образом:
<MPD xmlns="urn:mpeg:DASH:schema:MPD:2011" mediaPresentationDuration="PT0H3M1.63S" minBufferTime="PT1.5S" profiles="urn:mpeg:dash:profile:isoff-on-demand:2011"
type="static">
<Period duration="PT0H3M1.63S" start="PT0S">
<AdaptationSet>
<ContentComponent contentType="video" id="1" />
<Representation bandwidth="4190760" codecs="avc1.640028" height="1080" id="1" mimeType="video/mp4" width="1920">
<BaseURL>car-20120827-89.mp4</BaseURL>
<SegmentBase indexRange="674-1149">
<Initialization range="0-673" />
</SegmentBase>
</Representation>
<Representation bandwidth="2073921" codecs="avc1.4d401f" height="720" id="2" mimeType="video/mp4" width="1280">
<BaseURL>car-20120827-88.mp4</BaseURL>
<SegmentBase indexRange="708-1183">
<Initialization range="0-707" />
</SegmentBase>
</Representation>
…
</AdaptationSet>
</Period>
</MPD>
(Этот XML взят из файла .mpd, используемого для демонстрационного проигрывателя YouTube DASH )
Согласно спецификации DASH, файл MPD теоретически может использоваться в качестве src
для видео. Однако, чтобы предоставить большую гибкость веб-разработчикам, поставщики браузеров решили вместо этого оставить поддержку DASH библиотекам JavaScript, использующим MSE, таким как dash.js. Реализация DASH в JavaScript позволяет алгоритму адаптации развиваться без необходимости обновления браузера. Использование MSE также позволяет экспериментировать с альтернативными форматами манифеста и механизмами доставки без необходимости изменения браузера. Shaka Player от Google реализует клиент DASH с поддержкой EME.
На сайте Mozilla Developer Network имеются инструкции по использованию инструментов WebM и FFmpeg для сегментации видео и создания MPD.
Заключение
Использование Интернета для доставки платного видео и аудио растет огромными темпами . Кажется, что каждое новое устройство, будь то планшет, игровая консоль, подключенный телевизор или телевизионная приставка, может транслировать медиа от основных поставщиков контента по HTTP. Более 85% мобильных и настольных браузеров теперь поддерживают <video>
и <audio>
, и Cisco оценивает, что видео будет составлять от 80 до 90 процентов мирового потребительского интернет-трафика к 2017 году. В этом контексте поддержка браузерами защищенного распространения контента, вероятно, будет становиться все более значимой, поскольку поставщики браузеров сокращают поддержку API, на которые опирается большинство медиа-плагинов.
Дальнейшее чтение
Спецификации и стандарты
- Спецификация EME : последний редакторский черновик<
- Общее шифрование (CENC)
- Расширения медиа-источников
- Стандарт DASH (да, это PDF)
- О стандарте DASH
Статьи
- Вебинар DTG (частично устарел)
- Что такое ЭМЕ? , Анри Сивонен
- Статья HTML5 Rocks Media Source Extensions
- Тестовые потоки MPEG-DASH: запись в блоге BBC R&D