giuseppecastaldo / ha-addons

Home Assistant Whatsapp Add-on
Apache License 2.0
49 stars 18 forks source link

Use on HA Docker install #8

Closed Chief-T1 closed 1 year ago

Chief-T1 commented 1 year ago

Hi,

I use the HA docker installation and don't have the addon store. Your addon looks really amazing and I would be really keen to use it. Is there a method in which I can install this on the docker install or would this be difficult to implement?

Thanks

piit79 commented 1 year ago

I think you can easily install this manually on a HA Docker install as follows:

I think that should be it. Mind you I haven't tested it as I'm using a virtualised HassOS installation, so there might be further little modifications required.

swinster commented 1 year ago

I guess one man's "easy" is another man's "WTF?!?!". @piit79, I had to think about what you said above, and as I am no expert in this field, so I thought I would add some more defined steps. Unfortunately, I got so far then failed to build the docker image (step 5).

  1. On your local host that is running docker, clone this git repo. I did this on a Synology NAS, with home folders enabled and the git server package installed. SSH into the host and run:
    git clone https://github.com/giuseppecastaldo/ha-addons.git
  2. Move to the correct folder:
    cd  ha-addons/whatsapp_addon
  3. Edit the custom_component/whatsapp.py file as per @piit79 notes above, so for me, this was something like this:
    
    import requests
    from url_normalize import url_normalize

HOST = 'http://192.168.0.1:3000/'

class Whatsapp: def send_message(self, data): return requests.post(url_normalize(f'{HOST}/sendMessage'), json=data).content == 'OK'

def set_status(self, data):
    return requests.post(url_normalize(f'{HOST}/setStatus'), json=data).content == 'OK'

def presence_subscribe(self, data):
    return requests.post(url_normalize(f'{HOST}/presenceSubscribe'), json=data).content == 'OK'

def send_presence_update(self, data):
    return requests.post(url_normalize(f'{HOST}/sendPresenceUpdate'), json=data).content == 'OK'

def send_infinity_presence_update(self, data):
    return requests.post(url_normalize(f'{HOST}/sendInfinityPresenceUpdate'), json=data).content == 'OK'
4.  Edit the `Dockerfile` file to not run the `run.sh` file:

ARG BUILD_FROM FROM $BUILD_FROM

RUN apk add --no-cache git npm

COPY . /

RUN chmod a+x /run.sh

RUN chmod a+x /finish.sh

RUN cd / && npm install -f

EXPOSE 3000

CMD [ "/run.sh" ]

5.  Build the docker image from the `Dockerfile`. From what i can see, the `build.yaml` file is used as an argument to be passed into the `Dockerfile`. However, this fails. I _think_ i need to `cat` the file, and I _think_ this is the way to do it, but I have no joy. 

sudo docker build --build-arg BUILD_FROM="$(cat build.yaml)" -t whatsapp-ha .


I get the output:

Sending build context to Docker daemon 248.3kB Step 1/7 : ARG BUILD_FROM Step 2/7 : FROM $BUILD_FROM invalid reference format



Assuming the above works, I think the next step would be to create the container.

If you have any ideas on what I'm doing wrong, that would be great.
piit79 commented 1 year ago

Apologies I didn't provide more details in my original comment as I didn't really have time for that - I thought I'd leave the details as an exercise for you ;)

First, I see you're disabling the CMD line in the Dockerfile completely - it would be OK, but you would have to specify the startup command when creating the container. Since the only line remaining in run.sh after disabling the custom component installation would be node index, I'd probably just change the CMD line in the Dockerfile to

CMD ["node", "index"]

Then, when building the image, you would probably have to specify the concrete source image for the --build-arg BUILD_FROM= argument. The addon image build must be looking up the image in build.yaml by the HA host arch and specifying it in a similar way. At first I thought Synology NAS would have some kind of Arm CPU, but that seems to be history - it looks like all recent Synology NAS devices use Intel CPUs with amd64 architecture.

Please let me know how you get on. I'll try to help more if I can :)

swinster commented 1 year ago

Yep on the build front :) - you beat me to posting ;)

I changed the Dockerfile to be (note, I had NOT changed the CMD line just yet):

# ARG BUILD_FROM
FROM ghcr.io/home-assistant/amd64-base

RUN apk add --no-cache git npm

COPY . /
# RUN chmod a+x /run.sh
RUN chmod a+x /finish.sh

RUN cd / && npm install -f

EXPOSE 3000
# CMD [ "/run.sh" ]

then ran:

sudo docker build -t whatsapp-ha .

Which at least completed a build of the image.

I need to crash now and will look more at this tomorrow.

Thanks.

swinster commented 1 year ago

ok, just before I fall over, I change the Dockerfile and run.sh file to:

Dockerfile:

# ARG BUILD_FROM
FROM ghcr.io/home-assistant/amd64-base

RUN apk add --no-cache git npm

COPY . /
RUN chmod a+x /run.sh
RUN chmod a+x /finish.sh

RUN cd / && npm install -f

EXPOSE 3000
CMD [ "/run.sh" ]

run.sh

#!/usr/bin/with-contenv bashio
set +u

# sed -i "s/{{HOSTNAME}}/$HOSTNAME/g" custom_component/whatsapp.py

mkdir -p config/custom_components/whatsapp
cp --recursive /custom_component/* config/custom_components/whatsapp/
bashio::log.info "Installed custom component."

node index

Built with:

sudo docker build -t whatsapp-ha .

A build completes OK, but I will have to wait until tomorrow to see if the container works, and if I can get HA to work with it.

piit79 commented 1 year ago

You're making good progress!

I see you left the custom component installation in run.sh - I assume you will mount the HA config folder to the container's /config folder to make this work? Not a bad idea, and it will save you the manual step of installing (or updating) the custom component.

I would expect the container to work. Then it's just a matter of the main HA container being able to access the API of the whatsapp container.

Please keep us updated :)

swinster commented 1 year ago

Er... yes.. it was a great idea... completely meant... not a fluke or luck at all...

Actually, I did want to map a local host folder to the container config folder, but the next step of mapping that to HA eluded me.

Even an infinite number of monkeys with infinite time, and an infinite number of typewriters, may produce Shakespeare's complete works at some point. I guess randomly bashing on the keyboard will have a similar end result with this ;)

Have a good rest of what is left of Christmas :)

swinster commented 1 year ago

okey-dokey, finally back to the land of the living, the container creates using the following docker-compose.yaml entry:

  whatsapp-ha:
    image: whatsapp-ha:latest
    container_name: whatsapp-ha
    volumes:
      - /data/whatsapp-ha:/config
    ports:
      - 3000:3000

Unfortunately, then exists immediately. The docker logs show:

s6-rc: info: service s6rc-oneshot-runner: starting
s6-rc: info: service s6rc-oneshot-runner successfully started
s6-rc: info: service fix-attrs: starting
s6-rc: info: service fix-attrs successfully started
s6-rc: info: service legacy-cont-init: starting
s6-rc: info: service legacy-cont-init successfully started
s6-rc: info: service legacy-services: starting
s6-rc: info: service legacy-services successfully started
[12:11:29] INFO: Installed custom component.
undefined:1

d
^
SyntaxError: Unexpected token u in JSON at position 0
    at JSON.parse (<anonymous>)
    at ReadFileContext.callback (/index.js:108:22)
    at FSReqCallback.readFileAfterOpen [as oncomplete] (node:fs:328:13)
Node.js v18.9.1
s6-rc: info: service legacy-services: stopping
s6-rc: info: service legacy-services successfully stopped
s6-rc: info: service legacy-cont-init: stopping
s6-rc: info: service legacy-cont-init successfully stopped
s6-rc: info: service fix-attrs: stopping
s6-rc: info: service fix-attrs successfully stopped
s6-rc: info: service s6rc-oneshot-runner: stopping
s6-rc: info: service s6rc-oneshot-runner successfully stopped

So, I think something needs to be fixed with JSON parsing, I think? Looking at the index.js file, there seem to be references to the /data folder, which I guess is something to do with the HA OS file structure. The folder doesn't exist in the HA Docker container, so there is no /data/options.json or /data/${key}.json (whatever the variable $key is supposed to represent - I don't know a lot about JavaScript :( ).

Currently, I don't have a HA OS installation (my server recently blew up and took the HA VM with it, hence using the Synology NAS to run docker).

Chief-T1 commented 1 year ago

Wow, it's great to see how much progress has been made. I raised the question but haven't had a chance to implement this myself yet.

I did a bit of research and found this page: https://developers.home-assistant.io/docs/add-ons/configuration/ which explains the use of options.json and the data folder.

Looking through index.js I noticed it refers to the supervisor which doesn't exist on docker installs. I wonder if this could be causing the issue and if there is another route which needs to be used to connect to the home assistant api?

piit79 commented 1 year ago

@swinster

Looking at the index.js file, there seem to be references to the /data folder, which I guess is something to do with the HA OS file structure. The folder doesn't exist in the HA Docker container, so there is no /data/options.json or /data/${key}.json (whatever the variable $key is supposed to represent - I don't know a lot about JavaScript :( ).

As far as I understand (looking at the link @Chief-T1 posted above helped as well) - /data/options.json file is the add-on options file which is normally set up in the add-on configuration tab. It contains the definitions of the WhatsApp clients (the add-on apparently supports multiple clients at the same time). By default there's only one client named default - that's also the "key" you are seeing in other parts of index.js.

So you should be able to fix this by configuring a persistent volume for the container, mounting it in /data and creating an options.json file there with the following content:

{
  "clients": [
    "default"
  ]
}

Unfortunately, as @Chief-T1 pointed out, the add-on uses the supervisor API to display the persistent notification with the linking QR code. That would have to be replaced by the native HA API as you have no supervisor...

Another much simpler (but much less user-friendly) possibility would be to dump the linking data into the add-on logs and then create the QR code manually using an on-line QR code.

Chief-T1 commented 1 year ago

I might be wrong but I think the API may still be available to use if you replace "http://supervisor/core/api/services with "http://<HA ip>:<HA port>/api/services

The example in the Rest API docs doesn't seem to use supervisor and connects to api/services using the ip and port. https://developers.home-assistant.io/docs/api/rest/

swinster commented 1 year ago

I'm sorry, I have been busy for a few days. Indeed @Chief-T1, issuing a GET method against the /api/services endpoint on my docker container returns all the available services:

For example,

PS C:\Users\me> curl -X GET `
>> -H "Authorization: Bearer eyJhbGciOiJIUzI...." `
>> -H "Content-Type: application/json" `
>>  http://192.168.1.1:8123/api/services

returns (truncated for easier reading) :

[
   {
      "domain": "persistent_notification",
      "services": {
         "create": {
            "name": "Create",
            "description": "Show a notification in the frontend.",
            "fields": {
               "message": {
                  "name": "Message",
                  "description": "Message body of the notification. [Templates accepted]",
                  "required": true,
                  "example": "Please check your configuration.yaml.",
                  "selector": {
                     "text": null
                  }
               },
               "title": {
                  "name": "Title",
                  "description": "Optional title for your notification. [Templates accepted]",
                  "example": "Test notification",
                  "selector": {
                     "text": null
                  }
               },
               "notification_id": {
                  "name": "Notification ID",
                  "description": "Target ID of the notification, will replace a notification with the same ID.",
                  "example": 1234,
                  "selector": {
                     "text": null
                  }
               }
            }
         },
....
]
swinster commented 1 year ago

Oh, a bit more progress, thanks to you two.

So, I added a folder data to the local host volume folder on the Synology (of course, this could be any docker host).

So, on the Synology, I have the volume root (mapped to /data/whatsapp-ha/)

|
|--config -
                | -- custom_components -
                                         | - whatsapp-ha -
                                                                  | - stuff
|--data - 
                |-- options.yaml

The data folder contains the options.yaml file as outlined by @piit79 in https://github.com/giuseppecastaldo/ha-addons/issues/8#issuecomment-1367356059

The docker-compose.yaml now contains the following:

  whatsapp-ha:
    image: whatsapp-ha:latest
    container_name: whatsapp-ha
    volumes:
      - /data/whatsapp-ha/config:/config
      - /data/whatsapp-ha/data:/data
    ports:
      - 3000:3000

Now, the container still exits, BUT it does spit out a whole bunch more logs:

logs.txt

HAPPY NEW YEAR (well, it might be if this is resolved).

From the logs, it looks as if the following URL (and probably others after this call), cannot be found:

url: 'http://supervisor/core/api/services/persistent_notification/create',

So, if this were redirected to.http://HA_Docker_IP_address/api/services/persistent_notification/create, would this work?

swinster commented 1 year ago

FWIW, I asked a question regarding converting add-ons to stand-alone docker containers in the HA community, and there was some good info posted (see https://community.home-assistant.io/t/is-it-possible-to-convert-an-addon-for-ha-os-to-run-in-a-standalone-container-for-ha-as-a-docker/511306/4?u=swinster) relating to the need for authentication toward the above API (as shown in https://github.com/giuseppecastaldo/ha-addons/issues/8#issuecomment-1368284184 with the use of a long live token)

swinster commented 1 year ago

Ok, I think I have a docker container running :) without exiting - here are the logs:

s6-rc: info: service s6rc-oneshot-runner: starting
s6-rc: info: service s6rc-oneshot-runner successfully started
s6-rc: info: service fix-attrs: starting
s6-rc: info: service fix-attrs successfully started
s6-rc: info: service legacy-cont-init: starting
s6-rc: info: service legacy-cont-init successfully started
s6-rc: info: service legacy-services: starting
s6-rc: info: service legacy-services successfully started
[20:26:45] INFO: Installed custom component.
[2023-01-02T20:26:46.773] [INFO] default - Whatsapp Addon started.
[2023-01-02T20:26:47.242] [INFO] default - default require authentication over QRCode, please see your notifications...
[2023-01-02T20:27:47.291] [INFO] default - default require authentication over QRCode, please see your notifications...

I edited the index.js file to add some static content, although converting them to parameters and passing in environment variables from the docker-compose.yaml when the docker container starts would be best (I think).

  1. I added a const to contain a Long-lived token (for example):

    const token = "eyJhbGciOiJIUzI1NiIsInR5c...........";
    1. Then, there are four references to the supervisor URL, so I changed that code to point to the HA docker and altered the bearer to use the new token constant. For example:

Original code:

const onReady = (key) => {
  logger.info(key, "client is ready.");
  axios.post(
    "http://supervisor/core/api/services/persistent_notification/dismiss",
    {
      notification_id: `whatsapp_addon_qrcode_${key}`,
    },
    {
      headers: {
        Authorization: `Bearer ${process.env.SUPERVISOR_TOKEN}`,
      },
    }
  );
}

Modified code block:

const onReady = (key) => {
  logger.info(key, "client is ready.");
  axios.post(
    "http://192.168.1.1:8123/api/services/persistent_notification/dismiss",
    {
      notification_id: `whatsapp_addon_qrcode_${key}`,
    },
    {
      headers: {
        Authorization: `Bearer ${token}`,
      },
    }
  );
}

I then rebuilt the image as before and re-ran it, and et voila.

Not sure where to go now though.

swinster commented 1 year ago

OK, I needed to pay more attention to the main HA Settings - a QR code automagically popup up and allowed me to connect to my WhatsApp account. I now have a new device logged in on Ubuntu. So, we are getting there..

Unfortunately, there seem to be some crashes in the Whatsapp-HA docker code, and I see no _whatsapp.sendmessage service.:

s6-rc: info: service s6rc-oneshot-runner: starting
s6-rc: info: service s6rc-oneshot-runner successfully started
s6-rc: info: service fix-attrs: starting
s6-rc: info: service fix-attrs successfully started
s6-rc: info: service legacy-cont-init: starting
s6-rc: info: service legacy-cont-init successfully started
s6-rc: info: service legacy-services: starting
s6-rc: info: service legacy-services successfully started
[20:55:25] INFO: Installed custom component.
[2023-01-02T20:55:27.987] [INFO] default - Whatsapp Addon started.
[2023-01-02T20:55:28.383] [INFO] default - default require authentication over QRCode, please see your notifications...
[2023-01-02T20:56:28.424] [INFO] default - default require authentication over QRCode, please see your notifications...
[2023-01-02T20:56:48.460] [INFO] default - default require authentication over QRCode, please see your notifications...
[2023-01-02T20:57:08.478] [INFO] default - default require authentication over QRCode, please see your notifications...
[2023-01-02T20:57:22.268] [INFO] default - default client is ready.
2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 pid=83 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 pid=83 hostname=2022a2f1ac2c 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 pid=83 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 pid=83 hostname=2022a2f1ac2c stack=Error: mutex start
    at /node_modules/@giuseppecastaldo/baileys/lib/Utils/make-mutex.js:15:31
    at Object.mutex (/node_modules/@giuseppecastaldo/baileys/lib/Utils/make-mutex.js:35:15)
    at handleMessage (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:451:29)
    at execTask (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:554:20)
    at processNodeWithBuffer (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:551:15)
    at WebSocket.<anonymous> (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:560:9)
    at WebSocket.emit (node:events:513:28)
    at /node_modules/@giuseppecastaldo/baileys/lib/Socket/socket.js:222:35
    at Object.decodeFrame (/node_modules/@giuseppecastaldo/baileys/lib/Utils/noise-handler.js:131:17)
    at WebSocket.onMessageRecieved (/node_modules/@giuseppecastaldo/baileys/lib/Socket/socket.js:198:15) 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 pid=83 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 pid=83 hostname=2022a2f1ac2c 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 pid=83 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 pid=83 hostname=2022a2f1ac2c stack=Error: mutex start
    at /node_modules/@giuseppecastaldo/baileys/lib/Utils/make-mutex.js:15:31
    at Object.mutex (/node_modules/@giuseppecastaldo/baileys/lib/Utils/make-mutex.js:35:15)
    at handleMessage (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:451:29)
    at execTask (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:554:20)
    at processNodeWithBuffer (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:551:15)
    at WebSocket.<anonymous> (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:560:9)
    at WebSocket.emit (node:events:513:28)
    at /node_modules/@giuseppecastaldo/baileys/lib/Socket/socket.js:222:35
    at Object.decodeFrame (/node_modules/@giuseppecastaldo/baileys/lib/Utils/noise-handler.js:131:17)
    at WebSocket.onMessageRecieved (/node_modules/@giuseppecastaldo/baileys/lib/Socket/socket.js:198:15) waitOver=true 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 pid=83 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 pid=83 hostname=2022a2f1ac2c 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 pid=83 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 pid=83 hostname=2022a2f1ac2c stack=Error: mutex start
    at /node_modules/@giuseppecastaldo/baileys/lib/Utils/make-mutex.js:15:31
    at Object.mutex (/node_modules/@giuseppecastaldo/baileys/lib/Utils/make-mutex.js:35:15)
    at handleMessage (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:451:29)
    at execTask (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:554:20)
    at processNodeWithBuffer (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:551:15)
    at WebSocket.<anonymous> (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:560:9)
    at WebSocket.emit (node:events:513:28)
    at /node_modules/@giuseppecastaldo/baileys/lib/Socket/socket.js:222:35
    at Object.decodeFrame (/node_modules/@giuseppecastaldo/baileys/lib/Utils/noise-handler.js:131:17)
    at WebSocket.onMessageRecieved (/node_modules/@giuseppecastaldo/baileys/lib/Socket/socket.js:198:15) 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 pid=83 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 pid=83 hostname=2022a2f1ac2c 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 pid=83 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 2023-01-02T20:58:23.697Z 2023-01-02T20:58:23.697Z 40 pid=83 hostname=2022a2f1ac2c stack=Error: mutex start
    at /node_modules/@giuseppecastaldo/baileys/lib/Utils/make-mutex.js:15:31
    at Object.mutex (/node_modules/@giuseppecastaldo/baileys/lib/Utils/make-mutex.js:35:15)
    at handleMessage (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:451:29)
    at execTask (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:554:20)
    at processNodeWithBuffer (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:551:15)
    at WebSocket.<anonymous> (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:560:9)
    at WebSocket.emit (node:events:513:28)
    at /node_modules/@giuseppecastaldo/baileys/lib/Socket/socket.js:222:35
    at Object.decodeFrame (/node_modules/@giuseppecastaldo/baileys/lib/Utils/noise-handler.js:131:17)
    at WebSocket.onMessageRecieved (/node_modules/@giuseppecastaldo/baileys/lib/Socket/socket.js:198:15) waitOver=true msg=possible mutex deadlock
2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 pid=83 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 pid=83 hostname=2022a2f1ac2c 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 pid=83 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 pid=83 hostname=2022a2f1ac2c stack=Error: mutex start
    at /node_modules/@giuseppecastaldo/baileys/lib/Utils/make-mutex.js:15:31
    at Object.mutex (/node_modules/@giuseppecastaldo/baileys/lib/Utils/make-mutex.js:35:15)
    at handleMessage (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:451:29)
    at execTask (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:554:20)
    at processNodeWithBuffer (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:551:15)
    at WebSocket.<anonymous> (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:560:9)
    at WebSocket.emit (node:events:513:28)
    at /node_modules/@giuseppecastaldo/baileys/lib/Socket/socket.js:222:35
    at Object.decodeFrame (/node_modules/@giuseppecastaldo/baileys/lib/Utils/noise-handler.js:131:17)
    at WebSocket.onMessageRecieved (/node_modules/@giuseppecastaldo/baileys/lib/Socket/socket.js:198:15) 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 pid=83 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 pid=83 hostname=2022a2f1ac2c 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 pid=83 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 pid=83 hostname=2022a2f1ac2c stack=Error: mutex start
    at /node_modules/@giuseppecastaldo/baileys/lib/Utils/make-mutex.js:15:31
    at Object.mutex (/node_modules/@giuseppecastaldo/baileys/lib/Utils/make-mutex.js:35:15)
    at handleMessage (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:451:29)
    at execTask (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:554:20)
    at processNodeWithBuffer (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:551:15)
    at WebSocket.<anonymous> (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:560:9)
    at WebSocket.emit (node:events:513:28)
    at /node_modules/@giuseppecastaldo/baileys/lib/Socket/socket.js:222:35
    at Object.decodeFrame (/node_modules/@giuseppecastaldo/baileys/lib/Utils/noise-handler.js:131:17)
    at WebSocket.onMessageRecieved (/node_modules/@giuseppecastaldo/baileys/lib/Socket/socket.js:198:15) waitOver=true 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 pid=83 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 pid=83 hostname=2022a2f1ac2c 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 pid=83 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 pid=83 hostname=2022a2f1ac2c stack=Error: mutex start
    at /node_modules/@giuseppecastaldo/baileys/lib/Utils/make-mutex.js:15:31
    at Object.mutex (/node_modules/@giuseppecastaldo/baileys/lib/Utils/make-mutex.js:35:15)
    at handleMessage (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:451:29)
    at execTask (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:554:20)
    at processNodeWithBuffer (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:551:15)
    at WebSocket.<anonymous> (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:560:9)
    at WebSocket.emit (node:events:513:28)
    at /node_modules/@giuseppecastaldo/baileys/lib/Socket/socket.js:222:35
    at Object.decodeFrame (/node_modules/@giuseppecastaldo/baileys/lib/Utils/noise-handler.js:131:17)
    at WebSocket.onMessageRecieved (/node_modules/@giuseppecastaldo/baileys/lib/Socket/socket.js:198:15) 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 pid=83 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 pid=83 hostname=2022a2f1ac2c 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 pid=83 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 2023-01-02T20:58:23.728Z 2023-01-02T20:58:23.728Z 40 pid=83 hostname=2022a2f1ac2c stack=Error: mutex start
    at /node_modules/@giuseppecastaldo/baileys/lib/Utils/make-mutex.js:15:31
    at Object.mutex (/node_modules/@giuseppecastaldo/baileys/lib/Utils/make-mutex.js:35:15)
    at handleMessage (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:451:29)
    at execTask (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:554:20)
    at processNodeWithBuffer (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:551:15)
    at WebSocket.<anonymous> (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:560:9)
    at WebSocket.emit (node:events:513:28)
    at /node_modules/@giuseppecastaldo/baileys/lib/Socket/socket.js:222:35
    at Object.decodeFrame (/node_modules/@giuseppecastaldo/baileys/lib/Utils/noise-handler.js:131:17)
    at WebSocket.onMessageRecieved (/node_modules/@giuseppecastaldo/baileys/lib/Socket/socket.js:198:15) waitOver=true msg=possible mutex deadlock
2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 pid=83 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 pid=83 hostname=2022a2f1ac2c 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 pid=83 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 pid=83 hostname=2022a2f1ac2c stack=Error: mutex start
    at /node_modules/@giuseppecastaldo/baileys/lib/Utils/make-mutex.js:15:31
    at Object.mutex (/node_modules/@giuseppecastaldo/baileys/lib/Utils/make-mutex.js:35:15)
    at handleMessage (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:451:29)
    at execTask (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:554:20)
    at processNodeWithBuffer (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:551:15)
    at WebSocket.<anonymous> (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:560:9)
    at WebSocket.emit (node:events:513:28)
    at /node_modules/@giuseppecastaldo/baileys/lib/Socket/socket.js:222:35
    at Object.decodeFrame (/node_modules/@giuseppecastaldo/baileys/lib/Utils/noise-handler.js:131:17)
    at WebSocket.onMessageRecieved (/node_modules/@giuseppecastaldo/baileys/lib/Socket/socket.js:198:15) 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 pid=83 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 pid=83 hostname=2022a2f1ac2c 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 pid=83 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 pid=83 hostname=2022a2f1ac2c stack=Error: mutex start
    at /node_modules/@giuseppecastaldo/baileys/lib/Utils/make-mutex.js:15:31
    at Object.mutex (/node_modules/@giuseppecastaldo/baileys/lib/Utils/make-mutex.js:35:15)
    at handleMessage (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:451:29)
    at execTask (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:554:20)
    at processNodeWithBuffer (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:551:15)
    at WebSocket.<anonymous> (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:560:9)
    at WebSocket.emit (node:events:513:28)
    at /node_modules/@giuseppecastaldo/baileys/lib/Socket/socket.js:222:35
    at Object.decodeFrame (/node_modules/@giuseppecastaldo/baileys/lib/Utils/noise-handler.js:131:17)
    at WebSocket.onMessageRecieved (/node_modules/@giuseppecastaldo/baileys/lib/Socket/socket.js:198:15) waitOver=true 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 pid=83 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 pid=83 hostname=2022a2f1ac2c 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 pid=83 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 pid=83 hostname=2022a2f1ac2c stack=Error: mutex start
    at /node_modules/@giuseppecastaldo/baileys/lib/Utils/make-mutex.js:15:31
    at Object.mutex (/node_modules/@giuseppecastaldo/baileys/lib/Utils/make-mutex.js:35:15)
    at handleMessage (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:451:29)
    at execTask (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:554:20)
    at processNodeWithBuffer (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:551:15)
    at WebSocket.<anonymous> (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:560:9)
    at WebSocket.emit (node:events:513:28)
    at /node_modules/@giuseppecastaldo/baileys/lib/Socket/socket.js:222:35
    at Object.decodeFrame (/node_modules/@giuseppecastaldo/baileys/lib/Utils/noise-handler.js:131:17)
    at WebSocket.onMessageRecieved (/node_modules/@giuseppecastaldo/baileys/lib/Socket/socket.js:198:15) 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 pid=83 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 pid=83 hostname=2022a2f1ac2c 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 pid=83 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 2023-01-02T20:58:23.788Z 2023-01-02T20:58:23.788Z 40 pid=83 hostname=2022a2f1ac2c stack=Error: mutex start
    at /node_modules/@giuseppecastaldo/baileys/lib/Utils/make-mutex.js:15:31
    at Object.mutex (/node_modules/@giuseppecastaldo/baileys/lib/Utils/make-mutex.js:35:15)
    at handleMessage (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:451:29)
    at execTask (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:554:20)
    at processNodeWithBuffer (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:551:15)
    at WebSocket.<anonymous> (/node_modules/@giuseppecastaldo/baileys/lib/Socket/messages-recv.js:560:9)
    at WebSocket.emit (node:events:513:28)
    at /node_modules/@giuseppecastaldo/baileys/lib/Socket/socket.js:222:35
    at Object.decodeFrame (/node_modules/@giuseppecastaldo/baileys/lib/Utils/noise-handler.js:131:17)
    at WebSocket.onMessageRecieved (/node_modules/@giuseppecastaldo/baileys/lib/Socket/socket.js:198:15) waitOver=true msg=possible mutex deadlock

If I tried to add:

whatsapp:

to the HA configuration.yaml file (as you would do with an add-on, as directed per https://github.com/giuseppecastaldo/ha-addons#installation-guide), HA doesn't like it:

2023-01-02 21:02:00.425 ERROR (MainThread) [homeassistant.components.homeassistant] The system cannot restart because the configuration is not valid: Integration error: whatsapp - Integration 'whatsapp' not found.
2023-01-02 21:02:00.455 ERROR (MainThread) [homeassistant.components.websocket_api.http.connection] [140585782764368] The system cannot restart because the configuration is not valid: Integration error: whatsapp - Integration 'whatsapp' not found.
Traceback (most recent call last):
File "/usr/src/homeassistant/homeassistant/components/websocket_api/commands.py", line 200, in handle_call_service
await hass.services.async_call(
File "/usr/src/homeassistant/homeassistant/core.py", line 1745, in async_call
task.result()
File "/usr/src/homeassistant/homeassistant/core.py", line 1782, in _execute_service
await cast(Callable[[ServiceCall], Awaitable[None]], handler.job.target)(
File "/usr/src/homeassistant/homeassistant/helpers/service.py", line 748, in admin_handler
await result
File "/usr/src/homeassistant/homeassistant/components/homeassistant/__init__.py", line 174, in async_handle_core_service
raise HomeAssistantError(
homeassistant.exceptions.HomeAssistantError: The system cannot restart because the configuration is not valid: Integration error: whatsapp - Integration 'whatsapp' not found.
piit79 commented 1 year ago

@swinster

Good progress! I'm not sure what the mutex issues mean, or what could be causing them unfortunately...

If I tried to add: whatsapp:

That would mean you don't have the custom component installed yet, or it's installed, but not active. If you've installed it and want to avoid a double restart, just restart the main HA docker manually (skipping the configuration check).

Or remove the whatsapp: key from configuration.yaml, restart, and then add it back and restart again. Then you should be able to see the new whatsapp.* services.

swinster commented 1 year ago

Ok, I'm not entirely sure how to install the custom component yet. It's not an integration (and doesn't appear in that list), and other is no concept of add-ons in HA Docker. I will re-read the above to see if there are things I glossed over, but whatever I do to either restart HA or the HA docker (with the WhatsApp docker running), as soon as I re-add whatsapp: to the configuration.yaml, I get an invalid config.

piit79 commented 1 year ago

The custom component is the code that provides the new whatsapp integration that you can then add to your configuration.

If you check the docker entrypoint script run.sh, it's installed there automatically - it goes into $CONFIG/custom_components (where $CONFIG is your configuration folder that contains configuration.yaml). To manually install the custom component, copy the contents of custom_component folder into $CONFIG/custom_components/whatsapp. You will want to modify whatsapp.py first and change HOST = to the IP address/hostname of your whatsapp docker container.

Then restart HA, add whatsapp: to your configuration.yaml and you should be able to see the new services.

swinster commented 1 year ago

Awesome. I guess this is what you were talking about previously regarding mapping volumes. After sleeping on it, the change is simple and doesn't involve manually copying config, but rather redirecting the config/custom_components directory from the whatsapp contain to the HA container through updating the docker-compose.yaml. The new docker compose config for these containers are:

# Note: the local volume '/data' uses a symbolic link to allow simpler transportation of container data to a new server
# e.g., 'ln -s /volume1/docker /data' on a Synology NAS.
# 
version: '3'
services:
  homeassistant:
    container_name: homeassistant
    image: "ghcr.io/home-assistant/home-assistant:stable"
    volumes:
      - /data/homeassistant:/config
      - /etc/localtime:/etc/localtime:ro
    restart: unless-stopped
    privileged: true
    network_mode: host

  whatsapp-ha:
    image: whatsapp-ha:latest
    container_name: whatsapp-ha
    volumes:
      - /data/homeassistant/custom_components:/config/custom_components
      - /data/whatsapp-ha/data:/data
    ports:
      - 3000:3000

And once HA has restarted, we can see the WhatsApp services:

image

I haven't tried to send anything yet, which may need to wait for a bit but I will try later.

swinster commented 1 year ago

FWIW, I have tried to send some messages via the Dev Tools --> Services, but have not managed it yet. If I log out of the device, I immediately see a QR code to re-link, but I cannot seem to get the send params (and probably the Target User ID) correct.

Will try again tomorrow.

Chief-T1 commented 1 year ago

That's great you now see the services in home assistant. Hopefully this is the last stretch and you're nearly there πŸ™‚. I'm not sure what you're using for the send params but this page (hidden away from the home page) already has some example params for each service and states how the user id should be formatted.

swinster commented 1 year ago

In theWhatsApp container logs, I still see the mutex deadlock, but not also something simpler:

[2023-01-04T00:55:03.787] [ERROR] default - Cannot read properties of undefined (reading 'payload')
[2023-01-04T00:55:34.984] [ERROR] default - Cannot read properties of undefined (reading 'payload')

So I guess I am not creating the body of the message correctly: image

Chief-T1 commented 1 year ago

That all matches what I see in the documentation apart from body where they've used it in this format. So hopefully that should get it working body: text: Hi it's a simple text message

swinster commented 1 year ago

@Chief-T1 , I have missed this, where did you see this? It would imply that body has multiple sub properties, likely also subject and possibly others. I did try to read the code relating to this, but as nothing more than a amateur, I didn't extract what was required.

giuseppecastaldo commented 1 year ago

It seems that all problems have been solved, I close the issue.

swinster commented 1 year ago
piit79 commented 1 year ago

That's great to hear, @swinster! I'm glad I could help a bit.

The body parameter is indeed an object with quite a few possible properties. It's not very easy to find out what they are, as the actual message sending is handled by an external library @adiwajshing/baileys. Looking at the source, the content parameter of the sendMessage method is of type AnyMessageContent defined here (slightly below actually as it's a union type with AnyRegularMessageContent). One would still need to dive into the subtypes used by the various properties to get the full picture. I guess there must be a simpler description somewhere else :)

swinster commented 1 year ago

Hmm, I was looking to see if I could build an image that wouldn't require manual configuration for each user (by hopefully passing docker environment variables into the container to remove the reliance on the template variable {{HOSTNAME}} in the whatsapp.py file, plus the static URL http://supervisor/core and the HA supervisor token ${process.env.SUPERVISOR_TOKEN} from the index.js file), but I now seem to have a build error:

npm ERR! code 128
npm ERR! An unknown git error occurred
npm ERR! command git --no-replace-objects ls-remote ssh://git@github.com/giuseppecastaldo/Baileys.git
npm ERR! ssh -oStrictHostKeyChecking=accept-new: line 0: ssh: not found
npm ERR! fatal: Could not read from remote repository.
npm ERR! 
npm ERR! Please make sure you have the correct access rights
npm ERR! and the repository exists.

I checked, and the giuseppecastaldo/balieys repo no longer exists. I guess this was forked from adiwajshing/baileys in the first place?

swinster commented 1 year ago

OK, never mind, I see a bunch of things (including this) have changed in the last commit. Just trying to keep me on my toes ;)

giuseppecastaldo commented 1 year ago
  • whilst this is "working", I wouldn't necessarily say it's "fixed". There is a lot of hacking and manual configuration to get this to work (such as WRT authentication and host addressing). It would also be nice to update documentation and examples. I can try to summarise the steps below to get to this stage, but it might require someone with more coding experience to make the solution more elegant.

This add-on is tested on various supervised home assistant devices. I don't understand everything you did with the docker compose file, it's not included in my repo, sorry. In the README file there is also an installation guide which in my opinion is not that difficult.

swinster commented 1 year ago

UPDATED: Updated the index.js file to better use the environment variables.


UPDATED 2: There was a bug in the whatsapp.py file (wasn't using 'f'-strings), and we need to add an environment variable HOSTNAME_ID to the Home Assistant container, as this is the context where the whatsapp.py file runs (not the whatsapp-ha container)


@Chief-T1 , I think I might have made some progress in creating an image that can be reused (although, TBH, I am kind of randomly bashing the keyboard ;) ). Currently, this is built using the ghcr.io/home-assistant/amd64-base for my Synology device - I am not sure if that is useful for you? You can pull the image from here:

https://hub.docker.com/r/swinster/whatsapp-ha

The following docker-compose service component for the whatsapp-ha container should help:

NOTE: I link the /data/ folder to the docker root folder location, just for ease of use. The default Synology docker location is (also assuming that you use the default volume1 when creating a data volume) /volume1/docker/.

  whatsapp-ha:
    image: swinster/whatsapp-ha:amd64-base
    container_name: whatsapp-ha
    volumes:
      - /data/homeassistant/custom_components:/config/custom_components
      - /data/whatsapp-ha/data:/data
    ports:
      - 3000:3000
    environment:
      - HA_PORT=<Port_used_by_HA_container>
      - HOSTNAME_ID=<IP_Address_of_HA_container>
      - TOKEN=<long_livedHA_token>

The three environment variables map to variables used in the index.js file, which I have modified to read these variables, but if they do not exist, then ignore them and use what was coded previously. This should allow this file to be used to create both standalone docker images AND still be used to create the add-on.

You also need to add the HOSTNAME_ID environment variable to the HA container as the whatsapp.py file runs within this context, and should point to the whatsapp-ha container (likely to be the same IP as the HA container, assuming you are running everything in the same stack). Remember, the default port to connect to the whatsapp-ha container is 3000, but I haven't made this configurable at the moment (I suppose another env variable could be used if required). Again, the whatsapp.py file will read in this environment variable and use if it is exists, if it doesn't exist, it will use the what was coded previously, so this file should be able to be use in both add-on and stand-alone container.

As an example, here is my HA docker-compose.yaml service component:

  homeassistant:
    container_name: homeassistant
    image: "ghcr.io/home-assistant/home-assistant:stable"
    volumes:
      - /data/homeassistant:/config
      - /etc/localtime:/etc/localtime:ro
    restart: unless-stopped
    privileged: true
    network_mode: host
    environment:
      - HOSTNAME_ID=<IP_Address_of_WhatsApp-ha_container>

I'm sure this is an inefficient way of doing things, but its a start :)

For reference, here are the modified index.js and whatsapp.py files (named to .txt) :

index.js.txt whatsapp.py.txt

swinster commented 1 year ago
  • whilst this is "working", I wouldn't necessarily say it's "fixed". There is a lot of hacking and manual configuration to get this to work (such as WRT authentication and host addressing). It would also be nice to update documentation and examples. I can try to summarise the steps below to get to this stage, but it might require someone with more coding experience to make the solution more elegant.

This add-on is tested on various supervised home assistant devices. I don't understand everything you did with the docker compose file, it's not included in my repo, sorry. In the README file there is also an installation guide which in my opinion is not that difficult.

@giuseppecastaldo, you are correct, it is not that difficult - assuming you are using a supervised HA deployment. If you are running on a HA that is non-supervised (such as in an HA Docker container), there is no facility for an add-on at all, hence this thread. What we have done here is take the add-on and turned it into a stand-alone docker image that could then be deployed in non-supervised HA deployments. WIth a bit of luck, the modification above should allow people to deploy it as an add-on OR a stand-alone container.

swinster commented 1 year ago

UPDATE - to make better use of environment variables


UPDATE 2 - Added some steps to explain about persistent volumes and mapping them to the docker containers, and added the options.json file that it required.


I need help figuring out (at the moment) how to build the images for other architectures (such as arm7), given I do not have access to those architectures. If the various images could be built and published online as per the amd64 image above, all you would need is the docker-compose yaml info

In the meantime, here is my manual build process:


  1. On your local host that is running docker, clone this git repo. I did this on a Synology NAS, with home folders enabled and the git server package installed. SSH into the host and run:

    git clone https://github.com/giuseppecastaldo/ha-addons.git
  2. Move to the correct folder:

    cd  ha-addons/whatsapp_addon
  3. Upload/overwrite the index.js.txt to your current folder, and the whatsapp.py.txt to the custom_component/ folder (remembering to remove the .txt file extension).

  4. Edit the Dockerfile file build for the HA architecture that matches your architecture (edit the second line). For me, this is:

    
    ARG BUILD_FROM
    FROM ghcr.io/home-assistant/amd64-base

RUN apk add --no-cache git npm

COPY . / RUN chmod a+x /run.sh RUN chmod a+x /finish.sh

RUN cd / && npm install -f

EXPOSE 3000 CMD [ "/run.sh" ]

Other architectures are:

ghcr.io/home-assistant/aarch64-base ghcr.io/home-assistant/amd64-base ghcr.io/home-assistant/armhf-base ghcr.io/home-assistant/armv7-base ghcr.io/home-assistant/i386-base


 5.  Build the docker image from the `Dockerfile`, which will build the docker image locally

sudo docker build -t whatsapp-ha .


 6. Create some folders on the host to contain the persistent data for the WhatsApp-HA container. The HA container should already (hopefully) map the Custom Components folder, which we will also need. For example, I am using a Synology NAS drive, and by default, the docker containers are stored in `/volume1/docker/`. To make things a little more manageable _for me_ (in case I move data to another host later), I created a symbolic link to this folder that mapped to the `/data/` folder. Thus, I end up with two persistent volumes:

 - `/data/homeassistant/custom_components` - this is the persistent folder for the HA docker container that contains information about custom components. When the `whatsapp-ha` docker runs, it will copy some files into a `custom_components` folder (including the `whatsapp.py` file), and as this will also be mapped to the HA `custom_components` folder, so HA will have access to these files.  
 - `/data/whatsapp-ha/data` - this is where the WhatsApp-HA container will write its data into an `default.json` file (which stores things like logged in WhatsApp clients, sent messages, etc). It also needs to contain an `options.json` file, which will will add in the next step. 

 7. You need to add an `options.json` file to the persistent volume you just created (i.e. `/data/whatsapp-ha/data`). Use the follow file, but you need to remove the `.txt` extension. I'm sure this would be added to this repo to make this step simpler, but for now, it is what it is.
    [options.json.txt](https://github.com/giuseppecastaldo/ha-addons/files/10419364/options.json.txt)

 8.  Create the docker container. This YAML extract differs from the above as it creates the container based on the local image (rather than pulling from the online repo).
```yaml
  whatsapp-ha:
    image: whatsapp-ha
    container_name: whatsapp-ha
    volumes:
      - /data/homeassistant/custom_components:/config/custom_components
      - /data/whatsapp-ha/data:/data
    ports:
      - 3000:3000
    environment:
      - HA_PORT=<Port_used_by_HA_container>
      - HOSTNAME_ID=<IP_Address_of_HA_container>
      - TOKEN=<long_livedHA_token>

NOTE: make sure you then update the HA_PORT, HOSTNAME_ID and TOKEN. If HA_PORT is not defined, it defaults to 8123.

  1. Add an environment variable to the HA docker container so that the whatsapp.py file can connect to the whatsapp-ha container. For example:
  homeassistant:
    container_name: homeassistant
    image: "ghcr.io/home-assistant/home-assistant:stable"
    volumes:
      - /data/homeassistant:/config
      - /etc/localtime:/etc/localtime:ro
    restart: unless-stopped
    privileged: true
    network_mode: host
    environment:
      - HOSTNAME_ID=<IP_Address_of_WhatsApp-ha_container>

NOTE 2: make sure you update the HOSTNAME_ID (likely to be the same address as the HA container).

swinster commented 1 year ago

I was going to look at creating multiple architecture stand-alone docker images, but unfortunately (for some reason), I am now seeing a Syntax error in whatsapp.js when attempting to start the container. I could have sworn I had it working a few days ago :( .

[2023-01-07T17:56:58.972] [INFO] default - Whatsapp Addon has started.
undefined:1778
}{
 ^
SyntaxError: Unexpected token { in JSON at position 60391
    at JSON.parse (<anonymous>)
    at useFileAuthState (/utils/useFileAuthState.js:34:43)
    at async WhatsappClient.connect (/whatsapp.js:51:38)
Node.js v18.9.1

It does look like a commit was made that changed things on this line (https://github.com/giuseppecastaldo/ha-addons/commit/5429368a0b48e48f8b526884ecd90627957f4576#diff-042b282ca284738d79e928df8b79cf09d265058fd48103b6a401d9034701a3bf), but I am not skilled enough to understand why this is causing an issue now. Even so, things worked after I pulled these changes, so I wonder why they have broken now.

giuseppecastaldo commented 1 year ago

I was going to look at creating multiple architecture stand-alone docker images, but unfortunately (for some reason), I am now seeing a Syntax error in whatsapp.js when attempting to start the container. I could have sworn I had it working a few days ago :( .


[2023-01-07T17:56:58.972] [INFO] default - Whatsapp Addon has started.

undefined:1778

}{

 ^

SyntaxError: Unexpected token { in JSON at position 60391

    at JSON.parse (<anonymous>)

    at useFileAuthState (/utils/useFileAuthState.js:34:43)

    at async WhatsappClient.connect (/whatsapp.js:51:38)

Node.js v18.9.1

It does look like a commit was made that changed things on this line (https://github.com/giuseppecastaldo/ha-addons/commit/5429368a0b48e48f8b526884ecd90627957f4576#diff-042b282ca284738d79e928df8b79cf09d265058fd48103b6a401d9034701a3bf), but I am not skilled enough to understand why this is causing an issue now. Even so, things worked after I pulled these changes, so I wonder why they have broken now.

I'm checking the problem, thanks for reporting

giuseppecastaldo commented 1 year ago

I was going to look at creating multiple architecture stand-alone docker images, but unfortunately (for some reason), I am now seeing a Syntax error in whatsapp.js when attempting to start the container. I could have sworn I had it working a few days ago :( .

[2023-01-07T17:56:58.972] [INFO] default - Whatsapp Addon has started.
undefined:1778
}{
 ^
SyntaxError: Unexpected token { in JSON at position 60391
    at JSON.parse (<anonymous>)
    at useFileAuthState (/utils/useFileAuthState.js:34:43)
    at async WhatsappClient.connect (/whatsapp.js:51:38)
Node.js v18.9.1

It does look like a commit was made that changed things on this line (5429368#diff-042b282ca284738d79e928df8b79cf09d265058fd48103b6a401d9034701a3bf), but I am not skilled enough to understand why this is causing an issue now. Even so, things worked after I pulled these changes, so I wonder why they have broken now.

I installed the add-on on a clean instance of Home Assistant and there doesn't seem to be any issues. Maybe it's a cache problem. Try uninstalling the addon completely or doing a rebuild.

Chief-T1 commented 1 year ago

Hi @swinster Well done on your work, you've made really great progress. Sorry for the recent radio silence, I haven't had too much time to look at this recently. But am planning to try and follow your installation steps later this week.

I use a Raspberry pi 4 which is ARM64 architecture, so I can test the installation on this.

I just had a couple of questions from your comment here: https://github.com/giuseppecastaldo/ha-addons/issues/8#issuecomment-1371312444

When you say:

NOTE: I link the /data/ folder to the docker root folder location, just for ease of use. The default Synology docker location is (also assuming that you use the default volume1 when creating a data volume) /volume1/docker/.

I use openmediavault and my docker data folders are on different drives. I've never used symbolic links before (although it looks like something I should learn about using in the future) but can I just reference the path location as I normally would or do I need to change something else too?

For this bit here, I already have some custom_components which I want to keep separate, I assume I can just reference the whatsapp component folder inside the custom_component folder instead?

volumes:

  • /data/homeassistant/custom_components:/config/custom_components

I currently access HA over https and have an SSL certificate. Is this where the hostname environment variable you mentioned comes into play or would this not work over https?

environment:
- HOSTNAME_ID=<IP_Address_of_HA_container>

Thanks again for all your great work πŸ˜„

swinster commented 1 year ago

I installed the add-on on a clean instance of Home Assistant and there doesn't seem to be any issues. Maybe it's a cache problem. Try uninstalling the addon completely or doing a rebuild.

@giuseppecastaldo , indeed, whist what we are doing here is NOT working on the add-on and instead we are working on a standalone docker image, I removed all previous configuration, re-cloned this git repo and replace the index.js and whatsapp.py file with the modified versions (which I think should work for both standalone docker image builds as well as the add-on build), then rebuilt the docker image and container, and it looks like everything is back working.

FWIW, I have also figured out how to build separate containers based on different architectures using the HA builder, so with a bit of luck, we should be able to publish standalone docker containers for all architectures.

@Chief-T1 in the process of re-building the above and going back to a blank canvas, I realised that there were a couple of bit missing from my build process above. I will add those to the post above (https://github.com/giuseppecastaldo/ha-addons/issues/8#issuecomment-1371347953 - which will be UPDATE 2). However, if the build process works as I hope, then YOU would NOT need to build, merely add the relevant docker-compose configuration to grab the correct docker whatsapp-ha image .

P.S. I am merely floundering my way through this :) The "great work" celebration need to go towards @giuseppecastaldo and the others to bring this functionality to the stage.

swinster commented 1 year ago

@Chief-T1

When you say:

NOTE: I link the /data/ folder to the docker root folder location, just for ease of use. The default Synology docker location is (also assuming that you use the default volume1 when creating a data volume) /volume1/docker/.

I use openmediavault and my docker data folders are on different drives. I've never used symbolic links before (although it looks like something I should learn about using in the future) but can I just reference the path location as I normally would or do I need to change something else too?

Yes, you can use your path - i.e. /whatever/path/you/have/to/openmediavault/docker/

FWIW, think of a symbolic link as an alias to that folder. For example, if you ran:

ln -s /whatever/path/you/have/to/openmediavault/docker /data

it maps the /data folder to your actual folder (in this case, /whatever/path/you/have/to/openmediavault/docker/, but of course, it could be any folder). If you then list the contents of the root folder and show links (using the -l parameter), you will see the link. For me, this looks like this:

$ ls / -l
total 68
...
lrwxrwxrwx+   1 root root    15 Dec 28 03:36 data -> /volume1/docker
...

For this bit here, I already have some custom_components which I want to keep separate, I assume I can just reference the whatsapp component folder inside the custom_component folder instead?

volumes:

  • /data/homeassistant/custom_components:/config/custom_components

In this case, you do NOT want to keep it separate. You WANT the WhatsApp container to be able to access this folder, as this is what would happen when running it as an add-on. It will create it own whatsapp folder within the HA custom_component folder, which itself will contain files (such as the whatapp.py file) that HA will need to access and run. For example:

image (this image shows the folder structure on the host that will be used as a persistent volume by the HA container and has the cusotm_component/whatsapp folder added when the whatsapp-ha container runs).

I currently access HA over https and have an SSL certificate. Is this where the hostname environment variable you mentioned comes into play or would this not work over https?

environment:
- HOSTNAME_ID=<IP_Address_of_HA_container>

So what I'm doing here is trying to tell the WhatsApp container where to find the HA container, and indeed, vice versa. The modified index.js file in the whatsapp-ha container uses this information in place of the supervisor/core that would be used if it was run as an add-on. I think the modifications I made to this file should allow it to continue to work for the add-on build AND work for the standalone image build. There is a logical if statement that looks to see if this environment variable exists. In addition, the whatsapp.py (which needs to be copied to the HA custom_component folder as outlined above) will be run by HA, and a similar logical if statement will allow HA to find the whatsapp-ha container for both the add-in and standalone builds.

In your case, as long as the whatsapp-ha container can resolve the hostname of the HA container, I don't see why it wouldn't work (I haven't tested it, though - thanks for volunteering ;) ).

swinster commented 1 year ago

okey-dokey, looks like we have something resembling an actual resolution for this issue :)

@Chief-T1 , I have created a cross-architectural image that allows this add-on to run a standalone container, which finally resembles a resolution to this issue. There are still some things to think about, but it's close. I have had to post the images to individual Docker hub repositories as I can't figure out how to post the same image:tag to the same repo for different architectures. This means there are currently the following repos:

swinster/whatsapp-ha-armv7
swinster/whatsapp-ha-i386
swinster/whatsapp-ha-aarch64
swinster/whatsapp-ha-armhf
swinster/whatsapp-ha-amd64

To make use of these, you need to pull the image using the following docker-compose for this service:

  whatsapp-ha:
    image: swinster/whatsapp-ha-amd64
    container_name: whatsapp-ha
    restart: "no"
    depends_on:
      - homeassistant
    volumes:
      - /data/homeassistant/custom_components:/config/custom_components
      - /data/whatsapp-ha/data:/data
    ports:
      - 3000:3000
    environment:
      #- HA_PORT=8123
      - HA_HOSTNAME=<your_hostname_or_ip_of_the_HA_container>
      - TOKEN=<long_lived_API_token>

NOTE 1: Select the correct image for your architecture by updating the image parameter.

NOTE: 2 Ensure the /data/whatsapp-ha/data folder exists on the host, which will be used as a persistent volume for the whatsapp-ha container. The path is arbitrary - I use /data, but you can specify whatever path works for you. The image now contains an options.json file that will be compiled to the containers /data folder IF it is running only as a stand-alone container (this was achieved through a slight modification to the run.sh bash script.

NOTE 3: The /data/homeassistant/custom_component persistent volume should point to the same path used by the HA config/custom_component folder on the host.

NOTE 4: I have also changed the environment variable names (e.g. HA_HOSTNAME) to make them more obvious. The HA_PORT environment variable is now optional and will default to using port 8123 is not defined, AND this will be used in stand-alone mode.


In addition, you need to update the Home Assistant docker-compose service (for example):

  homeassistant:
    container_name: homeassistant
    image: "ghcr.io/home-assistant/home-assistant:stable"
    volumes:
      - /data/homeassistant:/config
      - /etc/localtime:/etc/localtime:ro
    restart: unless-stopped
    privileged: true
    network_mode: host
    environment:
      - WHATSAPP_HOSTNAME=<your_hostname_or_ip_of_the_whatsapp-ha_container>
      #- WHATSAPP_PORT=3000

NOTE: This is an example of my HA docker-compose, so you only need to update the environment options. The WHATSAPP_HOSTNAME point Home Assitant back to the whatsapp-ha container (for me, as both HA and whatsapp-ha are running in a single stack on the same host, I use the same IP address in both places (I have not tested using TLS services and host names yet). The WHATSAPP_PORT is optional but defaults to using port 3000


Once deployed, you still need to update the HA configuration.yaml file with:

whatsapp:

I might do a little video on all of this.

It would be super cool (@giuseppecastaldo) if the changes to the index.js, whatsapp.py, run.sh and options.json files could be added to this repo, meaning that in the future, this project could be built as a HA add-on or as a stand-alone container. I'm hopeful that the alterations should work for both cases.

swinster commented 1 year ago

@Chief-T1 - there was an update to this repo by @giuseppecastaldo in the last couple of days, and the version bumped to 1.3. I thought I would rebuild the standalone image, but unfortunately, in the first instance, it failed :(

I am still determining this issue, but it relates to the update to finish.sh. I will plug away again to see if we can get this version working.

 => [5/6] RUN chmod a+x /finish.sh                                        22.4s
 => ERROR [6/6] RUN cd /Baileys && npm i -f && cd .. && npm install -f   103.5s
------
#0 10.06 npm WARN using --force Recommended protections disabled.
#0 17.18 npm WARN skipping integrity check for git dependency ssh://git@github.com/adiwajshing/eslint-config.git 
#0 69.79 npm WARN skipping integrity check for git dependency ssh://git@github.com/adiwajshing/eslint-config.git 
#0 79.73 npm WARN deprecated querystring@0.2.0: The querystring API is considered Legacy. new code should use the URLSearchParams API instead.
#0 80.56 npm WARN deprecated w3c-hr-time@1.0.2: Use your platform's native performance.now() and performance.timeOrigin.
#0 101.5 npm ERR! code 1
#0 101.6 npm ERR! path /Baileys/node_modules/sharp
#0 101.6 npm ERR! command failed
#0 101.6 npm ERR! command sh -c (node install/libvips && node install/dll-copy && prebuild-install) || (node install/can-compile && node-gyp rebuild && node install/dll-copy)
#0 101.6 npm ERR! sharp: Please see https://sharp.pixelplumbing.com/install for required dependencies
#0 101.6 npm ERR! sharp: Installation error: Intel Architecture 32-bit systems require manual installation of libvips >= 8.12.2
#0 101.6 
#0 101.6 npm ERR! A complete log of this run can be found in:
#0 101.6 npm ERR!     /root/.npm/_logs/2023-01-21T18_46_26_442Z-debug-0.log
------
error: failed to solve: executor failed running [/bin/ash -o pipefail -c cd /Baileys && npm i -f && cd .. && npm install -f]: exit code: 1
swinster commented 1 year ago

Hmm - the folder /Baileys/node_modules/sharp doesn't exist in this repo, but neither does it exist in https://github.com/adiwajshing/Baileys, so I have no idea what's going on

I think @giuseppecastaldo was originally forking the entire Baileys repo (which seems to do all the WhatsApp stuff), then instead pointed to adiwajshing's repo within the whatsapp-ha, and now has returned to pulling in some of that repo.

Again, apologies if I do not understand this correctly.

swinster commented 1 year ago

A quick update. I thought this was my issue, as I had forked this repo to add the relevant changes to the index.js, run.sh, options.json and custom_component/whatsapp.py files, then built using my repo. However, the same thing happens if it try to build directly from this repo and with no additions. Interestingly, the arm64 build completes, but the ha-builder fails when building the other architectures (which was working last week)

The error printed above:

Installation error: Intel Architecture 32-bit systems require manual installation of libvips >= 8.12.2

seem to be similar to the issue https://github.com/giuseppecastaldo/ha-addons/issues/6, abliet that issue reference the arm7 architecture.

chinedu40 commented 1 year ago

Having an issue with the docker install. I've changed the port to 3001 as 3000 was already in use. upon sending a message i get the following error, any help would be appreciated:

Logger: homeassistant.components.websocket_api.http.connection Source: custom_components/whatsapp/whatsapp.py:20 Integration: Home Assistant WebSocket API (documentation, issues) First occurred: 01:24:15 (7 occurrences) Last logged: 14:00:33

[139975312049536] Error handling message: Unknown error (unknown_error) from 192.168.86.166 (Mozilla/5.0 (X11; CrOS x86_64 14541.0.0) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/109.0.0.0 Safari/537.36) [139974092042064] Error handling message: Unknown error (unknown_error) from 192.168.86.185 (Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/605.1.15 (KHTML, like Gecko) Version/16.3 Safari/605.1.15) [139974112843168] Error handling message: Unknown error (unknown_error) from 192.168.86.185 (Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/605.1.15 (KHTML, like Gecko) Version/16.3 Safari/605.1.15) [139974332081264] Error handling message: Unknown error (unknown_error) from 192.168.86.185 (Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/605.1.15 (KHTML, like Gecko) Version/16.3 Safari/605.1.15) Traceback (most recent call last): File "/usr/local/lib/python3.10/site-packages/urllib3/connection.py", line 174, in _new_conn conn = connection.create_connection( File "/usr/local/lib/python3.10/site-packages/urllib3/util/connection.py", line 95, in create_connection raise err File "/usr/local/lib/python3.10/site-packages/urllib3/util/connection.py", line 85, in create_connection sock.connect(sa) ConnectionRefusedError: [Errno 111] Connection refused

During handling of the above exception, another exception occurred:

Traceback (most recent call last): File "/usr/local/lib/python3.10/site-packages/urllib3/connectionpool.py", line 703, in urlopen httplib_response = self._make_request( File "/usr/local/lib/python3.10/site-packages/urllib3/connectionpool.py", line 398, in _make_request conn.request(method, url, **httplib_request_kw) File "/usr/local/lib/python3.10/site-packages/urllib3/connection.py", line 239, in request super(HTTPConnection, self).request(method, url, body=body, headers=headers) File "/usr/local/lib/python3.10/http/client.py", line 1282, in request self._send_request(method, url, body, headers, encode_chunked) File "/usr/local/lib/python3.10/http/client.py", line 1328, in _send_request self.endheaders(body, encode_chunked=encode_chunked) File "/usr/local/lib/python3.10/http/client.py", line 1277, in endheaders self._send_output(message_body, encode_chunked=encode_chunked) File "/usr/local/lib/python3.10/http/client.py", line 1037, in _send_output self.send(msg) File "/usr/local/lib/python3.10/http/client.py", line 975, in send self.connect() File "/usr/local/lib/python3.10/site-packages/urllib3/connection.py", line 205, in connect conn = self._new_conn() File "/usr/local/lib/python3.10/site-packages/urllib3/connection.py", line 186, in _new_conn raise NewConnectionError( urllib3.exceptions.NewConnectionError: <urllib3.connection.HTTPConnection object at 0x7f4e616a6290>: Failed to establish a new connection: [Errno 111] Connection refused

During handling of the above exception, another exception occurred:

Traceback (most recent call last): File "/usr/local/lib/python3.10/site-packages/requests/adapters.py", line 489, in send resp = conn.urlopen( File "/usr/local/lib/python3.10/site-packages/urllib3/connectionpool.py", line 787, in urlopen retries = retries.increment( File "/usr/local/lib/python3.10/site-packages/urllib3/util/retry.py", line 592, in increment raise MaxRetryError(_pool, url, error or ResponseError(cause)) urllib3.exceptions.MaxRetryError: HTTPConnectionPool(host='192.168.86.11', port=3001): Max retries exceeded with url: /sendMessage (Caused by NewConnectionError('<urllib3.connection.HTTPConnection object at 0x7f4e616a6290>: Failed to establish a new connection: [Errno 111] Connection refused'))

During handling of the above exception, another exception occurred:

Traceback (most recent call last): File "/usr/src/homeassistant/homeassistant/components/websocket_api/decorators.py", line 27, in _handle_async_response await func(hass, connection, msg) File "/usr/src/homeassistant/homeassistant/components/websocket_api/commands.py", line 646, in handle_execute_script await script_obj.async_run(msg.get("variables"), context=context) File "/usr/src/homeassistant/homeassistant/helpers/script.py", line 1524, in async_run await asyncio.shield(run.async_run()) File "/usr/src/homeassistant/homeassistant/helpers/script.py", line 409, in async_run await self._async_step(log_exceptions=False) File "/usr/src/homeassistant/homeassistant/helpers/script.py", line 453, in _async_step self._handle_exception( File "/usr/src/homeassistant/homeassistant/helpers/script.py", line 476, in _handle_exception raise exception File "/usr/src/homeassistant/homeassistant/helpers/script.py", line 451, in _async_step await getattr(self, handler)() File "/usr/src/homeassistant/homeassistant/helpers/script.py", line 684, in _async_call_service_step await service_task File "/usr/src/homeassistant/homeassistant/core.py", line 1755, in async_call task.result() File "/usr/src/homeassistant/homeassistant/core.py", line 1792, in _execute_service await cast(Callable[[ServiceCall], Awaitable[None]], handler.job.target)( File "/config/custom_components/whatsapp/init.py", line 18, in send_message await hass.async_add_executor_job(whatsapp.send_message, call.data) File "/usr/local/lib/python3.10/concurrent/futures/thread.py", line 58, in run result = self.fn(*self.args, self.kwargs) File "/config/custom_components/whatsapp/whatsapp.py", line 20, in send_message return requests.post(url_normalize(f'{HOST}/sendMessage'), json=data).content == 'OK' File "/usr/local/lib/python3.10/site-packages/requests/api.py", line 115, in post return request("post", url, data=data, json=json, kwargs) File "/usr/local/lib/python3.10/site-packages/requests/api.py", line 59, in request return session.request(method=method, url=url, kwargs) File "/usr/local/lib/python3.10/site-packages/requests/sessions.py", line 587, in request resp = self.send(prep, send_kwargs) File "/usr/local/lib/python3.10/site-packages/requests/sessions.py", line 701, in send r = adapter.send(request, **kwargs) File "/usr/local/lib/python3.10/site-packages/requests/adapters.py", line 565, in send raise ConnectionError(e, request=request) requests.exceptions.ConnectionError: HTTPConnectionPool(host='192.168.86.11', port=3001): Max retries exceeded with url: /sendMessage (Caused by NewConnectionError('<urllib3.connection.HTTPConnection object at 0x7f4e616a6290>: Failed to establish a new connection: [Errno 111] Connection refused'))

piit79 commented 1 year ago

@chinedu40 Did you verify that node is listening on port 3001 inside the WhatsApp container? The [Errno 111] Connection refused error would suggest that it doesn't.

chinedu40 commented 1 year ago

@chinedu40 Did you verify that node is listening on port 3001 inside the WhatsApp container? The [Errno 111] Connection refused error would suggest that it doesn't.

Thanks a lot for this nudge. It made me realise that if you are changing the ports, only the docker host port needs to change and not the container port. This meant i just needed to change the port mapping to 3001:3000 instead of 3001:3001. It appears for the plugin that port 3000 is a constant container port that the node is listening on.

swinster commented 1 year ago

@chinedu40 , I guess anything is doable. I have some other issue at the moment and haven't had time to figure out the update of this docker image. Hopefully, I can get back to it soon.

Chief-T1 commented 1 year ago

@swinster

I finally got around to testing this on my Raspberry Pi. It took me ages as I previously was using a selenium script to automate this with Node Red and while my hacky method wasn't perfect it worked.

First of all, this now works 10 times better and messages send instantly, I've had no issues with it randomly stopping working how I did with my old method.

I had some issues using your image on the Raspberry Pi related to what you mentioned above with the ha-builder not working. So I had to manually change the build argument in the Dockerfile to FROM ghcr.io/home-assistant/aarch64-base

I access home assistant using HTTPS and unfortunately, this failed to work as it's hardcoded to use HTTP. I have raised a pull request on your forked repo to take this into account.

I manually changed this on my build and it works seamlessly now. Just out of interest have you used any of the subscribe to WhatsApp status methods? I was reading about them but was unsure how one would unsubscribe.

Thanks

chinedu40 commented 1 year ago

Seems like this plugin has stopped working as I can no longer login using a QR Code. I don’t have the expertise to update @swinster image, but a possible fix it to update the version on src/Defaults/baileys-version.json to "version": [2, 2323, 4].

@swinster would this be possible?