Я смотрел видео с YouTube, и я решил исследовать некоторые части его видеопроигрывателя. Я заметил, что в отличие от большинства видеороликов HTML5, которые я видел, видеопроигрыватель Youtube не использует обычный источник видео и вместо этого использует URL-адрес blob в качестве источника.
Раньше я тестировал видео HTML5, и я обнаружил, что сервер начинает потоковое воспроизведение всего видео с самого начала и буферов в фоновом режиме всю оставшуюся часть видео. Это означает, что если ваше видео составляет 300 мегабайт, все 300 мегабайт будут загружены. Если вы ищете середину, она начнет загружаться из позиции поиска до конца.
Youtube не работает таким образом (по крайней мере, в хроме). Вместо этого ему удается управлять буферизацией, поэтому он лишь приостанавливает некоторую величину при паузе. Он также, кажется, только буферизует соответствующие фрагменты, поэтому, если вы пропустите его, убедитесь, что не буферизуете части, которые вряд ли будут наблюдаться.
В моих попытках исследовать, как это сработало, я заметил, что тег src для видео имеет значение blob:http%3A//www.youtube.com/ee625eee-2802-49b2-a13f-eb374d551d54
, которое указывало на blobs, который затем привел меня к типизированным массивам. Используя эти два ресурса, я могу загрузить mp4-видео в blob и отобразить его в теге HTML5.
Однако то, что я сейчас застрял, - это то, как Youtube занимается кусками. Рассматривая сетевой трафик, он отправляет запросы на http://r6---sn-p5q7ynee.c.youtube.com/videoplayback
, который возвращает двоичные видеоданные обратно в куски размером 1,1 МБ. Также кажется, стоит отметить, что большинство обычных запросов из-за видеообъявлений HTML5, похоже, получают ответный код 206 во время его потока, но вызовы playvideo для youtube получают 200 обратно.
Я пытался попытаться загрузить только диапазон байтов (через параметр Range
http header), который, к сожалению, не удался (я предполагаю, потому что метаданных для видео, идущего с видео) не было.
В этот момент я застрял в выяснении того, как Youtube справляется с этим. Я придумал несколько идей, хотя ни один из которых я полностью не продал:
1) Youtube отправляет автономные видео и аудио фрагменты с каждым вызовом /videoplayback
. Это кажется довольно тяжелым бременем на стороне загрузки, и кажется, что было бы сложно сшить их вместе, чтобы они выглядели как одно бесстрастное видео. Кроме того, видеотег, кажется, считает его одним полным видео, судя по звонкам $('video').duration
и $('video').currentTime
, что заставляет меня думать, что тег видео считает его единственным видео файлом. Наконец, vidoe src tag никогда не меняется, что заставляет меня поверить, что он работает с особым blob и не отключает blobs.
2) Youtube создает пустой блок, предварительно заданный до полного массива видео, и обновляет кусок с кусками, когда он загружает его. Затем он должен убедиться, что пользователь не слишком приблизился к последнему загруженному фрагменту (чтобы пользователь не мог войти в незанятый раздел блоба). Проблема, которую я вижу с этим, я не вижу возможности динамически обновлять blob через javascript (хотя, возможно, у меня просто проблемы с поиском по нему)
3) Youtube загружает метаданные, а затем начинает строить blob по порядку, добавляя фрагменты видео, когда он загружает их. Проблема, которую я вижу в этом методе, заключается в том, что я не понимаю, как она будет обрабатывать запросы в области после буферизации.
Возможно, мне просто не хватает очевидного ответа, который прямо передо мной. У кого-нибудь есть идеи?
edit: Я просто подумал о четвертом варианте. Другая идея заключается в том, что они могут использовать файл API для записи двоичных фрагментов в файл и использовать этот файл для потоковой передачи. API-интерфейс файла, похоже, имеет возможность искать конкретные позиции, поэтому позволяет вам заполнять видео пустыми байтами и заполнять их по мере их получения. Это, безусловно, будет включать в себя поиск видео.