HTTP-308

 

原文地址:https://airbrake.io/blog/http-errors/308-permanent-redirect

308永久转移:是什么,怎么修复它?

308是http的状态返回码,用来表示当前请求的资源已经永久的转移到其他的uri,一般通过返回header的location字段展示。308code是近期在2015年4月加入到http标准库的,文档RFC7538有对308状态码的详细描述。就像RFC7538描述的那样308状态码适合和301,302,307这类状态码放一起。

事实上,有几十种http状态码用来表示客户端,web应用,web服务器和第三方web服务之间复杂的关系,所以找到产生http code码的原因是一件非常困难的事情。应为,还有很多潜在的http code码,它们用来表示完全不同的状态和事务,这就更加剧了区分它们的不同的困难,和找到产生它们的原因的困难,例如308 状态码。

通过几个有用的点,整篇文章我们一起探索308状态码。我们也会用几个简单又实用的方法修复引起308 状态码的一般性问题。让我们开始吧。

服务端问题

所有的3XX类的状态码都是定向类问题。这类状态码提示客户端(例如你的浏览器)需要执行附加的动作来完成请求动作,或者获取到想要的资源。3XX类的状态码很明显和5XX类的状态码不同,5XX类的状态码明显包含着服务段的错误信息。例如503错误,服务不可用,我们可以通过这个状态码探索一个网站近一年内临时不可用。不同于一个5xx错误能够明确的表示这是服务端的错误,3XX类的几乎不可能准确的表示一个错误,它仅仅只能提示服务的行为或者配置有可能有问题,不表示服务端有bug或者错误。

308状态码和301状态码很相似,着篇文章讲述什么是301错误码和如何修复它https://airbrake.io/blog/http-errors/301-moved-permanently。像前文提到的那样,RFC1945 HTTP/1.0 标准文档明确的声明301没必要通知客户端(例如浏览器)自动重定向POST请求到GET请求。然而,很多客户端错误的将post的请求转化成get请求,并引出了不可预知的问题。

为了明确的控制这个从POST请求转化成GET请求,HTTP标准包含以下码:

    301:资源已经永久的转移,允许将POST改成GET

    307:  资源临时转移,不允许将post改成get

    302:   资源临时转移,允许将POST改成GET

你可以看到,这组三个状态码,缺少一个状态码用来表示资源永久转移,不允许将post改成get。这个正是308错误码的意义。

出现308状态码一般情况下不需要用户特别关心。所有的流行的浏览器都会自动的检测308状态码,并且自动的转到相应的地址。服务端返回308状态码的时候还会包含location头,返给客户端。location header 会提示新的资源地址。例如,如果客户端通过post方法尝试登录https://airbrake.io,web服务器可能会重定向到不同的地址,如https://airbrake.io/login。在这种场景下,服务器将返回308状态码和Location: https://airbrake.io/login header。这是告诉客户端(浏览器)post请求已经被服务器接受,但是资源已经被永久的移动到了Location header : https://airbrake.io/login。

区分使用308和其它类似的错误码的场景同样非常重要,例如上面提到的307状态码。307状态码告诉客户端Location URI只是临时的资源地址,后面所有的请求会继续访问原始的地址。相反308状态码告诉客户端,这次转移是永久转移,后面所有的请求将访问新的地址。

另外,因为308 状态码预示着服务端的应用有什么错误,我们可以忽略客户端的。如果你在尝试诊断你的应用,你可以立刻忽略客户端的代码和插件,例如html,css,js。这不仅仅适用于web网站。许多智能手机app也是一样。在你使用app的时候,出现了308状态码,一般不会是安装在你手机上或测试设备上的app的原因。相反,它可能是服务端的问题。

如果你的应用产生了意想不到的308状态码,这里有很多步骤帮助你定位问题,所以下面让我们一起探索。

首先做一个完整的备份

无论何事,最好在一开始就做好安全措施,而不是在半路上去拧螺丝,去后悔。因此,在尝试修复和更改你的系统之前,很有必要先对你的应用,数据库等做一个备份。更甚至你有能力的话,完全拷贝当前应用到一个不公开的平台上。这将提供给你一个非常干净的环境,去测试为解决问题而做的潜在的修改,这样也不会有安全问题,也不会以侵犯你的线上服务。

诊断308状态码

308状态码预示着请求的资源已经永久的迁移到新的URI,这个一般通过response header的location指定。然而,出现308也许本身就是一个误导,因为它完全有可能是服务器配置错误引起,服务器的错误配置可能会引起不合适的response同时带着308,而不是标准的200。这样,大部分时候通过诊断产生308状态码的代码能解决问题。

如果你的应用返回了308而它不应该返回,这个问题很多人都应该遇到过,神奇般的阻止应用为用户提供服务。下面我们根据一些检测点和技巧来解决这个问题。如果这些技巧也没有用的话,不要忘记去goole找答案。输入和你的问题相关的词条加上308,例如你的应用的名称或者web服务器软件。你将有机会找到遇到过此问题并解决这个问题的人。

检查服务端

这里有几条秘诀会帮助你检查在服务端是什么原因引起308。

确认你的服务配置

你的应用很可能运行在nginx或者apache服务器上。在文章发布时,这两个服务器软件占有84%的市场占有率。这样,第一步要做的就是检查配置文件里跳转相关的指令。

要找到你的应用使用的是哪个服务器,你需要找到关键文件。如果你使用的是Apache那就去网站的根目录找.htaccess文件。例如,如果你的应用使用了共享的主机,相应的你需要有一个对应的账号。在这种情况下,应用的根目录像这样/home/<username>/public_html/,而 .htaccess 将在 /home/<username>/public_html/.htaccess。

如果你已经定位了.htaccess文件,使用文本编辑器打开它找到RewriteXXX指令。仔细检查所有的规则是否正确,然而,基本的观念是rewriteCond指令定义基本的模型匹配传入的URL。当用户访问网站时候,如果一个url被一个或者多个Rewritecond匹配上,则将会定向到最合适的地址。

例如,这里有一个简单的RewriteCond和RewriteRule绑定,它将匹配所有的post请求,通过308将airbrake.io重定向到https://airbrake.io/login

RewriteEngine on
RewriteCond %{HTTP_HOST} ^airbrake.io$
RewriteRule ^(.*)$ http://airbrake.io/login$1 [R=308]

注意RewriteRule最后的标签,这个标签用来明确的声明返回的状态码是308,指示客户端请求应该重定向到指定的URI,同时仍然使用原来的HTTP方法(本例是指POST)。这样,如果你在.htaccess发现任何奇怪的RewriteCond或者RewriteRule指令,可以尝试去注释它们,然后重启服务去看看是否解决了问题。

另一方面,如果你的用的是nginx服务,你需要找一个和apache完全不同的配置文件。一般情况下这个文件是nginx.conf,并且这个文件一般放在以下共有目录下:/usr/local/nginx/conf/etc/nginx, 或者 /usr/local/etc/nginx。一旦定位文件后,使用文件编辑器打开nginx.conf,找到使用308的return或者rewrite指令。例如,这有一个简单的block指令,配置一个虚拟服务将POST请求从airbrake.io定向到airbrake.io/login。

server {
    listen 80;
    listen 443 ssl;
    server_name airbrake.io;
    if ($request_method = POST) {
        return 308 https://airbrake.io/login$request_uri;
    }
}

nginx的Return指令和Apache里面的RewriteCond和RewriteRule指令相似,它们都趋向于包含复杂的基于文本的模式用于搜索。无论哪种方式,通读nginx.conf文件找到不正常的包含308标签的return和rewrite指令。将不正常的指令注释掉,重启服务检查是否能解决问题。

检查日志

 几乎所有的应用都保存服务端日志。应用日志代表了应用的操作历史,例如哪个页面被访问了,哪个服务被链接了,它提供了哪个数据库的数据,等等。服务日志记录了硬件的实际运行情况,也会提供服务的运行状态。如果你使用CMS可以goole“logs[PLATFORM_NAME]”,如果你正在运行一个客户端应用可以goole“logs[PROGRAMMING_LANGUAGE]”和“logs[OPERATING_SYSTTEM]”,通过日志信息可以获取到有关问题的更多日志。

调试你的应用代码

如果以上都失败了,那么它有可能是你代码的问题,引起的问题。试着通过手动调试你的代码,来定位问题。在理想环境下,将整个应用拷贝到开发机器,一步一步调试程序,这将允许你重现308的时候错误。

无论是什么原因引起的,308在你的应用中的出现预示着你可能需要一个错误管理工具在将来帮助你自动检测这类错误。工具的最大好处是当错误出现的时候能立刻通知你和你的团队。

  • 2
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值