Smart Laundry Notifications with a Sonoff S31 & Home Assistant




Make your Laundry Smarter with our favorite smart plug, the Sonoff S31, and Home Assistant with Voice Notifications when the Washer and/or Dryer are finished.  Easy power monitoring and automations with this step by step tutorial of the setup.

Sonoff S31

Soldering Iron Station
Helping Hands(as shown)
Better Helping Hands
0.015 Solder
Female Jumper Wires
USB FTDI for Flashing

Tasmota Backlog (modify to your values)
backlog ssid MyWiFiz; password SooperSekret; mqtthost 192.168.1.5; mqttuser me123; mqttpassword 123that; powerretain 1; topic SNF-Washer; sensorretain 1; poweronstate 1; friendlyname SNF-Washer; teleperiod 60

Home Assistant Config Sample & Automations:

(configuration.yaml)
 sensor:
  - platform: mqtt
    name: "Dryer State"
    state_topic: "hass/state/dryer"
    icon: mdi:tumble-dryer
  - platform: mqtt
    name: "Washer State"
    state_topic: "hass/state/washer"
    icon: mdi:washing-machine
  - platform: mqtt
    name: "Washer Watts"
    state_topic: "tele/SNF-Washer/SENSOR"
    value_template: "{{value_json['ENERGY'].Power }}"
    qos: 2
    unit_of_measurement : "W"
    icon: mdi:flash-circle
    availability_topic: "tele/SNF-Washer/LWT"
    payload_available: "Online"
    payload_not_available: "Offline"
  - platform: mqtt
    name: "Washer Voltage"
    state_topic: "tele/SNF-Washer/SENSOR"
    value_template: "{{value_json['ENERGY'].Voltage }}"
    qos: 2
    unit_of_measurement : "V"
    icon: mdi:flash-circle
    availability_topic: "tele/SNF-Washer/LWT"
    payload_available: "Online"
    payload_not_available: "Offline"
  - platform: mqtt
    name: "Washer Amps"
    state_topic: "tele/SNF-Washer/SENSOR"
    value_template: "{{value_json['ENERGY'].Current }}"
    qos: 2
    unit_of_measurement : "A"
    icon: mdi:flash-circle
    availability_topic: "tele/SNF-Washer/LWT"
    payload_available: "Online"
    payload_not_available: "Offline"
  - platform: mqtt
    name: "Washer Energy Today"
    state_topic: "tele/SNF-Washer/SENSOR"
    value_template: "{{value_json['ENERGY'].Today }}"
    qos: 2
    unit_of_measurement : "kWh"
    availability_topic: "tele/SNF-Washer/LWT"
    payload_available: "Online"
    payload_not_available: "Offline"
  - platform: mqtt
    name: "Washer Energy Yesterday"
    state_topic: "tele/SNF-Washer/SENSOR"
    value_template: "{{value_json['ENERGY'].Yesterday }}"
    qos: 2
    unit_of_measurement : "kWh"
    availability_topic: "tele/SNF-Washer/LWT"
    payload_available: "Online"
    payload_not_available: "Offline"

  - platform: mqtt
    state_topic: "tele/SNF-Washer/STATE"
    name: "Washer Signal"
    unit_of_measurement: "%"
    value_template: "{{value_json['Wifi'].RSSI }}"
    availability_topic: "tele/SNF-Washer/LWT"
    qos: 1
    payload_available: "Online"
    payload_not_available: "Offline"

(group.yaml)

  washerpanel:
    name: Washer
    entities:
      - sensor.washer_state
      - sensor.washer_voltage
      - sensor.washer_watts
      - sensor.washer_amps
      - sensor.washer_energy_today
      - sensor.washer_energy_yesterday
      - sensor.washer_signal

(automations.yaml)

- alias: 'Dryer State - Door'
  trigger:
    platform: numeric_state
    entity_id: sensor.dryer_watts
    above: 7
    below: 20
    for:
      seconds: 2
  action:
    - service: mqtt.publish
      data:
        topic: hass/state/dryer
        payload: 'Door Open'
        retain: 'true'
- alias: 'Dryer State - Drying'
  trigger:
    platform: numeric_state
    entity_id: sensor.dryer_watts
    above: 50
    for:
      seconds: 2
  action:
    - service: mqtt.publish
      data:
        topic: hass/state/dryer
        payload: 'Drying'
        retain: 'true'
- alias: 'Dryer State - Idle'
  trigger:
    platform: numeric_state
    entity_id: sensor.dryer_watts
    below: 6
    for:
      seconds: 2
  action:
    - service: mqtt.publish
      data:
        topic: hass/state/dryer
        payload: 'Idle'
        retain: 'true'
# -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
#  Washing Machine Start/Finish
# -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
- alias: 'Washer State - Start'
  trigger:
    platform: numeric_state
    entity_id: sensor.washer_watts
    above: 5
    for:
      seconds: 4
# Make sure washer isn't already running and delaying between cycles - don't re-trigger and cause stopwatch reset
  condition:
    condition: template
    value_template: "{{ states.sensor.washer_state.state != 'Washing' }}"
  action:
    - service: mqtt.publish
      data:
        topic: hass/state/washer
        payload: 'Washing'
        retain: 'true'
- alias: 'Washer State - Idle'
  trigger:
    platform: numeric_state
    entity_id: sensor.washer_watts
    below: 5
    for:
      minutes: 5
  action:
    - service: mqtt.publish
      data:
        topic: hass/state/washer
        payload: 'Idle'
        retain: 'true'
- alias: 'Dryer Finished'
  trigger:
    platform: state
    entity_id: sensor.dryer_state
    from: 'Drying'
    to: 'Idle'
  action:
    - service: media_player.volume_set
      data:
        entity_id:
          - media_player.craft_room_speaker
          - media_player.kitchen_speaker
          - media_player.master_speaker
          - media_player.bedroom_speaker
        volume_level: '0.50'
    - service: tts.google_say
      entity_id:
        - media_player.craft_room_speaker
        - media_player.kitchen_speaker
        - media_player.master_speaker
        - media_player.bedroom_speaker
      data_template:
         message: "Hey.. Guess what..  The dryer is done! Exciting stuff, right?"
- alias: 'Washer Finished'
  trigger:
    platform: state
    entity_id: sensor.washer_state
    from: 'Washing'
    to: 'Idle'
  condition:
    condition: template
    value_template: "{{ states.sensor.dryer_state.state != 'Drying' }}"
  action:
    - service: media_player.volume_set
      data:
        entity_id:
          - media_player.craft_room_speaker
          - media_player.kitchen_speaker
          - media_player.master_speaker
          - media_player.bedroom_speaker
        volume_level: '0.50'
    - service: tts.google_say
      entity_id:
        - media_player.craft_room_speaker
        - media_player.kitchen_speaker
        - media_player.master_speaker
        - media_player.bedroom_speaker
      data_template:

         message: "Laundry in the washer can be moved over!"



Comments

  1. This is brilliant! Thank you for taking the time to make a video and share your code. I have planned on doing this for several years now. I have subscribed to your Youtube channel as well!

    ReplyDelete
  2. Thanks a lot for the examples. Just implemented the dryer part today without fussing about reading the documentation over and over

    ReplyDelete
  3. Nice trick getting Google's notification chime to play by setting the volume... I just wish one could read the current volume value so the volume setting could be restored after setting it to 50%.

    - service: media_player.volume_set
    data:
    entity_id:
    - media_player.craft_room_speaker
    - media_player.kitchen_speaker
    - media_player.master_speaker
    - media_player.bedroom_speaker
    volume_level: '0.50'

    I have been looking for an mp3 of that chime because I'd implemented a sound play followed by a TTS output. Two things, my current chime mp3 is a bit obnoxious, plus, no matter how I try to tweak the delay before playing the TTS, it's never reliable in not chopping the chime off mid-play. I did find a work-around I'm about to test which polls the value of the "Title" until its empty before sending the next media to play (https://community.openhab.org/t/chromecast-google-home-automatic-start-playing-a-stream-when-motion-is-detected-in-a-room/39994/20).

    Mike

    P.S. In my case, I created a Google Assistant audio group for the players I wanted to broadcast to and just play to that one device. That way, If I want to add or change which devices I notify, I just change the make-up of the group. Having said that, I'm wondering if your trick of adjusting the volume would work on audio groups.

    P.P.S. I play an audio notification only if it's during "waking" hours. I always send a text or e-mail afterwards. That way, I'm not waking up the house but we still know when the laundry is ready ;-)

    ReplyDelete
  4. Is there a way to do this with ESPHome? Flashed mine with Tasmota and used the configuration.yaml code provided. All the sensors show as "Unvailable" in the front-end...its an ongoing issue with MQTT in my setup for some reason. I have 4 other Tasmota devices (2 Sonoff Basics and 2 of the Tuya light switches you used in another video) that would only work if I commented out the availability topic...it's as if HA doesn't want to read MQTT topics. After dinking with it for far too long, I reflashed the 4 existing devices using ESPHome and they work great. I imagine the same would hold true if I went that route here as well, but not sure how to set it up in the ESPHome .yaml file.

    ReplyDelete
  5. Also wondering if you have tried setting the S31 up in ESPHome? I have gone thru and tried doing it, but when I put the UART section into the yaml file it ends up going into a loop of rebooting. I have another S31 that I can try as well but I think I am going to have the same problem.

    Just wondering if you have ever got the Sonoff S31 working with ESPHome. Keep up the great work.

    ReplyDelete
  6. Hi, I've recreated this with the exception of commenting out the items regarding the dryer. Now, I have the sensors showing up in my History timeline and reporting correctly. I have an error on a line in configuration.yaml which is: "group: !include groups.yaml" which is copied verbatim from your entry here.

    If you had some time to help, I would very much appreciate it. I can provide whatever logs and listings. Thanks!

    ReplyDelete
    Replies
    1. I uncommented all the dryer stuff and it passes configuration check so maybe something got missed.

      Delete
  7. unfortunatelly I wasn't able to run this project. Each timed I copied configuration to configuration.yaml my PI was crashing. Tried to many things but I didn't make it to work. Although I managed to flash the Tasmota firmware.

    ReplyDelete
  8. My sonoff s31 non soldering work around. I dont have a 3d printer either. Just need some pogo pins, dupont wire holders, super clue, and cheap clothes pins. http://imgur.com/gallery/Z2kqxvS

    ReplyDelete
  9. Love this, but when I go into the entries they have red exclamation marks next to them saying unavailable. Every piece of the yaml is correct all your instructions were followed.

    ReplyDelete
  10. In the automation you use above XX for 4 seconds. But you read the tele from Tasmota and that is only sent every 300 seconds so if it goes above or below a value it will always stay in with the same value for 300 seconds right? I have been looking into making rules in Tasmota to send sensor values when they change more than X watts up or down instead. Then you cantt read the tele from Tasmota that but need to change the mqtt sensor as well. You can change the tele period in tasmota but if you send it every 10 seconds I can imagine that the database will keep a lot of information that is not useful.

    ReplyDelete
    Replies
    1. No, don't change the teleperiod. The powerdelta will take care of it. You can adjust teh powerdelta if needed that makes it report based on when a certain percentage load change happens.

      Delete
    2. I don't really understand. You get the values from the tele every 300 seconds. Then you use automation that have a trigger that if it is above 5 watts for 4 seconds it will publish an MQTT message but you only get the value every 300 seconds. I can't see any instructions about Powerdelta. But after looking around, powerdelta seems to solve the 300 second problem but I have been trying to set a powerdelta but my device (Blitzwolf with Tasmota 8.1.0.2) just respond like this

      11:57:42 CMD: powerdelta 10
      11:57:42 MQT: stat/tvattmaskin/RESULT = {"Command":"Unknown"}

      Delete
    3. It is a default setting but yes if your plug doesn't have the command then you are probably running the lite version of the Tasmota software. Make sure you upgrade to the full version of tasmota.bin.

      Delete
    4. Tuye Convert installed version 8.1.0.2 and others seems to have had some problems with that as well. Updated to 8.3.1 and Powerdelta works. Great work!

      Delete
    5. Correct. TuyaConvert has to install a lite version of Tasmota to fit alongside the Tuya stuff. So it is always good practice to update to the full version after doing Tuya Convert.

      Delete
  11. I am using a different smart plug with power sensor, flashed with Tasmota. I copied over the yaml, changed the notifications for telegram and HA, and then replicated all the bits in configuration.yaml to also work with the dryer. It works just great! Many thanks for sharing, Travis.

    ReplyDelete
    Replies
    1. Definitely one on my to do list to redo and show it a bit easier but it still applies though. Still love this one ourselves and use it to this very day! Thanks!

      Delete
  12. Great work, thank you.
    I have just started to use it, still need to tweak times of loads and such, but I have a question.
    Why does both the washer and dryer state always display as Unknown. What step did I miss.
    Thanks so much, you have made this families life so much easier.

    ReplyDelete
    Replies
    1. Also the group.washerpanel shows as unknown.

      Delete
    2. Jump into discord so we can help get this sorted out.

      Delete
  13. Any suggestions on false alarms. I get a notification when it restarts or I think when it has a WIFI connection failure. I'm using the new version of the setup on Tasmota 9.2 it shows a connection error to MQTT but I'm assuming this is a failure to connect to WIFI although I don't see disconnects in the Unifi console. Sample of console output below. Curious if I increased the MQTT timeout or adjusted the automation rule?

    11:20:29 MQT: Connect failed to 192.168.1.42:1883, rc -2. Retry in 10 sec
    11:20:39 MQT: Attempting connection...
    11:20:40 MQT: Connect failed to 192.168.1.42:1883, rc -2. Retry in 20 sec
    11:21:00 MQT: Attempting connection...
    11:21:01 MQT: Connect failed to 192.168.1.42:1883, rc -2. Retry in 30 sec
    11:21:31 MQT: Attempting connection...
    11:21:32 MQT: Connect failed to 192.168.1.42:1883, rc -2. Retry in 40 sec
    11:22:12 MQT: Attempting connection...

    ReplyDelete

Post a Comment