¿Cómo usar async/await con un map en javascript? | CourseIt Blog
logo courseit

¿Cómo usar async/await con un map en javascript?

66

Bienvenides a otro hermoso blog.

Muchas veces cuando estamos trabajando con javascript nos encontramos con la extraña situación en la que tenemos que hacer un fetch por cada elemento de un array. En este artículo voy a explicar la manera que suelo utilizar para salir de ese momento incómodo.

Empecemos.

Supongamos que estamos trabajando con la poke api, y tenemos un array que contiene los ids de varios pokemones, por ejemplo: [6, 35, 133]

Lo que queremos hacer es generar un nuevo array, pero que en vez de solamente tener números, contenga un objeto con la información de cada pokemon correspondiente.

El método para generar un nuevo array según un array ya existente en javascript, es map().

Muy bien, entonces, la lógica me dice que primero tenemos que escribir dicho map.

const pokemonsIds = [6, 35, 133]

const newArray = pokemonsIds.map(id =>{
 //ir a buscar la información
})

Ahora bien, el problema se encuentra en lo que hacemos dentro del map, ya que necesitamos hacer un fetch. Y para poder recibir la información en tiempo y forma tenemos que usar async y await. Pero, dónde escribo este async / await?

Hagámoslo por partes. Lo primero que vamos a querer es hacer el fetch, y sabemos que va a necesitar un await.

const pokemonsIds = [6, 35, 133]

const newArray = pokemonsIds.map(id =>{
   const pokemon = await fetch(
          `https://pokeapi.co/api/v2/pokemon/${id}`
        );
  const parsedPokemon = await pokemon.json();

  return parsedPokemon;
})

Ya tenemos nuestro fetch, pero si queremos ejecutar esto, va a explotar todo por los aires, ya que NO estamos ejecutando await dentro de una función async. Agreguemos el async entonces:

const pokemonsIds = [6, 35, 133]

const newArray = pokemonsIds.map(async id =>{
   const pokemon = await fetch(
          `https://pokeapi.co/api/v2/pokemon/${id}`
        );
  const parsedPokemon = await pokemon.json();

  return parsedPokemon;
})

Presten atención que el async se encuentra previo a los parámetros del map. Con esto, el error de que estamos usando await sin async desaparece. Pero ahora tenemos otro problema. Si nosotros hacemos un console.log() de newArray (que es nuestro map), nos va a devolver un array de promesas. Esto es porque todavía no sabemos si se resolvieron los fetch dentro de cada iteración del array (ni tampoco cuando).

promise

Y si expandimos más el array podemos ver que cada elemento es una promesa.

promises

Genial, ya casi estamos. Lo que tenemos que hacer ahora es resolver la promesa. ¿Cómo hacemos eso? con nuestro viejo amigo Promise.all()

const pokemonsIds = [6, 35, 133]

const newArray = pokemonsIds.map(async id =>{
   const pokemon = await fetch(
          `https://pokeapi.co/api/v2/pokemon/${id}`
        );
  const parsedPokemon = await pokemon.json();

  return parsedPokemon;
})

Promise.all(newArray).then(data => {
  console.log(data);
});

Promise.all() es un método que nos permite transformar un array de promesas en un array de promesas resueltas. El .then recibe como callback una función que se va a ejecutar cuando la promesa (o array de promesas en realidad), se resuelvan. El parámetro de dicha función callback va a ser la data, o información legible, y resuelta. Entonces, todo lo que queda hacer es un console.log() de data, y ya vamos a poder ver en consola la información de nuestros tres pokemones.

solved

Si tienen dudas me las pueden mandar por twitter o siempre estoy conectado en discord para ayudarlos con lo que necesiten.

Agradecimiento especial a javascript por hacer tan divertido todo.

Y eso es todo folks.