690406:2310 Done Task BE-ERR-01
CI / CD Pipeline / build (push) Failing after 4m53s
CI / CD Pipeline / deploy (push) Has been skipped

This commit is contained in:
2026-04-06 23:10:56 +07:00
parent c95e0f537e
commit 961ee72343
24 changed files with 1329 additions and 268 deletions
+192
View File
@@ -0,0 +1,192 @@
# Error Catalog
**Version:** 1.0
**ADR Compliance:** ADR-007 (Error Handling & Recovery Strategy)
**Last Updated:** 2026-04-06
---
## Error Format (ADR-007)
All API errors follow this structure:
```json
{
"error": {
"type": "VALIDATION",
"code": "VALIDATION_ERROR",
"message": "ข้อมูลที่กรอกไม่ถูกต้อง กรุณาตรวจสอบและลองใหม่",
"severity": "LOW",
"timestamp": "2026-04-06T10:00:00.000Z",
"statusCode": 400,
"recoveryActions": ["ตรวจสอบข้อมูลที่กรอก", "ลองใหม่อีกครั้ง"]
}
}
```
---
## Error Types
| Error Type | HTTP Status | Description |
|------------|-------------|-------------|
| `VALIDATION` | 400 | ข้อมูล Input ไม่ถูกต้อง |
| `BUSINESS_RULE` | 422 | ละเมิดกฎทางธุรกิจ |
| `PERMISSION_DENIED` | 403 | ไม่มีสิทธิ์ดำเนินการ |
| `NOT_FOUND` | 404 | ไม่พบข้อมูลที่ร้องขอ |
| `CONFLICT` | 409 | ข้อมูลซ้ำหรือขัดแย้ง |
| `INTERNAL_ERROR` | 500 | ปัญหาระบบภายใน |
| `DATABASE_ERROR` | 500 | ปัญหาฐานข้อมูล |
| `EXTERNAL_SERVICE` | 500 | บริการภายนอกมีปัญหา |
| `INFRASTRUCTURE` | 500 | ปัญหาโครงสร้างพื้นฐาน |
## Severity Levels
| Severity | Description | User Impact |
|----------|-------------|-------------|
| `LOW` | ผู้ใช้ทำผิด แก้ไขง่าย | แก้ไขข้อมูลได้ทันที |
| `MEDIUM` | ละเมิดกฎทางธุรกิจ | ต้องดำเนินการก่อน |
| `HIGH` | ปัญหาระบบ | อาจต้องติดต่อ Support |
| `CRITICAL` | ระบบล้มเหลว | ต้องแก้ไขทันที |
---
## Error Codes Reference
### General Errors
| Error Code | Type | HTTP | User Message | Severity | Module |
|------------|------|------|--------------|----------|--------|
| `VALIDATION_ERROR` | VALIDATION | 400 | ข้อมูลที่กรอกไม่ถูกต้อง | LOW | All |
| `NOT_FOUND` | NOT_FOUND | 404 | ไม่พบข้อมูลที่ร้องขอ | LOW | All |
| `PERMISSION_DENIED` | PERMISSION_DENIED | 403 | ไม่มีสิทธิ์ดำเนินการ | MEDIUM | All |
| `INTERNAL_ERROR` | INTERNAL_ERROR | 500 | เกิดข้อผิดพลาดในระบบ | HIGH | All |
| `DATABASE_ERROR` | DATABASE_ERROR | 500 | เกิดข้อผิดพลาดของฐานข้อมูล | HIGH | All |
| `NETWORK_ERROR` | INFRASTRUCTURE | N/A | ไม่สามารถเชื่อมต่อได้ | HIGH | Frontend |
### Correspondence Errors
| Error Code | Type | HTTP | User Message | Severity | Recovery Actions |
|------------|------|------|--------------|----------|-----------------|
| `INVALID_DOCUMENT_TYPE` | BUSINESS_RULE | 422 | การสื่อสารภายในควรใช้ Circulation Sheet | MEDIUM | ใช้ Circulation Sheet |
| `CORRESPONDENCE_TO_SELF` | BUSINESS_RULE | 422 | ไม่สามารถส่งถึงองค์กรตัวเองได้ | MEDIUM | ใช้ Circulation Sheet |
| `SELF_REFERENCE` | BUSINESS_RULE | 422 | ไม่สามารถอ้างอิงเอกสารเดียวกัน | MEDIUM | เลือกเอกสารอื่น |
### RFA Errors
| Error Code | Type | HTTP | User Message | Severity | Recovery Actions |
|------------|------|------|--------------|----------|-----------------|
| `RFA_TYPE_CONTRACT_MISMATCH` | BUSINESS_RULE | 422 | ประเภท RFA ไม่ตรงกับสัญญา | MEDIUM | เลือกประเภท RFA ที่ถูกต้อง |
| `DISCIPLINE_CONTRACT_MISMATCH` | BUSINESS_RULE | 422 | Discipline ไม่ตรงกับสัญญา | MEDIUM | เลือก Discipline ที่ถูกต้อง |
| `EC_RFA_001_ACTIVE_RFA_EXISTS` | BUSINESS_RULE | 422 | Shop Drawing มี RFA ที่ใช้งานอยู่แล้ว | MEDIUM | ตรวจสอบ RFA ที่มีอยู่ |
| `ROUTING_TEMPLATE_NOT_FOUND` | BUSINESS_RULE | 422 | ไม่พบ Routing Template | MEDIUM | ตรวจสอบ Template |
| `ROUTING_TEMPLATE_EMPTY` | BUSINESS_RULE | 422 | Routing Template ไม่มีขั้นตอน | MEDIUM | เพิ่ม Step ใน Template |
| `RFA_INVALID_SUBMIT_STATUS` | BUSINESS_RULE | 422 | ส่งได้เฉพาะ DRAFT เท่านั้น | MEDIUM | ตรวจสอบสถานะ |
| `RFA_EDIT_NON_DRAFT` | BUSINESS_RULE | 422 | แก้ไขได้เฉพาะ DRAFT เท่านั้น | MEDIUM | สร้าง Revision ใหม่ |
| `NO_ACTIVE_WORKFLOW_STEP` | BUSINESS_RULE | 422 | ไม่พบ Workflow Step ที่เปิดอยู่ | MEDIUM | ตรวจสอบสถานะ Workflow |
### Workflow Engine Errors
| Error Code | Type | HTTP | User Message | Severity | Recovery Actions |
|------------|------|------|--------------|----------|-----------------|
| `WORKFLOW_NOT_ACTIVE` | BUSINESS_RULE | 422 | Workflow ไม่อยู่ในสถานะ Active | MEDIUM | ตรวจสอบสถานะ Workflow |
| `WORKFLOW_NO_INITIAL_STATE` | BUSINESS_RULE | 422 | Workflow ไม่มี Initial State | MEDIUM | ตรวจสอบ DSL |
| `WORKFLOW_INVALID_CURRENT_STATE` | BUSINESS_RULE | 422 | Workflow อยู่ในสถานะที่ไม่รู้จัก | MEDIUM | ตรวจสอบ DSL |
| `WORKFLOW_TERMINAL_STATE` | BUSINESS_RULE | 422 | ไม่สามารถดำเนินการจาก State สุดท้าย | MEDIUM | เอกสารสิ้นสุดแล้ว |
| `WORKFLOW_INVALID_ACTION` | BUSINESS_RULE | 422 | ไม่สามารถดำเนินการนี้ในสถานะปัจจุบัน | MEDIUM | เลือกการดำเนินการที่อนุญาต |
| `WORKFLOW_ROLE_REQUIRED` | BUSINESS_RULE | 422 | ต้องมี Role ที่กำหนด | MEDIUM | ขอสิทธิ์จาก Admin |
| `WORKFLOW_USER_MISMATCH` | BUSINESS_RULE | 422 | ผู้ใช้ไม่ได้รับอนุญาต | MEDIUM | ตรวจสอบบัญชีที่ใช้ |
| `WORKFLOW_CONDITION_NOT_MET` | BUSINESS_RULE | 422 | เงื่อนไขสำหรับการดำเนินการไม่ผ่าน | MEDIUM | ตรวจสอบเงื่อนไข |
| `WORKFLOW_INVALID_RETURN_TARGET` | BUSINESS_RULE | 422 | ไม่สามารถส่งคืนไปเกินขั้นตอนแรก | MEDIUM | ตรวจสอบลำดับขั้นตอน |
### DSL Validation Errors
| Error Code | Type | HTTP | User Message | Severity | Recovery Actions |
|------------|------|------|--------------|----------|-----------------|
| `DSL_MULTIPLE_INITIAL_STATES` | BUSINESS_RULE | 422 | DSL มี Initial State หลายค่า | MEDIUM | แก้ไข DSL |
| `DSL_UNKNOWN_TRANSITION_TARGET` | BUSINESS_RULE | 422 | DSL อ้างอิง State ที่ไม่พบ | MEDIUM | ตรวจสอบชื่อ State |
| `DSL_NO_INITIAL_STATE` | BUSINESS_RULE | 422 | DSL ไม่มี Initial State | MEDIUM | เพิ่ม initial: true |
| `INVALID_WORKFLOW_DSL` | BUSINESS_RULE | 422 | Workflow DSL ไม่ถูกต้อง | MEDIUM | ตรวจสอบ syntax |
---
## Exception Classes Reference
| Class | Code | HTTP | Usage |
|-------|------|------|-------|
| `ValidationException` | `VALIDATION_ERROR` | 400 | Input validation failures |
| `BusinessException` | custom | 422 | Business rule violations |
| `NotFoundException` | `NOT_FOUND` | 404 | Resource not found |
| `PermissionException` | `PERMISSION_DENIED` | 403 | RBAC failures |
| `ConflictException` | custom | 409 | Duplicate/conflict |
| `WorkflowException` | custom | 422 | Workflow state/transition errors |
| `SystemException` | `INTERNAL_ERROR` | 500 | Infrastructure issues |
| `DatabaseException` | `DATABASE_ERROR` | 500 | DB failures |
---
## Developer Guidelines
### When to use each exception
```typescript
// ✅ Input validation (user made a mistake)
throw new ValidationException('User must belong to an organization');
// ✅ Resource not found
throw new NotFoundException('Correspondence', publicId);
// ✅ Business rule violation
throw new BusinessException(
'EC_RFA_001_ACTIVE_RFA_EXISTS',
'Technical message for logs',
'Thai user message',
['Recovery action 1', 'Recovery action 2']
);
// ✅ Permission denied (RBAC)
throw new PermissionException('correspondence', 'cancel');
// ✅ Workflow state error
throw new WorkflowException(
'WORKFLOW_INVALID_ACTION',
'Technical message',
'Thai user message',
['Recovery actions']
);
// ✅ Master data / config missing (internal system issue)
throw new SystemException('Status DRAFT not found in Master Data');
```
### Anti-patterns (Do NOT use)
```typescript
// ❌ Never use NestJS built-in exceptions in service layer
import { NotFoundException } from '@nestjs/common'; // WRONG
// ❌ Never use generic error messages
throw new SystemException('Error'); // Too vague
// ❌ Never expose technical details in user messages
throw new BusinessException(
'DB_ERROR',
'DB error',
'SQL constraint error: ...' // Exposes internals
);
```
---
## Adding New Error Codes
1. Add entry to this catalog with full details
2. Add `code` constant if reused often (optional)
3. Use `BusinessException` or specific class
4. Provide Thai user message + recovery actions
5. Update test coverage
---
**Maintainers:** Backend Team Lead
**Review Cycle:** Every 6 months (next: 2026-10-06)