Logging to Slack
The Domoticz log is very helpful in realtime debugging, but is fairly limited to what it contains, and -at the time of writing- does not allow for more that filter between All, Status and Errors.
As an alternative, this article offers the option to use Slack as an additional logging mechanism. This will allow for:
- Custom logging, to dedicated channels (one channels for a specific category of devices, or a single device)
- User rights management for logging information (allow access to specific channels for specific users)
- Uploading files and images (e.g. uploading your security cam snapshots)
As a bonus, Slack offers a very user-friendly mobile app.
Creating a Slack account and a bot integration
Register at https://slack.com/ by creating a new team with your credentials. The result is a Slack environment with yourself as a user.
1) To proceed, first make a bot integration inside of your Slack channel. Go to the following URL: https://my.slack.com/services/new/bot
2) Enter a name for your bot. I've named mine simply 'bot' :)
3) When you click "Add Bot Integration", you are taken to a page where you can add additional details about your bot, like an avatar, as well as customize its name & description.
4) Copy the API token that Slack gives you, we are going to use this in the script to authenticate. It wil look something like xoxb-randomnumbers-randomcharacters
You can post to existing channels within Slack without problems, but if a channel is not yet available, you need to use another token than the one for your bot. For some reason Slack will not allow you to create a channel if you identify as a bot. As an alternative, I use the Slack API tester token to create channels.
5) Goto https://api.slack.com/methods/chat.postMessage/test to test your API call and to authenticate the Slack API Tester. As a result, you should be able to use (copy) this specific token, so you can use it to create channels if necessary.
That's all we need for awesomeness :) You can create your scripts using this information
Posting your first message on Slack
I have created a bash script that I can call from within Domoticz. Below is a very simple example. If you call this script with scriptname.sh Garden, it will post a message to the #garden channel with the time it was triggered.
#!/bin/bash # The first argument in this script will define the origin of the sensor. I have several sensors for triggering movement or doors/windows. So I call this with the name of the sensor. It will come up as channel in Slack. if [ -z "$1" ] then loc="unknown" else loc=$1 fi # Saving the time for logging timestamp=$( date +%T ) # Since Slack is only accepting lowercase, we're converting this input to lowercase VAR=$(echo "$loc" | tr '[:upper:]' '[:lower:]') # The proper way would be to check if this is necessary, but I am creating a channel every time. # Slack will deny this if it is already available. I use the Slack API tester for this - change with your own Slack API tester token curl -s -i -H "Accept: application/json" "https://slack.com/api/channels.create?token=xoxp-slack-API-tester&name=$VAR&pretty=1" # Next, post a message to the channel. I prefixed it with "Trigger: " # This message is posting to the lowercase version of the first argument to the script curl -s -i -H "Accept: application/json" "https://slack.com/api/chat.postMessage?token=xoxb-yourtoken5678-567890here1234&channel=$VAR&text=Trigger%2C%20$timestamp"
Uploading images to Slack
One awesome feature is to upload snapshots to Slack. Effectively, you can post security cam images, which is what i did in the example below: In this specific example, I have added a camera to the Domoticz setup. After this, It is available by ID (first camera you add has ID 1 ...etc)) This ID is the argument for the post_snapshot.sh script. I have created a specific channel for the images, which is called 'security-cams'. The script gets a snapshot from a specific camera (identified by the script argument) when there's a nearby IR sensor triggered and posts the resulting JPEG to the security-cams channel.
#!/bin/bash if [ -z "$1" ] then loc="1" else loc=$1 fi wget -O cam.jpg http://127.0.0.1:8080/camsnapshot.jpg?idx=$loc curl -F [email protected] -F channels=#security-cams -F token=xoxb-your-t0ken-h3r3 https://slack.com/api/files.upload rm cam.jpg
If all is well you will be able to see your Domoticz events coming into Slack.
Domoticz Logging
For this to work properly you have to:
- install 'dategrep' to grep recent items from your Domoticz logging. link dategrep
- need to have logging enabled in your Domoticz startup script (see the Wiki)
- need to have a channel defined already, since I stripped the previous script to only include the curl request
#!/bin/bash #Grep log lines from last 15 minutes # --skip-unparsable # strip alle regels die geen timestamp hebben # --format "%Y-%m-%d %H:%M:%S" # formaat van de domoticz log-file # /var/tmp/log/domoticz.txt is mijn logging die op een tmpfs gemount is. IFS=$'\n' # make newlines the only separator for line in `dategrep --skip-unparsable --last-minutes 15 --format "%Y-%m-%d %H:%M:%S" /var/tmp/log/domoticz.txt` do # split the curl request in two parts with -G and -d because we might need to URL encode our data. curl -s -i -H "Accept: application/json" https://slack.com/api/chat.postMessage -G -d "token=xoxb-xxxxx-xxxxxxxx&channel=domoticz-logging" --data-urlencode "text=${line}" done exit 0
It's even possible to only extract the errors or debug lines with this selection:
for line in `dategrep --skip-unparsable --last-minutes 15 --format "%Y-%m-%d %H:%M:%S" /var/tmp/log/domoticz.txt | grep -i -e error -e debug`
I've added the | grep -i -e error -e debug as an selection.
- I've added the script to my cronjob to have it execute every 15 minutes (therefore I required dategrep).
Tips & Tricks
- When you login into Domoticz using SSH, use "sh scriptname.sh argument" to test the scripts. The output will give you valuable information on how Slack is handling your requests.
- Once you have the basics covered in the Bash scripts, you can continue to refine your events with Lua. The os.execute() function is your friend.
commandArray = {} -- I've created a Dummy button, that allows for easy testing. The variable 'Afwezig' will only be '1' after 15 minutes of inactivity. if (otherdevices['TestMode'] == "On") or (uservariables['Afwezig'] == 1) then -- loop through all the changed devices for deviceName,deviceValue in pairs(devicechanged) do -- repeating the same logic for different areas of the house: -- the garden, with the camera at id#2 if (deviceName=='BewegingTuin') then if (deviceValue == "On") then os.execute("/home/pi/domoticz/scripts/post_snapshot.sh 2") end end -- the kitchen, with the cemara at id#1 if (deviceName=='DeurKeuken') then if (deviceValue == "Open") then os.execute("/home/pi/domoticz/scripts/post_snapshot.sh 1") end end -- the Hallway, with the camera at id#3 if (deviceName=='BewegingGang') then if (deviceValue == "On") then os.execute("/home/pi/domoticz/scripts/post_snapshot.sh 3") end end end end return commandArray