Запросы диапазона
HTTP-запросы диапазона
HTTP-запрос Range просит сервер отправить клиенту части ресурса. Запросы диапазона полезны для различных клиентов, включая медиаплееры с поддержкой произвольного доступа, инструменты для работы с данными, которым нужна только часть большого файла, и менеджеры загрузок, позволяющие пользователям приостанавливать и возобновлять загрузку.
Проверка поддержки частичных запросов сервером
Если HTTP-ответ содержит заголовок Accept-Ranges со значением, отличным от none, сервер поддерживает запросы диапазона. Если в ответах отсутствует заголовок Accept-Ranges, это означает, что сервер не поддерживает частичные запросы. Если запросы диапазона не поддерживаются, приложения могут адаптироваться к этому условию; например, менеджеры загрузок могут отключить кнопки приостановки, которые используют запросы диапазона для возобновления загрузки.
Чтобы проверить, поддерживает ли сервер запросы диапазона, можно отправить запрос HEAD и изучить заголовки, не запрашивая ресурс целиком. Если вы используете curl, можно указать флаг -I, чтобы отправить запрос HEAD:
curl -I https://i.imgur.com/z4d4kWk.jpg
В результате будет отправлен следующий HTTP-запрос:
HEAD /z4d4kWk.jpg HTTP/2 Host: i.imgur.com User-Agent: curl/8.7.1 Accept: */*
Ответ содержит только заголовки и не включает тело ответа:
HTTP/2 200 content-type: image/jpeg last-modified: Thu, 02 Feb 2017 11:15:53 GMT … accept-ranges: bytes content-length: 146515
В этом ответе Accept-Ranges: bytes указывает, что в качестве единиц для определения диапазона можно использовать «bytes» (сейчас другие единицы использовать нельзя). Заголовок Content-Length также полезен: он указывает общий размер изображения, если вместо этого отправить такой же запрос с методом GET.
Запрос определённого диапазона у сервера
Если сервер поддерживает запросы диапазона, можно указать, какую часть или части документа сервер должен вернуть, добавив в HTTP-запрос заголовок Range.
Диапазоны из одной части
Для наглядности запросить один диапазон ресурса можно с помощью curl. Параметр -H добавляет строку заголовка к запросу; в данном случае это заголовок Range, запрашивающий первые 1024 байта. Последний параметр — --output - — позволяет вывести двоичные данные в терминал:
curl https://i.imgur.com/z4d4kWk.jpg -i -H "Range: bytes=0-1023" --output -
Отправленный запрос выглядит так:
GET /z4d4kWk.jpg HTTP/2 Host: i.imgur.com User-Agent: curl/8.7.1 Accept: */* Range: bytes=0-1023
Сервер отвечает статусом 206 Partial Content:
HTTP/2 206 content-type: image/jpeg content-length: 1024 content-range: bytes 0-1023/146515 … (binary content)
Заголовок Content-Length указывает размер запрошенного диапазона, а не полный размер изображения. Заголовок ответа Content-Range показывает, где это частичное сообщение находится в полном ресурсе.
Диапазоны из нескольких частей
Заголовок Range также позволяет получить сразу несколько диапазонов в документе, состоящем из нескольких частей. Диапазоны разделяются запятой.
curl http://www.example.com -i -H "Range: bytes=0-50, 100-150"
Сервер отвечает статусом 206 Partial Content, как показано ниже. Ответ содержит заголовок Content-Type, указывающий на то, что далее следует набор байтовых диапазонов из нескольких частей. Строка-разделитель (в данном случае 3d6b6a416f9b5) отделяет части тела сообщения, каждая из которых содержит собственные поля Content-Type и Content-Range:
HTTP/1.1 206 Partial Content
Content-Type: multipart/byteranges; boundary=3d6b6a416f9b5
Content-Length: 282
--3d6b6a416f9b5
Content-Type: text/html
Content-Range: bytes 0-50/1270
<!doctype html>
<html lang="en-US">
<head>
<title>Example Do
--3d6b6a416f9b5
Content-Type: text/html
Content-Range: bytes 100-150/1270
eta http-equiv="Content-type" content="text/html; c
--3d6b6a416f9b5--
Условные запросы диапазона
При возобновлении загрузки и запросе дополнительных частей ресурса необходимо убедиться, что сохранённый ресурс не изменился с момента получения последнего фрагмента.
Заголовок HTTP-запроса If-Range делает запрос диапазона условным: если условие выполнено, отправляется запрос диапазона, а сервер возвращает ответ Partial Content со статусом 206 и соответствующим телом. Если условие не выполнено, сервер возвращает ресурс целиком со статусом OK 200. Этот заголовок можно использовать либо с валидатором Last-Modified, либо с ETag, но не с обоими одновременно.
If-Range: Wed, 21 Oct 2015 07:28:00 GMT
Ответы на частичные запросы
При работе с запросами диапазона важны три кода состояния:
- На успешный запрос диапазона сервер отвечает статусом
Partial Content206. - Если запрошенный диапазон выходит за границы ресурса, сервер возвращает статус
Requested Range Not Satisfiable416. Это означает, что ни одно из значений диапазона не пересекается с размером ресурса. Например, начальная позиция байта каждого диапазона может быть больше длины ресурса. - Если запросы диапазона не поддерживаются, сервер возвращает статус
OK200и передаёт всё тело ответа.
Сравнение с фрагментированной Transfer-Encoding
Заголовок Transfer-Encoding позволяет использовать фрагментированное кодирование, что удобно при отправке клиенту больших объёмов данных, когда общий размер ответа неизвестен до завершения обработки запроса. Сервер сразу отправляет данные клиенту, не буферизуя ответ и не определяя его точную длину, что снижает задержку. Запросы диапазона совместимы с фрагментированным кодированием и могут использоваться как вместе, так и по отдельности.
См. также
- Связанные коды состояния:
200,206,416. - Связанные заголовки:
Accept-Ranges,Range,Content-Range,If-Range,Transfer-Encoding.
© 2005–2025 MDN contributors.
Licensed under the Creative Commons Attribution-ShareAlike License v2.5 or later.
https://developer.mozilla.org/en-US/docs/Web/HTTP/Guides/Range_requests