Mazino
Mazino

Reputation: 356

Loop through parameter values - NodeJS (Puppeteer)

I am passing the values I get from MongoDb to my parameters in NodeJS Puppeteer with a for-Each loop.

This is the for-Each loop


dataGood = [{title: "username1", password: "password2"},{title: "username1", password: "password2"}]


 await dataGood.forEach(async element => {
        let title = element.title;
        let pass = element.password;
        let tags = element.tags;
        let actions = element.actions;
        
        await ig.initialize();

        await ig.login(title, pass);
  
        await ig.liketagsprocess(tags, actions);

This code works fine if there is a single data in the dataGood.

But if there are 2 or more values it does not work.

This is where the data is passed

initialize: async() => {
        instagram.browser = await puppeteer.launch({
            headless: false,
        });

        instagram.page = await instagram.browser.newPage();
    },

    login: async(username , password) => {

        console.log(username, password)


        await instagram.page.goto(BASE_URL, {waitUntil: 'load', timeout: 0});

        await instagram.page.waitForSelector('input[name="username"]');

        await instagram.page.type('input[name="username"]', username, {delay: 100});

        await instagram.page.type('input[name="password"]', password, {delay: 100});


Console Log : // Suppose usernames are username 1 and Username 2

username1 password1
username2 password2

How ever the main problem arises in the puppeteer.

The for-each loop of dataGood, opens up 2 puppeteer windows.

Two separate chromium windows open up. and this kind of error happens.

Please refer to these images.

This  is the first chromium window where nothing happens This is the second chromium window where both parameters gets mixed up

These are not the tabs of the same chromium window but entirely different windows

How can I loop through the parameters so that they work individually in the respective puppeteer windows.

Upvotes: 1

Views: 328

Answers (1)

theDavidBarton
theDavidBarton

Reputation: 8841

If you want to open all iteratees in the same chromium instance then you should call

await ig.initialize();

outside of the loop.

Other than that the Array.forEach may not executed the same way as you'd expect it, iterating async functions is tricky. See more on its background here.

With a regular for loop or with a for...of your iteratees will be executed in strict sequence without any side effects:

await ig.initialize();
for (const element of dataGood) {
  let title = element.title
  let pass = element.password
  await ig.login(title, pass)
}

If you'd still want to do it in a forEach I suggest to refactor your current code to deal with the asyncronous nature of the called functions.

Upvotes: 1

Related Questions