-
Notifications
You must be signed in to change notification settings - Fork 7
/
Copy pathmijia_mqtt.sh
executable file
·173 lines (147 loc) · 3.79 KB
/
mijia_mqtt.sh
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
#!/bin/bash
#
# Simple script to report temperature, humidity and battery level of
# Xiaomi Mijia Bluetooth Temperature and Humidity Sensor to MQTT.
# Requires gatttool, mosquitto_pub, bc and xxd tools to be installed.
#
# On Ubuntu 18.04 the required packages can be installed with:
# apt install xxd bc mosquitto-clients bluez
#
### Defaults
BROKER_IP="127.0.0.1"
MAXRETRY=6
MQTT_TOPIC_PREFIX="homeauto/xiaomi"
#######################################################################
# No need to change things below this line.
#######################################################################
SENSOR_ADDRESS=""
SENSOR_NAME=""
DEBUG=0
readonly USAGE="
$0 -a [address] -n [sensor name]
Mandatory arguments:
-a | --address Bluetooth MAC address of sensor.
-n | --name Name of the sensor to use for MQTT.
Optional arguments:
-b | --broker MQTT broker address. Default $BROKER_IP.
-r | --retries Number of max retry attempts. Default $MAXRETRY times.
-p | --prefix MQTT topic prefix. Default $MQTT_TOPIC_PREFIX.
-d | --debug Enable debug printouts.
-h | --help
"
debug_print() {
if [ $DEBUG -eq 1 ]; then
echo "$@"
fi
}
print_usage() {
echo "${USAGE}"
}
parse_command_line_parameters() {
while [[ $# -gt 0 ]]
do
key="$1"
case $key in
-a|--address)
SENSOR_ADDRESS="$2"
shift; shift
;;
-n|--name)
SENSOR_NAME="$2"
shift; shift
;;
-b|--broker)
BROKER_IP="$2"
shift; shift
;;
-r|--retries)
MAXRETRY="$2"
shift; shift
;;
-p|--prefix)
MQTT_TOPIC_PREFIX="$2"
shift; shift
;;
-d|--debug)
DEBUG=1
shift; shift
;;
-h|--help)
print_usage
exit 0
;;
*)
# Unknown parameter
print_usage
exit 1
;;
esac
done
if [ -z $SENSOR_NAME ]; then
echo "Sensor name is mandatory parameter."
print_usage
exit 2
fi
if [ -z $SENSOR_ADDRESS ]; then
echo "Sensor address is mandatory parameter."
print_usage
exit 2
fi
}
main() {
local retry=0
while true
do
debug_print "Querying $SENSOR_ADDRESS for temperature and humidity data."
data=$(timeout 20 gatttool -b $SENSOR_ADDRESS --char-write-req --handle=0x10 -n 0100 --listen | grep "Notification handle" -m 2)
rc=$?
if [ ${rc} -eq 0 ]; then
break
fi
if [ $retry -eq $MAXRETRY ]; then
debug_print "$MAXRETRY attemps made, aborting."
break
fi
retry=$((retry+1))
debug_print "Connection failed, retrying $retry/$MAXRETRY... "
sleep 5
done
retry=0
while true
do
debug_print "Querying $SENSOR_ADDRESS for battery data."
battery=$(timeout 20 gatttool -b $SENSOR_ADDRESS --char-read --handle=0x18)
rc=$?
if [ ${rc} -eq 0 ]; then
break
fi
if [ $retry -eq $MAXRETRY ]; then
debug_print "$MAXRETRY attemps made, aborting."
break
fi
retry=$((retry+1))
debug_print "Connection failed, retrying $retry/$MAXRETRY... "
sleep 5
done
battery=$(echo $battery | cut -f 2 -d":" | tr '[:lower:]' '[:upper:]')
temp=$(echo $data | tail -1 | grep -oP 'value: \K.*' | xxd -r -p | cut -f 1 -d" " | cut -f 2 -d"=")
humid=$(echo $data | tail -1 | grep -oP 'value: \K.*' | xxd -r -p | cut -f 2 -d" " | cut -f 2 -d"=" | tr -d '\0')
batt=$(echo "ibase=16; $battery" | bc)
debug_print "Temperature: $temp, Humidity: $humid, Battery: $batt"
MQTT_TOPIC="$MQTT_TOPIC_PREFIX/$SENSOR_NAME"
# Do validity check and publish
if [[ "$temp" =~ ^-?[0-9]+(\.[0-9]+)?$ ]]
then
mosquitto_pub -h $BROKER_IP -V mqttv311 -t "$MQTT_TOPIC/temperature" -m "$temp"
fi
if [[ "$humid" =~ ^[0-9]+(\.[0-9]+)?$ ]]
then
mosquitto_pub -h $BROKER_IP -V mqttv311 -t "$MQTT_TOPIC/humidity" -m "$humid"
fi
if [[ "$batt" =~ ^[0-9]+(\.[0-9]+)?$ ]]
then
mosquitto_pub -h $BROKER_IP -V mqttv311 -t "$MQTT_TOPIC/battery" -m "$batt"
fi
}
parse_command_line_parameters $@
main