HTTPS页面请求HTTP接口被浏览器直接拦截,属混合内容(Mixed Content)问题:因安全上下文要求,主动型子资源(如fetch、XMLHttpRequest)必须使用HTTPS协议,否则请求在发出前即被静默阻止,控制台报“Mixed Content”错误且Network面板无记录。

HTTPS 页面请求 HTTP 接口时,浏览器会直接阻止该请求,这不是 CORS 错误,而是混合内容(Mixed Content)拦截——它比 CORS 更早触发、更严格,且无法通过任何响应头绕过。
为什么 HTTPS 页面不能请求 HTTP 接口
现代浏览器(Chrome、Firefox、Edge 等)将主动型混合内容(如 script、fetch、XMLHttpRequest、WebSocket)视为高风险行为。当页面本身通过 HTTPS 加载,却试图用 不加密的 HTTP 协议 请求接口时,浏览器会在控制台报类似错误:
这个拦截发生在网络层,请求根本不会发出,所以你不会看到 OPTIONS 预检、也不会收到 400/500 响应,控制台里连 fetch 的 network 记录都找不到。
如何快速确认是混合内容而非 CORS
- 打开浏览器开发者工具 → Network 标签页,发起请求后看是否完全没有该请求的记录(而不是显示 failed 或 cors error)
- 查看 Console,找关键词 Mixed Content 或 was loaded over HTTPS, but requested an insecure resource
- 把 URL 中的
http://手动改成https://,粘贴到新标签页访问,看接口是否能正常返回数据(验证后端是否支持 HTTPS)
解决方式只有两个方向
-
后端必须提供 HTTPS 接口:这是唯一合规方案。检查你的 API 是否已部署 HTTPS(有有效证书),并确保前端调用地址使用
https://开头。自签名证书或过期证书也会被拦截,需用 Let’s Encrypt 或商业 CA 签发的有效证书 -
开发阶段临时规避(仅限本地):Chrome 启动时加参数
--unsafely-treat-insecure-origin-as-secure="http://api.example.com" --user-data-dir=/tmp/chrome-test;但此方式不适用于测试环境或他人访问,且新版 Chrome 已逐步限制
常见误判与补充提醒
- 不要在 Nginx 或后端加 CORS 头来“修复”混合内容——它压根没走到那一步
- 代理配置(如 vite.config.ts 中的 proxy)只在开发服务器运行时生效,它把
/api转发到http://localhost:8080是安全的,因为浏览器认为仍是同源(都是https://localhost:5173发起,代理由本地 dev server 完成),但上线后必须用 HTTPS 目标地址 - 微信小程序、uni-app 等平台对混合内容同样拦截,且不提供绕过方式,必须全链路 HTTPS


















