115 lines
3.4 KiB
Python
115 lines
3.4 KiB
Python
#!/usr/bin/env python3
|
|
|
|
# <xbar.title>Hubitat Menu</xbar.title>
|
|
# <xbar.version>v1.0</xbar.version>
|
|
# <xbar.author>Erick Ruiz de Chavez</xbar.author>
|
|
# <xbar.desc>Simple toggle menu for Hubitat devices. Requires the Toggle API App.</xbar.desc>
|
|
# <xbar.dependencies>python</xbar.dependencies>
|
|
# <xbar.var>string(LIST_DEVICES_URL): List Devices URL. Provided by the Toggle API App.</xbar.var>
|
|
# <xbar.var>boolean(USE_INTERNAL_URL=true): Whether to be use the internal or external toggle URL.</xbar.var>
|
|
# <xbar.var>boolean(RUN_IN_TERMINAL=false): Whether to run the menu selections in a terminal window. (For debugging purposes).</xbar.var>
|
|
# <xbar.var>boolean(SHOW_ICON=true): Whether to show the menu icon on the taskbar.</xbar.var>
|
|
# <xbar.var>boolean(SHOW_TEXT=false): Whether to show the menu label on the taskbar.</xbar.var>
|
|
|
|
import json
|
|
import os
|
|
import sys
|
|
from urllib.request import urlopen
|
|
|
|
LIST_DEVICES_URL = os.getenv("LIST_DEVICES_URL")
|
|
USE_INTERNAL_URL = os.getenv("USE_INTERNAL_URL", "true") == "true"
|
|
RUN_IN_TERMINAL = os.getenv("RUN_IN_TERMINAL") == "true"
|
|
SHOW_ICON = os.getenv("SHOW_ICON") == "true"
|
|
SHOW_TEXT = os.getenv("SHOW_TEXT") == "true"
|
|
|
|
|
|
def log_run(function_name):
|
|
with open(".hubitat.log", mode="a", encoding="utf8") as file:
|
|
content = f"FUNCTION: {function_name} | ARGS: {', '.join(sys.argv)} | LIST_DEVICES_URL: {LIST_DEVICES_URL} | USE_INTERNAL_URL: {USE_INTERNAL_URL} | RUN_IN_TERMINAL: {RUN_IN_TERMINAL}\n"
|
|
file.write(content)
|
|
|
|
|
|
def get_devices(list_devices_url):
|
|
log_run("get_devices")
|
|
devices = []
|
|
with urlopen(list_devices_url) as response:
|
|
devices = json.loads(response.read().decode())
|
|
return devices
|
|
|
|
|
|
def toggle_device(device_url):
|
|
log_run("toggle_device")
|
|
urlopen(device_url)
|
|
return
|
|
|
|
|
|
def print_menu(items):
|
|
log_run("print_menu")
|
|
menu_icon = ":house:" if SHOW_ICON else ""
|
|
menu_label = "Hubitat" if SHOW_TEXT else ""
|
|
menu_space = " " if SHOW_ICON and SHOW_TEXT else ""
|
|
menu = menu_space.join([menu_icon, menu_label])
|
|
menus = []
|
|
menus.append(menu)
|
|
menus.append("---")
|
|
menus += items
|
|
|
|
print("\n".join(menus))
|
|
|
|
|
|
def print_devices_menu(devices, use_internal_url, run_in_terminal):
|
|
log_run("print_devices_menu")
|
|
|
|
items = []
|
|
for device in devices:
|
|
device_name = device["Name"]
|
|
device_url = (
|
|
device["InternalURL"] if use_internal_url else device["ExternalURL"]
|
|
)
|
|
script_path = os.path.realpath(__file__)
|
|
|
|
segments = []
|
|
segments.append(device_name)
|
|
segments.append(f'shell="{script_path}"')
|
|
segments.append(f'param1="{device_url}"')
|
|
if run_in_terminal:
|
|
segments.append("terminal=true")
|
|
|
|
items.append(" | ".join(segments))
|
|
|
|
items.sort()
|
|
|
|
print_menu(items=items)
|
|
|
|
|
|
def print_error_menu():
|
|
log_run("print_error_menu")
|
|
print_menu(
|
|
items=[
|
|
'List Devices URL variable is missing! Please select "Open plugin..." from xbar\'s menu to configure the plugin.'
|
|
]
|
|
)
|
|
|
|
|
|
def main():
|
|
log_run("main")
|
|
|
|
if len(sys.argv) > 1:
|
|
toggle_device(device_url=sys.argv[1])
|
|
return
|
|
|
|
if LIST_DEVICES_URL is None:
|
|
print_error_menu()
|
|
return
|
|
|
|
devices = get_devices(list_devices_url=LIST_DEVICES_URL)
|
|
|
|
print_devices_menu(
|
|
devices=devices,
|
|
use_internal_url=USE_INTERNAL_URL,
|
|
run_in_terminal=RUN_IN_TERMINAL,
|
|
)
|
|
|
|
|
|
if __name__ == "__main__":
|
|
main()
|