浅析http状态码301、302、303、307、308区别及对SEO优化网址URL劫持的影响
http的重定向我们经常是张口就来,整个流程也非常简单,服务端HTTP返回码是30x,头里面的Location字段代表新的URL。如下图所示:
但重定向也还是有需要深入探讨地方,返回码不仅有我们经常使用301和303还有302 307 308 它们有啥区别呢。可以按照是否缓存和重定向方法,两个维度去拆分。
缓存(永久重定向) | 不缓存(临时重定向) | |
---|---|---|
转GET | 301 | 302、303 |
方法保持 | 308 | 307 |
如果是永久重定向那么浏览器客户端就会缓存此次重定向结果,下次如果有请求则直接从缓存读取,譬如我们切换域名,将所有老域名的流量转入新域名,可以使用永久重定向。
如果只是临时重定向那么浏览器则不会缓存,譬如我们的服务临时升级,会使用临时重定向。
方法保持的意思是原请求和重定向的请求是否使用相同的方法,譬如原请求是POST提交一个表单,如果是301重定向的话,重定向的请求会转为GET重新提交,如果是308则会保持原来POST请求不变。
一、状态码的解释
1、301 Moved Permanently(永久移动)
被请求的资源已永久移动到新位置,并且将来任何对此资源的引用都应该使用本响应返回的URI之一。如果可能,拥有链接编辑功能的客户端应当自动把请求的地址修改为从服务器反馈回来的地址。除非额外指定,否则这个响应也是可缓存的。新的永久性的URI应当在响应的Location域中返回。除非这是一个HEAD请求,否则响应的实体中应当包含指向新的URI的超链接及简短说明。如果这不是一个GET或者HEAD请求,因此浏览器禁止自动进行重定向,除非得到用户的确认,因为请求的条件可能因此发生变化。
注意:对于某些使用HTTP/1.0协议的浏览器,当它们发送的POST请求得到了一个301响应的话,接下来的重定向请求将会变成GET方式。
// 客户端发出请求
GET /blog HTTP/1.1
Host:www.example.com
// 服务端响应,不带Cache-Control头部
HTTP/1.1 302 Moved Permanently
Location:http://www.example.org/index.asp
// 服务端响应,带Cache-Control头部
HTTP/1.1 302 Moved Permanently
Location:http://www.example.org/index.asp
Cache-Control:private;max-age=600;
2、302 Found(发现)
要求客户端执行临时重定向(原始描述短语为“Moved Temporarily”)。由于这样的重定向是临时的,客户端应当继续向原有地址发送以后的请求。只有在Cache-Control或Expires中进行了指定的情况下,这个响应才是可缓存的。新的临时性的URI应当在响应的Location域中返回。除非这是一个HEAD请求,否则响应的实体中应当包含指向新的URI的超链接及简短说明。如果这不是一个GET或者HEAD请求,那么浏览器禁止自动进行重定向,除非得到用户的确认,因为请求的条件可能因此发生变化。
注意:虽然RFC 1945和RFC 2068规范不允许客户端在重定向时改变请求的方法,但是很多现存的浏览器将302响应视作为303响应,并且使用GET方式访问在Location中规定的URI,而无视原先请求的方法。因此状态码303和307被添加了进来,用以明确服务器期待客户端进行何种反应。
3、307 Temporary Redirect(临时重定向)
在这种情况下,请求应该与另一个URI重复,但后续的请求应仍使用原始的URI。 与302相反,当重新发出原始请求时,不允许更改请求方法。 例如,应该使用另一个POST请求来重复POST请求
4、308 Permanent Redirect (永久重定向)
请求和所有将来的请求应该使用另一个URI重复。
307和308分别重复302和301的行为,但不允许HTTP方法更改。 例如,将表单提交给永久重定向的资源可能会顺利进行。
5、301/302/303/307/308的区别
301,302是http1.0的内容,303、307、308是http1.1的内容。
301和302本来在规范中是不允许重定向时改变请求方法的(将POST改为GET),但是许多浏览器却允许重定向时改变请求方法(这是一种不规范的实现)。
303的出现正是为了给上面的301,302这种行为作出个规范(将错就错吧),也就是允许重定向时改变请求方法。此外303响应禁止被缓存。
大多数的浏览器处理302响应时的方式恰恰就是上述规范要求客户端处理303响应时应当做的,所以303基本用的很少,一般用302。
307和308的出现也是给上面的行为做个规范,不过是不允许重定向时改变请求方法。
总结一下就是:
(1)301、308是永久改变地址;302/303、307是临时改变地址;
(2)301、302允许改变请求方法(post会改get);308、307不允许改变请求方法(post方法还是post方法)
注:永久(Permanent)和临时(Temporary)的区别:永久是指原来访问的资源已经永久删除啦,客户端应该根据新的URI访问重定向。临时是指访问的资源可能暂时先用location的URI访问,但旧资源还在的,下次你再来访问的时候可能就不用重定向了。
(3)对SEO的友好性:(这里有些面试会问)
301与302的区别:301表示搜索引擎在抓取新内容的同时也将旧的网址交换为重定向之后的网址;302表示旧地址A的资源还在(仍然可以访问),这个重定向只是临时地从旧地址A跳转到地址B,搜索引擎会抓取新的内容而保存旧的网址。
由此可知301对于SEO更友好,下面来详细介绍。
二、301、302对SEO优化的影响及网址URL劫持
301和302跳转,虽然最终看到的效果是一样的,但对搜索引擎来讲,301和302还是有区别的。301的含义是“永久重定向”,而302的含义是“临时重定向”,那么,为什么不能用302呢?302 重定向和网址劫持(URL hijacking)有什么关系呢?这要从搜索引擎如何处理302转向说起。
从定义来说,从网址A做一个302重定向到网址B时,主机服务器的隐含意思是 网址A随时有可能改主意,重新显示本身的内容或转向其他的地方。大部分的搜索引擎在大部分情况下,当收到302重定向时,一般只要去抓取目标网址就可以 了,也就是说网址B。实际上如果搜索引擎在遇到302转向时,百分之百的都抓取目标网址B的话,就不用担心网址URL劫持了。
问 题就在于,有的时候搜索引擎,尤其是Google,并不能总是抓取目标网址。为什么呢?比如说,有的时候A网址很短,但是它做了一个302重定向到B网 址,而B网址是一个很长的乱七八糟的URL网址,甚至还有可能包含一些问号之类的参数。很自然的,A网址更加用户友好,而B网址既难看,又不用户友好。这 时Google很有可能会仍然显示网址A。
由于搜索引擎排名算法只是程序而不是人,在遇到302重定向的时候,并不能像人一样的去准确判定哪一个网址更适当,这就造成了网址URL劫持的可能性。也就是说,一个不道德的人在他自己的网址A做一个302重定向到你的网址B,出于某种原因, Google搜索结果所显示的仍然是网址A,但是所用的网页内容却是你的网址B上的内容,这种情况就叫做网址URL劫持。你辛辛苦苦所写的内容就这样被别 人偷走了。
其实302的跳转本身是没有错的,但因为被一些作弊者用多了,Google当然对这个就比较敏感了,毕竟Google面对的是如此海量的数据,你难道不怕被误杀吗?Google的官方内容一再强调用301来转移内容,况且,301和302在程序上的设置相差很小,既然如此,何必要冒险用302呢?如果你对上面还是没有看懂看看下面的的内容就知道了。
PR劫持的SEO作弊方法:
1、利用301和302跳转
一般搜索引擎在处理301和302转向的时候,都是把目标URL当作实际应该收录的URL。如果你从域名A做301或者是302跳转到域名B,而域名B的 PR 值比较高,域名A在PR更新后,也会显示域名B的PR值。PR挟持最简单的就是先做301或302跳转到高PR的域名B,等PR更新过后,立刻取消转向, 同时也获得了和B站相同的PR值。这个做假的PR显示值至少维持到下一次PR更新。
我的理解是,从网站A(网站比较烂)上做了一个302跳转到网站B(搜索排名很靠前),这时候有时搜索引擎会使用网站B的内容,但却收录了网站A的地址,这样在不知不觉间,网站B在为网站A作贡献,网站A的排名就靠前了。
302 重定向所造成的网址URL劫持现象,已经存在一段时间了。不过到目前为止,似乎也没有什么更好的解决方法。在正在进行的谷歌数据中心转换中,302 重定向问题也是要被解决的目标之一。从一些搜索结果来看,网址劫持现象有所改善,但是并没有完全解决。
301跳转对查找引擎是一种对照驯良的跳转编制,也是查找引擎能够遭遇的跳转编制,它告诉查找引擎,这个地址弃用了,永远转向一个新地址,可以转移新域名的权重。而302重定向很容易被搜索引擎误认为是利用多个域名指向同一网站,那么你的网站就会被封掉,罪名是“利用重复的内容来干扰Google搜索结果的网站排名”。
2、欺骗Google蜘蛛
通过程序检测到Google蜘蛛,返回301或302转向,对普通访问者和其他蜘蛛都返回正常内容。这样我们看到的是普通网站,只有Google会看到转向,但是这种网站上的链接对PR值没有任何贡献。
三、使用场景
因为301与302的区别,所以导致产生302网址劫持,故不建议使用302重定向(然而浏览器默认是使用302重定向)
1、使用301的场景:(一般是资源位置永久更改)
(1)域名到期不想续费(或者发现了更适合网站的域名),想换个域名。
(2)在搜索引擎的搜索结果中出现了不带www的域名,而带www的域名却没有收录,这个时候可以用301重定向来告诉搜索引擎我们目标的域名是哪一个。
(3)空间服务器不稳定,换空间的时候。
注:另外,返回301请求码进行跳转被谷歌认为是将网站地址由 HTTP 迁移到 HTTPS的最佳方法(然而大家都用302。。。。)
2、使用302的场景:(一般是普通的重定向需求:临时跳转)
(1)未登录前先使用302重定向到登录页面,登录成功后再跳回到原来请求的页面
举个例子,比如我未登录京东前我就访问京东的个人界面https://home.jd.com/,然后就会重定向到登录界面,我们可以通过浏览器的dev-tool查看状态码,有
我们可以发现响应的状态码为302,并且返回了location为登录界面的url,并且附带了ReturnUrl方便我们登录后跳回到https://home.jd.com/
(2)像微博之类的使用短域名,用户浏览后需要重定向到真实的地址之类。
例如我访问一个微博的秒拍视频链接:http://t.cn/RuUMBnI,然后重定向到了实际的视频地址miaopai.com,状态码为302。
3、使用307或308的场景
307很少用,与302类似,只不过是针对POST方法的请求不允许更改方法,不过我在访问百度时,发现用了307状态码
308也很少用,与301类似,只不过是针对POST方法的请求不允许更改方法。