มาลุยกันต่อจาก ตอนที่ 1: วางเป้าหมาย ตั้งใจจะบอกเล่าขั้นตอนการทำงานทั้งหมด ดังนั้นก็บรรยายไปทีละสเต็ปละกันเนอะ ขั้นตอนต่อไปก็คือการ "Research"
เคยบอกเล่าไว้นานแล้วว่า ก่อนจะลุยทำอะไร การ Research นั้นสำคัญมากๆ มันอาจจะทำให้เราเสียเวลาในช่วงเริ่มต้นไปหน่อยนึง แต่จะทำให้เราประหยัดเวลาในระยะยาวไปได้มหาศาล ตาม Quote ของลินคอร์นอันนี้เลย
จริงๆจะบอกว่าเป็นการเสียเวลาในช่วงแรกก็ไม่ถูก ควรเรียกว่าเป็นการ "ใช้เวลา" มากกว่า ใช้เวลาในช่วงต้นในการศึกษาอย่างรอบคอบว่าสิ่งที่จะทำนั้นเป็นไปได้มั้ย รวมถึงจะต้องใช้เทคโนโลยีอะไรในการทำงานเพื่อให้ได้ตามเป้าหมายที่วางไว้และไม่ทำให้เกิดปัญหาระหว่างการพัฒนาแน่นอน
เราไม่เชียร์ให้ลุยทำเลยโดยไม่ Research นะขอรับ เจอมาเยอะแล้วที่ทำเกือบเสร็จแล้วก็เจอว่าสิ่งที่ทำมานั้นมีปัญหาและไม่สามารถแก้ไขได้ ผลคือต้องรื้อใหม่หมด เห็นแล้วใช่มั้ยว่ามันเสียเวลากว่ากันเยอะ?
Research
ขั้นตอนการ Research นั้นทำไม่ยาก หลังจากวางเป้าหมายแล้วตามบล็อกก่อนหน้า ก็ให้ "ลิสต์" ความยากทางเทคนิค(Technical Challenge)ออกมาให้หมดว่ามีอะไรบ้าง แล้วก็ลุยหาคำตอบทีละอันว่าอันไหนทำได้ทำไม่ได้
ถ้าเป็นได้ทางเทคนิคก็ให้ Research จนเจอตัวที่เหมาะสมที่สุด(ใช้คำว่าเหมาะสมที่สุดนะครับ ไม่ได้ใช้คำว่าดีที่สุด เพราะความเหมาะสมมันเปลี่ยนไปตามบริบท) โดย Research ไปทีละข้อๆ เช่น ควรใช้ Framework อะไรในการพัฒนา? ที่ให้ดูทีละเรื่องก็เพราะเวลาค้นหาเรื่องใดๆก็จะสามารถเปรียบเทียบตัวเลือกต่างๆได้อย่างง่ายดายเนื่องจากสมองกำลังโฟกัสเรื่องนั้นอยู่
ถ้าข้อไหนเป็นไปไม่ได้ทางเทคนิคก็ให้เปลี่ยนวิธีคิดและวิธีทำดูจนกว่าจะเจอทางออกที่เป็นไปได้ ซึ่งตรงนี้อาจจะทำให้ภาพโครงสร้างของโปรเจคเปลี่ยนไปจากที่จินตนาการไว้ตอนแรกได้เลย แต่นั่นก็ดีแล้วเพราะจินตนาการทำให้โปรเจคเสร็จไม่ได้หรอก ...
ก็เตือนไว้ว่าถ้าเจออันไหนที่ยังทำไม่ได้อย่าเพิ่งเริ่มทำโปรเจคเป็นอันขาดเพราะหากเป็นฟีเจอร์สำคัญนั่นก็แปลว่าโปรเจคนั้นเป็นไปไม่ได้เลย ลุยจนเจอ Solution ก่อนเริ่มทำครับ
อันนี้เป็น Research ที่ทำในโปรเจคนี้
ใช้ Stack ไหนดี: LEMP
เพื่อลดเวลาการ Research และการพัฒนาลง เราเลยเลือกใช้ของที่มั่นใจว่าทำงานที่ต้องการได้แน่นอนและจากการที่ถนัดก็จะทำให้การพัฒนาเป็นไปได้อย่างรวดเร็ว
Stack ที่เลือกใช้ก็เลยเป็น LEMP (Linux - Nginx - MySQL - PHP) ที่เริ่มทำได้เลยเพราะเคยทำมาหลายสิบรอบแล้วและก็ไม่มีปัญหาทางเทคนิคใดๆที่เป็นข้อจำกัดของโปรเจคนี้
แต่ถามว่าในใจลึกๆอยากใช้ Stack ไหน? จริงๆอยากใช้ MEAN ครับ แต่มีปัจจัยด้านเวลามาค้ำคออยู่เลยต้องลดเวลา Research และ Implementation ลงให้ได้มากที่สุด เลยต้องเลือกตาม "ความเหมาะสม" ของสถานการณ์นั่นเอง ถึงแม้เนยจะทำ MEAN เป็นระดับนึงแล้ว แต่ถ้าเทียบความเร็วในการทำงานเพื่อให้งาน Deliver ทัน ยังไงเนยก็ทำ LEMP ได้เร็วกว่าเลยเลือก LEMP นั่นเอง
ก็จะเห็นว่าคำตอบมันมีบริบทหลายๆเรื่องเข้ามาเกี่ยวข้อง คนมาอ่านบล็อกนี้ก็ต้องหาคำตอบด้วยตัวเองด้วยน้อ ไม่ใช่ใช้ LEMP ตามกันหมด อันนั้นผิด มันก็แค่ Stack นึงเท่านั้นเอง
PHP7FPM or HHVM?
คำถามต่อมาคือ PHP ใน LEMP จะใช้อะไรดีนะ? หลักๆที่ใช้กันปกติก็ PHP7FPM กับ HHVM ซึ่งรีดประสิทธิภาพออกมาได้อย่างดีเยี่ยม
ทั้งสองตัวไม่มีข้อจำกัดทางด้านเทคนิค ก็คือทำได้ทุกอย่างที่ต้องใช้แหละ ที่สำคัญคือเรื่องของประสิทธิภาพและการกินทรัพยากรล้วนๆ
การ Research ตรงนี้ก็ไม่มีอะไรมากกว่าไป ... ลองเลย มันต้อง Benchmark อ่ะ อ่านตามเว็บต่างๆมันก็เชื่อไม่ได้เท่าไหร่ ทดสอบเองเลยละกัน ก็ตั้ง LEMP ไว้บน Environment จริง (DigitalOcean) เรียบร้อย โดยมีเงื่อนไขว่าต้องทำงานบนเครื่องต่ำๆ CPU 1 Core และแรม 1GB ได้
สุดท้ายหลังจากทดลองแล้วพบว่า HHVM (+JIT) กิน CPU สูงมากกกก ขึ้น 100% เป็นว่าเล่นเลย พอเป็นเครื่องต่ำๆก็เกิดคอขวดทาง CPU โดยทันที รับ Concurrent จากการยิงเข้าไปได้น้อยกว่า PHP7FPM เป็นเท่าตัว ยังไม่ได้ทดสอบบนเครื่องสเปคสูง แต่เนื่องจากโจทย์ของเราคือต้องทำงานบนเครื่องสเปคต่ำได้ดังนั้นก็เลยไม่ได้ทดสอบเพิ่ม
สรุปก็เลือกใช้ PHP7FPM ด้วยประสิทธิภาพที่ดีกว่า HHVM 2 เท่าตัว บนเครื่องทรัพยากรต่ำ
และเพื่อรีดประสิทธิภาพให้ PHP7FPM ทำงานดีขึ้นก็เปิด OPcache เพื่อแคชโค้ดด้วย ก็ได้ประสิทธิภาพดีขึ้นมาอีกหน่อยนึง
Framework ตัวไหนดี?: Laravel 5.x
เหตุผลเดียวกัน เคยใช้มาแล้ว แต่นี่ถือเป็นตัวแรกที่ใช้ Laravel 5.x ในโปรดักชัน จากที่ก่อนหน้านี้ใช้แต่ Laravel 4.x แต่ก็ไม่ใช่ปัญหาเพราะก่อนหน้านี้ก็ใช้ Laravel 5.x ทำโน่นทำนี่เล่นอยู่เรื่อยๆอยู่แล้ว
แต่แค่เคยใช้มาแล้วอย่างเดียวมันไม่พอหรอก ต้องมั่นใจว่ามันตอบโจทย์อย่างอื่นของโปรเจคนี้ด้วย มีเหตุผลอื่นที่ทำให้เลือกใช้ Laravel 5.x ในการพัฒนาอยู่ได้แก่
(1) Performance ถึงจะช้าแต่ก็อยู่ในระดับที่รับได้ ลอง ApacheBench และ wrk ดู ก็วัด Concurrent ได้ที่ 80 reqs/s บนเครื่อง CPU 1 Core RAM 1GB ซึ่งประสิทธิภาพอยู่ในระดับที่เพียงพอ นี่เฉพาะตัวที่ยิงเข้า Laravel นะ ถ้าเป็น Static File จะให้ Nginx เป็นคนจัดการซึ่งตรงนั้นได้ที่ 2000 reqs/s ดังนั้นโดยรวมแล้วเหลือเฟือครับ
(2) ได้รับความนิยมสูง หาคนมารับดูแลต่อในอนาคตได้ง่าย
(3) โครงสร้างโค้ดสวยงาม แนวคิดโครงสร้างออกแบบมาพร้อมระบบ Test เต็มรูปแบบ
เลยเลือก Laravel 5.x มาใช้ในการทำโปรเจคนี้ด้วยเหตุประการฉะนี้
Video Streaming Server: ตั้งเองหรือเช่าเค้าดี?
ฝั่ง Web ก็ Research ครบแล้ว ไม่ติดปัญหาด้านเทคนิคใดๆ แต่อีกฝั่งเนี่ยหนัก ... Video Streaming Server นั่นเอง
ส่วนตัวเคยเล่นมาบ้างแต่ก็แค่เล่นอ่ะนะ ไม่ได้ทำโปรดักชันจริง ความมั่นใจก็เลยไม่ได้สูงมาก งานส่วนนี้เลยถือเป็นส่วนที่ใช้เวลา Research และ Implement สูงสุดเลย
คำถามแรกของ Video Streaming Server เลยคือ ... จะไปใช้บริการ Video Hosting เช่น Wistia หรือจะไปใช้พวก Vimeo โฮสท์วีดีโอให้เรา หรือว่าจะตั้ง Server เองเลยดี?
โดยมีโจทย์อยู่สองข้อที่ค้ำคออยู่ในเรื่องนี้
1) คนไทยต้องเข้าถึงวีดีโอเร็วมาก มากๆ มากๆๆๆ
2) ต้อง Optimize ค่าใช้จ่าย ตอนสเกลขึ้นไม่ว่าจะเป็นจำนวนวีดีโอหรือจำนวนผู้ใช้จะต้องไม่กระทบค่าใช้จ่ายอย่างมีนัยสำคัญ (ไม่งั้นเจ๊ง)
หลังจาก Research อย่างบ้าคลั่งเรื่องราคาก็พบว่า Wistia นั้นสเกลไม่ได้ คิดราคาเป็นจำนวนวีดีโอ แพงมาก ส่วน Vimeo ก็สร้างประสบการณ์ผู้ใช้ได้ไม่ดี ไม่สามารถใช้งานแบบ Seamlessly บนเว็บที่ทำได้ จากนั้นก็ศึกษาไปอีกหลายบริการเหมือนกัน ก็เจอปัญหาเรื่องราคาและความเร็วทั้งสิ้น
สุดท้ายก็เลยมาศึกษาความเป็นไปได้ทางเทคนิคว่าเราจะตั้ง Server เองได้มั้ยและประสิทธิภาพเป็นยังไง
ก็ลองมาหลายตัวมาก เช่น nginx-vod-module ของ Kaltura, nginx-rtmp-module ของ arut แต่เจอปัญหาเรื่องประสิทธิภาพและฟังก์ชัน สุดท้ายก็เลยเลือกใช้ Nimble Streamer ซึ่งเป็น Freeware ที่เกิดขึ้นมาเพื่องาน Video Streaming โดยเฉพาะด้วยประสิทธิภาพที่ "เบามากกกกกกกกก" อันนี้เบามากจริงๆ ลองมาหลายตัว ไอ่ตัวนี้ถือว่าเบาสุดๆจริงๆ แถมฟีเจอร์ก็ครบครัน
สรุปก็เลยเลือกที่จะตั้ง Server เองและจัดการเองทุกอย่าง เพราะ Prove ความเป็นไปได้ทางเทคนิคเรียบร้อยแล้ว
Nimble Streamer เราเลือกนาย
ก่อนจะตัดสินใจตั้ง Server เองก็ใช้เวลาซัดกับมันนานพอสมควร หลักๆถึง Nimble Streamer จะฟรี แต่ตัว Config มันไม่ฟรี ถ้าต้องการ Config อะไรตัว Nimble Streamer จะต้องทำผ่านเว็บ WMSPanel ซึ่งมีค่าใช้จ่ายไม่แพงมาก 5 Servers แรกเดือนละ $20 เท่านั้นเอง เวลากดเปลี่ยน Config อะไรก็ตาม มันจะบันทึกเป็นไฟล์ json ส่งมาที่ Server เราให้โดยอัตโนมัติ สะดวกดีเลยหละ
ซึ่งมันก็เป็น Business Model ของเค้า จริงๆ Config เหล่านี้เขียนเป็น json เองก็ได้ แต่ว่าไม่มี Document ใดๆในโลกเขียนถึงจ้าาาา ดังนั้นก็คือเดาไม่ได้เลยว่าต้อง Config ว่าอะไร
แต่ก็คืองกไงงก ก็เลยใช้วิธีทดลองใช้ฟรี(เค้าให้สองอาทิตย์)แล้วก็แก้ไข Config โน่นนี่ทั้งหมดเท่าที่จะเป็นไปได้ แล้วก็นั่งหา diff ว่ามี json ตรงไหนโผล่ขึ้นมา ตรงไหนหายไป แล้วก็จดทำ Document เองซะเลย
หลังจากผ่านช่วงทดลองใช้ฟรีก็เลยสามารถ Config เองได้ด้วยประการฉะนี้ ทุกวันนี้ใช้ฟรีอยู่ตามเงื่อนไขสัญญานุญาตของผู้พัฒนา =D
ประสิทธิภาพของ Nimble Streamer ถือว่ายอดเยี่ยมมาก ใช้แรมน้อยมาก ซีพียูก็น้อยเข้าไปอีก ตามสเปคที่เค้าเขียนไว้คือ 1 Core สามารถจัดการวีดีโอได้สูงถึง 4Gbps ซึ่งคำนวณแล้วก็รับ Concurrent ได้ 200-400 ต่อ 1 Core เลยทีเดียว ดังนั้นไม่ต้องแปลกใจ เราสามารถตั้ง Video Streaming Server โดยใช้เครื่องสเปคต่ำสุดของ DigitalOcean ได้อย่างสบายและรับผู้ใช้ได้แบบเหลือเฟือเลยด้วยสเปคเท่านั้น
แถม Nimble Streamer ยังสนับสนุนโปรโตคอลมาตรฐานการทำ Streaming ได้ทุกรูปแบบอีกด้วย สุดท้ายหลังจากลองมาเยอะก็เลยตกลงปลงใจกับเจ้า Nimble Streamer แต่งงานกันเรียบร้อยจ้า
Video Streaming Technology: HLS
การเล่นกับวีดีโอเป็นอะไรที่เหนื่อยหนักเพราะต้องใช้ทรัพยากรเยอะ ถ้าทำไม่ดีก็กิน CPU บาน กินแรมบาน หรือไม่ก็แบนวิธเต็มจนรับ Concurrent ได้ไม่เยอะ
โจทย์คือ
1) จะทำยังไงให้โหลด Server ฝั่งนี้เบาที่สุดเพื่อให้ใช้จำนวน Server น้อยที่สุด
2) โปรโตคอลสตรีมวีดีโอต้องใช้ได้ทั้งบน Desktop และ Mobile
3) ต้องมีระบบ Security ที่ป้องกันการเข้าถึงวีดีโอโดยไม่ได้รับอนุญาตด้วย
ก็ไปเล่นมาเยอะพอสมควร RTMP, RTSP, PD, DASH ฯลฯ แต่สุดท้ายมาตกลงปลงใจที่ HLS เพราะมันตอบโจทย์ได้ทั้งหมด
HLS หรือ HTTP Live Streaming เป็นโปรโตคอลมาตรฐานในการสตรีมวีดีโอผ่าน HTTP ที่คิดค้นโดยแอปเปิ้ล หลักการทำงานของมันคือจะแบ่งวีดีโอออกเป็นชิ้นย่อยๆและให้ฝั่ง Client สามารถเลือกโหลดมาทีละชิ้นเพื่อเล่นได้ พอใกล้จะหมดชิ้นก็โหลดชิ้นใหม่มาเล่นต่อ (มันถึงเรียกว่า Streaming นั่นเอง)
ผลคือฝั่ง Server เบาลงมากเนื่องจากฝั่ง Client ไม่ได้โหลดวีดีโอมาทีเดียวหมด แต่จะคอยโหลดเฉพาะส่วนที่ผู้ใช้กำลังดูอยู่เท่านั้น เช่น วีดีโอความยาว 20 นาที มันก็โหลดมาแค่ 40 วินาที ทำให้ Server ทำงานเบาลงไปมหาศาลและยังกินแบนวิธน้อยลงมากๆอีกด้วย
Technical Challenge เล็กๆของ HLS คือมันเล่นแบบ Native ได้แค่บน Safari ที่เหลือต้องใช้ Javascript Plugin ในการเพิ่มความสามารถให้เล่นผ่าน HTML5 Video Player ได้ ซึ่งตรงนี้ก็ปวดหัวหน่อยๆแต่สุดท้ายก็ Work ออกมาได้
Prove เรียบร้อยว่า HLS สามารถใช้งานได้บนทุก Browser อย่างไม่มีปัญหาครับ ไม่ว่าจะเป็น Desktop หรือ Mobile ไม่มีปัญหาในอนาคตระยะยาวแน่นอน
ระบบ Security ป้องกันการละเมิดการเข้าถึง
Concern หลักๆข้อนึงของฝั่งคนสอนคือ ไม่อยากให้คนดูดวีดีโอไปได้ แต่ก็อย่างที่บอกมันกันไม่ได้ 100% หรอก แต่ช่องทางไหนกันได้ก็ควรทำให้เรียบร้อย ซึ่ง Nimble Streamer ก็มีระบบป้องกันการเข้าถึงไว้เรียบร้อย ล็อค IP ล็อคโน่นล็อคนี่ไว้ทำให้คนเข้าถึงแบบสุ่มมั่วซั่วไม่ได้
แต่ถึง Nimble Streamer จะทำให้แล้ว แต่เราก็ยังไม่พอใจในฟีเจอร์หลายๆอย่าง เราอยากจะล็อคกับระบบที่เราทำขึ้นมาเองด้วย และก็ไม่อยากให้สูตรวิธีการล็อคเป็นเหมือน Nimble Streamer ด้วยเพื่อป้องกันการโดนแฮค สุดท้ายก็เลยทำระบบล็อคขึ้นมาเองผ่านหน้าด่านก่อนจะเข้าถึง Nimble Streamer อย่าง nginx นั่นเอง
ตรงนี้ใช้ภาษา Lua ซึ่ง Integrate โดยตรงกับ nginx เข้ามาช่วยในการจัดการ (ศึกษาความเป็นไปได้และ Prove of Concept เรียบร้อย ณ จุดที่ Research)
การเก็บวีดีโอใน Resolution ต่างๆ
อีกวิธีนึงที่จะช่วยลดโหลดทางฝั่ง Server ได้และยังเพิ่มประสบการณ์ผู้ใช้งานฝั่ง Client ได้อีกด้วยคือการรองรับ Video Resolution ต่างๆเพื่อให้เหมาะสมกับฝั่ง Client
สรุปก็แบ่งวีดีโอไว้ 3 Resolutions คือ 1080p, 720p และ 480p แต่ตอนรันจริงก็ปล่อยออกมาแค่ 1080p และ 720p เพราะ 480p ภาพแตกเกินไปจนอ่านโค้ดไม่รู้เรื่องนั่นเอง แต่ก็ทำเผื่อไว้
โดย Default เพื่อให้ Server รับโหลดเบาที่สุด ทุกคนจะถูกเซตความละเอียดวีดีโอไว้ที่ 720p แต่ถ้าใครต้องการวีดีโอที่ละเอียดขึ้นก็ปรับเป็น 1080p ได้ ซึ่งก็ไม่ใช่ปัญหาอะไรเพราะมันเป็น Streaming พอสลับปุ๊บก็โหลด Chunk ของวีดีโอเฉพาะส่วนนั้นขึ้นมาใหม่เท่านั้นเอง
ส่วนเทคนิคที่ใช้ทำคือ Pre-resize ไว้และอัปโหลดทุก Resolution ขึ้นไปบน Server เพื่อให้ Server จะได้ไม่ต้อง Resize แบบ Real Time ลดโหลดไปได้เยอะครับ
ทั้งนี้การแบ่งวีดีโอเป็น Resolution ต่างๆเป็นสิ่งจำเป็นมาก โดยเฉพาะอย่างยิ่งตอนเอาไปรันบนมือถือที่มี CPU ช้าเร็วต่างกัน เราควรต้องเลือกวีดีโอขนาดที่เหมาะสมด้วยไม่งั้นจะเล่นไม่ได้
ทำ HTML5 Video Player เอง: Video.js
ฝั่ง Front End ก็เป็นงานอีกส่วนที่ค่อนข้างเหนื่อย โดยเฉพาะส่วนของ Video Player ที่ต้อง Custom ให้เหมาะกับฟังก์ชันที่ทำขึ้นมาของ Online Learning Platform
จะใช้ตัว Native Video Player ทั่วไปก็ไม่ได้เพราะฟีเจอร์ไม่ครบ เช่น ปรับ Resolution ก็ไม่ได้ ทำสตรีม HLS ก็ไม่ได้ ปรับความเร็วในการเล่นก็ไม่ได้
สุดท้ายก็เลย Build ขึ้นมาเองซะะะ โดยเลือกใช้ Video.js ซึ่งเป็น Player Framework ชื่อดังอันดับต้นๆของโลก มีปลั๊กอินให้ลงเพิ่มมากมายมหาศาลครบครันบานตะไท
ใช้ Cloud Server DigitalOcean โหนดสิงคโปร์
จะทำยังไงให้คนไทยเข้าถึงได้เร็วที่สุด? ตอบได้อย่างรวดเร็ว ... ก็ตั้ง Server ในไทยสิ
ก็เลย Research หา Cloud Server ในไทย เปิดโน่นเปิดนี่เล่นไว้หลายที่ โดยใช้เวลาทดสอบหลายเดือนอยู่ เพราะการ Research ด้านนี้มันไม่ใช่แค่ความเป็นไปได้ แต่เป็นเรื่องของความเสถียรในระยะยาวอีกด้วย
ในช่วงแรกที่ปล่อยไปก็ไปโฮสต์ที่ AR-BRO.com แต่ปรากฎว่าเกิดปัญหาหลายอย่างในช่วงหลังก็เลยย้ายไปอยู่ที่ DigitalOcean โหนดสิงคโปร์แทน
โจทย์ข้อนึงของการเลือก Server คือเงื่อนไขด้านจำนวน Data Transfer เพราะเราทำ Video Streaming อาจจะมีการ Surge ของ Bandwidth ได้เรื่อยๆ ซึ่งถึง DigitalOcean จะมีการระบุจำนวน Transfer ที่อนุญาตไว้ที่หน้า Pricing แต่ในแง่ปฏิบัติแล้ว DigitalOcean ก็ยังไม่ได้คิดเงินค่า Transfer ที่เกินมาเพราะระบบวัดยังไม่เสถียรพอนั่นเอง สรุปคือใช้ Transfer ได้อันลิมิต
ตอนนี้ก็เลยฝากของไว้อยู่บน DigitalOcean โอเคดีมากครับ
Docker
โจทย์สุดท้ายของระบบนี้คือ "ต้องสเกลได้" ซึ่งก็จะสอดคล้องกับคำว่า "ต้อง Deploy ง่าย" งานนี้ก็เลยจับยัดทุกอย่างไว้ใน Docker ให้เป็นชิ้นๆที่สามารถขยายขึ้นหรือลงได้เพื่อที่จะได้ยกไปตั้งที่ไหนก็ได้และสามารถ Deploy ได้ด้วยบรรทัดเดียว (docker-compose)
โดยการสเกลนี้จะต้องสเกลได้หมดเลยทั้งฝั่ง Web และฝั่ง Video Streaming Server ก็คือถ้า Server รับโหลดไม่ไหวจะต้องขึ้น Server ใหม่เพื่อรับการสเกลได้ใน 1 นาทีอะไรทำนองนี้ ซึ่งส่งผลต่อการออกแบบ Container ด้วย แต่จะอธิบายละเอียดในบล็อกถัดไป โดยรวมแล้ว Docker ที่มันเกิดมาเพื่อการณ์นี้ก็ทำงานของมันได้ดี
ผลพลอยได้ของการใช้ Docker ก็คือเราสามารถควบคุม Development Environment ให้เหมือนกับ Production ได้(เกือบ)ทุกประการ ก็คือเรา Dev บน Windows และ Mac OS X แต่ Server จริงเราเป็น Ubuntu 14.04.4 LTS
ซึ่งก็ไม่ใช่ปัญหาอีกต่อไปเพราะตอน Dev เราก็ตั้ง Docker Machine ไว้บน Windows และ Mac OS X และรันอิจเมจตัวเดียวกับที่ใช้ใน Production ทำให้มั่นใจได้ว่าตอนไปทำงานบน Production จะไม่มีปัญหาแน่ๆเพราะเป็น Environment เดียวกันเกือบจะเป๊ะๆ
จะมีปัญหาบ้างก็เรื่อง Permission ที่ Windows ดันเป็น 777 (เพราะ Windows ไม่มีระบบ Permission) หรือถ้ารันบน Mac OS X ก็จะเจอปัญหา Permission เช่นกันจากเรื่องของ User/Group ไม่ตรงกัน แต่ก็มี Workaround อยู่ หรือถ้าใช้ Vagrant ครอบอีกชั้นก็อาจจะช่วยได้ แต่เราไม่ได้ใช้อ่านะ ใช้แค่ Docker Machine ปกติ
มีคนถามว่าเราใช้ Docker ใน Development Machine ด้วยมั้ย คำตอบก็ตามนี้ครับ ใช้ และทำให้ชีวิตดีขึ้นมากๆ สิ่งที่ชอบสุดๆเลยคือเราไม่ต้องลงแอปอะไรบนเครื่อง Development เลยนอกจาก Docker Engine แล้วก็จิ้มบรรทัดเดียวมันก็ขึ้นมาให้ใช้งานเลย และถ้ามีเหตุให้เปลี่ยนคอมพ์สำหรับ Dev ก็เซตแป๊บเดียวแล้วทำงานต่อได้เลย นั่นเองทำให้การ Deploy ทำได้ง่ายมาก
ส่วนโครงสร้างของ Docker Image / Container ที่ทำขึ้นมาเป็นยังไงไว้ไปต่อกันอีกทีในเรื่องของการวาง Infra ครับ =)
สรุป
ทั้งหมดที่เขียนในบล็อกนี้ ผมทำก่อนเริ่มเขียนโค้ดและก่อนมาประกาศให้ทุกคนรู้ผ่านบล็อกว่าจะทำระบบของตัวเอง
ถ้ายัง Research ไม่เสร็จก็ยังพูดไม่เต็มปากหรอกว่ามันทำได้ มันเป็นไปได้ทางเทคนิค ศึกษา Feasibility Study เยอะๆ สำคัญมาก
ก็ Research ให้เยอะๆไว้ครับ เป็นสัปดาห์ก็คุ้มเพราะมันจะประหยัดเวลาระยะยาวได้เยอะมาก จากการพัฒนา 6 เดือนอาจจะเหลือ 1 เดือนถ้า Research ถูก
ใจความสำคัญของการ Research คือ "การตั้งคำถาม" ครับ คุณต้องรู้ก่อนว่าในเนื้องานที่คุณกำลังจะต้องทำนั้นคุณยังไม่รู้อะไรและคุณต้องรู้อะไร จากนั้นก็ไปหาคำตอบมาซะ จริงๆมันเหมือน MVP เลยนะ คือการทำชิ้นงานที่เล็กที่สุดที่เป็นไปได้เพื่อเอาคำตอบว่าเราสามารถทำสิ่งนั้นๆได้มั้ยหรือควรทำมั้ย ไม่ง่ายและไม่ยากครับ อยู่ที่สกิลการตั้งคำถามให้ตัวเอง หลายผลงานที่ทำมาเป็นปีแล้วไม่ได้ Launch ส่วนใหญ่ก็ผิดพลาดตรงนี้ ไม่รู้ว่าตัวเองไม่รู้อะไรและดันทุรังทำจนต้องรื้อใหม่ซ้ำแล้วซ้ำอีก
ด้านเทคนิคยังไม่จบครับ ยังมีอีกหลายเรื่องเลย สำหรับบล็อกถัดไปจะมาพูดถึงเรื่องการวาง Infra ด้วย Docker กันครับ ตอนแรกว่าจะใส่ในบล็อกนี้เลย แต่ไปๆมาๆเหมือนบล็อกจะยาวเกินไปละ ไว้เจอกันบล็อกหน้าละกันครับ =D