Physical Sonos like music button, write currently playing track to Domoticz text sensor

All kinds of 'OS' scripts
Post Reply
ben53252642
Posts: 392
Joined: Saturday 02 July 2016 5:17
Target OS: Linux
Domoticz version: Beta
Contact:

Physical Sonos like music button, write currently playing track to Domoticz text sensor

Post by ben53252642 » Wednesday 11 July 2018 12:31

Hey folks,

This is a bash script I wrote to write the currently playing track or radio station of a Sonos system into a Domoticz text sensor.

Essentially it's a way you can "like" whatever music is playing and save it to Domoticz so you can easily look at it later if you want to add it to Spotify or Google Music etc..

Personally I have a Wallmote button allocated to "liking" music in the living room. Makes my life easier, I don't have to open the Sonos App and often screenshot the name of a track playing on an internet radio station, the artist and track name are recorded to Domoticz!

nodesonoslike.JPG
nodesonoslike.JPG (163.19 KiB) Viewed 107 times

Requirements:

1) Node Sonos must be setup and working on the system
2) apt-get install jq
3) Create a text virtual sensor in Domoticz and enter it's IDX into the bash script
4) Fill out configuration section of the script and change the ip address in the nodesonos variable
5) Here is the bash script

Code: Select all

#!/bin/bash

# Domoticz Configuration
domoticzserver="192.168.0.5"
domoticzport="443"
domoticzuser=""
domoticzpass=""
domoticztextdevicesensoridx="1193"

# Get speaker group info from node sonos
nodesonos=$(curl -s "http://192.168.0.5:5005/zones")

# Loop through each speaker group
speakergroups=$(echo "$nodesonos" | jq "keys[]")
for sg in $speakergroups ; do

# Check if speaker group is playing or stopped
playstate=$(echo "$nodesonos" | jq ".[$sg] .members[0] .state .playbackState" | sed 's/\"//g')

if [ "$playstate" == "PLAYING" ]; then

# Check what type of audio is playing, we don't want to include TV!
type=$(echo "$nodesonos" | jq ".[$sg] .members[0] .state .currentTrack .type" | sed 's/\"//g')
if [ "$type" == "radio" ] || [ "$type" == "track" ] ; then

# Set the playing flag
playingflag="yes"

# Get the remaining info for the speaker group and put it into easy to access variables
artist=$(echo "$nodesonos" | jq ".[$sg] .members[0] .state .currentTrack .artist" | sed 's/\"//g')
title=$(echo "$nodesonos" | jq ".[$sg] .members[0] .state .currentTrack .title" | sed 's/\"//g')
stationname=$(echo "$nodesonos" | jq ".[$sg] .members[0] .state .currentTrack .stationName" | sed 's/\"//g')

# Apply a filter to only display a radio station name once
if [ "$artist" == "$stationname" ]; then
stationfilter="yes"
fi

# Format data and display in terminal
echo "State: $playstate"
data=$(echo "$artist - $title" $(if [ "$type" == "radio" ] && [ "$stationfilter" != "yes" ]; then echo " - $stationname"; fi))
echo "$data"

# Send data to Domoticz
domoticztext=$(echo "$data" | sed 's/ /%20/g')
curl --max-time 60 -k -s "https://{$domoticzuser}:{$domoticzpass}@{$domoticzserver}:{$domoticzport}/json.htm?type=command&param=udevice&idx={$domoticztextdevicesensoridx}&nvalue=0&svalue={$domoticztext}"

fi
fi
done

# Message if nothing is playing
if [ "$playingflag" != "yes" ]; then
echo "Nothing is playing..."
fi
6) Here is the Lua device script that executes the bash script

Code: Select all

commandArray = {}
if (devicechanged['Wallmote Like Track'] == 'On')  then
os.execute ('/root/scripts/sonos/like.sh &')
end
return commandArray

ben53252642
Posts: 392
Joined: Saturday 02 July 2016 5:17
Target OS: Linux
Domoticz version: Beta
Contact:

Re: Physical Sonos like music button, write currently playing track to Domoticz text sensor

Post by ben53252642 » Wednesday 11 July 2018 17:36

Modified version that hyperlinks a Google Music search for the track name (it's smart enough to exclude the name of an internet radio station if one is playing). 8-)

text1.JPG
text1.JPG (38.53 KiB) Viewed 83 times
text2.JPG
text2.JPG (131.43 KiB) Viewed 82 times

Code: Select all

#!/bin/bash

# Domoticz Configuration
domoticzserver="192.168.0.5"
domoticzport="443"
domoticzuser=""
domoticzpass=""
domoticztextdevicesensoridx="1193"

# Get speaker group info from node sonos
nodesonos=$(curl -s "http://192.168.0.5:5005/zones")

# Loop through each speaker group
speakergroups=$(echo "$nodesonos" | jq "keys[]")
for sg in $speakergroups ; do

# Check if speaker group is playing or stopped
playstate=$(echo "$nodesonos" | jq ".[$sg] .members[0] .state .playbackState" | sed 's/\"//g')

if [ "$playstate" == "PLAYING" ]; then

# Check what type of audio is playing, we don't want to include TV!
type=$(echo "$nodesonos" | jq ".[$sg] .members[0] .state .currentTrack .type" | sed 's/\"//g')
if [ "$type" == "radio" ] || [ "$type" == "track" ] ; then

# Set the playing flag
playingflag="yes"

# Get the remaining info for the speaker group and put it into easy to access variables
artist=$(echo "$nodesonos" | jq ".[$sg] .members[0] .state .currentTrack .artist" | sed 's/\"//g')
title=$(echo "$nodesonos" | jq ".[$sg] .members[0] .state .currentTrack .title" | sed 's/\"//g')
stationname=$(echo "$nodesonos" | jq ".[$sg] .members[0] .state .currentTrack .stationName" | sed 's/\"//g')

# Apply a filter to only display a radio station name once
if [ "$artist" == "$stationname" ]; then
stationfilter="yes"
fi

# Format data and display in terminal
echo "State: $playstate"
data=$(echo "$artist - $title" $(if [ "$type" == "radio" ] && [ "$stationfilter" != "yes" ]; then echo " - $stationname"; fi))
echo "$data"

# Send data to Domoticz
domoticztext=$(echo "$data" | sed 's/ /%20/g' | sed 's/-/%2D/g')
gsearch=$(echo $(if [ "$type" == "track" ]; then echo "$artist"; fi)  "$title" | sed 's/ /%2B/g' | sed 's/-/%2D/g')
curl --max-time 60 -k "https://{$domoticzuser}:{$domoticzpass}@{$domoticzserver}:{$domoticzport}/json.htm?type=command&param=udevice&\
idx={$domoticztextdevicesensoridx}&nvalue=0&svalue={$domoticztext}%20<a%20href="https://play.google.com/music/listen%23/sr/{$gsearch}"%20target="_blank"><font%20color=F36D0B>Google%20Music</font></a>"

fi
fi
done

# Message if nothing is playing
if [ "$playingflag" != "yes" ]; then
echo "Nothing is playing..."
fi

Post Reply

Who is online

Users browsing this forum: No registered users and 2 guests