เช็คลิสต์การส่งมอบแอพที่พร้อมใช้งานสำหรับการโฮสต์เอง
ใช้เช็คลิสต์การส่งมอบแอพที่พร้อมใช้งานนี้เพื่อจัดแพ็กสภาพแวดล้อม ความลับ การมอนิเตอร์ การสำรองข้อมูล และ runbook เพื่อให้ทีมปฏิบัติการสามารถดีพลอยและรับผิดชอบแอพได้

ความหมายเชิงปฏิบัติของ “การส่งมอบที่พร้อมใช้งาน”
การส่งมอบที่พร้อมใช้งานหมายความว่าทีมปฏิบัติการ (ops) สามารถรันแอพโดยไม่ต้องเดา พวกเขาต้องสามารถดีพลอยเวอร์ชันที่รู้จัก ยืนยันว่าสถานะปกติ ตอบสนองต่อการแจ้งเตือน และกู้คืนจากการปล่อยที่เสียหายหรือการหยุดให้บริการได้ หากสิ่งใดสิ่งหนึ่งต้องพึ่งความจำของนักพัฒนาคนใดคนหนึ่ง แปลว่าการส่งมอบยังไม่เสร็จ
มองการส่งมอบเป็นแพ็กเกจที่ตอบคำถามเดียว: ถ้าคนสร้างหายไปสัปดาห์หนึ่ง ทีมปฏิบัติการยังสามารถรักษาความปลอดภัยและให้บริการระบบได้ไหม?
แพ็กเกจที่มั่นคงมักครอบคลุมว่าแอพทำอะไร รูปลักษณ์ของสถานะ “ปกติ” วิธีการปล่อย (ดีพลอย ยืนยัน ย้อนกลับ) ที่อยู่ของคอนฟิก วิธีจัดการความลับ และวิธีมอนิเตอร์ สำรองข้อมูล และตอบสนองต่อเหตุการณ์
สิ่งที่สำคัญเท่าๆ กันคือสิ่งที่มันไม่ครอบคลุม การส่งมอบไม่ใช่คำสัญญาว่าจะเพิ่มฟีเจอร์ รีแฟกเตอร์ ออกแบบหน้าจอใหม่ หรือ “ทำความสะอาดทีหลัง” เหล่านี้เป็นโครงการแยกต่างหากที่มีขอบเขตของตัวเอง
ก่อนจะประกาศเสร็จ ให้ตกลงเรื่องความเป็นเจ้าของและเวลาในการตอบสนอง เช่น: ops เป็นเจ้าของ uptime และดีพลอย ทีมผลิตเป็นเจ้าของ roadmap การพัฒนา ทีม dev ให้หน้าต่างการสนับสนุนหลังส่งมอบที่กำหนดไว้สำหรับการแก้บั๊กและคำถาม
สร้างสินค้าคงคลังระบบแบบง่าย (อะไรรันที่ไหน)
ทีมปฏิบัติการจะเป็นเจ้าของได้ต่อเมื่อเห็นสิ่งที่ต้องเป็นเจ้าของ สินค้าคงคลังหน้าเดียวช่วยลดการเดาในการดีพลอย เหตุการณ์ และการตรวจสอบ เก็บไว้เป็นภาษาเรียบง่ายและชัดเจน
ระบุทุกส่วนที่รันได้และที่ตั้งของมัน: backend API, เว็บแอพ, background worker, งานตามตาราง และวิธีที่แอพมือถือเชื่อมต่อ ถึงแม้ iOS/Android จะกระจายผ่านสโตร์ แต่ก็ยังพึ่งพา backend เดียวกัน
ใส่บริการภายนอกที่แอพไม่สามารถรันได้หากขาด หากใช้ PostgreSQL คิว สตอเรจ หรือ API ภายนอก (เช่น Stripe, การส่งข้อความ, อีเมล/SMS, Telegram) ให้เขียนชื่อบริการที่แน่นอนและใช้งานอย่างไร
บันทึกข้อกำหนดเครือข่ายเพื่อป้องกันการทดลองผิดพลาด: โดเมนที่ต้องการ (app, api, admin), พอร์ตและโปรโตคอล ใครต่ออายุใบรับรอง TLS ที่ไหนจัดการ DNS และรายการอนุญาตเข้า/ออกใดๆ
สุดท้าย ระบุโหลดที่คาดหวังเป็นตัวเลขจริง: คำขอสูงสุดต่อนาที ผู้ใช้ที่ใช้งาน ขนาด payload ทั่วไป ขนาดฐานข้อมูลปัจจุบัน และการเติบโตที่คาดไว้ แม้จะเป็นช่วงคร่าวๆ ก็ช่วยให้ ops ตั้งขีดจำกัดและการแจ้งเตือนได้
ถ้าคุณสร้างด้วย AppMaster ให้จดสินค้าคงคลังของ backend ที่สร้าง เว็บแอพ และการผสานต่างๆ เพื่อให้ ops รู้ว่าอะไรต้องดีพลอยพร้อมกัน
จัดแพ็กคอนฟิกสภาพแวดล้อม (โดยไม่เปิดเผยความลับ)
การตั้งค่าผลิตจริงมักพังตรงส่วนที่น่าเบื่อ: คอนฟิกที่มีแต่ในหัวของใครบางคน ให้ถือว่าคอนฟิกเป็นสิ่งที่ต้องส่งมอบ ทีมปฏิบัติการควรเห็นว่าสิ่งใดมีอยู่ ค่าต่างกันตามสภาพแวดล้อมอย่างไร และเปลี่ยนอย่างปลอดภัยได้อย่างไร
เริ่มด้วยการตั้งชื่อทุกสภาพแวดล้อมที่มีอยู่วันนี้ แม้คิดว่าจะชั่วคราว ทีมส่วนใหญ่มี dev, staging, production และอาจมีสำเนาเช่น “production-eu” หรือ “staging-us” ระบุว่าสภาพแวดล้อมใดใช้ทดสอบการปล่อย การย้ายข้อมูล และการซ้อมเหตุการณ์
จัดทำเอกสารคอนฟิกฉบับเดียวที่ระบุชื่อคีย์และค่าตัวอย่างที่ปลอดภัย (ห้ามใส่ข้อมูลรับรองจริง) ทำ placeholder ให้ชัดเจน
แพ็กการส่งมอบของคุณควรมี:
- รายการสภาพแวดล้อมและหน้าที่ของแต่ละอัน
- เอกสารอ้างอิงคีย์คอนฟิก (env vars หรือคีย์ไฟล์คอนฟิก) ประเภทที่คาดหวัง และค่าตัวอย่างที่ไม่ใช่ความลับ
- ความแตกต่างที่รู้ระหว่างสภาพแวดล้อม (feature flags, rate limits, ขนาดแคช, โหมดอีเมล, ระดับ logging)
- ค่าดีฟอลต์และสิ่งที่จะเกิดขึ้นหากคีย์หายไป
- ที่เก็บคอนฟิกและวิธีนำไปใช้ตอนดีพลอย
เพิ่มกระบวนการเปลี่ยนแปลงง่ายๆ เช่น: ขอผ่านตั๋ว ตรวจสอบโดยเจ้าของบริการ นำไปใช้ใน staging ก่อน แล้วค่อยโปรโมทไป production ในช่วงเวลากำหนดพร้อมแผนย้อนกลับหากอัตราข้อผิดพลาดเพิ่ม
ถ้าคุณกำลังส่งออกและโฮสต์เองแอพจาก AppMaster ยังคงใช้กฎเดียวกัน: ส่งมอบชุดคีย์คอนฟิกที่สะอาดและมีเอกสารแนบกับซอร์สที่สร้างขึ้นเพื่อให้ ops รันข้ามสภาพแวดล้อมอย่างสม่ำเสมอ
ความลับและข้อมูลรับรอง: การเก็บ การหมุนเวียน และการเข้าถึง
ความลับเป็นวิธีเร็วที่สุดที่การส่งมอบที่สะอาดจะกลายเป็นเหตุการณ์ด้านความปลอดภัย เป้าหมายตรงไปตรงมา: ops ควรรู้ความลับทั้งหมดที่แอพต้องการ ที่เก็บ ใครอ่านได้ และเปลี่ยนโดยไม่ทำให้ระบบดาวน์ได้อย่างไร
เริ่มด้วยรายการความลับสั้นๆ ที่ ops สแกนได้ภายในหนึ่งนาที สำหรับแต่ละรายการ ระบุว่าเปิดอะไร (ฐานข้อมูล, SMTP, Stripe, คีย์เซ็น JWT), อยู่ที่ไหน (vault, cloud secret store, Kubernetes Secret, ไฟล์เข้ารหัส) และใครรับผิดชอบการหมุนเวียน
เขียนขั้นตอนการหมุนเวียนเป็นสูตร ไม่ใช่นโยบาย ระบุลำดับที่แน่นอน ระยะเวลาที่คีย์เก่าต้องยังมีผล และการตรวจสอบเดียวที่พิสูจน์ว่าการหมุนเวียนสำเร็จ
เช็คลิสต์การหมุนเวียน (ตัวอย่าง)
ใช้รูปแบบนี้สำหรับแต่ละความลับ:
- สร้างค่าความลับใหม่แล้วเก็บในตัวจัดการความลับที่อนุมัติแล้ว
- ดีพลอยการเปลี่ยนแปลงคอนฟิกเพื่อให้แอพใช้ค่าใหม่
- ยืนยัน: การล็อกอิน การชำระเงิน หรือการเรียก API สำเร็จและอัตราข้อผิดพลาดปกติ
- เพิกถอนความลับเก่าและยืนยันว่าไม่สามารถใช้งานได้อีก
- บันทึกวันที่หมุนเวียน ใครทำ และวันที่ครบถัดไป
ระบุความคาดหวังด้านการเข้ารหัสอย่างชัดเจน ความลับควรถูกเข้ารหัสขณะพักในที่เก็บและป้องกันขณะส่ง (TLS) ระหว่างแอพกับพึ่งพา อย่าใส่ความลับลงใน source control, build artifacts, หรือเอกสารแชร์
กำหนดการเข้าถึงฉุกเฉิน (break-glass) หากเหตุขัดข้องบล็อกการเข้าถึงปกติ ระบุว่าใครอนุมัติการเข้าถึงฉุกเฉิน ระยะเวลาที่ให้ และต้องตรวจสอบอะไรหลังจากนั้น
แพ็กการดีพลอย: อาร์ติแฟกต์ เวอร์ชัน และการย้อนกลับ
ops เป็นเจ้าของได้ต่อเมื่อทำซ้ำได้ แพ็กการดีพลอยที่ดีทำให้สามคำถามเป็นเรื่องง่าย: เรากำลังรันอะไรแน่ จะดีพลอยอีกครั้งอย่างไร และกลับมารวดเร็วถ้ามีปัญหาได้อย่างไร
รวม “รายการวัสดุ” ของบิลด์ให้ชัด ชื่อชนิดอาร์ติแฟกต์และวิธีตรวจสอบ ไม่ใช่แค่ที่เก็บ:
- รายละเอียดอาร์ติแฟกต์: ชื่อ/แท็กของรูปคอนเทนเนอร์ (หรือชื่อไบนารี/แพ็กเกจ), เวอร์ชันแอพ, วันที่ build, checksum
- อ้างอิงซอร์ส: แท็กรีลีสหรือ commit hash ที่ใช้สร้าง พร้อม flag ที่สำคัญ
- เป้าหมายที่รองรับ: VM, คอนเทนเนอร์ (Docker), หรือ Kubernetes และอันไหนแนะนำเป็นค่าเริ่มต้น
- ขั้นตอนการดีพลอย: prerequisite (runtime, DB, storage), ลำดับที่แน่นอน, และเวลาการดีพลอยโดยประมาณ
- การย้ายสคีมา: รันอย่างไร (รันอัตโนมัติบนสตาร์ทหรือแบบแมนนวล), อยู่ที่ไหนบันทึก, และยืนยันผลสำเร็จอย่างไร
เพิ่มตัวอย่างเล็กๆ ที่ชัดเจน เช่น: “ดีพลอย v1.8.2 โดยอัปเดตแท็กภาพ รัน migration แล้วรีสตาร์ท web workers หาก health check ล้มเหลวภายใน 10 นาที ให้ย้อนกลับเป็น v1.8.1 และหยุดงาน migration”
การย้อนกลับ โดยไม่ต้องเดา
แผนย้อนกลับควรอ่านเหมือนคำสั่งที่ปฏิบัติตามได้ตอนตีสอง ควาระบุ:
- สัญญาณที่เป็นตัวกระตุ้นการย้อนกลับ (อัตราข้อผิดพลาด, health check ล้มเหลว, การล็อกอินล้มเหลว)
- เวอร์ชันที่รู้ว่ายังดีล่าสุดและที่เก็บของมัน
- ว่าการเปลี่ยนแปลงฐานข้อมูลย้อนกลับได้หรือไม่ และต้องทำอย่างไรถ้าย้อนกลับไม่ได้
หากแอพสร้างด้วย AppMaster และส่งออกเป็นซอร์สโค้ดสำหรับโฮสต์เอง ให้รวมเวอร์ชันซอร์สที่สร้าง คำแนะนำการ build และความคาดหวังด้าน runtime เพื่อให้ ops สามารถสร้าง release เดิมได้อีกครั้ง
การมอนิเตอร์และการแจ้งเตือน: วัดอะไรและเมื่อไรควรแจ้ง
การส่งมอบไม่สมบูรณ์จนกว่า ops จะเห็นว่าแอพทำอะไรและได้รับเตือนก่อนผู้ใช้บ่น
ตกลงกันว่า log อะไรต้องมีและไปที่ไหน (ไฟล์, syslog, แพลตฟอร์ม log) ให้แน่ใจว่าเวลาใน log ซิงก์กันและมี request หรือ correlation ID เพื่อให้เหตุการณ์ตามรอยได้จากต้นจนจบ
โดยปกติคุณอยากได้ log แอพ (เหตุการณ์สำคัญและความล้มเหลว), log ข้อผิดพลาด (stack trace และงานที่ล้มเหลว), access log (คำขอและรหัสสถานะ), audit log (การกระทำของแอดมินและการส่งออก), และ log โครงสร้างพื้นฐาน (การรีสตาร์ท แรงกดดันของโหนด ปัญหาดิสก์)
ต่อมา กำหนดชุดเมตริกเล็กๆ ที่สะท้อนผลกระทบต่อผู้ใช้และสุขภาพระบบ ถ้าเลือกแค่ห้า: latency (p95/p99), อัตราข้อผิดพลาด, ความอิ่มตัว (CPU/หน่วยความจำ/ดิสก์), ความลึกของคิว, และการเช็คความพร้อมจากภายนอก
กฎการแจ้งเตือนควรชัดเจน: อะไรเป็นตัวกระตุ้น ความรุนแรง (page vs ticket), ใครอยู่ on-call, และเมื่อใดต้องยกระดับ เพิ่มสแนปช็อตแดชบอร์ด “สภาพดี” และบันทึกสั้นๆ ว่าปกติเป็นอย่างไร (ช่วง latency ปกติ อัตราข้อผิดพลาดคาดหวัง ความลึกคิวปกติ) คอนเท็กซ์นี้จะช่วยลดการแจ้งเตือนดังเกินไปและช่วยผู้ตอบเหตุการณ์ใหม่ทำงานได้เร็วขึ้น
การสำรองข้อมูลและการกู้คืน: ทำให้การคืนค่าทำซ้ำได้
การสำรองข้อมูลไม่ใช่สิ่งที่คุณ “มี” แต่มันคือสิ่งที่คุณสามารถกู้คืนได้ตามคำขอ
เขียนขอบเขตที่ชัดเจน: ฐานข้อมูล, ที่เก็บไฟล์ (uploads, reports, invoices), และส่วนที่คนมักลืม เช่น คอนฟิกที่ไม่อยู่ในโค้ด และกุญแจเข้ารหัสที่ต้องใช้ในการอ่านข้อมูลปกป้อง
เก็บเป้าหมายเป็นคำง่ายๆ RPO คือปริมาณข้อมูลที่ยอมเสียได้ (เช่น 15 นาที) RTO คือเวลาที่ยอมให้ระบบดาวน์ได้ (เช่น 1 ชั่วโมง) เลือกตัวเลขที่ธุรกิจเห็นชอบเพราะมันกำหนดต้นทุนและความพยายาม
รวม:
- อะไรถูกแบ็กอัพ ที่เก็บ และระยะเวลาเก็บ
- ใครสามารถรันการแบ็กอัพและการกู้คืน และวิธีอนุมัติการเข้าถึง
- ขั้นตอนกู้คืนทีละขั้นตอนพร้อมการตรวจสอบ
- ที่เก็บบันทึกการกู้คืน และนิยามของ “สำเร็จ”
- โหมดล้มเหลวที่พบบ่อย (กุญแจผิด ถังหาย สคีมาไม่ตรง) และการแก้ไข
ถ้าคุณส่งออกและโฮสต์เองแอพที่สร้างด้วย AppMaster ให้รวมขั้นตอนการกู้คืน PostgreSQL พร้อมถังสตอเรจภายนอกและกุญแจที่ใช้กับฟิลด์ที่เข้ารหัส
จัดตารางซ้อมการกู้คืน บันทึกเวลา สิ่งที่พัง และสิ่งที่เปลี่ยนเพื่อให้การกู้คืนครั้งต่อไปเร็วขึ้นและเครียดน้อยลง
Runbook และ on-call: ops จัดการเหตุการณ์จริงอย่างไร
การส่งมอบยังไม่เกิดผลจนกว่าจะมีคนถูก page ตอนตีสองแล้วแก้ปัญหาได้โดยไม่ต้องเดา Runbook แปลงความรู้เผ่าพันธุ์ให้เป็นขั้นตอนที่คน on-call ทำตามได้
เริ่มจากเหตุการณ์ที่คาดว่าจะเกิดก่อน: การหยุดบริการทั้งหมด คำขอช้า และการปล่อยที่ทำให้ระบบเสีย Runbook แต่ละฉบับให้สั้น วางการตรวจสอบที่เร็วที่สุดไว้บนสุดเพื่อให้ผู้ตอบเหตุการณ์ได้สัญญาณภายในไม่กี่นาที
สิ่งที่ runbook ดีๆ ควรมี
รักษาโครงสร้างให้สม่ำเสมอเพื่อให้สแกนหาได้ในเวลาคับขัน:
- ผู้ใช้เห็นอะไรและยืนยันอย่างไร (ตัวอย่าง: อัตราข้อผิดพลาดสูงกว่า X%, การชำระเงินล้มเหลว)
- การตรวจสอบแรก (สถานะบริการ ดีพลอยล่าสุด สุขภาพของพึ่งพา ดิสก์/CPU การเชื่อมต่อ DB)
- การตรวจสอบถัดไป (log สำคัญ แดชบอร์ด คอนฟิกที่เปลี่ยนล่าสุด ความลึกคิว)
- จุดตัดสินใจ (เมื่อย้อนกลับ เมื่อขยาย เมื่อปิดฟีเจอร์)
- การยกระดับ (ใครเป็นเจ้าของแอพ ใครเป็นเจ้าของ infra และเมื่อใดต้อง page คนเหล่านั้น)
ถ้าแอพส่งออกหรือโฮสต์เองจาก AppMaster ให้รวมว่าบริการที่สร้างวิ่งที่ไหน จะรีสตาร์ทอย่างปลอดภัยอย่างไร และค่าคอนฟิกคาดหวังต่อสภาพแวดล้อมคืออะไร
หลังเหตุการณ์: จับข้อเท็จจริงที่ถูกต้อง
เก็บเช็คลิสต์หลังเหตุการณ์สั้นๆ บันทึกไทม์ไลน์ สิ่งที่เปลี่ยนล่าสุด ข้อความผิดพลาดที่ชัดเจน ผู้ใช้ที่ได้รับผลกระทบ และการกระทำที่แก้ปัญหา จากนั้นอัพเดต runbook ในขณะที่รายละเอียดยังสดใหม่
การควบคุมการเข้าถึงและสิทธิ์: ใครทำอะไรได้บ้าง
ops จะเป็นเจ้าของระบบได้ก็ต่อเมื่อระบุชัดเจนว่าใครแตะอะไรได้และวิธีการติดตามการเข้าถึง
เขียนบทบาทที่คุณใช้งานจริง สำหรับหลายทีม บทบาทเหล่านี้เพียงพอแล้ว:
- Deployer: ดีพลอยเวอร์ชันที่อนุมัติและเริ่มย้อนกลับ
- DB admin: รันการเปลี่ยนแปลงสคีมาและกู้คืนแบ็กอัพ
- Read-only: ดูแดชบอร์ด logs และคอนฟิกโดยไม่แก้ไข
- Incident commander: อนุมัติการกระทำฉุกเฉินระหว่างการหยุดให้บริการ
จดนโยบายการให้สิทธิ์เป็นขั้นตอน เช่น ใครให้สิทธิ์ ที่ไหน (SSO, cloud IAM, ผู้ใช้ DB, CI/CD, แผงผู้ดูแล) ใครเพิกถอน และยืนยันอย่างไรว่าเอาออกตอน offboarding
อย่าลืมการเข้าถึงที่ไม่ใช่มนุษย์ รายการบัญชีบริการและโทเค็นทั้งหมดที่ใช้โดย job, integration, และการมอนิเตอร์ พร้อมบันทึก least-privilege สำหรับแต่ละรายการ (เช่น “อ่านจาก bucket X ได้เท่านั้น”) หากส่งออกซอร์สจาก AppMaster ให้รวม env vars หรือไฟล์คอนฟิกที่กำหนดตัวตนเหล่านี้ แต่ห้ามวางค่าความลับลงในเอกสารส่งมอบ
ตั้งความคาดหวังด้าน audit log: อะไรต้องบันทึก (การล็อกอิน ดีพลอย การเปลี่ยนคอนฟิก การกระทำ DB admin) ใครอ่าน logs ได้ ระยะเวลาเก็บ และที่เก็บ เพื่อให้สามารถร้องขอ logs ระหว่างเหตุการณ์หรือการตรวจสอบได้
พื้นฐานด้านความปลอดภัยและการปฏิบัติตามข้อกำหนด (แบบเข้าใจง่าย)
โน้ตด้านความปลอดภัยควรอ่านได้โดยคนทั่วไป แต่เฉพาะพอที่ ops จะทำตามได้ เพิ่มสรุปหน้าเดียวที่ตอบว่า เราเก็บข้อมูลอะไร ที่ไหน และใครเข้าถึงได้
เริ่มด้วยประเภทข้อมูล: โปรไฟล์ลูกค้า ตั๋วซัพพอร์ต เมตาดาต้าการชำระเงิน ไฟล์ ระบุหมวดที่ละเอียดอ่อนเช่น PII (ชื่อ อีเมล เบอร์โทร), ข้อมูลรับรอง และข้อมูลที่ต้องปฏิบัติตามกฎระเบียบ หากส่งออกซอร์สเพื่อโฮสต์เอง (รวมจาก AppMaster) ให้ระบุว่าข้อมูลเหล่านั้นอยู่ตรงไหนใน DB และบริการใดอ่านได้
แล้วเขียนกฎการเก็บและการลบอย่างปฏิบัติได้ กล่าวถึงเก็บอะไร เท่าไร และการลบทำอย่างไร (soft delete vs hard delete, การลบแบบหน่วง) หากมีการอายัดทางกฎหมายหรือการตรวจสอบ ให้ระบุว่าใครอนุมัติข้อยกเว้น
log มักรั่วข้อมูลมากกว่าฐานข้อมูล จงชัดเจนว่าข้อมูล PII อาจปรากฏที่ไหน (access log, error log, analytics event) และวิธีลดหรือมาสก์มัน หากฟิลด์ใดต้องไม่ถูกล็อก ให้ระบุเป็นกฎ
ทำให้การอนุมัติชัดเจน:
- การเปลี่ยนแปลงการพิสูจน์ตัวตนต้องมีผู้อนุมัติที่ชื่อตรง
- การเปลี่ยนที่เกี่ยวกับการชำระเงิน (คีย์ Stripe, webhook, โลจิกคืนเงิน) ต้องมีผู้อนุมัติที่ชื่อตรง
- การเปลี่ยนโมเดลบทบาทและสิทธิ์ต้องมีผู้อนุมัติที่ชื่อตรง
- หน้าต่างการแพตช์ความปลอดภัยและกฎการเปลี่ยนฉุกเฉินต้องถูกเขียนลง
ถ้าจะเพิ่มสิ่งเดียว ให้เพิ่มโน้ตหลักฐาน: ที่เก็บ audit log และวิธีส่งออกเมื่อมีคนขอหลักฐาน
ตัวอย่างสถานการณ์ส่งมอบ: ops รับช่วงในหนึ่งสัปดาห์
ops รับพอร์ทัลลูกค้าที่ทีมผลิตขนาดเล็กสร้างและย้ายไปยังโครงสร้างพื้นฐานที่โฮสต์เองใหม่ เป้าหมายไม่ใช่แค่ว่า “มันรันได้” แต่คือ “ops รันมันได้โดยไม่ต้องโทรหาผู้สร้าง”
หน้าตาสัปดาห์ที่หนึ่ง
Day 1: ops ทำการดีพลอยครั้งแรกในสภาพแวดล้อมใหม่โดยใช้แค่แพ็กการส่งมอบ แอพขึ้นแต่ล็อกอินล้มเหลวเพราะขาดตัวแปรสภาพแวดล้อมสำหรับผู้ให้บริการอีเมล ข้อนั้นถูกเพิ่มเข้าไปในเทมเพลต env และดีพลอยซ้ำจนขึ้นได้จากศูนย์
Day 2: แจ้งเตือนแรกถูกยิงตามจงใจ ops ทำความล้มเหลวที่ควบคุมได้ (หยุดหนึ่งบริการหรือบล็อกอีเมลขาออก) และยืนยันว่าเมตริกแสดงปัญหา การแจ้งเตือนไปถึงช่องทางที่ถูกต้อง และข้อความบอกว่าต้องทำอะไรต่อ
Day 3: โทเค็นหมดอายุใน sandbox การชำระเงิน เพราะตำแหน่งของข้อมูลรับรองและขั้นตอนการหมุนเวียนถูกบันทึกไว้ ops จึงเปลี่ยนโดยไม่ต้องเดาหรือเปิดเผยความลับ
Day 4: ตัด DNS ระเบียนผิดชี้ไปที่ IP เก่า ทำให้พอร์ทัลดูเหมือนล่มสำหรับผู้ใช้บางคน ops ใช้ runbook ตรวจสอบ DNS, TLS, และ health check ตามลำดับที่เหมาะสม
Day 5: ทดสอบการกู้คืนสำรองครั้งแรก ops กู้คืนไปยังฐานข้อมูลใหม่และพิสูจน์ว่าพอร์ทัลโหลดข้อมูลจริงได้
ภาพของคำว่า “เสร็จ” หลัง 1 สัปดาห์
แอพรันเป็นเวลา 7 วันโดยไม่มีการแก้ไขปริศนา หนึ่งการกู้คืนสำเร็จ แจ้งเตือนชัดเจน และการดีพลอยทำซ้ำได้ที่ ops ทำได้เอง
ข้อผิดพลาดทั่วไปที่ทำให้ต้องออกไปรับสายตอนดึก
วิธีที่เร็วที่สุดทำให้การส่งมอบสงบกลายเป็นไฟตอนตีสองคือคิดว่า “เราเล่าให้ ops ฟังทุกอย่างแล้ว” เหมือนกับ “ops รันได้โดยไม่ต้องพึ่งเรา”
รูปแบบความล้มเหลวทั่วไปหลังการส่งมอบโฮสต์เองรวมถึงความลับแชร์ในสเปรดชีตหรือแชท การย้อนกลับที่พึ่งพานักพัฒนา สำรองที่มีแต่ไม่เคยทดสอบการกู้คืน การแจ้งเตือนที่ดังทั้งวันเพราะไม่ได้ปรับเกณฑ์ และรายละเอียดสภาพแวดล้อมที่มีแต่ในหัวของใครบางคน (พอร์ต ชื่อ DNS ตาราง cron สิทธิ์คลาวด์)
ตัวอย่าง: คุณส่งออกซอร์สโค้ดจาก AppMaster เพื่อโฮสต์เอง และการดีพลอยแรกผ่านได้ สองสัปดาห์ต่อมามีการเปลี่ยนคอนฟิกที่ทำให้ล็อกอินพัง ถ้าความลับถูกส่งผ่านแชทและการย้อนกลับต้องการผู้สร้างเดิม ops จะเสียเวลาหลายชั่วโมงเพื่อกลับไปที่ “ทำงานได้เมื่อวาน”
ตรวจเร็วๆ ก่อนบอกว่า “ส่งมอบเสร็จ”
ก่อนปิดตั๋ว ให้ทำการซ้อมเริ่มใหม่สั้นๆ ให้แพ็กการส่งมอบแก่วิศวกร ops หนึ่งคนและสภาพแวดล้อมสะอาด (VM ใหม่ namespace Kubernetes ใหม่ หรือโปรเจคคลาวด์ว่าง) ถ้าพวกเขาสามารถดีพลอย สังเกต และกู้คืนแอพภายในเวลาที่กำหนด (เช่น 2 ชั่วโมง) คุณใกล้จะเสร็จแล้ว
ใช้การตรวจเหล่านี้:
- สร้างใหม่และดีพลอยจากศูนย์โดยใช้แค่ artifacts ที่จัดให้ เอกสารคอนฟิก และ runbook (รวมการย้อนกลับ)
- ยืนยันว่าทุกความลับอยู่ในที่ตกลงกันไว้ และขั้นตอนการหมุนเวียนถูกเขียนและทดสอบ
- เปิดแดชบอร์ดและยืนยันว่ามันตอบคำถามพื้นฐาน: ขึ้นไหม ช้าไหม เป็นข้อผิดพลาดไหม กำลังจะหมดทรัพยากรไหม
- ยิงการแจ้งเตือนทดสอบที่ปลอดภัยหนึ่งครั้งเพื่อยืนยันเส้นทางการ page เจ้าของ และช่วงเวลาที่เงียบ
- ทำการทดสอบกู้คืนจริงในสภาพแวดล้อมแยก แล้วจดขั้นตอนและผลลัพธ์ที่คาดหวัง
ถ้าส่งออกซอร์สที่สร้างเพื่อโฮสต์เอง ให้ยืนยันว่า ops รู้ว่าข้อมูลเข้า build, เวอร์ชัน และแท็กรีลีสบันทึกไว้ที่ไหนเพื่อให้ release ในอนาคตทำซ้ำได้
ขั้นตอนถัดไป: สรุปความเป็นเจ้าของและทำให้แพ็กทันสมัย
จัดการทัวร์สรุปสุดท้ายกับคนที่จะถือ pager ถือมันเหมือนซ้อม ลองดีพลอย ย้อนกลับ กู้คืน และแจ้งเตือนด้วยแพ็กที่คุณจะส่งมอบจริงๆ
การทัวร์มักครอบคลุม: ดีพลอยสู่สภาพแวดล้อมทดสอบแล้วไป production ด้วยขั้นตอนเดียวกัน ย้อนกลับเป็นเวอร์ชันก่อนหน้าและยืนยันแอพยังทำงาน กู้คืนจากแบ็กอัพสู่สภาพแวดล้อมสะอาดและยืนยันการตรวจสอบจริงหนึ่งอย่าง (ล็อกอิน สร้างเรคคอร์ด ส่งข้อความ) ยิงการแจ้งเตือนทดสอบ และยืนยันว่าจะหา logs และแดชบอร์ดได้ที่ไหนระหว่างเหตุการณ์
ทำความเป็นเจ้าของให้ชัดเจน กำหนดเจ้าของที่ชื่อตรงสำหรับแต่ละ runbook (ดีพลอย เหตุการณ์ กู้คืน) และสำหรับแต่ละเส้นทางการแจ้งเตือน (on-call หลัก สำรอง พฤติกรรมหลังเวลางาน) ถ้าไม่มีใครเป็นเจ้าของการแจ้งเตือน มันจะถูกละเลยหรือปลุกคนผิด
เขียนแผน Day 2 สั้นๆ เพื่อให้ ops รู้ว่าสิ่งใดต้องปรับปรุงหลังสัปดาห์แรก: ปรับเกณฑ์ ทำความสะอาดค่าใช้จ่าย ลบอาร์ติแฟกต์เก่า และตรวจสอบการเข้าถึง เก็บไว้สั้นและกำหนดเวลา
ถ้าคุณสร้างด้วย AppMaster (appmaster.io) ให้รวมซอร์สโค้ดที่ส่งออกหรือรายละเอียดเป้าหมายการดีพลอยที่แน่นอน (คลาวด์, ภูมิภาค, การตั้งค่า build, บริการที่ต้องการ) เพื่อให้ ops ทำซ้ำแอพได้โดยไม่ต้องพึ่ง workspace โปรเจคเดิม ตั้งจังหวะง่ายๆ ในการอัปเดตแพ็กเมื่อความต้องการเปลี่ยนเพื่อไม่ให้ runbook เบี่ยงจากความจริง
คำถามที่พบบ่อย
การส่งมอบที่พร้อมใช้งานหมายความว่าทีมปฏิบัติการสามารถดีพลอยเวอร์ชันที่รู้จัก ยืนยันว่าสถานะปกติ ตอบสนองต่อการแจ้งเตือน และกู้คืนจากความล้มเหลวได้โดยไม่ต้องพึ่งความทรงจำของนักพัฒนารายใดรายหนึ่ง หากทีมผู้สร้างหายไปเป็นสัปดาห์แล้วสถานะพร้อมใช้งานยังเสี่ยงอยู่ แปลว่าการส่งมอบยังไม่เสร็จสมบูรณ์
เริ่มจากแผ่นเดียวที่สรุประบบ: ระบุส่วนประกอบที่รันอยู่ทั้งหมดและสถานที่ที่มันอยู่ เช่น API, เว็บ แอพ, worker, งานตามตาราง, ฐานข้อมูล, ที่เก็บไฟล์ และบริการภายนอกที่จำเป็น เพิ่มโดเมน พอร์ต เจ้าของ DNS/TLS และการประมาณโหลดคร่าวๆ เพื่อให้ทีมปฏิบัติการทำงานโดยไม่ต้องเดา
จัดเตรียมเอกสารอ้างอิงค่าคอนฟิกเดียวที่แสดงคีย์ทั้งหมด ประเภทค่า และตัวอย่างค่าปลอดภัย (อย่าใส่ข้อมูลรับรองจริง) พร้อมระบุความแตกต่างระหว่าง dev/staging/prod อธิบายว่าคอนฟิกถูกเก็บไว้ที่ไหนและนำไปใช้ระหว่างการดีพลอยอย่างไร เพื่อให้การเปลี่ยนแปลงทดสอบซ้ำได้
ทำรายการความลับสั้นๆ ระบุว่าแต่ละความลับใช้เปิดอะไร อยู่ที่ไหน ใครอ่านได้ และใครรับผิดชอบการหมุนเวียน เขียนขั้นตอนการหมุนเวียนเป็นเช็คลิสต์พร้อมการตรวจสอบเดียวที่ชัดเจน รวมถึงกระบวนการฉุกเฉิน (break-glass) และความคาดหวังด้านการตรวจสอบ
ให้ทีมปฏิบัติการรู้ว่าโปรแกรมที่รันคืออะไรและทำซ้ำได้ยังไง: ชื่อ/แท็กของอาร์ติแฟกต์ เวอร์ชัน วันที่ build checksum และข้อมูลอ้างอิงซอร์สที่ใช้สร้าง ระบุแพลตฟอร์มที่รองรับ ขั้นตอนการดีพลอยเรียงลำดับและเวลาประมาณ รวมถึงวิธีรันและยืนยันการย้ายสคีมา
กำหนดสัญญาณที่ชัดเจนสำหรับการย้อนกลับ (เช่น อัตราข้อผิดพลาดสูงหรือ health check ล้มเหลว) ระบุเวอร์ชันที่รู้ว่าใช้งานได้ล่าสุดและที่เก็บมันไว้ ระบุว่า migration ในฐานข้อมูลย้อนกลับได้หรือไม่ และทางเลือกที่ปลอดภัยถ้าไม่สามารถย้อนกลับได้ เพื่อให้การย้อนกลับทำได้แม้ในช่วงกลางดึก
เลือกสัญญาณที่สะท้อนผลกระทบต่อผู้ใช้: เวลาในการตอบสนอง (p95/p99), อัตราข้อผิดพลาด, ความอิ่มตัวของทรัพยากร (CPU/หน่วยความจำ/ดิสก์), ความลึกของคิว และการตรวจสอบความพร้อมจากภายนอก กำหนดระดับความรุนแรงของการแจ้งเตือน ใครต้องถูกเรียก และคำอธิบายว่าปกติเป็นอย่างไร เพื่อให้การแจ้งเตือนไม่ดังเกินไปและผู้ตอบเหตุการณ์ใหม่ทำงานได้เร็วขึ้น
ระบุชัดว่าอะไรถูกแบ็กอัพ ที่เก็บ และนโยบายการเก็บรักษา ระบุคนที่สามารถรันการสำรองและการกู้คืน รวมขั้นตอนกู้คืนทีละขั้นตอนพร้อมการตรวจสอบ และซ้อมการกู้คืนเป็นประจำ สำรองข้อมูลมีความหมายก็ต่อเมื่อกู้คืนได้จริงในสภาพแวดล้อมที่สะอาด
ทำ runbook ให้สั้นและสม่ำเสมอ: อาการที่ผู้ใช้เห็น วิธียืนยัน อันดับตรวจสอบแรก (สถานะบริการ ดีพลอยล่าสุด ขึ้นของพึ่งพา ดิสก์/CPU การเชื่อมต่อฐานข้อมูล) และการตรวจสอบต่อไป รวมทั้งจุดตัดสินใจและการยกระดับ ให้โฟกัสกับเหตุการณ์ที่คาดว่าจะเกิดบ่อยแล้วอัพเดตรายละเอียดหลังเหตุการณ์ทันที
ระบุบทบาทที่ใช้จริง เช่น deployer, DB admin, read-only, incident commander อธิบายขั้นตอนการให้สิทธิ์และเพิกถอนว่าทำอย่างไร ที่ไหน (SSO, cloud IAM, ฐานข้อมูล, CI/CD, แผงผู้ดูแล) และบอกชัดว่าต้องบันทึกอะไรเพื่อตรวจสอบ รวมถึงบัญชีบริการที่ไม่ใช่มนุษย์และสิ่งที่พวกมันเข้าถึง โดยไม่ใส่ค่าความลับลงในเอกสารส่งมอบ


