Merge branch 'develop' into working
All checks were successful
Build & Deploy on Dev / build (push) Successful in 1m0s
All checks were successful
Build & Deploy on Dev / build (push) Successful in 1m0s
This commit is contained in:
commit
702eb13782
5 changed files with 180 additions and 4 deletions
|
|
@ -18,6 +18,7 @@ import {
|
|||
CreateProfileAbsentLateBatch,
|
||||
UpdateProfileAbsentLate,
|
||||
} from "../entities/ProfileAbsentLate";
|
||||
import { ProfileAbsentLateHistory } from "../entities/ProfileAbsentLateHistory";
|
||||
import HttpSuccess from "../interfaces/http-success";
|
||||
import HttpStatus from "../interfaces/http-status";
|
||||
import HttpError from "../interfaces/http-error";
|
||||
|
|
@ -32,6 +33,7 @@ import { setLogDataDiff } from "../interfaces/utils";
|
|||
export class ProfileAbsentLateController extends Controller {
|
||||
private profileRepo = AppDataSource.getRepository(Profile);
|
||||
private absentLateRepo = AppDataSource.getRepository(ProfileAbsentLate);
|
||||
private historyRepo = AppDataSource.getRepository(ProfileAbsentLateHistory);
|
||||
|
||||
/**
|
||||
* API ดึงข้อมูลการมาสาย/ขาดราชการของ user
|
||||
|
|
@ -99,8 +101,15 @@ export class ProfileAbsentLateController extends Controller {
|
|||
};
|
||||
|
||||
Object.assign(data, { ...body, ...meta });
|
||||
|
||||
// บันทึก history
|
||||
const history = new ProfileAbsentLateHistory();
|
||||
Object.assign(history, { ...data, id: undefined });
|
||||
|
||||
await this.absentLateRepo.save(data, { data: req });
|
||||
setLogDataDiff(req, { before, after: data });
|
||||
history.profileAbsentLateId = data.id;
|
||||
await this.historyRepo.save(history, { data: req });
|
||||
|
||||
return new HttpSuccess(data.id);
|
||||
}
|
||||
|
|
@ -114,8 +123,9 @@ export class ProfileAbsentLateController extends Controller {
|
|||
@Request() req: RequestWithUser,
|
||||
@Body() body: CreateProfileAbsentLateBatch,
|
||||
) {
|
||||
// กรณีไม่มีข้อมูลส่งมา (วันที่ไม่มีคนขาด/มาสาย)
|
||||
if (!body.records || body.records.length === 0) {
|
||||
throw new HttpError(HttpStatus.BAD_REQUEST, "กรุณาระบุข้อมูลอย่างน้อย 1 รายการ");
|
||||
return new HttpSuccess({ count: 0, ids: [] });
|
||||
}
|
||||
|
||||
const profileIds = [...new Set(body.records.map((r) => r.profileId))];
|
||||
|
|
@ -126,8 +136,9 @@ export class ProfileAbsentLateController extends Controller {
|
|||
const foundProfileIds = new Set(profiles.map((p) => p.id));
|
||||
const validRecords = body.records.filter((r) => foundProfileIds.has(r.profileId));
|
||||
|
||||
// กรณีไม่พบ profile เลย
|
||||
if (validRecords.length === 0) {
|
||||
throw new HttpError(HttpStatus.BAD_REQUEST, "ไม่พบ profile ที่ระบุ");
|
||||
return new HttpSuccess({ count: 0, ids: [] });
|
||||
}
|
||||
|
||||
const meta = {
|
||||
|
|
@ -147,6 +158,15 @@ export class ProfileAbsentLateController extends Controller {
|
|||
|
||||
const result = await this.absentLateRepo.save(records, { data: req });
|
||||
|
||||
// บันทึก history สำหรับแต่ละ record
|
||||
const historyRecords = result.map((data) => {
|
||||
const history = new ProfileAbsentLateHistory();
|
||||
Object.assign(history, { ...data, id: undefined });
|
||||
history.profileAbsentLateId = data.id;
|
||||
return history;
|
||||
});
|
||||
await this.historyRepo.save(historyRecords, { data: req });
|
||||
|
||||
return new HttpSuccess({ count: result.length, ids: result.map((r) => r.id) });
|
||||
}
|
||||
|
||||
|
|
@ -170,15 +190,27 @@ export class ProfileAbsentLateController extends Controller {
|
|||
);
|
||||
|
||||
const before = structuredClone(record);
|
||||
const history = new ProfileAbsentLateHistory();
|
||||
Object.assign(history, { ...record, id: undefined });
|
||||
|
||||
Object.assign(record, body);
|
||||
Object.assign(history, { ...record, id: undefined });
|
||||
|
||||
history.profileAbsentLateId = absentLateId;
|
||||
record.lastUpdateUserId = req.user.sub;
|
||||
record.lastUpdateFullName = req.user.name;
|
||||
record.lastUpdatedAt = new Date();
|
||||
history.lastUpdateUserId = req.user.sub;
|
||||
history.lastUpdateFullName = req.user.name;
|
||||
history.createdUserId = req.user.sub;
|
||||
history.createdFullName = req.user.name;
|
||||
history.createdAt = new Date();
|
||||
history.lastUpdatedAt = new Date();
|
||||
|
||||
await Promise.all([
|
||||
this.absentLateRepo.save(record, { data: req }),
|
||||
setLogDataDiff(req, { before, after: record }),
|
||||
this.historyRepo.save(history, { data: req }),
|
||||
]);
|
||||
|
||||
return new HttpSuccess();
|
||||
|
|
@ -202,16 +234,44 @@ export class ProfileAbsentLateController extends Controller {
|
|||
await new permission().PermissionOrgUserDelete(req, "SYS_REGISTRY_OFFICER", record.profileId);
|
||||
|
||||
const before = structuredClone(record);
|
||||
const history = new ProfileAbsentLateHistory();
|
||||
Object.assign(history, { ...record, id: undefined });
|
||||
|
||||
record.isDeleted = true;
|
||||
record.lastUpdateUserId = req.user.sub;
|
||||
record.lastUpdateFullName = req.user.name;
|
||||
record.lastUpdatedAt = new Date();
|
||||
|
||||
history.profileAbsentLateId = absentLateId;
|
||||
history.isDeleted = true;
|
||||
history.lastUpdateUserId = req.user.sub;
|
||||
history.lastUpdateFullName = req.user.name;
|
||||
history.lastUpdatedAt = new Date();
|
||||
|
||||
await Promise.all([
|
||||
this.absentLateRepo.save(record, { data: req }),
|
||||
setLogDataDiff(req, { before, after: record }),
|
||||
this.historyRepo.save(history, { data: req }),
|
||||
]);
|
||||
|
||||
return new HttpSuccess();
|
||||
}
|
||||
|
||||
/**
|
||||
* API ดึงประวัติการมาสาย/ขาดราชการ
|
||||
* @summary API ดึงประวัติการมาสาย/ขาดราชการ
|
||||
* @param absentLateId คีย์การมาสาย/ขาดราชการ
|
||||
*/
|
||||
@Get("history/{absentLateId}")
|
||||
public async getHistory(@Path() absentLateId: string, @Request() req: RequestWithUser) {
|
||||
const record = await this.absentLateRepo.findOneBy({ id: absentLateId });
|
||||
if (!record) throw new HttpError(HttpStatus.NOT_FOUND, "ไม่พบข้อมูล");
|
||||
await new permission().PermissionOrgUserGet(req, "SYS_REGISTRY_OFFICER", record.profileId);
|
||||
|
||||
const history = await this.historyRepo.find({
|
||||
where: { profileAbsentLateId: absentLateId },
|
||||
order: { createdAt: "DESC" },
|
||||
});
|
||||
return new HttpSuccess(history);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -18,6 +18,7 @@ import {
|
|||
CreateProfileEmployeeAbsentLateBatch,
|
||||
UpdateProfileEmployeeAbsentLate,
|
||||
} from "../entities/ProfileEmployeeAbsentLate";
|
||||
import { ProfileEmployeeAbsentLateHistory } from "../entities/ProfileEmployeeAbsentLateHistory";
|
||||
import HttpSuccess from "../interfaces/http-success";
|
||||
import HttpStatus from "../interfaces/http-status";
|
||||
import HttpError from "../interfaces/http-error";
|
||||
|
|
@ -32,6 +33,7 @@ import { setLogDataDiff } from "../interfaces/utils";
|
|||
export class ProfileEmployeeAbsentLateController extends Controller {
|
||||
private profileRepo = AppDataSource.getRepository(ProfileEmployee);
|
||||
private absentLateRepo = AppDataSource.getRepository(ProfileEmployeeAbsentLate);
|
||||
private historyRepo = AppDataSource.getRepository(ProfileEmployeeAbsentLateHistory);
|
||||
|
||||
/**
|
||||
* API ดึงข้อมูลการมาสาย/ขาดราชการของ user
|
||||
|
|
@ -99,8 +101,15 @@ export class ProfileEmployeeAbsentLateController extends Controller {
|
|||
};
|
||||
|
||||
Object.assign(data, { ...body, ...meta });
|
||||
|
||||
// บันทึก history
|
||||
const history = new ProfileEmployeeAbsentLateHistory();
|
||||
Object.assign(history, { ...data, id: undefined });
|
||||
|
||||
await this.absentLateRepo.save(data, { data: req });
|
||||
setLogDataDiff(req, { before, after: data });
|
||||
history.profileEmployeeAbsentLateId = data.id;
|
||||
await this.historyRepo.save(history, { data: req });
|
||||
|
||||
return new HttpSuccess(data.id);
|
||||
}
|
||||
|
|
@ -114,8 +123,9 @@ export class ProfileEmployeeAbsentLateController extends Controller {
|
|||
@Request() req: RequestWithUser,
|
||||
@Body() body: CreateProfileEmployeeAbsentLateBatch,
|
||||
) {
|
||||
// กรณีไม่มีข้อมูลส่งมา (วันที่ไม่มีคนขาด/มาสาย)
|
||||
if (!body.records || body.records.length === 0) {
|
||||
throw new HttpError(HttpStatus.BAD_REQUEST, "กรุณาระบุข้อมูลอย่างน้อย 1 รายการ");
|
||||
return new HttpSuccess({ count: 0, ids: [] });
|
||||
}
|
||||
|
||||
const profileIds = [...new Set(body.records.map((r) => r.profileEmployeeId))];
|
||||
|
|
@ -126,8 +136,9 @@ export class ProfileEmployeeAbsentLateController extends Controller {
|
|||
const foundProfileIds = new Set(profiles.map((p) => p.id));
|
||||
const validRecords = body.records.filter((r) => foundProfileIds.has(r.profileEmployeeId));
|
||||
|
||||
// กรณีไม่พบ profile เลย
|
||||
if (validRecords.length === 0) {
|
||||
throw new HttpError(HttpStatus.BAD_REQUEST, "ไม่พบ profile ที่ระบุ");
|
||||
return new HttpSuccess({ count: 0, ids: [] });
|
||||
}
|
||||
|
||||
const meta = {
|
||||
|
|
@ -147,6 +158,15 @@ export class ProfileEmployeeAbsentLateController extends Controller {
|
|||
|
||||
const result = await this.absentLateRepo.save(records, { data: req });
|
||||
|
||||
// บันทึก history สำหรับแต่ละ record
|
||||
const historyRecords = result.map((data) => {
|
||||
const history = new ProfileEmployeeAbsentLateHistory();
|
||||
Object.assign(history, { ...data, id: undefined });
|
||||
history.profileEmployeeAbsentLateId = data.id;
|
||||
return history;
|
||||
});
|
||||
await this.historyRepo.save(historyRecords, { data: req });
|
||||
|
||||
return new HttpSuccess({ count: result.length, ids: result.map((r) => r.id) });
|
||||
}
|
||||
|
||||
|
|
@ -170,15 +190,27 @@ export class ProfileEmployeeAbsentLateController extends Controller {
|
|||
);
|
||||
|
||||
const before = structuredClone(record);
|
||||
const history = new ProfileEmployeeAbsentLateHistory();
|
||||
Object.assign(history, { ...record, id: undefined });
|
||||
|
||||
Object.assign(record, body);
|
||||
Object.assign(history, { ...record, id: undefined });
|
||||
|
||||
history.profileEmployeeAbsentLateId = absentLateId;
|
||||
record.lastUpdateUserId = req.user.sub;
|
||||
record.lastUpdateFullName = req.user.name;
|
||||
record.lastUpdatedAt = new Date();
|
||||
history.lastUpdateUserId = req.user.sub;
|
||||
history.lastUpdateFullName = req.user.name;
|
||||
history.createdUserId = req.user.sub;
|
||||
history.createdFullName = req.user.name;
|
||||
history.createdAt = new Date();
|
||||
history.lastUpdatedAt = new Date();
|
||||
|
||||
await Promise.all([
|
||||
this.absentLateRepo.save(record, { data: req }),
|
||||
setLogDataDiff(req, { before, after: record }),
|
||||
this.historyRepo.save(history, { data: req }),
|
||||
]);
|
||||
|
||||
return new HttpSuccess();
|
||||
|
|
@ -202,16 +234,44 @@ export class ProfileEmployeeAbsentLateController extends Controller {
|
|||
await new permission().PermissionOrgUserDelete(req, "SYS_REGISTRY_EMP", record.profileEmployeeId);
|
||||
|
||||
const before = structuredClone(record);
|
||||
const history = new ProfileEmployeeAbsentLateHistory();
|
||||
Object.assign(history, { ...record, id: undefined });
|
||||
|
||||
record.isDeleted = true;
|
||||
record.lastUpdateUserId = req.user.sub;
|
||||
record.lastUpdateFullName = req.user.name;
|
||||
record.lastUpdatedAt = new Date();
|
||||
|
||||
history.profileEmployeeAbsentLateId = absentLateId;
|
||||
history.isDeleted = true;
|
||||
history.lastUpdateUserId = req.user.sub;
|
||||
history.lastUpdateFullName = req.user.name;
|
||||
history.lastUpdatedAt = new Date();
|
||||
|
||||
await Promise.all([
|
||||
this.absentLateRepo.save(record, { data: req }),
|
||||
setLogDataDiff(req, { before, after: record }),
|
||||
this.historyRepo.save(history, { data: req }),
|
||||
]);
|
||||
|
||||
return new HttpSuccess();
|
||||
}
|
||||
|
||||
/**
|
||||
* API ดึงประวัติการมาสาย/ขาดราชการ
|
||||
* @summary API ดึงประวัติการมาสาย/ขาดราชการ
|
||||
* @param absentLateId คีย์การมาสาย/ขาดราชการ
|
||||
*/
|
||||
@Get("history/{absentLateId}")
|
||||
public async getHistory(@Path() absentLateId: string, @Request() req: RequestWithUser) {
|
||||
const record = await this.absentLateRepo.findOneBy({ id: absentLateId });
|
||||
if (!record) throw new HttpError(HttpStatus.NOT_FOUND, "ไม่พบข้อมูล");
|
||||
await new permission().PermissionOrgUserGet(req, "SYS_REGISTRY_EMP", record.profileEmployeeId);
|
||||
|
||||
const history = await this.historyRepo.find({
|
||||
where: { profileEmployeeAbsentLateId: absentLateId },
|
||||
order: { createdAt: "DESC" },
|
||||
});
|
||||
return new HttpSuccess(history);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
20
src/entities/ProfileAbsentLateHistory.ts
Normal file
20
src/entities/ProfileAbsentLateHistory.ts
Normal file
|
|
@ -0,0 +1,20 @@
|
|||
import { Entity, Column } from "typeorm";
|
||||
import {
|
||||
ProfileAbsentLate,
|
||||
AbsentLateStatus,
|
||||
StampType,
|
||||
} from "./ProfileAbsentLate";
|
||||
|
||||
@Entity("profileAbsentLateHistory")
|
||||
export class ProfileAbsentLateHistory extends ProfileAbsentLate {
|
||||
@Column({
|
||||
nullable: true,
|
||||
length: 40,
|
||||
comment: "คีย์นอก(FK)ของตาราง ProfileAbsentLate",
|
||||
default: null,
|
||||
})
|
||||
profileAbsentLateId: string;
|
||||
}
|
||||
|
||||
// Export enums for re-use
|
||||
export { AbsentLateStatus, StampType };
|
||||
17
src/entities/ProfileEmployeeAbsentLateHistory.ts
Normal file
17
src/entities/ProfileEmployeeAbsentLateHistory.ts
Normal file
|
|
@ -0,0 +1,17 @@
|
|||
import { Entity, Column } from "typeorm";
|
||||
import { ProfileEmployeeAbsentLate } from "./ProfileEmployeeAbsentLate";
|
||||
import { AbsentLateStatus, StampType } from "./ProfileAbsentLate";
|
||||
|
||||
@Entity("profileEmployeeAbsentLateHistory")
|
||||
export class ProfileEmployeeAbsentLateHistory extends ProfileEmployeeAbsentLate {
|
||||
@Column({
|
||||
nullable: true,
|
||||
length: 40,
|
||||
comment: "คีย์นอก(FK)ของตาราง ProfileEmployeeAbsentLate",
|
||||
default: null,
|
||||
})
|
||||
profileEmployeeAbsentLateId: string;
|
||||
}
|
||||
|
||||
// Export enums for re-use
|
||||
export { AbsentLateStatus, StampType };
|
||||
19
src/migration/1774408245407-add_table_absentLateHistory.ts
Normal file
19
src/migration/1774408245407-add_table_absentLateHistory.ts
Normal file
|
|
@ -0,0 +1,19 @@
|
|||
import { MigrationInterface, QueryRunner } from "typeorm";
|
||||
|
||||
export class AddTableAbsentLateHistory1774408245407 implements MigrationInterface {
|
||||
name = 'AddTableAbsentLateHistory1774408245407'
|
||||
|
||||
public async up(queryRunner: QueryRunner): Promise<void> {
|
||||
|
||||
await queryRunner.query(`CREATE TABLE \`profileEmployeeAbsentLateHistory\` (\`id\` varchar(36) NOT NULL, \`createdAt\` datetime(6) NOT NULL COMMENT 'สร้างข้อมูลเมื่อ' DEFAULT CURRENT_TIMESTAMP(6), \`createdUserId\` varchar(40) NOT NULL COMMENT 'User Id ที่สร้างข้อมูล' DEFAULT '00000000-0000-0000-0000-000000000000', \`lastUpdatedAt\` datetime(6) NOT NULL COMMENT 'แก้ไขข้อมูลล่าสุดเมื่อ' DEFAULT CURRENT_TIMESTAMP(6), \`lastUpdateUserId\` varchar(40) NOT NULL COMMENT 'User Id ที่แก้ไขข้อมูล' DEFAULT '00000000-0000-0000-0000-000000000000', \`createdFullName\` varchar(200) NOT NULL COMMENT 'ชื่อ User ที่สร้างข้อมูล' DEFAULT 'System Administrator', \`lastUpdateFullName\` varchar(200) NOT NULL COMMENT 'ชื่อ User ที่แก้ไขข้อมูลล่าสุด' DEFAULT 'System Administrator', \`profileEmployeeId\` varchar(40) NULL COMMENT 'คีย์นอก(FK)ของตาราง ProfileEmployee', \`status\` enum ('LATE', 'ABSENT') NOT NULL COMMENT 'สถานะ มาสาย/ขาดราชการ', \`stampDate\` datetime NOT NULL COMMENT 'วันที่และเวลาที่ลงเวลา', \`stampType\` enum ('FULL_DAY', 'MORNING', 'AFTERNOON') NOT NULL COMMENT 'เต็มวัน/ครึ่งเช้า/ครึ่งบ่าย' DEFAULT 'FULL_DAY', \`stampAmount\` decimal(2,1) NOT NULL COMMENT 'จำนวน (1.0/0.5)' DEFAULT '1.0', \`remark\` varchar(250) NULL COMMENT 'หมายเหตุ', \`isDeleted\` tinyint NOT NULL COMMENT 'สถานะลบข้อมูล' DEFAULT 0, \`profileEmployeeAbsentLateId\` varchar(40) NULL COMMENT 'คีย์นอก(FK)ของตาราง ProfileEmployeeAbsentLate', PRIMARY KEY (\`id\`)) ENGINE=InnoDB`);
|
||||
await queryRunner.query(`CREATE TABLE \`profileAbsentLateHistory\` (\`id\` varchar(36) NOT NULL, \`createdAt\` datetime(6) NOT NULL COMMENT 'สร้างข้อมูลเมื่อ' DEFAULT CURRENT_TIMESTAMP(6), \`createdUserId\` varchar(40) NOT NULL COMMENT 'User Id ที่สร้างข้อมูล' DEFAULT '00000000-0000-0000-0000-000000000000', \`lastUpdatedAt\` datetime(6) NOT NULL COMMENT 'แก้ไขข้อมูลล่าสุดเมื่อ' DEFAULT CURRENT_TIMESTAMP(6), \`lastUpdateUserId\` varchar(40) NOT NULL COMMENT 'User Id ที่แก้ไขข้อมูล' DEFAULT '00000000-0000-0000-0000-000000000000', \`createdFullName\` varchar(200) NOT NULL COMMENT 'ชื่อ User ที่สร้างข้อมูล' DEFAULT 'System Administrator', \`lastUpdateFullName\` varchar(200) NOT NULL COMMENT 'ชื่อ User ที่แก้ไขข้อมูลล่าสุด' DEFAULT 'System Administrator', \`profileId\` varchar(40) NULL COMMENT 'คีย์นอก(FK)ของตาราง Profile', \`status\` enum ('LATE', 'ABSENT') NOT NULL COMMENT 'สถานะ มาสาย/ขาดราชการ', \`stampDate\` datetime NOT NULL COMMENT 'วันที่และเวลาที่ลงเวลา', \`stampType\` enum ('FULL_DAY', 'MORNING', 'AFTERNOON') NOT NULL COMMENT 'เต็มวัน/ครึ่งเช้า/ครึ่งบ่าย' DEFAULT 'FULL_DAY', \`stampAmount\` decimal(2,1) NOT NULL COMMENT 'จำนวน (1.0/0.5)' DEFAULT '1.0', \`remark\` varchar(250) NULL COMMENT 'หมายเหตุ', \`isDeleted\` tinyint NOT NULL COMMENT 'สถานะลบข้อมูล' DEFAULT 0, \`profileAbsentLateId\` varchar(40) NULL COMMENT 'คีย์นอก(FK)ของตาราง ProfileAbsentLate', PRIMARY KEY (\`id\`)) ENGINE=InnoDB`);
|
||||
await queryRunner.query(`ALTER TABLE \`profileEmployeeAbsentLateHistory\` ADD CONSTRAINT \`FK_8b06ca79d6f75c7d6577c86f3d4\` FOREIGN KEY (\`profileEmployeeId\`) REFERENCES \`profileEmployee\`(\`id\`) ON DELETE NO ACTION ON UPDATE NO ACTION`);
|
||||
await queryRunner.query(`ALTER TABLE \`profileAbsentLateHistory\` ADD CONSTRAINT \`FK_0fa6a843d0e6d901a4f2f56c541\` FOREIGN KEY (\`profileId\`) REFERENCES \`profile\`(\`id\`) ON DELETE NO ACTION ON UPDATE NO ACTION`);
|
||||
}
|
||||
|
||||
public async down(queryRunner: QueryRunner): Promise<void> {
|
||||
await queryRunner.query(`DROP TABLE \`profileAbsentLateHistory\``);
|
||||
await queryRunner.query(`DROP TABLE \`profileEmployeeAbsentLateHistory\``);
|
||||
}
|
||||
|
||||
}
|
||||
Loading…
Add table
Add a link
Reference in a new issue