目录
[2.VUE CLI代理](#2.VUE CLI代理)
[1.Vue CLI代理](#1.Vue CLI代理)
[1. 什么是跨域](#1. 什么是跨域)
[2. 跨域的例子](#2. 跨域的例子)
[3. 配置代理解决跨域问题](#3. 配置代理解决跨域问题)
[4. 如何配置代理](#4. 如何配置代理)
一、Websocket跨域问题
1. nginx配置
bash
server {
listen 8004;
server_name 192.168.80.4;
client_max_body_size 10M;
ssl_protocols TLSv1 TLSv1.1 TLSv1.2;
server_tokens off;
proxy_buffering on;
proxy_buffer_size 1024k;
proxy_buffers 100 1024k;
proxy_busy_buffers_size 2048k;
location / {
root im-web;
index index.html index.htm;
}
# IM 接口
location /imapi/ {
proxy_pass http://192.168.80.4:8888/;
}
# WebSocket
location /im/ {
proxy_pass http://192.168.80.4:8878/;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
}
}
2.VUE CLI代理
bash
module.exports = {
devServer: {
proxy: {
'/imapi': {
target: 'http://192.168.80.4:8004/imapi',
changeOrigin: true,
ws: false,
pathRewrite: {
'^/imapi': ''
}
}
,'/im': {
target: 'http://192.168.80.4:8004/im',
changeOrigin: true,
ws: true,
pathRewrite: {
'^/im': ''
}
}
}
}
};
3. env.development配置
bash
# 接口请求地址
VUE_APP_BASE_API = '/imapi'
# ws地址
VUE_APP_WS_URL = 'ws://192.168.80.4:8004/im'
本地启动前端vue,端口是8080,访问服务器上的服务,通过nginx代理,可以登录,登录后提示websocket无法连接,ws一直处于连接中

4. nginx日志

5. 解决
ngixn日志获取的ws地址是"GET /im HTTP/1.1",可知道。im后面没带斜杠/,所以location的路径也要不到斜杠,转发的地址后面也不要带斜杠,负负得正,
bash
# WebSocket
location /im {
proxy_pass http://192.168.80.4:8878;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
}
实际请求地址http://192.168.80.4:8878/im
WebSocket 在线测试:http://www.websocket-test.com/
一、 解决跨域的几种常用方法
1. Vue CLI 代理
可以配置一个代理服务器来转发 API 请求,绕过浏览器的同源策略。vue中通过 Vue CLI 的代理,Vue CLI 提供了一个内置的开发服务器(基于 Webpack Dev Server),可以通过配置代理来解决开发环境中的跨域问题,在vue-cli搭建的项目中有一个配置文件vue.config.js,可以在该文件中进行相应的配置解决开发环境的跨域问题。
在 vue.config.js 文件中进行配置,示例如下:
javascript
devServer: {
// 1.指定服务的ip
host: "192.168.0.128",
// 2.指定服务的端口
port: 3000,
open: true,
overlay: {
warnings: false,
errors: true
},
// 3.开发环境进行http的代理
proxy: {
// 匹配 url 路径的开头
'/api': {
// 1.路劲只要是/api开头的url都代理到下面这个网站。
// 例如:'/api/xxxx' 会代理到 https://119.20.224.137/api/xxxx
target: 'http://119.20.224.137:8201',
changeOrigin: true,
pathRewrite: { '^/api': '/api/' }
}
}
}
target: 后端服务器的地址。
changeOrigin: 设置为 true,代理会将请求的 Origin 改为目标地址,避免 CORS 限制。
pathRewrite: 如果前端请求路径以 /api 开头,可将其重写为空,避免在后端 URL 中重复。
对"/api"进行拦截配置,目的是凡是以"/api"开头的请求url都会将url中的"/api"**的前面添加上我们指定的内容。 例如:
'/api/user/login' 替换成 'http://119.20.224.137:8201/api/user/login'
在上述的例子中,其实 pathRewrite 也可以不写,例如:
javascript
devServer: {
open: true,
port: 8080,
// headers: {},
host: "192.168.0.128",
disableHostCheck: true,
https: true,
proxy: {
"/gwkf": { // "/gwky" 是后端的服务名,地址后端以它为开头的
target: "http://119.20.224.137:8201", //你需要访问的网址
changeOrigin: true,
},
// 像这种可以配置多个,后端会有多个服务名的情况
// 首先我们需要获取到后端的服务名,就是需要代理的服务名,这个我们可以通过swagger,来找到
// 第二点,我们需要找到请求路径,如果是测试环境(开发环境),就用测试环境、生产环境就用生产环境的路径。
// 然后就在target里面,添加上域名就可以了
// changeOrigin 要为true,意思就是:当进行代理时,Host 的源默认会保留
// (即Host是浏览器发过来的host),
// 如果将changeOrigin设置为true,则host会变成target的值;在vue-cli3中,
// 默认changeOrigin的值是true,意味着host设置成target,这与cue-cli2不一致,
// vue-cli2这个默认值是false。
"fast-admin": {
target: "https://test-analysis.com/",
changeOrigin: true,
},
"fast-service": {
target: "https://test-analysis.com/",
changeOrigin: true,
},
"mth-core-service": {
target: "https://test-masterdata.com/",
changeOrigin: true,
},
"mth-core-admin": {
target: "https://test-masterdata.com/",
changeOrigin: true,
},
"mth-capital-service": {
target: "https://test-analysis.com/",
changeOrigin: true,
}
}
},
示例:Axios 配置
javascript
import axios from 'axios';
const instance = axios.create({
baseURL: '/api', // 开发环境代理前缀
withCredentials: true, // 支持跨域携带 Cookies
});
instance.get('/users').then(res => console.log(res.data));
2. JSONP
如果后端支持 JSONP 跨域请求,可以使用 Vue 中的 JSONP 库(如 vue-jsonp)来发送跨域请求。
JSONP不推荐JSONP 是一种老旧的跨域解决方案,仅支持 GET 请求,且安全性较低。Vue 项目中一般不建议使用,除非后端仅支持 JSONP。
3. WebSocket
如果需要在 Vue 中与支持 WebSocket 的服务器进行跨域通信,可以使用 WebSocket API 进行连接和通信。WebSocket 不受同源策略的限制。
4. NGINX解决跨域问题
NGINX 解决跨域问题(CORS,Cross-Origin Resource Sharing)通常通过配置响应头来实现。以下是具体步骤和配置示例:
1. 理解跨域问题
跨域问题是由于浏览器的同源策略(Same-Origin Policy)导致的,当前端页面(如 http://a.com)请求不同域名(如 http://b.com)的资源时,浏览器会限制响应,除非服务器明确允许。
2. NGINX 配置解决跨域
在 NGINX 中,可以通过添加 Access-Control-Allow-* 响应头来解决跨域问题。以下是一个常见的配置方法:
bash
server {
listen 80;
server_name your_domain.com;
location / {
# 允许的来源(如前端域名),* 表示允许所有来源
add_header 'Access-Control-Allow-Origin' '*' always;
# 允许的请求方法
add_header 'Access-Control-Allow-Methods' 'GET, POST, PUT, DELETE, OPTIONS' always;
# 允许的请求头
add_header 'Access-Control-Allow-Headers' 'DNT,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Range,Authorization' always;
# 允许携带凭证(如 Cookies)
add_header 'Access-Control-Allow-Credentials' 'true' always;
# 预检请求(OPTIONS)的缓存时间
add_header 'Access-Control-Max-Age' 1728000 always;
# 处理 OPTIONS 预检请求
if ($request_method = 'OPTIONS') {
return 204;
}
# 你的其他配置,如 proxy_pass 或 root
# 示例:反向代理到后端
proxy_pass http://backend_server;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
}
}
配置说明
Access-Control-Allow-Origin: 指定允许的来源域名,* 表示所有域名(生产环境建议指定具体域名以提高安全性)。
Access-Control-Allow-Methods: 指定允许的 HTTP 方法。
Access-Control- Allow-Methods : 指定允许的 HTTP 方法。
Access-Control-Allow-Headers: 指定允许的请求头。
Access-Control-Allow-Credentials: 如果需要支持 Cookies 或认证信息,设为 true(此时 Access-Control-Allow-Origin 不能为 *)。
Access-Control-Max-Age: 预检请求的缓存时间,单位为秒。
处理 OPTIONS 请求: 浏览器在发送复杂请求(如带自定义头或非 GET/POST 请求)前会发送一个 OPTIONS 预检请求,NGINX 需要返回 204 状态码。
3. 注意事项
安全性: 避免盲目使用 *,建议明确指定允许的域名(如 http://frontend.com)。
Credentials 与 Origin: 如果设置了 Access-Control-Allow-Credentials: true,则 Access-Control-Allow-Origin 必须是具体域名,不能是 *。
Credentials 与 Origin: 如果设置了 Access-Control-Allow-Credentials: true,则 Access-Control-Allow-Origin 必须是具体域名,不能是*。
测试: 配置后,使用浏览器的开发者工具(Network 面板)检查响应头,确保 CORS 头正确返回。
重启 NGINX: 修改配置后,运行 nginx -s reload 重载配置。
4 . 验证配置
使用 curl 测试:
curl -I -X OPTIONS http://your_domain.com/api
检查响应头是否包含 Access-Control-Allow-*。
浏览器测试:打开前端页面,检查是否有 CORS 错误。
6.Java解决跨域
java
import org.springframework.web.bind.annotation.CrossOrigin;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;
@RestController
@CrossOrigin(origins = "http://frontend.com")
public class Controller {
@GetMapping("/users")
public String getUsers() {
return "Users";
}
}
参考:
vue跨域解决的几种方案【建议收藏】_vue跨域解决方案-CSDN博客
vue解决跨域问题的几种常用方法(CORS)_vue.js_脚本之家
二、 Vue 跨域问题详解
1. 什么是跨域
跨域问题是由于浏览器的同源策略(Same-Origin Policy)所导致的,同源策略是浏览器的一种安全机制,限制一个域的网页与另一个域的资源进行交互,即限制了一个源(协议、域名、端口)下的文档或脚本与另一个源的资源进行交互,也就是浏览器向不同源(不用协议、不用域名、不同端口)发送ajax请求会失败。
2. 跨域的例子
比如,我们启动的项目,启动了两个服务:
前端端口是5173
后端端口是8080
当浏览器启动后,会先发送请求,到前端服务,比如得到一个登录页面,这个登录页面所在的源,就是http://localhost:5173,在登录页面里,嵌套了一段js代码,里面有一个登录按钮,当用户点击登录按钮时,会发送请求到后端服务http://localhost:8080,此时ajax请求所在的源是5173,但它请求的目标是8080,这个时候,属于不同的源,由于浏览器的同源策略限制,该请求会发送失败,这种就是跨域问题。
3. 配置代理解决跨域问题
配置代理后,请求就不会从5173直接发向8080,当点击登录按钮,发送异步请求时,会先把请求发向前端服务5173,此时异步请求所在的源就是5173,所以就不会出现跨域问题,再由前端服务5173,转发到后端服务8080,也就是说,该请求是由服务端发起的,就没有跨域问题了。
4. 如何配置代理
首先在utils中的请求工具request.js里,把写固定的路径修改一下。
utils中的请求工具request.js

示例代码如下:
javascript
//这里边相当于请求的工具,用来定制请求的实例
//导入axios npm install axios
import axios from 'axios';
//导入Message消息提示
import { ElMessage } from 'element-plus';
//定义一个变量,记录公共的前缀,baseURL
// const baseURL = 'http://localhost:8080';
// 这里的'/api'只是给后台访问的请求路径添加一个标识
const baseURL = '/api';
/* axios.create()方法,把baseURL作为参数传入,
该方法返回一个请求的实例instance,
以后发送请求时,就不用axios.get了,
直接用instance.get就可以 */
const instance = axios.create({baseURL})
/* axios提供的拦截器,
在请求或响应,被then或catch处理前拦截
也就是在请求发出之前,有一个请求拦截器
或在响应到达之前,有一个响应拦截器 */
//添加响应拦截器(这个拦截器本身就是异步的)
instance.interceptors.response.use(
//成功的回调
result=>{
//判断业务状态码
if(result.data.code === 0){
return result.data;
}
//操作失败
ElMessage.error(result.data.msg?result.data.msg:'服务异常');
//异步操作的状态转换为失败
return Promise.reject(result.data);
},
//失败的回调
err=>{
alert('服务异常');
//异步的状态转化成失败的状态
return Promise.reject(err);
}
)
//把请求的实例instance导出,供其他地方调用
export default instance;
上述代码中,只是把const baseURL = 'http://localhost:8080';改成了const baseURL = '/api';意思就是,比如以前写的 const baseURL = 'http://localhost:8080';现在改成 const baseURL = '/api';这里的 '/api' 其实就是是给后台访问的请求路径添加一个标识,然后在配置代理里,会把这个 '/api' 替换为我们想要的路径,api前边并没有写端口号,就会把当前ajax请求所在的源自动拼进去,就相当于写的http://localhost:5173/api,因为当前ajax代码所处的源,就是刚才页面所处的源http://localhost:5173,所以当用户点击登录按钮时,请求就发送给5173的这个前端服务,两个源都是5173,所以不会出现跨域,在vite.config.js配置信息里边,添加 '/api' 的对应配置

这里的配置,才是真正配置代理的,这里才是配置请求路径和端口号的地方。
示例代码:
javascript
//这里边写的是vue项目的配置信息,如端口号等
import { fileURLToPath, URL } from 'node:url'
import { defineConfig } from 'vite'
import vue from '@vitejs/plugin-vue'
import vueDevTools from 'vite-plugin-vue-devtools'
// https://vite.dev/config/
export default defineConfig({
plugins: [
vue(),
vueDevTools(),
],
resolve: {
alias: {
'@': fileURLToPath(new URL('./src', import.meta.url))
},
},
//server:代表是要做服务相关的配置
server: {
//proxy: 指的是要配置一些代理
proxy: {
//这里的'/api'是指:请求路径中,是否有带/api这部分的路径,如果有/api,就对其进行处理
'/api': { //获取路径中包含了/api的请求
//target:指的是,如果要更换源,要更换成谁,就写谁,这里写的是后台服务所在的源
target: 'http://localhost:8080',
//changeOrigin:指的是,是否要更换换源
changeOrigin: true,
// rewrite:是路径的重写,这里把/api替换为''
rewrite: (path) => path.replace(/^\/api/, '')
}
}
}
})
为了更好的理解上边的配置,举个例子:比如发送异步请求,路径是http://localhost:5173/api/user/register,这个路径中,有 /api,配置信息里的 changeOrigin: true,就会更改源,把源改为target的 'http://localhost:8080',改完后就变成了http://localhost:8080/api/user/register,就是把 /api 前边的路径给换了,同时,rewrite重写路径,把 /api重写成空字符串,最后,路径就是这样的http://localhost:8080/user/register。