การสร้าง Knowledge Graph หนึ่งเดียวจาก 46 Repositories
ผม Ryan เป็น CTO ที่ airCloset
ผมใช้เวลาสามเดือนในการสร้าง code-graph ซึ่งเป็น knowledge graph หนึ่งเดียวที่รวบรวม 46 repositories จากหลากหลายบริการเข้าด้วยกัน
หลายคนคิดว่าคุณสามารถส่งโค้ดทั้งหมดให้ AI แล้วถามคำถามได้เลย แต่วิธีนี้ล้มเหลวด้วยเหตุผลสองประการ:
- Context windows: คุณไม่สามารถใส่โค้ดที่สะสมมาหลายปีจาก 46 repos ลงใน prompt เดียวได้
- Hallucination: AI มักจะทำผิดพลาดเมื่อพยายามอนุมานความสัมพันธ์ และอาจมองข้ามการเชื่อมต่อต่างๆ ไป
เพื่อแก้ปัญหานี้ ผมจึงใช้ static analysis เพื่อสร้างแหล่งข้อมูลที่ถูกต้องแม่นยำ (source of truth)
ความท้าทาย: การข้ามขอบเขต (Crossing Boundaries)
Codebase ขนาดใหญ่ย่อมมีความซับซ้อน API หนึ่งตัวอาจถูกเรียกใช้งานจาก 5 repositories ที่แตกต่างกัน หรือตารางในฐานข้อมูลหนึ่งอาจถูกใช้งานโดย 3 services ที่ต่างกัน
หากคุณดูเพียง repository เดียว คุณจะมองไม่เห็นภาพรวมทั้งหมด ซึ่งเป็นเรื่องอันตราย หากคุณแก้ไขโค้ดโดยไม่เห็นขอบเขตผลกระทบ (blast radius) ที่แท้จริง คุณอาจทำให้ระบบพังได้
แนวทางของผมคือการใช้ tree-sitter เพื่อ parse โค้ดให้เป็น syntax trees แต่ลำพังแค่ tree-sitter ไม่สามารถมองเห็นข้ามขอบเขตของ repository ได้
ผมจึงสร้าง boundary nodes ขึ้นมาเพื่อแก้ปัญหานี้
วิธีการทำงาน:
- เราดึงความสัมพันธ์ภายใน repo โดยใช้ tree-sitter
- เราใช้ TypeScript Compiler API เพื่อจัดการเรื่อง types และ variables
- เราใช้ Gemini เพื่อจัดการกับกรณีที่เป็น dynamic ซึ่งเครื่องมืออื่นๆ อาจมองข้ามไป
แทนที่จะให้ AI เดา เราให้ข้อเท็จจริงแก่ตัวมันแทน โดยเราจะบอกมันว่า: "API นี้ถูกเรียกใช้งานจาก Repo X ด้วยเช่นกัน" วิธีนี้จะช่วยป้องกันการเกิด hallucination
ส่วนที่ยากที่สุด: ความหลากหลายของ Framework (The Framework Zoo)
การต่อสู้ที่แท้จริงคือการดึงขอบเขตเหล่านี้ออกมา เพราะแต่ละ framework มีวิธีการเขียนขอบเขตที่แตกต่างกัน
ทีมหนึ่งอาจใช้ NestJS decorators อีกทีมใช้ Express routes และอีกทีมอาจใช้ jQuery แบบดั้งเดิม ซึ่งแต่ละแบบจะสร้างโครงสร้างที่แตกต่างกันในโค้ด
เพื่อให้สิ่งนี้ใช้งานได้ เราจึงต้องสร้าง custom parsers สำหรับ:
- NestJS และ TypeORM
- Express และ Fastify
- AngularJS และ Redux
- รูปแบบ path-alias ต่างๆ
เราต้องตั้งเป้าความแม่นยำไว้ที่ 99% เพราะหากอัตราการเชื่อมต่อของเราอยู่ที่ 90% AI ก็จะพลาดการเชื่อมต่อไปถึง 10% และในระบบ production เจ้า 10% ที่หายไปนี่แหละคือที่ที่บั๊กซ่อนตัวอยู่
ปัจจุบันเรามีการตรวจสอบทุกวัน หากอัตราการเชื่อมต่อลดลงมากกว่า 5% เราจะได้รับแจ้งเตือน ซึ่งช่วยให้เราตรวจพบเมื่อรูปแบบโค้ดใหม่ๆ ทำให้ parser ของเราทำงานผิดพลาด
ข้อจำกัดในปัจจุบัน
Knowledge graph นี้ยังไม่สมบูรณ์แบบ
- การค้นหายังทำได้ยาก บ่อยครั้งที่คุณจำเป็นต้องรู้ชื่อฟังก์ชันก่อนถึงจะเริ่มค้นหาได้
- ปัญหา Node explosion การไล่ตามเส้นทางหนึ่งอาจดึงเอาฟังก์ชัน helper เล็กๆ ที่ไม่จำเป็นเข้ามานับพันฟังก์ชัน
- การบำรุงรักษา ทุกครั้งที่มี framework ใหม่เข้ามาใน stack ของเรา เราต้องเขียน parser ใหม่เสมอ
นี่คือตอนที่ 1 ในตอนที่ 2 ผมจะพูดถึงเลเยอร์ service-product-graph (SPG) ที่ผมสร้างขึ้นเพื่อปิดช่องว่างเหล่านี้
Optional learning community: https://t.me/GyaanSetuAi
