用 YAML 写进阶自动化逻辑
什么时候该用 YAML
可视化编辑器能覆盖 80% 的日常场景,但碰到以下情况就得切到 YAML:
- 需要用 Jinja2 模板动态计算值
- 一个触发器触发后对多个实体循环执行
- 条件逻辑极其复杂(多层嵌套 OR/AND/NOT)
- 需要用自定义事件、MQTT 等非可视化触发器
切换方法:编辑器右上角 → 菜单 → Edit in YAML。
YAML 自动化的完整结构
alias: "日落开客厅灯"
description: "日落时打开客厅主灯,亮度 60%"
trigger:
- platform: sun
event: sunset
offset: "-00:10:00"
condition:
- condition: state
entity_id: person.me
state: home
action:
- service: light.turn_on
target:
entity_id: light.living_room
data:
brightness_pct: 60
mode: single
每个字段对应:
| 字段 | 含义 | 必填 |
|---|---|---|
alias | 自动化名称 | ✅ |
description | 描述 | ❌ |
trigger | 触发器 | ✅(至少一个) |
condition | 条件 | ❌ |
action | 动作 | ✅(至少一个) |
mode | 执行模式 | ❌(默认 single) |
用模板做动态计算
YAML 里可以嵌入 Jinja2 模板来动态计算值。模板用 {{ }} 包裹:
场景:根据日出时间自动开窗帘
alias: 起床自动开窗帘
trigger:
- platform: time
at: "07:00:00"
action:
- service: cover.open_cover
target:
entity_id: cover.bedroom_window
- service: light.turn_on
target:
entity_id: light.bedroom
data:
# 根据当前日出时间动态计算亮度
brightness_pct: "{{ [100, 50 + (now() - state_attr('sun.sun', 'next_rising')).total_seconds() / 3600 * 10] | min | int }}"
场景:把触发传感器的状态值放进通知
alias: 温度过高推送
trigger:
- platform: numeric_state
entity_id: sensor.kitchen_temperature
above: 30
for:
minutes: 3
action:
- service: notify.mobile_app_me
data:
title: "厨房高温提醒"
message: >
厨房温度已达 {{ trigger.to_state.state }}°C
触发时间:{{ now().strftime('%H:%M') }}
场景:动态获取一组实体
action:
- service: light.turn_on
target:
entity_id: "{{ states.light | selectattr('state', 'equalto', 'off') | map(attribute='entity_id') | list }}"
上面这个模板获取所有当前状态为 off 的 light 实体。
变量(Variables)
自动化的 variables 字段可以定义可复用的变量:
alias: 夜间走廊灯
trigger:
- platform: state
entity_id: binary_sensor.motion_corridor
to: "on"
variables:
# 定义一个变量,之后可以复用
motion_sensor: "{{ trigger.entity_id }}"
light_target: "light.corridor"
action:
- service: light.turn_on
target:
entity_id: "{{ light_target }}"
- delay:
minutes: 2
- service: light.turn_off
target:
entity_id: "{{ light_target }}"
Choose / If / While 高级流程
Choose(多路分支)
action:
- choose:
- conditions:
- condition: numeric_state
entity_id: sensor.temperature
above: 30
sequence:
- service: climate.set_temperature
target:
entity_id: climate.living_room
data:
temperature: 24
- conditions:
- condition: numeric_state
entity_id: sensor.temperature
below: 18
sequence:
- service: climate.set_temperature
target:
entity_id: climate.living_room
data:
temperature: 22
default:
- service: notify.mobile_app_me
data:
message: 温度正常
If / Then / Else(单路判断)
action:
- if:
condition: state
entity_id: person.me
state: home
then:
- service: light.turn_on
target:
entity_id: light.living_room
else:
- service: light.turn_off
target:
entity_id: group.all_lights
Repeat(循环)
action:
- repeat:
count: 3
sequence:
- service: notify.mobile_app_me
data:
message: >
第 {{ repeat.index }} 次提醒
- delay:
seconds: 10
保存与验证
写好 YAML 后点编辑器右上角 Save。Home Assistant 会先做语法校验——如果 YAML 格式错了会直接拒绝保存。如果报模板语法错误,可以先用 Developer Tools → Template 工具单独测试模板表达式。
也可以直接编辑 config/automations.yaml 文件,然后在 Settings → Automations & scenes → 右上角菜单 → Reload automations 让改动生效(不需要重启)。
YAML 缩进——最常见的坑
YAML 对缩进极其敏感。规则:
- 用空格缩进(2 个或 4 个都可以,但必须一致)
- 不要用 Tab——Home Assistant 会报错
trigger:下面的触发器列表用- platform:起始的列表项- 模板字符串里的换行要用
>或|保留
保存前建议先过一遍:Developer Tools → Check Config → Configuration validation。