Estoy intentando ejecutar un bot que rastrea Amazon (usando amazon-buddy) para ciertos productos (usando una variedad de ASIN) y verifica el precio. Si el precio no es 0, debería estar enviando un mensaje de discordia. Actualmente tengo este conjunto para ejecutarse cada 30 segundos y está funcionando, pero hay momentos en los que parece que cada elemento no está esperando que el anterior obtenga una respuesta en el bucle forEach y mi función no parece ser correcta ( Todavía estoy tratando de entender correctamente las funciones async / await).

¿Hay una mejor manera de ejecutar esto para que cada elemento espere a que el elemento anterior se raspe antes de pasar al siguiente y ENTONCES vuelva a ejecutar el ciclo después de 30 segundos?

(function() {
  var c = 0;
  var timeout = setInterval(function() {
      const checkStock = (async () => {
        config.items.itemGroup.forEach(element => {
          console.log('Checking stock on ' + element)
        try {
          const product_by_asin = await amazonScraper.asin({ asin: element });
          console.log(product_by_asin)
          const price = product_by_asin.result[0].price.current_price
          const symbol = product_by_asin.result[0].price.symbol
          const asin = product_by_asin.result[0].asin
          const title = product_by_asin.result[0].title
          const url = product_by_asin.result[0].url
          const image = product_by_asin.result[0].main_image

          if (price != 0) {
            const inStockResponse = {
              color: 0x008000,
              title: title + ' is in stock!',
              url: url,
              author: {
                name: config.botName,
                icon_url: config.botImg,
                url: config.botUrl
              },
              description: '<@767456705306165298>, click the tite to go purchase!\n\n' +
              'Price: ' + symbol + price,
              thumbnail: {
                url: image
              },
              timestamp: new Date()
              }
        
            message.channel.send({embed: inStockResponse });
            console.log(title + ' (' + asin + ') IS available!')
          } else {
            console.log(title + ' (' + asin + ') IS NOT available!')
          }
        } catch (error) {
          console.log(error);
        }
      });
      checkStock()
    });
    console.log('Counter: ' + c)
    c++;
  }, 30000);
})();
0
David Gonzalez 20 oct. 2020 a las 07:21

1 respuesta

La mejor respuesta

Puede usar un bucle for...of que puede esperar a que finalice cada iteración:

async function checkItems(items) {
  // Check all items, wait for each to complete.
  for (const item of items) {
    try {
      const product_by_asin = await amazonScraper.asin({ asin: item });
      console.log(product_by_asin);
      const price = product_by_asin.result[0].price.current_price;
      const symbol = product_by_asin.result[0].price.symbol;
      const asin = product_by_asin.result[0].asin;
      const title = product_by_asin.result[0].title;
      const url = product_by_asin.result[0].url;
      const image = product_by_asin.result[0].main_image;

      if (price != 0) {
        const inStockResponse = {
          color: 0x008000,
          title: title + " is in stock!",
          url: url,
          author: {
            name: config.botName,
            icon_url: config.botImg,
            url: config.botUrl,
          },
          description:
            "<@767456705306165298>, click the tite to go purchase!\n\n" +
            "Price: " +
            symbol +
            price,
          thumbnail: {
            url: image,
          },
          timestamp: new Date(),
        };

        // NOTE: you might want to wait for this too, the error
        // currently isn't being handled like this either.
        message.channel.send({ embed: inStockResponse });
        console.log(title + " (" + asin + ") IS available!");
      } else {
        console.log(title + " (" + asin + ") IS NOT available!");
      }
    } catch (err) {
      console.log(err);
    }
  }

  // Wait 30s and check again.
  setTimeout(() => checkItems(items), 30000);
}

checkItems(config.items.itemGroup);
1
Dominic 20 oct. 2020 a las 04:33