Async Await 사용 및 Array.prototype.map() 및 연결의 함정

Originally published @ puruvj.dev



아래 코드를 고려해보자

const IDs = [1, 2, 3];

const usersData = IDs.map(async (id) => await getUserData(id));

console.log(usersData);


이 출력은 무엇입니까?

[Promise, Promise, Promise];


이 모든 것이 약속입니다. 그러나 여기서는 데이터를 개체(또는 생각할 수 있는 다른 형식)로 예상합니다. 모든 단일 배열 항목을 어떻게await 수행합니까?

여기서 해결책은 Promise.all 입니다. 요약:
Promise.all 프라미스 배열을 가져와서 all 해결될 때까지 동시에 실행하고 해당 프라미스의 결과를 Array로 해결된 값으로 더 큰 값promise을 반환합니다.

예를 들어

await Promise.all([getUserData(1), getUserData(2), getUserData(3)]);


돌아올 것이다

[
  { id: 1, ...otherData },
  { id: 2, ...otherData },
  { id: 3, ...otherData },
];


생각해보면, 우리가 ID를 매핑하는 코드 조각은 단지 약속의 배열일 뿐입니다. 우리는 그 배열을 직접Promise.all 할 수 있습니다.

const IDs = [1, 2, 3];

const usersDataPromises = IDs.map(async (id) => await getUserData(id));

const usersData = await Promise.all(usersDataPromises);

console.log(usersData);


그러면 위와 같은 객체가 출력됩니다.

[
  { id: 1, ...otherData },
  { id: 2, ...otherData },
  { id: 3, ...otherData },
];


까다로운 부분



위의 트릭은 매력처럼 작동합니다. 그러나 다음과 같이 다른 배열 메서드를 기존 배열에 연결할 때 어려움이 발생합니다.

const IDs = [1, 2, 3];

const usersDataPromise = IDs.map(async (id) => await getUserData(id)).map(
  async (data) => await getPosts(data)
);

const usersData = Promise.all(usersDataPromise);

console.log(usersData);


오류가 반환됩니다. 왜요?
Promise.all 모든 약속을 한 번에 실행하려고 합니다. 그리고 내 말은, 그들 모두입니다. 첫 번째 지도와 함께 두 번째map를 실행하려고 합니다. 두 번째map가 첫 번째 값에 의존하기 때문에 이것이 문제임을 스스로 알 수 있습니다.

이 문제를 어떻게 해결합니까(말장난 😎)?

솔루션



이 문제를 해결하는 방법에는 여러 가지가 있을 수 있습니다. 여기에 2를 공유합니다

1위


Promise.all 모든 단계에서

const IDs = [1, 2, 3];

const usersData = await Promise.all(
  IDs.map(async (id) => await getUserData(id))
);

const usersPosts = await Promise.all(
  usersData.map(async (userData) => await getPosts(userData))
);


2위



평범한 오래된 for of 루프:

const IDs = [1, 2, 3];

const usersPosts = [];

for (let id of IDs) {
  const userData = await getUsersData(id);

  const userPosts = await getPosts(userData);

  usersPosts.push(userPosts);
}


나는 두 번째 접근 방식을 선호합니다. 추가 단계를 추가하려면 추가 행을 추가하기만 하면 되는 반면, 2단계에는 전체 추가Promise.all(array map)가 필요하며 이는 궁극적으로 코드 중복성입니다.

좋은 웹페이지 즐겨찾기