【Vue+Element-UI】实现登陆注册界面及axios之get、post请求登录功能实现、跨域问题的解决

目录

一、实现登陆注册界面

1、前期准备

2、登录静态页实现

2.1、创建Vue组件

2.2、静态页面实现

2.3、配置路由

2.4、更改App.vue样式

2.5、效果

3、注册静态页实现

3.1、静态页面实现

3.2、配置路由

3.3、效果

二、axios

1、前期准备

1.1、准备项目

1.2、安装axios

1.3、更改端口

2、GET请求

2.1、导入axios

2.2、编写get请求

3、POST请求

3.1、get、post的区别

3.2、导入qs

3.3、编写post请求

3.4、优化处理

3.4.1、下载安装vue-axios

3.4.2、写入api模块添加全局配置

3.4.2.1、action.js

3.4.2.2、http.js

3.4.3、main.js配置vue-axios

3.4.3、使用封装后的axios发送请求

3.4.4、修改后的提交事件

三、跨域

1、什么是跨域问题

2、解决跨域问题


一、实现登陆注册界面

1、前期准备

使用vue-cli构建SPA项目:

  1. 进入你想创建项目的目录位置

  2. 使用命令vue init webpack 项目名,构建一个vue项目

    复制代码
    vue init webpack element_ui_spa
  3. 使用命令npm install element-ui -S,添加Element-UI模块

    1. npm install element-ui -S:后面有 -s,他们分别是:
      1. -g:将依赖下载node_global全局依赖。
      2. -d:下载依赖da到spa工程中,不会参与打包。
      3. -s:下载依赖da到spa工程中,会参与打包。
  4. 打开项目的package.json文件可查看具体添加模块信息。

  5. 在src目录下创建views目录(该目录用于存放vue组件)。

  6. 在main.js中引入element-ui模块

    javascript 复制代码
    // The Vue build version to load with the `import` command
    // (runtime-only or standalone) has been set in webpack.base.conf with an alias.
    import Vue from 'vue'
    // 新添加1
    import ElementUI from 'element-ui'
    // 新添加2,避免后期打包样式不同,要放在import App from './App';之前
    import 'element-ui/lib/theme-chalk/index.css'
    
    import App from './App'
    import router from './router'
    
    // 新添加3----实例进行一个挂载
    Vue.use(ElementUI)
    Vue.config.productionTip = false
    
    /* eslint-disable no-new */
    new Vue({
      el: '#app',
      router,
      components: {App},
      template: '<App/>'
    })

    在指定位置!!!在指定位置!!!在指定位置!!!---添加三行代码

2、登录静态页实现

2.1、创建Vue组件

在我们src 里面创建我们的登录注册的vue组件

2.2、静态页面实现

设置我们的html样式,当然我们也可以在组件 | Element里面自己进行一个自定义

html 复制代码
<template>
  <div class="Login">
    <el-form class="login-container">
      <h1 class="title">用户登录</h1>
      <el-form-item label="">
        <el-input type="text" v-model="username" placeholder="登录账号" autocomplete="off"></el-input>
      </el-form-item>
      <el-form-item label="">
        <el-input type="password" v-model="password" placeholder="登录密码" autocomplete="off"></el-input>
      </el-form-item>
      <el-form-item>
        <el-button type="primary" style="width:100%;" @click="doSubmit()">提交</el-button>
      </el-form-item>
      <el-row style="text-align: center;margin-top:-10px">
        <el-link type="primary">忘记密码</el-link>
        <el-link type="primary" @click="gotoRegister()">用户注册</el-link>
      </el-row>
    </el-form>
  </div>
</template>
<script>
export default {
  name: "Login",
  data() {
    return {
      msg: "登录界面",
      username: "",
      password: ""
    }
  },
  methods: {
    gotoRegister() {
      this.$router.push("/Register");
    },
    doSubmit() {

    }
  }
}
</script>

<style scoped>
.login-wrap {
  box-sizing: border-box;
  width: 100%;
  height: 100%;
  padding-top: 10%;
  background-image: url(https://pic4.zhimg.com/v2-c5880f5a6d44766feb085c3ae94899c7_r.jpg);
  //background-image: url();
  background-repeat: no-repeat;
  background-position: center right;
  background-size: 100%;
}

.login-container {
  border-radius: 10px;
  margin: 0px auto;
  width: 350px;
  padding: 30px 35px 15px 35px;
  background: #fff;
  border: 1px solid #eaeaea;
  text-align: left;
  box-shadow: 0 0 20px 2px rgba(0, 0, 0, 0.1);
}

.title {
  margin: 0px auto 40px auto;
  text-align: center;
  color: #505458;
}
</style>

2.3、配置路由

在router/index.js中修改vue项目默认显示路由

javascript 复制代码
import Vue from 'vue'
import Router from 'vue-router'
import HelloWorld from '@/components/HelloWorld'
import Login from '@/views/Login'

Vue.use(Router)

export default new Router({
  routes: [
    {
      path: '/Login',
      name: 'Login',
      component: Login
    }
  ]
})

2.4、更改App.vue样式

更改原有<style>样式

html 复制代码
<template>
  <div id="app">
    <!--    <img src="./assets/logo.png"><br>-->
    <br>
    <router-view/>
  </div>
</template>

<script>
export default {
  name: 'App'
}
</script>

<style>
html,
body {
  width: 100%;
  height: 100%;
  box-sizing: border-box;
  padding: 0px;
  margin: 0px;
}

#app {
  font-family: "Avenir", Helvetica, Arial, sans-serif;
  -webkit-font-smoothing: antialiased;
  -moz-osx-font-smoothing: grayscale;
  color: #2c3e50;
  widows: 100%;
  height: 100%;
}
</style>

2.5、效果

3、注册静态页实现

在登陆的基础上实现一样的操作

3.1、静态页面实现

html 复制代码
<template>
  <div class="Register">
    <el-form class="login-container">
      <h1 class="title">用户注册</h1>
      <el-form-item label="">
        <el-input type="text" v-model="username" placeholder="注册账号" autocomplete="off"></el-input>
      </el-form-item>
      <el-form-item label="">
        <el-input type="password" v-model="password" placeholder="注册密码" autocomplete="off"></el-input>
      </el-form-item>
      <el-form-item>
        <el-button type="primary" style="width:100%;" @click="doSubmit()">提交</el-button>
      </el-form-item>
      <el-row style="text-align: center;margin-top:-10px">
        <el-link type="primary">忘记密码</el-link>
        <el-link type="primary" @click="gotoLogin()">用户注册</el-link>
      </el-row>
    </el-form>
  </div>
</template>
<script>
export default {
  name: "Register",
  data() {
    return {
      msg: "注册界面",
      username: "",
      password: ""
    }
  },
  methods: {
    gotoLogin() {
      this.$router.push("/Login");
    },
    doSubmit() {

    }
  }
}
</script>

<style scoped>
.login-wrap {
  box-sizing: border-box;
  width: 100%;
  height: 100%;
  padding-top: 10%;
  background-image: url();
  background-repeat: no-repeat;
  background-position: center right;
  background-size: 100%;
}

.login-container {
  border-radius: 10px;
  margin: 0px auto;
  width: 350px;
  padding: 30px 35px 15px 35px;
  background: #fff;
  border: 1px solid #eaeaea;
  text-align: left;
  box-shadow: 0 0 20px 2px rgba(0, 0, 0, 0.1);
}

.title {
  margin: 0px auto 40px auto;
  text-align: center;
  color: #505458;
}
</style>

3.2、配置路由

javascript 复制代码
import Vue from 'vue'
import Router from 'vue-router'
import HelloWorld from '@/components/HelloWorld'
import Login from '@/views/Login'
import Register from '@/views/Register'

Vue.use(Router)

export default new Router({
  routes: [
    {
      path: '/Login',
      name: 'Login',
      component: Login
    },
    {
      path: '/Register',
      name: 'Register',
      component: Register
    }
  ]
})

3.3、效果

二、axios

使用SSM项目构建Java后台,模拟提供一个用户登录的action地址,Vue通过请求指定的用户登录接口。

1、前期准备

1.1、准备项目

需要准备自己做好的一个项目,比如SSM的项目、maven项目、SpringMVC的项目都可 ,如果不会写可以参考我以前的博客内容spring系列_无法自律的人的博客-CSDN博客

1.2、安装axios

进入项目里面CMD窗口进行下载,必须要在你的项目文件路径里面进行CMD的窗口

javascript 复制代码
npm i axios -S

在我们的package.json里面可以看到我们下载的

1.3、更改端口

config/index.js目录下修改vue项目运行端口

2、GET请求

2.1、导入axios

在登录的vue文件里面导入我们需要的axios。

javascript 复制代码
import axios from 'axios'

2.2、编写get请求

测试的时候记得开启你的项目

javascript 复制代码
//提交事件
    doSubmit() {
      //设置登录访问地址
      let url = "http://localhost:8080/ssm/user/userLogin";
      // 使用json格式进行传值
      let params = {
        username: this.username,
        password: this.password
      }
//get请求
      axios.get(url, {params: params}).then(r => {
        console.log(r);
        if (r.data.success) {//判断success是否为true
          // 为true给一个提示框
          this.$message({
            //message: '登陆成功',
            message: r.data.msg,
            type: 'success'
          });
        } else {
          this.$message({
            //message: '登陆失败',
            message: r.data.msg,
            type: 'warning'
          });
        }

      }).catch(e => {
        // console.log(e);
      });
    }

3、POST请求

3.1、get、post的区别

GET 请求和 POST 请求是两种常见的 HTTP 请求方法,它们的区别:

  1. 数据传输方式:GET 请求通过 URL 参数传输数据,而 POST 请求通过请求体传输数据。GET 请求的数据会附加在 URL 的末尾,可见于 URL 地址栏,而 POST 请求的数据则被放置在请求体中,不会在 URL 中暴露。
  2. 数据长度限制:由于 GET 请求的数据附加在 URL 中,URL 的长度有限制,一般约为 2048 个字符,超过该限制会导致 URL 过长,而 POST 请求则没有明确的数据长度限制。
  3. 安全性:GET 请求的参数以明文形式附加在 URL 上,因此不适合传输敏感信息,而 POST 请求的数据放置在请求体中,相对而言更安全。
  4. 缓存:GET 请求可以被浏览器缓存下来,可以被重复使用,而 POST 请求对浏览器不可缓存,每次都需要重新发送请求。
  5. 特殊字符处理:GET 请求会对特殊字符进行 URL 编码,如空格会被替换为 "%20",而 POST 请求不会对特殊字符进行编码。
  6. 幂等性:GET 请求是幂等的,即多次相同的 GET 请求不会对服务器产生副作用,而 POST 请求不具有幂等性,每次 POST 请求都可能有副作用,如创建资源或修改数据。

3.2、导入qs

如上面的请求一样,怎么导入axios的,我们照样导入qs。

javascript 复制代码
import qs from 'qs'

3.3、编写post请求

唯一和get请求不一样的是

  • get:axios.get(url, {params: params}).then(r => {}).catch(e => {});
  • post:axios.get(url,qs.stringify(params)).then(r => {}).catch(e => {});
javascript 复制代码
//提交事件
    doSubmit() {
      //设置登录访问地址
      let url = "http://localhost:8080/ssm/user/userLogin";
      // 使用json格式进行传值
      let params = {
        username: this.username,
        password: this.password
      }
//post请求
      axios.post(url, qs.stringify(params)).then(r => {
        console.log(r);
        if (r.data.success) {//判断success是否为true
          // 为true给一个提示框
          this.$message({
            //message: '登陆成功',
            message: r.data.msg,
            type: 'success'
          });
        } else {
          this.$message({
            //message: '登陆失败',
            message: r.data.msg,
            type: 'warning'
          });
        }

      }).catch(e => {
        // console.log(e);
      });
    }

3.4、优化处理

3.4.1、下载安装vue-axios

在CMD命令窗口进行下载vue-axios。

3.4.2、写入api模块添加全局配置

在src目录下新建api文件夹,在下面建立两个文件action.jshttp.js

3.4.2.1、action.js
javascript 复制代码
/**
 * 文件接口地址定义文件
 * 对后台请求的地址的封装,URL格式如下:
 * 模块名_实体名_操作
 */
export default {
  'SERVER': 'http://localhost:8080/ssm', //服务器访问地址
  'SYSTEM_USER_DOLOGIN': '/user/userLogin', //登陆请求
  'SYSTEM_USER_DOREG': '/user/userRegister', //注册请求
  'getFullPath': k => { //获得请求的完整地址,用于mockjs测试时使用
    return this.SERVER + this[k];
  }
}
3.4.2.2、http.js
javascript 复制代码
/**
 * vue项目对axios的全局配置
 */
import axios from 'axios'
import qs from 'qs'

//引入action模块,并添加至axios的类属性urls上
import action from '@/api/action'
axios.urls = action

// axios默认配置
axios.defaults.timeout = 10000; // 超时时间
// axios.defaults.baseURL = 'http://localhost:8080/j2ee15'; // 默认地址
axios.defaults.baseURL = action.SERVER;

//整理数据
// 只适用于 POST,PUT,PATCH,transformRequest` 允许在向服务器发送前,修改请求数据
axios.defaults.transformRequest = function(data) {
	data = qs.stringify(data);
	return data;
};


// 请求拦截器
axios.interceptors.request.use(function(config) {
	return config;
}, function(error) {
	return Promise.reject(error);
});

// 响应拦截器
axios.interceptors.response.use(function(response) {
	return response;
}, function(error) {
	return Promise.reject(error);
});

export default axios;
3.4.3、main.js配置vue-axios

main.js 文件中引入api 模块和vue-axios模块

javascript 复制代码
import axios from '@/api/http'                 
import VueAxios from 'vue-axios' 

Vue.use(VueAxios,axios)
3.4.3、使用封装后的axios发送请求

Login.vue 组件中移除导入的axios和qs模块

javascript 复制代码
import axios from 'axios'
import qs from 'qs'
3.4.4、修改后的提交事件
javascript 复制代码
doSubmit() {
      //设置登录访问地址
      let url = this.axios.urls.SYSTEM_USER_DOLOGIN;
      // 使用json格式进行传值
      let params = {
        username: this.username,
        password: this.password
      }
      this.axios.post(url, params).then(r => {
        console.log(r);
        if (r.data.success) {//判断success是否为true
          // 为true给一个提示框
          this.$message({
            message: r.data.msg,
            type: 'success'
          });
        } else {
          this.$message({
            message: r.data.msg,
            type: 'warning'
          });
        }

      }).catch(e => {
      });

    }

4、注册功能实现

4.1、页面实现

当然可以根据自己的数据库和自己的需求来定义自己的页面

html 复制代码
<template>
  <div class="Register">

    <el-form class="login-container">
      <h1 class="title">用户注册</h1>
      <el-form-item label="">
        <el-input type="text" v-model="username" placeholder="输入账号" autocomplete="off"></el-input>
      </el-form-item>
      <el-form-item label="">
        <el-input type="password" v-model="password" placeholder="输入密码" show-password autocomplete="off"></el-input>
      </el-form-item>

      <el-form-item label="账号名称" label-width="80px" style="margin-left: 5px;" prop="name">
        <el-input v-model="realname"></el-input>
      </el-form-item>

      <el-form-item label="性别" style="margin-left: 20px;">
        <el-radio-group v-model="sex">
          <el-radio label="1">男</el-radio>
          <el-radio label="2">女</el-radio>
          <el-radio label="3">其他</el-radio>
        </el-radio-group>
      </el-form-item>

      <el-form-item label="身 份 证" label-width="80px" style="margin-left: 0px;" prop="name">
        <el-input v-model="idcard"></el-input>
      </el-form-item>

      <el-input type="textarea" :rows="2" placeholder="请输入地址" v-model="address">
      </el-input>

      <el-form-item style="margin-top: 30px;">
        <el-button type="primary" style="width:100%;"
                   @click="Register()">注&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;册
        </el-button>
      </el-form-item>
      <el-row style="text-align: center;margin-top:-10px">
        <el-link type="primary">忘记密码</el-link>
        <el-link type="primary" @click="Login()">用户登入</el-link>
      </el-row>
    </el-form>
  </div>
</template>

<script>
export default {
  name: 'Register',
  data() {
    return {
      username: "",
      password: "",
      realname: '',
      sex: 0,
      idcard: '',
      address: '',
      msg: '嗨!嗨!嗨!',
      rules: {
        realname: [{
          required: true,
          message: '请输入账号名称',
          trigger: 'blur'
        },
          {
            min: 3,
            max: 18,
            message: '长度在 3 到 18 个字符',
            trigger: 'blur'
          }
        ]
      }
    }

  },
  methods: {
    Login() {
      this.$router.push('/Login');
    },
    Register() {
      let params = {
        username: this.username,
        password: this.password,
        realname: this.realname,
        sex: this.sex,
        idcard: this.idcard,
        address: this.address
      };
      //定义后端都请求地址
      var url = this.axios.urls.SYSTEM_USER_DOREG;
      console.log(params);
      console.log(url);
      //以下是post请求及整合资源
      //通过qs中的stringify方法进行格式转换
      //注意数据是保存到json对象的params属性
      this.axios.post(url, params).then(r => {
        console.log(r);
        //如果携带的参数数据跟后端数据对应正确,说明登入成功,提示
        if (r.data.success) {
          this.$message({
            showClose: true,
            message: r.data.msg,
            type: 'success'
          });
          //注册完成后自动进入登入界面
          this.$router.push('/Login');
        } else {
          //如果携带的参数数据跟后端数据对应错误,说明登入失败,提示
          this.$message.error(r.data.msg);
        }
      }).catch(e => {
        console.log(e);
      });


    }
  }
}
</script>

<style scoped>
.login-wrap {
  padding-top: 30px;
  box-sizing: border-box;
  width: 100%;
  height: 100%;
  background-image: url();
  background-repeat: no-repeat;
  background-position: center right;
  background-size: 100%;
}

.login-container {
  border-radius: 10px;
  margin: 0px auto;
  width: 350px;
  padding: 30px 35px 15px 35px;
  background: #fff;
  border: 1px solid #eaeaea;
  text-align: left;
  box-shadow: 0 0 20px 2px rgba(0, 0, 0, 0.1);
}

.title {
  margin: 0px auto 40px auto;
  text-align: center;
  color: #505458;
}
</style>

4.2、定义接口、接口实现类

接口

java 复制代码
int insertSelective(User record);

接口实现

java 复制代码
    @Override
    public int insertSelective(User record) {
        return userMapper.insertSelective(record);
    }

4.3、Controller层

在Controller编写方法,需要一定springmvc的基础

java 复制代码
 @RequestMapping("/userRegister")
    @ResponseBody
    public JsonResponseBody<?> userRegister(UserVo userVo, HttpServletResponse response) {
        //状态新注册默认为0
        userVo.setStatus("0");
        //因为ID为String类型需要手动设置,当然可以根据自己的需要改为Int类型
        userVo.setId("6");
        int i = userService.insertSelective(userVo);
        if (i > 0) {
            return new JsonResponseBody<>("用户注册完成!快去登入吧!", true, 0, null);
        } else {
            return new JsonResponseBody<>("用户注册失败!重新输入。", false, 0, null);
        }
    }

4.4、测试

三、跨域

1、什么是跨域问题

跨域问题(Cross-Origin Resource Sharing,CORS) 指的是在浏览器端,由于安全策略限制,不同源(域/协议/端口)之间的网页(或者Ajax请求)无法直接进行交互或访问对方的资源。同源策略是浏览器的一种安全机制,用于保护用户信息和防止恶意攻击。

同源策略要求网页只能与相同源的资源进行交互,源(Origin)由协议、域名和端口号组成。当源不一致时,浏览器会阻止跨域的请求。例如,一个网页在域A中运行,试图通过JavaScript向域B发送AJAX请求,此时就会触发跨域问题。

2、解决跨域问题

在你的项目里编写跨域过滤器CorsFilter2

java 复制代码
package com.zking.ssm.util;

import java.io.IOException;

import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletResponse;

/**
 * 配置tomcat允许跨域访问
 * 
 * @author Administrator
 *
 */
public class CorsFilter2 implements Filter {

	@Override
	public void init(FilterConfig filterConfig) throws ServletException {
	}

	@Override
	public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain)
			throws IOException, ServletException {
		HttpServletResponse httpResponse = (HttpServletResponse) servletResponse;

		// Access-Control-Allow-Origin就是我们需要设置的域名
		// Access-Control-Allow-Headers跨域允许包含的头。
		// Access-Control-Allow-Methods是允许的请求方式
		httpResponse.setHeader("Access-Control-Allow-Origin", "*");// *,任何域名
		httpResponse.setHeader("Access-Control-Allow-Headers", "responseType,Origin, X-Requested-With, Content-Type, Accept");
		httpResponse.setHeader("Access-Control-Allow-Methods", "POST, GET, PUT, DELETE");

		//允许客户端处理一个新的响应头jwt
		//httpResponse.setHeader("Access-Control-Expose-Headers", "jwt,Content-Disposition");
		filterChain.doFilter(servletRequest, servletResponse);
	}

	@Override
	public void destroy() {

	}
}

在web.xml里面添加过滤器的配置,然后就能解决我的跨域问题了。

XML 复制代码
  <!--CrosFilter跨域过滤器-->
  <filter>
    <filter-name>corsFilter</filter-name>
    <filter-class>com.zking.ssm.util.CorsFilter2</filter-class>
  </filter>
  <filter-mapping>
    <filter-name>corsFilter</filter-name>
    <url-pattern>/*</url-pattern>
  </filter-mapping>

我的分享就到这里,欢迎各位大佬在评论区讨论!!!

相关推荐
崔庆才丨静觅6 小时前
hCaptcha 验证码图像识别 API 对接教程
前端
passerby60617 小时前
完成前端时间处理的另一块版图
前端·github·web components
掘了7 小时前
「2025 年终总结」在所有失去的人中,我最怀念我自己
前端·后端·年终总结
崔庆才丨静觅7 小时前
实用免费的 Short URL 短链接 API 对接说明
前端
崔庆才丨静觅7 小时前
5分钟快速搭建 AI 平台并用它赚钱!
前端
崔庆才丨静觅8 小时前
比官方便宜一半以上!Midjourney API 申请及使用
前端
Moment8 小时前
富文本编辑器在 AI 时代为什么这么受欢迎
前端·javascript·后端
崔庆才丨静觅8 小时前
刷屏全网的“nano-banana”API接入指南!0.1元/张量产高清创意图,开发者必藏
前端
剪刀石头布啊8 小时前
jwt介绍
前端
爱敲代码的小鱼8 小时前
AJAX(异步交互的技术来实现从服务端中获取数据):
前端·javascript·ajax