🚀个人主页:欢迎访问Ali.s的首页
⏰ 最近更新:2022年10月13日
⛽ Java框架学习系列:【Spring】【SpringMVC】【Mybatis】
🔥 Java项目实战系列:【飞机大战】【图书管理系统】
🍭 Java算法21天系列:【查找】【排序】【递归】
⛳ Java基础学习系列:【继承】【封装】【多态】
🏆 通信仿真学习系列:【硬件】【通信】【MATLAB】
🍄 个人简介:通信工程本硕🌈、Java程序员🚴。目前只会CURD😂
💌 点赞 👍 收藏 💗留言 💬 都是我最大的动力💯
前言
这里是【JAVASE】
项目实战的第七节课,前面完成了书籍管理功能,今天做的是学生管理功能,使用【Servlet】
、【AJax】
、【MySql】
、【Jsp】
来实现学生管理功能,主要包含院系、班级、学生的后台服务。
一、需求分析
与前面的书籍管理基本类似,主要不同时院级和班级有一个级联查询操作,这里使用篇【Ajax】异步回写数据,完成多级联动的效果,而学生与院级、班属于一个三级联动,建议后面使用【Springboot】和前端框架【vue】做更好。
二、功能实现
在dao
层和service
层中创建接口。这里与用户模块类似,首先完成前端页面的信息,然后进行后端的校验逻辑的判断,到层处理sql
语句,需要准备student、department、class
实体类,便于关系的映射和值的获取与传递。
1.实体的创建
结合数据库字段信息,完成实体类的创建,这里使用逆向工程生成相应的实体类,刚开始做项目,建议手动写实体类,对每个字段的类型有一个基本的了解,还要注意使用工具类需要自己手动添加下toString()
方法。
package com.song.bookmanagersystem.entity;
import java.io.Serializable;
/**
* (TStudent)实体类
*
* @author Ali.S
* @since 2022-08-15 19:18:54
*/
public class Student implements Serializable {
private static final long serialVersionUID = -62801523208012657L;
/**
* 学员id
*/
private Integer id;
/**
* 学籍编号
*/
private String stuNum;
/**
* 学员姓名
*/
private String stuName;
/**
* 手机号
*/
private String phoneNum;
/**
* 性别
*/
private String gender;
/**
* 家庭地址
*/
private String address;
/**
* 所属班级
*/
private Integer classid;
/**
* 班级名称-冗余字段
*/
private String className;
/**
* 所属系别-冗余字段
*/
private Integer departid;
/**
* 院系名称-冗余字段
*/
private String departName;
private Integer isDeleted;
public Integer getId() {
return id;
}
public void setId(Integer id) {
this.id = id;
}
public String getStuNum() {
return stuNum;
}
public void setStuNum(String stuNum) {
this.stuNum = stuNum;
}
public String getStuName() {
return stuName;
}
public void setStuName(String stuName) {
this.stuName = stuName;
}
public String getPhoneNum() {
return phoneNum;
}
public void setPhoneNum(String phoneNum) {
this.phoneNum = phoneNum;
}
public String getGender() {
return gender;
}
public void setGender(String gender) {
this.gender = gender;
}
public String getAddress() {
return address;
}
public void setAddress(String address) {
this.address = address;
}
public Integer getClassid() {
return classid;
}
public void setClassid(Integer classid) {
this.classid = classid;
}
public String getClassName() {
return className;
}
public void setClassName(String className) {
this.className = className;
}
public Integer getDepartid() {
return departid;
}
public void setDepartid(Integer departid) {
this.departid = departid;
}
public String getDepartName() {
return departName;
}
public void setDepartName(String departName) {
this.departName = departName;
}
public Integer getIsDeleted() {
return isDeleted;
}
public void setIsDeleted(Integer isDeleted) {
this.isDeleted = isDeleted;
}
@Override
public String toString() {
return "Student{" +
"id=" + id +
", stuNum='" + stuNum + '\'' +
", stuName='" + stuName + '\'' +
", phoneNum='" + phoneNum + '\'' +
", gender='" + gender + '\'' +
", address='" + address + '\'' +
", classid='" + classid + '\'' +
", className='" + className + '\'' +
", departid='" + departid + '\'' +
", departName='" + departName + '\'' +
", isDeleted=" + isDeleted +
'}';
}
}
2.持久层接口
后端开发一般从dao
层开始写,这样整个架构比较清楚,创建数据持久层的接口与实现,并完成增删改查的相关方法,为业务逻辑层做准备。
public interface StudentDao {
/**
* 对学生增删改查的方法
* @param student
* @return
*/
public List<Student> list(Student student);
public Integer saveStudent(Student student);
public Integer updateStudent(Student student);
public Integer deleteStudent(Integer id);
public Student queryStudentById(Integer id);
}
在完成接口的时候,在实现接口的类中完成相关的方法,注意添加和更新可以在同一个方法中,在具体的方法中通过Ajax
是否拿到当前的数据的id
作为判断标准,进而将两个功能进行单独的处理,这里是单独完成的,代码显得有些冗余,但是逻辑思路更加清,与前面模块类似,可以参考之前写的,这里就不多赘述。
@Override
public Integer saveStudent(Student student) {
queryRunner=DBUtils.getQueryRunner();
sql="insert into t_student (stu_num, stu_name, phone_num, gender, address, classid, class_name, departid, depart_name)values (?,?,?,?,?,?,?,?,?)";
try {
return queryRunner.update(sql,student.getStuNum(),student.getStuName(),student.getPhoneNum(),student.getGender(),student.getAddress(),student.getClassid(),student.getClassName(),student.getDepartid(),student.getDepartName());
} catch (SQLException e) {
e.printStackTrace();
}
return -1;
}
3.院系管理
基本的增删改查前面已经讲的很清楚,这里主要写一下与前面不一样的地方,在院系做信息处理的时候,需要拿到学生信息和所在班级信息,所以使用【Ajax】
异步请求来完成数据的获取与回写,可以使用学生的id
或者手机号作为唯一的关联字段信息,便于整体的数据操作。
private void delete(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
String id = req.getParameter("id");
//判断是否有班级存在
List<Classes> list = classesService.queryClassesByDepartment(Integer.parseInt(id));
if (list!=null && list.size()>0){
//不能删除,给出提示信息
resp.setContentType("text/html;charset=UTF-8");
PrintWriter writer = resp.getWriter();
writer.println("<script type='text/javascript'>");
writer.println("alert(\"对不起,该院系中还存在班级,无法完成院系删除\")");
writer.println("location.href='/departmentServlet?sqltype=query';");
writer.println("</script>");
writer.flush();
}else{
departmentService.deleteDepartment(Integer.parseInt(id));
//重定向
resp.sendRedirect("/departmentServlet?sqltype=qurey");
}
}
4.班级管理
与院系管理类似,需要获取到学生信息,所以根据id查询到班级信息和院系信息,然后做参数绑定,对班级数据进行增删改查,注意重定向与转发的区别与联系,涉及多级联动的数据回写操作,十分容易找不到页面信息。
private void queryById(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
//根据id查询到班级和院系信息
String id= req.getParameter("id");
Classes cla=classesService.queryClassesById(Integer.parseInt(id));
//查询所有院系信息
List<Department> list=departmentService.list(null);
req.setAttribute("cla",cla);
req.setAttribute("depts",list);
//进行页面跳转
req.getRequestDispatcher("/classes/classesUpdate.jsp").forward(req, resp);
}
三、功能测试
启动服务器,让项目在服务器中运行,进入登录页面,输入账号密码后进行学生、班级、院系的查询功能的测试:
接着进行删除功能的测试,这里对院系删除会对当前院系下面是否有班级存在做判断,对班级删除会当前班级内是否存在学生进行判断。
如果存在有班级或者学生是无法完成对应的删除操作,请求就会被终止,不触发任何数据的修改。
总结
以上就是今天要讲的内容,使用【Servlet】
、【AJax】
、【MySql】
、【Jsp】
来实现学生管理功能,对院系、班级、学生三级联动进行了实现,为后续借阅管理做准备。