When Deepgram launched its Voice Agent API, it became a direct competitor to the application teams building on its infrastructure. For Contact Center as a Service (CCaaS) platforms, meeting assistant products, and post-call analytics teams, that shift introduced a fundamental conflict: your transcription vendor now ships into the same product category you're building.
Add stacked add-on pricing (base rate, then diarization, then sentiment, each billed separately), with no native translation offering, and the business case for switching becomes straightforward.
This guide answers that question with exact payload mappings, WebSocket state-machine translations, and a zero-downtime cutover strategy. We've structured it so each step can be completed independently, without requiring cross-team coordination or a full engineering sprint.
Baseline requirements before switching providers
Complete each step before cutover to reduce the surface area for production incidents during the switch.
Audit your current Deepgram integration
Catalog every active Deepgram touchpoint in your codebase:
- REST endpoints: Every call to
/v1/listen with a file or URL payload. - WebSocket connections: Every live transcription handshake and its query parameter string.
- SDK usages: Any Deepgram Node.js or Python SDK calls that abstract over the raw HTTP or WebSocket layer.
- Downstream consumers: Every service, queue, or database that reads from the Deepgram response JSON (speaker objects, word timestamps, confidence scores, metadata fields). The downstream audit often surfaces dependencies that are not visible from the API integration layer alone. Downstream consumers that read speaker IDs, confidence scores, or word timestamps directly from the response JSON are not protected by your API error handling and require explicit schema validation after the migration.
Define cutover failure protocols
Before writing a single line of migration code, agree on rollback thresholds: the p95 API latency that triggers a rollback, the 5xx error percentage over a defined time window that triggers a rollback, and the WER regression on your shadow-tested dataset that is unacceptable. Write these into a runbook, not a Slack thread.
Provision your Gladia API credentials
Sign up and retrieve your API key. New users receive a one-time €50 credit on the Starter plan, enough to run a full proof-of-concept against your own audio samples before cutover.
Mapping Deepgram auth to Gladia endpoints
The authentication change is a header substitution - replace Authorization: Token <key> with x-gladia-key: <key> - and all other connection changes follow from the updated base URL.
Mapping Deepgram requests to Gladia
Deepgram uses Authorization: Token <key> as the HTTP header. We use x-gladia-key instead. The base URL shifts to https://api.gladia.io/v2/. Per our authentication reference, all REST and WebSocket requests authenticate via that single header.
| Component |
Deepgram |
Gladia |
| Auth header |
Authorization: Token <key> |
x-gladia-key: <key> |
| REST base URL |
https://api.deepgram.com |
https://api.gladia.io/v2/ |
| WebSocket URL |
wss://api.deepgram.com/v1/listen |
wss://api.gladia.io/v2/live |
WebSocket message schema migration
We changed the connection URL from Deepgram's /v1/listen endpoint to wss://api.gladia.io/v2/live, and this is the only structural WebSocket change at the handshake level. Query parameters are replaced with a JSON configuration object sent as the first message after the connection opens, which is covered in the streaming section below. The live flow API reference documents the full initialization schema. Initialize the client using the patterns in our getting started guide, substituting x-gladia-key for the Deepgram auth header.
Mapping Deepgram logic to Gladia specs
With authentication resolved, the next step is parameter mapping. The parameters covered in the table below either map directly to a Gladia equivalent or are marked Built-in where our pipeline applies the behaviour by default.
Mapping Deepgram parameters to Gladia
The transcription init endpoint accepts the full parameter set below. Use the recommended parameters by use case guide to select the right configuration for async workloads.
| Deepgram parameter |
Gladia equivalent |
Notes |
punctuate=true |
Built-in |
Punctuation applied by default |
diarize_model=latest |
"diarization": true |
Async only, powered by pyannoteAI Precision-2 |
language=en |
"language": "en" |
Specify language or omit for automatic detection |
smart_format=true |
Built-in |
Formatting handled automatically |
utterances=true |
Built-in |
Utterances included in default response |
model=nova-3 |
"model": "solaria-1" or "model": "solaria-3" |
Not a direct equivalent; choose based on use case |
Model selection: Use Solaria-3 for real-world European business audio (EN, FR, DE, ES, IT) and contact-center recordings. Use Solaria-1 for maximum language coverage, code-switching, and real-time streaming. The two models are complementary, not mutually exclusive.
Configuring language detection logic
Language detection is on by default. Pass "detect_language": true explicitly in your payload if you want to be deliberate about the setting. For audio with strong accents, detection accuracy may vary - pass an explicit "language" value to force single-language transcription when the target language is known.
For conversations where speakers switch languages mid-call, code-switching detection activates via "enable_code_switching": true. This is a native capability of Solaria-1 across 100+ supported languages.
Configuring transcription text styles
Our formatting engine handles capitalization and punctuation by default. For specialized terms and brand names, use "custom_vocabulary" to guide pronunciation and ensure correct spelling of known terms. For capitalization-specific corrections where the engine nearly gets the term right, custom spelling may be more appropriate as it provides deterministic results.
Mapping Deepgram keywords to Gladia
Deepgram's keywords parameter maps to our custom_vocabulary_config parameter. Our implementation uses phoneme-matching with an intensity control, giving you more precision than a simple keyword list:
```json
{
"custom_vocabulary": true,
"custom_vocabulary_config": {
"vocabulary": [
"Gladia",
{
"value": "Solaria",
"pronunciations": ["So-lar-ee-uh"],
"intensity": 0.5,
"language": "en"
}
],
"default_intensity": 0.4
}
}
```
The intensity field (range 0.0 to 1.0) controls how aggressively the replacement is applied. Values between 0.4 and 0.6 work well for most production workloads.
Resolving speaker label discrepancies
Diarization is where the JSON schema difference between Deepgram and our API is most visible. The outputs are structurally similar but not drop-in compatible, so downstream parsers need an adapter.
Enabling multi-speaker tracking
Enable diarization by adding "diarization": true to your async request payload. Our diarization is powered by pyannoteAI's Precision-2 model and is the highest-accuracy option for batch workflows. For real-time streams, speaker attribution can be handled in post-processing for higher accuracy.
Mapping diarization output formats
We assign speakers by order of appearance, starting at index 0. Each utterance in the response carries "text", "language", "start", "end", "confidence", "speaker", and a "words" array:
```json
{
"result": {
"transcription": {
"utterances": [
{
"text": "This is the first speaker.",
"language": "en",
"start": 0.733,
"end": 2.364,
"confidence": 0.891,
"speaker": 0,
"words": [
{
"word": "This",
"start": 0.733,
"end": 0.853,
"confidence": 0.92
}
]
},
{
"text": "And this is the second speaker.",
"language": "en",
"start": 2.800,
"end": 4.500,
"confidence": 0.912,
"speaker": 1,
"words": [
{
"word": "And",
"start": 2.800,
"end": 2.920,
"confidence": 0.95
}
]
}
]
}
}
}
```
Translating diarization output formats
If your downstream UI components expect Deepgram's speaker schema, use this Python adapter to avoid a full consumer rewrite during the migration:
```python
def adapt_gladia_to_deepgram_speaker_format(gladia_response):
utterances = gladia_response.get("result", {}).get("transcription", {}).get("utterances", [])
adapted_utterances = []
for utterance in utterances:
adapted = {
"transcript": utterance.get("text", ""),
"start": utterance.get("start"),
"end": utterance.get("end"),
"confidence": utterance.get("confidence"),
"speaker": utterance.get("speaker"),
"words": [
{
"word": w.get("word"),
"start": w.get("start"),
"end": w.get("end"),
"confidence": w.get("confidence"),
"speaker": utterance.get("speaker")
}
for w in utterance.get("words", [])
]
}
adapted_utterances.append(adapted)
return {"utterances": adapted_utterances}
```
The function is only required for consumers that have not yet been updated to read the native Gladia schema directly.
Mapping live transcription streams to Gladia
Real-time streaming migration requires translating both the connection lifecycle and the message schema.
Mapping Deepgram to Gladia sockets
Deepgram accepts query parameters in the WebSocket URL. We require a POST request to initialize the session first: the same configuration (encoding, sample rate, language, etc.) goes in that POST body, and the response returns a WebSocket URL with a session token embedded. The client connects to that URL directly, with no headers or config frame needed on the socket itself.
```javascript
// Deepgram pattern
const deepgramSocket = new WebSocket(
"wss://api.deepgram.com/v1/listen?language=en&punctuate=true",
["token", DEEPGRAM_API_KEY]
);
// Gladia pattern (Node.js with ws library)
const WebSocket = require('ws');
async function connectToGladia() {
// Step 1: initialize the session — config goes in the POST body, not the socket
const initResponse = await fetch("https://api.gladia.io/v2/live", {
method: "POST",
headers: {
"Content-Type": "application/json",
"x-gladia-key": GLADIA_API_KEY,
},
body: JSON.stringify({
encoding: "wav/pcm",
sample_rate: 16000,
bit_depth: 16,
channels: 1,
language: "en",
messages_config: { receive_partial_transcripts: true }
}),
});
const session = await initResponse.json();
// Step 2: connect to the returned URL directly — token is embedded, no headers needed
const gladiaSocket = new WebSocket(session.url);
gladiaSocket.addEventListener("open", () => {
// socket is ready — begin streaming audio chunks
});
return gladiaSocket;
}
```
The recommended parameters for live use cases provides configuration profiles for telephony, browser audio, and voice agent workloads.
Mapping Deepgram streaming chunks
We require audio chunks encoded as WAV/PCM. Valid sample rates are 8000, 16000, 32000, 44100, and 48000 Hz, with 16000 as the default. For telephony integration (standard 8kHz PSTN), mu-law encoding at 8kHz is supported. Maximum chunk duration is 120 seconds. These specifications align with the WAV/PCM and mu-law formats defined in the live flow API reference - validate your capture pipeline's output format against these values before connecting.
Handling partial and final transcripts
We use an is_final boolean on the transcript message to distinguish partial from final results. The structural pattern maps cleanly from Deepgram's event model:
```javascript
// Gladia event handling
gladiaSocket.addEventListener("message", (event) => {
const message = JSON.parse(event.data.toString());
if (message.type === "transcript") {
if (message.data.is_final) {
console.log("Final:", message.data.utterance.text);
} else {
console.log("Partial:", message.data.utterance.text);
}
}
});
```
The primary path change is from data.channel.alternatives[0].transcript to message.data.utterance.text, as demonstrated in a TypeScript frontend context in the build real-time transcription in React guide.
Managing WebSocket drops and retries
Use exponential backoff to handle dropped connections without overwhelming the API:
```javascript
}
// Usage
const client = new GladiaStreamingClient(GLADIA_API_KEY, {
encoding: "wav/pcm",
sample_rate: 16000,
bit_depth: 16,
channels: 1,
language: "en",
messages_config: { receive_partial_transcripts: true }
});
client.onTranscript = (text) => {
// Your handling logic here
console.log("Final transcript:", text);
};
client.connect();
```
Mapping batch jobs to Gladia
Async REST migration is simpler than the WebSocket path. The payload structure is familiar and the response schema closely mirrors what you're already parsing.
Handling file uploads vs URLs
Our v2/pre-recorded endpoint accepts both remote URLs and local file uploads. For URL-based workflows, pass "audio_url" directly. For file uploads, send a multipart request with the file attached as "audio". The pre-recorded init reference covers both patterns. Accepted formats include WAV, M4A, FLAC, and AAC, with file sizes up to 1000MB and content up to 135 minutes per submission.
Setting up asynchronous webhooks
Pass a "callback_url" in your request payload to receive a notification via HTTP POST once processing finishes. We POST a JSON object to your endpoint containing the transcription id and an event property indicating success or error. Use the returned id to retrieve the full transcript via a subsequent call to the result URL:
```python
payload = {
"audio_url": "https://your-cdn.com/call-recording.wav",
"diarization": True,
"callback_url": "https://your-service.com/webhooks/transcription-complete"
}
```
This is the recommended pattern for contact-center and meeting assistant workloads processing thousands of files concurrently.
Tracking async task progress
If webhooks aren't viable, poll the status endpoint using the id returned from the initial submission. The audio-to-LLM pipeline reference shows how to chain structured outputs (summaries, action items, named entity recognition, sentiment) into downstream systems once the job resolves.
Adapting API payloads for Gladia integration
Update any JSON path references in your downstream parsers. Both APIs express word-level timestamps in seconds as floating-point values and use 0.0 to 1.0 confidence scores, so no unit conversion is required.
| Field |
Deepgram path |
Gladia path |
| Utterance text |
results.channels[0].alternatives[0].transcript |
result.transcription.utterances[N].text |
| Speaker ID |
results.utterances[N].words[M].speaker |
result.transcription.utterances[N].speaker |
| Word start time |
results.channels[0].alternatives[0].words[M].start |
result.transcription.utterances[N].words[M].start |
| Confidence |
results.channels[0].alternatives[0].confidence |
result.transcription.utterances[N].confidence |
To pass session IDs or custom metadata through the pipeline, include a "custom_metadata" object in your request payload. The metadata is echoed back in the response, preserving traceability without any database lookups.
Verification protocols for post-switch quality
Before flipping traffic, run a structured validation phase to confirm accuracy, latency, and concurrency performance against your own audio.
Validate switch with shadow testing
Shadow testing duplicates production audio to both Deepgram and Gladia simultaneously, letting you compare outputs on real traffic before committing to the switch. Fork audio at the ingestion layer, capture both responses, and run automated comparison scripts against reference transcripts. Run this across a representative sample of your audio types (clean recordings, noisy calls, multilingual sessions).
Benchmarking Gladia against Deepgram
Use the following Python snippet to compute word error rate on your shadow-tested dataset:
```python
def compute_wer(reference, hypothesis):
ref_words = reference.lower().split()
hyp_words = hypothesis.lower().split()
d = [[0] * (len(hyp_words) + 1) for _ in range(len(ref_words) + 1)]
for i in range(len(ref_words) + 1):
d[i][0] = i
for j in range(len(hyp_words) + 1):
d[0][j] = j
for i in range(1, len(ref_words) + 1):
for j in range(1, len(hyp_words) + 1):
if ref_words[i-1] == hyp_words[j-1]:
d[i][j] = d[i-1][j-1]
else:
d[i][j] = 1 + min(d[i-1][j], d[i][j-1], d[i-1][j-1])
return d[len(ref_words)][len(hyp_words)] / len(ref_words)
```
On published benchmarks, Solaria-3 achieves 6.4% WER on Earnings22 financial calls. This makes it the only model under 7% in that benchmark, ahead of Deepgram Nova-3. For a blind accuracy comparison on your own audio without exposing PHI, upload non-PHI test audio to our STT comparison tool. It runs a blind evaluation across providers so you can assess accuracy on your specific audio conditions rather than taking any vendor's benchmark at face value.
Stress testing your Gladia integration
Before the phased cutover, verify your integration holds at peak load. Contact us before your migration window if your peak volume requires higher concurrency limits than the default tier supports.
Validation and rollback procedures for STT swaps
A zero-downtime cutover requires a deployment architecture that makes rollback instantaneous, not just a correct integration.
Configuring feature flags for migration
Wrap your provider selection logic in a feature flag so you can route traffic dynamically without a deployment:
```python
def get_transcription_provider():
flag_value = feature_flags.get("transcription_provider", default="deepgram")
return flag_value
def transcribe(audio_url):
provider = get_transcription_provider()
if provider == "gladia":
return gladia_transcribe(audio_url)
else:
return deepgram_transcribe(audio_url)
```
Phased traffic cutover strategy
Execute the cutover in four stages, monitoring error rates, latency, and accuracy metrics at each stage before advancing:
- 1% traffic to Gladia: Validate that your monitoring dashboards are capturing latency, error rates, and accuracy metrics correctly.
- 10% traffic to Gladia: Confirm that accuracy on your shadow-tested dataset holds at this sample size.
- 50% traffic to Gladia: Monitor for any concurrency-related latency increases.
- 100% traffic to Gladia: Full cutover. Keep your rollback path ready for immediate reversion if needed.
Establishing real-time alert thresholds
Configure the following alerts in your observability stack (Datadog, Prometheus, or equivalent) before starting the cutover:
- API p95 latency above your acceptable baseline threshold for a sustained period.
- 5xx error rate above your acceptable threshold over a rolling window.
- Transcript confidence score average below your shadow-testing baseline by a significant margin. Set all three alerts to page the on-call engineer, not just write to a log.
Strategies for instant rollback
If any alert fires during cutover, follow this checklist:
- Keep your Deepgram API key configured in your secrets manager and referenced by the
transcription_provider feature flag throughout the cutover window - reverting the flag is all that's needed to route traffic back to Deepgram immediately. - Confirm the flag has propagated across all instances via your flag management console.
- Monitor error rate and latency for 5 minutes to confirm traffic has reverted.
- Write a post-incident note in your runbook with the alert that triggered rollback and the time of reversion.
With feature flag infrastructure already in place, steps 1 through 3 require no deployment cycle to execute. This is why pre-migration setup matters more than the cutover itself.
Resolving common data transition hurdles
Managing simultaneous Deepgram and Gladia
During the shadow testing and phased cutover window, you'll be billed by both providers for the audio running through each. Our Growth plan pricing is as low as $0.20/hr for async with diarization, translation, named entity recognition (NER), and sentiment included at the base rate. Deepgram charges separate add-on fees for diarization, NER, and sentiment. It does not offer native translation.
On Growth and Enterprise plans, your audio is never used to train our models and no opt-out configuration is required. This is the default behavior for those tiers, which matters if your recordings include regulated conversation data.
Migrating custom models to Gladia
If you've built a Deepgram custom model for domain-specific vocabulary (medical terminology, financial identifiers, brand names), our custom_vocabulary_config handles the majority of these cases without retraining. The phoneme-matching system described in the parameter mapping section above applies corrections at inference time rather than requiring a new model.
For CCaaS teams processing multilingual BPO audio, our CCaaS platform page covers how Solaria-3 handles real-world contact-center audio for English and core European languages, while Solaria-1 covers Tagalog, Bengali, Punjabi, Tamil, and other languages common in Southeast Asian and South Asian BPO operations.
Handling API rate limits during cutover
Concurrent pre-recorded request limits vary by plan. Before planning your cutover window, review the pricing page for current tier limits. Enterprise plans scale concurrency on demand with no capacity forecasting required. Aircall processes over 1M calls per week through Gladia without pre-provisioning. If your peak batch size approaches your plan limit, contact us before your migration window.
Start with €50 in free credits and have your integration in production in less than a day. Test Gladia on your own multilingual audio to see how it handles language detection, accent-heavy speech, and code-switching in production conditions.
FAQs
How long does a typical Deepgram to Gladia migration take?
The migration involves updating API endpoints, mapping JSON payloads, and configuring feature flags for the cutover. The integration itself - authentication changes, parameter mapping, and WebSocket schema updates - can be completed in under 24 hours of active development, based on multiple customer reports. Cutover duration beyond that depends on your shadow testing window and the phased traffic rollout you define before committing to full production traffic.
Does Gladia charge extra for speaker diarization?
No, speaker diarization is included in the base per-hour rate on our Starter and Growth plans, which avoids the stacked add-on fees common with other providers.
Is customer data used to train your models?
On our Growth and Enterprise plans, customer data is never used for model training and no manual opt-out action is required. On the Starter plan, data can be used for training.
What audio formats does the live API support?
Our live API supports WAV/PCM encoding with a sample rate of 16000 Hz, 16-bit depth, and mono channel by default. Mu-law encoding at 8kHz is also supported for standard telephony pipelines.
Can I run Solaria-3 for real-time transcription?
Solaria-3 is optimized for async workflows, which is where contact-center QA and reporting runs. For real-time WebSocket streaming, Solaria-1 delivers partial results under 103ms and final transcripts at ~300ms latency.
What happens if Gladia goes down during my production cutover?
Monitor our public status page during the cutover window. We maintain 99.9%+ uptime, but your feature flag rollback procedure lets you revert traffic to Deepgram without a deployment cycle if needed.
Do you support on-premises deployment for regulated audio?
No. Gladia runs on dedicated cloud clusters across EU and US regions. On-premises and air-gapped deployment are not available on any plan, including Enterprise. For organizations with strict data residency requirements, our EU and US cluster options are paired with SOC 2 Type II, ISO 27001, HIPAA, HDS, and GDPR compliance to meet most regulated-industry qualification criteria.
Key terms glossary
Word error rate (WER): The standard metric for measuring speech-to-text accuracy, calculated as the percentage of insertions, deletions, and substitutions relative to a reference transcript.
Diarization error rate (DER): The metric used to evaluate speaker diarization performance, calculated as the time-weighted fraction of audio where speech is missed, falsely inserted, or attributed to the wrong speaker.
Code-switching: The practice of alternating between two or more languages within a single conversation. We support this natively via the enable_code_switching parameter on Solaria-1.
Shadow testing: A deployment pattern where production traffic is duplicated and sent to both the legacy and new systems in parallel to validate performance before committing to the cutover.
Custom vocabulary: Our custom_vocabulary_config parameter uses phoneme-matching with adjustable intensity to ensure domain-specific terms, brand names, and proper nouns are transcribed correctly without retraining a model.
Diarization: The process of partitioning an audio stream by speaker identity and assigning each segment to a specific speaker. In our API, async diarization is powered by pyannoteAI's Precision-2 model for highest accuracy.