【发布时间】:2010-10-17 18:02:25
【问题描述】:
我一直在尝试使用 Range 标头值从特定点流式传输音频,但我总是从一开始就得到歌曲。我是通过程序执行此操作的,因此不确定问题出在我的代码还是服务器上。
如何判断服务器是否支持 Range 标头参数?
谢谢。
【问题讨论】:
-
在服务器故障上查看这个问题:Test a server for byte range support?
标签: http http-headers
我一直在尝试使用 Range 标头值从特定点流式传输音频,但我总是从一开始就得到歌曲。我是通过程序执行此操作的,因此不确定问题出在我的代码还是服务器上。
如何判断服务器是否支持 Range 标头参数?
谢谢。
【问题讨论】:
标签: http http-headers
HTTP spec 定义它的方式,如果服务器知道如何支持 Range 标头,它会。这反过来要求它在向您返回内容时返回带有Content-Range 标头的206 Partial Content 响应代码。否则,它将简单地忽略您请求中的 Range 标头,并返回 200 响应代码。
这可能看起来很愚蠢,但是您确定您正在制作一个有效的 HTTP 请求标头吗?太常见了,我忘记在请求中指定 HTTP/1.1,或者忘记指定范围说明符,例如“字节”。
哦,如果您只想检查,那么只需发送 HEAD 请求而不是 GET 请求。相同的标题,相同的一切,只是“HEAD”而不是“GET”。如果您收到206 响应,您将知道Range 受支持,否则您将收到200 响应。
【讨论】:
Accept-Ranges。
这是供其他人搜索如何执行此操作的。你可以使用 curl:
curl -I http://exampleserver.com/example_video.mp4
在标题中你应该看到
Accept-Ranges: bytes
您可以进一步测试检索范围
curl --header "Range: bytes=100-107" -I http://exampleserver.com/example_vide0.mp4
在标题中你应该看到
HTTP/1.1 206 Partial Content
和
Content-Range: bytes 100-107/10000000
Content-Length: 8
[你会看到文件的长度而不是 10000000]
【讨论】:
虽然我回答这个问题有点晚,但我认为我的回答会对未来的访客有所帮助。这是一个检测服务器是否支持范围查询的python方法。
def accepts_byte_ranges(self, effective_url):
"""Test if the server supports multi-part file download. Method expects effective (absolute) url."""
import pycurl
import cStringIO
import re
c = pycurl.Curl()
header = cStringIO.StringIO()
# Get http header
c.setopt(c.URL, effective_url)
c.setopt(c.NOBODY, 1)
c.setopt(c.HEADERFUNCTION, header.write)
c.perform()
c.close()
header_text = header.getvalue()
header.close()
verbose_print(header_text)
# Check if server accepts byte-ranges
match = re.search('Accept-Ranges:\s+bytes', header_text)
if match:
return True
else:
# If server explicitly specifies "Accept-Ranges: none" in the header, we do not attempt partial download.
match = re.search('Accept-Ranges:\s+none', header_text)
if match:
return False
else:
c = pycurl.Curl()
# There is still hope, try a simple byte range query
c.setopt(c.RANGE, '0-0') # First byte
c.setopt(c.URL, effective_url)
c.setopt(c.NOBODY, 1)
c.perform()
http_code = c.getinfo(c.HTTP_CODE)
c.close()
if http_code == 206: # Http status code 206 means byte-ranges are accepted
return True
else:
return False
【讨论】:
一种方法是尝试并检查响应。在您的情况下,服务器似乎不支持范围。
或者,对 URI 执行 GET 或 HEAD,并检查 Accept-Ranges response header。
【讨论】:
GET方法和0-0Range请求头,检查响应码是否为206,会响应
响应正文的第一个和最后一个字节HEAD 方法执行与第一个会话相同的操作,这将获得相同的响应标头和代码而无需响应正文另外,你可以查看响应头上的
Accept-Ranges来判断是否支持范围,但请注意如果Accept-Ranges字段的值为none,则表示不支持范围,如果响应标头没有Accept-Ranges字段,您也无法指出它不支持范围。
如果你在请求头上使用0- Range 和GET 方法来检查响应代码,还有一件事你必须知道,响应正文消息将自动缓存在TCP接收窗口中,直到缓存已满。
【讨论】: