Google Cast Audio(Chromecast) control

Tags: #<Tag:0x00007f7455e24ed0> #<Tag:0x00007f7455e24d40>

Hi guys, I just wanna share my script to get status and control Chromecast audio devices. It is based on python library pychromecast.

from time import sleep
import socket
import pychromecast
import sys

sys.stderr = open('/var/log/chromecast.log', 'a')

bedroom = pychromecast.get_chromecast(friendly_name="Bedroom")
kitchen = pychromecast.get_chromecast(friendly_name="Kitchen")
bath = pychromecast.get_chromecast(friendly_name="Bath")

bedroom.wait()
kitchen.wait()
bath.wait()

print("Chromcasts connected")

def device( name ):
     if name == "Bedroom":
         return bedroom
     elif name == "Kitchen":
         return kitchen
     elif name == "Bath":
         return bath
     else:
         print("Unknown name of device: \"", name, "\"")
         return False

def get_volume( name ):
     vl = round(device(name).status.volume_level,2) * 100
     return str(int(vl))

def set_volume( name, level ):
    vl = int(level) / 100
    device(name).set_volume(vl)
    sleep(0.2)
    return get_volume( name )

def status( name ):
     session_id = device(name).status.session_id
     if session_id == None:
         return "OFF"
     else:
         return "ON"

host = '127.0.0.1'
port = 12345
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
sock.bind((host, port))

while True:
    sock.listen(1)
    conn, addr = sock.accept()
    while True:
        data = conn.recv(1024).decode('ascii')

        if not data:
            break
        print("Recived string: \"", data, "\" from ", addr)
        data = data.split(" ")

        if data[1] == "get_volume":
            conn.sendall(get_volume(data[0]).encode('ascii'))
        elif data[1] == "set_volume":
            conn.sendall(set_volume(data[0],data[2]).encode('ascii'))
        elif data[1] == "status":
            conn.sendall(status(data[0]).encode('ascii'))
        else:
            print("Unknown command")
            breae
    conn.close()

You can add next line to rc.local to start it at boot time:

( sleep 3; sudo -u root python3 /scripts/chromecast.py > /var/log/chromecast.log )&

Items should looks like this:

Switch  CastKitchenStatus 	"Cast Kitchen [MAP(cast_status.map):%s]"	<chromecast>	(Cast,Kitchen)	{ exec="<[/scripts/chromecast.sh Kitchen status:60000:]" }
Dimmer 	CastKitchenVolume 	"Cast Kitchen Vol [%.1f %%]"			<volume>	(Cast,Kitchen)	{ exec="<[/scripts/chromecast.sh Kitchen get_volume:60000:] >[*:/scripts/chromecast.sh Kitchen set_volume %2$s]" }

Chromecast.sh:

#!/bin/bash
echo -n "$@" | nc 127.0.0.1 12345

I’m using it for about two weeks and it is pretty stable.
Also, i’m going to add option to send link to chromecast device. It will make possible to play some notifications, alarms, etc.

2 Likes

I’ve been using the script this guy has posted on reddit: https://www.reddit.com/r/homeautomation/comments/4fc01z/quick_question_for_openhab_users/d28vnc4

It’s been pretty good for me and supports message queues etc.

The only thing I can’t figure out is how to detect and a device stops casting :confused:

1 Like

Has anyone got this working with TTS? That would be amazing…

TBH, all you need is TTS-> WAV then push that to chromecast as a stream. should be reasonable possible. Might be a little laggy though.

I’m using “.status.session_id” for that. If response is empty - nobody is connected to the device.

Is there an event you can subscribe to to know when that changes?

Hi i’m thinking about to get chromcast device to use for notifications only today I’ve got squeezelite players for notifications but doorbell notification gets womwhere between 5-30secoinds delay anyone have an idea about notification delays with chromecast. And could i test i with my vide chromecast or is it strictly working for audio cromecast.

Hi, like to find a way to turn off my stereo(with a xiaomi plug) when my chromecast is not reciving anything. Can I do this with this script or do you know of any other way to do it?

check out the new binding. it has an idling status and your can also check for a change in appid

1 Like

The new OH chromecast binding or an other?

Openhab binding. Its been updated.

The 2.2.0 snapshot file, doesn’t load, it’s the one from today (this evening):

2017-11-29 23:47:37.026 [WARN ] [org.apache.felix.fileinstall ] - Error while starting bundle: file:/usr/share/openhab2/addons/org.openhab.binding.chromecast-2.2.0-SNAPSHOT.jar
org.osgi.framework.BundleException: Could not resolve module: org.openhab.binding.chromecast [230]
Unresolved requirement: Import-Package: com.fasterxml.jackson.annotation
at org.eclipse.osgi.container.Module.start(Module.java:434)[org.eclipse.osgi-3.10.101.v20150820-1432.jar:]
at org.eclipse.osgi.internal.framework.EquinoxBundle.start(EquinoxBundle.java:392)[org.eclipse.osgi-3.10.101.v20150820-1432.jar:]
at org.apache.felix.fileinstall.internal.DirectoryWatcher.startBundle(DirectoryWatcher.java:1253)[4:org.apache.felix.fileinstall:3.5.6]
at org.apache.felix.fileinstall.internal.DirectoryWatcher.startBundles(DirectoryWatcher.java:1225)[4:org.apache.felix.fileinstall:3.5.6]
at org.apache.felix.fileinstall.internal.DirectoryWatcher.doProcess(DirectoryWatcher.java:512)[4:org.apache.felix.fileinstall:3.5.6]
at org.apache.felix.fileinstall.internal.DirectoryWatcher.process(DirectoryWatcher.java:361)[4:org.apache.felix.fileinstall:3.5.6]
at org.apache.felix.fileinstall.internal.DirectoryWatcher.run(DirectoryWatcher.java:312)[4:org.apache.felix.fileinstall:3.5.6]

I’m not sure about that one. it’s working for me.

I updated my openHAB installation and now the binding is working again

Will check the new features

1 Like