6 trap destroy SIGINT SIGTERM ERR EXIT
9 temp_file="/tmp/elgatokeylights"
10 script_dir=$(cd "$(dirname "${BASH_SOURCE[0]}")" &>/dev/null && pwd -P)
11 icon="${script_dir}/assets/elgato.png"
14 declare -i {silent,list,pretty}=0
15 declare action="usage"
18 declare call="curl --silent --show-error --location --header 'Accept: application/json' --request"
19 declare devices="/elgato/lights"
20 declare accessory_info="/elgato/accessory-info"
21 declare settings="/elgato/lights/settings"
23 if [ ! -r "${icon}" ]; then icon=sunny; fi
27 if [ $silent -eq 0 ]; then
28 notify-send -i "$icon" "Key Light Controller" "$1"
38 local code=${2-1} # default exit status 1
45 rm "$temp_file" 2>/dev/null
52 Usage: $(basename "${BASH_SOURCE[0]}") [-h] [-l] [-p] [-s] [-v] <action>
54 Elgato Lights controller. Works for Key Light and Key Light Air.
57 list List available lights
58 status Get state of lights
60 off Turn all lights off
61 temperature Set temperature level (260-470)
62 brightness Set brightness level (0-100)
63 increase Increases brightness by 10
64 decrease Decreases brightness by 10
68 -h, --help Print this help and exit
69 -p, --pretty Pretty print console output
70 -v, --verbose Print script debug info
71 -f, --flag Some flag description
72 -s, --silent Supress notifications
78 # default values of variables set from params
83 -p | --pretty) pretty=1;;
84 -v | --verbose) set -x ;;
85 -s | --silent) silent=1 ;;
86 -?*) die "Unknown option: $1" ;;
94 # check required params and arguments
95 declare -A actions=([help]=1 [list]=1)
96 #[[ -z "${param-}" ]] && die "Missing required parameter: param"
97 [[ ${#args[@]} -ne 1 ]] && die "Incorrect action count, 1 allowed"
99 [[ -n "${actions[${args[0]}]}" ]] && action="${args[0]}"
106 if ! command -v $var &>/dev/null; then
107 error "Dependency $var was not found, please install and try again"
115 for l in "${!lights[@]}"; do
116 json+="${lights[$l]},"
119 lights_json="[${json%,}]"
123 if [[ $pretty -eq 1 ]]; then
126 echo "$1"|jq -c -M '.'
133 die "To be implemented"
138 die "To be implemented"
143 # Scan the network for Elgato devices
144 avahi-browse -d local _elg._tcp --resolve -t | grep -v "^\+" >"$temp_file"
147 declare {device,hostname,manufacturer,ip,port,mac,protocol,sku}="N/A"
148 cat "$temp_file" > tmp
149 while read -r line; do
151 # Gather information about the light
152 if [[ ($line == =*) && ($line =~ IPv4[[:space:]](.+)[[:space:]]_elg) ]]; then
153 device=$(eval echo "${BASH_REMATCH[1]}") # eval to strip whitespace
154 elif [[ $line =~ hostname.+\[(.+)\] ]]; then hostname=${BASH_REMATCH[1]};
155 elif [[ $line =~ address.+\[(.+)\] ]]; then ip=${BASH_REMATCH[1]};
156 elif [[ $line =~ port.+\[(.+)\] ]]; then port=${BASH_REMATCH[1]};
157 elif [[ $line =~ txt.+\[(.+)\] ]]; then
158 txt=$(eval echo "${BASH_REMATCH[1]}") # eval to strip single and double quotes
160 if [[ $txt =~ mf=([^[[:space:]]*]*) ]]; then manufacturer=${BASH_REMATCH[1]}; fi
161 if [[ $txt =~ id=([^[[:space:]]*]*) ]]; then mac=${BASH_REMATCH[1]}; fi
162 if [[ $txt =~ md=.+[[:space:]]([^[[:space:]]*]*)[[:space:]]id= ]]; then sku=${BASH_REMATCH[1]}; fi
165 # Get information from the light
166 declare {cfg,url,info,light}="{}"
167 if [[ ! (-z $ip) && ! (-z $port) ]]; then
168 url="http://$ip:$port"
169 #echo "${call} GET ${url}${settings}"
170 cfg=$(eval "${call} GET ${url}${settings}") > /dev/null
171 #echo "${call} GET ${url}${accessory_info}"
172 info=$(eval "${call} GET ${url}${accessory_info}") > /dev/null
173 #echo "${call} GET ${url}${devices}"
174 light=$(eval "${call} GET ${url}${devices}") > /dev/null
176 # Store the light as json
177 lights["$ip"]=$( jq -n \
178 --arg dev "$device" \
179 --arg hn "$hostname" \
182 --arg mf "$manufacturer" \
186 --argjson light "$light" \
187 --argjson cfg "$cfg" \
188 --argjson info "$info" \
189 '{device: $dev, manufacturer: $mf, hostname: $hn, url: $url, ip: $ip,
190 port: $port, mac: $mac, sku: $sku, light: $light, settings: $cfg, info: $info}' )
192 declare {device,hostname,manufacturer,url,ip,port,mac,protocol,sku,cfg}="N/A"
196 rm "$temp_file" 2>/dev/null
199 # Manage user parameters
202 # Make sure dependencies are installed
203 dependencies avahi-browse curl notify-send jq
207 # Fail if we cannot find lights
208 [[ ${#lights[@]} -eq 0 ]] && error "No lights found" 1
213 [[ $action == "usage" ]] && usage
214 [[ $action == "list" ]] && print_json "${lights_json}"
215 [[ $action == "status" ]] && status
216 [[ $action == "on" ]] && set_state 1
217 [[ $action == "off" ]] && set_state 0
221 # Manage printing (parameter -l/--list specicified)