NOTE to anyone coming here from Hackaday link - MQTT sensor definitions have changed considerably since this was posted. I will update later…
I have got into home automation in a big way since I found Home Assistant, but my wife is less fond of the whole talk to Google or use your phone thing just to turn on a light bulb.
Sure - she likes the automations, like the fact that our garden lights turn on every night at the end of dusk, and that we can turn on the low voltage lighting in our outdoor entertaining area without going into the garage to flick a switch, but “Hey Google” really gets her goat up.
I have a couple of nice LCD touch screens in the house with a fancy and user friendly interface, but no, still no love.
So I decided, if you can’t beat 'em, join 'em.
A bit of background, our house was bult in 1890 and electric lighting (and power points for that matter) are a bit of an afterthought, so remote controlled lights is a perfect solution. Light switches are behind doors, or at one end of a 15 metre dark corridor.
I have thus sought (and found) a solution to place normal light switches switches at any location in the house, and use them to turn on and control various smart bulbs.
First lets cover the hardware. The solution is based around the relatively cheap GS-WDS07 433Mhz door sensor and the Sonoff 433Mhz to Wifi bridge flashed with Tasmota,
The sensors are available for between $6 and $7.50 AU from Banggood or Aliexpress and the bridge direct from the Sonoff site for about $20 AU
The sensor circuit boards are mounted inside a standard Australian wallplate with a 13mm extension - avaiable from Bunnings
The sensor circuit board can be removed from the case by removing one screw. Pop it out and remove the battery.
Unsolder the reed switch - shown highlighted below.
The GS-WDS07 is superior in some ways to the Sonoff reed switches or some other brands, in that it sends a packet both on open AND closed door events. Other sensors may send a packet only on open and it is this difference that makes this reed switch suitable for other uses. The GS-WDS07 also has a tamper switch (usually unpopulated) and a low battery alarm.
The solder points for the reed switch and tamper switch are highlighted below.
For extended battery life and to secure the battery once removed from the case an external AA battery holder is connected to the existing battery terminals. These are fairly cheap from Aliexpress or even your local parts store.
Solder some hookup wire to the switch contacts and mount the battery holder and board inside the assembled light switch and mounting block. I use hot glue to hold them in place. Face the LED on the board to the front of the enclosure, you can see it flash through the plastic of the switch when the sensor sends a packet.
Finally hook up the rocker switch to the reed switch wires. It’s easiest if you do this last.
Pop in a battery, the blue LED should flash. If you go to the console screen of your Sonoff bridge you can identify the ID of the sensor by flicking the switch on and off and observing the packets received. They will look something like:
21:06:06 MQT: tele/bridge/RESULT = {"RfReceived":{"Sync":13980,"Low":450,"High":1350,"Data":"189A0E","RfKey":"None"}}
21:06:08 MQT: tele/bridge/RESULT = {"RfReceived":{"Sync":13970,"Low":460,"High":1350,"Data":"189A0A","RfKey":"None"}}
The six hex digits after “Data” are the values for the sensor. The first 4 uniquely identify the sensor and the last 2 the function invoked: 0E = ON (or CLOSED), 0A = OFF (or OPEN), 06 = LOW BATT and 07 = TAMPER. More about the last two functions later.
The switch is defined as a binary sensor, just as it would be if you were using it as a door or window sensor, noting that the ON and OFF are reversed from the way a door sensor would be set up.
binary_sensor:
- platform: mqtt
name: "Hall Lights Switch"
state_topic: "tele/bridge/RESULT"
value_template: '{{value_json.RfReceived.Data}}'
payload_on: "189A0E"
payload_off: "189A0A"
retain: true
Once we have this working, set up automations for on and off in automations.yaml:
- alias: 'Hall Light Switch ON'
trigger:
platform: state
entity_id: binary_sensor.hall_lights_switch
to: 'on'
action:
service: light.turn_on
entity_id: group.hallway
- alias: 'Hall Light Switch OFF'
trigger:
platform: state
entity_id: binary_sensor.hall_lights_switch
to: 'off'
action:
service: light.turn_off
entity_id: group.hallway
Note that in this example I am turning on a group, not just a single light.
Now we need to set up a binary sensor for the low battery alarm:
- platform: mqtt
name: "Hall Lights Switch Battery"
state_topic: "tele/bridge/RESULT"
value_template: '{{value_json.RfReceived.Data}}'
payload_on: "189A06"
payload_off: "999999"
device_class: battery
And an automation to react to it, setting a persistent notification:
- alias: 'Battery Low'
trigger:
- entity_id: binary_sensor.back_door_reed_battery,
binary_sensor.east_front_window_reed_battery,
binary_sensor.front_door_reed_battery,
binary_sensor.lounge_door_reed_battery,
binary_sensor.office_window_reed_battery,
binary_sensor.sunroom_east_door_reed_battery,
binary_sensor.west_front_window_reed_battery,
binary_sensor.lounge_lights_switch_battery,
binary_sensor.hall_lights_switch_battery,
binary_sensor.office_lights_switch_battery
platform: state
to: 'on'
action:
service: persistent_notification.create
data_template:
message: "Sensor {{ trigger.entity_id }} low battery"
title: "Low Battery Alert"
On my to-do list is an automation to reset the low battery status on acknowledgment but currently this has to be done manually.
The light switch when installed looks like any other switch in the house:
Bonus stuff!
Lastly I have a solution that makes use of the tamper switch on the GS-WDS07. This switch will only send a packet on circuit closed, so cannot perform an on/off function, but can still be used to perform functions when connected to a momentary contact push button.
The push button contacts are connected to the tamper switch solder pads, pressing the button sends a packet ending in 07. The button in this case is used to cycle through a series of colour schemes for some table lamps.
The automations and switch definitions for the rocker switch are the same:
- platform: mqtt
name: "Lounge Lights Switch"
state_topic: "tele/bridge/RESULT"
value_template: '{{value_json.RfReceived.Data}}'
payload_on: "19190E"
payload_off: "19190A"
- alias: 'Lounge Light Switch ON'
trigger:
platform: state
entity_id: binary_sensor.lounge_lights_switch
to: 'on'
action:
service: light.turn_on
entity_id: group.lounge_lights
- alias: 'Lounge Light Switch OFF'
trigger:
platform: state
entity_id: binary_sensor.lounge_lights_switch
to: 'off'
action:
service: light.turn_off
entity_id: group.lounge_lights
The definitions for the push-button get a bit more complex. For starters - you need to define a dummy value for the switch off packet, I chose the ID with a suffix of 09 for this. Note that the sensor will never send this “off” packet, we need to generate that event ourselves:
- platform: mqtt
name: "Lounge Lights Cycle"
state_topic: "tele/bridge/RESULT"
value_template: '{{value_json.RfReceived.Data}}'
payload_on: "191907"
payload_off: "191909"
retain: true
And these are the automations to handle the push-button event, note the last thing we do is manually publish a MQTT packet to reset the switch state:
- alias: 'Lounge Light Cycle Colours'
trigger:
platform: state
entity_id: binary_sensor.lounge_lights_cycle
to: 'on'
action:
- service: mqtt.publish
data_template:
payload: >
{% if is_state('device_tracker.lounge_light_color', 'white') %}
lightyellow
{% else %}
{% if is_state('device_tracker.lounge_light_color', 'lightyellow') %}
lightgoldenrodyellow
{% else %}
{% if is_state('device_tracker.lounge_light_color', 'lightgoldenrodyellow') %}
wheat
{% else %}
{% if is_state('device_tracker.lounge_light_color', 'wheat') %}
white
{% else %}
white
{% endif %}
{% endif %}
{% endif %}
{% endif %}
topic: color/lounge
retain: true
- service: light.lifx_set_state
data_template:
entity_id: group.lounge_lights
color_name: >
{{ states('device_tracker.lounge_light_color') }}
brightness: 255
- service: mqtt.publish
data:
payload: '191909'
topic: tele/bridge/RESULT
retain: true
The first service call checks what the colour the light is now, and to then sets the new colour based on that. This uses my MQTT variables method shown here: Global variables that are stored between automations - without using add-ons.
The second service call switches the light colour, and finally the third service call resets the sensor state, ready for the next push-button event to trigger it.
There are probably plenty of less complex use cases for a push button switch - pick your own.
I hope this proves useful to someone, meanwhile it has made my wife happy to turn on our smart lights without resorting to powering them completely down and back up again