feat(ai): add ADR-036 unified OCR architecture and frontend test coverage
CI / CD Pipeline / build (push) Failing after 6m24s
CI / CD Pipeline / deploy (push) Has been skipped

- Add ADR-036 unified OCR architecture (typhoon-ocr via Ollama)
- Extend AI execution profiles for OCR sandbox configuration
- Add comprehensive frontend test coverage (components, hooks, services)
- Add backend test coverage for document-numbering services
- Update OCR sidecar with typhoon-ocr integration
- Add AI policy service and execution profile management
- Update AGENTS.md and architecture documentation
This commit is contained in:
2026-06-14 06:34:07 +07:00
parent e3503b6a77
commit 7e8f4859cd
108 changed files with 33914 additions and 339 deletions
+23
View File
@@ -0,0 +1,23 @@
// File: frontend/__tests__/README.md
// Change Log
// - 2026-06-13: Document frontend unit test naming and header conventions.
# Frontend Test Conventions
ใช้ไฟล์ `*.test.ts` หรือ `*.test.tsx` เท่านั้น เพราะ `frontend/vitest.config.ts` include pattern รองรับชื่อนี้
ทุก test file ต้องขึ้นต้นด้วย:
```ts
// File: frontend/path/to/file.test.ts
// Change Log
// - YYYY-MM-DD: คำอธิบายการเปลี่ยนแปลง
```
แนวทางหลัก:
- ใช้ `createTestQueryClient()` จาก `@/lib/test-utils` สำหรับ hook/component ที่ใช้ TanStack Query
- Mock HTTP ผ่าน `apiClient` ที่ตั้งค่าไว้ใน `vitest.setup.ts`
- Mock data ฝั่ง Public API ต้องใช้ `publicId` เป็น UUIDv7 ตาม ADR-019
- ห้ามใช้ `console.log` ใน test
- หลีกเลี่ยง `any`; ถ้าจำเป็นต้อง mock shape บางส่วน ให้ใช้ `Partial<T>` หรือ type เฉพาะของ test
+24
View File
@@ -0,0 +1,24 @@
// File: frontend/__tests__/helpers/api-mock.ts
// Change Log
// - 2026-06-13: Add shared API client mock shape assertions for frontend tests.
import { expect, type Mock } from 'vitest';
type ApiClientMock = {
get: Mock;
post: Mock;
put: Mock;
patch: Mock;
delete: Mock;
};
/**
* ตรวจสอบว่า apiClient mock จาก vitest.setup.ts มี method ครบตาม pattern กลาง
*/
export function expectApiClientMockShape(apiClient: ApiClientMock): void {
expect(apiClient.get).toBeTypeOf('function');
expect(apiClient.post).toBeTypeOf('function');
expect(apiClient.put).toBeTypeOf('function');
expect(apiClient.patch).toBeTypeOf('function');
expect(apiClient.delete).toBeTypeOf('function');
}