Every developer who has built applications for enterprise convention centers knows the nightmare of venue Wi-Fi.
You test your audio streaming and WebSocket connections on 1 Gbps office fiber. In local staging, packets stream with five millisecond latency. Audio chunks pass directly to your transcription worker and everything looks solid.
Then your team arrives on site at the exhibition hall.
Ten thousand delegates enter the venue, pull out their smartphones, and overwhelm local cellular towers. Convention Wi-Fi networks suffer forty percent packet drop rates. Sockets close without clean TCP FIN packets. Mobile browser audio contexts pause when the operating system throttles background tabs.
If your audio ingestion pipeline relies on persistent, uninterrupted WebSockets, your application fails in production. Half completed conversations get lost, transcription models receive fragmented audio frames, and reps lose critical qualification notes.
In building PravahAI audio ingestion for high decibel trade show floors, we designed an offline first streaming pipeline that guarantees zero audio loss even across ninety second connectivity blackouts.
Here is how we architected client side ring buffers, exponential reconnection backoff, and idempotent backend ingestion.
The failure modes of naive WebSocket streaming
A standard WebRTC or WebSocket audio pipeline captures PCM audio via the browser MediaStream Recording API and immediately dispatches chunks over a live socket connection.
This naive architecture breaks under three specific convention hall edge cases:
- Silent TCP disconnects: In dense RF environments, mobile Wi-Fi adapters drop packets without the browser triggering a WebSocket
oncloseoronerrorevent. The client continues emitting audio chunks into a dead socket buffer for up to thirty seconds before the browser detects a broken pipe. - Audio context clock drift: When mobile devices experience thermal throttling on 85dB exhibition floors, Web Audio API contexts slip out of alignment with system clocks. Audio chunks arrive at the backend out of order.
- Partial chunk corruption: Poor network quality causes fragmented TCP frames, corrupting header bytes in raw linear PCM audio streams.
Architectural solution: Client-side RingBuffer with sequence indexing
To solve packet loss, we replaced direct socket streaming with an in memory circular buffer (RingBuffer) coupled with IndexedDB persistent chunk caching.
interface AudioChunkPayload { sessionId: string; sequenceId: number; timestamp: number; sampleRate: number; data: Float32Array; isTerminal: boolean; } The browser audio worklet processes raw audio in four kilobyte frames. Instead of dispatching directly to the network, the worklet pushes each frame into a local RingBuffer and writes an uncompressed chunk to IndexedDB every 250 milliseconds.
Each chunk receives a monotonically increasing sequence ID and session identifier.
class ResilientAudioStreamer { private buffer: AudioChunkPayload[] = []; private sequence = 0; private ws: WebSocket | null = null; private isConnected = false; public pushChunk(pcmData: Float32Array): void { const chunk: AudioChunkPayload = { sessionId: this.sessionId, sequenceId: this.sequence++, timestamp: Date.now(), sampleRate: 16000, data: pcmData, isTerminal: false }; this.buffer.push(chunk); this.persistToIndexedDB(chunk); this.flushBuffer(); } } Idempotent backend ingestion and frame reassembly
When connectivity restores, the client flushes buffered chunks in sequential order.
However, in erratic Wi-Fi environments, retransmitted packets frequently collide with fresh chunks. The backend ingestion service must handle duplicate or out of sequence packets without corrupting transcription workers.
Our Node.js and FastAPI ingestion pipeline utilizes an in memory sliding window buffer per session. When a chunk arrives, the ingestion service checks the sequence index against a session bitmap. Duplicate chunks are acknowledged and discarded. Missing sequence gaps trigger an immediate client retransmission request for the missing frame range.
Once the window fills sequentially, the normalized audio buffer passes to our speech to text inference worker.
Key takeaways for building offline-first voice applications
- Never trust the browser socket state: Use client side heartbeat pings with four second timeouts to detect silent connection drops faster than TCP keepalive.
- Cache uncompressed PCM frames locally: Store raw audio chunks in IndexedDB before attempting network dispatch. If the browser tab crashes, the audio persists across page reload.
- Enforce sequence idempotency on the server: Design backend ingestion to reorder and deduplicate packets strictly by sequence index.
Building software for enterprise trade show floors requires designing for the worst network conditions on earth. Treating offline as the default state ensures your revenue team never loses critical buyer intent.
Explore our technical documentation and architecture at PravahAI.