Home Intercom — Push-to-Talk PWA for Any Smart Speaker via Home Assistant

What it does

Turns your phone into a home intercom. Hold a button on a PWA, say something, and it plays on your smart speakers — one room or the whole house.

The built-in broadcast on smart speakers? “Hey Google/Alexa” → wait → “broadcast” → wait → speak your message. Three steps, inconsistent results, and half the time it fails silently. No TTS typing. No fumbling with voice assistants. Just push, talk, release, done.

Demo

  • :green_circle: Each room gets a card with a big round PTT button. Hold to record, release to play.
  • :loudspeaker: The “Broadcast All” card at the top sends to every room at once.
  • :green_circle:/:black_circle: Each room has a live online indicator — green dot means the speaker is reachable via HA.
  • Recording: button turns green with ripple animation + bouncing sound bars.
  • Sending: green spinner ring around the button.
  • Sent: big green checkmark.
  • :globe_with_meridians: i18n: Chinese / English toggle in the top-right corner.

Architecture

Phone PWA → HA Native Integration → Home Assistant API → your speakers
                  ↕
      configuration.yaml / UI Config
   (or Docker standalone — still supported)

v2.0.0+ runs natively inside Home Assistant — zero extra containers. Just drop it into custom_components/, configure via the UI (or YAML), done.

For Docker users: Flask + waitress handles audio receive → PCM → WAV, calls HA REST API directly. No ffmpeg (131MB image), no n8n, no SSH. Broadcast-all fires parallel play_media calls — fire and forget.

Quick Start

HA Integration (recommended · v2.0.0+)

Install (HACS or manual)

HACS: Add custom repository https://github.com/mdj2812/home-intercom → search “Home Intercom” → install.

Manual:

cd /config/custom_components
curl -LO https://github.com/mdj2812/home-intercom/releases/latest/download/home_intercom.zip
unzip -o home_intercom.zip -d home_intercom && rm home_intercom.zip
ha core restart

Configure

Settings → Devices & Services → Add Integration → search “Home Intercom” → pick area & media player → done.

Existing configuration.yaml rooms are auto-imported — no manual migration needed.

Add to sidebar

Create a dashboard → Add Webpage card → URL: /home_intercom.

Docker (legacy, fully supported)

git clone https://github.com/mdj2812/home-intercom.git
cd home-intercom
cat > docker/.env << EOF
HA_URL=http://192.168.1.10:8123
HA_TOKEN=your_ha_long_lived_token
EOF
export IMAGE=ghcr.io/mdj2812/home-intercom:v2.0.0
docker compose -f docker/docker-compose.example.yml up -d

HTTPS is required for microphone access — use Caddy or Nginx reverse proxy.

Tech Stack

Item Detail
Integration Native HA custom_component (Config Flow + Options Flow + Device Registry) or Flask + waitress
Audio pipeline MediaRecorder opus → decodeAudioData → resample 16kHz → pure Python WAV
Image size 131 MB (zero external dependencies, Docker mode)
Tests 127 pytest tests, 92% coverage
CI/CD GitHub Actions — tag push → build → push to ghcr.io + release ZIP
i18n Chinese / English, localStorage persistence, room names translate
HACS Custom repository, hassfest + hacs/action validated

Works With

Any HA media_player entity that supports play_media. Tested daily with Xiaomi smart speakers, but it’ll work with Google Nest, Sonos, or anything HA can send audio to.

Links


Star it if you find it useful. Happy to answer setup questions in the thread!


ESP32 Physical Button — now open source

No phone needed. Press the button, speak, broadcast to all your smart speakers.


Changelog

v2.0.0 (2026-07-16) — Stable Release

  • Native HA Integration: Runs directly inside Home Assistant. Config Flow (UI room setup), Options Flow (UI manage rooms), Device Registry (auto-link to Areas).
  • Dual Config Entry: YAML + UI coexist, auto-merge with UI precedence.
  • PWA Auth Fix: Shared secret token works reliably in Companion App WebView.
  • Xiaomi Screen Fix: Clears display metadata after announcements.
  • HTTP Security Warning: Detects insecure origins, disables buttons with helpful message (#42, #45).
  • Three-tier Playback: Music Assistant → repeat_set(off) → timed pause — auto-selects per speaker.

Docker: ghcr.io/mdj2812/home-intercom:v2.0.0
HACS: Add custom repository, one-click install.

Thanks to @ngocjohn for testing and suggestions!

v1.6.3: Device names on room cards, offline speaker buttons auto-disabled, STATE_TIMEOUT for slow Bluetooth/MA devices, UI overhaul.

v1.6.2: Doorbell chime before announcements. MA players native, standard players get it baked into WAV. Per-room announce volume, greyed-out unavailable speakers.

v1.6.1: Three-tier auto-stop. MA play_announcement → HomePod/Chromecast repeat_set(off) → Xiaomi PAUSE_BUFFER timer.

Great, this is exactly what I've been missing since switching from iOS to Android. I can confirm that the intercom works with HomePod via the Music Assistant player (AirPlay provider).

I'm just not sure if this is a bug or if it's intentional. It seems to me that the audio stops too early, specifically, about 1 sec before the end of the recording. Here's the container log

[intercom] WAV written: intercom_office.wav (288044B, 9.0s, 16000Hz)
[intercom] played on 0/1 rooms for Office
[intercom] media_player.office playing confirmed (attempt 1)
[intercom] media_player.office elapsed 0.0s, sleeping 9.0s
[intercom] media_player.office paused (attempt 1)
[intercom] WAV written: intercom_office.wav (257324B, 8.0s, 16000Hz)
[intercom] played on 0/1 rooms for Office
[intercom] media_player.office playing confirmed (attempt 1)
[intercom] media_player.office elapsed 0.0s, sleeping 8.0s
[intercom] media_player.office paused (attempt 1)
[intercom] WAV written: intercom_office.wav (270764B, 8.5s, 16000Hz)
[intercom] played on 0/1 rooms for Office
[intercom] media_player.office playing confirmed (attempt 1)
[intercom] media_player.office elapsed 0.1s, sleeping 8.3s
[intercom] media_player.office paused (attempt 1)

If I send audio url from standard action call, the audio plays for its entire duration. Is it possible to set a delay for a pause?

First of all, thank you for trying! I have not tried with other brands other than Xiaomi's speakers. So which speaker were you using? The behaviour seems vary for different hardware. I am cobsidering to make the delay configurable via the docker variable. I will let you know once that is ready.
Or if possible, please share more details by raising an issue on Github. Appreciate it.

The speaker is HomePod device, added to Music Assistant addon, media_player entity exposed from Music Assistant integration. gh issue created

The potential fix is ready, please follow this: Intercom audio cuts off before playback finishes · Issue #1 · mdj2812/home-intercom · GitHub.
The explicit pause was needed, otherwise my Xiaomi speaker will play the record in loop, non stop. I am still seeking a more elegant way to solve such issue.

I just realized that in your case, this explicit pause may not be needed, because in Music Assistant, there should be no undesired loop issue. I will make this "explicit pause" an optional feature, only enable it if needed.

PR ready: fix: add PAUSE_BUFFER env to prevent early audio cutoff by mdj2812 · Pull Request #2 · mdj2812/home-intercom · GitHub. Waiting for your testing result. :crossed_fingers:

I can’t wait for the add-on with custom cards to be released. For now, I have to use the iframe card. :roll_eyes:

CleanShot 2026-07-10 at 22.00.57

Please follow this milestone: GitHub · Where software is built. I will try to deliver it next week.

In parallel, I did not pay much attention to the UI. So, I am doing some redesign. @VietNgoc Could you please try with this image: Package home-intercom · GitHub. And provide your feedback here. Here is a preview:

Hi, I can’t seem to load THEME=nothing. But I like the current UI. It’s simple and practical.

Maybe I’d just move the “All” button to the end. I rarely send message to all devices at once.

services:
  intercom:
    image: ghcr.io/mdj2812/home-intercom:v1.6.3
    container_name: home-intercom
    restart: unless-stopped
    volumes:
      # Audio files served by Flask (no SCP)
      - ./audio:/data/audio
      # rooms.json editable without rebuild
      - ../src/rooms.json:/app/rooms.json:ro
    environment:
      - THEME=nothing
      - HA_URL=http://192.168.1.189:8123

@VietNgoc v2.0.0-rc1 is ready to be tested. As it is a pre-release, you will need to install manually:

cd /config/custom_components
curl -L https://github.com/mdj2812/home-intercom/releases/download/v2.0.0-rc1/home_intercom.zip
unzip -o home_intercom.zip && rm home_intercom.zip
ha core restart

And please follow the instruction here to configure it via configuration.yaml.
Do not hesitate to let me know here or on github if you encounter any issue.