hi there,
is there anybody who uses matrix/synapse (element) to send messages from openhab?
i think its very similar to xmpp.
maybe someone has already had experience with it and can share it
thanks
hi there,
is there anybody who uses matrix/synapse (element) to send messages from openhab?
i think its very similar to xmpp.
maybe someone has already had experience with it and can share it
thanks
Note There’s a much easier way of doing this using Even easier, just use the HTTP binding, and JINJA transformation - see post 4.sendHttpPostRequest
- see the next post!
I’m self-hosting Matrix using the Synapse package.
I am pushing messages from openHAB to Matrix via MQTT. The flow is roughly as follows, though is not for the faint-of-heart - it’s ugly!
openhab → MQTT broker → paho-mqtt → matrix-commander → Matrix/Synapse
Bridge mqtt:broker:MosquittoMqttBroker "Mosquitto MQTT Broker" [
host="mqtt.lan",
secure=false,
port=1883,
clientID="OpenHAB3",
username="",
password=""
]
// Main Bedroom Light
Thing mqtt:topic:log "Log" (mqtt:broker:MosquittoMqttBroker) {
Channels:
Type string : strInfo "Info" [
commandTopic="openhab/log/info"
]
}
String strLogInfo "Log Info" {channel="mqtt:topic:log:strInfo"}
openhab
using app.element.io
openhab/log/info
and relay any messages received to matrix-commander
#!/usr/bin/env python3
import paho.mqtt.client as mqtt
import os
# The callback for when the client receives a CONNACK response from the server.
def on_connect(client, userdata, flags, rc):
print("Connected with result code "+str(rc))
# Subscribing in on_connect() means that if we lose the connection and
# reconnect then subscriptions will be renewed.
client.subscribe("openhab/log/info")
# The callback for when a PUBLISH message is received from the server.
def on_message(client, userdata, msg):
message = msg.payload
message = message.decode("utf-8")
print(msg.topic+" "+message)
os.system("/path/to/matrix-commander/matrix-commander.py -c \"/path/to/matrix-commander/credentials.json\" -s \"/path/to/matrix-commander/store/\" -m \""+message+"\"")
client = mqtt.Client()
client.on_connect = on_connect
client.on_message = on_message
client.connect("192.168.1.151", 1883, 60)
# Blocking call that processes network traffic, dispatches callbacks and
# handles reconnecting.
# Other loop*() functions are available that give a threaded interface and a
# manual interface.
client.loop_forever()
I use Jython rules, so just send a command to the Item with the text that I want to be published to the Matrix room:
events.sendCommand("strLogInfo","DAY mode activated.")
In DSL rules this would be
strLogInfo.sendCommand("DAY mode activated")
matrix-commander
directly from openHAB, but for me:
Here’s a much easier way of sending messages to a Matrix room from a rule:
sendHttpPostRequest("https://YOURMATRIXDOMAIN/_matrix/client/r0/rooms/YOURROOMID/send/m.room.message?access_token=YOURACCESSTOKEN", "application/json", "{\"msgtype\":\"m.text\", \"body\":\"YOURMESSAGE\"}")
or a little more readable
val String URL = 'https://YOURMATRIXDOMAIN/_matrix/client/r0/rooms/YOURROOMID/send/m.room.message?access_token=YOURACCESSTOKEN'
var String DATA = '{
"msgtype": "m.text",
"body": "YOURMESSAGE"
}'
sendHttpPostRequest(URL, "application/json", DATA)
where:
YOURMATRIXDOMAIN
your (subdomain) URL, such as matrix.example.org
YOURROOMID
is the room ID in which you want the messages to appear. If you’re using Element as a client you can click on the room name, go to Advanced and you’ll find the Internal room ID which will look something like !hGbNiOPDjfsJfF:matrix.example.org
YOURACCESSTOKEN
is the access token for your user. To find out my user token for my Matrix user openhab
I executed the following command (substituting the password and URL) in a terminal on the same system that is running openHAB:curl -XPOST -d '{"type":"m.login.password", "user":"openhab", "password":"PASSWORD"}' "https://matrix.example.org/_matrix/client/r0/login"
This will spit out something like the following, from which you can grab your access token.
{
"user_id": "@openhab:matrix.example.org",
"access_token": "YOURACCESSTOKEN",
"home_server": "matrix.example.org",
"device_id": "HFNFBSUHSK",
"well_known": {
"m.homeserver": {
"base_url": "https://matrix.example.org/"
}
}
}
Notes
openhab
) on your Matrix/Synapse homeserver, and that you have created a room with the user and one other user (maybe yourself).from core.actions import HTTP
matrix_openhab_token = "MYUSERTOKEN"
matrix_homeserver_url = "MYMATRIXDOMAIN"
matrix_openhab_room = "MYROOMID"
matrix_message = "MYMESSAGE"
url = "https://{}/_matrix/client/r0/rooms/{}/send/m.room.message?access_token={}".format(matrix_homeserver_url, matrix_openhab_room,matrix_openhab_token)
HTTP.sendHttpPostRequest(str(url), 'application/json', '{"msgtype":"m.text", "body":matrix_message}')
Even easier - use the HTTP Binding and JINJA transformation - no rules required.
All the prerequisites/caveats of the previous post still hold true, but everything can be configured via the UI if you desire. Simply, a String Item is linked to a String Channel in the HTTP Thing, and that String Channel uses a JINJA transformation to put the message into JSON required by the Matrix server.
//Matrix server
Thing http:url:matrix "Matrix" [
baseURL = "https://YOURMATRIXDOMAIN/",
refresh = "300",
timeout ="3000",
ignoreSSLErrors = "true",
commandMethod = "POST"
]
{
Channels:
Type string: home "Home Room" [
mode = "WRITEONLY",
commandExtension = "_matrix/client/r0/rooms/YOURROOMID/send/m.room.message?access_token=YOURACCESSTOKEN",
commandTransformation = "JINJA:{\"msgtype\":\"m.text\", \"body\":\"{{value}}\"}"
]
}
UID: http:url:matrix
label: Matrix
thingTypeUID: http:url
configuration:
authMode: BASIC
ignoreSSLErrors: "true"
baseURL: https://YOURMATRIXDOMAIN/
delay: 0
stateMethod: GET
refresh: "300"
commandMethod: POST
timeout: "3000"
bufferSize: 2048
channels:
- id: home
channelTypeUID: http:string
label: Home Room
description: null
configuration:
mode: WRITEONLY
commandExtension: _matrix/client/r0/rooms/YOURROOMID/send/m.room.message?access_token=YOURACCESSTOKEN
commandTransformation: JINJA:{"msgtype":"m.text", "body":"{{value}}"}
String strMatrixMessageHomeRoom "Matrix message home room" {channel="http:url:matrix:home"}
When I enter something like
https://YOURMATRIXDOMAIN/_matrix/client/r0/rooms/YOURROOMID/send/m.room.message?access_token=YOURACCESSTOKEN
into my browser, it says
As YOURMATRIXDOMAIN, I entered “matrix.org”. Could it be that this is not working for matrix.org instance?
Oh, no idea! Did you enter known working values for the room ID and access token too?
Wouldn’t surprise me if matrix.org prevented robots.
All of my posts have assumed a self hosted Synapse server.