North Lanarkshire Council schedule, weekly Wednesday Green/Blue/Black rotation with alternating brown. 4 HA sensors, dedicated alert sensor avoids daily false-positive notifications, bell-curve schedule-expiry alerts.
Architecture-and-hardware-selection complete: 4× load cells + HX711 + ESP32, MR24BSD1 mmWave at headboard, dedicated Python state-machine container over MQTT, SQLite event log. ML informs changes the operator approves.
On the home-services VM (104) — IaC-provisioned, Mosquitto MQTT, host networking for LAN device discovery.
No automation tunes itself. Insights surface as suggestions; the operator changes thresholds manually if they agree.
Why this layer matters
Without the personal layer, the homelab is just infrastructure for its own sake.
The infrastructure is interesting. The platform is satisfying to build. But none of it pays its rent unless it actually does something for the household. The personal project line is where the homelab proves it earns its keep.
The discipline is consistent across every automation here: nothing depends on a SaaS, nothing depends on a cloud, everything is owned end-to-end, every signal that drives a decision is captured locally and stored locally. If the broadband drops, the bins still get notified. If a vendor pivots, the heating still works. The bar for adding a new automation is that it has to survive a permanent disconnection from the internet.
Bin Collection — the first real workload
Trivial-sounding, surprisingly intricate. The story of how a 'just send me a notification' task became a four-sensor state machine.
The North Lanarkshire Council bin schedule is a colour-coded calendar PDF — Wednesday collection, three-week green / blue / black rotation, brown bin every other week. Easy to read; surprisingly fiddly to automate without producing false-positive notifications six days a week.
The shape that landed:
schedule.jsonwith metadata (address, confirmed-from / confirmed-until dates, rotation rules) and an array of confirmed dates. When today goes pastconfirmed_until, a projection layer continues the rotation forward up to 90 days, prefixing output with(PROJECTED)so the source of truth stays obvious.check_bins.shas the dashboard sensor — always shows the next collection with a countdown.check_tomorrow.shas the notification sensor — returns “none” six days a week and only returns bin names when tomorrow is collection day. This split was the key fix: previously the dashboard sensor was used for both display and notification, which fired every day.check_schedule_expiry.shfor the bell-curve reminder — fires notifications at ±28, ±14, ±7, ±3, and 0 days relative toconfirmed_untilso the schedule never silently lapses.check_address.shso the dashboard card shows the property the schedule belongs to (useful when the schedule changes after moving house).
All four sensors are HA command_line sensors with sensible scan_intervals. All deployed via Ansible — the files live on iaccn01, the playbook copies them into the HA container’s /config/bin-schedule/ mount. Pushing a new schedule is cat > schedule.json && ansible-playbook home-services.yml.
There’s also a separate Bin.Watch React portal built for the design exercise — iCal parsing, monthly calendar, alerts cross-referenced against Open-Meteo weather forecasts, configurable bin colour mapping. That’s the “could I rebuild the entire UX of bin tracking from scratch as a proper PWA” version; the HA implementation is the one that actually wakes me up on a Tuesday.
Smart Sleep System — sensor stack settled, build pending
Architecture done, hardware selection done, components not yet purchased. Captured here so the design intent doesn't drift before assembly.
The system has three jobs: detect that I’m in bed and asleep, run a wake sequence aligned to 90-minute cycles with weekday / weekend / OOO / sick logic, and never falsely wake me at 04:00 because someone moved the duvet.
The sensor stack is the bit that took the most iteration. Resistive force sensors were rejected (drift under sustained static load). Under-mattress pads were rejected (8Sleep pod cover muddies the signal). The settled answer is layered:
- 4× load cells under the bed legs, HX711 ADC, ESP32 running ESPHome. Layer-independent — the 8Sleep, topper, sheets, duvet are all irrelevant. Strain gauges are industrially proven for long-term static load. Gives weight delta plus centre-of-mass for posture inference.
- Seeed MR24BSD1 mmWave at headboard height for localised head-present and breathing confirmation.
- Wider mmWave under the bed frame (LD2410B class) for whole-body micro-movement and restlessness signals.
The brain isn’t a stack of HA automations; it’s a dedicated Python container publishing and subscribing over MQTT, with a real state machine (SLEEPING → ALARMING → DISMISSED → CONFIRMED_AWAKE, plus SNOOZED, BRIEF_WAKE, COUCH_SLEEP, PUSH_TO_11, AWAY branches). Every event lands in a SQLite log so the same data feeds health analytics downstream.
Future integrations subscribe to the same MQTT topics: smart blinds, smart TRVs for room-level heating, a future Grafana / React health dashboard reading the event log. The brain doesn’t change when peripherals are added.
The operator principle is non-negotiable: ML can surface “you slept 6h on average this week, your wake threshold is high relative to that” — but it cannot autonomously change the threshold. Suggestions in a sidebar; tuning by hand.
Personal-project chronology
- April 2026
Home Assistant up on the IaC pipeline
home-services VM 104 stood up via Terraform + Ansible. HA container on host networking, Mosquitto MQTT broker. The platform that everything personal hangs off. - April 2026
Bin Collection v1
Schedule JSON, four command-line sensors, projection layer, bell-curve schedule-expiry notifications, dedicated alert sensor pattern. - April 2026
Bin.Watch React portal
Parallel build exploring the design exercise of "what does bin tracking look like as a real PWA". Calendar view, weather-cross-referenced alerts, configurable colour mapping. Useful design system reference; HA is still the production path. - April 2026
Smart Sleep System architecture v1
Sensor stack settled (4× load cells + headboard mmWave + bed-frame mmWave), Python state-machine container chosen over HA automations, MQTT topic structure designed, future integrations (blinds, climate) mapped to the same event bus. - Next
Sleep system hardware procurement
Load cells + HX711 + ESP32 (~£25 total) + MR24BSD1 + LD2410B. Bench-build first, then bedroom install. - Future
Smart TRVs + boiler relay for per-room climate
Zigbee TRVs (Sonoff TRVZB class) on each radiator, Shelly relay on the boiler. HA → MQTT events from the sleep system drive bedroom cool-down at pre-sleep and warm-up before wake. - Future
Health analytics dashboard
Grafana or custom React over the SQLite event log. Sleep duration heatmap, bedtime drift, restlessness over time. The point of capturing every event from day one.