Fetch Promise
fetch 和 Promise 是 JavaScript 中處理異步操作的重要工具,特別是在進行網路請求時。fetch 提供了一個基於 Promise 的 API,用於進行 HTTP 請求,而 Promise 是一種更強大且靈活的異步編程方式。下面將詳細說明這兩者的使用方法及其在實際應用中的結合。
1. Promise 的基本概念
Promise 是 JavaScript 中用來表示一個可能在未來完成(或失敗)的異步操作及其結果的物件。Promise 有三種狀態:
- Pending(進行中): 初始狀態,操作尚未完成或失敗。
- Fulfilled(已完成): 操作成功完成,並有一個結果值。
- Rejected(已拒絕): 操作失敗,並有一個錯誤原因。
1.1 創建 Promise
你可以使用 new Promise() 來創建一個 Promise,並傳入一個包含 resolve 和 reject 參數的回呼函式,用來處理成功和失敗的情況。
let promise = new Promise((resolve, reject) => {
// 模擬一個異步操作
setTimeout(() => {
let success = true; // 模擬成功或失敗
if (success) {
resolve("Operation was successful!");
} else {
reject("Operation failed.");
}
}, 1000);
});
1.2 使用 Promise
Promise 通過 then 和 catch 方法來處理成功和失敗的結果。
promise
.then(result => {
console.log(result); // 如果成功,輸出 "Operation was successful!"
})
.catch(error => {
console.error(error); // 如果失敗,輸出 "Operation failed."
});
1.3 鏈式 Promise
then 方法返回一個新的 Promise,這允許你串聯多個異步操作。
promise
.then(result => {
console.log(result);
return new Promise((resolve) => setTimeout(() => resolve("Another operation"), 1000));
})
.then(result => {
console.log(result); // 輸出 "Another operation"
})
.catch(error => {
console.error(error);
});
2. fetch 的基本用法
fetch 是一個用於發送網路請求並處理回應的現代方法。它返回一個 Promise,該 Promise 會在請求完成後被解析。
fetch('https://api.example.com/data')
.then(response => {
if (!response.ok) {
throw new Error('Network response was not ok');
}
return response.json(); // 將回應解析為 JSON
})
.then(data => {
console.log(data); // 處理解析後的 JSON 資料
})
.catch(error => {
console.error('There was a problem with the fetch operation:', error);
});
3. fetch 的進階使用
3.1 發送 POST 請求
除了 GET 請求,fetch 也可以用來發送 POST 請求,並傳送資料。
fetch('https://api.example.com/data', {
method: 'POST',
headers: {
'Content-Type': 'application/json'
},
body: JSON.stringify({
name: 'John',
age: 30
})
})
.then(response => response.json())
.then(data => console.log(data))
.catch(error => console.error('Error:', error));
3.2 處理不同類型的回應
fetch API 可以處理多種不同格式的回應,比如 JSON、文字、二進制等。
fetch('https://api.example.com/data')
.then(response => response.text()) // 解析為文字
.then(data => console.log(data))
.catch(error => console.error('Error:', error));
3.3 處理 HTTP 錯誤
fetch 只會拒絕 Promise 當遇到網路錯誤時(例如網絡中斷),如果 HTTP 回應碼為 404 或 500,仍會被視為成功的請求,因此需要手動檢查 response.ok 狀態。
fetch('https://api.example.com/data')
.then(response => {
if (!response.ok) {
throw new Error('HTTP error! status: ' + response.status);
}
return response.json();
})
.then(data => console.log(data))
.catch(error => console.error('Fetch error:', error));
4. Promise 與 async/await
雖然 then 和 catch 是處理 Promise 的常用方式,但在現代 JavaScript 中,async/await 提供了更簡潔的語法來寫異步代碼。
4.1 使用 async/await 進行 fetch 請求
async function fetchData() {
try {
let response = await fetch('https://api.example.com/data');
if (!response.ok) {
throw new Error('HTTP error! status: ' + response.status);
}
let data = await response.json();
console.log(data);
} catch (error) {
console.error('Fetch error:', error);
}
}
fetchData();
5. Promise 的進階操作
5.1 Promise.all
Promise.all 方法用於並行執行多個 Promise,並在所有 Promise` 都完成後返回一個新的 Promise。這個新的 Promise 會 resolve 成一個包含每個 Promise 結果的陣列。
let promise1 = fetch('https://api.example.com/data1').then(res => res.json());
let promise2 = fetch('https://api.example.com/data2').then(res => res.json());
Promise.all([promise1, promise2])
.then(results => {
console.log(results[0]); // 第一個請求的結果
console.log(results[1]); // 第二個請求的結果
})
.catch(error => console.error('Error:', error));
5.2 Promise.race
Promise.race 方法會返回第一個完成的 Promise 的結果(無論成功或失敗)。
let slowPromise = new Promise((resolve) => setTimeout(resolve, 2000, 'slow'));
let fastPromise = new Promise((resolve) => setTimeout(resolve, 1000, 'fast'));
Promise.race([slowPromise, fastPromise])
.then(result => console.log(result)); // 輸出 "fast"
總結
fetch 和 Promise 是現代 JavaScript 中處理異步操作的核心工具。fetch 為網路請求提供了一個簡單且靈活的接口,而 Promise 則是處理異步操作結果的基礎。通過結合這兩者,尤其是在使用 async/await 語法的情況下,可以使得異步程式碼更加簡潔和易於理解。這對於構建現代的 Web 應用程式尤為重要。