คลาส Promise ใน JavaScript
ในบทความนี้ เราจะอธิบายเกี่ยวกับคลาส Promise ใน JavaScript
YouTube Video
Promise
คลาส Promise เป็นคลาสสำหรับจัดการการทำงานแบบอะซิงโครนัส มันจัดการผลลัพธ์ในกรณีที่การทำงานสำเร็จ หรือจัดการข้อผิดพลาดในกรณีที่ล้มเหลว ในอดีต เราใช้งานฟังก์ชันคอลแบ็คเมื่อจำเป็นต้องรอการทำงานแบบอะซิงโครนัสให้เสร็จสิ้น แต่ Promise ทำให้สิ่งนี้ชัดเจนและทรงพลังยิ่งขึ้น
1const promise = new Promise((resolve, reject) => {
2 setTimeout(() => resolve("Done!"), 1000);
3});
4
5// Displays "Done!" after 1 second
6promise.then(result => console.log(result));- โค้ดนี้เป็นตัวอย่างของกระบวนการแบบอะซิงโครนัสที่แสดงข้อความ "เสร็จสิ้น!" หลังจากหนึ่งวินาที
- ก่อนอื่นจะมีการสร้างอ็อบเจ็กต์
Promiseใหม่โดยใช้new Promiseอาร์กิวเมนต์เป็นฟังก์ชันที่รับ callback สองตัว:resolveสำหรับความสำเร็จและrejectสำหรับความล้มเหลว setTimeoutถูกใช้เพื่อเรียกresolve()หลังจากหนึ่งวินาที- เมธอด
then()ของอ็อบเจ็กต์promiseจะรอให้กระบวนการเสร็จสิ้นและแสดงผลลัพธ์
- ก่อนอื่นจะมีการสร้างอ็อบเจ็กต์
โครงสร้างพื้นฐาน
Promise คืออ็อบเจ็กต์ที่ท้ายที่สุดจะนำไปสู่สถานะ สำเร็จ หรือ ล้มเหลว
1const promise = new Promise((resolve, reject) => {
2 // Asynchronous operation
3 // Flag indicating whether the operation was successful
4 const success = true;
5
6 if (success) {
7 resolve('Operation successful!');
8 } else {
9 reject('An error occurred');
10 }
11});- ในกรณี สำเร็จ จะมีการเรียกใช้
resolve() - ในกรณี ล้มเหลว จะมีการเรียกใช้
reject()
ออบเจกต์ Promise มีสามสถานะ
1promise
2 .then((result) => {
3 console.log(result);
4 })
5 .catch((error) => {
6 console.error(error);
7 })- รอดำเนินการ
- กระบวนการอะซิงโครนัสยังไม่เสร็จสิ้น
- สำเร็จ
- กระบวนการอะซิงโครนัสสำเร็จ และผลลัพธ์ถูกส่งกลับโดย
resolve()ผลลัพธ์จะได้รับโดยใช้เมธอดthen()
- กระบวนการอะซิงโครนัสสำเร็จ และผลลัพธ์ถูกส่งกลับโดย
- ล้มเหลว
- กระบวนการอะซิงโครนัสล้มเหลว และเกิดข้อผิดพลาดผ่าน
reject()ข้อผิดพลาดจะได้รับโดยใช้เมธอดcatch()
- กระบวนการอะซิงโครนัสล้มเหลว และเกิดข้อผิดพลาดผ่าน
เมธอด then() และ catch()
เมื่อใช้ Promise คุณสามารถกำหนดว่าควรทำอะไรเมื่อการทำงานแบบอะซิงโครนัสเสร็จสมบูรณ์ คุณสามารถทำได้โดยใช้เมธอด then() และ catch()
then()
1const promise = new Promise((resolve, reject) => {
2 resolve('Operation successful!');
3});
4
5promise.then((result) => {
6 console.log(result); // "Operation successful!"
7});- เมธอด
then()ระบุฟังก์ชันที่จะถูกเรียกใช้งานเมื่อPromiseสำเร็จ
catch()
1const promise = new Promise((resolve, reject) => {
2 reject('An error occurred');
3});
4
5promise.catch((error) => {
6 console.error(error); // "An error occurred"
7});- เมธอด
catch()ระบุฟังก์ชันที่จะถูกเรียกใช้งานเมื่อPromiseล้มเหลว
เมธอด finally()
1const promise = new Promise((resolve, reject) => {
2 resolve('Operation successful!');
3});
4
5promise
6 .then((result) => {
7 console.log(result);
8 })
9 .catch((error) => {
10 console.error(error);
11 })
12 .finally(() => {
13 console.log('The operation has completed');
14 });- เมธอด
finally()ระบุโค้ดที่จะถูกดำเนินการในขั้นตอนสุดท้าย ไม่ว่าจะPromiseสำเร็จหรือล้มเหลวก็ตาม
การเชื่อมต่อแบบ then()
then() ส่งกลับ Promise ใหม่ ดังนั้นคุณสามารถ เชื่อมต่อ then() ถัดไปได้
1const promise = new Promise((resolve, reject) => {
2 setTimeout(() => {
3 resolve(1);
4 }, 1000);
5});
6
7promise
8 .then(result => {
9 console.log(result); // 1
10 return result + 1;
11 })
12 .then(result => {
13 console.log(result); // 2
14 return result + 1;
15 })
16 .then(result => {
17 console.log(result); // 3
18 })
19 .catch(error => {
20 console.error(error.message); // Something went wrong
21 });- ในโค้ดนี้
resolve()เริ่มต้นจะส่งผ่านค่า 1 และแต่ละค่าที่ถูกส่งกลับโดยthenจะถูกส่งต่อไปยังthenถัดไป - โดยการใช้
catch()คุณสามารถจัดการข้อผิดพลาดที่เกิดขึ้นในสายเชื่อมต่อทั้งหมดได้ในที่เดียว
ตัวอย่างเชิงปฏิบัติ
ตัวอย่างเช่น Promises มักใช้ในการดึงข้อมูลจากเซิร์ฟเวอร์ มาดูตัวอย่างที่ใช้ fetch() API กัน
1fetch('https://codesparklab.com/json/example.json')
2 .then(response => {
3 if (!response.ok) {
4 throw new Error('Network error');
5 }
6 return response.json();
7 })
8 .then(data => {
9 console.log(data);
10 })
11 .catch(error => {
12 console.error('Error:', error);
13 });- ในโค้ดนี้, เนื่องจาก
fetch()คืนค่าเป็นPromise, จึงใช้then()ในการประมวลผลข้อมูลหลังจากได้รับการตอบกลับจากเซิร์ฟเวอร์ ข้อผิดพลาดจะถูกจัดการด้วยcatch()
การจัดการ Promises หลายตัว
Promise.all()
หากต้องการดำเนินการ Promises หลายตัวพร้อมกันและดำเนินการต่อหากทุกตัวสำเร็จ, ให้ใช้ Promise.all()
1const promise1 = Promise.resolve(1);
2const promise2 = Promise.resolve(2);
3const promise3 = Promise.resolve(3);
4
5Promise.all([promise1, promise2, promise3])
6 .then((results) => {
7 console.log(results); // [1, 2, 3]
8 })
9 .catch((error) => {
10 console.error('Error :', error);
11 });then()จะถูกเรียกใช้ก็ต่อเมื่อPromisesทุกตัวสำเร็จcatch()จะถูกเรียกใช้หากแม้แต่ตัวเดียวล้มเหลว
Promise.allSettled()
หากคุณต้องการรัน Promise หลายรายการพร้อมกันและรับผลลัพธ์ทั้งหมดไม่ว่าจะสำเร็จหรือไม่ ให้ใช้ Promise.allSettled()
1const promise1 = Promise.resolve(1);
2const promise2 = Promise.reject("Failed");
3const promise3 = Promise.resolve(3);
4
5Promise.allSettled([promise1, promise2, promise3])
6 .then((results) => {
7 results.forEach(result => console.log(result));
8 // [
9 // { status: 'fulfilled', value: 1 },
10 // { status: 'rejected', reason: 'Failed' },
11 // { status: 'fulfilled', value: 3 }
12 // ]
13 });then()จะถูกรันเมื่อPromiseทั้งหมดสิ้นสุด (ไม่ว่าจะสำเร็จหรือล้มเหลว) แต่ละผลลัพธ์จะมีพร็อพเพอร์ตี้status('fulfilled'หรือ'rejected') แม้ว่าบางอันจะล้มเหลว ก็จะไม่ส่งผลกระทบต่อการทำงานอื่น ๆ
Promise.race()
Promise.race() จะคืนค่าผลลัพธ์ของ Promise ที่เสร็จก่อน ไม่ว่าจะสำเร็จหรือไม่สำเร็จก็ตาม
1const promise1 = new Promise((resolve) => setTimeout(resolve, 100, 'First'));
2const promise2 = new Promise((resolve) => setTimeout(resolve, 500, 'Second'));
3
4Promise.race([promise1, promise2]).then((result) => {
5 console.log(result); // "First"
6});- เช่นเดียวกับในตัวอย่างนี้ ผลลัพธ์ของ
Promiseที่เสร็จสิ้นก่อนจะถูกรายงานกลับมา
ความสัมพันธ์กับ async/await
การใช้ไวยากรณ์ async/await ช่วยให้เขียน Promises ได้อย่างเข้าใจง่ายขึ้น ฟังก์ชัน async จะคืนค่าเป็น Promise เสมอ และ await จะรอให้ Promise ได้รับการแก้ไข
1async function fetchData() {
2 try {
3 const response = await fetch('https://codesparklab.com/json/example.json');
4 const data = await response.json();
5 console.log(data);
6 } catch (error) {
7 console.error('Error :', error);
8 }
9}
10
11fetchData();โดยการใช้ async/await แบบนี้, การดำเนินการแบบ asynchronous สามารถเขียนให้เหมือนโค้ดแบบ synchronous ทำให้อ่านง่ายขึ้น
สรุป
Promiseเป็นอ็อบเจ็กต์ที่ใช้จัดการการสำเร็จหรือล้มเหลวของการดำเนินการแบบ asynchronous- จัดการการดำเนินการที่สำเร็จด้วย
then()และข้อผิดพลาดด้วยcatch() finally()กำหนดโค้ดที่จะถูกดำเนินการในตอนท้ายไม่ว่าจะสำเร็จหรือล้มเหลว- คุณสามารถจัดการ
Promiseหลายตัวพร้อมกันได้โดยใช้Promise.all()หรือPromise.race() async/awaitเป็นไวยากรณ์สำหรับเขียนPromiseให้เรียบง่ายขึ้น
คุณสามารถติดตามบทความข้างต้นโดยใช้ Visual Studio Code บนช่อง YouTube ของเรา กรุณาตรวจสอบช่อง YouTube ด้วย