first commit

This commit is contained in:
seahi 2024-12-06 09:53:30 +08:00
commit a3e2a782ea
22 changed files with 2023 additions and 0 deletions

8
AbsenceManager.iml Normal file
View File

@ -0,0 +1,8 @@
<?xml version="1.0" encoding="UTF-8"?>
<module version="4">
<component name="AdditionalModuleElements">
<content url="file://$MODULE_DIR$" dumb="true">
<sourceFolder url="file://$MODULE_DIR$/src" isTestSource="false" />
</content>
</component>
</module>

43
src/dao/BaseDAO.java Normal file
View File

@ -0,0 +1,43 @@
package dao;
import java.util.List;
/**
* 基础DAO接口定义通用的CRUD操作
* @param <T> 实体类型
*/
public interface BaseDAO<T> {
/**
* 插入一条记录
* @param entity 实体对象
* @return 影响的行数
*/
int insert(T entity);
/**
* 根据ID删除记录
* @param id 主键ID
* @return 影响的行数
*/
int deleteById(int id);
/**
* 更新记录
* @param entity 实体对象
* @return 影响的行数
*/
int update(T entity);
/**
* 根据ID查询记录
* @param id 主键ID
* @return 实体对象
*/
T findById(int id);
/**
* 查询所有记录
* @return 实体对象列表
*/
List<T> findAll();
}

38
src/dao/DAOFactory.java Normal file
View File

@ -0,0 +1,38 @@
package dao;
import dao.impl.StudentDAOImpl;
import dao.impl.TeacherDAOImpl;
import dao.impl.LeaveRequestDAOImpl;
/**
* DAO工厂类用于获取各种DAO的实例
*/
public class DAOFactory {
private static final StudentDAO studentDAO = new StudentDAOImpl();
private static final TeacherDAO teacherDAO = new TeacherDAOImpl();
private static final LeaveRequestDAO leaveRequestDAO = new LeaveRequestDAOImpl();
/**
* 获取StudentDAO实例
* @return StudentDAO实例
*/
public static StudentDAO getStudentDAO() {
return studentDAO;
}
/**
* 获取TeacherDAO实例
* @return TeacherDAO实例
*/
public static TeacherDAO getTeacherDAO() {
return teacherDAO;
}
/**
* 获取LeaveRequestDAO实例
* @return LeaveRequestDAO实例
*/
public static LeaveRequestDAO getLeaveRequestDAO() {
return leaveRequestDAO;
}
}

View File

@ -0,0 +1,35 @@
package dao;
import model.LeaveRequest;
import model.ApprovalStatus;
import java.util.Date;
import java.util.List;
/**
* 请假申请DAO接口
*/
public interface LeaveRequestDAO extends BaseDAO<LeaveRequest> {
/**
* 根据学生ID查询请假记录
* @param studentId 学生ID
* @return 请假记录列表
*/
List<LeaveRequest> findByStudentId(int studentId);
/**
* 根据审批状态查询请假记录
* @param status 审批状态
* @return 请假记录列表
*/
List<LeaveRequest> findByStatus(ApprovalStatus status);
/**
* 更新请假申请状态
* @param id 请假申请ID
* @param status 新状态
* @param approverComment 审批意见
* @return 影响的行数
*/
int updateStatus(int id, ApprovalStatus status, String approverComment);
}

30
src/dao/StudentDAO.java Normal file
View File

@ -0,0 +1,30 @@
package dao;
import model.Student;
import java.util.List;
/**
* 学生DAO接口
*/
public interface StudentDAO extends BaseDAO<Student> {
/**
* 根据学号查询学生
* @param studentId 学号
* @return 学生对象
*/
Student findByStudentId(String studentId);
/**
* 根据班级查询学生列表
* @param className 班级名称
* @return 学生列表
*/
List<Student> findByClassName(String className);
/**
* 根据姓名模糊查询学生
* @param name 学生姓名
* @return 学生列表
*/
List<Student> findByNameLike(String name);
}

30
src/dao/TeacherDAO.java Normal file
View File

@ -0,0 +1,30 @@
package dao;
import model.Teacher;
import java.util.List;
/**
* 教师DAO接口
*/
public interface TeacherDAO extends BaseDAO<Teacher> {
/**
* 根据工号查询教师
* @param teacherId 教师工号
* @return 教师对象
*/
Teacher findByTeacherId(String teacherId);
/**
* 根据部门查询教师列表
* @param department 部门名称
* @return 教师列表
*/
List<Teacher> findByDepartment(String department);
/**
* 根据姓名模糊查询教师
* @param name 教师姓名
* @return 教师列表
*/
List<Teacher> findByNameLike(String name);
}

View File

@ -0,0 +1,227 @@
package dao.impl;
import dao.LeaveRequestDAO;
import model.ApprovalStatus;
import model.LeaveRequest;
import model.Student;
import model.Teacher;
import util.DatabaseUtil;
import java.sql.*;
import java.util.ArrayList;
import java.util.List;
public class LeaveRequestDAOImpl implements LeaveRequestDAO {
private final StudentDAOImpl studentDAO = new StudentDAOImpl();
private final TeacherDAOImpl teacherDAO = new TeacherDAOImpl();
@Override
public int insert(LeaveRequest request) {
String sql = "INSERT INTO leave_requests (student_id, start_time, end_time, status, " +
"duration, location, reason_type, reason_detail, is_leaving_city, " +
"special_situation, request_time) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)";
try (Connection conn = DatabaseUtil.getConnection();
PreparedStatement stmt = conn.prepareStatement(sql, Statement.RETURN_GENERATED_KEYS)) {
stmt.setInt(1, request.getStudent().getId());
stmt.setTimestamp(2, new Timestamp(request.getStartTime().getTime()));
stmt.setTimestamp(3, new Timestamp(request.getEndTime().getTime()));
stmt.setString(4, request.getStatus().name());
stmt.setDouble(5, request.getDuration());
stmt.setString(6, request.getLocation());
stmt.setString(7, request.getReasonType());
stmt.setString(8, request.getReasonDetail());
stmt.setBoolean(9, request.isLeavingCity());
stmt.setString(10, request.getSpecialSituation());
stmt.setTimestamp(11, new Timestamp(request.getRequestTime().getTime()));
int affectedRows = stmt.executeUpdate();
if (affectedRows == 0) {
return 0;
}
try (ResultSet generatedKeys = stmt.getGeneratedKeys()) {
if (generatedKeys.next()) {
request.setId(generatedKeys.getInt(1));
}
}
return affectedRows;
} catch (SQLException e) {
e.printStackTrace();
return 0;
}
}
@Override
public int deleteById(int id) {
String sql = "DELETE FROM leave_requests WHERE id = ?";
try (Connection conn = DatabaseUtil.getConnection();
PreparedStatement stmt = conn.prepareStatement(sql)) {
stmt.setInt(1, id);
return stmt.executeUpdate();
} catch (SQLException e) {
e.printStackTrace();
return 0;
}
}
@Override
public int update(LeaveRequest request) {
String sql = "UPDATE leave_requests SET student_id = ?, start_time = ?, " +
"end_time = ?, status = ?, duration = ?, location = ?, " +
"reason_type = ?, reason_detail = ?, is_leaving_city = ?, " +
"special_situation = ?, request_time = ? WHERE id = ?";
try (Connection conn = DatabaseUtil.getConnection();
PreparedStatement stmt = conn.prepareStatement(sql)) {
stmt.setInt(1, request.getStudent().getId());
stmt.setTimestamp(2, new Timestamp(request.getStartTime().getTime()));
stmt.setTimestamp(3, new Timestamp(request.getEndTime().getTime()));
stmt.setString(4, request.getStatus().name());
stmt.setDouble(5, request.getDuration());
stmt.setString(6, request.getLocation());
stmt.setString(7, request.getReasonType());
stmt.setString(8, request.getReasonDetail());
stmt.setBoolean(9, request.isLeavingCity());
stmt.setString(10, request.getSpecialSituation());
stmt.setTimestamp(11, new Timestamp(request.getRequestTime().getTime()));
stmt.setInt(12, request.getId());
return stmt.executeUpdate();
} catch (SQLException e) {
e.printStackTrace();
return 0;
}
}
@Override
public LeaveRequest findById(int id) {
String sql = "SELECT lr.*, s.* FROM leave_requests lr " +
"JOIN students s ON lr.student_id = s.id " +
"WHERE lr.id = ?";
try (Connection conn = DatabaseUtil.getConnection();
PreparedStatement stmt = conn.prepareStatement(sql)) {
stmt.setInt(1, id);
ResultSet rs = stmt.executeQuery();
if (rs.next()) {
return mapResultSetToLeaveRequest(rs);
}
} catch (SQLException e) {
e.printStackTrace();
}
return null;
}
@Override
public List<LeaveRequest> findAll() {
List<LeaveRequest> requests = new ArrayList<>();
String sql = "SELECT lr.*, s.* FROM leave_requests lr " +
"JOIN students s ON lr.student_id = s.id";
try (Connection conn = DatabaseUtil.getConnection();
Statement stmt = conn.createStatement();
ResultSet rs = stmt.executeQuery(sql)) {
while (rs.next()) {
requests.add(mapResultSetToLeaveRequest(rs));
}
} catch (SQLException e) {
e.printStackTrace();
}
return requests;
}
@Override
public List<LeaveRequest> findByStudentId(int studentId) {
List<LeaveRequest> requests = new ArrayList<>();
String sql = "SELECT lr.*, s.* FROM leave_requests lr " +
"JOIN students s ON lr.student_id = s.id " +
"WHERE lr.student_id = ? ORDER BY lr.request_time DESC";
try (Connection conn = DatabaseUtil.getConnection();
PreparedStatement stmt = conn.prepareStatement(sql)) {
stmt.setInt(1, studentId);
ResultSet rs = stmt.executeQuery();
while (rs.next()) {
requests.add(mapResultSetToLeaveRequest(rs));
}
} catch (SQLException e) {
e.printStackTrace();
}
return requests;
}
@Override
public List<LeaveRequest> findByStatus(ApprovalStatus status) {
List<LeaveRequest> requests = new ArrayList<>();
String sql = "SELECT lr.*, s.* FROM leave_requests lr " +
"JOIN students s ON lr.student_id = s.id " +
"WHERE lr.status = ? ORDER BY lr.request_time DESC";
try (Connection conn = DatabaseUtil.getConnection();
PreparedStatement stmt = conn.prepareStatement(sql)) {
stmt.setString(1, status.name());
ResultSet rs = stmt.executeQuery();
while (rs.next()) {
requests.add(mapResultSetToLeaveRequest(rs));
}
} catch (SQLException e) {
e.printStackTrace();
}
return requests;
}
@Override
public int updateStatus(int requestId, ApprovalStatus status, String comment) {
String sql = "UPDATE leave_requests SET status = ?, approval_comment = ?, approval_time = ? WHERE id = ?";
try (Connection conn = DatabaseUtil.getConnection();
PreparedStatement stmt = conn.prepareStatement(sql)) {
stmt.setString(1, status.name());
stmt.setString(2, comment);
stmt.setTimestamp(3, new Timestamp(System.currentTimeMillis()));
stmt.setInt(4, requestId);
return stmt.executeUpdate();
} catch (SQLException e) {
e.printStackTrace();
return 0;
}
}
private LeaveRequest mapResultSetToLeaveRequest(ResultSet rs) throws SQLException {
LeaveRequest request = new LeaveRequest();
request.setId(rs.getInt("id"));
request.setLocation(rs.getString("location"));
request.setStartTime(rs.getTimestamp("start_time"));
request.setEndTime(rs.getTimestamp("end_time"));
request.setStatus(ApprovalStatus.valueOf(rs.getString("status")));
request.setDuration(rs.getDouble("duration"));
request.setReasonType(rs.getString("reason_type"));
request.setReasonDetail(rs.getString("reason_detail"));
request.setLeavingCity(rs.getBoolean("is_leaving_city"));
request.setSpecialSituation(rs.getString("special_situation"));
request.setRequestTime(rs.getTimestamp("request_time"));
// 设置学生信息
Student student = new Student();
student.setId(rs.getInt("student_id"));
student.setStudentId(rs.getString("student_id"));
student.setName(rs.getString("name"));
student.setClassName(rs.getString("class_name"));
student.setContact(rs.getString("contact"));
request.setStudent(student);
Timestamp approvalTime = rs.getTimestamp("approval_time");
if (approvalTime != null) {
request.setApprovalTime(approvalTime);
}
return request;
}
}

View File

@ -0,0 +1,189 @@
package dao.impl;
import dao.StudentDAO;
import model.Student;
import util.DatabaseUtil;
import java.sql.*;
import java.util.ArrayList;
import java.util.List;
/**
* StudentDAO实现类
*/
public class StudentDAOImpl implements StudentDAO {
@Override
public int insert(Student student) {
String sql = "INSERT INTO students (student_id, name, class_name, contact, college, major, is_graduating) VALUES (?, ?, ?, ?, ?, ?, ?)";
try (Connection conn = DatabaseUtil.getConnection();
PreparedStatement stmt = conn.prepareStatement(sql, Statement.RETURN_GENERATED_KEYS)) {
stmt.setString(1, student.getStudentId());
stmt.setString(2, student.getName());
stmt.setString(3, student.getClassName());
stmt.setString(4, student.getContact());
stmt.setString(5, student.getCollege());
stmt.setString(6, student.getMajor());
stmt.setBoolean(7, student.isGraduating());
int affectedRows = stmt.executeUpdate();
if (affectedRows == 0) {
return 0;
}
try (ResultSet generatedKeys = stmt.getGeneratedKeys()) {
if (generatedKeys.next()) {
student.setId(generatedKeys.getInt(1));
}
}
return affectedRows;
} catch (SQLException e) {
e.printStackTrace();
return 0;
}
}
@Override
public int deleteById(int id) {
String sql = "DELETE FROM students WHERE id = ?";
try (Connection conn = DatabaseUtil.getConnection();
PreparedStatement stmt = conn.prepareStatement(sql)) {
stmt.setInt(1, id);
return stmt.executeUpdate();
} catch (SQLException e) {
e.printStackTrace();
return 0;
}
}
@Override
public int update(Student student) {
String sql = "UPDATE students SET student_id = ?, name = ?, class_name = ?, contact = ?, college = ?, major = ?, is_graduating = ? WHERE id = ?";
try (Connection conn = DatabaseUtil.getConnection();
PreparedStatement stmt = conn.prepareStatement(sql)) {
stmt.setString(1, student.getStudentId());
stmt.setString(2, student.getName());
stmt.setString(3, student.getClassName());
stmt.setString(4, student.getContact());
stmt.setString(5, student.getCollege());
stmt.setString(6, student.getMajor());
stmt.setBoolean(7, student.isGraduating());
stmt.setInt(8, student.getId());
return stmt.executeUpdate();
} catch (SQLException e) {
e.printStackTrace();
return 0;
}
}
@Override
public Student findById(int id) {
String sql = "SELECT * FROM students WHERE id = ?";
try (Connection conn = DatabaseUtil.getConnection();
PreparedStatement stmt = conn.prepareStatement(sql)) {
stmt.setInt(1, id);
ResultSet rs = stmt.executeQuery();
if (rs.next()) {
return mapResultSetToStudent(rs);
}
} catch (SQLException e) {
e.printStackTrace();
}
return null;
}
@Override
public List<Student> findAll() {
List<Student> students = new ArrayList<>();
String sql = "SELECT * FROM students";
try (Connection conn = DatabaseUtil.getConnection();
Statement stmt = conn.createStatement();
ResultSet rs = stmt.executeQuery(sql)) {
while (rs.next()) {
students.add(mapResultSetToStudent(rs));
}
} catch (SQLException e) {
e.printStackTrace();
}
return students;
}
@Override
public Student findByStudentId(String studentId) {
String sql = "SELECT * FROM students WHERE student_id = ?";
try (Connection conn = DatabaseUtil.getConnection();
PreparedStatement stmt = conn.prepareStatement(sql)) {
stmt.setString(1, studentId);
ResultSet rs = stmt.executeQuery();
if (rs.next()) {
return mapResultSetToStudent(rs);
}
} catch (SQLException e) {
e.printStackTrace();
}
return null;
}
@Override
public List<Student> findByClassName(String className) {
List<Student> students = new ArrayList<>();
String sql = "SELECT * FROM students WHERE class_name = ?";
try (Connection conn = DatabaseUtil.getConnection();
PreparedStatement stmt = conn.prepareStatement(sql)) {
stmt.setString(1, className);
ResultSet rs = stmt.executeQuery();
while (rs.next()) {
students.add(mapResultSetToStudent(rs));
}
} catch (SQLException e) {
e.printStackTrace();
}
return students;
}
@Override
public List<Student> findByNameLike(String name) {
List<Student> students = new ArrayList<>();
String sql = "SELECT * FROM students WHERE name LIKE ?";
try (Connection conn = DatabaseUtil.getConnection();
PreparedStatement stmt = conn.prepareStatement(sql)) {
stmt.setString(1, "%" + name + "%");
ResultSet rs = stmt.executeQuery();
while (rs.next()) {
students.add(mapResultSetToStudent(rs));
}
} catch (SQLException e) {
e.printStackTrace();
}
return students;
}
/**
* 将ResultSet映射为Student对象
*/
private Student mapResultSetToStudent(ResultSet rs) throws SQLException {
Student student = new Student();
student.setId(rs.getInt("id"));
student.setStudentId(rs.getString("student_id"));
student.setName(rs.getString("name"));
student.setClassName(rs.getString("class_name"));
student.setContact(rs.getString("contact"));
student.setCollege(rs.getString("college"));
student.setMajor(rs.getString("major"));
student.setGraduating(rs.getBoolean("is_graduating"));
return student;
}
}

View File

@ -0,0 +1,180 @@
package dao.impl;
import dao.TeacherDAO;
import model.Teacher;
import util.DatabaseUtil;
import java.sql.*;
import java.util.ArrayList;
import java.util.List;
/**
* TeacherDAO实现类
*/
public class TeacherDAOImpl implements TeacherDAO {
@Override
public int insert(Teacher teacher) {
String sql = "INSERT INTO teachers (teacher_id, name, department, contact) VALUES (?, ?, ?, ?)";
try (Connection conn = DatabaseUtil.getConnection();
PreparedStatement stmt = conn.prepareStatement(sql, Statement.RETURN_GENERATED_KEYS)) {
stmt.setString(1, teacher.getTeacherId());
stmt.setString(2, teacher.getName());
stmt.setString(3, teacher.getDepartment());
stmt.setString(4, teacher.getContact());
int affectedRows = stmt.executeUpdate();
if (affectedRows == 0) {
return 0;
}
try (ResultSet generatedKeys = stmt.getGeneratedKeys()) {
if (generatedKeys.next()) {
teacher.setId(generatedKeys.getInt(1));
}
}
return affectedRows;
} catch (SQLException e) {
e.printStackTrace();
return 0;
}
}
@Override
public int deleteById(int id) {
String sql = "DELETE FROM teachers WHERE id = ?";
try (Connection conn = DatabaseUtil.getConnection();
PreparedStatement stmt = conn.prepareStatement(sql)) {
stmt.setInt(1, id);
return stmt.executeUpdate();
} catch (SQLException e) {
e.printStackTrace();
return 0;
}
}
@Override
public int update(Teacher teacher) {
String sql = "UPDATE teachers SET teacher_id = ?, name = ?, department = ?, contact = ? WHERE id = ?";
try (Connection conn = DatabaseUtil.getConnection();
PreparedStatement stmt = conn.prepareStatement(sql)) {
stmt.setString(1, teacher.getTeacherId());
stmt.setString(2, teacher.getName());
stmt.setString(3, teacher.getDepartment());
stmt.setString(4, teacher.getContact());
stmt.setInt(5, teacher.getId());
return stmt.executeUpdate();
} catch (SQLException e) {
e.printStackTrace();
return 0;
}
}
@Override
public Teacher findById(int id) {
String sql = "SELECT * FROM teachers WHERE id = ?";
try (Connection conn = DatabaseUtil.getConnection();
PreparedStatement stmt = conn.prepareStatement(sql)) {
stmt.setInt(1, id);
ResultSet rs = stmt.executeQuery();
if (rs.next()) {
return mapResultSetToTeacher(rs);
}
} catch (SQLException e) {
e.printStackTrace();
}
return null;
}
@Override
public List<Teacher> findAll() {
List<Teacher> teachers = new ArrayList<>();
String sql = "SELECT * FROM teachers";
try (Connection conn = DatabaseUtil.getConnection();
Statement stmt = conn.createStatement();
ResultSet rs = stmt.executeQuery(sql)) {
while (rs.next()) {
teachers.add(mapResultSetToTeacher(rs));
}
} catch (SQLException e) {
e.printStackTrace();
}
return teachers;
}
@Override
public Teacher findByTeacherId(String teacherId) {
String sql = "SELECT * FROM teachers WHERE teacher_id = ?";
try (Connection conn = DatabaseUtil.getConnection();
PreparedStatement stmt = conn.prepareStatement(sql)) {
stmt.setString(1, teacherId);
ResultSet rs = stmt.executeQuery();
if (rs.next()) {
return mapResultSetToTeacher(rs);
}
} catch (SQLException e) {
e.printStackTrace();
}
return null;
}
@Override
public List<Teacher> findByDepartment(String department) {
List<Teacher> teachers = new ArrayList<>();
String sql = "SELECT * FROM teachers WHERE department = ?";
try (Connection conn = DatabaseUtil.getConnection();
PreparedStatement stmt = conn.prepareStatement(sql)) {
stmt.setString(1, department);
ResultSet rs = stmt.executeQuery();
while (rs.next()) {
teachers.add(mapResultSetToTeacher(rs));
}
} catch (SQLException e) {
e.printStackTrace();
}
return teachers;
}
@Override
public List<Teacher> findByNameLike(String name) {
List<Teacher> teachers = new ArrayList<>();
String sql = "SELECT * FROM teachers WHERE name LIKE ?";
try (Connection conn = DatabaseUtil.getConnection();
PreparedStatement stmt = conn.prepareStatement(sql)) {
stmt.setString(1, "%" + name + "%");
ResultSet rs = stmt.executeQuery();
while (rs.next()) {
teachers.add(mapResultSetToTeacher(rs));
}
} catch (SQLException e) {
e.printStackTrace();
}
return teachers;
}
/**
* 将ResultSet映射为Teacher对象
*/
private Teacher mapResultSetToTeacher(ResultSet rs) throws SQLException {
Teacher teacher = new Teacher();
teacher.setId(rs.getInt("id"));
teacher.setTeacherId(rs.getString("teacher_id"));
teacher.setName(rs.getString("name"));
teacher.setDepartment(rs.getString("department"));
teacher.setContact(rs.getString("contact"));
return teacher;
}
}

94
src/gui/LoginFrame.java Normal file
View File

@ -0,0 +1,94 @@
package gui;
import javax.swing.*;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import util.DatabaseUtil;
public class LoginFrame extends JFrame {
private JComboBox<String> userTypeComboBox;
private JTextField idField;
private JPasswordField passwordField;
private JButton loginButton;
public LoginFrame() {
setTitle("登录");
setSize(300, 200);
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
setLocationRelativeTo(null);
JPanel panel = new JPanel();
panel.setLayout(new GridLayout(4, 2));
panel.add(new JLabel("用户类型:"));
userTypeComboBox = new JComboBox<>(new String[]{"学生", "教师"});
panel.add(userTypeComboBox);
panel.add(new JLabel("ID:"));
idField = new JTextField();
panel.add(idField);
panel.add(new JLabel("密码:"));
passwordField = new JPasswordField();
panel.add(passwordField);
loginButton = new JButton("登录");
panel.add(loginButton);
loginButton.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
handleLogin();
}
});
add(panel);
}
private void handleLogin() {
String userType = (String) userTypeComboBox.getSelectedItem();
String id = idField.getText();
String password = new String(passwordField.getPassword());
String tableName = "学生".equals(userType) ? "students" : "teachers";
String idColumnName = "学生".equals(userType) ? "student_id" : "teacher_id";
String sql = "SELECT * FROM " + tableName + " WHERE " + idColumnName + " = ? AND password = ?";
try (Connection conn = DatabaseUtil.getConnection();
PreparedStatement stmt = conn.prepareStatement(sql)) {
stmt.setString(1, id);
stmt.setString(2, password);
ResultSet rs = stmt.executeQuery();
if (rs.next()) {
if ("教师".equals(userType)) {
TeacherMainFrame teacherMainFrame = new TeacherMainFrame();
teacherMainFrame.setVisible(true);
} else {
// TODO: 打开学生主界面
JOptionPane.showMessageDialog(this, "学生登录成功!", "提示", JOptionPane.INFORMATION_MESSAGE);
}
dispose();
} else {
JOptionPane.showMessageDialog(this, "无效的ID或密码", "错误", JOptionPane.ERROR_MESSAGE);
}
} catch (SQLException e) {
e.printStackTrace();
JOptionPane.showMessageDialog(this, "数据库错误:" + e.getMessage(), "错误", JOptionPane.ERROR_MESSAGE);
}
}
public static void main(String[] args) {
SwingUtilities.invokeLater(() -> {
LoginFrame loginFrame = new LoginFrame();
loginFrame.setVisible(true);
});
}
}

View File

@ -0,0 +1,165 @@
package gui;
import model.ApprovalStatus;
import model.LeaveRequest;
import service.LeaveRequestService;
import service.ServiceFactory;
import javax.swing.*;
import java.awt.*;
import java.text.SimpleDateFormat;
import java.util.List;
public class RequestDetailDialog extends JDialog {
private final LeaveRequestService leaveRequestService;
private LeaveRequest currentRequest;
public RequestDetailDialog(JFrame parent, String studentName) {
super(parent, "请假详情", true);
this.leaveRequestService = ServiceFactory.getLeaveRequestService();
// 根据学生姓名获取请假信息
List<LeaveRequest> requests = leaveRequestService.getAllLeaveRequests();
this.currentRequest = requests.stream()
.filter(r -> r.getStudent().getName().equals(studentName))
.findFirst()
.orElse(null);
if (currentRequest == null) {
JOptionPane.showMessageDialog(parent, "未找到请假信息!", "错误", JOptionPane.ERROR_MESSAGE);
dispose();
return;
}
setSize(500, 700);
setLocationRelativeTo(parent);
setResizable(false);
initComponents();
}
private void initComponents() {
// 主面板使用GridBagLayout
JPanel mainPanel = new JPanel(new GridBagLayout());
GridBagConstraints gbc = new GridBagConstraints();
gbc.gridwidth = GridBagConstraints.REMAINDER;
gbc.fill = GridBagConstraints.HORIZONTAL;
gbc.insets = new Insets(5, 10, 5, 10);
SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
// 学生基本信息
addInfoField(mainPanel, gbc, "审核进度:", "班主任");
addInfoField(mainPanel, gbc, "学院:", currentRequest.getStudent().getCollege());
addInfoField(mainPanel, gbc, "专业:", currentRequest.getStudent().getMajor());
addInfoField(mainPanel, gbc, "班级:", currentRequest.getStudent().getClassName());
addInfoField(mainPanel, gbc, "姓名:", currentRequest.getStudent().getName());
addInfoField(mainPanel, gbc, "学号:", currentRequest.getStudent().getStudentId());
addInfoField(mainPanel, gbc, "手机号:", currentRequest.getStudent().getPhone());
// 请假信息
addInfoField(mainPanel, gbc, "申请外出时间:", dateFormat.format(currentRequest.getStartTime()));
addInfoField(mainPanel, gbc, "预计返校时间:", dateFormat.format(currentRequest.getEndTime()));
addInfoField(mainPanel, gbc, "时长:", String.format("%.2f", currentRequest.getDuration()));
addInfoField(mainPanel, gbc, "外出地址:", currentRequest.getLocation());
addInfoField(mainPanel, gbc, "外出事由:", currentRequest.getReasonType());
addInfoField(mainPanel, gbc, "详细事由:", currentRequest.getReasonDetail());
addInfoField(mainPanel, gbc, "是否离津:", currentRequest.isLeavingCity() ? "" : "");
addInfoField(mainPanel, gbc, "其他特殊情况:",
currentRequest.getSpecialSituation() == null ? "" : currentRequest.getSpecialSituation());
addInfoField(mainPanel, gbc, "发起时间:", dateFormat.format(currentRequest.getRequestTime()));
// 如果已经审批过显示审批信息
if (currentRequest.getStatus() != ApprovalStatus.PENDING) {
addInfoField(mainPanel, gbc, "审批状态:", currentRequest.getStatus().getDescription());
if (currentRequest.getApprovalComment() != null) {
addInfoField(mainPanel, gbc, "审批意见:", currentRequest.getApprovalComment());
}
if (currentRequest.getApprovalTime() != null) {
addInfoField(mainPanel, gbc, "审批时间:", dateFormat.format(currentRequest.getApprovalTime()));
}
}
// 审批按钮
JPanel buttonPanel = new JPanel(new FlowLayout(FlowLayout.CENTER, 20, 10));
JButton approveButton = new JButton("通过");
JButton rejectButton = new JButton("驳回");
// 如果已经审批过禁用按钮
if (currentRequest.getStatus() != ApprovalStatus.PENDING) {
approveButton.setEnabled(false);
rejectButton.setEnabled(false);
}
approveButton.setPreferredSize(new Dimension(100, 30));
rejectButton.setPreferredSize(new Dimension(100, 30));
// 设置按钮颜色
approveButton.setBackground(new Color(39, 174, 96));
approveButton.setForeground(Color.WHITE);
rejectButton.setBackground(new Color(231, 76, 60));
rejectButton.setForeground(Color.WHITE);
buttonPanel.add(approveButton);
buttonPanel.add(rejectButton);
// 添加按钮面板
gbc.insets = new Insets(20, 10, 10, 10);
mainPanel.add(buttonPanel, gbc);
// 添加事件监听
approveButton.addActionListener(e -> {
int result = JOptionPane.showConfirmDialog(
this,
"确定通过该请假申请吗?",
"确认",
JOptionPane.YES_NO_OPTION
);
if (result == JOptionPane.YES_OPTION) {
leaveRequestService.approveLeaveRequest(
currentRequest.getId(),
ApprovalStatus.APPROVED,
"已通过"
);
dispose();
}
});
rejectButton.addActionListener(e -> {
String reason = JOptionPane.showInputDialog(
this,
"请输入驳回原因:",
"驳回原因",
JOptionPane.QUESTION_MESSAGE
);
if (reason != null && !reason.trim().isEmpty()) {
leaveRequestService.approveLeaveRequest(
currentRequest.getId(),
ApprovalStatus.REJECTED,
reason
);
dispose();
}
});
// 添加滚动面板
JScrollPane scrollPane = new JScrollPane(mainPanel);
scrollPane.setBorder(null);
add(scrollPane);
}
private void addInfoField(JPanel panel, GridBagConstraints gbc, String label, String value) {
JPanel fieldPanel = new JPanel(new BorderLayout(10, 0));
JLabel labelComponent = new JLabel(label);
labelComponent.setFont(new Font("微软雅黑", Font.BOLD, 12));
JLabel valueComponent = new JLabel(value);
valueComponent.setFont(new Font("微软雅黑", Font.PLAIN, 12));
fieldPanel.add(labelComponent, BorderLayout.WEST);
fieldPanel.add(valueComponent, BorderLayout.CENTER);
panel.add(fieldPanel, gbc);
}
}

View File

@ -0,0 +1,189 @@
package gui;
import model.ApprovalStatus;
import model.LeaveRequest;
import service.LeaveRequestService;
import service.ServiceFactory;
import javax.swing.*;
import javax.swing.table.DefaultTableModel;
import javax.swing.table.TableColumnModel;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.text.SimpleDateFormat;
import java.util.List;
public class TeacherMainFrame extends JFrame {
private final LeaveRequestService leaveRequestService;
private JTable requestTable;
private DefaultTableModel tableModel;
private JTextField searchField;
private JComboBox<String> statusFilter;
private int currentPage = 1;
private static final int PAGE_SIZE = 10;
public TeacherMainFrame() {
leaveRequestService = ServiceFactory.getLeaveRequestService();
initComponents();
loadLeaveRequests();
}
private void initComponents() {
setTitle("平安校园 - 日常出校申请");
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
setSize(400, 600);
setLocationRelativeTo(null);
// 顶部面板
JPanel topPanel = new JPanel(new BorderLayout());
JPanel searchPanel = new JPanel(new FlowLayout(FlowLayout.LEFT));
// 标题
JLabel titleLabel = new JLabel("日常出校申请", SwingConstants.CENTER);
titleLabel.setFont(new Font("微软雅黑", Font.PLAIN, 18));
topPanel.add(titleLabel, BorderLayout.CENTER);
// 状态过滤器
JPanel filterPanel = new JPanel(new FlowLayout(FlowLayout.CENTER));
String[] statuses = {"全部", "待审批", "已通过", "已驳回"};
statusFilter = new JComboBox<>(statuses);
statusFilter.addActionListener(e -> loadLeaveRequests());
filterPanel.add(statusFilter);
// 搜索框
searchField = new JTextField(15);
JButton searchButton = new JButton("筛选");
searchPanel.add(new JLabel("请输入学号或姓名:"));
searchPanel.add(searchField);
searchPanel.add(searchButton);
topPanel.add(searchPanel, BorderLayout.NORTH);
topPanel.add(filterPanel, BorderLayout.SOUTH);
// 表格
String[] columnNames = {"姓名", "班级", "状态", "申请时间", "外出事由"};
tableModel = new DefaultTableModel(columnNames, 0) {
@Override
public boolean isCellEditable(int row, int column) {
return false;
}
};
requestTable = new JTable(tableModel);
requestTable.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
// 设置表格样式
requestTable.setRowHeight(30);
requestTable.getTableHeader().setFont(new Font("微软雅黑", Font.BOLD, 12));
requestTable.setFont(new Font("微软雅黑", Font.PLAIN, 12));
// 设置列宽
TableColumnModel columnModel = requestTable.getColumnModel();
columnModel.getColumn(0).setPreferredWidth(50); // 姓名
columnModel.getColumn(1).setPreferredWidth(90); // 班级
columnModel.getColumn(2).setPreferredWidth(50); // 状态
columnModel.getColumn(3).setPreferredWidth(100); // 申请时间
columnModel.getColumn(4).setPreferredWidth(60); // 外出事由
// 分页控制
JPanel pagePanel = new JPanel(new FlowLayout(FlowLayout.CENTER));
JButton prevButton = new JButton("上一页");
JButton nextButton = new JButton("下一页");
JLabel pageLabel = new JLabel("1/1");
pagePanel.add(prevButton);
pagePanel.add(pageLabel);
pagePanel.add(nextButton);
// 添加到主面板
JPanel mainPanel = new JPanel(new BorderLayout());
mainPanel.add(topPanel, BorderLayout.NORTH);
mainPanel.add(new JScrollPane(requestTable), BorderLayout.CENTER);
mainPanel.add(pagePanel, BorderLayout.SOUTH);
// 添加事件监听
searchButton.addActionListener(e -> loadLeaveRequests());
requestTable.getSelectionModel().addListSelectionListener(e -> {
if (!e.getValueIsAdjusting() && requestTable.getSelectedRow() != -1) {
showRequestDetails(requestTable.getSelectedRow());
}
});
prevButton.addActionListener(e -> {
if (currentPage > 1) {
currentPage--;
loadLeaveRequests();
}
});
nextButton.addActionListener(e -> {
currentPage++;
loadLeaveRequests();
});
add(mainPanel);
}
private void loadLeaveRequests() {
tableModel.setRowCount(0);
String searchText = searchField.getText().trim();
String statusText = (String) statusFilter.getSelectedItem();
List<LeaveRequest> requests;
if ("全部".equals(statusText)) {
requests = leaveRequestService.getAllLeaveRequests();
} else {
ApprovalStatus status = null;
switch (statusText) {
case "待审批":
status = ApprovalStatus.PENDING;
break;
case "已通过":
status = ApprovalStatus.APPROVED;
break;
case "已驳回":
status = ApprovalStatus.REJECTED;
break;
}
requests = leaveRequestService.getLeaveRequestsByStatus(status);
}
// 过滤搜索结果
if (!searchText.isEmpty()) {
requests.removeIf(request ->
!request.getStudent().getName().contains(searchText) &&
!request.getStudent().getStudentId().contains(searchText));
}
// 添加到表格
for (LeaveRequest request : requests) {
Object[] row = {
request.getStudent().getName(),
request.getStudent().getClassName(),
request.getStatus().getDescription(),
new SimpleDateFormat("MM-dd HH:mm").format(request.getRequestTime()),
request.getReasonType()
};
tableModel.addRow(row);
}
}
private void showRequestDetails(int row) {
// 创建详情对话框
RequestDetailDialog dialog = new RequestDetailDialog(this, tableModel.getValueAt(row, 0).toString());
dialog.setVisible(true);
}
public static void main(String[] args) {
try {
UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
} catch (Exception e) {
e.printStackTrace();
}
SwingUtilities.invokeLater(() -> {
TeacherMainFrame frame = new TeacherMainFrame();
frame.setVisible(true);
});
}
}

View File

@ -0,0 +1,20 @@
package model;
/**
* 请假审批状态枚举类
*/
public enum ApprovalStatus {
PENDING("待审批"), // 等待审批
APPROVED("已批准"), // 已经批准
REJECTED("已驳回"); // 已经驳回
private final String description; // 状态描述
ApprovalStatus(String description) {
this.description = description;
}
public String getDescription() {
return description;
}
}

151
src/model/LeaveRequest.java Normal file
View File

@ -0,0 +1,151 @@
package model;
import java.util.Date;
/**
* 请假条实体类
*/
public class LeaveRequest {
private int id; // 数据库主键ID
private Student student; // 学生信息
private Date startTime; // 开始时间
private Date endTime; // 结束时间
private double duration; // 时长
private String location; // 外出地址
private String reasonType; // 外出事由类型
private String reasonDetail; // 详细事由
private boolean isLeavingCity; // 是否离津
private String specialSituation; // 其他特殊情况
private ApprovalStatus status; // 审批状态
private Teacher approver; // 审批人
private String approvalComment; // 审批意见
private Date requestTime; // 申请时间
private Date approvalTime; // 审批时间
// Constructors
public LeaveRequest() {
this.status = ApprovalStatus.PENDING;
this.requestTime = new Date();
}
// Getters and Setters
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public Student getStudent() {
return student;
}
public void setStudent(Student student) {
this.student = student;
}
public Date getStartTime() {
return startTime;
}
public void setStartTime(Date startTime) {
this.startTime = startTime;
}
public Date getEndTime() {
return endTime;
}
public void setEndTime(Date endTime) {
this.endTime = endTime;
}
public double getDuration() {
return duration;
}
public void setDuration(double duration) {
this.duration = duration;
}
public String getLocation() {
return location;
}
public void setLocation(String location) {
this.location = location;
}
public String getReasonType() {
return reasonType;
}
public void setReasonType(String reasonType) {
this.reasonType = reasonType;
}
public String getReasonDetail() {
return reasonDetail;
}
public void setReasonDetail(String reasonDetail) {
this.reasonDetail = reasonDetail;
}
public boolean isLeavingCity() {
return isLeavingCity;
}
public void setLeavingCity(boolean leavingCity) {
isLeavingCity = leavingCity;
}
public String getSpecialSituation() {
return specialSituation;
}
public void setSpecialSituation(String specialSituation) {
this.specialSituation = specialSituation;
}
public ApprovalStatus getStatus() {
return status;
}
public void setStatus(ApprovalStatus status) {
this.status = status;
}
public Teacher getApprover() {
return approver;
}
public void setApprover(Teacher approver) {
this.approver = approver;
}
public String getApprovalComment() {
return approvalComment;
}
public void setApprovalComment(String approvalComment) {
this.approvalComment = approvalComment;
}
public Date getRequestTime() {
return requestTime;
}
public void setRequestTime(Date requestTime) {
this.requestTime = requestTime;
}
public Date getApprovalTime() {
return approvalTime;
}
public void setApprovalTime(Date approvalTime) {
this.approvalTime = approvalTime;
}
}

93
src/model/Student.java Normal file
View File

@ -0,0 +1,93 @@
package model;
/**
* 学生实体类
*/
public class Student {
private int id; // 数据库主键ID
private String studentId; // 学号
private String name; // 学生姓名
private String className; // 班级
private String contact; // 联系方式
private String college; // 学院
private String major; // 专业
private boolean isGraduating; // 是否毕业班
// Constructors
public Student() {}
public Student(String studentId, String name, String className, String contact, String college, String major, boolean isGraduating) {
this.studentId = studentId;
this.name = name;
this.className = className;
this.contact = contact;
this.college = college;
this.major = major;
this.isGraduating = isGraduating;
}
// Getters and Setters
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getStudentId() {
return studentId;
}
public void setStudentId(String studentId) {
this.studentId = studentId;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getClassName() {
return className;
}
public void setClassName(String className) {
this.className = className;
}
public String getContact() {
return contact;
}
public void setContact(String contact) {
this.contact = contact;
}
public String getCollege() {
return college;
}
public void setCollege(String college) {
this.college = college;
}
public String getMajor() {
return major;
}
public void setMajor(String major) {
this.major = major;
}
public boolean isGraduating() {
return isGraduating;
}
public void setGraduating(boolean graduating) {
isGraduating = graduating;
}
}

63
src/model/Teacher.java Normal file
View File

@ -0,0 +1,63 @@
package model;
/**
* 教师实体类
*/
public class Teacher {
private int id; // 数据库主键ID
private String teacherId; // 教师工号
private String name; // 教师姓名
private String department; // 所属部门
private String contact; // 联系方式
// Constructors
public Teacher() {}
public Teacher(String teacherId, String name, String department, String contact) {
this.teacherId = teacherId;
this.name = name;
this.department = department;
this.contact = contact;
}
// Getters and Setters
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getTeacherId() {
return teacherId;
}
public void setTeacherId(String teacherId) {
this.teacherId = teacherId;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getDepartment() {
return department;
}
public void setDepartment(String department) {
this.department = department;
}
public String getContact() {
return contact;
}
public void setContact(String contact) {
this.contact = contact;
}
}

View File

@ -0,0 +1,116 @@
package service;
import dao.DAOFactory;
import dao.LeaveRequestDAO;
import model.LeaveRequest;
import model.Student;
import model.ApprovalStatus;
import java.util.Date;
import java.util.List;
/**
* 请假申请服务类
*/
public class LeaveRequestService {
private final LeaveRequestDAO leaveRequestDAO = DAOFactory.getLeaveRequestDAO();
private final StudentService studentService = new StudentService();
/**
* 提交请假申请
* @param request 请假申请信息
* @return 是否提交成功
*/
public boolean submitLeaveRequest(LeaveRequest request) {
// 检查学生是否存在
Student student = studentService.getStudentById(request.getStudent().getId());
if (student == null) {
return false;
}
// 检查请假时间是否合理
if (!isValidLeaveTime(request.getStartTime(), request.getEndTime())) {
return false;
}
// 设置初始状态为待审批
request.setStatus(ApprovalStatus.PENDING);
request.setRequestTime(new Date());
return leaveRequestDAO.insert(request) > 0;
}
/**
* 审批请假申请
* @param requestId 请假申请ID
* @param status 审批状态
* @param comment 审批意见
* @return 是否审批成功
*/
public boolean approveLeaveRequest(int requestId, ApprovalStatus status, String comment) {
// 检查请假申请是否存在
LeaveRequest request = leaveRequestDAO.findById(requestId);
if (request == null) {
return false;
}
// 检查是否可以审批
if (request.getStatus() != ApprovalStatus.PENDING) {
return false;
}
return leaveRequestDAO.updateStatus(requestId, status, comment) > 0;
}
/**
* 获取学生的请假记录
* @param studentId 学生ID
* @return 请假记录列表
*/
public List<LeaveRequest> getStudentLeaveRequests(int studentId) {
return leaveRequestDAO.findByStudentId(studentId);
}
/**
* 获取指定状态的请假申请
* @param status 审批状态
* @return 请假申请列表
*/
public List<LeaveRequest> getLeaveRequestsByStatus(ApprovalStatus status) {
return leaveRequestDAO.findByStatus(status);
}
/**
* 获取所有请假申请
* @return 请假申请列表
*/
public List<LeaveRequest> getAllLeaveRequests() {
return leaveRequestDAO.findAll();
}
/**
* 检查请假时间是否合理
* @param startTime 开始时间
* @param endTime 结束时间
* @return 是否合理
*/
private boolean isValidLeaveTime(Date startTime, Date endTime) {
// 开始时间不能为空
if (startTime == null || endTime == null) {
return false;
}
// 结束时间必须在开始时间之后
if (endTime.before(startTime)) {
return false;
}
// 开始时间不能是过去的时间
Date now = new Date();
if (startTime.before(now)) {
return false;
}
return true;
}
}

View File

@ -0,0 +1,34 @@
package service;
/**
* Service工厂类用于获取各种Service的实例
*/
public class ServiceFactory {
private static final StudentService studentService = new StudentService();
private static final TeacherService teacherService = new TeacherService();
private static final LeaveRequestService leaveRequestService = new LeaveRequestService();
/**
* 获取StudentService实例
* @return StudentService实例
*/
public static StudentService getStudentService() {
return studentService;
}
/**
* 获取TeacherService实例
* @return TeacherService实例
*/
public static TeacherService getTeacherService() {
return teacherService;
}
/**
* 获取LeaveRequestService实例
* @return LeaveRequestService实例
*/
public static LeaveRequestService getLeaveRequestService() {
return leaveRequestService;
}
}

View File

@ -0,0 +1,98 @@
package service;
import dao.DAOFactory;
import dao.StudentDAO;
import model.Student;
import java.util.List;
/**
* 学生信息服务类
*/
public class StudentService {
private final StudentDAO studentDAO = DAOFactory.getStudentDAO();
/**
* 添加学生
* @param student 学生信息
* @return 是否添加成功
*/
public boolean addStudent(Student student) {
// 检查学号是否已存在
if (studentDAO.findByStudentId(student.getStudentId()) != null) {
return false;
}
return studentDAO.insert(student) > 0;
}
/**
* 更新学生信息
* @param student 学生信息
* @return 是否更新成功
*/
public boolean updateStudent(Student student) {
// 检查是否存在
Student existingStudent = studentDAO.findById(student.getId());
if (existingStudent == null) {
return false;
}
// 检查学号是否被其他学生使用
Student studentWithSameId = studentDAO.findByStudentId(student.getStudentId());
if (studentWithSameId != null && studentWithSameId.getId() != student.getId()) {
return false;
}
return studentDAO.update(student) > 0;
}
/**
* 删除学生
* @param id 学生ID
* @return 是否删除成功
*/
public boolean deleteStudent(int id) {
return studentDAO.deleteById(id) > 0;
}
/**
* 根据ID查询学生
* @param id 学生ID
* @return 学生信息
*/
public Student getStudentById(int id) {
return studentDAO.findById(id);
}
/**
* 根据学号查询学生
* @param studentId 学号
* @return 学生信息
*/
public Student getStudentByStudentId(String studentId) {
return studentDAO.findByStudentId(studentId);
}
/**
* 查询所有学生
* @return 学生列表
*/
public List<Student> getAllStudents() {
return studentDAO.findAll();
}
/**
* 根据班级查询学生
* @param className 班级名称
* @return 学生列表
*/
public List<Student> getStudentsByClass(String className) {
return studentDAO.findByClassName(className);
}
/**
* 根据姓名模糊查询学生
* @param name 学生姓名
* @return 学生列表
*/
public List<Student> searchStudentsByName(String name) {
return studentDAO.findByNameLike(name);
}
}

View File

@ -0,0 +1,98 @@
package service;
import dao.DAOFactory;
import dao.TeacherDAO;
import model.Teacher;
import java.util.List;
/**
* 教师信息服务类
*/
public class TeacherService {
private final TeacherDAO teacherDAO = DAOFactory.getTeacherDAO();
/**
* 添加教师
* @param teacher 教师信息
* @return 是否添加成功
*/
public boolean addTeacher(Teacher teacher) {
// 检查工号是否已存在
if (teacherDAO.findByTeacherId(teacher.getTeacherId()) != null) {
return false;
}
return teacherDAO.insert(teacher) > 0;
}
/**
* 更新教师信息
* @param teacher 教师信息
* @return 是否更新成功
*/
public boolean updateTeacher(Teacher teacher) {
// 检查是否存在
Teacher existingTeacher = teacherDAO.findById(teacher.getId());
if (existingTeacher == null) {
return false;
}
// 检查工号是否被其他教师使用
Teacher teacherWithSameId = teacherDAO.findByTeacherId(teacher.getTeacherId());
if (teacherWithSameId != null && teacherWithSameId.getId() != teacher.getId()) {
return false;
}
return teacherDAO.update(teacher) > 0;
}
/**
* 删除教师
* @param id 教师ID
* @return 是否删除成功
*/
public boolean deleteTeacher(int id) {
return teacherDAO.deleteById(id) > 0;
}
/**
* 根据ID查询教师
* @param id 教师ID
* @return 教师信息
*/
public Teacher getTeacherById(int id) {
return teacherDAO.findById(id);
}
/**
* 根据工号查询教师
* @param teacherId 工号
* @return 教师信息
*/
public Teacher getTeacherByTeacherId(String teacherId) {
return teacherDAO.findByTeacherId(teacherId);
}
/**
* 查询所有教师
* @return 教师列表
*/
public List<Teacher> getAllTeachers() {
return teacherDAO.findAll();
}
/**
* 根据部门查询教师
* @param department 部门名称
* @return 教师列表
*/
public List<Teacher> getTeachersByDepartment(String department) {
return teacherDAO.findByDepartment(department);
}
/**
* 根据姓名模糊查询教师
* @param name 教师姓名
* @return 教师列表
*/
public List<Teacher> searchTeachersByName(String name) {
return teacherDAO.findByNameLike(name);
}
}

76
src/sql/init.sql Normal file
View File

@ -0,0 +1,76 @@
-- 创建数据库
CREATE DATABASE IF NOT EXISTS absence_manager DEFAULT CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci;
USE absence_manager;
-- 创建学生表
CREATE TABLE IF NOT EXISTS students (
id INT PRIMARY KEY AUTO_INCREMENT,
student_id VARCHAR(20) UNIQUE NOT NULL, -- 学号
name VARCHAR(50) NOT NULL, -- 姓名
class_name VARCHAR(50) NOT NULL, -- 班级
contact VARCHAR(20), -- 联系方式
college VARCHAR(50) NOT NULL, -- 学院
major VARCHAR(50) NOT NULL, -- 专业
is_graduating BOOLEAN DEFAULT FALSE, -- 是否毕业班
password VARCHAR(50) NOT NULL, -- 密码
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COMMENT='学生信息表';
-- 创建教师表
CREATE TABLE IF NOT EXISTS teachers (
id INT PRIMARY KEY AUTO_INCREMENT,
teacher_id VARCHAR(20) UNIQUE NOT NULL, -- 工号
name VARCHAR(50) NOT NULL, -- 姓名
department VARCHAR(50) NOT NULL, -- 部门
contact VARCHAR(20), -- 联系方式
password VARCHAR(50) NOT NULL, -- 密码
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COMMENT='教师信息表';
-- 创建请假申请表
CREATE TABLE IF NOT EXISTS leave_requests (
id INT PRIMARY KEY AUTO_INCREMENT,
student_id INT NOT NULL, -- 关联学生ID
start_time DATETIME NOT NULL, -- 开始时间
end_time DATETIME NOT NULL, -- 结束时间
duration DECIMAL(5,2) NOT NULL, -- 时长
location VARCHAR(100) NOT NULL, -- 外出地址
reason_type VARCHAR(50) NOT NULL, -- 外出事由类型
reason_detail TEXT, -- 详细事由
is_leaving_city BOOLEAN DEFAULT FALSE, -- 是否离津
special_situation TEXT, -- 其他特殊情况
status VARCHAR(20) NOT NULL DEFAULT 'PENDING', -- 审批状态
approver_id INT, -- 审批人ID
approval_comment TEXT, -- 审批意见
request_time TIMESTAMP DEFAULT CURRENT_TIMESTAMP, -- 申请时间
approval_time TIMESTAMP NULL, -- 审批时间
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
FOREIGN KEY (student_id) REFERENCES students(id),
FOREIGN KEY (approver_id) REFERENCES teachers(id)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COMMENT='请假申请表';
-- 插入示例数据
INSERT INTO students (student_id, name, class_name, contact, college, major, is_graduating, password) VALUES
('2023208145', '李同学', '云计算G23-1', '15842087237', '信息工程学院', '云计算技术应用', false, '123456'),
('2023208146', '张同学', '云计算G23-1', '15842087238', '信息工程学院', '云计算技术应用', false, '123456');
INSERT INTO teachers (teacher_id, name, department, contact, password) VALUES
('2023001', '王老师', '信息工程学院', '13912345678', '123456'),
('2023002', '李老师', '信息工程学院', '13912345679', '123456');
-- 插入请假申请示例数据
INSERT INTO leave_requests (student_id, start_time, end_time, duration, location, reason_type, reason_detail, is_leaving_city, status, approver_id, approval_comment, request_time) VALUES
(1, '2024-01-15 08:00:00', '2024-01-15 17:00:00', 9.00, '天津市河西区图书馆', '学习', '去图书馆学习准备考试', false, 'APPROVED', 1, '同意', '2024-01-14 10:00:00'),
(2, '2024-01-16 13:00:00', '2024-01-16 17:30:00', 4.50, '天津市南开医院', '就医', '牙科复诊', false, 'APPROVED', 1, '注意安全', '2024-01-15 09:30:00'),
(1, '2024-01-17 09:00:00', '2024-01-17 12:00:00', 3.00, '天津市档案馆', '办事', '办理个人档案', false, 'PENDING', null, null, '2024-01-16 16:20:00'),
(2, '2024-01-18 14:00:00', '2024-01-18 18:00:00', 4.00, '和平区文化中心', '活动', '参加志愿者活动', false, 'REJECTED', 2, '活动时间与课程冲突', '2024-01-17 11:15:00'),
(1, '2024-01-19 10:00:00', '2024-01-19 16:00:00', 6.00, '天津站', '返乡', '购买返乡车票', true, 'APPROVED', 2, '请注意防疫', '2024-01-18 14:40:00'),
(2, '2024-01-20 09:30:00', '2024-01-20 11:30:00', 2.00, '河西区人才市场', '求职', '参加招聘会', false, 'PENDING', null, null, '2024-01-19 17:00:00'),
(1, '2024-01-21 13:00:00', '2024-01-21 17:00:00', 4.00, '天津市第一中心医院', '就医', '例行体检', false, 'APPROVED', 1, '准假', '2024-01-20 10:25:00'),
(2, '2024-01-22 08:00:00', '2024-01-22 18:00:00', 10.00, '滨海新区图书馆', '实习', '企业实地考察', false, 'PENDING', null, null, '2024-01-21 15:30:00'),
(1, '2024-01-23 14:00:00', '2024-01-23 16:00:00', 2.00, '南开区政务中心', '办事', '办理身份证', false, 'APPROVED', 2, '同意', '2024-01-22 09:45:00'),
(2, '2024-01-24 09:00:00', '2024-01-24 18:00:00', 9.00, '天津市人民医院', '就医', '陪同父亲做检查', false, 'PENDING', null, null, '2024-01-23 16:50:00');

View File

@ -0,0 +1,46 @@
package util;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.SQLException;
/**
* 数据库工具类
*/
public class DatabaseUtil {
private static final String URL = "jdbc:mysql://localhost:3306/absence_manager?useSSL=false&serverTimezone=UTC&characterEncoding=UTF-8";
private static final String USERNAME = "root";
private static final String PASSWORD = "root";
static {
try {
// 加载MySQL驱动
Class.forName("com.mysql.cj.jdbc.Driver");
} catch (ClassNotFoundException e) {
e.printStackTrace();
}
}
/**
* 获取数据库连接
* @return 数据库连接对象
* @throws SQLException SQL异常
*/
public static Connection getConnection() throws SQLException {
return DriverManager.getConnection(URL, USERNAME, PASSWORD);
}
/**
* 关闭数据库连接
* @param conn 要关闭的连接对象
*/
public static void closeConnection(Connection conn) {
if (conn != null) {
try {
conn.close();
} catch (SQLException e) {
e.printStackTrace();
}
}
}
}