1. 项目背景与需求分析
在高校日常管理中,学生请假管理一直是个让人头疼的问题。西安工商学院作为一所拥有上万名学生的综合性院校,传统的纸质请假条和Excel表格管理方式已经明显跟不上需求。教务处的王老师跟我吐槽说,光是整理上周的请假记录就花了整整两天时间,还经常出现信息遗漏、审批流程混乱的情况。
这个基于ThinkPHP和Laravel框架开发的请假管理系统,正是为了解决这些痛点而生。系统需要处理的核心场景包括:
- 学生在线提交请假申请(包括事假、病假、公假等类型)
- 辅导员/班主任多级审批流程
- 与学校现有教务系统的数据对接
- 请假记录的统计分析与报表生成
需要模型API调用? 免费领10W Token,多模型网关一键接入 Claude、DeepSeek 等主流模型。
2. 技术选型对比
2.1 为什么选择双框架架构
这个项目最特别的地方在于同时使用了ThinkPHP和Laravel两个PHP框架。刚开始接到需求时我也很困惑,但经过分析发现这样的架构有其独特优势:
ThinkPHP(6.0版本)的优势:
- 中文文档完善,适合快速开发管理后台
- 内置的验证器、中间件等组件开箱即用
- 对国内服务器环境兼容性更好
Laravel(8.x版本)的优势:
- 更适合构建RESTful API接口
- Eloquent ORM在复杂查询时更灵活
- 队列任务处理更完善(用于异步处理审批通知)
实际部署方案:ThinkPHP处理后台管理功能(占70%代码量),Laravel专注API服务(占30%代码量),通过JWT进行鉴权通信。
2.2 数据库设计要点
考虑到学校每学期约3万条请假记录的增长量,我们采用了分表策略:
sql复制CREATE TABLE `leave_2023_1` (
`id` bigint(20) UNSIGNED NOT NULL COMMENT '雪花ID',
`student_id` varchar(20) NOT NULL COMMENT '学号',
`type` tinyint(4) NOT NULL DEFAULT 1 COMMENT '1病假 2事假 3公假',
`start_time` datetime NOT NULL,
`end_time` datetime NOT NULL,
`status` tinyint(4) NOT NULL DEFAULT 0 COMMENT '0待审核 1通过 2拒绝',
`attachments` json DEFAULT NULL COMMENT '电子证明',
`created_at` timestamp NULL DEFAULT NULL,
`updated_at` timestamp NULL DEFAULT NULL
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;
3. 核心功能实现细节
3.1 多级审批工作流
系统设计了灵活的审批流程配置:
- 3天以内请假:班主任审批
- 3-7天请假:班主任→辅导员两级审批
- 7天以上请假:班主任→辅导员→院领导三级审批
在Laravel中采用状态机模式实现:
php复制class LeaveApplication implements ShouldQueue
{
public function handle(Leave $leave)
{
switch ($leave->days) {
case $leave->days <= 3:
$leave->approver_id = $leave->class_teacher_id;
break;
case $leave->days <=7:
$leave->approver_id = $leave->counselor_id;
$leave->next_approver = $leave->department_head_id;
break;
default:
// 更复杂的审批链
}
$leave->save();
}
}
3.2 微信通知集成
考虑到师生使用习惯,我们放弃了短信通知方案,改用企业微信API:
php复制// ThinkPHP控制器中的通知方法
public function notify($openid, $content)
{
$corpSecret = config('wechat.corp_secret');
$wx = new \think\wechat\Work($corpSecret);
$res = $wx->message->send([
'touser' => $openid,
'msgtype' => 'text',
'agentid' => config('wechat.agentid'),
'text' => ['content' => $content],
'safe' => 0
]);
if ($res['errcode'] != 0) {
Log::error('微信通知失败:'.$res['errmsg']);
}
}
4. 踩坑实录与优化方案
4.1 性能优化实践
在压力测试阶段发现,当并发量超过500时,请假提交接口响应时间从200ms飙升到3s。通过XHProf分析发现瓶颈在于:
- 每次提交都同步查询学生课表(验证请假时间冲突)
- 审批日志采用同步写入方式
优化方案:
- 课表查询改用Redis缓存,设置5分钟过期时间
- 日志写入改为Laravel队列处理
优化后性能对比:
| 指标 | 优化前 | 优化后 |
|---|---|---|
| 平均响应时间 | 3200ms | 450ms |
| 最大并发量 | 800 | 2500 |
| CPU占用率 | 85% | 35% |
4.2 数据迁移的坑
系统上线时需要导入近3年的历史请假数据(约8万条),最初使用ThinkPHP的批量插入:
php复制LeaveModel::insertAll($data);
结果内存爆涨到2GB,耗时15分钟。最终改用原生SQL分块处理:
php复制$chunks = array_chunk($data, 500);
foreach ($chunks as $chunk) {
$sql = "INSERT INTO leave_records (...) VALUES ";
$values = [];
foreach ($chunk as $item) {
$values[] = "('{$item['field1']}', ...)";
}
Db::execute($sql.implode(',', $values));
}
处理时间缩短到3分钟,内存占用稳定在200MB以内。
5. 安全防护措施
5.1 防篡改机制
请假审批通过后,系统会自动生成防伪二维码:
php复制// Laravel中的生成逻辑
public function generateQrCode($leaveId)
{
$key = config('app.key');
$hash = hash_hmac('sha256', $leaveId, $key);
return QrCode::format('png')
->size(300)
->generate(route('leave.verify', [
'id' => $leaveId,
'sig' => substr($hash, 0, 16)
]));
}
5.2 敏感操作审计
所有审批操作都记录详细日志:
sql复制CREATE TABLE `audit_logs` (
`id` bigint(20) NOT NULL,
`user_id` int(11) NOT NULL,
`action` varchar(50) NOT NULL COMMENT 'approve/reject/edit',
`ip` varchar(45) NOT NULL,
`user_agent` varchar(255) DEFAULT NULL,
`before_data` json DEFAULT NULL,
`after_data` json DEFAULT NULL,
`created_at` timestamp NULL DEFAULT NULL
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
6. 项目部署方案
6.1 服务器配置建议
根据实际运行情况推荐配置:
- 前端Nginx:2核4G(静态资源分离)
- ThinkPHP后端:4核8G(PHP 7.4 + Swoole)
- Laravel后端:4核8G(PHP 8.0 + Octane)
- MySQL:8核16G(主从架构)
- Redis:2核4G(持久化开启)
6.2 监控方案
使用Prometheus+Grafana搭建监控看板,关键指标包括:
- 请假提交成功率
- 平均审批耗时
- 各时段并发量
- 数据库查询耗时
配置的告警规则示例:
yaml复制- alert: HighRejectionRate
expr: sum(rate(leave_status_total{status="rejected"}[5m])) by (department) / sum(rate(leave_status_total[5m])) by (department) > 0.3
for: 10m
labels:
severity: warning
annotations:
summary: "高拒绝率告警 {{ $labels.department }}"
7. 扩展性设计
系统预留了多个扩展点:
- 与考勤机对接的接口规范
- 电子签名组件接入方案
- 疫情防控特殊请假流程开关
- 数据大屏可视化接口
例如疫情模块的代码结构:
code复制app/
├── Http/
│ ├── Controllers/
│ │ ├── Covid/
│ │ │ ├── VaccineController.php
│ │ │ └── TravelController.php
│ ├── Requests/
│ │ └── CovidLeaveRequest.php
resources/
└── lang/
└── zh-CN/
└── covid.php
这个项目让我深刻体会到,教育行业的管理系统开发不能只考虑技术实现,更要理解学校特有的组织架构和业务流程。比如最初设计的自动审批规则,在实际运行中发现需要为体育特长生、艺术生等特殊群体设置白名单,这些都是在教科书里学不到的经验。
