Matrix Chat support for photos, file attachments, and encryption

The Matrix chat/notification platform was added in 0.69 and is now newly available as a HassIO Addon which greatly simplifies deploying it:

It is basically a locally hosted, federated version of Slack and I am really loving it and it’s client apps, end to end encryption and VoIP are also out of the box features.

The only downside is it currently only does basic text notifications with the HA component.

I would love photo/file attachment support, and being able to use the e2e encryption would be ideal.

Are there any other Matrix users? I did find this Node-Red integration but it also only supports text notifications and the repo is a few years stale.

I was able to use node red to send a photo message from scratch to my matrix home server. I used the home assistant camera api to get a binary buffer of the snapshot. Then I send an http request to my matrix server to login and get an access token. Next I upload the image to the matrix server and finally I post a message to a room using the image I just uploaded. What I would like to try next is see if I can use node red to encrypt the image sent to the matrix server. Here is the flow I ended up with that should help you to use as a guide to accomplish the same thing or something similar:

[{"id":"e50e094a.a9d4e8","type":"http request","z":"aa153788.b82028","name":"get image","method":"use","ret":"bin","url":"","tls":"","x":440,"y":640,"wires":[["5ddfa53d.dfc7bc"]]},{"id":"766b8dda.6e7794","type":"function","z":"aa153788.b82028","name":"get image","func":"delete msg.headers;\nmsg.method = 'GET';\nmsg.headers = {Authorization:\"Bearer HATOKEN\",\"Content-Type\":\"application/json\" };\nmsg.url = \"\"\nreturn msg;","outputs":1,"noerr":0,"x":280,"y":640,"wires":[["e50e094a.a9d4e8"]]},{"id":"5ddfa53d.dfc7bc","type":"change","z":"aa153788.b82028","name":"photo & time","rules":[{"t":"move","p":"payload","pt":"msg","to":"photo","tot":"msg"},{"t":"set","p":"time","pt":"msg","to":"$now()","tot":"jsonata"}],"action":"","property":"","from":"","to":"","reg":false,"x":130,"y":740,"wires":[["c2e68636.4dcb48"]]},{"id":"c07e3d7.c0695c","type":"function","z":"aa153788.b82028","name":"post image","func":"delete msg.headers;\nmsg.token = msg.payload.access_token;\nmsg.payload =;\nmsg.method = 'POST';\nmsg.headers = {Authorization:\"Bearer \" + msg.token,\"Content-Type\":\"application/json\"}\nmsg.url = \"\" + msg.time + \"-mycamimage.jpg\";\nreturn msg;","outputs":1,"noerr":0,"x":710,"y":780,"wires":[["a914b253.ca53f"]]},{"id":"a914b253.ca53f","type":"http request","z":"aa153788.b82028","name":"post image","method":"use","ret":"obj","url":"","tls":"","x":890,"y":780,"wires":[["2791a9c3.a11506"]]},{"id":"2791a9c3.a11506","type":"function","z":"aa153788.b82028","name":"put image","func":"delete msg.headers;\ndelete;\ndelete msg.thumb;\nmsg.photo_uri = msg.payload.content_uri;\n\ndelete msg.topic;\nmsg.method = 'PUT';\nmsg.headers = {Authorization:\"Bearer \" + msg.token,\"Content-Type\":\"application/json\"};\nmsg.url = \"\" + msg.random;\nmsg.payload = {body:\"Camera Snapshot\",msgtype:\"m.image\",url:msg.photo_uri,info:{h:1080,w:1920,mimetype:\"image/jpeg\"}};\ndelete msg.photo_uri;\ndelete msg.random;\nreturn msg;","outputs":1,"noerr":0,"x":180,"y":860,"wires":[["4ccb334d.691cdc"]]},{"id":"4ccb334d.691cdc","type":"http request","z":"aa153788.b82028","name":"http","method":"use","ret":"obj","url":"","tls":"","x":390,"y":860,"wires":[[]]},{"id":"8ac07cbe.e955","type":"random","z":"aa153788.b82028","name":"","low":"1","high":"1000000000","inte":"true","property":"random","x":120,"y":640,"wires":[["766b8dda.6e7794"]]},{"id":"c2e68636.4dcb48","type":"function","z":"aa153788.b82028","name":"post login","func":"delete msg.headers;\nmsg.payload = {\"type\":\"m.login.password\", \"user\":\"\", \"password\":\"mybotpassword\", \"device_id\":\"BOEBPWVQRE\", \"initial_device_display_name\":\"node_red\"};\nmsg.method = 'POST';\nmsg.url = \"\";\nreturn msg;","outputs":1,"noerr":0,"x":300,"y":740,"wires":[["f07ba4b5.e2a768"]]},{"id":"f07ba4b5.e2a768","type":"http request","z":"aa153788.b82028","name":"post login","method":"use","ret":"obj","url":"","tls":"","x":500,"y":760,"wires":[["c07e3d7.c0695c"]]}]

EDIT: Make up your own device_id. That way each time node red logs in and retrieves an access_token it will replace the access_token of the device id you put. I have since added the credentials node to my flow before the login request so that the matrix username and password aren’t stored in plain text

1 Like

That seems like a great work around, I will give it a try! Thank you

Hi, I am interested in this addon, and trying to install it.

Is it possible to create user on the same self hosted server?

I ma trying to add a user but it says

**Cannot reach homeserver**

Ensure you have a stable internet connection, or get in touch with the server admin

means I am obliged to open an user account in

It seems to me that when I login with a user created in, also the Rooms and all are not from the hosted server???

I am missing smething, my installation is the following
Router dorwards port 80 to 80 nd 443 to 443 to a Caddy nginx proxy (is on my main HASSIO
Caddy HASSIO addon forwards various addresses inside my lan
https// to (main HASSIO) to (HASSIO with MAtrix)

in The RIOTIM app in the URL server name what do I have to put?

When I am in my LAN and put it connects and it works
When I am outside my LAN and put it does not connect


Are you sure, you are running Matrix on port 443? The add-on by default will give you access to local Matrix instance on port 8448.
So, you would use for login something like or locally.
For this your add-on setting should look like:

  "ssl": true,
  "certfile": "fullchain.pem",
  "keyfile": "privkey.pem",
  "server_name": ""

You will need to forward port 8448 to your Matrix instance and make sure, you have trusted certificate.

It is possible to create a local user. I believe, it’s even a default way to start with add-on.

I do use NGINX proxy manager HAssio addon, (to access 2 different HASSIO in WAN), in my case I have all the other addon to false … will Matrix work?, which would be the Nginx proxy manager configuration for MAtrix server?

Hi, will this work also as self hosted VoIP chat server?

Now an error … but I have no matrix.yaml file under /config …

[15:27:44] FATAL: The server_name has changed!
[15:27:44] FATAL: Are you sure you want to do this?
[15:27:44] FATAL: If so, delete the “matrix.yaml” file located in “/config” and restart the addon.

If you get it working in your setup, it should work as a self hosted VoIP server.
This I found in add-on documentation:

Option: server_name

This is the hostname of your server. Set this to the host that you will be connecting to with your clients without the port and without the http:// or https:// . For example: if your domain name is set your server_name to this.
Note : You should only set this once. You will likely have to reinstall the addon to change this after the fact, losing all your rooms and users.

I would try to reinstall the add-on and fqdn without http:// and port as a server_name.

thnks I had it without

Hi @sea3pea0, thanks a lot for the flow - really helped fill a missing gap in my home alarm system.

I only have one issue with the result at the moment, which is that the matrix server doesn’t seem to produce thumnails for the images uploaded. When I get the message on my phone it appears blank in the chat and i get a pop-up notification to tell me the media doesn’t exist at the thumbnail url. When I click on the blank image I do then correctly get shown the full-size image as expected. Is this a behaviour anyone else has seen - not sure if it is the API interaction or the configuration of my particular server but I haven’t seen this issue with normal images posted from a phone or PC using the riot clients before.

Cheers for any help!

I just implemented this and am seeing the same behavior. Would be nice if the integration could handle, though looks like they’d need to change libraries to this one

ETA: I tried messing around with pulling the thumbnail using the api and I got it but it doesn’t show on desktop. Oddly on my phone the thumbnail shows up just fine, it’s just desktop.

Edit 2: Looks like there’s a PR to add this!

Thanks for pointing the PR out! I tested it out an it seems to works fine. A thumbnail would be nice, but it is ok. My reason for using Matrix is platform independent notifications. I have a Pixel, my wife has an iPhone, but we use a self hosted synapse/matrix server. Make notifications a lot easier to manage!!

I have a couple questions…to implement this change, which is not yet implemented, I search in my “/var/lib/docker/overlay2” for “”, which will return lots of very_long_string/merged/usr/src/homeassistant/homeassistant/components/ directories, one of which is “Matrix”. I backup the original files, paste the new files, restart HA and done.

Not very convenient, and I am afraid those files will be back to original after an update. Is there a better way of doing this?

Yes. Create a custom_component folder inside your config folder. Copy ALL the files from here to a folder located inside custom_components named “matrix”. Reboot HASS.

Cool thanks! I had done exactly that except I had renamed matrix to matrix_custom, thinking the custom component would conflict the original one. I was getting bunch of errors…

I guess the custom component takes over!

You should see something in the logs on a reboot how a custom_component is loaded and the HASS developers don’t review/promise anything (can’t remember the exact language). That’s how you know you successfully loaded the custom component.