Build a Voice Notification System with ElevenLabs
Why Voice Notifications Matter In a world where people are constantly scrolling through their feeds, a clear, audible alert can be the difference between a user noticing an important message or missing it entirely. Whe
Why Voice Notifications Matter
In a world where people are constantly scrolling through their feeds, a clear, audible alert can be the difference between a user noticing an important message or missing it entirely. Whether youβre building a smartβhome hub, a delivery app, or a healthβmonitoring dashboard, adding a voice layer turns a silent notification into a compelling user experience.
Voice notifications let you:
- Reduce visual clutter β perfect for onβtheβgo users or for devices with limited screen realβestate.
- Provide accessibility β make your app usable for people with visual impairments or reading difficulties.
- Add personality β a friendly voice can humanize an otherwise robotic interface.
Below, Iβll walk you through building a simple, yet productionβready, voice notification system using ElevenLabsβ textβtoβspeech (TTS) API. By the end, youβll have a reusable Python module that can generate and stream audio files on demand.
1. HighβLevel Architecture
βββββββββββββββββββββββ
β Notification Source β <-- app logic, webhook, or cron job
βββββββββ¬βββββββββββββββ
β
βΌ
βββββββββββββββββββββββ
β Notification Engine β <-- Python service that formats text
βββββββββ¬βββββββββββββββ
β
βΌ
βββββββββββββββββββββββ
β ElevenLabs TTS API β <-- Converts text β wav/ogg
βββββββββ¬βββββββββββββββ
β
βΌ
βββββββββββββββββββββββ
β Audio Storage / CDN β <-- S3, CloudFront, etc.
βββββββββ¬βββββββββββββββ
β
βΌ
βββββββββββββββββββββββ
β Playback Service β <-- Browser, mobile, speaker
βββββββββββββββββββββββ
The core of this stack is the Notification Engine, which takes a message payload, injects it into a template, and hands it off to ElevenLabs. The engine also handles caching, error handling, and optional voice cloning.
2. Getting Started with ElevenLabs
ElevenLabs offers a modern, highβquality TTS API that supports:
- Voice cloning β upload a few minutes of audio to generate a custom voice.
- Realβtime streaming β send a request and stream the audio back as itβs generated.
- Multiple formats β WAV, MP3, OGG, and more.
You can sign up for a free tier that includes a generous number of characters per month. Grab your API key and get started with the link below:
π Try ElevenLabs now
3. Building the Notification Engine
Below is a minimal Python module that:
- Accepts a notification payload.
- Renders a message template.
- Calls ElevenLabsβ TTS endpoint.
- Saves the audio to local storage (you can replace this with S3 later).
import os
import requests
from pathlib import Path
ELEVENLABS_API_KEY = os.getenv("ELEVENLABS_API_KEY")
ELEVENLABS_URL = "https://api.elevenlabs.io/v1/text-to-speech"
VOICE_ID = "en-US-Standard-B" # Pick a default voice
def synthesize(text: str, voice_id: str = VOICE_ID, output_path: str = None) -> Path:
"""
Convert text to speech using ElevenLabs and save the audio file.
"""
headers = {
"xi-api-key": ELEVENLABS_API_KEY,
"Content-Type": "application/json",
}
payload = {
"text": text,
"voice_settings": {
"stability": 0.75,
"similarity_boost": 0.65
},
}
response = requests.post(
f"{ELEVENLABS_URL}/{voice_id}",
json=payload,
headers=headers,
stream=True
)
response.raise_for_status()
if not output_path:
output_path = Path(f"audio_{voice_id}.mp3")
with open(output_path, "wb") as f:
for chunk in response.iter_content(chunk_size=8192):
f.write(chunk)
return output_path
if __name__ == "__main__":
# Simple test
message = "Hello! Your package has arrived and is ready for pickup."
audio_file = synthesize(message)
print(f"Audio saved to: {audio_file}")
Whatβs happening here?
| Step | Why it matters |
|---|---|
| Headers |
xi-api-key authenticates you. |
| Payload |
voice_settings lets you tweak the prosody. |
| Streaming |
stream=True keeps memory usage low for large texts. |
| Output | You can pipe the file to any media player or CDN. |
4. Using curl for Quick Tests
If you want to prototype without writing code, curl works fine:
curl -X POST "https://api.elevenlabs.io/v1/text-to-speech/en-US-Standard-B" \
-H "xi-api-key: YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{"text":"Your meeting starts in 10 minutes."}' \
--output meeting_reminder.mp3
Replace YOUR_API_KEY with the key you got from the affiliate link.
5. Voice Cloning: Make It Personal
One of ElevenLabsβ standout features is the ability to clone a voice from a short audio sample. This is great for creating consistent brand voices or personalized assistants.
Step 1 β Upload a sample
def upload_voice_sample(audio_path: Path, name: str) -> str:
"""
Upload a short clip and receive a voice_id.
"""
url = "https://api.elevenlabs.io/v1/voice-cloning"
files = {"file": open(audio_path, "rb")}
data = {"name": name}
headers = {"xi-api-key": ELEVENLABS_API_KEY}
resp = requests.post(url, files=files, data=data, headers=headers)
resp.raise_for_status()
return resp.json()["voice_id"]
Step 2 β Use the cloned voice
cloned_voice_id = upload_voice_sample(Path("sample.wav"), "MyBrandVoice")
synthesize("Welcome back! How can I assist you today?", voice_id=cloned_voice_id)
Tip: Keep the sample under 30 seconds for best results, and make sure itβs clear, wellβrecorded audio.
6. Error Handling & Rate Limits
ElevenLabs enforces perβminute and perβhour limits. To make your engine robust:
try:
audio_file = synthesize(message)
except requests.exceptions.HTTPError as err:
if err.response.status_code == 429:
print("Rate limit hit β backing off for 60 seconds")
time.sleep(60)
else:
raise
You can also cache audio files locally or in a CDN to avoid repeated requests for the same message template.
7. Integrating with Your App
Example β Flask Endpoint
from flask import Flask, request, send_file
app = Flask(__name__)
@app.route("/notify", methods=["POST"])
def notify():
data = request.json
message = data.get("message", "No message provided")
audio = synthesize(message)
return send_file(audio, as_attachment=True, mimetype="audio/mp3")
Now any client can POST a JSON payload and receive an MP3 stream. Pair this with a webhook or a scheduled job to trigger notifications automatically.
Example β Streaming to a Smart Speaker
If youβre working with a smart speaker that accepts an MP3 URL, simply upload the audio to an S3 bucket and return the public link:
def upload_to_s3(file_path: Path) -> str:
s3_client.upload_file(str(file_path), "my-bucket", f"audio/{file_path.name}")
return f"https://my-bucket.s3.amazonaws.com/audio/{file_path.name}"
8. Best Practices
| Practice | Why |
|---|---|
| Use templates | Keep your message logic separate from voice logic. |
| Cache frequently used messages | Saves API calls and reduces latency. |
| Monitor usage | Avoid hitting rate limits; ElevenLabs provides usage dashboards. |
| Fallback to default voice | If cloning fails, fall back to a reliable standard voice. |
| Add metadata | Store voice ID, timestamp, and message hash for debugging. |
9. WrapβUp
Building a voice notification system is surprisingly straightforward when you have a highβquality TTS service like ElevenLabs. With just a few lines of code, you can:
- Convert any text into naturalβsounding speech.
- Clone custom voices for brand consistency.
- Stream or cache audio for fast, reliable playback.
Give it a spin today and hear the difference a humanβlike voice can make in your application.
π Try ElevenLabs now and start creating voice notifications that your users will actually listen to!
Originally published by Dev.to WebDev. Aggregated on AIWithGhost for educational purposes β full credit and traffic to the original publisher.