[工程架构思考-请求] 协议自适应

43 阅读2分钟

背景/场景

  • 在站点 tieba.baidu.com -> 发起 ajax 请求,调用 -> www.baidu.com 的接口

比如: 在 http 环境下:tieba.baidu.com -> ajax -> www.baidu.com/api/v1/user

后来 baidu 站点也可以在 https 环境访问了:

新版本:tieba.baidu.com -> ajax -> www.baidu.com/api/v1/user

痛点/问题

A、B域名升级为 HTTPS,且其同时又要支持http访问,那么对前端带来了糟糕的开发体验:

  1. 在每次请求接口时,就需要根据当前是http还是https,在接口请求的时候,补充协议协议

  2. 上面一种代码看起来就比较糟糕了,能有更优雅的方式吗?:在统一请求拦截器的地方,获取站点域名协议,将其添加在接口API前面

  3. 还是需要编码,能否有更好的方案,有的,如下: 协议自适应,即浏览器自动识别当前协议,在请求的时候自动补充对应协议即可,参见解决方案

  4. 引申一个问题:无论是http还是https的网址,都请求https 接口可不可以? 答案:不可以❌ 原因:Chrome 90之后,即使大家是同一个域名下,但跨协议请求将无法携带cookie,会导致 401。这样会导致一个现象:访问http业务页面 请求https接口 cookie无法携带 401 - 跳转至sso登录页,登录页判断其有cookie - 跳转至原页面 - 原页面请求又请求https接口 又 401 死循环 如何解决:

  • 方案1: http网址请求http接口,不要跨协议请求 -> 协议自适应

  • 方案2: 全站升级https(推荐)

解决方案

协议自适应(这里的协议是指:网络请求协议,比如 http/https/file/ftp等)

详解: 在请求 baidu.com 的API 的时候,写成 $.ajax('//baidu.com/api/xxx/') 即可,也就是省略目标站点协议,根据 origin 的协议自动适配。

扩展应用场景: 该方式也适用于请求第三方 CDN 资源,比如 Bootstrap、jQuery...(为啥:因为作为静态资源cdn提供方,无法得知你的站点是跑在啥协议下的,那怎么办?自适应呗,当然协议自适应是一个https过渡期间的方案,还是期待全站https)

对了,// 开头的链接也可以视作绝对链接😂