[JS] async와 await

cabbage·2023년 1월 17일

JS

목록 보기
29/43
post-thumbnail

동기와 비동기

동기는 현재 실행 중인 코드의 실행이 완료된 후 다음 코드를 실행하는 방식이다.
비동기는 현재 실행 중인 코드의 실행 완료 여부에 상관하지 않고 바로 다음 코드를 실행하는 방식이다.

클라이언트가 서버에 어떤 API를 요청하는 경우, 동기와 비동기를 모두 사용할 수 있다.

  • 동기적 방식: 서버의 API 응답을 기다림
  • 비동기적 방식: 서버의 API 응답을 기다리지 않고 다음 코드 실행

클라이언트가 서버의 API 응답을 기다리기 위해 동기적 방식을 사용하는 경우는 다음과 같은 경우가 있을 수 있다.

  • 게시글 등록 API 호출
  • 게시글 조회 API 호출

게시글 등록 API를 호출하고, 게시글 조회 API를 비동기적으로 호출했을 때 게시글이 아직 데이터베이스에 저장되지 않았다면 게시글 조회 API의 응답 결과로 아무 데이터도 확인할 수 없다.

이런 경우 게시글 등록 API 호출과 게시글 조회 API 호출은 동기적 방식으로 진행되어야 한다. 서버와 통신하는 라이브러리 등은 비동기적으로 동작하지만, 동기적으로 동작하도록 응답 결과를 기다릴 수도 있다.

클라이언트가 서버의 API 응답을 기다리지 않는 비동기적 방식을 사용하는 경우는 다음과 같은 경우가 있을 수 있다.

  • 게시글 조회 API 호출
  • 상품 정보 조회 API 호출

하나의 웹페이지에서 게시글과 상품 정보를 모두 보여주는 경우, 두 API는 비동기적으로 동작해서 응답 결과를 받아오는 것이 효율적이다. 왜냐하면 두 API는 서로 의존하는 관계가 아니기 때문이다.

결국 동기와 비동기는 상황에 따라 적절하게 사용해야 한다.

Axios 그리고 async와 await

Axios는 브라우저와 Node.js를 위한 HTTP 비동기 통신 라이브러리이다. Axios의 특징은 다음과 같다.

  • 사용 환경에 따라 브라우저의 XMLHttpRequest 객체 또는 Node.js의 HTTP API를 사용한다.
  • Promise API를 사용한다.
  • async/await API를 사용한다.

자바스크립트는 싱글 스레드를 기반으로 동기적으로 동작한다. 따라서 현재 코드의 실행 결과를 기다린 후 다음 코드를 실행한다. 그러나 일반적인 API 통신 기능들은 실행 시간이 상대적으로 오래 걸리기 때문에 대부분 비동기적으로 동작하는 것이 기본이다.

Axios를 사용해 GET 메서드로 데이터를 가져오는 예시 코드이다.

function fetchAsync() {
  const asyncResult = axios.get("https://koreanjson.com/posts/1");
  console.log("비동기방식: ", asyncResult); // Promise {<pending>}
}

fetchAsync();
// 비동기방식: Promise { <pending> }
  • axios.get 메서드는 비동기 방식으로 API를 요청하고, 그 응답을 기다리지 않고 곧바로 pending 상태의 Promise를 할당한다.
  • 그리고 곧바로 아래 코드를 실행한다.
  • 따라서 asyncResult를 확인하면 pending 상태의 Promise가 할당된 것을 볼 수 있다.

비동기 방식의 API 요청에 대한 응답 결과를 기다리기 위해 await를 사용할 수 있다. await를 사용하려면 함수에 async를 붙여야 한다.

const fetchSync = async () => {
  const syncResult = await axios.get("https://koreanjson.com/posts/1"); // get API 요청 결과를 await로 기다림
  console.log("동기방식: ", syncResult.data.title);
  console.log("동기방식: ", syncResult.data.content);
};

fetchSync();
// 동기방식: 정당의 목적이나 활동이 ...
// 동기방식: 모든 국민은 인간으로서의 ...
  • await를 사용하기 위해 화살표 함수 앞에 async를 붙인다.
  • await를 사용하면 비동기 방식으로 동작하는 API 요청의 결과를 기다린다.
  • API 요청에 대한 응답이 도착하면 syncResult에 응답 결과를 할당한다.
  • API 요청에 대한 응답 결과를 확인할 수 있다.

await를 사용하면 비동기 요청 API에 대한 응답을 기다렸다가 아래 코드를 실행한다. API 요청은 비동기적으로 동작하지만 그 응답을 기다리기 때문에 동기적으로 실행된다.

만약 어떤 API 요청이 이전 API 요청의 응답 결과에 의존한다면 await를 사용해 이전 API 요청의 응답 결과를 기다리고, 이 응답 결과를 사용해 다음 API 요청을 호출할 수 있다.

then() 메서드

axios는 응답 결과로 Promise를 반환하기 때문에 비동기 요청에 대한 응답 결과를 then() 메서드에서 받을 수 있다.

axios.get("https://koreanjson.com/posts/1").then((res) => {
  console.log(`응답 결과: ${res.data.title}`);
});

axios.get("https://koreanjson.com/posts/2").then((res) => {
  console.log(`응답 결과2: ${res.data.title}`);
});

// 응답 결과2: 누구든지 법률에 의하지 아니하고는...
// 응답 결과1: 정당의 목적이나 활동이 민주적 ...
  • then() 메서드를 사용하면 비동기 요청 API에 대한 응답을 기다리지 않고 곧바로 아래 코드를 실행할 수 있다.
  • 비동기 요청 API에 대한 응답이 도착하면 then() 메서드에 전달한 콜백 함수가 응답 결과를 받아 출력한다.
  • 따라서 먼저 도착하는 응답 결과가 먼저 출력된다.

만약 어떤 API 요청이 이전 API 요청의 응답 결과에 의존하지 않는다면 비동기적으로 두 API를 요청할 수 있다.

정리

  • API 요청 결과를 기다려야 하는 경우에는 await를 사용해 응답 결과를 기다릴 수 있다.
  • API 요청 결과를 기다릴 필요가 없는 경우, 이전 API의 응답 결과를 기다리지 않고 비동기적으로 응답 결과를 가져오면 된다.
profile
캐비지 개발 블로그입니다. :)

0개의 댓글