我有一个业务需求,需要浏览 URL 列表并找出返回错误的 URL。我编写了一个简单的脚本来获取特定 URL 的标头,因为我不关心内容。我只想知道获取内容时是否出错。在某些情况下,我的脚本在返回内容的同时返回 503 错误。以下是一个例子。
$ curl --head https://www.eia.gov/consumption/
HTTP/1.1 503 Service Unavailable
Server: AkamaiGHost
Mime-Version: 1.0
Content-Type: text/html
Content-Length: 175
Expires: Fri, 05 Jan 2018 21:32:47 GMT
Cache-Control: max-age=0, no-cache, no-store
Pragma: no-cache
Date: Fri, 05 Jan 2018 21:32:47 GMT
Connection: keep-alive
运行相同的 curl 命令(不带“--head”部分)将返回一个 HTML 页面,并且它不是错误页面。它是相关内容。因此,该 503 错误具有误导性。
这是一个配置错误的 Web 服务器返回了错误的响应标头还是我遗漏了什么?
真正的问题是:是否有可靠的方法来确定 URL 是否返回有效内容或是否返回错误?在这种情况下,HTML 的存在很有用,但我不会指望获得 HTML 意味着没有错误。404 错误是获得 HTML 页面但错误代码告诉我未找到该页面的典型情况。
答案1
该--head
选项会curl
发送实际请求。某些服务器可能不遵守该选项,或者可能不会像浏览器发送的请求HTTP HEAD
那样路由该请求。使用该选项将打印响应标头,但仍会发送请求。这还将返回响应的整个正文。您可以使用以下命令将其缩减为仅包含协议版本和响应状态的第一行:HTTP GET
-i
GET
head
$ curl -si https://www.eia.gov/consumption/ | head -n 1
HTTP/1.1 200 OK
(-s
curl 的选项可防止显示通过将 curl 管道传输到另一个进程触发的下载状态。head-n
上的选项是返回的行数。)
如何确定成功取决于你对“有效”的定义。HTTP 标准认为 200 或 300 范围内的任何值都是成功的。如果你想根据这个值进行检测,你可以grep
像这样使用:
$ curl -si https://www.eia.gov/consumption/ | head -n 1 | grep -E 'HTTP/\d\.\d (2|3)\d\d '
这使用正则表达式来匹配以 2 或 3 开头的任何返回代码。请确保您不要尝试匹配 HTTP 协议版本,因为它可能并不总是相同的。
curl
一旦获得了和返回的行head
,就可以根据您的实际需要无限地处理、格式化和返回结果。