Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

WhatsApp Web.js - Messages Not Sending Properly #2554

Closed
1 task done
Pdk3Dragon opened this issue Oct 3, 2023 · 9 comments
Closed
1 task done

WhatsApp Web.js - Messages Not Sending Properly #2554

Pdk3Dragon opened this issue Oct 3, 2023 · 9 comments
Labels
bug Something isn't working

Comments

@Pdk3Dragon
Copy link

Pdk3Dragon commented Oct 3, 2023

Is there an existing issue for this?

  • I have searched the existing issues

Describe the bug

I am using the WhatsApp Web.js library to send scheduled messages via WhatsApp Web. The goal is to send messages at specified times, but I'm encountering an issue where the messages are not being sent as expected. Interestingly, when I restart the server, the messages are sent successfully.

Expected behavior

The issue at hand is that when the sendMessage function is called, the message is not sent as expected. However, upon restarting the server, the message is sent successfully. This suggests that there might be a session management or client initialization problem.

Steps to Reproduce the Bug or Issue

NA

Relevant Code

I'm using WhatsApp Web.js for sending scheduled messages, and I'm implementing LocalAuth for managing multiple sessions. In the provided API code, I'm saving scheduled messages to the database and managing client sessions on the server. However, when the sendMessages() function is called, the client isn't authenticated, doesn't listen for the 'ready' event, and fails to send messages. Interestingly, if I restart the server, the messages are sent successfully. I hope you can assist me in correctly sorting out this issue.

Browser Type

Google Chrome

WhatsApp Account Type

Standard

Does your WhatsApp account have multidevice enabled?

Yes, I am using Multi Device

Environment

  • Node.js version: [v18.17.0]
  • WhatsApp Web.js version: ["https://github.com/Julzk/whatsapp-web.js/tarball/jkr_hotfix_7"]
  • Operating System: [Windows]

Additional context

No response

@Pdk3Dragon Pdk3Dragon added the bug Something isn't working label Oct 3, 2023
@marcioscf
Copy link

Okay, so the problem is:
You're recreating the client object every time you enter the sendMessage function.
You should do this:

Your Client should be global, or you can pass it down as a variable to the sendMessage function. That way, you won't have to instantiate it every time you enter the sendMessage function.

Try to think it this way:
It is a async function, that will be called 10, 20 or 200 times at the same second.
At every time you call it, it will try to reopen the puppeteer that is inside the whatsapp-web.js lib, open the whatsapp web website, log in at whatsapp with your authstrategy and then try to send a message. It just won't work, since whatsapp web can only have one active session at a time.

So you need to pass the session down or make it global, and then you will be able to send messages properly.

As a rule of thumb, you can only have the client created ONE TIME at your project, except for very specific use cases.

@Pdk3Dragon
Copy link
Author

Okay, so the problem is: You're recreating the client object every time you enter the sendMessage function. You should do this:

Your Client should be global, or you can pass it down as a variable to the sendMessage function. That way, you won't have to instantiate it every time you enter the sendMessage function.

Try to think it this way: It is a async function, that will be called 10, 20 or 200 times at the same second. At every time you call it, it will try to reopen the puppeteer that is inside the whatsapp-web.js lib, open the whatsapp web website, log in at whatsapp with your authstrategy and then try to send a message. It just won't work, since whatsapp web can only have one active session at a time.

So you need to pass the session down or make it global, and then you will be able to send messages properly.

As a rule of thumb, you can only have the client created ONE TIME at your project, except for very specific use cases.

"Thanks for your reply sir. Here I have a list of scheduled messages, each with a different sessionID. For example, message[0].sessionID = "2001," and message[1].sessionID = "2002." Each sessionID corresponds to a different WhatsApp account. In this situation, I kindly request your guidance on how to effectively resolve this issue. Your assistance would be greatly appreciated."

@Pdk3Dragon
Copy link
Author

Pdk3Dragon commented Oct 4, 2023

I have made some changes to my code.

// Object to store client objects by session ID
const sessionClients = {};

// When a user creates a scheduled message and specifies a session ID, create a new client
function createClient(sessionID) {
    if (!sessionClients[sessionID]) {
        const client = new Client({
            qrMaxRetries: 2,
            puppeteer: {
                executablePath: CHROME_PATH,
            },
            authStrategy: new LocalAuth({
                clientId: sessionID,
            }),
            
        });

        // Initialize the client
        client.initialize();

        // Store the client in the data structure
        sessionClients[sessionID] = client;
    }
}

Api to create scheduled messages


After storing scheduled messages, the autoCheckScheduledMessages() function will retrieve and execute all messages for which the scheduled delivery times have already passed. autoCheckScheduledMessages() is called every minute.


This function invokes the sendMessage(message, client) function, which contains the following code:


In the sendMessage function, client.on("authenticated") and client.on("ready") events are not working. I got the console.logs here that

Start sendMessage
Before initialize
After initialize

I was unable to resolve this issue. I hope someone can offer assistance. Thank you!

Okay, so the problem is: You're recreating the client object every time you enter the sendMessage function. You should do this:
Your Client should be global, or you can pass it down as a variable to the sendMessage function. That way, you won't have to instantiate it every time you enter the sendMessage function.
Try to think it this way: It is a async function, that will be called 10, 20 or 200 times at the same second. At every time you call it, it will try to reopen the puppeteer that is inside the whatsapp-web.js lib, open the whatsapp web website, log in at whatsapp with your authstrategy and then try to send a message. It just won't work, since whatsapp web can only have one active session at a time.
So you need to pass the session down or make it global, and then you will be able to send messages properly.
As a rule of thumb, you can only have the client created ONE TIME at your project, except for very specific use cases.

"Thanks for your reply sir. Here I have a list of scheduled messages, each with a different sessionID. For example, message[0].sessionID = "2001," and message[1].sessionID = "2002." Each sessionID corresponds to a different WhatsApp account. In this situation, I kindly request your guidance on how to effectively resolve this issue. Your assistance would be greatly appreciated."

@claudiocassimiro
Copy link

I have the same problem here, the messages are sent to the whatsapp but the interface of the application not is updated and the messages are not saved to the database.

Yesterday on morning the application run normally, but without any changes, the behavior of not sent messages begin and I not find a solution for now

@marcioscf
Copy link

marcioscf commented Oct 4, 2023

createClient

You got most of it.
The biggest change i would make is on the createClient function:

    // When a user creates a scheduled message and specifies a session ID, create a new client
    function createClient(sessionID) {
        if (!sessionClients[sessionID]) {
            const client = new Client({
            qrMaxRetries: 2,
            puppeteer: {
                executablePath: CHROME_PATH,
            },
            authStrategy: new LocalAuth({
                clientId: sessionID,
            }),
            });
            client.on("qr", (qr) => {
            // Display the QR code for the user to scan
            console.log("Scan the QR code to authenticate:");
            console.log(qr);
            qrcode.generate(qr, { small: true });
            });

            client.on("authenticated", (data) => {
            console.log("AUTHENTICATED");
            });

            client.on("ready", async () => {
            console.log("Client is ready!");

            //Storing scheduled messages in a database.

            res.status(201).json({
                success: true,
                scheduledMessage,
            });
            });

            client.on("disconnected", async (reason) => {
            client.destroy(); // Destroy the client
            console.log("disconnected reason:", reason);
            return next(new ErrorHandler(reason, 500));
            });

            // Initialize the client
            client.initialize();

            // Store the client in the data structure
            sessionClients[sessionID] = client;
        }
        return sessionClients[sessionID];
    }

The events should be defined before the call of client.initialize().
That way, you can get the session as a variable. So i would initialize the client var this way:

// Create or use the client associated with this session const client = createClient(sessionID);

Just checked and another problem you should me receiving at your console is something like:
Can't set headers after they are sent to the client

That problem is because you're returning a HTTP response at every "ready" event.
Whatsapp-web.js is a event based library, so you will have to make some changes to your code if you want to use it as part of a server.

@marcioscf
Copy link

I have the same problem here, the messages are sent to the whatsapp but the interface of the application not is updated and the messages are not saved to the database.

Yesterday on morning the application run normally, but without any changes, the behavior of not sent messages begin and I not find a solution for now

Opa amigo!
Consegue colocar um código de exemplo para eu me basear?
No caso, você está conseguindo acessar as funções nativas do client e enviando a mensagem no whatsapp, porém não está não conseguindo enviar para o seu banco de dados?
Creio que esse problema seria o oposto do que está sendo discutido aqui, mas marca sua implementação que te dou uma ajuda!

@claudiocassimiro
Copy link

I have the same problem here, the messages are sent to the whatsapp but the interface of the application not is updated and the messages are not saved to the database.
Yesterday on morning the application run normally, but without any changes, the behavior of not sent messages begin and I not find a solution for now

Opa amigo! Consegue colocar um código de exemplo para eu me basear? No caso, você está conseguindo acessar as funções nativas do client e enviando a mensagem no whatsapp, porém não está não conseguindo enviar para o seu banco de dados? Creio que esse problema seria o oposto do que está sendo discutido aqui, mas marca sua implementação que te dou uma ajuda!

O meu problema aconteceu quando eu justamente agendei uma mensagem, antes de agendar uma mensagem tava funcionando normalmente vou tentar seguir sua solução e ver se dá certo

@Pdk3Dragon
Copy link
Author

createClient

You got most of it. The biggest change i would make is on the createClient function:

    // When a user creates a scheduled message and specifies a session ID, create a new client
    function createClient(sessionID) {
        if (!sessionClients[sessionID]) {
            const client = new Client({
            qrMaxRetries: 2,
            puppeteer: {
                executablePath: CHROME_PATH,
            },
            authStrategy: new LocalAuth({
                clientId: sessionID,
            }),
            });
            client.on("qr", (qr) => {
            // Display the QR code for the user to scan
            console.log("Scan the QR code to authenticate:");
            console.log(qr);
            qrcode.generate(qr, { small: true });
            });

            client.on("authenticated", (data) => {
            console.log("AUTHENTICATED");
            });

            client.on("ready", async () => {
            console.log("Client is ready!");

            //Storing scheduled messages in a database.

            res.status(201).json({
                success: true,
                scheduledMessage,
            });
            });

            client.on("disconnected", async (reason) => {
            client.destroy(); // Destroy the client
            console.log("disconnected reason:", reason);
            return next(new ErrorHandler(reason, 500));
            });

            // Initialize the client
            client.initialize();

            // Store the client in the data structure
            sessionClients[sessionID] = client;
        }
        return sessionClients[sessionID];
    }

The events should be defined before the call of client.initialize(). That way, you can get the session as a variable. So i would initialize the client var this way:

// Create or use the client associated with this session const client = createClient(sessionID);

Just checked and another problem you should me receiving at your console is something like: Can't set headers after they are sent to the client

That problem is because you're returning a HTTP response at every "ready" event. Whatsapp-web.js is a event based library, so you will have to make some changes to your code if you want to use it as part of a server.

Thank you, sir, your assistance has resolved my issue. I appreciate your help.

@alechkos
Copy link
Collaborator

alechkos commented Dec 1, 2023

Solved by @marcioscf

@alechkos alechkos closed this as completed Dec 1, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something isn't working
Projects
None yet
Development

No branches or pull requests

4 participants