async와 await는 자바스크립트의 비동기 처리 패턴 중 가장 최근에 나온 문법이다.
기존의 비동기 처리 방식인 콜백 함수와 프로미스의 단점을 보완하고, 가독성 좋은 코드를 작성할 수 있도록 도와준다.
비동기 실행 : 서버 컴퓨터의 작업이 끝날 때까지 기다리지 않는 통신으로 서버에 요청(등록, 수정, 삭제 등)이 저장될 때까지 기다리지 않고 다른 작업을 진행한다.
이러한 특징 때문에 여러 가지 요청을 동시에 처리해 줄때에 사용된다.
동기 실행 : 서버 컴퓨터의 작업이 끝날 때까지 기다린 후 다음 작업을 실행하는 통신이다.
비동기 실행 / 동기 실행 상황에 맞게 잘 사용해야 한다!
데이터를 주고 받기 위해 브라우저에서 데이터를 요청하면 요청받은 백엔드 컴퓨터는 데이터베이스에서 데이터를 처리하여 브라우저에 응답을 돌려준다.
하지만 이 때, 게시글을 등록 후 게시글을 불러왔을 때 게시글이 불러와지지 않는 경우가 있다.
이러한 문제는 비동기 실행에 의해 나타나는데 게시글 등록 요청을 전송하고 데이터가 처리된 후 게시글 불러오기 과정이 실행되어야 하는데 데이터 처리 이전에 게시글 불러오기 과정이 실행되어져 발생하는 문제이다.
아래는 async & await를 사용하지 않은 코드이다.
const callRestApi = () => {
const result = axios.get("https://koreanjson.com/posts/1");
setData(result.data.title);
};
여기서 아래와 같이 async와 await를 추가하면
const callRestApi = async () => {
const result = await axios.get("https://koreanjson.com/posts/1");
setData(result.data.title);
};
async & await를 사용할 수 있다.
async function 함수명() {
await 비동기_처리_메서드_명();
}
먼저 함수의 앞에 async 라는 예약어를 붙인다.
그 후 함수의 내부 로직 중 HTTP 통신을 하는 비동기 처리 코드 앞에 await를 붙인다.
여기서 주의할 점은 비동기 처리 메서드가 꼭 프로미스 객체를 반환해야 await가 의도한 대로 동작한다.
일반적으로 await의 대상이 되는 비동기 처리 코드는 Axios 등 Promise를 반환하는 API 호출 함수이다.
async & await 문법이 가장 빛을 발하는 순간은 여러 개의 비동기 처리 코드를 다룰 때이다.
아래와 같이 각각 사용자와 할 일 목록을 받아오는 HTTP 통신 코드가 있다고 하자.
function fetchUser() {
const url = 'https://jsonplaceholder.typicode.com/users/1'
return fetch(url).then(function(response) {
return response.json();
});
}
function fetchTodo() {
const url = 'https://jsonplaceholder.typicode.com/todos/1';
return fetch(url).then(function(response) {
return response.json();
});
}
위 함수들을 실행하면 각각 사용자 정보와 할 일 정보가 담긴 프로미스 객체가 반환된다.
이제 이 두 함수를 이용해 할 일 제목을 출력해보겠다.
async function logTodoTitle() {
const user = await fetchUser();
if (user.id === 1) {
const todo = await fetchTodo();
console.log(todo.title); // delectus aut autem
}
}
logTodoTitle() 를 실행하면 콘솔에 delectus aut autem이 출력된다.
위 비동기 처리 코드를 만약에 콜백이나 프로미스로 처리했다면 훨씬 복잡한 코드가 된다.
비동기 처리를 위해 async를 사용하는 것은 알겠다.
그런데 async를 사용할 때 await는 왜 사용할까?
이는 동기 통신을 위해 사용한다.
await라는 단어를 직역하면 기다리다 라는 뜻인데
이는 비동기통신에서도 그대로 await의 역할을 의미한다.
아래 코드에서 await가 없다면 어떻게 될까?
updateBoard가 비동기 처리하는 동안 기다려주지 않고
바로 다음 줄 alert("수정이 완료되었습니다.")
로 넘어가
의도와는 다르게 진행 될 것이다.
따라서 updateBoard를 동기처리 해서 등록될 때까지 기다리기위해 await를 사용한다.