怎样避免跨域发出OPTIONS请求?

2021-10-13  本文已影响0人  Small_Song

前言

我们在做移动开发的时候,往往在服务器中加入Access-Control-Allow-Origin,用来跨域,虽然这是最简单的跨域方案了,但是有一个问题,就是每一次正式请求的前面总是会带上一次OPTIONS请求,一些程序员往往一头雾水。

image

image.png

原因

浏览器在处理跨域请求之前,会先对跨域请求做一个分析,将跨域请求分为2种:简单请求,和非简单请求。

具备以下特征的是简单请求:

  1. 请求方式只能是:GET、POST、HEAD

  2. HTTP请求头限制这几种字段:Accept、Accept-Language、Content-Language、Content-Type、Last-Event-ID

  3. Content-type只能取:application/x-www-form-urlencoded、multipart/form-data、text/plain

凡是超出这些限制的请求一律被浏览器视为复杂请求,如果想跨域,浏览器会发送一个OPTIONS请求,跟服务器一探究竟。

如果服务器返回的数据让浏览器很满意,那么浏览器才会发出正式请求。

怎样避免OPTIONS请求?

因为OPTIONS请求也是占带宽和时间的,从上图也可以看到,每个请求都带一个OPTIONS,非常难受。怎么避免?

改默认请求类型

axios的默认请求内容类型是application/json,这就倒霉催的了,只能是修改成application/x-www-form-urlencoded。相应的,post数据的时候,要用qs库。具体做法去搜索吧。

还是不行,咋回事?

你肯定是往headers里放东西了。别放就行了。

有人说了,我token就喜欢放在headers里,怎么办?

这下子前端是没有好办法了,只能从后端想办法了,就是使用Access-Control-Max-Age。

这需要后端同学配合,在设置OPTIONS跨域响应headers的时候,添加 Access-Control-Max-Age ,这个参数的意思是把 OPTIONS 响应缓存起来,在指定的时间内,不会再次发起 OPTIONS 预请求,这样只有在第一次请求的时候会有 OPTIONS ,之后浏览器会从缓存里读取响应,也就不会再发送OPTIONS请求了。比如:

// 后端设置,2592000,单位秒,也就是30天,如果是一天,就是86400
response.addHeader( "Access-Control-Max-Age", "2592000" )

注意,后端只需要处理OPTIONS请求,不要改正常的GET、POST请求。

上一篇下一篇

猜你喜欢

热点阅读