690617:1649 237 #01.4
CI / CD Pipeline / build (push) Successful in 7m34s
CI / CD Pipeline / deploy (push) Successful in 20m3s

This commit is contained in:
2026-06-17 16:49:28 +07:00
parent db16c95019
commit 037fbb65f5
9 changed files with 361 additions and 136 deletions
@@ -0,0 +1,58 @@
# Session 18 — 2026-06-17 (RFA Service Code Review & Refactor)
## Summary
Implement 8 improvement suggestions from code review ของ `rfa.service.ts` ตาม AGENTS.md — magic strings → constants, DRY helper extraction, DTO narrowing, method extraction, repository injection fix, workflow cleanup on cancel, และ `terminateInstance()` ใน WorkflowEngineService
## ปัญหาที่พบ (Root Cause)
| # | ปัญหา | ระดับ |
|---|-------|-------|
| 1 | Magic strings (`'DDW'`, `'SDW'`, `'ADW'`, `'DFT'`, `'CC'`, `'DRAFT'`, `'TO'` ฯลฯ) กระจาย ~20 ตำแหน่ง | 🟡 |
| 2 | `getCurrentRevision()` pattern ซ้ำ 4 ครั้ง (submit, processAction, update, cancel) | 🟡 |
| 3 | `disciplineId ?? 0` — dead code (DTO require `@Min(1)`) | 🟡 |
| 4 | `UpdateRfaDto` contract กว้างเกิน — รับ 10+ fields แต่ใช้แค่ 6 | 🟡 |
| 5 | `create()` ยาว 388 บรรทัด — validation, entity creation, post-commit รวมกัน | 🟢 |
| 6 | `notifyRecipients()` ใช้ `this.dataSource.manager.find()` แทน injected repo | 🟢 |
| 7 | `cancel()` ไม่ cleanup workflow instance — orphan instance ค้าง | 🟡 |
| 8 | Fire-and-forget (.catch log-only) — already acceptable per ADR-007 | 🟢 (deferred) |
## การแก้ไข (Fix)
| ไฟล์ | การเปลี่ยนแปลง |
|------|---------------|
| `backend/src/modules/rfa/constants/rfa.constants.ts` | **NEW** — Constants: type codes, status codes, workflow states, error codes, search types |
| `backend/src/modules/rfa/dto/update-rfa.dto.ts` | **Narrow** — จาก 10+ fields (extends PartialType CreateRfaRevisionDto) → 6 fields เฉพาะที่ใช้ |
| `backend/src/modules/rfa/rfa.service.ts` | **Imports**`import * as RFA from './constants/rfa.constants'` + `CorrespondenceRecipient` repo injection |
| | **Static constants**`WORKFLOW_CODE`, `STATE_TO_STATUS`, `DEFAULT_APPROVED_CODE` → อ่านจาก constants |
| | **`getCurrentRevision()` helper** — DRY 4× blocks → 1 private method |
| | **`validateRfaTypeDrawingConstraints()`** — extracted from `create()` |
| | **`disciplineId ?? 0`** → `disciplineId` (DTO require `@Min(1)`) |
| | **Magic strings** → constants (~20 ตำแหน่ง) |
| | **`notifyRecipients()`** → `this.corrRecipientRepo.find()` แทน `this.dataSource.manager.find()` |
| | **`cancel()`** — terminate workflow instance via `workflowEngine.terminateInstance()` |
| `backend/src/modules/workflow-engine/workflow-engine.service.ts` | **NEW `terminateInstance()`** — set status=CANCELLED + currentState=CANCELLED สำหรับ cancel workflow |
## กฎที่ Lock แล้ว
- 🔒 **Magic strings → Constants** — type codes, status codes, error codes, workflow states ต้องใช้จาก `rfa.constants.ts` เสมอ ห้าม hardcode
- 🔒 **`getCurrentRevision()`** — ทุก method ที่ต้องการ revision ปัจจุบัน ต้องใช้ helper นี้ ไม่ duplicate logic
- 🔒 **`cancel()` ต้อง terminate workflow** — เมื่อยกเลิก DRAFT RFA ให้ cleanup workflow instance ด้วย
- 🔒 **`notifyRecipients()`** — use injected repo (ไม่ใช่ `dataSource.manager.find()`)
## Verification
- [x] TypeScript `tsc --noEmit`**0 errors** ใน rfa.service.ts, workflow-engine.service.ts, rfa.constants.ts, update-rfa.dto.ts
- [x] magic strings grep — ไม่เหลือ `'DFT'`, `'FRE'`, `'FAP'`, `'FCO'`, `'CC'`, `'OBS'`, `'DRAFT'`, `'DDW'`, `'SDW'`, `'ADW'`, `'TO'` ใน rfa.service.ts
- [x] Build integrity — unchanged files not affected
## Files Changed
```
backend/src/modules/rfa/constants/rfa.constants.ts (NEW — 70 lines)
backend/src/modules/rfa/dto/update-rfa.dto.ts (OVERWRITTEN — 22 lines)
backend/src/modules/rfa/rfa.service.ts (MODIFIED — 1056 lines, +45/-55 net)
backend/src/modules/workflow-engine/workflow-engine.service.ts (MODIFIED — +20 lines)
specs/88-logs/session-2026-06-17-rfa-service-refactor.md (THIS FILE)
specs/88-logs/rollouts.md (UPDATED)
```