690606:1120 ADR-035-135 #02
CI / CD Pipeline / build (push) Successful in 5m11s
CI / CD Pipeline / deploy (push) Successful in 3m32s

This commit is contained in:
2026-06-06 11:20:13 +07:00
parent 26cc71ce60
commit ed1b302274
11 changed files with 467 additions and 224 deletions
+1 -1
View File
@@ -1,7 +1,7 @@
# NAP-DMS Project Context & Rules
- For: Windsurf Cascade (and compatible: Codex CLI, opencode, Amp, Antigravity, AGENTS.md tools)
- Version: 1.9.6 | Last synced from repo: 2026-05-22
- Version: 1.9.10 | Last synced from repo: 2026-06-06
- Repo: [https://git.np-dms.work/np-dms/lcbp3](https://git.np-dms.work/np-dms/lcbp3)
- Skill pack: `.agents/skills/` (v1.9.0, 21 skills) — see [`skills/README.md`](./.agents/skills/README.md) + [`skills/_LCBP3-CONTEXT.md`](./.agents/skills/_LCBP3-CONTEXT.md)
+96
View File
@@ -112,3 +112,99 @@
| "แก้ bug / bugfix" | `.agents/workflows/bugfix.md`, `error-catalog.md` | ใช้ bugfix workflow สำหรับเคสที่สาเหตุชัดเจน |
| "ตรวจแอปจริง" | `.windsurf/workflows/check-real-app.md` | ตรวจ endpoint/UI/console หลัง build pass — No Fake Evidence |
| "งานค้าง / resume" | `.windsurf/workflows/resume-pending-work.md` | อ่าน checkpoint เดิม → ตรวจ build → วางแผนต่อโดยไม่ทำงานซ้ำ |
---
## 🔌 MCP MariaDB Tools
MCP MariaDB server ให้เครื่องมือสำหรับตรวจสอบและจัดการ database โดยตรง ใช้สำหรับ:
- ตรวจสอบ schema กับ spec file `specs/03-Data-and-Storage/lcbp3-v1.9.0-schema-02-tables.sql`
- Debug ปัญหา database โดยไม่ต้องเข้า MySQL client
- ตรวจสอบ data ใน production/staging
- Validate การเปลี่ยนแปลง schema ก่อน deploy
### Available Tools
| Tool | หน้าที่ | ตัวอย่างการใช้งาน |
|------|----------|------------------|
| `mcp1_mysql_test_connection` | ทดสอบ connection กับ database | ตรวจสอบว่า MCP server เชื่อมต่อได้ |
| `mcp1_mysql_show_databases` | แสดง databases ทั้งหมด | ดูว่ามี database อะไรบ้าง |
| `mcp1_mysql_show_tables` | แสดง tables ทั้งหมดใน database | ดูรายชื่อ tables ใน `lcbp3` |
| `mcp1_mysql_describe_table` | ดู structure/columns ของ table | ตรวจสอบ columns, types, keys ของ `correspondences` |
| `mcp1_mysql_query` | รัน SELECT query | ดู data ใน table หรือ join query |
| `mcp1_mysql_insert` | INSERT data | เพิ่ม seed data หรือ test data |
| `mcp1_mysql_update` | UPDATE data | แก้ไข data ใน table |
| `mcp1_mysql_delete` | DELETE data | ลบ data ใน table |
### การใช้งานร่วมกับ Development Flow
**เมื่อเขียน query ใหม่:**
1. ใช้ `mcp1_mysql_describe_table` เพื่อตรวจสอบ columns และ types
2. เปรียบเทียบกับ `specs/03-Data-and-Storage/lcbp3-v1.9.0-schema-02-tables.sql`
3. ใช้ `mcp1_mysql_query` เพื่อทดสอบ query ก่อน implement
**เมื่อเปลี่ยน schema (ADR-009):**
1. ใช้ `mcp1_mysql_describe_table` เพื่อดู structure ปัจจุบัน
2. สร้าง SQL delta ใน `specs/03-Data-and-Storage/deltas/`
3. ใช้ `mcp1_mysql_query` เพื่อตรวจสอบผลลัพธ์หลัง apply delta
**เมื่อ debug ปัญหา database:**
1. ใช้ `mcp1_mysql_query` เพื่อดู data จริง
2. เปรียบเทียบกับ spec และ data dictionary
3. ตรวจสอบ foreign keys และ constraints
### ข้อควรระวัง
- **❌ ห้ามใช้ MCP MariaDB สำหรับ DDL operations** (CREATE/ALTER/DROP) โดยตรง — ต้องใช้ SQL delta ตาม ADR-009
- **✅ ใช้สำหรับ DQL/DML operations** (SELECT/INSERT/UPDATE/DELETE) เพื่อ debug และ test เท่านั้น
- **⚠️ ระวัง DELETE operations** — อาจทำให้เสีย data ใน production
- **✅ ตรวจสอบ schema กับ spec file เสมอ** ก่อนเขียน query
---
## 🧠 MCP Memory Tools
MCP Memory server ให้เครื่องมือสำหรับจัดการ Knowledge Graph และ Long-term Memory ใช้สำหรับ:
- จัดเก็บความรู้และ context ของโปรเจกต์ในรูปแบบ Graph (Entities + Relations + Observations)
- ค้นหาและดึงข้อมูล context จาก memory ที่บันทึกไว้ใน session ก่อนหน้า
- สร้าง/แก้ไข/ลบ entities, relations, และ observations ใน knowledge graph
### Available Tools
| Tool | หน้าที่ | ตัวอย่างการใช้งาน |
|------|----------|------------------|
| `mcp3_create_entities` | สร้าง entities ใหม่หลายตัวพร้อม observations | สร้าง entity ใหม่เช่น Project, User, Task |
| `mcp3_create_relations` | สร้าง relations ระหว่าง entities | สร้าง relation: Project → has → User |
| `mcp3_add_observations` | เพิ่ม observations ให้ entity ที่มีอยู่แล้ว | เพิ่ม context เพิ่มเติมให้ entity |
| `mcp3_delete_entities` | ลบ entities และ relations ที่เกี่ยวข้อง | ลบ entity ที่ไม่ใช้แล้ว |
| `mcp3_delete_relations` | ลบ relations ระหว่าง entities | ลบ relation ที่ผิดหรือไม่ใช้แล้ว |
| `mcp3_delete_observations` | ลบ observations จาก entity | ลบ context ที่ผิดหรือล้าสุด |
| `mcp3_open_nodes` | ดึงข้อมูล entities ตามชื่อ | ดึง entity ที่ระบุชื่อ |
| `mcp3_read_graph` | อ่าน knowledge graph ทั้งหมด | ดูทั้ง graph structure |
| `mcp3_search_nodes` | ค้นหา entities ตาม query | ค้นหา entity จากชื่อ, type, หรือ observation |
### การใช้งานร่วมกับ Development Flow
**เมื่อบันทึก context ใหม่:**
1. ใช้ `mcp3_create_entities` เพื่อสร้าง entities ใหม่ (ถ้ายังไม่มี)
2. ใช้ `mcp3_create_relations` เพื่อเชื่อมโยง entities
3. ใช้ `mcp3_add_observations` เพื่อเพิ่ม context/observations
**เมื่อค้นหา context:**
1. ใช้ `mcp3_search_nodes` เพื่อค้นหา entities ที่เกี่ยวข้อง
2. ใช้ `mcp3_open_nodes` เพื่อดึงข้อมูล entities ที่ต้องการ
3. ใช้ `mcp3_read_graph` เพื่อดู relations ระหว่าง entities
**เมื่อแก้ไข context:**
1. ใช้ `mcp3_add_observations` เพื่อเพิ่ม observations ใหม่
2. ใช้ `mcp3_delete_observations` เพื่อลบ observations ที่ผิด
3. ใช้ `mcp3_create_relations` หรือ `mcp3_delete_relations` เพื่อปรับ relations
### ข้อควรระวัง
- **✅ ใช้สำหรับบันทึก context ที่ต้องใช้ร่วมกันหลาย session** — เช่น การตัดสินใจสำคัญ, architecture decisions, rollout history
- **⚠️ ระวังการลบ entities** — อาจทำให้เสีย context ที่ยังใช้งานอยู่
- **✅ ตรวจสอบว่า entity มีอยู่แล้วก่อนสร้าง** — ใช้ `mcp3_search_nodes` หรือ `mcp3_open_nodes` ก่อน
- **✅ ใช้ชื่อ entity ที่ชัดเจนและไม่ซ้ำกัน** — เพื่อป้องกันความสับสน
+1 -1
View File
@@ -5,7 +5,7 @@ trigger: always_on
# NAP-DMS Project Context & Rules
- For: Windsurf Cascade (and compatible: Codex CLI, opencode, Amp, Antigravity, AGENTS.md tools)
- Version: 1.9.6 | Last synced from repo: 2026-05-22
- Version: 1.9.10 | Last synced from repo: 2026-06-06
- Repo: [https://git.np-dms.work/np-dms/lcbp3](https://git.np-dms.work/np-dms/lcbp3)
- Skill pack: `.agents/skills/` (v1.9.0, 21 skills) — see [`skills/README.md`](./.agents/skills/README.md) + [`skills/_LCBP3-CONTEXT.md`](./.agents/skills/_LCBP3-CONTEXT.md)
+96
View File
@@ -116,3 +116,99 @@ trigger: always_on
| "แก้ bug / bugfix" | `.agents/workflows/bugfix.md`, `error-catalog.md` | ใช้ bugfix workflow สำหรับเคสที่สาเหตุชัดเจน |
| "ตรวจแอปจริง" | `.windsurf/workflows/check-real-app.md` | ตรวจ endpoint/UI/console หลัง build pass — No Fake Evidence |
| "งานค้าง / resume" | `.windsurf/workflows/resume-pending-work.md` | อ่าน checkpoint เดิม → ตรวจ build → วางแผนต่อโดยไม่ทำงานซ้ำ |
---
## 🔌 MCP MariaDB Tools
MCP MariaDB server ให้เครื่องมือสำหรับตรวจสอบและจัดการ database โดยตรง ใช้สำหรับ:
- ตรวจสอบ schema กับ spec file `specs/03-Data-and-Storage/lcbp3-v1.9.0-schema-02-tables.sql`
- Debug ปัญหา database โดยไม่ต้องเข้า MySQL client
- ตรวจสอบ data ใน production/staging
- Validate การเปลี่ยนแปลง schema ก่อน deploy
### Available Tools
| Tool | หน้าที่ | ตัวอย่างการใช้งาน |
|------|----------|------------------|
| `mcp1_mysql_test_connection` | ทดสอบ connection กับ database | ตรวจสอบว่า MCP server เชื่อมต่อได้ |
| `mcp1_mysql_show_databases` | แสดง databases ทั้งหมด | ดูว่ามี database อะไรบ้าง |
| `mcp1_mysql_show_tables` | แสดง tables ทั้งหมดใน database | ดูรายชื่อ tables ใน `lcbp3` |
| `mcp1_mysql_describe_table` | ดู structure/columns ของ table | ตรวจสอบ columns, types, keys ของ `correspondences` |
| `mcp1_mysql_query` | รัน SELECT query | ดู data ใน table หรือ join query |
| `mcp1_mysql_insert` | INSERT data | เพิ่ม seed data หรือ test data |
| `mcp1_mysql_update` | UPDATE data | แก้ไข data ใน table |
| `mcp1_mysql_delete` | DELETE data | ลบ data ใน table |
### การใช้งานร่วมกับ Development Flow
**เมื่อเขียน query ใหม่:**
1. ใช้ `mcp1_mysql_describe_table` เพื่อตรวจสอบ columns และ types
2. เปรียบเทียบกับ `specs/03-Data-and-Storage/lcbp3-v1.9.0-schema-02-tables.sql`
3. ใช้ `mcp1_mysql_query` เพื่อทดสอบ query ก่อน implement
**เมื่อเปลี่ยน schema (ADR-009):**
1. ใช้ `mcp1_mysql_describe_table` เพื่อดู structure ปัจจุบัน
2. สร้าง SQL delta ใน `specs/03-Data-and-Storage/deltas/`
3. ใช้ `mcp1_mysql_query` เพื่อตรวจสอบผลลัพธ์หลัง apply delta
**เมื่อ debug ปัญหา database:**
1. ใช้ `mcp1_mysql_query` เพื่อดู data จริง
2. เปรียบเทียบกับ spec และ data dictionary
3. ตรวจสอบ foreign keys และ constraints
### ข้อควรระวัง
- **❌ ห้ามใช้ MCP MariaDB สำหรับ DDL operations** (CREATE/ALTER/DROP) โดยตรง — ต้องใช้ SQL delta ตาม ADR-009
- **✅ ใช้สำหรับ DQL/DML operations** (SELECT/INSERT/UPDATE/DELETE) เพื่อ debug และ test เท่านั้น
- **⚠️ ระวัง DELETE operations** — อาจทำให้เสีย data ใน production
- **✅ ตรวจสอบ schema กับ spec file เสมอ** ก่อนเขียน query
---
## 🧠 MCP Memory Tools
MCP Memory server ให้เครื่องมือสำหรับจัดการ Knowledge Graph และ Long-term Memory ใช้สำหรับ:
- จัดเก็บความรู้และ context ของโปรเจกต์ในรูปแบบ Graph (Entities + Relations + Observations)
- ค้นหาและดึงข้อมูล context จาก memory ที่บันทึกไว้ใน session ก่อนหน้า
- สร้าง/แก้ไข/ลบ entities, relations, และ observations ใน knowledge graph
### Available Tools
| Tool | หน้าที่ | ตัวอย่างการใช้งาน |
|------|----------|------------------|
| `mcp3_create_entities` | สร้าง entities ใหม่หลายตัวพร้อม observations | สร้าง entity ใหม่เช่น Project, User, Task |
| `mcp3_create_relations` | สร้าง relations ระหว่าง entities | สร้าง relation: Project → has → User |
| `mcp3_add_observations` | เพิ่ม observations ให้ entity ที่มีอยู่แล้ว | เพิ่ม context เพิ่มเติมให้ entity |
| `mcp3_delete_entities` | ลบ entities และ relations ที่เกี่ยวข้อง | ลบ entity ที่ไม่ใช้แล้ว |
| `mcp3_delete_relations` | ลบ relations ระหว่าง entities | ลบ relation ที่ผิดหรือไม่ใช้แล้ว |
| `mcp3_delete_observations` | ลบ observations จาก entity | ลบ context ที่ผิดหรือล้าสุด |
| `mcp3_open_nodes` | ดึงข้อมูล entities ตามชื่อ | ดึง entity ที่ระบุชื่อ |
| `mcp3_read_graph` | อ่าน knowledge graph ทั้งหมด | ดูทั้ง graph structure |
| `mcp3_search_nodes` | ค้นหา entities ตาม query | ค้นหา entity จากชื่อ, type, หรือ observation |
### การใช้งานร่วมกับ Development Flow
**เมื่อบันทึก context ใหม่:**
1. ใช้ `mcp3_create_entities` เพื่อสร้าง entities ใหม่ (ถ้ายังไม่มี)
2. ใช้ `mcp3_create_relations` เพื่อเชื่อมโยง entities
3. ใช้ `mcp3_add_observations` เพื่อเพิ่ม context/observations
**เมื่อค้นหา context:**
1. ใช้ `mcp3_search_nodes` เพื่อค้นหา entities ที่เกี่ยวข้อง
2. ใช้ `mcp3_open_nodes` เพื่อดึงข้อมูล entities ที่ต้องการ
3. ใช้ `mcp3_read_graph` เพื่อดู relations ระหว่าง entities
**เมื่อแก้ไข context:**
1. ใช้ `mcp3_add_observations` เพื่อเพิ่ม observations ใหม่
2. ใช้ `mcp3_delete_observations` เพื่อลบ observations ที่ผิด
3. ใช้ `mcp3_create_relations` หรือ `mcp3_delete_relations` เพื่อปรับ relations
### ข้อควรระวัง
- **✅ ใช้สำหรับบันทึก context ที่ต้องใช้ร่วมกันหลาย session** — เช่น การตัดสินใจสำคัญ, architecture decisions, rollout history
- **⚠️ ระวังการลบ entities** — อาจทำให้เสีย context ที่ยังใช้งานอยู่
- **✅ ตรวจสอบว่า entity มีอยู่แล้วก่อนสร้าง** — ใช้ `mcp3_search_nodes` หรือ `mcp3_open_nodes` ก่อน
- **✅ ใช้ชื่อ entity ที่ชัดเจนและไม่ซ้ำกัน** — เพื่อป้องกันความสับสน
+100 -1
View File
@@ -1,7 +1,7 @@
# NAP-DMS Project Context & Rules
- For: Windsurf Cascade (and compatible: Codex CLI, opencode, Amp, Antigravity, AGENTS.md tools)
- Version: 1.9.9 | Last synced from repo: 2026-06-03
- Version: 1.9.10 | Last synced from repo: 2026-06-06
- Repo: [https://git.np-dms.work/np-dms/lcbp3](https://git.np-dms.work/np-dms/lcbp3)
- Skill pack: `.agents/skills/` (v1.9.0, 21 skills) — see [`skills/README.md`](./.agents/skills/README.md) + [`skills/_LCBP3-CONTEXT.md`](./.agents/skills/_LCBP3-CONTEXT.md)
@@ -501,6 +501,104 @@ When user asks about... check these files:
- 🔄 In development
- ❌ Not yet started
---
## 🔌 MCP MariaDB Tools
MCP MariaDB server ให้เครื่องมือสำหรับตรวจสอบและจัดการ database โดยตรง ใช้สำหรับ:
- ตรวจสอบ schema กับ spec file `specs/03-Data-and-Storage/lcbp3-v1.9.0-schema-02-tables.sql`
- Debug ปัญหา database โดยไม่ต้องเข้า MySQL client
- ตรวจสอบ data ใน production/staging
- Validate การเปลี่ยนแปลง schema ก่อน deploy
### Available Tools
| Tool | หน้าที่ | ตัวอย่างการใช้งาน |
|------|----------|------------------|
| `mcp1_mysql_test_connection` | ทดสอบ connection กับ database | ตรวจสอบว่า MCP server เชื่อมต่อได้ |
| `mcp1_mysql_show_databases` | แสดง databases ทั้งหมด | ดูว่ามี database อะไรบ้าง |
| `mcp1_mysql_show_tables` | แสดง tables ทั้งหมดใน database | ดูรายชื่อ tables ใน `lcbp3` |
| `mcp1_mysql_describe_table` | ดู structure/columns ของ table | ตรวจสอบ columns, types, keys ของ `correspondences` |
| `mcp1_mysql_query` | รัน SELECT query | ดู data ใน table หรือ join query |
| `mcp1_mysql_insert` | INSERT data | เพิ่ม seed data หรือ test data |
| `mcp1_mysql_update` | UPDATE data | แก้ไข data ใน table |
| `mcp1_mysql_delete` | DELETE data | ลบ data ใน table |
### การใช้งานร่วมกับ Development Flow
**เมื่อเขียน query ใหม่:**
1. ใช้ `mcp1_mysql_describe_table` เพื่อตรวจสอบ columns และ types
2. เปรียบเทียบกับ `specs/03-Data-and-Storage/lcbp3-v1.9.0-schema-02-tables.sql`
3. ใช้ `mcp1_mysql_query` เพื่อทดสอบ query ก่อน implement
**เมื่อเปลี่ยน schema (ADR-009):**
1. ใช้ `mcp1_mysql_describe_table` เพื่อดู structure ปัจจุบัน
2. สร้าง SQL delta ใน `specs/03-Data-and-Storage/deltas/`
3. ใช้ `mcp1_mysql_query` เพื่อตรวจสอบผลลัพธ์หลัง apply delta
**เมื่อ debug ปัญหา database:**
1. ใช้ `mcp1_mysql_query` เพื่อดู data จริง
2. เปรียบเทียบกับ spec และ data dictionary
3. ตรวจสอบ foreign keys และ constraints
### ข้อควรระวัง
- **❌ ห้ามใช้ MCP MariaDB สำหรับ DDL operations** (CREATE/ALTER/DROP) โดยตรง — ต้องใช้ SQL delta ตาม ADR-009
- **✅ ใช้สำหรับ DQL/DML operations** (SELECT/INSERT/UPDATE/DELETE) เพื่อ debug และ test เท่านั้น
- **⚠️ ระวัง DELETE operations** — อาจทำให้เสีย data ใน production
- **✅ ตรวจสอบ schema กับ spec file เสมอ** ก่อนเขียน query
---
## 🧠 MCP Memory Tools
MCP Memory server ให้เครื่องมือสำหรับจัดการ Knowledge Graph และ Long-term Memory ใช้สำหรับ:
- จัดเก็บความรู้และ context ของโปรเจกต์ในรูปแบบ Graph (Entities + Relations + Observations)
- ค้นหาและดึงข้อมูล context จาก memory ที่บันทึกไว้ใน session ก่อนหน้า
- สร้าง/แก้ไข/ลบ entities, relations, และ observations ใน knowledge graph
### Available Tools
| Tool | หน้าที่ | ตัวอย่างการใช้งาน |
|------|----------|------------------|
| `mcp3_create_entities` | สร้าง entities ใหม่หลายตัวพร้อม observations | สร้าง entity ใหม่เช่น Project, User, Task |
| `mcp3_create_relations` | สร้าง relations ระหว่าง entities | สร้าง relation: Project → has → User |
| `mcp3_add_observations` | เพิ่ม observations ให้ entity ที่มีอยู่แล้ว | เพิ่ม context เพิ่มเติมให้ entity |
| `mcp3_delete_entities` | ลบ entities และ relations ที่เกี่ยวข้อง | ลบ entity ที่ไม่ใช้แล้ว |
| `mcp3_delete_relations` | ลบ relations ระหว่าง entities | ลบ relation ที่ผิดหรือไม่ใช้แล้ว |
| `mcp3_delete_observations` | ลบ observations จาก entity | ลบ context ที่ผิดหรือล้าสุด |
| `mcp3_open_nodes` | ดึงข้อมูล entities ตามชื่อ | ดึง entity ที่ระบุชื่อ |
| `mcp3_read_graph` | อ่าน knowledge graph ทั้งหมด | ดูทั้ง graph structure |
| `mcp3_search_nodes` | ค้นหา entities ตาม query | ค้นหา entity จากชื่อ, type, หรือ observation |
### การใช้งานร่วมกับ Development Flow
**เมื่อบันทึก context ใหม่:**
1. ใช้ `mcp3_create_entities` เพื่อสร้าง entities ใหม่ (ถ้ายังไม่มี)
2. ใช้ `mcp3_create_relations` เพื่อเชื่อมโยง entities
3. ใช้ `mcp3_add_observations` เพื่อเพิ่ม context/observations
**เมื่อค้นหา context:**
1. ใช้ `mcp3_search_nodes` เพื่อค้นหา entities ที่เกี่ยวข้อง
2. ใช้ `mcp3_open_nodes` เพื่อดึงข้อมูล entities ที่ต้องการ
3. ใช้ `mcp3_read_graph` เพื่อดู relations ระหว่าง entities
**เมื่อแก้ไข context:**
1. ใช้ `mcp3_add_observations` เพื่อเพิ่ม observations ใหม่
2. ใช้ `mcp3_delete_observations` เพื่อลบ observations ที่ผิด
3. ใช้ `mcp3_create_relations` หรือ `mcp3_delete_relations` เพื่อปรับ relations
### ข้อควรระวัง
- **✅ ใช้สำหรับบันทึก context ที่ต้องใช้ร่วมกันหลาย session** — เช่น การตัดสินใจสำคัญ, architecture decisions, rollout history
- **⚠️ ระวังการลบ entities** — อาจทำให้เสีย context ที่ยังใช้งานอยู่
- **✅ ตรวจสอบว่า entity มีอยู่แล้วก่อนสร้าง** — ใช้ `mcp3_search_nodes` หรือ `mcp3_open_nodes` ก่อน
- **✅ ใช้ชื่อ entity ที่ชัดเจนและไม่ซ้ำกัน** — เพื่อป้องกันความสับสน
---
## 🛠️ Final Checklists
### 🔴 Tier 1 — CRITICAL (CI BLOCKER)
@@ -613,6 +711,7 @@ This file is a **quick reference**. For detailed information:
| Version | Date | Changes | Updated By |
| ------- | ---------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | -------------- |
| 1.9.10 | 2026-06-06 | Added MCP MariaDB Tools section with available tools (test_connection, show_databases, show_tables, describe_table, query, insert, update, delete), usage guidelines for development flow, and safety warnings for DDL operations; Added MCP Memory Tools section with Knowledge Graph management tools (create_entities, create_relations, add_observations, delete_entities, delete_relations, delete_observations, open_nodes, read_graph, search_nodes) for long-term context storage | Windsurf AI |
| 1.9.9 | 2026-06-03 | ADR-034 Thai-Optimized AI Model Stack: typhoon2.5-np-dms:latest (main) + typhoon-np-dms-ocr:latest (OCR); model switching in ai-batch processor; AiSettingsService static constants; SQL delta; updated Key Spec Files + AI isolation rule | Windsurf AI |
| 1.9.8 | 2026-06-02 | Added ADR-033 Active Model & OCR Runner Management; implemented Synchronous LLM switches, GPU Memory Auto-release, sidecar `X-API-Key` headers protection; updated Key Spec Files & Specialized Work AI runtime sections | Windsurf AI |
| 1.9.7 | 2026-05-25 | Added ADR-029 Dynamic Prompt Management to Key Spec Files table; fixed gemma4 model name e2b→e4b Q8_0; added Dynamic Prompt context trigger; added ADR-029 to Tier 3 AI checklist; bumped last synced date | Windsurf AI |
@@ -10,6 +10,7 @@
// - 2026-05-26: แก้ไข bug lockDuration=30000ms ทำให้ sandbox-extract job stall เมื่อ Ollama ใช้เวลา >30s — เพิ่ม lockDuration: 150000
// - 2026-05-28: EC-001 ใช้ findOrSuggestTags เพื่อตรวจจับ Tag ใหม่และบันทึก aiIssues; EC-002 ตรวจสอบ UUID ของผู้ส่ง/ผู้รับ และ Flag เมื่อหาไม่พบ
// - 2026-06-03: ADR-034 — เพิ่ม 'ocr-extract' job type + OCR_JOB_TYPES constant + processOcrExtract() ที่มี model switching logic (unload main → load OCR → generate → reload main)
// - 2026-06-06: แก้ไข bug LLM JSON parse failure — เพิ่ม retry logic (2 attempts), debug log raw response, และปรับปรุง error message ให้แสดงทั้ง raw และ cleaned response
import { Processor, WorkerHost } from '@nestjs/bullmq';
import { Logger } from '@nestjs/common';
@@ -430,19 +431,40 @@ export class AiBatchProcessor extends WorkerHost {
const response = await this.ollamaService.generate(resolvedPrompt, {
timeoutMs: 120000,
});
this.logger.debug(`Raw LLM response: ${response}`);
const cleanedResponse = response
.replace(/```json/g, '')
.replace(/```/g, '')
.trim();
let extractedMetadata: Record<string, unknown>;
try {
extractedMetadata = JSON.parse(cleanedResponse) as Record<
string,
unknown
>;
} catch {
let extractedMetadata: Record<string, unknown> | null = null;
let parseAttempts = 0;
const maxParseAttempts = 2;
while (parseAttempts < maxParseAttempts) {
try {
extractedMetadata = JSON.parse(cleanedResponse) as Record<
string,
unknown
>;
break;
} catch {
parseAttempts++;
if (parseAttempts >= maxParseAttempts) {
this.logger.error(
`Failed to parse LLM response as JSON after ${maxParseAttempts} attempts. Raw: ${response}, Cleaned: ${cleanedResponse}`
);
throw new Error(
`Failed to parse LLM response as JSON after ${maxParseAttempts} attempts. Raw: ${response.substring(0, 200)}, Cleaned: ${cleanedResponse.substring(0, 200)}`
);
}
this.logger.warn(
`JSON parse attempt ${parseAttempts} failed, retrying...`
);
await new Promise((resolve) => setTimeout(resolve, 1000));
}
}
if (!extractedMetadata) {
throw new Error(
`Failed to parse LLM response as JSON: ${cleanedResponse}`
`Failed to parse LLM response as JSON after ${maxParseAttempts} attempts`
);
}
await this.aiPromptsService.saveTestResult(
@@ -625,20 +647,41 @@ export class AiBatchProcessor extends WorkerHost {
timeoutMs: 120000,
});
this.logger.debug(`Raw LLM response: ${response}`);
const cleanedResponse = response
.replace(/```json/g, '')
.replace(/```/g, '')
.trim();
let extractedMetadata: Record<string, unknown>;
try {
extractedMetadata = JSON.parse(cleanedResponse) as Record<
string,
unknown
>;
} catch {
let extractedMetadata: Record<string, unknown> | null = null;
let parseAttempts = 0;
const maxParseAttempts = 2;
while (parseAttempts < maxParseAttempts) {
try {
extractedMetadata = JSON.parse(cleanedResponse) as Record<
string,
unknown
>;
break;
} catch {
parseAttempts++;
if (parseAttempts >= maxParseAttempts) {
this.logger.error(
`Failed to parse LLM response as JSON after ${maxParseAttempts} attempts. Raw: ${response}, Cleaned: ${cleanedResponse}`
);
throw new Error(
`Failed to parse LLM response as JSON after ${maxParseAttempts} attempts. Raw: ${response.substring(0, 200)}, Cleaned: ${cleanedResponse.substring(0, 200)}`
);
}
this.logger.warn(
`JSON parse attempt ${parseAttempts} failed, retrying...`
);
await new Promise((resolve) => setTimeout(resolve, 1000));
}
}
if (!extractedMetadata) {
throw new Error(
`Failed to parse LLM response as JSON: ${cleanedResponse}`
`Failed to parse LLM response as JSON after ${maxParseAttempts} attempts`
);
}
+100 -2
View File
@@ -16,8 +16,10 @@
- 2026-06-03: Thai-Optimized AI Model Stack (ADR-034) — เปลี่ยนโมเดลหลักเป็น `typhoon2.5-np-dms:latest` + `typhoon-np-dms-ocr:latest` (สำหรับ OCR, keep_alive:0); เพิ่ม model switching logic ใน ai-batch processor; เพิ่ม static constants ใน AiSettingsService; สร้าง SQL delta สำหรับ ai_available_models
- 2026-06-05 (Session 12): Typhoon OCR Prompt Cleaning — แก้ปัญหา prompt/instruction ติดมาใน Typhoon OCR output โดยย้าย instruction จาก Modelfile SYSTEM มา prompt ใน app.py แทน ลบ clean_typhoon_output() filter downstream และแก้ git conflict โดยเลือกเวอร์ชัน local (ไม่มี SYSTEM instruction)
- 2026-06-05 (Session 13): OCR Sandbox Step 2 AI Extraction Bug Fix — แก้ปัญหา "Not Found Exception" ใน Step 2 AI Extraction โดยเพิ่ม conditional check ใน processSandboxExtract และ processSandboxAiExtract เพื่อส่ง undefined แทน 'default' projectPublicId ไปยัง resolveContext (เพราะ 'default' ไม่ใช่ project UUID ที่ถูกต้อง). Frontend: เพิ่ม startPolling method ใน useSandboxRun hook เพื่อรองรับ 2-step flow และแก้ OcrSandboxPromptManager.tsx ให้ใช้ startPolling แทน custom polling logic. Model Switching Analysis: Production OCR Extraction มี model switching (unload main → load OCR model → run → reload main) เพื่อประหยัด VRAM แต่ Sandbox AI Extraction ไม่มี model switching เพราะใช้ main model สกัด metadata จาก OCR text ที่มาจาก Step 1 (Tesseract OCR sidecar) แล้ว ไม่ใช่ OCR model. OCR Sidecar Location: specs/04-Infrastructure-OPS/04-00-docker-compose/Desk-5439/ocr-sidecar/ (ใช้ Tesseract OCR ไม่ใช่ PaddleOCR ตั้งแต่ 2026-05-30). Model Config: เพิ่ม SYSTEM prompt ภาษาไทยใน typhoon2.5-np-dms.model.md และ typhoon2.5-np-dms.main-model.md สำหรับ LCBP3 DMS context
- 2026-06-05 (Session 14): RAG Pipeline Enhancements (Spec 234 / ADR-035) — แก้ compile blockers 4 จุดหลังเปลี่ยน contract ของ Embedding/Qdrant, เพิ่ม `projectPublicId` ใน vector deletion path, ย้าย dashboard RAG page ไป `/ai/rag/*`, ถอด legacy frontend RAG hook/components, mark legacy `/rag/*` deprecated, และสุดท้ายถอด `RagModule` + `rag.controller.ts` ออกจาก runtime พร้อมอัปเดต ADR-035
- 2026-06-05 (Session 14): RAG Pipeline Enhancements (Spec 234 / ADR-035) — แก้ compile blockers 4 จุดหลักหลังเปลี่ยน contract ของ Embedding/Qdrant, เพิ่ม `projectPublicId` ใน vector deletion path, ย้าย dashboard RAG page ไป `/ai/rag/*`, ถอด legacy frontend RAG hook/components, mark legacy `/rag/*` deprecated, และสุดท้ายถอด `RagModule` + `rag.controller.ts` ออกจาก runtime พร้อมอัปเดต ADR-035
- 2026-06-05 (Session 15): Feature 234 RAG Pipeline สมบูรณ์ — implement BGE-M3 embedding (dense 1024 + sparse), BGE-Reranker-Large, Semantic Chunking (typhoon2.5 + `<chunk topic>` tags + fallback), Hybrid Qdrant schema (drop+recreate), workflow hook `syncStatus()``enqueueRagPrepare()`, processRagPrepare pipeline ใน ai-batch.processor; แก้ CRITICAL 2 ประเด็นจาก speckit-analyze; ผ่าน speckit-tester (19/19 tests), speckit-validate (15/15 FR, ทุก SC); ปิด Gap ทั้ง 2 รายการ (jobId dedup confirmed + integration test 9 tests); สร้าง validation-report.md ใน specs/200-fullstacks/234-rag-pipeline-enhancements/
- 2026-06-06: เพิ่ม MCP MariaDB Tools section ใน memory/agent-memory.md, AGENTS.md, และ rule files (.agents/rules/08-development-flow.md, .devin/rules/08-development-flow.md) — รวม 8 tools (test_connection, show_databases, show_tables, describe_table, query, insert, update, delete), การใช้งานร่วมกับ Development Flow, และข้อควรระวังเรื่อง DDL operations
- 2026-06-06: เพิ่ม MCP Memory Tools section ใน memory/agent-memory.md — รวม 9 tools (create_entities, create_relations, add_observations, delete_entities, delete_relations, delete_observations, open_nodes, read_graph, search_nodes), การใช้งานร่วมกับ Development Flow สำหรับจัดการ Knowledge Graph และ Long-term Memory
-->
# 🧠 Agent Long-term Project Memory
@@ -218,7 +220,103 @@ QDRANT_URL
---
## 🚀 8. Recent Rollouts
## 8. MCP MariaDB Tools
MCP MariaDB server ให้เครื่องมือสำหรับตรวจสอบและจัดการ database โดยตรง ใช้สำหรับ:
- ตรวจสอบ schema กับ spec file `specs/03-Data-and-Storage/lcbp3-v1.9.0-schema-02-tables.sql`
- Debug ปัญหา database โดยไม่ต้องเข้า MySQL client
- ตรวจสอบ data ใน production/staging
- Validate การเปลี่ยนแปลง schema ก่อน deploy
### Available Tools
| Tool | หน้าที่ | ตัวอย่างการใช้งาน |
|------|----------|------------------|
| `mcp1_mysql_test_connection` | ทดสอบ connection กับ database | ตรวจสอบว่า MCP server เชื่อมต่อได้ |
| `mcp1_mysql_show_databases` | แสดง databases ทั้งหมด | ดูว่ามี database อะไรบ้าง |
| `mcp1_mysql_show_tables` | แสดง tables ทั้งหมดใน database | ดูรายชื่อ tables ใน `lcbp3` |
| `mcp1_mysql_describe_table` | ดู structure/columns ของ table | ตรวจสอบ columns, types, keys ของ `correspondences` |
| `mcp1_mysql_query` | รัน SELECT query | ดู data ใน table หรือ join query |
| `mcp1_mysql_insert` | INSERT data | เพิ่ม seed data หรือ test data |
| `mcp1_mysql_update` | UPDATE data | แก้ไข data ใน table |
| `mcp1_mysql_delete` | DELETE data | ลบ data ใน table |
### การใช้งานร่วมกับ Development Flow
**เมื่อเขียน query ใหม่:**
1. ใช้ `mcp1_mysql_describe_table` เพื่อตรวจสอบ columns และ types
2. เปรียบเทียบกับ `specs/03-Data-and-Storage/lcbp3-v1.9.0-schema-02-tables.sql`
3. ใช้ `mcp1_mysql_query` เพื่อทดสอบ query ก่อน implement
**เมื่อเปลี่ยน schema (ADR-009):**
1. ใช้ `mcp1_mysql_describe_table` เพื่อดู structure ปัจจุบัน
2. สร้าง SQL delta ใน `specs/03-Data-and-Storage/deltas/`
3. ใช้ `mcp1_mysql_query` เพื่อตรวจสอบผลลัพธ์หลัง apply delta
**เมื่อ debug ปัญหา database:**
1. ใช้ `mcp1_mysql_query` เพื่อดู data จริง
2. เปรียบเทียบกับ spec และ data dictionary
3. ตรวจสอบ foreign keys และ constraints
### ข้อควรระวัง
- **❌ ห้ามใช้ MCP MariaDB สำหรับ DDL operations** (CREATE/ALTER/DROP) โดยตรง — ต้องใช้ SQL delta ตาม ADR-009
- **✅ ใช้สำหรับ DQL/DML operations** (SELECT/INSERT/UPDATE/DELETE) เพื่อ debug และ test เท่านั้น
- **⚠️ ระวัง DELETE operations** — อาจทำให้เสีย data ใน production
- **✅ ตรวจสอบ schema กับ spec file เสมอ** ก่อนเขียน query
---
## 🧠 9. MCP Memory Tools
MCP Memory server ให้เครื่องมือสำหรับจัดการ Knowledge Graph และ Long-term Memory ใช้สำหรับ:
- จัดเก็บความรู้และ context ของโปรเจกต์ในรูปแบบ Graph (Entities + Relations + Observations)
- ค้นหาและดึงข้อมูล context จาก memory ที่บันทึกไว้ใน session ก่อนหน้า
- สร้าง/แก้ไข/ลบ entities, relations, และ observations ใน knowledge graph
### Available Tools
| Tool | หน้าที่ | ตัวอย่างการใช้งาน |
|------|----------|------------------|
| `mcp3_create_entities` | สร้าง entities ใหม่หลายตัวพร้อม observations | สร้าง entity ใหม่เช่น Project, User, Task |
| `mcp3_create_relations` | สร้าง relations ระหว่าง entities | สร้าง relation: Project → has → User |
| `mcp3_add_observations` | เพิ่ม observations ให้ entity ที่มีอยู่แล้ว | เพิ่ม context เพิ่มเติมให้ entity |
| `mcp3_delete_entities` | ลบ entities และ relations ที่เกี่ยวข้อง | ลบ entity ที่ไม่ใช้แล้ว |
| `mcp3_delete_relations` | ลบ relations ระหว่าง entities | ลบ relation ที่ผิดหรือไม่ใช้แล้ว |
| `mcp3_delete_observations` | ลบ observations จาก entity | ลบ context ที่ผิดหรือล้าสุด |
| `mcp3_open_nodes` | ดึงข้อมูล entities ตามชื่อ | ดึง entity ที่ระบุชื่อ |
| `mcp3_read_graph` | อ่าน knowledge graph ทั้งหมด | ดูทั้ง graph structure |
| `mcp3_search_nodes` | ค้นหา entities ตาม query | ค้นหา entity จากชื่อ, type, หรือ observation |
### การใช้งานร่วมกับ Development Flow
**เมื่อบันทึก context ใหม่:**
1. ใช้ `mcp3_create_entities` เพื่อสร้าง entities ใหม่ (ถ้ายังไม่มี)
2. ใช้ `mcp3_create_relations` เพื่อเชื่อมโยง entities
3. ใช้ `mcp3_add_observations` เพื่อเพิ่ม context/observations
**เมื่อค้นหา context:**
1. ใช้ `mcp3_search_nodes` เพื่อค้นหา entities ที่เกี่ยวข้อง
2. ใช้ `mcp3_open_nodes` เพื่อดึงข้อมูล entities ที่ต้องการ
3. ใช้ `mcp3_read_graph` เพื่อดู relations ระหว่าง entities
**เมื่อแก้ไข context:**
1. ใช้ `mcp3_add_observations` เพื่อเพิ่ม observations ใหม่
2. ใช้ `mcp3_delete_observations` เพื่อลบ observations ที่ผิด
3. ใช้ `mcp3_create_relations` หรือ `mcp3_delete_relations` เพื่อปรับ relations
### ข้อควรระวัง
- **✅ ใช้สำหรับบันทึก context ที่ต้องใช้ร่วมกันหลาย session** — เช่น การตัดสินใจสำคัญ, architecture decisions, rollout history
- **⚠️ ระวังการลบ entities** — อาจทำให้เสีย context ที่ยังใช้งานอยู่
- **✅ ตรวจสอบว่า entity มีอยู่แล้วก่อนสร้าง** — ใช้ `mcp3_search_nodes` หรือ `mcp3_open_nodes` ก่อน
- **✅ ใช้ชื่อ entity ที่ชัดเจนและไม่ซ้ำกัน** — เพื่อป้องกันความสับสน
---
## 🚀 10. Recent Rollouts
| วันที่ | Version | รายการ | สถานะ |
| ---------- | ------- | ---------------------------------------------------------------------------------------------------- | ----------------------------- |
@@ -1,11 +1,18 @@
FROM scb10x/typhoon2.5-qwen3-4b:latest
PARAMETER num_ctx 8192
PARAMETER num_predict 4096
PARAMETER temperature 0.4
PARAMETER top_k 40
PARAMETER top_p 0.9
PARAMETER repeat_penalty 1.15
SYSTEM """You are an AI system specialized in analyzing and managing project documents (Document Management System)
Your role is to carefully read Thai text extracted from OCR systems and follow these instructions strictly:
Guidelines:
- Input is raw OCR text which may contain spelling errors, missing lines, or noise characters
- Extract and identify 'Document Number' and 'Document Date' accurately. If not found, mark as 'Not Specified'
- Summarize the key content of this document concisely and clearly, using overall context for interpretation. If uncertain, mark status as "Unclear"
- Do NOT create or hallucinate data that does not exist in the original text
- Do NOT guess numbers, dates, or any information not explicitly visible in the raw text
- If information is incomplete, use null and provide reason in the _missing_fields field
Return ONLY the specified JSON structure. Do NOT add any text outside the structure"""
SYSTEM """คุณเป็นระบบ AI ผู้เชี่ยวชาญด้านการตอบคำถามเกี่ยวกับเอกสารการก่อสร้าง (LCBP3 DMS)
@@ -1,21 +0,0 @@
FROM scb10x/typhoon2.5-qwen3-4b:latest
PARAMETER num_ctx 8192
PARAMETER num_predict 4096
PARAMETER temperature 0.1
PARAMETER top_p 0.85
PARAMETER repeat_penalty 1.15
SYSTEM """You are an AI system specialized in analyzing and managing project documents (Document Management System)
Your role is to carefully read Thai text extracted from OCR systems and follow these instructions strictly:
Guidelines:
- Input is raw OCR text which may contain spelling errors, missing lines, or noise characters
- Extract and identify 'Document Number' and 'Document Date' accurately. If not found, mark as 'Not Specified'
- Summarize the key content of this document concisely and clearly, using overall context for interpretation. If uncertain, mark status as "Unclear"
- Do NOT create or hallucinate data that does not exist in the original text
- Do NOT guess numbers, dates, or any information not explicitly visible in the raw text
- If information is incomplete, use null and provide reason in the _missing_fields field
Return ONLY the specified JSON structure. Do NOT add any text outside the structure"""
@@ -1,19 +1,8 @@
FROM scb10x/typhoon2.5-qwen3-4b:latest
PARAMETER num_ctx 8192
PARAMETER num_ctx 12288
PARAMETER num_predict 4096
PARAMETER temperature 0.4
PARAMETER top_k 40
PARAMETER top_p 0.9
PARAMETER repeat_penalty 1.15
SYSTEM """คุณเป็นระบบ AI ผู้เชี่ยวชาญด้านการตอบคำถามเกี่ยวกับเอกสารการก่อสร้าง (LCBP3 DMS)
หน้าที่: ตอบคำถามของผู้ใช้โดยอ้างอิงจากเอกสารที่เกี่ยวข้อง
Guidelines:
1. อ้างอิงเลขที่เอกสาร และวันที่ของแหล่งข้อมูลทุกครั้ง
2. หากข้อมูลไม่ชัดเจนหรือไม่ครบถ้วน ให้ระบุความไม่แน่นอน
3. ตอบเป็นภาษาไทยที่เข้าใจง่าย โดยเน้นความถูกต้องเหนือการสร้างสรรค์
4. หากไม่พบข้อมูลที่เกี่ยวข้อง ให้บอกว่า "ไม่พบข้อมูลในเอกสาร"
5. ให้สรุปสั้นๆ แต่ครอบคลุมคำถาม"""
-164
View File
@@ -1,164 +0,0 @@
เพื่อให้สถาปัตยกรรม RAG สำหรับระบบ DMS ของคุณใช้งานได้จริงและมีประสิทธิภาพสูงสุด นี่คือ **รายละเอียดการ Implementation พร้อมตัวอย่างการตั้งค่า (Configuration)** ในแต่ละส่วน โดยอิงจากการใช้ Python เป็นหลักในการควบคุม Pipeline ครับ
## 1. Ingestion & Semantic Chunking Pipeline (Typhoon OCR + Typhoon 2.5)
ในขั้นตอนนี้ เราจะรับไฟล์เอกสาร นำเข้าสู่ OCR และส่งข้อความดิบให้ Typhoon 2.5 จัดโครงสร้างโดยใส่ <chunk> tag เพื่อนำมาตัดแบ่งเนื้อหาตามบริบทจริง
### ตัวอย่าง Prompt สำหรับ Typhoon 2.5 (รอบแรก) เพื่อใส่ Tag
```text
คุณคือผู้เชี่ยวชาญด้านการจัดการเอกสาร (DMS Editor)
หน้าที่ของคุณคือรับข้อความดิบจากระบบ OCR แล้วนำมาจัดโครงสร้างใหม่ให้อยู่ในรูปแบบ Markdown
เงื่อนไขสำคัญ:
1. ห้ามแก้ไข ตัดทอน หรือบิดเบือนข้อความสำคัญในเอกสาร
2. ให้วิเคราะห์เนื้อหา และแบ่งเนื้อหาออกเป็นส่วนๆ (Semantic Chunks) โดยใช้ Tag พิเศษ ครอบเนื้อหาที่เป็นเรื่องเดียวกันไว้ ดังนี้:
<chunk topic="หัวข้อหลักของเนื้อหาใน tag นี้"> ...ข้อความ... </chunk>
3. หากมีข้อมูลสำคัญ เช่น เลขที่เอกสาร, วันที่, ชื่อบุคคล หรือเรื่อง ให้สกัดออกมาในรูปแบบของ Metadata ไว้ที่ส่วนบนสุดของเอกสารด้วยโครงสร้าง JSON ใน Tag <metadata>...</metadata>
```
### Python Implementation (การตัด Chunk จาก Tag)
```python
import re
import json
# สมมติผลลัพธ์ที่ได้มาจาก Typhoon 2.5 รอบแรก
typhoon_output = """
<metadata>
{
"doc_number": "REQ-009",
"date": "2026-06-05",
"subject": "ขออนุมัติจัดซื้ออุปกรณ์เครือข่ายสำหรับโครงการ"
}
</metadata>
<chunk topic="วัตถุประสงค์และหลักการ">
เนื่องด้วยระบบเครือข่ายเดิมในสำนักงานสนามมีความเร็วไม่เพียงพอต่อการใช้งาน...
</chunk>
<chunk topic="รายการอุปกรณ์ที่ต้องการจัดซื้อ">
1. Managed Switch 24-Port 2.5GbE จำนวน 1 ตัว
2. Core Router ER7206 จำนวน 1 ตัว
</chunk>
"""
def parse_typhoon_chunks(output):
# สกัด Metadata
metadata_match = re.search(r'<metadata>(.*?)</metadata>', output, re.DOTALL)
metadata = json.loads(metadata_match.group(1).strip()) if metadata_match else {}
# สกัด Chunks
chunk_pattern = r'<chunk topic="(.*?)">(.*?)</chunk>'
chunks = re.findall(chunk_pattern, output, re.DOTALL)
processed_chunks = []
for topic, content in chunks:
processed_chunks.append({
"text": content.strip(),
"metadata": {
**metadata,
"chunk_topic": topic
}
})
return processed_chunks
chunks_to_embed = parse_typhoon_chunks(typhoon_output)
```
## 2. Vector Storage & Search Setup (BGE-M3 + Qdrant)
BGE-M3 สามารถทำ **Hybrid Search** ได้ดีมาก (Dense Vector แทนความหมายเชิงลึก + Sparse Vector แทนคำสำคัญ/Keyword) เราจะตั้งค่า Qdrant Collection ให้รองรับทั้งสองแบบเพื่อป้องกันปัญหาคำค้นหาเฉพาะ (เช่น เลขที่เอกสาร หรือรหัสพัสดุ) หลุดหาย
### ตัวอย่างการตั้งค่า Qdrant Collection (Python Client)
```python
from qdrant_client import QdrantClient
from qdrant_client.models import Distance, VectorParams, SparseVectorParams, OptimizersConfigDiff
client = QdrantClient(url="http://localhost:6333")
# สร้าง Collection ที่รองรับทั้ง Dense และ Sparse (Hybrid)
client.create_collection(
collection_name="dms_documents",
vectors_config={
# Dense Vector สำหรับ BGE-M3 (ขนาด 1024 มิติ)
"bge_dense": VectorParams(
size=1024,
distance=Distance.COSINE
)
},
sparse_vectors_config={
# Sparse Vector สำหรับทำ Keyword Matching จาก BGE-M3
"bge_sparse": SparseVectorParams()
},
# เปิดใช้งาน Payload Index สำหรับ Metadata Filtering (เช่น ค้นหาเฉพาะเลขที่เอกสาร)
optimizers_config=OptimizersConfigDiff(memmap_threshold=20000)
)
```
## 3. Retrieval & Re-ranking Pipeline (Qdrant Search + BGE-Reranker)
เมื่อผู้ใช้ส่งคำถามเข้ามา เราจะดึงข้อมูลแบบ Hybrid จาก Qdrant ออกมาจำนวนหนึ่ง (เช่น 15 Chunks) แล้วใช้ **BGE-Reranker** สแกนซ้ำเพื่อเลือกตัวที่ใช่ที่สุด 3-5 อันดับแรก
### Python Implementation สำหรับ Hybrid Search และ Rerank
```python
from sentence_transformers import SentenceTransformer
from transformers import AutoModelForSequenceClassification, AutoTokenizer
import torch
# 1. โหลดโมเดลสำหรับ Embedding และ Reranking
# (ในงานจริงแนะนำให้ Host เป็น API แยก เช่น Tei หรือใช้ Local Inference)
embedding_model = SentenceTransformer('BAAI/bge-m3')
rerank_tokenizer = AutoTokenizer.from_pretrained('BAAI/bge-reranker-large')
rerank_model = AutoModelForSequenceClassification.from_pretrained('BAAI/bge-reranker-large')
rerank_model.eval()
def hybrid_search_and_rerank(query, top_k_qdrant=15, top_k_final=3):
# ก้าวที่ 1: แปลง Query เป็น Vector
query_dense_vector = embedding_model.encode(query).tolist()
# ก้าวที่ 2: ดึงข้อมูลจาก Qdrant (สมมติเรียกใช้ client.search)
# *ในจุดนี้สามารถใส่ Filter สำหรับเจาะจงเลขเอกสารหรือวันที่ได้จาก Payload*
qdrant_results = client.search(
collection_name="dms_documents",
query_vector=("bge_dense", query_dense_vector),
limit=top_k_qdrant
)
# ก้าวที่ 3: เตรียมข้อมูลเข้า Reranker
pairs = [[query, res.payload['text']] for res in qdrant_results]
with torch.no_grad():
inputs = rerank_tokenizer(pairs, padding=True, truncation=True, return_tensors='pt', max_length=512)
scores = rerank_model(**inputs).logits.view(-1).tolist()
# ก้าวที่ 4: ประกบคะแนนใหม่และจัดเรียงลำดับ
reranked_results = []
for i, res in enumerate(qdrant_results):
reranked_results.append({
"text": res.payload['text'],
"metadata": res.payload['metadata'],
"rerank_score": scores[i]
})
# เรียงจากคะแนนมากไปน้อย
reranked_results.sort(key=lambda x: x['rerank_score'], reverse=True)
# ส่งคืนเฉพาะ Top K ที่ดีที่สุดไปให้ LLM
return reranked_results[:top_k_final]
```
## 4. Generation Pipeline (Typhoon 2.5 รอบสุดท้าย)
นำ Chunks ที่ผ่านการ Rerank มาเรียงต่อกันเป็น Context เพื่อให้ Typhoon 2.5 ตอบคำถาม โดยเน้นย้ำให้โมเดลตอบตามข้อเท็จจริงในเอกสารเท่านั้น
### ตัวอย่างการประกอบ System Prompt และ Prompt template
```text
System Prompt:
คุณคือผู้ช่วยอัจฉริยะประจำระบบจัดการเอกสาร (DMS AI Assistant)
หน้าที่ของคุณคือตอบคำถามของผู้ใช้โดยใช้ข้อมูลจาก "Context เอกสารที่กำหนดให้" เท่านั้น
ห้ามใช้ความรู้ภายนอกที่ไม่มีในเอกสารตอบโดยเด็ดขาด
หากใน Context ไม่มีข้อมูลที่ตอบคำถามได้ ให้แจ้งผู้ใช้ตรงๆ ว่า "ไม่พบข้อมูลดังกล่าวในเอกสาร"
และโปรดอ้างอิง เลขที่เอกสาร (doc_number) ทุกครั้งที่ตอบคำถามเพื่อความน่าเชื่อถือ
----------------
Context เอกสารที่ค้นพบ:
[ข้อความจาก Chunk ที่ 1] (อ้างอิง: REQ-009)
[ข้อความจาก Chunk ที่ 2] (อ้างอิง: REQ-009)
----------------
คำถามของผู้ใช้:
อุปกรณ์เครือข่ายที่ขออนุมัติจัดซื้อในเอกสาร REQ-009 มีอะไรบ้างและใช้ที่ไหน?
```
### 🛠️ คำแนะนำเพิ่มเติมสำหรับการดูแลระบบ (Ops & Infrastructure)
1. **การลด Latency ของ Reranker:** เนื่องจาก Reranker ต้องคำนวณ Cross-Attention ทุกครั้งที่ค้นหา หากรันบน CPU อาจจะช้า (ประมาณ 1-2 วินาทีต่อการ Query) แนะนำให้รันบน **GPU** หรือเลือกใช้โมเดลย่อส่วนอย่าง bge-reranker-base เพื่อทำความเร็วให้ตอบรับกับระบบ DMS ที่มีผู้ใช้งานพร้อมกันจำนวนมาก
2. **การทำ Document Version Control (Void & Replace):** ในระบบ DMS เมื่อเอกสารมีการแก้ไข (เช่น ออกเวอร์ชันใหม่ของ REQ-009) อย่าลืมส่ง Metadata version หรือรันคำสั่ง **Delete Points** ใน Qdrant โดยกรองจาก doc_number เก่าออกไปก่อน เพื่อไม่ให้ระบบดึงเอาข้อความจากเอกสารเวอร์ชันเก่าขึ้นมาตอบปนกับเวอร์ชันปัจจุบันครับ
3.