Promise, Async, Await ของ JS ES6+ ฉบับสั้นๆ ไม่พูดเยอะ เจ็บคอ แถม RxJS
อ่านฉันหน่อย: บทความนี้ใช้ javascript ES6 นะครับ ใครยังไม่ชินไปตามอ่านได้ใน Cheat sheet นี้เลย มีภาษาไทยด้วย
https://github.com/mbeaudru/modern-js-cheatsheet/blob/master/translations/th-TH.md
หมายเหตุ ต่อไป: ผมเขียน Python, C เป็นหลักนะครับ Java เป็นรอง แต่เขียน Async บน Java ด้วย ดังนั้น อาจจะไม่ถูกใจขา JS
สวัสดีครับ บล็อกนี้มาสั้นๆ ไม่เกริ่นทีมา ว่าทำไมถึงใช้ และหลักการต่างๆ ข้ามไว้ก่อน เพราะเราขี้เกียจเขียน (ไว้ค่อยกลับมาเขียน 555)
สรุปสั้นๆ
- ใช้ Promise เพื่อแก้ปัญหา Callback Hell
- ใช้ Async, Await เพื่อไม่ต้องใช้
.then()
แล้วยังไงล่ะ ไปดู - เนื่องจาก Promise
resolve
ได้แค่ครั้งเดียว ถ้าอยากresolve
หลายครั้ง เช่นข้อมูลแบบ stream ใช้ RxJS เพื่อแก้ปัญหา
สรุปจบ ไปดูโค๊ด
เราจะเขียน Promise กันง่ายๆ คือ ให้ฟังชั่นที่ทำงานนานๆ ตัวนึงชื่อ upperAfter
โดยทำหน้าที่แปลงเป็นตัวพิมพ์ใหญ่ หลังจาก 2 วินาที ไปดูตัวอย่างกัน
1. Promise
;
เมื่อเรารัน main()
แล้ว มันจะทำงานดังนี้
- เรียก
upperAfter('test',2000)
จะ return เป็น Promise ออกมา - object ของ promise จะสามารถต่อด้วย
.then()
หรือ.catch()
ก็ได้- ถ้าทำสำเร็จก็ใช้
.then()
(คือค่า ที่ถูก resolve ออกมา ในที่นี้คือtext.toUpperCase()
) - ถ้าทำไม่สำเร็จก็ใช้
.catch()
(คือค่า ที่ถูก reject ออกมา )
- ถ้าทำสำเร็จก็ใช้
- เมื่อเรียก
.then()
ค่าของข้อความจะมาใส่มาในdata
เราก็สามารถเอาdata
ไปต้มยำทำแกงอะไรก็ได้ เย้ จบ!
ข้อสังเกตุ คือเราใช้ .then()
เพื่อทำให้ Blocking i/O หรือ Synchronous นั้นเอง คล้ายกับการเรียก callback นั้นแล แต่ .then()
เราสามารถต่อกันได้ ทำให้โค้ดสวยมากขึ้น และ debug ง่ายขึ้นนะ
2. Async, Await
เอาโค้ดข้างบนมาแก้ main
ใหม่
เป็นไงล่ะ ทำงานได้เหมือนเดิม แต่ชีวิตง่ายขึ้นมั้ย ทีนี้เราก็ทำตัวเหมือนเขียน Blocking I/O หรือ Synchronous แบบ C, Python ได้แล้ว เจ๋งป่ะล่ะ
ข้อสังเกตุ ฟังก์ชัน main()
ต้องเป็น async
เพื่อบอกว่าฟังก์ชันนี้มี การทำ blocking I/O หรือ Synchronous อยู่นะ เราใส่ await
หน้า promise นั้นเอง มันจะ auto .then()
ให้เลย สะดวกสุดๆ
ในบรรทัดนี้ const data = await upperAfter('test',2000)
อารมณ์เหมือนเราได้ค่า data
มาเลย แล้วก็เอาไปทำอะไรต่อก็ได้ ไม่ต้องอยู่ใน .then()
แล้ว
ก่อนปิดบล็อก
อ่าวจบแล้ว? RxJS ล่ะ เอาแค่นี้ก่อน พอรู้ข้อจำกัดของการใช้ Promise แล้ว คราวหน้า เราสามารถไปใช้ RxJS ได้
ของแถม แล้ว Promise มาช่วยแก้ปัญหา Callback Hell ยังไง
อันนี้เอาตัวอย่างมาจาก โปรเจ็ค promise-it-wont-hurt
ของ https://nodeschool.io/
อันนี้เค้าเรียกกันว่า Callback Hell ถ้ามีมากกว่าหลายชั้นก็นี้ก็ hell จริงๆ ละคับ
'user', 'pass', ;
แล้วถ้าใช้ Promise ช่วยล่ะ
'user', 'pass';
เป็นไงบ้าง ดูง่ายขึ้นเยอะมั้ย ครับ
พอล่ะไม่อธิบายเยอะ เจ็บขอ แล้วพบกันใหม่ครับ
อ่านเพิ่มเติม
- Modern JS Cheat sheet one-stop cheat sheet for JS developer
- https://nodeschool.io/ เว็บนี้ก็ดีงาม สอน JS แบบ interactive เลย
- ES6 Cheat sheet: https://github.com/DrkSephy/es6-cheatsheet อันนี้ก็ดีนะ ไปดูได้
Cross published at Medium.com