aw_watcher_window/macos_jxa.py
import os
import json
import logging
from typing import Dict
logger = logging.getLogger(__name__)
script = None
def compileScript():
"""
Compiles the JXA script and caches the result.
Resources:
- https://stackoverflow.com/questions/44209057/how-can-i-run-jxa-from-swift
- https://stackoverflow.com/questions/16065162/calling-applescript-from-python-without-using-osascript-or-appscript
"""
# use a global variable to cache the compiled script for performance
global script
if script:
return script
from OSAKit import OSAScript, OSALanguage
scriptPath = os.path.join(
os.path.dirname(os.path.realpath(__file__)), "printAppStatus.jxa"
)
with open(scriptPath) as f:
scriptContents = f.read()
# remove shebang line
if scriptContents.split("\n")[0].startswith("#"):
scriptContents = "\n".join(scriptContents.split("\n")[1:])
script = OSAScript.alloc().initWithSource_language_(
scriptContents, OSALanguage.languageForName_("JavaScript")
)
success, err = script.compileAndReturnError_(None)
# should only occur if jxa was modified incorrectly
if not success:
raise Exception(f"error compiling jxa script: {err['NSLocalizedDescription']}")
return script
def getInfo() -> Dict[str, str]:
script = compileScript()
result, err = script.executeAndReturnError_(None)
if err:
# error structure:
# {
# NSLocalizedDescription = "Error: Error: Can't get object.";
# NSLocalizedFailureReason = "Error: Error: Can't get object.";
# OSAScriptErrorBriefMessageKey = "Error: Error: Can't get object.";
# OSAScriptErrorMessageKey = "Error: Error: Can't get object.";
# OSAScriptErrorNumberKey = "-1728";
# OSAScriptErrorRangeKey = "NSRange: {0, 0}";
# }
raise Exception(f"jxa error: {err['NSLocalizedDescription']}")
return json.loads(result.stringValue())
if __name__ == "__main__":
print(getInfo())
print("Waiting 5 seconds...")
import time
time.sleep(5)
print(getInfo())