Home Assistant¶
Home automation hub for the homelab. Runs in the home namespace alongside its supporting stack — Mosquitto (MQTT broker), Node-RED (flow automation), ESPHome (device firmware), and Ring MQTT (Ring device bridge).
- URL — ha.hdhomelab.com
- Node-RED — nodered.hdhomelab.com
- ESPHome — esphome.hdhomelab.com
- Namespace —
home
Architecture¶
graph LR
subgraph home["Namespace: home"]
HA[Home Assistant\nport 8123]
NR[Node-RED\nport 1880]
MQ[Mosquitto\nport 1883]
ESP[ESPHome\nport 6052]
RM[Ring MQTT\nport 55123]
end
DEVICES[IoT Devices\nESPHome firmware] -->|MQTT| MQ
RING[Ring Doorbell\n& Cameras] -->|MQTT bridge| RM
SLZB[SMLIGHT SLZB-06U\nZigbee coordinator]
RM -->|MQTT| MQ
MQ -->|topics| HA
NR -->|flows| HA
HA ~~~ ESP
SLZB -->|TCP socket\nZHA / EZSP| HA
Components¶
Home Assistant¶
The core automation hub. Manages all integrations, automations, and dashboards.
| Setting | Value |
|---|---|
| Image | homeassistant/home-assistant (Flux image policy) |
| Port | 8123 |
| Memory | 1–4 Gi |
| Strategy | Recreate (safe for single-replica stateful apps) |
| Storage | homeassistant PVC — 50Gi local-path on worker-0b (hourly rsync backup to NFS) |
| Networking | Ingress at ha.hdhomelab.com (cert-manager TLS) |
Mosquitto¶
MQTT broker. All IoT devices and bridges publish and subscribe through it.
| Setting | Value |
|---|---|
| Image | eclipse-mosquitto (Flux image policy) |
| Ports | 1883 (MQTT) · 9001 (WebSocket) |
| Memory | 128–256 Mi |
| LoadBalancer IP | 192.168.71.243 (Cilium L2) |
| Storage | mosquitto PVC — 1Gi NFS (data/, config/, log/ subPaths) |
| HTTPRoute | mqtt.hdhomelab.com → port 9001 |
Note
Mosquitto gets a dedicated LoadBalancer IP (192.168.71.243) so MQTT clients on the LAN can reach it directly on port 1883 without going through the HTTP gateway.
Node-RED¶
Low-code flow automation. Connects to Home Assistant via the HA integration node and can trigger automations, read states, and react to events.
| Setting | Value |
|---|---|
| Image | nodered/node-red (Flux image policy) |
| Port | 1880 |
| Memory | 1–2 Gi |
| Storage | nodered PVC — 1Gi NFS |
| Networking | Ingress at nodered.hdhomelab.com (cert-manager TLS) |
ESPHome¶
Compiles and manages firmware for ESP8266/ESP32 microcontrollers. Devices flashed with ESPHome report their state to Home Assistant via native API or MQTT.
| Setting | Value |
|---|---|
| Image | esphome/esphome (Flux image policy) |
| Port | 6052 |
| Memory | 256Mi–2Gi |
| Storage | esphome-data PVC — 512Mi NFS |
| Networking | Ingress at esphome.hdhomelab.com (cert-manager TLS) |
Zigbee (ZHA + SMLIGHT SLZB-06U)¶
Zigbee devices are managed through the built-in ZHA (Zigbee Home Automation) integration. The coordinator is an SMLIGHT SLZB-06U, connected to Home Assistant over the LAN via a TCP socket — no USB passthrough or node pinning required.
| Setting | Value |
|---|---|
| Coordinator | SMLIGHT SLZB-06U |
| Radio type | EZSP (Silicon Labs EFR32) |
| Connection | socket:// TCP — network-attached |
| TCP port | 6638 |
| ZHA database | /config/zigbee.db (in the homeassistant NFS PVC) |
Adding Zigbee devices
Settings → Devices & Services → Zigbee Home Automation → Add device. Put the device in pairing mode before clicking.
No manifest changes needed
Because the coordinator connects over TCP, the HA pod requires no hostPath volume, securityContext: privileged, or nodeSelector. The Cilium policy for the home namespace has no egress restrictions, so the pod reaches the coordinator freely.
Ring MQTT¶
Bridges Ring devices (doorbell, cameras) into the MQTT ecosystem so Home Assistant can consume them like any other MQTT device. Connects to the Mosquitto broker internally.
| Setting | Value |
|---|---|
| Image | tsightler/ring-mqtt (Flux image policy) |
| Ports | 8554 (RTSP) · 55123 (HTTP) |
| Memory | 128–256 Mi |
| Storage | ring-mqtt PVC — 128Mi NFS |
Storage¶
| PVC | Size | Storage class | Notes |
|---|---|---|---|
homeassistant |
50Gi | local-path on worker-0b |
Primary config — fast local I/O for SQLite |
homeassistant-config-backup |
50Gi | syno-nfs-retain |
Hourly rsync backup via CronJob |
nodered |
1Gi | syno-nfs-retain |
/volume2/homelab/k8s/pvc-nodered |
mosquitto |
1Gi | syno-nfs-retain |
/volume2/homelab/k8s/pvc-mosquitto |
ring-mqtt |
128Mi | syno-nfs-retain |
/volume2/homelab/k8s/pvc-ring-mqtt |
esphome-data |
512Mi | syno-nfs-retain |
/volume2/homelab/k8s/pvc-esphome |
The HA config PVC uses local-path to avoid SQLite-over-NFS sluggishness. See SQLite on Local Path for the backup pattern.
See Storage for storage class details.
Configuration Management¶
The HA config lives on a local-path PVC (node-local, not network-accessible). A SSH sidecar in the HA pod exposes the volume over SSH, and Mutagen syncs it live to the developer machine — no macFUSE or kernel extensions needed.
graph LR
DEV["Mac\n~/mnt/ha-config"]
MUTAGEN["Mutagen"]
PF["kubectl port-forward\n:2222"]
SSH["SSH sidecar\nalpine + openssh"]
PVC["local-path PVC\n/config"]
HA["Home Assistant\n/config"]
GIT["Gitea"]
DEV <-->|"live sync"| MUTAGEN
MUTAGEN <-->|SSH| PF
PF <-->|port-forward| SSH
SSH <--> PVC
HA <--> PVC
DEV -->|"git push"| GIT
~/repos/dotfiles/scripts/ha-mount.sh start # live sync on
~/repos/dotfiles/scripts/ha-mount.sh stop # live sync off
See Local-Path SSH Sidecar pattern for full setup details.
Structure¶
Dashboards are YAML-mode Lovelace configs split into per-view files using !include:
dashboards/
├── monitoring.yaml # view registry (!include list)
├── control.yaml
└── monitoring/
├── view_overview.yaml
├── view_climate.yaml
├── view_batteries.yaml # battery health dashboard
└── view_plants.yaml
monitoring.yaml assembles views at runtime:
views:
- !include monitoring/view_overview.yaml
- !include monitoring/view_climate.yaml
- !include monitoring/view_batteries.yaml
Dashboards are registered in configuration.yaml:
Automations are split into per-feature files under automations/. HA merges them all at load time:
automations/
├── lights.yaml
├── door_hvac.yaml
├── garage_door_notification.yaml
├── temperature_warning.yaml
├── battery_notification.yaml # low battery alerts
└── ...
Each file is a YAML list of automation objects:
- id: battery_low_notification
alias: Low Battery Notification
triggers:
- trigger: numeric_state
entity_id:
- sensor.motion_detector_battery
...
actions:
- action: notify.mobiles
data:
message: "{{ trigger.to_state.name }} battery is at {{ trigger.to_state.state | int }}%."
Workflow¶
| Change type | Apply with | Restart? |
|---|---|---|
| Dashboard view | Browser hard-refresh (Cmd+Shift+R) |
No |
| Automation | hass-cli service call automation.reload |
No |
| Scripts / Scenes | hass-cli service call script.reload |
No |
configuration.yaml |
ha core restart |
Yes |
# Start live sync, edit files, reload HA, commit
~/repos/dotfiles/scripts/ha-mount.sh start
hass-cli service call automation.reload
cd ~/mnt/ha-config
git add automations/my_automation.yaml
git commit -m "feat(ha): add my automation"
git push
MCP Integration¶
Two MCP servers expose Home Assistant to Claude Code, configured in homelab/.mcp.json.
Home Assistant's built-in /api/mcp endpoint — lightweight, no local process.
"ha": {
"type": "http",
"url": "https://ha.hdhomelab.com/api/mcp",
"headers": {
"Authorization": "Bearer ${HASS_TOKEN}"
}
}
HASS_TOKEN must be set in the shell before Claude Code starts. Token is stored in the macOS keychain under service ha-token.
Full-featured local Python MCP server with 86 tools — automations, dashboards, HACS, backups, device registry, history, and more.
The wrapper script reads the token from the macOS keychain and runs uvx --python 3.13 ha-mcp. Python 3.13 is pinned because ha-mcp requires >=3.13,<3.14.
Source: homeassistant-ai/ha-mcp
When to use which
Use the native endpoint for simple state reads and service calls. Use ha-mcp when you need automation CRUD, dashboard editing, HACS management, or device registry access.
Networking¶
Home Assistant and Node-RED use the Cilium Ingress controller (legacy Ingress resources with cert-manager TLS). Mosquitto's WebSocket endpoint is exposed via Gateway API HTTPRoute. See Networking for details.
| Service | Exposure | Host |
|---|---|---|
| Home Assistant | Ingress | ha.hdhomelab.com |
| Node-RED | Ingress | nodered.hdhomelab.com |
| ESPHome | Ingress | esphome.hdhomelab.com |
| Mosquitto (MQTT) | LoadBalancer 192.168.71.243 |
— |
| Mosquitto (WS) | HTTPRoute | mqtt.hdhomelab.com |