🛑 1. The Problem First: "สถาปัตยกรรมที่ใหญ่เกินตัว" (Over-Engineering)
ลองดูการตัดสินใจแบบจูเนียร์ที่เพิ่งเริ่มโปรเจกต์ใหม่ (Start-up):
# ❌ Naive Approach: ทำ Microservices ตั้งแต่วันแรกที่มี User 0 คน
Frontend (Next.js) -> API Gateway -> Auth Service -> Payment Service -> User Service
# ผลลัพธ์: เสียเวลา 3 เดือนเพื่อ Config Kubernetes และเครือข่าย โดยที่ยังไม่มีฟีเจอร์ให้ลูกค้าใช้สักอย่าง!
ปัญหา: Microservices มาพร้อมกับ "ภาษีการสื่อสาร" (Network Latency) และ "ภาษีการดูแล" (DevOps Overhead) มหาศาล ถ้าทีมคุณมีแค่ 2-3 คน แล้วต้องมานั่งแก้ Network Error แทนที่จะเขียนฟีเจอร์ คุณกำลังพาบริษัทไปสู่ทางตันครับ Architecture ที่ดีคือสิ่งที่แก้ปัญหาปัจจุบัน ไม่ใช่ปัญหาในจินตนาการอีก 5 ปีข้างหน้า
💡 2. Real-Life Analogy: ร้านอาหารตามสั่ง, ฟู้ดคอร์ท และตู้กดอัตโนมัติ
- Monolith: เหมือน "ร้านอาหารตามสั่ง 1 คูหา". เชฟ พนักงานเสิร์ฟ ล้างจาน ทุกคนอยู่ในที่เดียวกัน คุยกันง่าย สั่งแล้วทำได้ทันที (Fast & Simple) แต่ถ้ามีลูกค้า 1,000 คนมาพร้อมกัน ร้านจะรับไม่ไหว
- Microservices: เหมือน "ฟู้ดคอร์ทขนาดใหญ่". ร้านข้าวร้านหนึ่ง ร้านน้ำร้านหนึ่ง ร้านขนมร้านหนึ่ง แต่ละร้านมีพนักงานของตัวเอง (Autonomy) แต่การจะคุมความสะอาดหรือจัดโปรโมชั่นรวมกันทำได้ยากมาก (Coordination Overhead)
- Serverless: เหมือน "ตู้หยอดเหรียญอัตโนมัติ". คุณไม่ต้องมีพนักงานนั่งเฝ้า มีคนมากดเหรียญตู้ถึงจะทำงาน (Pay-per-use) แต่ถ้ามีคนมากดรัวๆ ตรูอาจจะค้าง (Cold Start) หรือสินค้าหมด (Resource Limits)
🚀 3. Execution Journey: เส้นทางจากการเริ่มสู่การ Scale
Senior จะเลือก Architecture ตาม "ระยะของโปรเจกต์"
🛠 Step-by-step:
- Pilot Stage: เริ่มที่ Modular Monolith (โค้ดก้อนเดียวแต่แบ่งสัดส่วนชัดเจน) เพื่อความเร็วสูงสุดในการขยับ Product
- Growth Stage: เมื่อคนเริ่มเยอะ (เช่น Team Payment ใหญ่ขึ้น) ค่อยๆ แงะ (Extract) ส่วนนั้นออกมาเป็น Service แยก (เรียกว่า Strangler Pattern)
- Execution Tool: ใช้ Docker เพื่อให้ไม่ว่า Architecture ไหน ก็สามารถย้ายไปมาระหว่างเครื่องได้ง่าย
// ✅ Best Practice: เขียน Monolith ให้เป็นสัดส่วน (Modular Monolith)
// /src/services/payment.js -- logic อยู่ตรงนี้ที่เดียว
// /src/services/order.js -- logic อยู่ตรงนี้ที่เดียว
// 🛠 เวลาจะแยกเป็น Microservices แค่ยก Folder นี้ออกไปใส่ Repo ใหม่จบ!
🪤 4. The Junior Trap: โรค "Micro-Database" ที่เชื่อมกันไม่ได้
จูเนียร์มักจะแยก Service แต่ดันอยากทำ JOIN ข้ามกันเหมือนเดิม:
// ❌ Junior Trap: พยายามทำ Distributed Join
// Service A: "ขอดูข้อมูล User หน่อยนะ" (ยิง API ไปถาม Service B ในลูป 100 รอบ)
// 🌋 พัง! ระบบจะอืดมากเพราะ Network Latency และถ้า Service B ล่ม Service A จะล่มตามไปด้วย
ระวัง: เมื่อแยก Service แล้ว คุณจะไม่มี SQL JOIN อีกต่อไป!
✅ การแก้ไข: ต้องใช้เทคนิค Database per Service และสื่อสารผ่าน Event (เช่น RabbitMQ/Kafka) หรือทำข้อมูลซ้ำ (Data Denormalization) เพื่อให้แต่ละ Service ทำงานแยกกันได้จริง
⚖️ 5. The Why Matrix: เลือกท่าไหนคุ้มที่สุด?
| หัวข้อ | Monolith (บ้านๆ) | Microservices (หรูหรา) | Serverless (ทันสมัย) |
|---|---|---|---|
| ความเร็วในการ Dev | ⚡⚡⚡ สูงสุด (ง่ายที่สุด) | ช้าในช่วงแรก | ⚡⚡ สูง (ไม่ต้องห่วง Infra) |
| การดูแลรักษา | ง่าย | 🐢 ยากมาก (ต้องการทีม DevOps) | ง่าย (Zero Ops) |
| การ Scalability | ปานกลาง (Scale ทั้งก้อน) | ⚡⚡⚡ สูงสุด (แยกชิ้น) | 🚀 อัตโนมัติ (Infinite Scale) |
| เหมาะกับทีม | 1-10 คน | 30-100 คนขึ้นไป | งานเป็นชิ้นๆ / Traffic ไม่นิ่ง |
🎓 6. Senior Mindset Summary
การเป็น Senior คือการมองว่า "ไม่มี Architecture ไหนดีที่สุด มีแต่ Architecture ที่ราคาถูกที่สุดสำหรับการแก้ปัญหาปัจจุบัน". อย่ากลัวการเริ่มต้นด้วย Monolith เพราะมันคือรากฐานที่มั่นคงที่สุดสำหรับการสร้าง Product ให้สำเร็จครับ!