Promise و زنجیره Promise
در جاوااسکریپت، Promise یک ابزار اساسی برای مدیریت عملیاتهای غیرهمزمان (Asynchronous) است. Promise نمایندهی نتیجهای است که ممکن است در آینده حاصل شود و میتواند موفق یا ناموفق باشد. زنجیره Promise (Promise Chain) به شما امکان میدهد چند عملیات غیرهمزمان را به ترتیب اجرا کنید، بهطوری که نتیجه یک عملیات به عملیات بعدی منتقل شود. میتوان این فرآیند را شبیه به ساختن یک خانه، تزئین یک اتاق، نوشتن یک نامه یا سازماندهی یک کتابخانه در نظر گرفت؛ هر مرحله باید به ترتیب و با دقت انجام شود.
در وبسایتهای فروشگاه آنلاین، خبرگزاری، وبلاگ شخصی یا پرتالهای دولتی، بارگذاری دادهها به صورت غیرهمزمان یک ضرورت است. برای مثال، ابتدا باید لیست محصولات یا اخبار را بارگذاری کرد و سپس جزئیات هر مورد را نمایش داد. بدون استفاده از Promise، کد به سرعت وارد Callback Hell میشود که نگهداری آن دشوار است.
در این آموزش، یاد میگیرید که چگونه Promise بسازید، موفقیت و خطا را مدیریت کنید، از متدهای then، catch و finally استفاده کنید و زنجیره Promise را برای جریانهای پیچیده بسازید. مثالهای عملی، اجرای توالیها و عملیات موازی، مدیریت خطا و کاربرد واقعی در وبسایتهای مختلف را نشان میدهند. پس از مطالعه این آموزش، شما قادر خواهید بود منطق غیرهمزمان را به شکل سازمانیافته و قابل پیشبینی پیادهسازی کنید، مانند سازماندهی یک کتابخانه یا نوشتن یک نامه مرحله به مرحله.
مثال پایه
javascript// ایجاد یک Promise پایه و مدیریت آن
const fetchData = () => {
return new Promise((resolve, reject) => {
const success = true; // شبیهسازی نتیجه عملیات
if (success) {
resolve("داده با موفقیت دریافت شد"); // حالت موفق
} else {
reject("خطا در دریافت داده"); // حالت خطا
}
});
};
fetchData()
.then(result => console.log(result)) // مدیریت موفقیت
.catch(error => console.error(error)); // مدیریت خطا
در این مثال، تابع fetchData یک Promise برمیگرداند. سازنده Promise دو آرگومان resolve و reject میگیرد. resolve نشاندهنده موفقیت عملیات و ارسال نتیجه به then بعدی است، و reject برای ارسال خطا به catch استفاده میشود. متغیر success نتیجه عملیات را شبیهسازی میکند.
وقتی fetchData() فراخوانی میشود، یک Promise برگردانده میشود. then برای مدیریت موفقیت و catch برای مدیریت خطا استفاده میشود. این ساختار، کد را از callbackهای تو در تو آزاد میکند و نگهداری آن آسانتر است. در فروشگاه آنلاین، ابتدا لیست محصولات و سپس جزئیات موجودی هر محصول را میتوان به همین ترتیب فراخوانی کرد. هر مرحله مشابه تزئین یک اتاق یا نوشتن یک پاراگراف در نامه است.
مثال کاربردی
javascript// مثال عملی با زنجیره Promise در یک وبلاگ
const fetchPosts = () => {
return new Promise((resolve) => {
setTimeout(() => resolve(\["خبر ۱", "خبر ۲", "خبر ۳"]), 1000);
});
};
const fetchComments = (post) => {
return new Promise((resolve) => {
setTimeout(() => resolve(`کامنتها برای ${post}`), 500);
});
};
fetchPosts()
.then(posts => {
console.log("پستها:", posts);
return fetchComments(posts\[0]); // دریافت کامنتهای پست اول
})
.then(comments => console.log(comments))
.catch(error => console.error("خطا:", error))
.finally(() => console.log("عملیات تکمیل شد"));
در این مثال عملی، دو تابع fetchPosts و fetchComments داریم. fetchPosts پس از ۱ ثانیه لیست پستها را resolve میکند و fetchComments پس از ۰.۵ ثانیه کامنتهای یک پست را برمیگرداند.
زنجیره Promise با fetchPosts().then(...) شروع میشود. ابتدا پستها در کنسول چاپ میشوند و سپس fetchComments برای اولین پست فراخوانی میشود. then بعدی کامنتها را نمایش میدهد. catch برای مدیریت خطا و finally برای عملیات نهایی یا cleanup استفاده میشود.
این ساختار اطمینان میدهد که عملیاتها به ترتیب اجرا میشوند، مشابه سازماندهی یک کتابخانه یا تزئین مرحله به مرحله یک اتاق. در پرتالهای خبری، پروفایل کاربران و پستها میتوانند به همین ترتیب فراخوانی شوند تا جریان دادهها قابل پیشبینی و منظم باشد.
Best Practices و اشتباهات رایج:
Best Practices:
- استفاده از async/await برای خوانایی بهتر کد.
- همیشه از catch یا try/catch برای مدیریت خطا استفاده کنید.
- تقسیم عملیات غیرهمزمان به توابع کوچک برای حفظ وضوح زنجیره.
-
استفاده از Promise.all برای اجرای موازی عملیاتها و بهینهسازی عملکرد.
اشتباهات رایج: -
عدم مدیریت خطاها که باعث silent failure میشود.
- بازنگرداندن Promise که باعث قطع شدن زنجیره میشود.
- استفاده بیش از حد از then تو در تو، که منطق کد را پیچیده میکند.
- حذف finally که باعث عدم اجرای cleanup میشود.
نکات Debug:
- از console.log و debugger برای ردیابی وضعیت Promise استفاده کنید.
- اطمینان حاصل کنید که هر then یک مقدار یا Promise بازمیگرداند.
- درخواستهای شبکه و setTimeout را مانیتور کنید تا از memory leak جلوگیری شود.
📊 مرجع سریع
Property/Method | Description | Example |
---|---|---|
Promise | نماینده یک عملیات غیرهمزمان | const p = new Promise((res, rej) => res("موفق")) |
then | مدیریت نتایج موفق | p.then(result => console.log(result)) |
catch | مدیریت خطا | p.catch(error => console.error(error)) |
finally | اجرای عمل نهایی بدون توجه به نتیجه | p.finally(() => console.log("تکمیل شد")) |
Promise.all | اجرای موازی چند Promise | Promise.all(\[p1, p2]).then(results => console.log(results)) |
Promise.race | اولین Promise تکمیل شده را بازمیگرداند | Promise.race(\[p1, p2]).then(result => console.log(result)) |
خلاصه و مراحل بعدی:
این آموزش مفاهیم اصلی Promise و زنجیره Promise را پوشش داد، از جمله ایجاد Promise، استفاده از then، catch و finally و ساخت زنجیرههای ترتیبی. اکنون میتوانید جریانهای غیرهمزمان را در فروشگاههای آنلاین، وبلاگها، سایتهای خبری و پرتالهای دولتی سازماندهی کنید.
Promises به راحتی با HTML DOM ترکیب میشوند تا دادهها به صورت دینامیک نمایش داده شوند و در ارتباط با backend، تعاملات API قابل پیشبینی و نگهداریپذیر خواهند بود.
مرحله بعدی مطالعه async/await، Promise.all و Promise.race و پیادهسازی آنها در APIهای واقعی است. استفاده عملی از این مفاهیم مهارت شما در برنامهنویسی غیرهمزمان جاوااسکریپت را تقویت خواهد کرد.
🧠 دانش خود را بیازمایید
آزمون دانش شما
درک خود از این موضوع را با سوالات کاربردی بسنجید.
📝 دستورالعملها
- هر سوال را با دقت بخوانید
- بهترین پاسخ را برای هر سوال انتخاب کنید
- میتوانید آزمون را هر چند بار که میخواهید تکرار کنید
- پیشرفت شما در بالا نمایش داده میشود