项目中遇到浏览器跨域前端和后端解决方案以及大概过程

前言: ‌浏览器出于安全考虑,要求请求的 ‌协议(HTTP/HTTPS)、域名、端口(如 90/455 ‌ 三者完全一致,否则视为跨域。跨域问题的本质是 ‌浏览器通过同源策略保护用户数据安全‌,强制要求前后端资源同源。开发中因为环境分离、多域名部署等场景就会触发该策略的拦截机制‌。

一. 纯前端解决方案

1. ‌本地开发环境推荐使用代理解决‌‌

1.在Vue/React项目中配置 vue.config.jswebpack.config.js(vue3中是vite.config.ts文件)

js 复制代码
//vue3的Vite示例
export default defineConfig({
  // 服务端渲染
    server: {
      // 端口号
      port: "8980",
      host: "0.0.0.0",
      // 本地跨域代理 http://192.145.1.95:1216
      proxy: {
        "/admin-api": {
          // 这里填写后端地址
          // target: "https://test.com",
          target: VITE_API_PATH, //或者封装起来
          changeOrigin: true,
          rewrite: path => path.replace(/^\/admin-api/, ""),
          secure: false // 验证 SSL 证书
        }
      },
    },
});
// vue2的webpack示例示例
module.exports = {
    devServer: {
        proxy: {
            '/admin-api': {
                target: 'https://test.com',
                changeOrigin: true
            }
        }
    }
};

// 不同的前端语言大致实现思路都一样

2.重启开发服务器,前端请求本地路径包含 /api 自动代理到后端接口地址。

2. ‌利用WebSocket协议解决‌‌

WebSocket 解决跨域的核心原理是在 HTTP 握手阶段通过服务器主动验证 Origin 字段完成跨域授权,而非依赖浏览器同源策略的默认拦截机制‌

1.前端使用WebSocket建立连接:

js 复制代码
const socket = new WebSocket('ws://test.com:9090');
socket.onmessage = (event) => { console.log(event.data); };

2.后端需实现WebSocket服务端(如Socket.io)。

3.postMessage(跨窗口通信)

1.父窗口向iframe子窗口发送消息

js 复制代码
const iframe = document.getElementById('child-frame');
iframe.contentWindow.postMessage('data', 'http://child.com');

2.子窗口监听消息:

js 复制代码
window.addEventListener('message', (event) => {
    if (event.origin === 'http://parent.com') console.log(event.data);
});

二. 后端解决方案

1. ‌CORS(跨域资源共享)--->生产环境推荐 ‌‌

1.后端在响应头中设置 Access-Control-Allow-Origin,允许指定源访问:

java 复制代码
// Spring Boot示例
@CrossOrigin(origins = "http://localhost:9090")
@GetMapping("/api/data")
public String getData() { /*...*/ }

2.若需携带Cookie,需设置 Access-Control-Allow-Credentials: true 并指定具体源(不能为*)。

3.预检请求(如PUT、DELETE)需处理OPTIONS方法,返回允许的HTTP方法和头信息。

2. ‌Nginx反向代理--->生产环境推荐‌‌

1.在Nginx配置文件中添加代理规则:

nginx 复制代码
server {
    listen 90;
    server_name frontend.com;
    location /api {
        proxy_pass http://test.com:9090;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
    }
}

2.重启Nginx服务,使前端通过统一域名访问后端接口

3. ‌JSONP(仅GET请求) ‌‌

1.前端动态创建<script>标签,指定回调函数名:

js 复制代码
function handleData(data) { /*...*/ }
const script = document.createElement('script');
script.src = 'http://test.com/data?callback=handleData';
document.body.appendChild(script);

2.后端返回包裹回调函数的数据:

js 复制代码
handleData({ "result": "success" });

三、其他场景方案

同主域不同子域 ‌:设置 document.domain = 'test.com'(需主域相同)‌

IE兼容性‌:使用XDomainRequest对象替代XMLHttpRequest‌

结尾

推荐方案‌:生产环境优先使用CORS或Nginx反向代理‌,开发环境用本地代理‌更方便快捷(配置简单且无侵入性‌)

慎用方案‌:JSONP仅适用于简单GET请求且安全性较低‌(需注意XSS风险‌),postMessage适用于特定跨窗口场景‌。

如果兄弟们还有其他更方便的解决方案欢迎评论区讨论分享,具体实现还需根据项目来定最适合的解决方案

相关推荐
前端摸鱼匠1 小时前
Vue 3 的v-bind合并行为:讲解v-bind与普通属性合并的规则
前端·javascript·vue.js·前端框架·ecmascript
REDcker2 小时前
浏览器端Web程序性能分析与优化实战 DevTools指标与工程清单
开发语言·前端·javascript·vue·ecmascript·php·js
donecoding3 小时前
一个 sudo 引发的血案:npm 全局包权限错乱彻底修复
前端·node.js·前端工程化
风骏时光牛马3 小时前
Raku正则匹配与数据批量处理实操案例
前端
nbwenren3 小时前
2026实测:Gemini 3 镜像站视觉能力实践——拍照原型图,一键生成 HTML+CSS 代码
前端·css·html
Lee川3 小时前
Prisma 实战指南:像搭积木一样设计古诗词数据库
前端·数据库·后端
jinanwuhuaguo4 小时前
(第二十九篇)OpenClaw 实时与具身的跃迁——从异步孤岛到数字世界的“原住民”
前端·网络·人工智能·重构·openclaw
广州华水科技4 小时前
深度测评2026年单北斗GNSS位移监测系统推荐,与高口碑变形监测设备一同引领行业新风尚
前端
Alice-YUE4 小时前
【js高频八股】防抖与节流
开发语言·前端·javascript·笔记·学习·ecmascript