1. 项目概述
这个考勤管理系统采用前后端分离架构,后端基于SpringBoot框架开发,前端使用Vue.js实现,数据库选用MySQL。整套系统开箱即用,已经实现了员工考勤管理、请假审批、数据统计等核心功能模块。
作为一名参与过多个企业管理系统开发的工程师,我发现这套系统有几个亮点值得关注:首先是完整的权限控制体系,可以区分管理员、部门主管和普通员工角色;其次是考勤数据的可视化展示,通过图表直观呈现部门出勤情况;最后是移动端适配,员工可以通过手机完成打卡操作。
2. 技术架构解析
2.1 后端技术栈
SpringBoot作为后端框架,版本选用2.7.x稳定版。这个版本在性能和功能上都有不错的表现,同时社区支持完善。主要依赖包括:
- Spring Security:处理认证授权
- MyBatis-Plus:简化数据库操作
- Lombok:减少样板代码
- Hutool:提供各种实用工具
数据库设计遵循第三范式,主要表包括:
- 员工表(employee):存储员工基本信息
- 考勤记录表(attendance):记录每日打卡情况
- 请假申请表(leave_application):管理请假流程
- 部门表(department):组织结构信息
2.2 前端技术栈
Vue 3.x配合Element Plus组件库构建管理界面。前端工程采用标准的Vue CLI创建,主要技术特点:
- Axios处理HTTP请求
- Vue Router管理路由
- Vuex/Pinia状态管理
- ECharts实现数据可视化
3. 核心功能实现
3.1 考勤打卡模块
打卡功能需要考虑的几个关键点:
- 定位验证:通过GPS坐标确认打卡位置
- 时间校验:防止提前打卡或补卡
- 异常处理:网络中断等情况下的容错机制
后端接口示例:
java复制@PostMapping("/check-in")
public Result checkIn(@RequestBody CheckInDTO dto) {
// 验证员工身份
Employee employee = employeeService.getById(dto.getEmployeeId());
if(employee == null) {
return Result.error("员工不存在");
}
// 检查是否已打卡
if(attendanceService.hasCheckedInToday(dto.getEmployeeId())) {
return Result.error("今日已打卡");
}
// 保存考勤记录
Attendance record = new Attendance();
record.setEmployeeId(dto.getEmployeeId());
record.setCheckInTime(LocalDateTime.now());
record.setLocation(dto.getLocation());
attendanceService.save(record);
return Result.ok("打卡成功");
}
3.2 请假审批流程
请假审批采用状态机模式设计,主要状态包括:
- 待审批(PENDING)
- 已批准(APPROVED)
- 已拒绝(REJECTED)
- 已取消(CANCELLED)
状态转换规则:
mermaid复制stateDiagram
[*] --> PENDING
PENDING --> APPROVED: 主管审批通过
PENDING --> REJECTED: 主管审批拒绝
PENDING --> CANCELLED: 员工取消申请
3.3 数据统计报表
使用ECharts实现的考勤统计包含:
- 部门出勤率对比图
- 个人月度考勤日历
- 迟到早退趋势分析
关键SQL查询示例:
sql复制SELECT
d.name AS department,
COUNT(DISTINCT e.id) AS total_employees,
SUM(CASE WHEN a.status = 'NORMAL' THEN 1 ELSE 0 END) AS normal_count,
CONCAT(ROUND(SUM(CASE WHEN a.status = 'NORMAL' THEN 1 ELSE 0 END) /
COUNT(DISTINCT e.id) * 100, 2), '%') AS attendance_rate
FROM
department d
LEFT JOIN
employee e ON d.id = e.department_id
LEFT JOIN
attendance a ON e.id = a.employee_id
WHERE
a.record_date BETWEEN :startDate AND :endDate
GROUP BY
d.id
ORDER BY
attendance_rate DESC;
4. 部署指南
4.1 环境准备
需要预先安装:
- JDK 1.8+
- Node.js 14+
- MySQL 5.7+
- Maven 3.6+
4.2 后端部署步骤
- 导入SQL脚本初始化数据库
- 修改application.yml中的数据库配置
- 构建项目:
bash复制mvn clean package
- 运行jar包:
bash复制java -jar attendance-system.jar
4.3 前端部署步骤
- 安装依赖:
bash复制npm install
- 配置API地址:
修改.env文件中的VUE_APP_API_BASE_URL - 构建项目:
bash复制npm run build
- 部署生成的dist目录到Nginx
5. 常见问题解决
5.1 跨域问题
解决方案:
- 后端配置CORS:
java复制@Configuration
public class CorsConfig implements WebMvcConfigurer {
@Override
public void addCorsMappings(CorsRegistry registry) {
registry.addMapping("/**")
.allowedOrigins("*")
.allowedMethods("GET", "POST", "PUT", "DELETE")
.allowCredentials(true)
.maxAge(3600);
}
}
- 前端开发环境配置代理:
javascript复制// vue.config.js
module.exports = {
devServer: {
proxy: {
'/api': {
target: 'http://localhost:8080',
changeOrigin: true,
pathRewrite: {
'^/api': ''
}
}
}
}
}
5.2 时区问题
MySQL时区设置:
sql复制SET GLOBAL time_zone = '+8:00';
SpringBoot配置:
yaml复制spring:
datasource:
url: jdbc:mysql://localhost:3306/attendance?useSSL=false&serverTimezone=Asia/Shanghai
5.3 性能优化建议
- 数据库索引优化:
sql复制ALTER TABLE attendance ADD INDEX idx_employee_date (employee_id, record_date);
- 缓存高频查询:
java复制@Cacheable(value = "employee", key = "#id")
public Employee getById(Long id) {
return employeeMapper.selectById(id);
}
- 前端懒加载:
javascript复制const routes = [
{
path: '/report',
component: () => import('./views/Report.vue')
}
]
6. 扩展开发建议
6.1 集成钉钉/企业微信
实现步骤:
- 申请开发者账号
- 配置OAuth2.0认证
- 同步组织架构
- 对接消息通知
6.2 添加人脸识别打卡
技术方案:
- 使用OpenCV进行人脸检测
- 集成百度AI或Face++的人脸识别API
- 设计活体检测机制
6.3 开发移动端APP
可选技术栈:
- Uni-app:跨平台方案
- Flutter:高性能UI
- React Native:生态丰富
这套系统在实际部署时,我建议先在小范围试用,收集用户反馈后再逐步推广。特别是考勤规则部分,不同企业的要求差异很大,可能需要根据实际情况调整。