Controlling a Google Home, with a zigbee button and Node-RED

(Amazon links are affiliate links, where I get a small commission of purchased item)

Our son has a SmartThings button, and a Google Home in his bedroom. He plays with the GHome and we use it for sleep sounds at night. Anytime after 9pm, the button turns on his lamp at 10% red, and then we yell “Hey Google, play the sound of rain at 70% volume!” The whole point of all this automation stuff is to make our lives easier. So I set off to make his GHome come on with the nightlight.

I had no idea how to do this. I spent many days searching and turning up nothing. So I had to figure it out, and this is how I dood it.

I started by connecting an “events: state node” to a “debug” node. Remember to set the debug node to “complete msg object”

I go into my son’s room and say “Hey Google, play the sound of rain”, and then checking out the output of the debug node. You’ll see something like this:

When the Google Home started playing, it was “idle”, and then the state changed to “playing”. The “topic” shows you the device id, and the “payload” shows you the state. The “msgid” is unique to every message and is what keeps track of an individual message as it travels through nodes. We’re not worried about that in this example, but I wanted to give an explanation on it.

Let’s break down the “playing” message. Hit the arrow next to topic to drill down. This will show the topic, which is the original information, just a little easier to read.

We now need to drill down into data, so hit the arrow next to “data: object“. This shows you the data of the object.

You’ll see old_state, and new state. We’ll review both of these, but lets start with old_state.

Here you see the entity_id “media_player.wyatts_speaker” and that its old_state was “idle” at 2:13pm on 10-15-19. Silly Brits and how they do time 😉 Ignore attributes and context for the time being.

Let’s go ahead and close old_state by clicking the arrow, and drill down “new_state“.

This shows pretty much the same info as old_state, but now shows that it is “playing”. Let’s drill down into attributes.

There’s a lot of info here. Let’s take a break from this for a minute, so we can see exactly what information we need to play the rain sounds on Wyatt’s GHome. To find this out, grab a call service node. Under domain, type “media_player” and in service, type “play_media”, then click out of the field.

Once you type in the Domain and Service, a list of commands will populate below, which are very helpful in figuring this out. In this example we see “entity_id“, “media_content_id” and “media_content_type“. In this case, we need to use all three of these commands, which I figured out from trial and error. A lot of times, and probably most of the time, you will not need all of the commands listed, just a few of them.

So with this information, lets go back to the attributes of the new_state.

I have no idea what app_id is, so I blurred it.. It seems to be the only thing that is unique between devices so I blurred it just in case.

Here we can see the media_content_id that we’re going to need to find and play the media, in this case it’s the sound of rain. We’re going to take this and plug it into the call service node. Go ahead and enter the entity_id that you want this to play on, as well as the content id. The format should be “media_content_id”:”” . Pay attention to the quotes and semi colon placement, and make sure to type in the open and closed brackets. Click the JSON editor to see if the code is properly formatted.

Here’s how the code looks in the JSON editor:

At this point, we’ve satisfied two of the requirements that are needed to make this happen.

The last part “media_content_type” is an easy one, as it tells us what our options are in the description. For this one, we need to use “music“, so it will look like this; “media_content_type”:”music”. Here’s how it looks in the node config:

Here’s how it looks in the JSON editor:

So now we have a properly configured call service node to play the rain sounds on the GHome. To test it, we’ll connect an inject node.

When the inject tab is clicked, it plays the rain sounds from the GHome. Now, when it starts playing, it’s going to play at what ever volume the Google Home was last used at. Let’s fix that…grab another call service node.

The domain needs to be “media_player“, the service needs to be “volume_set“, the entity_id is whatever device you’re adjusting the volume on and the data needs to be {“volume_level”:0.x}. The volume level is in .1 increments. So 0.7 is 70% volume. 0.2 would be 20%, 1.0 would be 100%, etc.

Now we’ll take this service node and place it after the inject node, but before the other service node.

Now when the tab is pressed, the volume of the GHome is set to 70% and then the rain sounds start to play.

So now we have a working flow, although it is manually triggered. There are many ways to automate this. One way is to use an inject node set to trigger at specific times.

The way that I’m doing it is by button press. Let’s get into it.

We will first need an “events: all” node , and configure it to grab all zigbee events

We will need to know what the hardware address of the switch is, this is called the device_ieee. To figure that out, you need to connect a debug node to the zha_event node and look for the messages when you press the button. Inside the payload will be the device_ieee. Copy that, and paste it into a switch node. Make sure to change the msg property to “msg.payload.event.device_ieee”.

So now we have the zha_event node monitoring all zha_events. Anytime a zigbee device is triggered, it sends a zha_event, with all of it’s information. The switch node then reads the zha_events and filters the specific device_ieee to the output node.

This is what we have now

Now we need to differentiate the different button presses ie; single press, double press, long press, etc. Well, how do we figure that out? We need another debug node, attached to the switch node.

Now when you press the button in different ways, look for the “msg.payload.event.command”. Usually it will be close to the description of the action you performed. In the case of the SmartThings button, the event command for a single press is button_single, a double press is button_double and a hold is button_hold. For your button, just keep pressing it and digging through the debug node output to find out what yours is. Once you figure that out, paste them into a switch node. Make sure to change the msg property to “payload.event.command.” so the switch can grab the individual button presses.

A single button press will come from the top output, a double press will come from the middle and a button hold will come from the bottom output. Place this switch node, behind the last switch node we worked with.

So, if we want the Google Home to play rain sounds with a single button press, we need to connect the two service nodes we worked with earlier, to the top node.

So now we have a working flow. a single button press will turn on the GHome and play rain sounds at 70% volume. Let’s make a double press turn it off. All we need is a call service node configured to turn off the GHome.

Then connect it to the middle output on the switch node.

So now we have a complete, working flow. A single button press will play the rain sounds at 70% volume, and a double press will turn them off.