Access-Ctrol-Allow-Headers:*兼容问题导致的跨域失败
現象:
通過抓包看到在部分客戶端上跨域的非簡單請求只發送一個預檢的OPTIONS請求,之后的真實請求并沒有發送。
出現問題的環境:
部分IOS低版本系統。
windows系統微信內必現(2020-04-29)。
分析
通過上面條件OPTIONS請求發送成功,但是實際請求沒有發送,可以推斷出是服務端相關HTTP頭沒有設置正確,導致客戶端認為服務端不允許當前源上的web應用跨域訪問該資源,所以后面真正的請求沒有發送(fetch的表現為status: 0)。
服務端響應頭如下:
Access-Control-Allow-Origin: * Access-Control-Allow-Headers: * Access-Control-Allow-Methods: *正常來說不存在問題,因為設置的值也都是合法的,并且在絕大部分客戶端上都是正常的。
CORS定義:
CORS跨域資源共享,是通過額外的HTTP頭來告訴瀏覽器,源上的web應用被允許訪問來自不同源服務器的指定資源。
這里額外的HTTP頭值得注意,可以看出來CORS在不同的瀏覽器上可能是有兼容性問題。
方案
一開始的猜想是HTTP請求的method的值OPTIONS被客戶端錯誤設置為小寫,導致服務端異常。但是通過抓包看到OPTIONS請求正確返回(status: 204),并且后端日志中并未收到小寫的OPTIONS請求。所以這個排除。
然后著眼于服務端返回的相關HTTP頭
Access-Control-Allow-Origin: * Access-Control-Allow-Headers: * Access-Control-Allow-Methods: *本地復現出來,并排查是因為Access-Control-Allow-Headers: * 導致的,這個屬性有某些兼容性問題。
Access-Control-Allow-Headers: *
MDN中介紹 Access-Control-Allow-Headers: * 有兩重意思。
一個是在服務端設置Access-Control-Allow-Credentials: true的時候這個 * 只會被客戶端當做字符串 * (我們不希望的,會出錯的)。
另一個是沒有這個設置則會被當做通配符(我們希望的,不會出錯的)。
猜測是客戶端對于 * 的實現上有兼容性問題,所以建議不要這樣設置,用到什么設置什么最好,例如:Access-Control-Allow-Headers: Content-Type。
之后成功排除了問題。
結論
Access-Control-Allow-Headers: * 在部分客戶端上有兼容問題。
注:跨域錯誤是不會暴露給JS的,就意味著 try{}catch(corsError){corsError.message}拿不到錯誤的具體信息,不太好在沒有控制臺的環境看到問題。
總結
以上是生活随笔為你收集整理的Access-Ctrol-Allow-Headers:*兼容问题导致的跨域失败的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: CORS(跨域资源共享)
- 下一篇: 阅读react-redux源码 - 一