javaScript Promise Kullanımı
Promise(Sözler), JavaScript'teki eşzamansız(zaman uyumsuz) işlemlerle başa çıkmanın yollarından biridir.
JavaScript Promise
, eşzamansız bir işlemin sonucunu elde etmek için, bu sonuç anında elde edilemediğinde kullanılabilen bir nesnedir.
JavaScript kodları engellemeyen bir şekilde çalıştığından, kodların geri kalanının yürütülmesini engellemeden eşzamansız bir işlem beklememiz gerektiğinde promise
nesnesi önemli hale gelir.
JavaScript'teki bir söz, gerçek hayattaki bir söze benzer. Gerçek hayatta bir söz verdiğimizde, gelecekte bir şeyler yapacağımızın garantisidir. Çünkü sözler ancak gelecek için verilebilir.
Bir sözün 2 olası sonucu vardır: Ya zamanı geldiğinde gerçekleşir ya da olmaz.
Bu, JavaScript'teki promise
Nesneler için de aynıdır. JavaScript'te bir söz tanımladığımızda, zamanı geldiğinde Gerçekleşek veya reddedilecektir.
JavaScript Promises
Her şeyden önce, bir Söz(promise) bir nesnedir. Promise
nesnesinin 3 durumu vardır:
- Pending(Beklemede): Promise(söz) başarılı veya başarısız olmadan önce İlk Durum
- Resolved:(Gerçekleşti):Tamamlanmış Promise(Söz)
- Rejected:(Reddedildi):Başarısız Promise(Söz)
Örneğin, bir Promise Nesnesini kullanarak sunucudan veri istediğimizde, verilerimizi alana kadar bekleme modunda kalacaktır.
Bilgiyi sunucudan almayı başarırsak, promise
başarıyla Resolved
(Gerçekleşti) Ancak bilgiyi alamazsak, promise Rejected
(reddedilmiş) durumda olacaktır.
Ek olarak, birden fazla istek varsa, ilk Söz Gerçekleştikten (veya reddedildikten) sonra, zincirleme adı verilen bir yöntemle onu doğrudan ekleyebileceğimiz yeni bir süreç başlayacaktır.
Callbacks ve Promises arasındaki fark nedir?
callback
nedir dersek bir hatırlıyalım: Callback
, en basit haliyle herhangi bir fonksiyona parametre olarak verdiğimiz ve sonra geri çağıracağımız fonksiyonlara denir. İstenilen değere ulaştığında veya işlem sonlandığında görevini yerine getirir.
Yalnızca bir eşzamansız eylemimiz varsa, bu mutlaka bir sorun değildir. Ancak, birden çok eşzamansız adımı sırayla tamamlamamız gerekirse, geri aramalar yönetilemez hale gelir ve callback hell (geri arama cehennemiyle sonuçlanır).
Buradaki sıkıntılı nokta callback
yapısıyla ilgili bir güven sorunu olduğu aşikar. Güvenemememizin başlıca sebepleri şunlar:
Callback
’in beklenenden erken çağırılmasıCallback
’in hiç çağırılmamasıCallback
’in beklenilenden az veya çok çağırılması- Gerekli parametreleri doğru bir şekilde alamaması
- Hataların yutulması
Promise
, callback’lerin sıkıntılı yönlerini düzeltmek amacıyla önerilmiş bir yapıdır. Söz diziminden bahsettiğimde daha net akıllarda oturacaktır ancak şimdiden avantajlarından bahsetmekte fayda var.
- Promise istenilen görevi yerine getirdiğinde değeri değişmez (immutable)
- Sadece bir kere başarıya (resolved) ulaşır, veya başarısız (rejected) olur.
- Öngörülemeyen hatalar otomatik olarak
Promise
’i başarısız (rejected) sonuca götürür. Bu da hataları kontrol etme noktasında faydalıdır. - Yapısı gereği, gelecekteki bir değerin göstergesi olduğundan daha güvenilirdir.
Bir dizi işlevi yerine getirmek istediğimizde bir söz zinciri kullanırız.
Chaining(Zincirleme) Nedir?
Callback
Fonksiyonlar, uzun yıllardır JavaScript'te eşzamansız işlemler için tek başına kullanılmıştır. Ancak bazı durumlarda Promise
kullanmak daha iyi bir seçenek olabilir.
Yapılması gereken birden fazla async(Eşzamansız) işlemi varsa ve onlar için iyi eski Callbacks
fonksiyonlar kullanmaya çalışırsak, kendimizi callback
cehennemi denilen bir durumun içinde çabucak buluruz:
firstRequest(function(response) {
secondRequest(response, function(nextResponse) {
thirdRequest(nextResponse, function(finalResponse) {
console.log('Final response: ' + finalResponse);
}, failureCallback);
}, failureCallback);
}, failureCallback);
Promises
ile aynı işlemi gerçekleştirirsek, Callback
'leri iletmek yerine ekleyebileceğimiz için, bu sefer yukarıdaki aynı kod çok daha temiz ve okunması daha kolay görünür:
firstRequest()
.then(function(response) {
return secondRequest(response);
}).then(function(nextResponse) {
return thirdRequest(nextResponse);
}).then(function(finalResponse) {
console.log('Final response: ' + finalResponse);
}).catch(failureCallback);
Yukarıdaki kodlar, birden fazla calback
fonksiyonu birbiri ardına nasıl zincirlenebileceğini gösterir. Zincirleme, Promise
Nesnesinin en iyi özelliklerinden biridir.
Adım Adım Promise Oluşturma ve Kullanma
İlk olarak, bir Promise
nesnesi oluşturmak için bir yapıcı kullanıyoruz:
const myPromise = new Promise();
Biri başarı (resolve) ve diğeri başarısızlık (reject) olmak üzere iki parametre alır:
const myPromise = new Promise((resolve, reject) => {
// kodlar
});
Promise()
Yapıcı bir argüman olarak bir fonksiyon alır. Fonksiyon ayrıca iki işlevi kabul eder resolve()
ve reject()
.
Promise
başarıyla geri dönerse, resolve()
işlev çağrılır. Ve bir hata oluşursa reject()
işlev çağrılır.
Aşağıdaki programın asenkron bir program olduğunu varsayalım. Daha sonra program bir promise
kullanılarak ele alınabilir.
let count = true;
let countValue = new Promise(function (resolve, reject) {
if (count) {
resolve("Bir sayı değeri var.");
} else {
reject("Sayı değeri yok");
}
});
console.log(countValue);
ÇIKTI:
Yukarıdaki programda, Promise iki işlevi alan bir nesne oluşturulur; resolve()
ve reject()
. resolve() Süreç başarılı olursa kullanılır ve reject() bir hata vaadi oluştuğunda kullanılır.
Promise
, Nesnesi değer olarak count= true başarılı.
Böylece ilk Promise
oluşturduk. Şimdi onu kullanalım.
.then() resolved(Başarılı) Promises:
Bu yazının başındaki yazıyı tekrar okursanız, 2 durum olduğunu göreceksiniz: Biri resolve
(Başarı) promise
ve diğeri rejected
(reddedildi). .then()
Method iki isteğe bağlı parametreleri kabul eder. İlk olarak, sözün yerine getirilmesi durumunda bir işlev çağrılır. İkincisi, söz reddedilirse çağrılan bir işlev.
myPromise.then();
.Then()
methodu Promise
çözüldükten sonra çağrılır. Sonra çözülmüş Promise
ne yapacağımıza karar verebiliriz.
Örneğin, Promise
'den aldığımız mesajı konsola yazdıralım:
myPromise.then((message) => {
console.log(message);
});
Rejected(reddedilen) Promise için catch() Methodu
Ancak .then()
Methodu yalnızca Başarılı Promise(Sözler) içindir. Ya Promise
Nesnesi başarısız olursa? Ardından .catch()
Methodu kullanmamız gerekir.
Aynı şekilde .then()
methodu ekliyoruz. Ayrıca doğrudan sonrasına da .catch()
methodu ekleyebiliriz:
myPromise.then((message) => {
console.log(message);
}).catch((message) => {
console.log(message);
});
İç içe Geçmiş Promise ve .then()
JavaScript'te, bir dizide birden çok eşzamansız işlem gerçekleştirirken promise
birden çok .then()
Methodu zincirleyerek oluşturulmalıdır. Bu yuvalama yapmaktan daha iyi bir uygulamadır.
Zincirleme, geliştirme sürecini kolaylaştırmaya yardımcı olur çünkü kodları daha okunaklı hale getirir ve hata ayıklamayı kolaylaştırır.
const promise = new Promise((resolve, reject) => {
setTimeout(() => {
resolve('*');
}, 1000);
});
const twoStars = (star) => {
return (star + star);
};
const oneDot = (star) => {
return (star + '.');
};
const print = (val) => {
console.log(val);
};
// Hepsini birbirine zincirleyelim
promise.then(twoStars).then(oneDot).then(print);
Javascript dilinde çoğunlukla senkron fonksiyonları kullanıyoruz. Senkron(Synchronous) fonksiyonlar sırasıyla çalışan fonksiyonlardır. javascript'de komutlar yukarıdan aşağıya doğru çalışırlar. Bu çalışma sistemine Senkron proğramlama yada Eş zamanlı çalışma denir. Temel bir örneğe bakalım.
function selamla(){
console.log("Hey, Merhaba Nasılsın.");
}
function selamla1(){
console.log("Teşekkür Ederim İyiyim Ya Sen!");
}
selamla();
selamla1();
ÇIKTI:
Hey, Merhaba Nasılsın. Teşekkür Ederim İyiyim Ya Sen!
Beklediğiniz gibi, önce selamla
fonksiyon yürütülür ve sonra selamla1
fonksiyon yürütülür.
Fonksiyonumuzu zaman uyumsuz hala getirelim, selamla
fonksiyonu ajax vasıtayla veritabanından bilgimizi 3 saniye geçikmeli olarak veriyi alıyor kabul edin; çıktı nasıl olacak.
setTimeout():
milisaniye cinsinden bir gecikme ayarlandıktan sonra bir kod bloğu yürüten veya bir geri arama işlevi aracılığıyla bir ifadeyi değerlendiren eşzamansız bir JavaScript fonksiyonudur.
function selamla(){
setTimeout(function(){
console.log("Hey, Merhaba Nasılsın.");
}, 3000);
}
function selamla1(){
console.log("Teşekkür Ederim İyiyim Ya Sen!");
}
selamla();
selamla1();
ÇIKTI:
Teşekkür Ederim İyiyim Ya Sen! Hey, Merhaba Nasılsın. //3 saniye sonra yazar
Yukarıdaki örnekte görüldüğü üzere cümle sırası değişti mantıksız selamla
oldu. JavaScrip'te fonksiyonlarımızı bir sırayla çalıştırmak istediğimizde callback
fonksiyonlardan yararlanıyorduk. Basitçe bir parametre olarak gönderdiğimiz fonksiyonu çalışmasını istediğimiz zaman çağırıyorduk.
Bu zaman uyumsuz fonksiyonların çalıştırılması için calback
fonksiyonların hatasını gideren gelişmiş Promise yapılarını kullanacağız.
const promise = new Promise((resolve, reject) => {
const test =true;
setTimeout(() => {
if(test) {
console.log("Hey, Merhaba Nasılsın.");
resolve();
} else {
reject("hata!");
}
}, 2000);
});
function selamla1(){
console.log("Teşekkür Ederim İyiyim Ya Sen!");
}
promise.then((data) => {
selamla1();
})
.catch((error) => {
console.log(error);
});
ÇIKTI:
Hey, Merhaba Nasılsın. Teşekkür Ederim İyiyim Ya Sen!
Yukarıda görüldüğü üzere zaman uyumsuz olarak veritabanından bilgi gelince sıralı çalışacak.
Ayrıca Promise
yapısını doğrudan return
değeri olarakta tanımlayabiliriz. Hatta bir fonksiyon içersinde tanımlayıp değerde gönderebiliriz.
function selamla()
{
return new Promise((resolve, reject) => {
const test =true;
setTimeout(() => {
if(test) {
console.log("Hey, Merhaba Nasılsın.");
resolve();
} else {
reject("hata!");
}
}, 2000);
});
}
function selamla1(){
console.log("Teşekkür Ederim İyiyim Ya Sen!");
}
selamla()
.then((data) => {
selamla1();
})
.catch((error) => {
console.log(error);
});
ÇIKTI:
Hey, Merhaba Nasılsın. Teşekkür Ederim İyiyim Ya Sen!
Promise
yapısının en güzel yanı Promise Chain
. Promise zinciri olarak çevirebileceğimiz bu yapı bize sıralı fonksiyonlarımızı bir düzen içersinde yazmamızı sağlıyor. Şöyle ki bir .then
Methodu içerisinde return
değeri oluşturulursa peşi sıra gelen .then
Methodu ile yakalanabilmekte.
function sayi(data) {
return new Promise((resolve, reject) => {
if (data < 800)
resolve(data * 5);
else
reject('sonuç 800 den küçük sayıları çarp');
});
}
sayi(2).then((data)=>{
console.log(data);
return sayi(data);
}).then((data)=>{
console.log(data);
return sayi(data);
}).then((data)=>{
console.log(data);
return sayi(data);
}).then((data)=>{
console.log(data);
return sayi(data);
}).catch((err)=>{
console.log(err);
});
ÇIKTI:
10 50 250 1250 sonuç 800 den küçük sayıları çarp
- HTML
- CSS
- PHP
- JQUERY
- PHOTOSHOP
- JavaScript
- Web Dünyası
- Linux
- MİTHRİL FRAMEWORK
- Laravel
- Git
- React
- HTML LİNK(Bağlantı)EKLEME - LİNK VERME
- HTML YAZI VE RESİM ORTALAMA
- HTML RESME LİNK VERME
- HTML FORM OLUŞTURMA
- CSS YATAY MENÜ YAPIMI
- HTML RESİM EKLEME
- CSS (BOYUT) GENİŞLİK VE YÜKSEKLİK (Width-Height)
- HTML DİV ve SPAN NEDİR?
- HTML ARKAPLANA MÜZİK EKLEME
- KALİTE KAYBETMEDEN RESİMLERİ BÜYÜTME