Turning a Raspberry Pi into a Bluetooth Speaker Receiver: A2DP Sink Setup with BlueALSA
Plenty of guides cover turning a Raspberry Pi into an AirPlay or Spotify Connect receiver, but the simplest and most universal option — a plain Bluetooth A2DP sink that any phone, tablet, or laptop can pair with directly, no app or subscription required — gets less attention despite being the easiest to set up and the most broadly compatible. This turns a Pi with a basic DAC HAT or even just its onboard headphone jack into a Bluetooth speaker receiver for an old stereo, a pair of powered speakers, or a whole-house amp, using the standard Linux Bluetooth stack and BlueALSA rather than any vendor-specific software.
Why BlueALSA Instead of PulseAudio's Bluetooth Module
Raspberry Pi OS can route Bluetooth audio through PulseAudio's built-in Bluetooth module, and on a desktop-oriented install with PulseAudio already running that's often the path of least resistance. But for a headless, dedicated-purpose speaker receiver, BlueALSA is the leaner choice: it talks to BlueZ (the Linux Bluetooth stack) directly and exposes Bluetooth audio as a standard ALSA device, without the overhead or occasional flakiness of running a full PulseAudio session just to move audio from a phone to a headphone jack. It's also the same underlying approach used by many commercial Bluetooth-receiver Pi images, so it's well trodden ground with predictable behavior.
Hardware
- Any Raspberry Pi with Bluetooth — Pi 3, 4, 5, Zero 2 W, or a Pi Zero W with a USB Bluetooth dongle if using an original Pi Zero
- An audio output: the onboard 3.5mm jack for casual use, or a proper I2S DAC HAT (PCM5102A-based boards are common and cheap) for meaningfully better sound quality — the built-in jack's PWM-based audio output has audible noise floor and limited dynamic range compared to even a basic I2S DAC
- A case with decent Bluetooth antenna clearance — metal enclosures noticeably reduce range if the Pi's PCB antenna is boxed in
Installing the Bluetooth Audio Stack
Starting from a fresh headless Raspberry Pi OS Lite install (see this site's guide to setting up a Raspberry Pi headless with SSH and WiFi if you haven't done initial setup), install the required packages:
sudo apt update sudo apt install -y bluez bluez-tools bluealsaSome Raspberry Pi OS releases ship bluealsa in the default repos; on others you may need to build it from source or pull it from a community repository, since BlueALSA isn't always kept current in the default Debian/Raspberry Pi OS package set. Check apt-cache policy bluealsa first — if it's missing, the project's GitHub README has current build instructions for Raspberry Pi OS.
Making the Pi Discoverable and Pairable by Default
A dedicated speaker receiver needs to be discoverable and auto-accept pairing without manual intervention every time, which stock bluetoothctl doesn't do out of the box. Create a simple agent script or use bt-agent from bluez-tools with a "NoInputNoOutput" pairing agent, and configure BlueZ to stay discoverable and pairable persistently by editing /etc/bluetooth/main.conf:
[General] DiscoverableTimeout = 0 PairableTimeout = 0 Class = 0x200414The Class value sets the reported Bluetooth device class so phones show it as an audio/speaker device in their pairing list rather than a generic unknown device, which meaningfully improves the pairing experience on iOS and Android.
Setting Up the A2DP Sink Profile
Enable the A2DP sink profile in BlueALSA's systemd service (most packaged versions default to source mode or need the sink profile explicitly enabled via a --profile=a2dp-sink flag in the service unit or a drop-in override), then start and enable both bluetooth and bluealsa services. With the sink profile active, route audio from the BlueALSA PCM device to your actual output using bluealsa-aplay, which continuously plays whatever audio is streamed to any paired A2DP source:
bluealsa-aplay --profile-a2dp 00:00:00:00:00:00Using the all-zeros MAC address tells bluealsa-aplay to accept audio from any connected device rather than a single paired MAC, which is what you want for a general-purpose receiver anyone in the house can pair with. Wrap this in a systemd service so it starts automatically on boot and restarts if a connection drops.
Improving Audio Quality
Bluetooth A2DP audio is compressed — most phones default to SBC (the mandatory baseline codec), with better codecs like AAC or aptX available if both the source device and the Pi's Bluetooth stack support them. BlueZ's SBC implementation quality and available codec negotiation can vary by kernel and firmware version, so if audio sounds noticeably worse than the source material, check whether a newer BlueZ version with better codec support is available, and confirm you're actually running through an I2S DAC rather than the Pi's onboard PWM audio output, which is the more common source of audible quality loss in practice.
Auto-Reconnect and Multi-Room Considerations
For a fixed installation (living room stereo, garage speaker), it's worth setting up a systemd service that keeps bluealsa-aplay running persistently and a udev or bluetoothctl trust policy that lets previously-paired phones reconnect automatically without a fresh pairing prompt each time. If you want genuinely synchronized multi-room audio rather than a single independent Bluetooth receiver per room, that's a different and more involved project — this site's guide to building a whole-home audio streamer with Volumio and DAC HATs covers the network-synchronized alternative, which sidesteps Bluetooth's inherent one-device-at-a-time limitation.
Troubleshooting Common Issues
SymptomLikely cause Phone can't find the Pi when scanningDiscoverableTimeout not set to 0, or bluetoothd not restarted after config change Pairs but no audio playsbluealsa-aplay not running, or A2DP sink profile not enabled in the bluealsa service Audio choppy or stutteringWiFi and Bluetooth interference on 2.4GHz — try a wired Ethernet connection and 5GHz WiFi if the Pi model supports it Works with one phone, fails to reconnect after a whileDevice not marked trusted in bluetoothctl, or another paired device holding the connectionOnce running, this setup is genuinely "it just works" from the listener's side — pair once, and it reconnects automatically every time afterward, with no app, account, or network dependency beyond Bluetooth itself. For a Pi that's otherwise sitting idle, or as an add-on service on a Pi already running something else, it's a low-effort way to get real audio output into an old amp or a pair of powered speakers.
Related Guides
- Build a Bluetooth A2DP Audio Receiver with ESP32
- ESP32 I2S Audio: Playing and Recording Sound with a MAX98357A DAC and INMP441 Microphone
- Turning a Raspberry Pi into an AirPlay and Spotify Connect Receiver with Shairport-Sync and Raspotify
- How to Build a Class-D Audio Amplifier: TPA3116, Power Supply, and Speaker Matching
- How to Install Klipper on Any 3D Printer: Complete Setup Guide
- How to Use Bluetooth HID on the Flipper Zero for Wireless BadUSB Attacks
- How to Hack Wi-Fi and Bluetooth with the Flipper Zero and Wi-Fi Marauder
- How to Set Up OpenCV Machine Vision on a Raspberry Pi