> 文档中心 > 学生管理 + 用户管理(Element版)

学生管理 + 用户管理(Element版)


1.1 搭建环境

  • 创建vue项目:vue create day16_element_student

  • 安装第三方组件:axios、element

npm install axios
vue add element

1.2 查询所有前端

1.2.1. 显示页面

  • 创建页面

  • 配置路由
const routes = [  {    path: '/studentList',    name: '学生列表',    component: () => import('../views/StudentList.vue')  }]
  • 访问路径

          http://localhost:8080/studentList

1.2.2 ajax操作

  
{{studentPage}}
// 导入axiosimport axios from 'axios'export default { data() { return { studentVo: { //条件查询 }, studentPage: { //分页数据 pageNum: 1, pageSize: 3 } } }, methods: { async condition() { // ajax查询 var url = `http://localhost:8888/student/condition/${this.studentPage.pageSize}/${this.studentPage.pageNum}` let {data:baseResult} = await axios.post(url, this.studentVo) // 保存结果 this.studentPage = baseResult.data } }, mounted() { // 查询 this.condition() },}

1.2.3 整合element ui

  
- 查询 {{scope.row.gender == 1 ? "男" : "女"}} 编辑 删除
// 导入axiosimport axios from 'axios'export default { data() { return { studentVo: { //条件查询 }, studentPage: { //分页数据 pageNum: 1, pageSize: 3 } } }, methods: { async condition(num) { if(num) { this.studentPage.pageNum = num } // ajax查询 var url = `http://localhost:8888/student/condition/${this.studentPage.pageSize}/${this.studentPage.pageNum}` let {data:baseResult} = await axios.post(url, this.studentVo) // 保存结果 this.studentPage = baseResult.data }, handleSelectionChange(val) { console.info('批量删除') }, handleSizeChange(val) { console.log(`每页 ${val} 条`); this.studentPage.pageSize = val this.studentPage.pageNum = 1 // 重新开始 this.condition() }, handleCurrentChange(val) { console.log(`当前页: ${val}`); this.studentPage.pageNum = val // 重新开始 this.condition() } }, mounted() { // 查询 this.condition() },}

1.3 导航(嵌套路由)

  • 步骤1:创建页面

    • 创建登录页面(模板页面)

    • 编写首页Home(上中下布局),编写导航(首页、班级管理/班级列表、学生管理/学生列表)

    • 创建页面:ClassesList.vue

  • 步骤2:配置路由

  • 步骤3:编写布局容器和导航

步骤1:创建页面

  • 创建登录页面(模板页面)

  • 编写首页Home(上中下布局),编写导航(首页、班级管理/班级列表、学生管理/学生列表)

  • 创建页面:ClassesList.vue

 步骤2:配置路由

const routes = [  {    path: '/',    redirect: '/home'    //重定向  },  {    path: '/login',    name: '登录',    component: () => import('../views/Login.vue')  },  {    path: '/home',    name: '首页',    component: () => import('../views/Home.vue'),    children: [      { path: '/studentList', name: '学生列表', component: () => import('../views/StudentList.vue')      },      { path: '/classesList', name: '班级列表', component: () => import('../views/ClassesList.vue')      }    ]  },  ]

步骤3:编写布局容器和导航

  • 修改main.js,配置css加载顺序(配置重置样式)

  • 修改App.vue,配置样式,上下自动填充

  •  编写Home页面,完成导航和二级路由显示
                   首页    班级管理   班级列表     学生管理   学生列表                                         学生管理系统Element UI 版  export default {}  .el-container {    height: 100%;  }  .home-header {    padding: 0;  }  .el-header, .el-footer {    background-color: #B3C0D1;    color: #333;    text-align: center;    line-height: 60px;  }

1.4 编辑学生(弹出框)

1.4.1 分析

  • 页面布局:

    • 添加一个“添加”按钮,点击可以显示弹出层

    • 拷贝添加的弹出框Dialog,且要求表单(班级列表、id、名称、年龄、生日、性别)

  • 提供student变量,用于表单数据的绑定

  • ajax操作

    • 查询班级列表

    • 添加按钮绑定事件,进行ajax提交(成功:刷新列表关闭弹出框,失败:错误提示,但不关闭弹出框)

1.4.2 页面布局

  • 页面布局:

    • 添加一个“添加”按钮,点击可以显示弹出层

  •  拷贝添加的弹出框Dialog,且要求表单(班级列表、id、名称、年龄、生日、性别)
                                                     男     女                        
  • 提供student变量,用于表单数据的绑定

1.4.3 添加:ajax操作

  • 查询班级列表

  •  添加按钮绑定事件,进行ajax提交(成功:刷新列表关闭弹出框,失败:错误提示,但不关闭弹出框)

  
- 查询 添加 男 女 {{scope.row.gender == 1 ? "男" : "女"}} 编辑 删除
// 导入axiosimport axios from 'axios'export default { data() { return { studentVo: { //条件查询 }, studentPage: { //分页数据 pageNum: 1, pageSize: 3 }, addStudentDialogVisible: false, //添加弹出框的控制变量 student: { //添加表单对象 }, classesList: [], // 所有班级 } }, methods: { async condition(num) { if(num) { this.studentPage.pageNum = num } // ajax查询 var url = `http://localhost:8888/student/condition/${this.studentPage.pageSize}/${this.studentPage.pageNum}` let {data:baseResult} = await axios.post(url, this.studentVo) // 保存结果 this.studentPage = baseResult.data }, handleSelectionChange(val) { console.info('批量删除') }, handleSizeChange(val) { console.log(`每页 ${val} 条`); this.studentPage.pageSize = val this.studentPage.pageNum = 1 // 重新开始 this.condition() }, handleCurrentChange(val) { console.log(`当前页: ${val}`); this.studentPage.pageNum = val // 重新开始 this.condition() }, async selectAllClasses() { // ajax 查询所有的班级 var url = `http://localhost:8888/classes` let { data: baseResult } = await axios.get(url) // 保存结果 this.classesList = baseResult.data }, openAddDialog() { // 打开弹出框 this.addStudentDialogVisible = true // 清空表单数据 this.student = {} // 查询班级列表 this.selectAllClasses() }, async addStudent() { // 添加学生ajax var url = `http://localhost:8888/student/saveOrUpdate` let { data: baseResult } = await axios.post(url, this.student) // 处理结果 if(baseResult.code == 20000) { // 成功:刷新页面,成功提示,关闭弹出框 this.condition() this.$message.success(baseResult.message) this.addStudentDialogVisible = false } else { // 失败:失败提示 this.$message.error(baseResult.message) } } }, mounted() { // 查询班级 this.selectAllClasses() // 查询学生 this.condition() },}

1.4.4 修改:ajax操作

  • 点击修改按钮,通过id查询详情,显示弹出框,并自动填充表单。

  
- 查询 添加 男 女 {{scope.row.gender == 1 ? "男" : "女"}} 编辑 删除
// 导入axiosimport axios from 'axios'export default { data() { return { studentVo: { //条件查询 }, studentPage: { //分页数据 pageNum: 1, pageSize: 3 }, addStudentDialogVisible: false, //添加弹出框的控制变量 student: { //添加表单对象 }, classesList: [], // 所有班级 dialogTitle: '', // 弹出框的标题 } }, methods: { async condition(num) { if(num) { this.studentPage.pageNum = num } // ajax查询 var url = `http://localhost:8888/student/condition/${this.studentPage.pageSize}/${this.studentPage.pageNum}` let {data:baseResult} = await axios.post(url, this.studentVo) // 保存结果 this.studentPage = baseResult.data }, handleSelectionChange(val) { console.info('批量删除') }, handleSizeChange(val) { console.log(`每页 ${val} 条`); this.studentPage.pageSize = val this.studentPage.pageNum = 1 // 重新开始 this.condition() }, handleCurrentChange(val) { console.log(`当前页: ${val}`); this.studentPage.pageNum = val // 重新开始 this.condition() }, async selectAllClasses() { // ajax 查询所有的班级 var url = `http://localhost:8888/classes` let { data: baseResult } = await axios.get(url) // 保存结果 this.classesList = baseResult.data }, openAddDialog() { // 设置标题 this.dialogTitle = '添加学生' // 打开弹出框 this.addStudentDialogVisible = true // 清空表单数据 this.student = {} // 查询班级列表 this.selectAllClasses() }, async openUpdateDialog(sid) { // 设置标题 this.dialogTitle = '修改学生' // 通过id查询详情 var url = `http://localhost:8888/student/${sid}` let { data: baseResult } = await axios.get(url) this.student = baseResult.data // 查询班级列表 this.selectAllClasses() // 打开弹出框 this.addStudentDialogVisible = true }, async addStudent() { // 添加学生ajax var url = `http://localhost:8888/student/saveOrUpdate` let { data: baseResult } = await axios.post(url, this.student) // 处理结果 if(baseResult.code == 20000) { // 成功:刷新页面,成功提示,关闭弹出框 this.condition() this.$message.success(baseResult.message) this.addStudentDialogVisible = false } else { // 失败:失败提示 this.$message.error(baseResult.message) } } }, mounted() { // 查询班级 this.selectAllClasses() // 查询学生 this.condition() },}

2. 用户管理

2.1 用户名登录

2.1.1 显示登录页面

  export default {  data() {    return {      user: {},    }  },  methods: {    login() {   }  },}  .login {    height: 100%;    display: flex;    flex-direction: row;    justify-content: center;    align-items: center;  }  .login-card {    width: 500px;  }

2.1.2 表单校验

  • 普通字段校验

  export default {  data() {    return {      user: {},      loginRules: {   //校验规则 username: [   { required: true, message: '请输入用户名', trigger: 'blur' },   { min: 3, max: 6, message: '长度在 3 到 6 个字符', trigger: 'blur' } ], password: [   { required: true, message: '请输入密码', trigger: 'blur' },   { min: 6, max: 9, message: '长度在 6 到 9 个字符', trigger: 'blur' } ]      }    }  },  methods: {    login() {      this.$message.success('ajax发送')    }  },}  .login {    height: 100%;    display: flex;    flex-direction: row;    justify-content: center;    align-items: center;  }  .login-card {    width: 500px;  }
  • 程序校验

  export default {  data() {    return {      user: {},      loginRules: {   //校验规则 username: [   { required: true, message: '请输入用户名', trigger: 'blur' },   { min: 3, max: 6, message: '长度在 3 到 6 个字符', trigger: 'blur' } ], password: [   { required: true, message: '请输入密码', trigger: 'blur' },   { min: 6, max: 9, message: '长度在 6 到 9 个字符', trigger: 'blur' } ]      }    }  },  methods: {    login() {      this.$refs.loginForm.validate((valid) => { if (valid) {   // 校验通过   this.$message.success('ajax发送') } else {   console.log('error submit!!');   return false; }      });   }  },}  .login {    height: 100%;    display: flex;    flex-direction: row;    justify-content: center;    align-items: center;  }  .login-card {    width: 500px;  }

2.1.3 ajax提交

  • 表单校验通过后,发送ajax,如果登录成功跳转到首页,如果失败提示“用户名或密码不匹配”

methods: {    login() {      this.$refs.loginForm.validate(async (valid) => { if (valid) {   // 校验通过 发送ajax start   var url = `http://localhost:8888/user/login`   let { data: baseResult } = await axios.post(url, this.user)   if( baseResult.code == 20000) {     // 登录成功,跳转到首页     this.$router.push('/home')   } else {     // 登录失败     this.$message.error(baseResult.message)   }   // 校验通过 发送ajax end } else {   console.log('error submit!!');   return false; }      });   }  },

2.1.4 后端实现

  • 步骤:

    • 步骤1:拷贝表

    • 步骤2:编写JavaBean

    • 步骤3:编写mapper

    • 步骤4:编写service,提供login,使用用户名和密码进行查询,null或user

    • 步骤5:编写controller,根据返回值提出,登录成功/账号或密码不匹配

步骤1:拷贝表

CREATE TABLE `tb_user` (  `u_id` varchar(32) NOT NULL COMMENT '用户编号',  `user_name` varchar(50) DEFAULT NULL COMMENT '用户名',  `password` varchar(32) DEFAULT NULL COMMENT '密码',  `gender` bit(1) DEFAULT NULL COMMENT '性别,1表示男,0表示女',  PRIMARY KEY (`u_id`),  UNIQUE KEY `user_name` (`user_name`)) ENGINE=InnoDB DEFAULT CHARSET=utf8;/*Data for the table `tb_user` */insert  into `tb_user`(`u_id`,`user_name`,`password`,`gender`) values ('1','jack','1234',''),('10','jack5','1234',''),('2','rose','1234','\0'),('3','张三','1234',''),('4','tom','1234',''),('5','jack2','1234',''),('6','jack1','1234',''),('7','jack3','1234',''),('8','jack4','1234',''),('cd0d2523b5024589af142787de8a7b2a','jack6','1234','');

步骤2:编写JavaBean

package com.czxy.domain;import lombok.Data;import javax.persistence.Column;import javax.persistence.Id;import javax.persistence.Table;@Data@Table(name = "tb_user")public class User {    @Id    @Column(name = "u_id")    private String uid;    @Column(name = "user_name")    private String username;    @Column(name = "password")    private String password;    @Column(name = "gender")    private Integer gender;     // 0 或 1}

步骤3:编写mapper

package com.czxy.mapper;import com.czxy.domain.User;import tk.mybatis.mapper.common.Mapper;@org.apache.ibatis.annotations.Mapperpublic interface UserMapper extends Mapper {}

步骤4:编写service,提供login,使用用户名和密码进行查询,null或user

  • 接口

package com.czxy.service;import com.czxy.domain.User;public interface UserService {    /**     *     * @param userLogin 用户名和密码(表单提交)     * @return 查询结果(数据库查询)     */    public User login(User userLogin);}
  • 实现类
package com.czxy.service.impl;import com.czxy.domain.User;import com.czxy.mapper.UserMapper;import com.czxy.service.UserService;import org.springframework.stereotype.Service;import org.springframework.transaction.annotation.Transactional;import tk.mybatis.mapper.entity.Example;import javax.annotation.Resource;import java.util.List;@Service@Transactionalpublic class UserServiceImpl implements UserService {    @Resource    private UserMapper userMapper;    @Override    public User login(User userLogin) { // 用户名和密码查询,如果有结果返回,如果没有返回null Example example = new Example(User.class); Example.Criteria criteria = example.createCriteria(); criteria.andEqualTo("username", userLogin.getUsername()); criteria.andEqualTo("password", userLogin.getPassword()); // 查询 List list = userMapper.selectByExample(example); // 返回第一个数据 if(list != null && list.size() > 0) {     return list.get(0); } return null;    }}
  • 步骤5:编写controller,根据返回值提出,登录成功/账号或密码不匹配
package com.czxy.controller;import com.czxy.domain.User;import com.czxy.service.UserService;import com.czxy.vo.BaseResult;import org.springframework.web.bind.annotation.*;import javax.annotation.Resource;@RestController@CrossOrigin //跨域@RequestMapping("/user")public class UserController {    @Resource    private UserService userService;    @PostMapping("/login")    public BaseResult login(@RequestBody User user) { // 登录 User loginUser = userService.login(user); // 判断 if(loginUser != null) {     // 登录成功     return BaseResult.ok("登录成功", loginUser); } else {     // 登录失败     return BaseResult.error("用户名或密码不匹配"); }    }}

2.2 注册:用户名校验(ajax校验)

2.2.1 需求

  • 用户名存在,表单不能注册。用户名不存在,可以注册。

2.2.2 后端

  • 通过用户名查询,根据查询结果提示

    • 查询到,提示“用户名已存在”

    • 没有查询到,提示“用户名可用”

  • 步骤:

    • 步骤1:service,通过用户名查询

    • 步骤2:controller,post,json数据,判断

  • 步骤1:service,通过用户名查询

    • 接口

 /**     * 通过用户名查询     * @param username     * @return     */    public User findByUsername(String username);
  • 实现类
 @Override    public User findByUsername(String username) { // 用户名和密码查询,如果有结果返回,如果没有返回null Example example = new Example(User.class); Example.Criteria criteria = example.createCriteria(); criteria.andEqualTo("username", username); // 查询 List list = userMapper.selectByExample(example); // 返回第一个数据 if(list != null && list.size() > 0) {     return list.get(0); } return null;    }

步骤2:controller,post,json数据,判断

@PostMapping("/check")    public BaseResult check(@RequestBody User user) { // 登录 User findUser = userService.findByUsername(user.getUsername()); // 判断 if(findUser == null) {     // 没有结果,可用     return BaseResult.ok("用户名可用"); } else {     // 有结果,不可用,已存在     return BaseResult.error("用户名已存在"); }    }

2.2.3 前端:页面

  • 步骤:

    • 步骤1:注册编写路由

    • 步骤2:创建注册页面

    • 步骤3:拷贝注册表单

步骤1:注册编写路由

  {    path: '/register',    name: '注册',    component: () => import('../views/Register.vue')  },

步骤2:创建注册页面

 步骤3:拷贝注册表单

                                                                                        男   女                 抽烟   喝酒   烫头                                        注册 重置              {{ user }}  export default {  data() {    return {      user: { hobbies: [] ,     //必须是数组      },      cityList: [ {   value: 'js',   label: '江苏省',   children: [     {value: 'nj',label: '南京市',     },     {value: 'sq',label: '宿迁市',children: [  {    value: 'sy',    label: '沭阳县',    children: [      { value: 'nh', label: '南湖街道',      },      { value: 'mx', label: '梦溪街道',      }    ]  },  {    value: 'sh',    label: '泗洪县',  }]     }   ] }, {   value: 'hb',   label: '河北省', }      ]    }  },}  .register-card {    width: 500px;  }

2.2.4 前端:自定义校验

  • 步骤

    • 步骤1:完成用户名普通校验(必填、长度3-6)

    • 步骤2:自定义ajax用户名校验

  • 步骤1:完成用户名普通校验(必填、长度3-6)

                                                                                        男   女                 抽烟   喝酒   烫头                                        注册 重置              {{ user }}  export default {  data() {    return {      user: { hobbies: [] ,     //必须是数组      },      cityList: [ {   value: 'js',   label: '江苏省',   children: [     {value: 'nj',label: '南京市',     },     {value: 'sq',label: '宿迁市',children: [  {    value: 'sy',    label: '沭阳县',    children: [      { value: 'nh', label: '南湖街道',      },      { value: 'mx', label: '梦溪街道',      }    ]  },  {    value: 'sh',    label: '泗洪县',  }]     }   ] }, {   value: 'hb',   label: '河北省', }      ],      registerRules: { username: [   { required: true, message: '请输入用户名', trigger: 'blur' },   { min: 3, max: 6, message: '长度在 3 到 6 个字符', trigger: 'blur' } ],      },    }  },  methods: {    register() {      this.$refs.registerForm.validate((valid) => { if (valid) {   // 校验通过 } else {   // 没通过   console.log('error submit!!');   return false; }      });    }  },}  .register-card {    width: 500px;  }

步骤2:自定义ajax用户名校验

                                                                                        男   女                 抽烟   喝酒   烫头                                        注册 重置              {{ user }}  import axios from 'axios'export default {  data() {    // 自定义校验器   var 函数名 = 箭头函数(规则,数据,回调函数)    // 校验通过:callback();    // 校验失败:callback(new Error('失败原因'));    var validateUsername = async (rule, value, callback) => {      // 1 发送ajax根据用户查询      var url = `http://localhost:8888/user/check`      let { data: baseResult } = await axios.post(url,{username: value})      // 2 根据结果处理:20000通过,否则失败      if(baseResult.code == 20000) { // 2.1 成功 callback();      } else { // 2.2 失败 callback(new Error(baseResult.message));      }    };    return {      user: { hobbies: [] ,     //必须是数组      },      cityList: [ {   value: 'js',   label: '江苏省',   children: [     {value: 'nj',label: '南京市',     },     {value: 'sq',label: '宿迁市',children: [  {    value: 'sy',    label: '沭阳县',    children: [      { value: 'nh', label: '南湖街道',      },      { value: 'mx', label: '梦溪街道',      }    ]  },  {    value: 'sh',    label: '泗洪县',  }]     }   ] }, {   value: 'hb',   label: '河北省', }      ],      registerRules: { username: [   { required: true, message: '请输入用户名', trigger: 'blur' },  //内置校验:必填   { min: 3, max: 6, message: '长度在 3 到 6 个字符', trigger: 'blur' }, //内置校验:长度   { validator: validateUsername, trigger: 'blur' }     //自定义校验:用户名校验 validateUsername ],      },    }  },  methods: {    register() {      this.$refs.registerForm.validate((valid) => { if (valid) {   // 校验通过 } else {   // 没通过   console.log('error submit!!');   return false; }      });    }  },}  .register-card {    width: 500px;  }

页面展示

Job256网站商业源码