WebSocket 跨域问题解决:从 CORS 配置到 Nginx 反向代理的完整实战流程
通过以上方案,可彻底解决 WebSocket 跨域问题。WebSocket 协议本身支持跨域,但浏览器会验证服务器响应头中的。若服务端未正确配置,浏览器会拒绝连接。的 HTTP 请求。WebSocket 建立连接时,浏览器发送包含。组合方案,兼顾安全性与可维护性。
·
WebSocket 跨域问题解决方案:完整实战流程
问题本质
WebSocket 协议本身支持跨域,但浏览器会验证服务器响应头中的 Origin 字段。若服务端未正确配置,浏览器会拒绝连接。核心解决方案分两种:
- 服务端配置 CORS 头部
- Nginx 反向代理统一域名
方案一:服务端 CORS 配置(原生实现)
步骤 1:验证握手阶段
WebSocket 建立连接时,浏览器发送包含 Origin 的 HTTP 请求。服务端需在握手阶段返回允许的源:
// Node.js 示例 (使用 ws 库)
const WebSocket = require('ws');
const server = new WebSocket.Server({ port: 8080 });
server.on('connection', (socket, req) => {
// 业务逻辑...
});
// 处理握手请求
server.on('headers', (headers, req) => {
const origin = req.headers.origin;
if (origin === 'https://your-frontend.com') {
headers.push('Access-Control-Allow-Origin: https://your-frontend.com');
headers.push('Access-Control-Allow-Credentials: true');
}
});
关键响应头
| 头部字段 | 说明 |
|---|---|
Access-Control-Allow-Origin |
允许的源(需精确匹配) |
Access-Control-Allow-Credentials |
是否允许携带 Cookie(需设为 true) |
步骤 2:客户端连接
// 浏览器端代码
const socket = new WebSocket('wss://your-backend.com');
socket.onopen = () => {
console.log('跨域连接成功!');
};
方案二:Nginx 反向代理(生产推荐)
架构优势
客户端 → Nginx (统一域名) → WebSocket 服务
↑ 解决跨域 ↑ 隐藏真实端口
配置步骤
- 修改 Nginx 配置
server {
listen 80;
server_name your-domain.com;
location /ws {
proxy_pass http://localhost:8080; # 后端WS服务地址
# 关键协议升级配置
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
# 跨域控制
proxy_set_header Origin '';
add_header Access-Control-Allow-Origin * always;
}
}
- 重载 Nginx
sudo nginx -s reload
- 客户端连接
// 使用代理路径连接
const socket = new WebSocket('wss://your-domain.com/ws');
完整流程对比
| 方案 | 适用场景 | 优势 | 注意事项 |
|---|---|---|---|
| CORS 配置 | 直接控制后端代码 | 无需额外组件 | 需处理 OPTIONS 预检请求 |
| Nginx 代理 | 多服务/微服务架构 | 统一入口、负载均衡、隐藏端口 | 需维护 Nginx 配置 |
调试技巧
-
浏览器检查
- 在 DevTools → Network 查看 WebSocket 请求的
Response Headers - 验证是否存在
101 Switching Protocols状态码
- 在 DevTools → Network 查看 WebSocket 请求的
-
常见错误
403 Forbidden:Nginx 权限问题426 Upgrade Required:未配置协议升级头Origin mismatch:CORS 源配置错误
-
测试工具
# 使用 wscat 测试连接 npm install -g wscat wscat -c wss://your-domain.com/ws
安全增强建议
-
Origin 白名单校验
# Nginx 中校验 Origin if ($http_origin ~* (https?://(allowed1.com|allowed2.com))) { add_header Access-Control-Allow-Origin $http_origin; } -
WSS 加密传输
# 配置 SSL listen 443 ssl; ssl_certificate /path/to/cert.pem; ssl_certificate_key /path/to/privkey.pem; -
连接限流
# 限制每秒新连接数 limit_conn_zone $binary_remote_addr zone=wslimit:10m; limit_conn wslimit 20;
通过以上方案,可彻底解决 WebSocket 跨域问题。生产环境推荐使用 Nginx 反向代理 + WSS 加密 组合方案,兼顾安全性与可维护性。
更多推荐
所有评论(0)