วันนี้เห็นมีการ share บทความเรื่อง Continuous Deployment at Instagram
เป็นบทความที่อธิบายขั้นตอนการ deploy ระบบงานของ Instagram ว่าเป็นอย่างไร
ดังนั้นจึงทำการแปล และ สรุปส่วนที่น่าสนใจไว้นิดหน่อย
ซึ่งถือว่าเป็นแนวทางหนึ่งของการพัฒนา software ที่ดี
เริ่มกันเลยดีกว่า
ระบบ Instagram นั้น ทำการ deploy code ส่วน backend ประมาณวันละ 30-40 ครั้งต่อวัน
หรือว่าทำทุก ๆ ครั้งเมื่อมีการเปลี่ยนแปลง code ที่ branch master โดยส่วนใหญ่แล้วจะไม่มีคนเข้าไปมีส่วนร่วมเลย !! นั่นคือทำงานแบบอัตโนมัตินั่นเอง เป็นไงล่ะ แค่เริ่มต้นก็ต้องร้อง ว้าววววว กันแล้ว และทาง Instagram บอกว่า ด้วยขนาดและการ scale ของระบบนั้น ต้องการการทำงานในรูปแบบนี้ ซึ่งมันแจ่ม และ เหมาะมาก ๆ ดังนั้นมาเรียนรู้กันว่า Instagram ทำกันอย่างไร ?เริ่มด้วยคำถามอีกแล้ว ทำไปทำไม ?
ข้อดีของ Continuous Deployment มีดังนี้ ทำให้ทีมพัฒนาทำงานได้รวดเร็วขึ้น เนื่องจากสามารถทำการ deploy code ได้บ่อยเท่าที่ต้องการ ไม่ต้องมารอช่วงเวลา และ จำนวนครั้งที่จำกัดในการ deploy ต่อวัน ผลที่ตามมาก็คือ ไม่ต้องสูญเสียเวลาไปโดยเปล่าประโยชน์ รวมทั้งค่อย ๆ ทำการเปลี่ยนแปลงระบบไปทีละเล็กละน้อย ทำให้รู้ว่าแต่ละการเปลี่ยนแปลงมันผิดหรือถูกได้รวดเร็วขึ้น เนื่องจากทำการ deploy ทุก ๆ การเปลี่ยนแปลง ทำให้ไม่ต้องมานั่งหาข้อผิดพลาดจากการเปลี่ยนแปลงมากมาย ดังนั้น ถ้าการเปลี่ยนแปลงไหนผิด ก็จะรู้ได้ทันที ทำให้สามารถระบุปัญหาได้ทันที และ แก้ไขได้รวดเร็วขึ้น แนวคิดนี้คือ Fail fast, Break things จริง ๆ มันคุ้น ๆ ไหม ถ้าการ deploy แต่ละครั้งมีการเปลี่ยนแปลงเยอะ ๆ การหาข้อผิดพลาดแต่ละเรื่องก็ยากใช่ไหม ?ทำการสร้างระบบอย่างไร ?
การพัฒนาระบบ Continuous Deployment จะประสบความสำเร็จได้นั้น มันมาจากหลายปัจจัย จะสร้างครั้งเดียวให้เสร็จนั้น เป็นไปไม่ได้เลย !! ดังนั้นวิธีการที่ทำคือ ค่อย ๆ สร้างอย่างยั่งยืน (Iterative approch) ค่อย ๆ สร้างที่ละส่วนขึ้นมา จากนั้นดูผลลัพธ์และทำการปรับปรุงให้ดียิ่งขึ้นอย่างสม่ำเสมอ จนทำให้ได้ระบบ Continuous Deployment ในปัจจุบันขึ้นมาได้ก่อนที่จะมีระบบ Continuous Deployment นั้น ทำการ deploy อย่างไร ?
นักพัฒนาทุกคนจะทำการ deploy การเปลี่ยนแปลงต่าง ๆ เอง โดยงานเหล่านี้คืองาน ad-doc หรืองานที่ไม่ได้เตรียมการไว้ล่วงหน้า ซึ่งจะทำการ run script การ rollout เอง หรือบางครั้งก็ต้องรอคนอื่น ๆ ที่จะ deploy ด้วย โดยขั้นตอนแรกทำการ deploy ไปยังเครื่อง production server เพียง 1 ตัว เพื่อทดสอบว่า การทำงานมันถูกต้องตามที่คาดหวังหรือไม่ ? ด้วยการ run ระบบ และเข้าไปดู logg ที่ server ถ้าผลจาก logg ไม่มีข้อผิดพลาดอะไร ก็จะทำการ deploy ไปยังเครื่องทั้งหมด โดยระบบ logging ของการ rollout/deploy จะเรียกว่า Sauron ชื่อคุ้น ๆ ไหม จากเรื่อง The Lord of the Rings นั่นเอง ปล. การทดสอบนั้นใช้ traffic จริง ๆ กันเลยนะต่อมาเริ่มมีการเตรียมเครื่อง server สำหรับการทดสอบโดยเฉพาะเรียกว่า Canary server
ทำให้ควบคุมการ deploy และทดสอบได้ง่ายกว่า แต่การทดสอบเพียงตรวจสอบการ log การทำงานอย่างเดียวมันไม่เพียงพอ จึงได้เพิ่มให้ทำการ run ชุดการทดสอบ ซึ่งแต่ก่อนชุดการทดสอบมีอยู่แล้ว เพียงแต่ถูกทดสอบเฉพาะเครื่องของนักพัฒนาแต่ละคนเท่านั้น ดังนั้นจึงทำการติดตั้ง และ configuration Jenkins server ขึ้นมา เพื่อทำการทดสอบในทุก ๆ การเปลี่ยนแปลงที่ branch master และส่งผลการทดสอบไปยังเครื่อง Sauron ดังนั้นในตอนนี้เครื่อง Sauron จะรู้ว่า ในแต่ละการเปลี่ยนแปลงผ่านการทดสอบหรือไม่ ? ถ้าไม่ผ่านการทดสอบ การเปลี่ยนแปลงเหล่านั้นก็ไม่ถูกสนใจ หรือนำไป deploy ส่งผลทำให้การ deploy มีประสิทธิภาพยิ่งขึ้น คือ ไม่ deploy สิ่งผิด ๆ ขึ้นไป โดยที่ Facebook นั้น ใช้ Fabricator สำหรับการทำ code review ใช้ Sandcastle สำหรับสร้างระบบ Continuous Integration ซึ่งสามารถทำงานร่วมกับ Fabricator ได้ ซึ่ง Sandcastle จะทำการทดสอบทุก ๆ ครั้งที่มีการเปลี่ยนแปลง และส่งผลการทดสอบของการเปลี่ยนแปลงนั้นออกมาจากนั้นเริ่มสร้างระบบการทำงานแบบอัตโนมัติขึ้นมา
เมื่อระบบการทำงานรู้แล้วว่า ในแต่ละการเปลี่ยนแปลงมีสถานะเป็นอย่างไร ต้องใช้คนมาตัดสินใจว่า จะต้องทำอย่างไรต่อไป เช่นตัดสินใจว่า ต้องทำการ rollout/deploy การเปลี่ยนแปลงใด เมื่อผ่านไปสักระยะ จะเริ่มเห็นรูปแบบการทำงาน และทำการสร้าง algorithm สำหรับตัดสินใจว่า rollout/deploy อะไรบ้างขึ้นมา โดยรูปแบบที่ได้คือ- ต้องผ่านการทดสอบทั้งหมด
- จำนวนการเปลี่ยนแปลงต้องน้อย ๆ
- ทำการ deploy การเปลี่ยนแปลง A ไปยัง Canary server
- ทำการทดสอบอีกรอบ
- ทำการ deploy ไปยังทุก ๆ เครื่อง
แต่เส้นทางนี้ ใช่ว่าจะโรยด้วยกลีบกุหลาบ ปัญหาก็เพียบเช่นกัน !!
โดยมีข้อผิดพลาด และ บกพร่องไปมากมาย อาทิเช่น การทดสอบที่ผิดพลาดและล่าช้า นั่นคือ การทดสอบมันผิดพลาดได้ง่าย หรือ ไม่เสถียรนั่นเอง บางครั้งทดสอบผ่าน บางครั้งทดสอบผิดพลาด รวมทั้งการทดสอบมันช้า !! แทนที่ระบบการทำงานจะดี กลับสร้างปัญหาให้อีก มันขัดแย้งกับข้อดีของ Continuous Deployment เลยนะ ดังนั้นจึงต้องลงทั้งแรงกายและแรงใจ เพื่อปรับปรุงให้การทดสอบจากเดิมที่ใช้เวลา 12-15 นาที ให้เหลือเพียง 5 นาที รวมทั้งแก้ไขระบบ infrastructure เพื่อทำให้ระบบการทดสอบมีความน่าเชื่อถือ และ เสถียรขึ้น ส่วนเรื่อง backlog ยังอ่านไม่เข้าใจ ขอข้ามไปก่อน !!มาดูเรื่อง Key Principle หรือแนวคิดของการสร้างกันหน่อยว่ามีอะไรบ้าง ?
1. Tests หรือชุดการทดสอบแบบอัตโนมัติ ต้องทำงานอย่างรวดเร็ว มีจำนวน test coverage ที่เหมาะสม ไม่จำเป็นต้อง 100% เนื่องจากการทดสอบต้องทดสอบอยู่บ่อย ๆ ทั้งก่อนส่งการเปลี่ยนแปลง ทั้งระหว่างการทำ code review ทั้งหลังจากการ deploy 2. Canary ต้องมี canary server เพื่อป้องกันการ deploy การเปลี่ยนแปลงที่แย่ ๆ ขึ้นไป แน่นอนว่า ไม่ได้ต้องการการทำงานที่สมบูรณ์แบบ แต่ต้องการเพียงข้อมูลเชิงสถิติแบบง่าย ๆ เพื่อช่วยวิเคราะห์ว่า แต่ละการเปลี่ยนแปลงส่งผลกระทบอย่างไร 3. Automate the normal case เราไม่สามารถให้ทำงานแบบอัตโนมัติได้ทุก ๆ กรณี ดังนั้น ให้สร้างระบบทำงานแบบอัตโนมัติ เฉพาะส่วนที่เรารู้ และเป็นกรณีแบบปกติทั่วไป แต่ถ้ามีเหตุการณ์หรือกรณีอะไรที่ดูแปลก ๆ หรือผิดปกติ ให้ระบบหยุดการทำงานทันที และให้คนเข้ามาจัดการต่อไป 4. Make people comfortable ปัญหาเรื่องคน มันคือกำแพงที่ยิ่งใหญ่และใหญ่ยิ่ง ของการสร้างระบบการทำงานแบบอัตโนมัติ เนื่องจากคนที่ทำงานอยู่ตรงนั้นก่อนหน้านี้ จะรู้สึกว่า ตัวเองไม่มีความสำคัญ และ ไม่สามารถควบคุมอะไรเองได้เลย ดังนั้นสิ่งที่ต้องทำก็คือ การทำงานของระบบต้องแสดงออกมาให้ทุกคนเห็นอย่างชัดเจน ว่ามีงานอะไรที่ทำเสร็จไปแล้วบ้าง ว่ามีงานอะไรที่กำลังทำอยู่บ้าง ว่าสิ่งที่ทำคืออะไร เพื่อทำให้เห็นว่า สิ่งต่าง ๆ เหล่านี้มันเข้ามาช่วยนะ 5. Expect bad deploys ต้องทำการระบุว่าการเปลี่ยนแปลงใดที่มันแย่ ๆ ให้เร็วที่สุด เพื่อทำให้เราสามารถ rollback ได้รวดเร็ว นั่นคือลดผลกระทบจากความผิดพลาดนั่นเองสิ่งต่าง ๆ เหล่านี้ทุกบริษัทสามารถนำไปสร้างเองได้เลย โดยที่ระบบ Continuous Deployment ไม่จำเป็นต้องมีความซับซ้อน ให้เริ่มจากวิธีการที่ง่าย ๆ เน้นทำตามแนวคิดทั้ง 5 ข้อ เพื่อทำการแก้ไข และ ปรับปรุงกันต่อไป