🌅 Wake Alarm 0.5.0
Inspired by lots of great comments and ideas this is the biggest release I've shipped for Wake Alarm - more robust and some great new features. It now wakes you the way you want — a silent sunrise, a music-only alarm, or both; gated on whatever makes sense (presence, a bed sensor, a workday, link your own); with your own scripts woven in. And under the hood I gave it a load of reliability checks so the alarm always goes off (I hope!!).
✨ Highlights
- 🔦 Lights-only or 🎵 music-only Media players are now optional. Configure just lights for a silent sunrise, just speakers for a music alarm, or both. (#22)
- ⏰ Three script hooks, including a new "at alarm" one. Run your own automations before the light ramp starts, exactly at the alarm time (the new hook — coffee on, TTS greeting, blinds), and after (music ends / dismiss). All fire non-blocking, so a slow script never delays your wake-up. (#24)
- 🛏️ Condition-sensor gate. Only sound the alarm when a
binary_sensoris on — a bed sensor (only if you're actually in bed) or Home Assistant's Workday sensor (skip bank holidays). ANDs with presence. (#23) - 🎲 No more "same song every morning." A single speaker now shuffles and skips a random 1–4 tracks (silently, before the fade).
- 🛡️ Music and lights separated so the alarm always fires. Music now runs on its own independent timer — nothing in the light phase can stop it — plus restart catch-up if HA was down, and pinned DST behaviour.
- 🔎 Easier troubleshooting. Opt-in debug logging that prints a clean timeline, and a one-click Download diagnostics snapshot for bug reports.
🎁 Nice touches
- At-alarm precision — the new hook fires the instant the music starts (or the fire moment for a lights-only alarm), so "do X the moment I'm woken" finally has a home.
- Auto-dismiss is honoured even mid-snooze — a long snooze can't outlive your "stop after N minutes" setting.
- Friendlier card — clearer settings copy (auto-dismiss now says it counts from the music start), a dedicated Notifications section, and graceful UI when there's no speaker.
- Tested for real — the whole state machine runs against a real Home Assistant core with a frozen clock, so "does the alarm actually fire?" is a CI gate.
⬆️ Upgrading
Should be seamless. Your config entry migrates automatically (v2 → v5, all no-op steps) — nothing to re-toggle, and your lights/speakers/presence/notification settings and media selection are all preserved. Minimum Home Assistant: 2024.6.
🙏 Thanks
To be honest I wrote this for me so great to have community feedback. Thanks to everyone whose issues, enhancement requests, and forum feedback drove it. Most of what's here came straight from ideas and bug reports. 🙌
I built it with a big assist from Claude Code as an AI pair-programmer.
📋 Full changelog (appendix)
Added
- Media player is optional — lights-only or music-only alarms (#22). Pick at least one of lights / media players. With no speaker, the alarm runs the light ramp + standard notification and settles (urgent "speaker unavailable"/"no media" notices suppressed; snooze and auto-dismiss are music-only).
- Condition-sensor gate (#23). Optional
binary_sensorgate (bed sensor, Workday, etc.), checked at ramp-start and again at alarm time, ANDed with presence. - Before / at-alarm / after script hooks (#24). Three optional
script.*targets: before at ramp start (Lengthmin before the alarm), at-alarm exactly at the alarm time (music start, or the fire moment for lights-only), after at music end / dismiss / auto-dismiss (not on snooze). All non-blocking; receiveslug+nameas variables. - Restart catch-up. If HA is down across the alarm but boots back within the grace window (default 15 min), the alarm fires immediately on startup (music only); beyond that it rolls forward.
- Troubleshooting: debug logging + diagnostics. DEBUG logs across the scheduler/state machine, plus a config-entry Download diagnostics snapshot (person/notify targets redacted) showing the live schedule, state flags, and armed timers/tasks.
Changed
- Music is scheduled independently of the light ramp. Two separate timers (light ramp at
alarm_time − length, authoritative music atalarm_time); a failure anywhere in the light phase can no longer stop the alarm sounding. - Presence is re-checked at alarm time — gates lights (ramp start) and music (alarm time) independently.
- Single-player music now shuffles + random-skips like the Sonos group path, so the wake-up song varies; degrades gracefully on players without shuffle/next-track.
- The card hides music-only controls for a lights-only alarm (#46).
- A player failing mid-sequence no longer aborts the alarm (#45).
Fixed
- Unload/reload teardown race (#48) — a cancelled music task could re-arm timers and fire the after-script after teardown; teardown is now inert to those paths.
- Snooze during the ramp resumed ungrouped (#48) — now does a full music (re)start unless music was actually playing when snoozed.
- Card stuck on a transient resolve error (#48) — now retries (bounded) as the integration finishes loading.
- Mid-occurrence interference (#43, #44) — settings changes mid-fire are deferred so they can't double-fire; test buttons refused during the ramp→alarm gap.
- Auto-dismiss now fires during a snooze (#38); background tasks tracked + cancelled on unload (#35).
- Stranded alarm cycle when disabled during the ramp→alarm gap (#34).
- DST gap / fall-back alarm-time semantics pinned (#36).
- Card registration hardening (#19, #20, #37) — async version read, route claimed before await, executor
is_file(), and signed Music Assistant artwork URLs. - Ramp no longer restarts from zero when it finishes seconds before the alarm.
Migration
Config entry v2 → v5 (condition gate, before/after hooks, at-alarm hook) — all additive no-ops; nothing to re-toggle.
Tests / CI
HA-backed coordinator tests with a frozen clock; config_flow + migration suites (#39, #40); coverage reporting; min/latest HA matrix; HACS + hassfest validation.