declare -i pretty=0
declare action="usage"
declare target='.'
+declare limit=""
declare format="json"
declare -A lights
declare lights_json
+declare full_json
+declare simple_json
declare flat_json
declare call='curl --silent --show-error --location --header "Accept: application/json" --request'
declare devices="/elgato/lights"
usage() {
cat <<EOF
-Usage: $(basename "${BASH_SOURCE[0]}") [-h] [-f <value>] [-l] [-p] [-s] [-t <value>][-v] [--<option>] [--<option> <value>] <action>
+Usage: $(basename "${BASH_SOURCE[0]}") [-h] [-f <value>] [-l <value>] [-p] [-s] [-t <value>][-v] [--<option>] [--<option> <value>] <action>
Elgato Lights controller. Works for Key Light and Key Light Air.
status Get state of lights
on Turn all lights on
off Turn all lights off
- temperature Set temperature level (260-470)
+ temperature Set temperature level (260-470)
brightness Set brightness level (0-100)
increase Increases brightness by 10
decrease Decreases brightness by 10
Available formats:
json Renders output as JSON (default)
- flat Renders output as flattened JSON with .(dot) notation JSON (default)
+ simple Renders output as JSON array of single level objects with subarrays as .(dot) notation JSON
+ flat Renders output as fully flattened single level JSON with .(dot) notation JSON
html Renders output as basic html table
csv Renders output as csv
table Renders output as a printed table
Available options:
--h, --help Print this help and exit
--f --format Set output format
--p, --pretty Pretty print console output
--s, --silent Supress notifications
--t, --target Only perform action on devices where value matches filter
--v, --verbose Print script debug info
+-h, --help Print this help and exit
+-f, --format Set output format
+-l, --limit <list> Limit top level output fields to the specified comma separated list
+-p, --pretty Pretty print console output
+-s, --silent Supress notifications
+-t, --target <filter> Only perform action on devices where value matches filter
+-v, --verbose Print script debug info
EOF
exit
}
format="${2-}"
shift
;;
+ -l | --limit)
+ limit=$(eval echo "\| {${2-}} ")
+ shift
+ ;;
-p | --pretty) pretty=1 ;;
-v | --verbose) set -x ;;
-s | --silent) silent=1 ;;
}
produce_json() {
- t=$(eval echo "'[.[] | select($target)]'")
+ t=$(eval echo "'[.[] $limit| select($target)]'")
+ f=$(eval echo "'[.[] | select($target)]'")
lights_json=$(echo "${lights[@]}" | jq -c -s "$t")
+ full_json=$(echo "${lights[@]}" | jq -c -s "$f")
+ simple_json=$(echo "${lights_json}" | jq -c '.[] | reduce ( tostream | select(length==2) | .[0] |= [join(".")] ) as [$p,$v] ({}; setpath($p; $v)) ')
+ simple_json=$(echo "${simple_json}" | jq -c -s '.') # slurp it to make it an array
+ flat_json=$(echo "${lights_json}" | jq -c -s '.[] | reduce ( tostream | select(length==2) | .[0] |= [join(".")] ) as [$p,$v] ({}; setpath($p; $v)) ')
+
}
output() {
- data=${1-}
- type=${2-"$format"}
# Mange user requested output format
case $format in
- json | flat) print_json "$data" ;;
- table) print_json "$data" ;;
- csv) print_csv "$data" ;;
- pair) print_pair "$data" ;;
- html) print_html "$data" ;;
- -?*) die "Unknown output format (-f/--format): $type" ;;
+ json) print_json "$lights_json" ;;
+ simple) print_json "$simple_json" ;;
+ flat) print_json "$flat_json" ;;
+ table) print_structured '@tsv' ;;
+ csv) print_structured '@csv' ;;
+ pair) print_structured 'pairs' ;;
+ html) print_html ;;
+ -?*) die "Unknown output format (-f/--format): $format" ;;
esac
}
print_json() {
- # TODO: Evaluate adding jq filtering as filter argument
- query=""
-
- # Deconstruct json and assemble in flattened with .(dot) notation
- if [[ $format == "flat" ]]; then
- query='reduce ( tostream | select(length==2) | .[0] |= [join(".")] ) as [$p,$v] ({}; setpath($p; $v))'
- else
- query='.'
- fi
# Manage pretty printing
if [[ $pretty -eq 1 ]]; then
- echo "${1-}" | jq "$query"
+ echo "${1-}" | jq '.'
else
- echo "${1-}" | jq -c -M "$query"
+ echo "${1-}" | jq -c -M '.'
fi
exit 0
}
-print_table() {
- bold=$(tput bold)
- normal=$(tput sgr0)
- message='
-
-'
- die "To be implemented"
+print_structured() {
+ pp=${2-$pretty}
+
+ # Handle csv and table printing
+ query="(.[0] | keys_unsorted | map(ascii_upcase)), (.[] | [.[]])|${1-@csv}"
+
+ # Handle printing as key value pairs
+ if [[ ${1} == 'pairs' ]]; then
+ query='.[] | "--------------",(to_entries[] | [.key, "=", .value] | @tsv)'
+ fi
+
+ # Manage pretty printing
+ if [[ $pp -eq 1 ]]; then
+ echo "${simple_json}" | jq --raw-output "$query" | column -t -s$'\t' | sed -e 's/"//g'
+ else
+ if [[ ${1} == 'pairs' ]]; then
+ echo "${simple_json}" | jq -r "$query" | sed -e 's/\t//g'
+ else
+ echo "${simple_json}" | jq -r "$query"
+ fi
+ fi
+}
+
+print_html() {
+ data=$(print_structured '@csv' 1)
+
+ html="
+ <table>
+ $(
+ print_header=true
+ while read d; do
+ if $print_header; then
+ echo "<tr><th>${d//,/<\/th><th>}</th></tr>"
+ print_header=false
+ continue
+ fi
+ echo "<tr><td>${d//,/</td><td>}</td></tr>"
+ done <<<"${data}"
+ )
+ </table>"
+ echo "$html"
}
set_state() {
'{device: $dev, manufacturer: $mf, hostname: $hn, url: $url, ipv4: $ipv4, ipv6: $ipv6,
port: $port, mac: $mac, sku: $sku, settings: $cfg}')
- # Store the light as json
+ # Store the light as json and merge info + light into base object
lights["$device"]=$(echo "$info $light $json" | jq -s '. | add')
# Reset for next light as we are processing the last avahi line
done
}
+# Quit if script is run by root
+[[ "$EUID" -eq 0 ]] && die "Not allowed to run as root"
+
# Manage user parameters
parse_params "$@"
find_lights
# Fail if we cannot find lights
-[[ ${#lights[@]} -eq 0 ]] && die "No lights found" 2
+[[ ${#lights[@]} -eq 0 ]] && die "No lights found"
produce_json
# Dispatch actions
case $action in
usage) usage ;;
-list) output "${lights_json}" ;;
+list) output ;;
status) status ;;
on) set_state 1 ;;
off) set_state 0 ;;