How to start using Pyscript
Pyscript - how to use it to run a python script?
PyScript: Why isn't everyone using it already?
Guidance for First pyscript
I initially worked with YAML and native automations, only to find they were challenging to scale and decipher. I tried NodeRed as an alternative; while it was a step forward, the necessity to duplicate similar logic via copied nodes was tedious. Additionally, it didn't gel well with version control due to its source files not being human-readable.
However, my discovery of PyScript a few months ago transformed my approach. As a software engineer, I find using Python for all my automation needs appealing. It empowers me to create intricate, reusable functions and the process of coding automation logic becomes enjoyable, to a large extent!
Let's delve into a couple of examples.
Example 1: Code Shared by Bathrooms
Every bathroom in my home shares a set of logic:
-
Motion detection: Trigger lights.
-
Door closure: Activate lights and fan.
-
Door opening: Switch off lights and fan.
-
Absence of motion with an open door: Lights out.
-
Absence of motion with a closed door: Lights out after 'X' minutes (where 'X' depends on the bathroom, e.g., upstairs bathrooms have a more extended timeout to accommodate showering).
Thanks to PyScript, I could devise a single BathroomTriggers class encapsulating this shared logic, then generate an instance of that class for each bathroom:
# FILE: entity_ids.py
class HalfBath:
AREA_ID = 'half_bathroom'
MOTION = 'binary_sensor.half_bathroom_motion_sensor_iaszone'
DOOR = 'binary_sensor.lk_zb_doorsensor_d0002_iaszone'
# ... other class definitions ...
# FILE: bathrooms.py
class BathTriggers:
def __init__(self, room, lightsOutDelayMins):
@motion_trigger(room.MOTION)
def motion_lights_on():
if is_open(room.DOOR) and input_select.sleepstatus != 'Sleeping':
light.turn_on(area_id=room.AREA_ID)
self.motion_lights_on = motion_lights_on
# ... other methods ...
# Invoke the shared trigger class for each bathroom:
halfBathTriggers = BathTriggers(HalfBath, lightsOutDelayMins=10)
basementBathTriggers = BathTriggers(BasementBath, lightsOutDelayMins=20)
upstairsBathTriggers = BathTriggers(UpstairsBath, lightsOutDelayMins=45)Example 2: Inovelli Switches
I use several Inovelli switches, which come with a customizable LED strip operable via Zigbee or Z-Wave. Although they're fantastic, the command to send the Zigbee LED signal is verbose and non-intuitive. To sidestep repeatedly issuing the command, I devised a straightforward LED control function:
def set_inovelli_switch_led(
device, color, brightness=255, effect=Effects.SOLID, duration=255):
'''Configures the light switch LED based on the specified parameters.'''
zha.issue_zigbee_cluster_command(
ieee=device_ieee,
endpoint_id=1,
command=1,
cluster_id=64561,
cluster_type='in',
command_type='server',
manufacturer=4655,
params={
'led_effect': effect,
'led_color': color,
'led_level': brightness,
'led_duration': duration})With this, modifying the switch LED becomes a breeze:
set_inovelli_switch_led('42:a2:f2:13:42', Colors.RED, effect=Effects.FAST_BLINK)
Moreover, I've integrated custom enums for Colors and Effects, which map to numeric codes, making it more intuitive (Colors.BLUE is more readable than 172!).
Why Persist with YAML?
Despite its remarkable features, I'm perplexed that PyScript isn't as mainstream as it could be. For those not yet using PyScript: Do you prefer YAML for your automations over Python? Or is there some other factor discouraging your transition to PyScript? I'd love to hear your thoughts!
If you aren't using pyscript already, you probably should be.
It installs as a custom component and makes writing automations that would normally take several different automations and many lines of template code and "choose" actions quite easy with just a little Python.
It's similar to AppDaemon in that you're writing your Automations in Python. However, it doesn't require a separate process, an API Key, or any YAML if you don't want it to.
The syntax is quite simple and Craig has crafted it so that variable names are what you'd expect in Home Assistant. For instance, want to turn on a light when motion is detected?
if binary_sensor.motion == 'on': light.turn_on(entity_id="light.overhead")
It also has quite a few advanced features -- like packaging code into an "app" to be used by others with just a little YAML to configure it. So, if you make something useful (like my conditional average app) you can share it and no one else ever has to write that code again. In a way, it's like the "Apps" that SmartThings has, only in Python, and specifically for Home Assistant.
Give it a shot. And if you get stuck on something, I'm happy to help.
Inside the pyscript folder, I created a python script named test.py -> This python script read a JSON file from a particular path. Now I want to use this python script as a service, so that front-end can use it. How can I do that? Read the document but found nothing there.