Async/Await in TypeScript (Live Playground)
In this tutorial, we will explore async/await in TypeScript, which is a syntactic sugar built on top of Promises that allows you to write asynchronous code that looks like synchronous code, making it more readable and easier to maintain.
What are Async/Await?
Async/await is a feature that enables you to write asynchronous code using a syntax that resembles synchronous code. It makes your code more readable and easier to understand, especially when dealing with multiple asynchronous tasks.
Async/await is built on top of Promises and requires the following two keywords:
- async: A keyword used to declare an asynchronous function. It indicates that the function contains asynchronous code and returns a Promise.
- await: A keyword used to pause the execution of an async function until a Promise is resolved or rejected. It can only be used inside an async function.
Async Functions
An async function is a function declared with the async
keyword. It automatically returns a Promise that resolves to the value returned by the function or rejects with an error if the function throws an error.
async function fetchData(): Promise<string> {
return 'Data fetched!';
}
Using Await
The await
keyword is used inside an async function to pause the execution until a Promise is settled (fulfilled or rejected). The value of the settled Promise is then returned by the await
expression.
async function fetchUser(id: number): Promise<string> {
return new Promise((resolve, reject) => {
setTimeout(() => {
if (id === 1) {
resolve('John Doe');
} else {
reject('User not found');
}
}, 1000);
});
}
async function getUserData(id: number): Promise<void> {
try {
const user = await fetchUser(id);
console.log(`User's name is ${user}`);
} catch (error) {
console.error(error);
}
}
getUserData(1);
Combining Async/Await with Promises
Async/await and Promises can be combined to create more readable and maintainable asynchronous code. For example, you can use Promise.all
with async/await to wait for multiple Promises to settle.
async function fetchUserData(): Promise<string[]> {
// ... Fetch user data ...
}
async function fetchPostsData(): Promise<string[]> {
// ... Fetch posts data ...
}
async function fetchData(): Promise<void> {
try {
const [users, posts] = await Promise.all([fetchUserData(), fetchPostsData()]);
console.log(users);
console.log(posts);
} catch (error) {
console.error(error);
}
}
fetchData();
Async Function Types
Async function types are a way to define the types of asynchronous functions that return Promises. They are used to ensure type safety when working with asynchronous code in TypeScript.
type FetchData = (url: string) => Promise<string>;
Using Async Function Types
Async function types can be used to define the types of async functions, arrow functions, or functions that return Promises.
type FetchData = (url: string) => Promise<string>;
const fetchData: FetchData = async (url: string) => {
const response = await fetch(url);
const data = await response.text();
return data;
};
Type Aliases vs Interface for Async Function Types
You can use type aliases or interfaces to define async function types, depending on your preference and use case.
- Type Aliases
type FetchData = (url: string) => Promise<string>;
- Interface
interface FetchData {
(url: string): Promise<string>;
}
Async Function Types with Generics
Async function types can also be used with generics, allowing you to define more flexible and reusable async function types.
type FetchData<T> = (url: string) => Promise<T>;
const fetchJsonData: FetchData<object> = async (url: string) => {
const response = await fetch(url);
const data = await response.json();
return data;
};
Conclusion
In this tutorial, we have explored async/await in TypeScript, which allows you to write asynchronous code that looks like synchronous code, making it more readable and easier to maintain.