处理vue与后端的跨域问题

修改端口 为了端口不冲突

package.json—— “serve”: “vue-cli-service serve --port=80”,

处理vue与后端的跨域问题_第1张图片

形成跨域:

  1. 协议是否一样
  2. 服务器的ip是否一样
  3. 端口是否一样

上面三个只要有一个不一样, 形成跨域

处理跨域

  1. 前台解决:配置代理服务器
//后台服务器 代理服务器解决跨域问题
  devServer: {
    //后台服务器协议+端口
    proxy: {
      '/api': {//api替代url
        target: 'http://localhost:8888',
        ws: false,
        changeOrigin:true,//支持跨域请求
  }
    }
  }

发送的请求加 /api前缀

login() {
                    //前端解决跨域
            this.$http.get("/api/vuelogin?user=zhangsan&password=123")
                .then(function (response) {
                    //处理成功情况
                    console.log(response)
                })
                .catch(function (error) {
                    //处理错误情况
                    console.log(error);
                })
        }
  1. 后台解决:配置处理跨越的过滤器
@WebFilter(filterName = "CrossFilter",urlPatterns = "/*")
public class CrossFilter implements Filter {

    public void doFilter(ServletRequest req, ServletResponse res, FilterChain chain) throws IOException, ServletException {
        HttpServletResponse response = (HttpServletResponse) res;
        response.setHeader("Access-Control-Allow-Origin", "*"); //允许所有的域名访问
        response.setHeader("Access-Control-Allow-Methods", "POST, GET, PUT, PATCH, DELETE"); //允许的提交方式
        response.setHeader("Access-Control-Max-Age", "3600"); //最大有效时间
        response.setHeader("Access-Control-Allow-Headers", "x-requested-with, Content-Type, Accept, Origin"); //允许那些请求头
        response.setHeader("Access-Control-Allow-Credentials", "true"); //是否支持ajax提交cookie
        chain.doFilter(req, res);
    }

    public void init(FilterConfig filterConfig) {}

    public void destroy() {}

}

3.使用nginx,其他的服务器处理跨域


实际开发中:确定api文档,统一响应数据格式

验证

处理vue与后端的跨域问题_第2张图片

//    禁止序列化密码
    @JSONField(serialize = false)
    private String password;

处理vue与后端的跨域问题_第3张图片

统一响应数据格式后 前端返回的数据

处理vue与后端的跨域问题_第4张图片

login(){
                    //后端解决跨域
var that = this; // 函数内的this指向函数 没有指向data
            that.$axios.get("http://localhost:8888/api/vuelogin?user=" + that.username + "&password=" + that.password)
                .then(function (response) {
                    console.log(response)
                    //处理成功情况
                
  // response.data.meta.status === 200  
 //1.const res = response.data return res响应拦截器  2. === 数据类型也要相同
                       
                    if (response.meta.status === 200) {
                        //保持token到本地
                        let admin = response.data;
                        localStorage.setItem("token", admin.username);

                        //跳转页面
                        that.$router.push({
                            name: 'home',
                            query: {
                                username: admin.username
                            }
                        });
                    } else {
                        that.user = "";
                        that.password = "";
                        alert(response.meta.msg);
                    }
                })
                .catch(function (error) {
                    //处理错误情况
                    console.log(error);
                    alert("服务器出错..")
                })
        }

跳转页面获取参数

{{username}}

computed: { username() { // 函数内加this return this.$route.query.username; } }

问题:post请求 参数不能跟在请求路径后

注意:

axios 发送请求, 使用请求体发送请求参数, 以json形式传递给服务器

request.getParameter("user") //要求请求参数是key/value对的方式

utils.request.js

import axios from 'axios'
import qs from 'qs'
/**
 * axios的传参方式:
 * 1.url 传参 一般用于Get和Delete 实现方式:config.params={JSON}
 * 2.body传参 实现方式:config.data = {JSON},且请求头为:headers: { 'Content-Type': 'application/json;charset=UTF-8' }
 * 3.表单传参 实现方式:config.data = qs.stringify({JSON}),且请求头为:且请求头为:headers: { 'Content-Type': 'application/x-www-form-urlencoded;charset=UTF-8' }
 */
// axios实例
const $http = axios.create({
	baseURL: 'http://localhost:8888/api/',
    timeout: 60000,
	headers: { 'Content-Type': 'application/x-www-form-urlencoded;charset=UTF-8' }
})
 
// 请求拦截器
$http.interceptors.request.use(
	(config) => {
		// 追加时间戳,防止GET请求缓存
		if (config.method?.toUpperCase() === 'GET') {
			config.params = { ...config.params, t: new Date().getTime() }
		}
		//如果是post qs将json转成key/value
		if (Object.values(config.headers).includes('application/x-www-form-urlencoded')) {
			config.data = qs.stringify(config.data)
		}
		return config
	},
	error => {
		return Promise.reject(error)
	}
)
 
// 响应拦截器
$http.interceptors.response.use(
	response => {
		const res = response.data
		return res
	},
	error => {
		return Promise.reject(error)
	}
)
 
// 导出 axios 实例
export default $http

main.js

 import $http from './utils/request'

//globalProperties 全局  app的全局属性名为$axios 
app.config.globalProperties.$axios = $http;
login(){
       //后端解决跨域
            var that = this; // 函数内的this指向函数 没有指向data
            that.$axios.post("vuelogin", {
                username: that.username,
                password:that.password
            })
                .then(function (response) {
                    console.log(response)
                    //处理成功情况
                    // response.data.meta.status === 200  
                    //1.const res = response.data return res响应拦截器  2. === 数据类型也要相同
                    if (response.meta.status === 200) {
                        //保持token到本地
                        let admin = response.data;
                        localStorage.setItem("token", admin.username);

                        //跳转页面
                        that.$router.push({
                            name: 'home',
                            query: {
                                username: admin.username
                            }
                        });
                    } else {
                        that.user = "";
                        that.password = "";
                        alert(response.meta.msg);
                    }
                })
                .catch(function (error) {
                    //处理错误情况
                    console.log(error);
                    alert("服务器出错..")
                })
        }

删除token

          alert(response.meta.msg);
                    }
                })
                .catch(function (error) {
                    //处理错误情况
                    console.log(error);
                    alert("服务器出错..")
                })
        }

处理vue与后端的跨域问题_第5张图片

验证码

加了验证码
处理vue与后端的跨域问题_第6张图片

处理vue与后端的跨域问题_第7张图片

原因:验证码更新

使用session,创建session对象把JSessionId 以cookie的形式保存在客户端浏览器。 没有携带cookieID ,会再次使用session

axios默认不携带cookie

解决:在request.js或main.js中

//CROS跨域是否允许凭证
$http.defaults.withCredentials = true; 

request.js 表单登录 key/value

	headers: { 'Content-Type': 'application/x-www-form-urlencoded;charset=UTF-8' }

处理vue与后端的跨域问题_第8张图片

CrossFilter

 HttpServletRequest request = (HttpServletRequest) req;
      //  response.setHeader("Access-Control-Allow-Origin", "*"); //允许所有的域名访问
        //axios允许携带cookie Access-Control-Allow-Origin"不能设置为 "*"
        //设置为携带cookie的前端域名"https://localhost"
        //动态获取request.getHeader("origin")

你可能感兴趣的:(vue,java基础,vue)