saber酱的抱枕

哀哉京阿尼

03/11
08:00
学习 软件

GM_xmlhttpRequest获取响应头

JavaScript是可以获取Response Header(响应头)的信息的:

如果是使用XMLHttpRequest, 这个对象本身有一个getResponseHeader(DOMString header)的方法来获取。
如果是使用jQuery.ajax, 在success属性对应的回调函数中,第三个参数会被jQuery设置一个jqXHR的对象,这个对象是对XMLHttpRequest对象的一个封装,也是有getResponseHeader方法的。

不过我这里要说的是GM_xmlhttpRequest,也就是俗称的“油猴脚本”里的功能。在firefox里的油猴扩展是Greasemonkey,在chrome中则是Tampermonkey。它们都内置了GM_xmlhttpRequest方法,用于处理ajax事件。

GM_xmlhttpRequest有个很好用的地方是它不会受跨域限制(当油猴脚本跨域时,会先提示你是否允许跨域,允许即可)。

要使用GM_xmlhttpRequest,需要先在脚本头部引入GM_xmlhttpRequest:

// @grant        GM_xmlhttpRequest

然后用GM_xmlhttpRequest的head方法获取响应头:

GM_xmlhttpRequest({
	url: "url",
	method: "HEAD",
	onload: function(response) {
		console.log(response.responseHeaders);
	}
});

我获取了p站一个图片的响应头,输出类似下面:

Date: Tue, 07 Mar 2017 05:31:54 GMT
X-Content-Type-Options: nosniff
Last-Modified: Tue, 08 Mar 2016 09:00:36 GMT
Server: nginx
Content-Type: image/jpeg
Cache-Control: max-age=31536000
Accept-Ranges: bytes
Content-Length: 528794
Expires: Fri, 02 Mar 2018 10:41:44 GMT

不过我现在还有个疑惑,就是油猴怎么从响应头中提取某个特性属性的值。它好像没有getResponseHeader方法。

参考文档

这玩意让我栽了个坑,因为GM_xmlhttpRequest的head方法是异步的……所以我们需要在GM_xmlhttpRequest外定义一个函数作为回调函数,然后在GM_xmlhttpRequest获取到结果之后在GM_xmlhttpRequest里执行这个回调函数。

示例如下:

// 判断url是否可用
function testURL(url) {
	GM_xmlhttpRequest({
		url: url,
		method: "HEAD",
		onload: function(response) {
			// 获取请求头并在请求头内查找 Content-Type是否为image类型。如果图片网址是错的,那么Content-Type为提示错误的text/html类型。
			if (response.responseHeaders.indexOf("image/") > -1) {
				getResult(true);
			} else {
				getResult(false);
			};
		}
	});
}

var getResult = function(result) {
	if (result) {
		console.log("结果为true");
		//code......
	}else{
		console.log("结果为false");
		//code......
	}
}

testURL("http://i3.pixiv.net/img-original/img/2016/03/08/18/00/36/55694302_p0.jpg", getResult);

太蛋疼了……

后来我还发现有时候明明图片url是对的,但获取的状态码却是403的,判断失败,尚不不清楚原因。这导致我改进pixiv下载器的计划受阻了。

最后我还是用php做了这个功能,放弃油猴了……

header("Access-Control-Allow-Origin:http://www.pixiv.net");
function http_status($url) {
    $refer = "http://www.pixiv.net/";
    $ch = curl_init();
    curl_setopt($ch, CURLOPT_URL, $url);
    curl_setopt($ch, CURLOPT_HEADER, 1);
    curl_setopt($ch, CURLOPT_NOBODY, 1);
    curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
    curl_setopt($ch, CURLOPT_TIMEOUT, 5);
    curl_setopt($ch, CURLOPT_REFERER, $refer);
    curl_exec($ch);
    $status = (int)curl_getinfo($ch, CURLINFO_HTTP_CODE);
    curl_close($ch);
    return $status;
}
$url=$_GET['url'];
echo http_status($url);

GM_xmlhttpRequest获取响应头