Http重定向

HTTP1.0在介绍302时说,如果客户端发出POST请求后,收到服务端的302状态码,那么不能自动的向新的URI发送重复请求,必须跟用户确认是否该重发,因为第二次POST时,环境可能已经发生变化(嗯,POST方法不是幂等的),POST操作会不符合用户预期。但是,很多浏览器(user agent我描述为浏览器以方便介绍)在这种情况下都会把POST请求变为GET请求。

HTTP1.1在介绍302时说,如果客户端发出非GET、HEAD请求后,收到服务端的302状态码,那么就不能自动的向新URI发送重复请求,除非得到用户的确认。但是,很多浏览器都把302当作303处理了(注意,303是HTTP1.1才加进来的,其实从HTTP1.0进化到HTTP1.1,浏览器什么都没动),它们获取到HTTP响应报文头部的Location字段信息,并发起一个GET请求。

  从上面的介绍可以知道,HTTP1.1和HTTP1.0的302状态码意义是一样的,浏览器对它的处理也是一样的。POST方法的重定向在未询问用户的情况下就变成GET,这种不符合文档规范的问题依然存在。实践在前而文档在后,HTTP1.1把这种POST变GET的行为纳入了RFC文档:HTTP1.1新加入303和307状态码。

    文档中规定303状态码的响应,也就是上边提到的现在浏览器对302状态码的处理:POST重定向为GET。

    HTTP1.1文档中307状态码则相当于HTTP1.0文档中的302状态码,当客户端的POST请求收到服务端307状态码响应时,需要跟用户询问是否应该在新URI上发起POST方法,也就是说,307是不会把POST转为GET的。

  为兼容很多HTTP1.1之前的浏览器,服务端在需要发出303状态码时,会选择用302状态码替代;而对于307的处理,则需要在响应实体中包含信息,以便不能处理307状态码的用户有能力在新URI中发起重复请求,也就是说,把重定向的页面展示给用户,让用户去点重定向URI链接(URI现在基本就是URL)。

当前如果是现在的主流浏览器,收到307的状态会继续以post方式去访问新的URL

在serlvlet中,需要重定的时候,我们都习惯调用response.sendRedirect来实现。

但是我们往往没有去想,这个函数底层做了什么?

  其实很简单,这个函数的功能,类似于

response.setStatus(302);  
response.setHeader("Location", "URL");

wireshark抓包如下

    

但是302这个状态码,意味着浏览器会以get方式向新的URL发起请求。如果原先的请求是post方式的,也会因为重定向后,改成get方式。

response.setStatus(307);  
response.setHeader("Location", "URL");  

我们可以通过在servlet中自己设置状态码和header中的location以及其他一些header参数,来实现post方法重定向后依然使用post方式向新的URL发起请求。

https://www.cnblogs.com/bruce-L/p/4035428.html

https://blog.csdn.net/nakey_xie/article/details/82837413

猜你喜欢

转载自blog.csdn.net/sinat_33822516/article/details/89222161