[JAVA MVC] Quickly build a simple student information management system

scene import

        In modern web development, choosing the right technology stack is crucial to building robust and scalable applications. This blog will introduce a very popular and powerful combination of technologies such as Spring Boot, JPA, Thymeleaf, MySQL, and additional Bootstrap libraries. This combination can not only help developers efficiently build web applications, but also provide better user experience and simplify the development process. Let's follow a certain requirement to develop a student information management system, as shown in the figure:

1. Technical introduction

1.Spring Boot:

        Spring Boot is a development tool based on the Spring Framework that simplifies the development of Java applications by providing automated configuration and the principles of convention over configuration. Spring Boot can greatly improve development efficiency, and also provides a wealth of plug-ins and functions, such as embedded servers, automated dependency management and configuration, and integration of many commonly used development components.

2.JPA(Java Persistence API)

        JPA is an ORM (Object-Relational Mapping) specification on the Java platform, which provides a way to map Java objects into relational databases. Compared with traditional SQL programming, using JPA can operate the database more conveniently, provides object-level query and persistent operations, and reduces developers' troubles in database access.

3.Thymeleaf

        Thymeleaf is a modern server-side Java template engine for building server-side Java templates. It allows developers to render dynamic data to HTML pages and supports a powerful expression language and template layout. Thymeleaf's syntax is simple and easy to use, making front-end development easier.

4.MySQL

       MySQL is an open source relational database management system that is widely used for web application development. It has excellent performance, reliability and scalability, and provides rich query language and stored procedure support. By combining with Spring Boot and JPA, we can easily perform database operations and realize data persistence and query.

5.Bootstrap

        Bootstrap is a popular front-end development framework, which provides rich CSS and JavaScript components, which can help us quickly build a modern user interface. By integrating Bootstrap, we can beautify and enhance the appearance and user interaction of the web application, making the display effect of the application on different devices more uniform and friendly.

2. Implementation process

1. Create a new project

As shown in the figure, when IDEA creates a new project, select Spring Initializr and select Maven;

JDK 17 is recommended; add the following five dependencies

 

2. Add Bootstrap style

There are many styles on the official website, which can be modified according to the actual situation

3. Add database configuration

Add local or remote database information in the application.properties file for subsequent use

4. Framework construction

 

5. Write model properties

        The Model layer is used to write our business composition attributes. We are now writing a student management system, so write the student’s name, gender and other attributes in the Model layer , and simultaneously build the Students student information table in the database

6. Add student information

        If you want to add web page information to the database, you need to write the adding method in the business interface StudentService first, then inject the JPA interface dependency into the StudentServiceLmpl class , then inherit the business interface and implement the method, and then set the mapping in the control layer StudentController , when the URL is When specifying the URL, call the Add function to get the data passed in from the web page and call the Add method to store the data in the database, and then jump back to the main page, as shown in the figure:

 

 It should be noted that both the business layer implementation class and the control layer must first rely on injection, as shown in the figure:

7. Modify student information

        The implementation steps of the modification function are similar to those of the addition, but in the control layer, a new mapping needs to be created, and the student information is searched through the id information in the URL spliced ​​and jumped by the web page, and the information is displayed on the new web page. After the user changes, it will jump to the save function , as shown in the figure:

 

 

 

8. Delete student information

       The implementation steps of the modification function are similar to those of the addition, but in the control layer, a new mapping needs to be created, and the student information can be found through the id information in the URL spliced ​​and jumped from the web page, and directly deleted and then jumped to the save function, as shown in the figure:

 

9. Find

         The search function is to specify the student name for fuzzy query, so we need to create a method in the JPA interface, and then create and implement the method in the business layer, and then the steps are the same as before

        Here is a small detail. Mapping is established in the control layer, the name of the URL is obtained, and the search is performed, so the jump link needs to be set in the index.html file, as shown in the figure:

10. Paging, sorting

        Paging and sorting are methods that come with MVC. We only need to understand and call them according to the syntax. First, inject JPA interface dependencies into the StudentServiceLmpl class, then inherit the business interface and implement the methods, and then set the mapping in the control layer StudentController. The URL is, call the add function, get the data passed in from the webpage, call the add method, store the data in the database, and then jump back to the main page. The process is shown in the figure: It is stipulated that each page has more than five data and enters the next page. Set The number of them is increasing in order, and the web page settings can be sorted according to different numbers of columns according to different needs. desc: is descending order, asc: is ascending order

11. Expansion (database one-to-one)

       In order to achieve the one-to-one effect of the database, I added a class class table with the class name in it. The data first set two classes and unassigned, then added a foreign key link to the class table in the student table, and finally added the JPA interface of the class , Business layer, you can get all the class names in the class table at the control layer, and then pass the data to the index main page, you can add a drop-down box to select the class, and use it to realize the search. And added operations such as class management page and adding, modifying and checking, and when the class name changes, the class name of the student information also changes

 

 

 

 

 

 The final effect of the web page

Add to

Revise

look up

Pagination and sorting

View all classes and search here

class management page

Modify class information

Add class information


 

3. Code display

1. Model layer (Studnt, Class1)

package com.example.studentproj.model;

import jakarta.persistence.*;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import lombok.ToString;

@Data
@NoArgsConstructor
@AllArgsConstructor
@ToString

/**
 * Class1实体类,对应数据库中的class表
 */
@Entity
@Table(name = "class")
public class Class1 {
    /**
     * 主键ID,自动生成且自增长
     */
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Column(name = "id")
    private Long id;

    /**
     * 班级名称
     */
    @Column(name = "classname")
    private String name;
}
package com.example.studentproj.model;

import jakarta.persistence.*;
import lombok.Data;

@Data
@Entity
@Table(name = "students")
public class Student {
    /**
     * 学生ID,自动生成且自增长
     */
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private long id;

    /**
     * 学生姓名
     */
    @Column(name = "name")
    private String name;

    /**
     * 学生性别
     */
    @Column(name = "sex")
    private String sex;

    /**
     * 学生年龄
     */
    @Column(name = "age")
    private int age;

    /**
     * 学籍状态
     */
    @Column(name = "status")
    private String status;

    /**
     * 学生籍贯
     */
    @Column(name = "ticy")
    private String ticy;

    /**
     * 班级名称
     */
    @Column(name = "class_name")
    private String className;

    /**
     * 班级关联
     */
    @ManyToOne
    @JoinColumn(name = "class_id")
    private Class1 class1;
}

2. Control layer (StudentController)

package com.example.studentproj.controller;

import com.example.studentproj.model.Class1;
import com.example.studentproj.model.Student;
import com.example.studentproj.repository.ClassRepository;
import com.example.studentproj.service.ClassService;
import com.example.studentproj.service.StudentService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.*;

import java.util.List;

@Controller
public class StudentController {

    //依赖注入StudentService接口
    @Autowired
    private StudentService studentService;

    //依赖注入ClassService接口
    @Autowired
    private ClassService classService;



    //将获取到的班级名称信息传入model,并且跳转分页函数
    @GetMapping("/")
    public String viewHomePage(Model model) {
        List<Class1> listclass = classService.getAllClass();
        model.addAttribute("listclass",listclass);
        return findPaginated(1, "name", "asc" ,model);
    }


    //跳转添加学生信息网页
    @GetMapping("/showNewStudentForm")
    public String showStudet(Model model){
        Student student = new Student();
        List<Class1> listclass = classService.getAllClass();
        model.addAttribute("listclass",listclass);
        model.addAttribute("student",student);
        return "new_student";
    }

    //跳转保存学生信息网页
    @PostMapping("/saveStudent")
    public String saveStudnt(@ModelAttribute("student") Student student){
        studentService.saveStudent(student);
        return "redirect:/";
    }

    //根据id读取数据库数据,并支持修改
    @GetMapping("/showNewStudentUpdate{id}")
    public String showFormForUpdate(@PathVariable(value = "id") long id,Model model){
        Student student = studentService.getStudentByid(id);
        List<Class1> listclass = classService.getAllClass();
        model.addAttribute("listclass",listclass);
        model.addAttribute("student",student);
        return "update_student";
    }


    //根据id读取数据库数据,并直接删除掉
    @GetMapping("/deleteStudent{id}")
    public String deleteStudent(@PathVariable(value = "id") long id){
        this.studentService.deleteStudentByid(id);
        return "redirect:/";
    }

    
    //获取分页数据
    @GetMapping("/page/{pageNo}")
    public String findPaginated(@PathVariable (value = "pageNo") int pageNo,
                                @RequestParam("sortField") String sortField,
                                @RequestParam("sortDir") String sortDir,
                                Model model) {
        //设置每4条数据分一页
        int pageSize = 4;

        Page<Student> page = studentService.findPaginated(pageNo, pageSize, sortField, sortDir);
        List<Student> ListStudent = page.getContent();

        model.addAttribute("currentPage", pageNo);
        model.addAttribute("totalPages", page.getTotalPages());
        model.addAttribute("totalItems", page.getTotalElements());

        model.addAttribute("sortField", sortField);
        model.addAttribute("sortDir", sortDir);
        model.addAttribute("reverseSortDir", sortDir.equals("asc") ? "desc" : "asc");

        model.addAttribute("listStudent", ListStudent);
        return "index";
    }

    //搜索名字
    @GetMapping("/query{inpname}")
    public String query(@PathVariable(value = "inpname") String inpame,Model model){
        List<Student> listStudent = studentService.findByNameContaining(inpame);
        List<Class1> listclass = classService.getAllClass();
        model.addAttribute("listclass",listclass);
        model.addAttribute("listStudent",listStudent);
        return "index";
    }


    //根据班级名称来查找数据
    @GetMapping("/classname{inpname}")
    public String classname(@PathVariable(value = "inpname") String inpame,Model model){
        List<Student> listStudent = studentService.findByClassName(inpame);
        List<Class1> listclass = classService.getAllClass();
        model.addAttribute("listclass",listclass);
        model.addAttribute("listStudent",listStudent);
        return "index";
    }

}

2. JPA interface layer (ClassRepository, StudentRepository)

package com.example.studentproj.repository;


import com.example.studentproj.model.Class1;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.data.jpa.repository.Query;
import org.springframework.stereotype.Repository;

import java.util.List;

@Repository
public interface ClassRepository extends JpaRepository<Class1, Long> {

    //获取class所有班级名字
    @Query("select c.name from Class1 c ")
    List<Class1> findByClassName();

}
package com.example.studentproj.repository;
import com.example.studentproj.model.Student;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.data.jpa.repository.Query;
import org.springframework.data.repository.query.Param;
import org.springframework.stereotype.Repository;
import java.util.List;


@Repository
public interface StudentRepository extends JpaRepository<Student, Long> {

    //通过学生名字来查找学生数据
    @Query("select s from Student s where s.name like %:name%")
    List<Student> findByName(@Param("name") String name);


    //通过班级名字来查找学生数据
    @Query("select s from Student s where s.className = :name")
    List<Student> findByClassName(@Param("name") String name);

}

2. Business interface layer (ClassService, ClassServiceLmpl, StudentService, StudentServiceLmpl)

package com.example.studentproj.service;


import com.example.studentproj.model.Class1;
import java.util.List;


public interface ClassService {
   //获取所有班级数据
    List<Class1> getAllClass();
    
}
package com.example.studentproj.service;

import com.example.studentproj.model.Class1;
import com.example.studentproj.repository.ClassRepository;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.List;

@Service
public class ClassServiceImpl implements ClassService {

    @Autowired
    private ClassRepository classRepository;

    /**
     * 获取所有班级列表
     *
     * @return 所有班级列表
     */
    @Override
    public List<Class1> getAllClasses() {
        return classRepository.findAll();
    }
}
package com.example.studentproj.service;

import com.example.studentproj.model.Student;
import org.springframework.data.domain.Page;

import java.util.List;

public interface StudentService {

    /**
     * 获取所有学生列表
     *
     * @return 所有学生列表
     */
    List<Student> getAllStudents();

    /**
     * 存储学生信息
     *
     * @param student 学生对象
     */
    void saveStudent(Student student);

    /**
     * 通过姓名查询学生列表
     *
     * @param name 姓名
     * @return 符合条件的学生列表
     */
    List<Student> findByNameContaining(String name);

    /**
     * 通过班级查询学生列表
     *
     * @param name 班级名称
     * @return 符合条件的学生列表
     */
    List<Student> findByClassName(String name);

    /**
     * 根据学生ID获取学生信息
     *
     * @param id 学生ID
     * @return 学生对象
     */
    Student getStudentById(Long id);

    /**
     * 根据学生ID删除学生信息
     *
     * @param id 学生ID
     */
    void deleteStudentById(Long id);

    /**
     * 分页查询学生列表
     *
     * @param pageNo         当前页码
     * @param pageSize       每页记录数
     * @param sortField      排序字段
     * @param sortDirection  排序方向
     * @return 分页结果
     */
    Page<Student> findPaginated(int pageNo, int pageSize, String sortField, String sortDirection);
}
package com.example.studentproj.service;

import com.example.studentproj.model.Student;
import com.example.studentproj.repository.StudentRepository;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.domain.Pageable;
import org.springframework.data.domain.Sort;
import org.springframework.stereotype.Service;

import java.util.List;
import java.util.Optional;

@Service
public class StudentServiceImpl implements StudentService {
    @Autowired
    private StudentRepository studentRepository;

    /**
     * 获取所有学生列表
     *
     * @return 所有学生列表
     */
    @Override
    public List<Student> getAllStudents() {
        return studentRepository.findAll();
    }

    /**
     * 存储学生信息
     *
     * @param student 学生对象
     */
    @Override
    public void saveStudent(Student student) {
        studentRepository.save(student);
    }

    /**
     * 通过姓名查询学生列表
     *
     * @param name 姓名
     * @return 符合条件的学生列表
     */
    @Override
    public List<Student> findByNameContaining(String name) {
        return studentRepository.findByNameContaining(name);
    }

    /**
     * 通过班级查询学生列表
     *
     * @param name 班级名称
     * @return 符合条件的学生列表
     */
    @Override
    public List<Student> findByClassName(String name) {
        return studentRepository.findByClassName(name);
    }

    /**
     * 根据学生ID获取学生信息
     *
     * @param id 学生ID
     * @return 学生对象
     */
    @Override
    public Student getStudentById(Long id) {
        Optional<Student> optional = studentRepository.findById(id);
        if (optional.isPresent()) {
            return optional.get();
        } else {
            throw new RuntimeException("查无此人,请重新输入,id: " + id);
        }
    }

    /**
     * 根据学生ID删除学生信息
     *
     * @param id 学生ID
     */
    @Override
    public void deleteStudentById(Long id) {
        studentRepository.deleteById(id);
    }

    /**
     * 分页查询学生列表
     * @param pageNo       当前页码
     * @param pageSize     每页记录数
     * @param sortField    排序字段
     * @param sortDirection  排序方向(ASC或DESC)
     * @return 分页结果
     */
    @Override
    public Page<Student> findPaginated(int pageNo, int pageSize, String sortField, String         sortDirection) {
    Sort sort = sortDirection.equalsIgnoreCase(Sort.Direction.ASC.name())
            ? Sort.by(sortField).ascending()
            : Sort.by(sortField).descending();

    Pageable pageable = PageRequest.of(pageNo - 1, pageSize, sort);
    return studentRepository.findAll(pageable);
}    

        The overall structure code has been put here. The source code of html and the extension code of class will not be put up here. If you are interested, you can explore by yourself or private message me.


Summarize

        Follow  Bai Dao to learn  programming, and by combining Spring Boot, JPA, Thymeleaf, MySQL, and Bootstrap, we can build powerful, efficient, and easy-to-maintain web applications. Spring Boot provides the basic framework for development, JPA simplifies database operations, Thymeleaf and Bootstrap provide better user experience and interface design. I believe that by learning these technology stacks, everyone can quickly get started and develop excellent web applications.

Guess you like

Origin blog.csdn.net/qq_51294997/article/details/131545399