vue-cli3搭建的项目:vue.config.js解决跨域问题

在实际的项目开发中,如果客户端和服务器的协议、域名以及端口三者存在一个不一样的话,那么由于浏览器的同源策略的限制,我们就无法完成接口的调用访问。

1.在前端配置跨域解决方案

在前端配置跨域的方式,是属于代理的方式,这种方式主要是在开发环境下的跨域的解决方案。

  1. 第一步:找到vue.config.js,在该文件下,增加devServer.proxy属性,其中devServer是一个对象,配置项如下:
module.exports = {
  	devServer: {
	    open: true, //是否自动弹出浏览器页面
	    host: "localhost", 
	    port: 8080,
	    // https: true,
	    hotOnly: false, 
	    proxy: {
	        '/api': {
	            target: 'http://localhost:8554', 
	            changeOrigin: true, // 虚拟的站点需要更管origin
	            pathRewrite: {  
	                '^/api': ''
	            }
	        }
	    },
	},
}

如果只是进行了以上的配置,那么当我们在使用axios发送请求的时候,会出现404错误。

image.png 出现图中所示错误的原因:就是没有代理成功。 没有代理成功的话,可能是在使用axios访问接口的时候,类似于下面的写法:

this.$axios.get('/techInfo/10/1').then(res => {
        if (res && res.status === 200) {
                console.log(res)
        }
}).catch(error => {
        console.log(error);
})

通过上面方法访问接口的话,实际访问的接口是:http://localhost:8080/techInfo/10/1。那么就是代理配置出现问题。

如果有同学是按照上面的方法进行配置的,那么恭喜你,距离成功更近一步了,接下来的配置是: 在入口文件main.js中,添加axios调用接口的默认URL地址。

/* 配置axios */
axios.defaults.baseURL = 'http://localhost:8554/api'

2.后端配置解决跨域问题

对于使用SpringBoot开发的项目,在后端采用CORS(跨域资源共享)完成跨域的配置,具体的配置如下:

@SpringBootConfiguration
public class MyWebConfigurer implements WebMvcConfigurer {

    @Override
    /*添加跨域资源共享请求*/
    public void addCorsMappings(CorsRegistry registry) {
        //所有请求都允许跨域,使用这种配置方法就不能在 interceptor 中再配置 header 了
        /*需要进行的配置包括
        * 请求路径:/**所有请求都可以跨域
        * allowCredentials:是否允许请求cookie
        * allowedOrigins:允许访问的源:由协议+域名+端口号组成,表示请求的源
        * allowedMethods:允许访问的请求方式
        * allowedHeaders:允许访问的请求头
        * */
        registry.addMapping("/**")
                .allowCredentials(true)
                .allowedOrigins("http://localhost:8080")
                .allowedMethods("POST", "GET", "PUT", "OPTIONS", "DELETE")
                .allowedHeaders("*")
                .maxAge(3600);
    }

下面对CORS进行解释: CORS其实更像是服务器和客户端根据HTTP协议头来做一些限制和约束。双方通过协商沟通讨论出什么情况下服务器端的资源是可以被客户端访问的,以实现资源的共享。 CORS主要包括两种请求方式: (1)简单请求 简单请求需要满足一定的条件,这里就不再展开说明。 (2)非简单请求 当请求的方式不满足简单请求时,就是非简单请求,包括预检请求(浏览器主动发起的),

浏览器发送带有access-control-request-headers和 access-control-request-method来进行预检请求,目的是询问服务器端,我现在用这种方式请求你的资源,是被允许的吗?

如果允许的话,接下来就会发送第二次请求,将服务器端的数据返回。 上述过程中,客户端除了预检请求外,几乎不用有额外的设置。 但是客户端的工作量就比较庞大了,主要包括以下几种响应头:

  • access-control-allow-origin:指定可以访问服务器端资源的URI,值可以是"*"或者域名信息。
  • access-control-allow-credentials:是否在跨域请求的时候,浏览器端携带cookie信息
  • access-control-allow-methods:指明实际请求可以使用的HTTP请求方法
  • access-control-allow-headers:指明实际请求可以使用的HTTP请求头

3.生产环境下的跨域解决方案

(1)打包 将我们的前端项目通过npm run build进行打包

(2)服务器安装nginx服务器

在云端服务器上安装Nginx服务器

(3)配置nginx

  找到nginx的配置文件  nginx.conf , nginx.conf的配置如下

server {
        listen       8080;
        server_name  localhost;
        #access_log  logs/host.access.log  main;
        location /api {
            proxy_pass https://www.hahah.com;  #代理的域名
            add_header 'Access-Control-Allow-Origin' '*'; 
            add_header 'Access-Control-Allow-Credentials' 'true'; 
        }
        location  / {
            root   /home/fortend/;
            index  index.html index.htm;
        }
    }