feat: 拆分学号/身份证字段 + 考勤教师展示 + 代码优化

- 入住导入模板:学号和身份证号拆为独立字段,前后端对齐
- 排课查询关联教师,考勤归档页展示教师姓名
- 抽查时段增加 IsIn 校验
- 抽取 withPessimisticWriteLock 去重悲观锁查询
- import 增加文件空 buffer 校验
- 测试 mock 补全,适配事务 manager
- MySQL init.sql VALUES() 语法兼容修复
This commit is contained in:
2026-07-20 11:54:01 +08:00
parent 375c7ec60b
commit c7ba2799b9
12 changed files with 772 additions and 365 deletions

View File

@@ -7,6 +7,7 @@ import { AttendanceService } from './attendance.service';
import { AttendanceRecord } from '../entities/attendance-record.entity';
import { AttendanceSession } from '../entities/attendance-session.entity';
import { AttendanceDevice } from '../entities/attendance-device.entity';
import { AttendancePeriodConfig } from '../entities/attendance-period-config.entity';
import { DingAttendanceRaw } from '../entities/ding-attendance-raw.entity';
import { Class } from '../entities/class.entity';
import { Student } from '../entities/student.entity';
@@ -59,6 +60,7 @@ describe('AttendanceService — batchCreate', () => {
{ provide: getRepositoryToken(ClassTeacher), useValue: { findOne: jest.fn() } },
{ provide: getRepositoryToken(AttendanceSession), useValue: {} },
{ provide: getRepositoryToken(AttendanceDevice), useValue: mockAttendanceDeviceRepo },
{ provide: getRepositoryToken(AttendancePeriodConfig), useValue: {} },
{ provide: getDataSourceToken(), useValue: { transaction: jest.fn() } },
],
}).compile();
@@ -140,6 +142,7 @@ describe('AttendanceService — teacher DingTalk class scope', () => {
{} as never,
{} as never,
{} as never,
{} as never,
);
beforeEach(() => {
@@ -216,6 +219,7 @@ describe('AttendanceService — DingTalk raw query', () => {
{} as never,
{} as never,
{} as never,
{} as never,
);
await expect(
@@ -280,6 +284,7 @@ describe('AttendanceService — attendance device display mappings', () => {
{} as never,
attendanceDeviceRepo as never,
{} as never,
{} as never,
);
return { service, qb, attendanceDeviceRepo };
}
@@ -389,6 +394,7 @@ describe('AttendanceService — session serialization', () => {
{} as never,
{} as never,
{ find: jest.fn().mockResolvedValue([]) } as never,
{} as never,
dataSourceMock as never,
);
}