IOS低版本系统,APP内嵌H5请求跨域Network Error问题

1,718 阅读2分钟

一、问题背景:

APP中有一个功能是H5做的,通过webview加载显示,H5页面中会请求后端,获取数据后,展示页面给用户。上线后陆续收到用户反馈此页面无法打开,报Network Error错误。

二、问题排查过程

  • 开始怀疑是因为网络原因导致没有加载完成,缓存问题,引导用户清除缓存以后,问题还存在。
  • 通过对日志的详细排查,发现用户有对应接口的OPTIONS请求,但是没有后续POST请求。分析应该是跨域问题引起的。
  • 但是后端的跨域设置本身应该是没问题的,上线前包括上线后绝大部分用户都是正常的。
  • 根据陆续的反馈,发现用户主要集中在IOS用户,系统版本集中在iOS12,IOS12是2018年发布的,已经有5年了,合理怀疑和IOS12版本有关系。
  • 结合上面结论,优先排查方向是,IOS12跨域问题设置问题。
  • 通过对国内外网站的一波搜索,基本定位是IOS12跨域请求不支持通配符(也就是*)的问题。网上搜索的原因说的是Access-Control-Allow-Origin不支持*,需要配置成对应的origin,比如a.com 设置以后,经过一波验证发现问题还存在。

三、结论

最后经过反复测试,发现不止Access-Control-Allow-Origin不支持*,而是所有跨域相关的header头都不要设置*,网上的解决方案只说了Access-Control-Allow-Origin的设置,并没有说Access-Control-Allow-Headers推测是因为对方没有传递自定义header头,但是我们的场景是有传自定义header头的。最后修改后header头如下:

res.setHeader("Access-Control-Allow-Origin", origin); // origin是对应的允许跨站的域名
res.setHeader("Access-Control-Allow-Methods","POST,OPTIONS,GET");
res.setHeader("Access-Control-Allow-Headers","Accept,content-type....");
res.setHeader("Access-Control-Max-Age", "3600");

Access-Control-Allow-Headers 的设置会比较麻烦,为了防止漏掉某个参数最好是比对OPTIONS请求的access-control-request-headers头来设置。options请求的access-control-request-headers会把需要跨域的header头都会带上,参考着设置肯定不会有问题。

到此为止问题解决,此问题来来回回耗时2天,主要是因为问题不容易复现,需要反复测试,加上我们有自定义header头也走了一些弯路。在此记录一下,希望能让帮助到后续遇到此问题的朋友。