CORS预检请求返回400:同配置Flask服务Swagger跨域调用失败排查
可能的原因及排查步骤
- 反向代理/CDN拦截OPTIONS请求
这是最高概率的原因,大部分云CDN、Nginx反向代理默认不会转发OPTIONS类型的跨域预检请求,会直接返回400响应,请求根本没有到达你的Flask服务层,耗时翻倍也符合代理层拦截的特征。
排查方法:直接在b服务部署的服务器本地执行curl命令测试Flask进程的OPTIONS响应:
如果本地请求返回200且携带正确的CORS响应头,即可确认是前置代理/CDN的配置问题,需要在代理层开启OPTIONS请求转发,或者配置代理层直接返回CORS预检响应。curl -v -X OPTIONS \ -H "Origin: https://swagger.mydomain.com" \ -H "Access-Control-Request-Method: POST" \ http://127.0.0.1:<你的Flask服务端口>/<测试接口路径> - 全局中间件拦截了OPTIONS请求
如果你给b服务配置了全局的请求参数校验、身份校验中间件,且没有对OPTIONS请求做豁免处理,中间件会因为OPTIONS请求没有携带业务参数、身份凭证直接返回400错误,请求还没到达Flask-CORS的处理逻辑。
排查方法:注释掉b服务所有全局中间件后重试,或者在中间件中添加逻辑,遇到OPTIONS请求直接放行。 - Flask-CORS初始化顺序错误
Flask-CORS必须在路由注册之前完成初始化,如果你的b服务代码是先写了@app.route路由注册逻辑,再执行CORS(app),CORS配置对已经注册的路由不会生效。对比a、b两个服务的代码初始化顺序,确保CORS(app)执行在所有路由注册之前。 - 依赖版本差异
检查两个服务的flask、flask-cors依赖版本是否一致,旧版本的flask-cors对正则格式的origin匹配存在已知bug,可能导致合法Origin被拦截。可以执行pip list | grep -E "flask|Flask-CORS"对比两个服务的依赖版本。 - 小优化建议
你当前的CORS正则配置存在被恶意域名绕过的风险,可以优化为严格匹配子域名的格式:CORS(app, origins=r"^https?://.*\.mydomain\.com$")
内容的提问来源于stack exchange,提问作者Syzygy
相关产品推荐
相关产品推荐

