---
title: "Deploy Livekit [Updated Sep'26]"
description: "Run a LiveKit voice agent worker — STT, LLM, TTS, sub-second replies"
category: "AI/ML"
url: https://railway.com/deploy/livekit-agent-worker
---

# Deploy Livekit [Updated Sep'26]

Run a LiveKit voice agent worker — STT, LLM, TTS, sub-second replies

**[Deploy Livekit [Updated Sep'26] on Railway](https://railway.com/template/livekit-agent-worker)**

Machine-readable deploy manifest (JSON, validated by TemplateCI): https://railway.com/deploy/livekit-agent-worker/manifest.json

- **Creator:** SB
- **Category:** AI/ML

## Template content

### web-frontend

- **Source:** yuting1214/LiveKit-Template

### voice-agent

- **Source:** yuting1214/LiveKit-Template

### Redis https://cdn.sanity.io/images/sy1jschh/production/0ce0bfdcfbdbf69662b1116671f97c2dd788b655-157x157.svg

- **Image:** redis:8.2
- **Start command:** `/bin/sh -c "rm -rf $RAILWAY_VOLUME_MOUNT_PATH/lost+found/ && exec docker-entrypoint.sh redis-server --requirepass $REDIS_PASSWORD --save 60 1 --dir $RAILWAY_VOLUME_MOUNT_PATH"`

### livekit-server

- **Source:** yuting1214/LiveKit-Template

## Documentation

# Deploy and Host LiveKit Voice Agent on Railway

LiveKit Agents is the open-source framework behind production voice AI — the same stack powering ChatGPT's voice mode. An agent joins a room as a participant, listens, thinks and speaks back, with turn detection and barge-in handled for you. This template deploys the agent worker itself: a long-lived process that dials out to your LiveKit server or LiveKit Cloud, with speech models baked in at build time so the first call doesn't stall waiting on a download.

## What This Template Deploys

| Service | Purpose |
| --- | --- |
| `agent` | LiveKit Agents worker. Connects outbound to `LIVEKIT_URL`, registers for job dispatch, runs the STT → LLM → TTS pipeline. |

One service, no public domain, no inbound ports. The worker holds a persistent WebSocket out to LiveKit and receives jobs over it, so nothing needs to reach it from the internet. Nothing is stored locally either, which is why there is no volume here.

## About Hosting

A voice agent is judged on one number: the gap between someone finishing a sentence and hearing a reply. Almost everything below is a way that number quietly gets worse.

**Keep media off Railway.** Railway does not route UDP, so self-hosting the media server here forces WebRTC over TCP: head-of-line blocking and retransmission on a real-time audio stream, where a late packet is worse than a dropped one. Workable for a demo, a real latency tax on production voice. This template runs only the agent and points it at a LiveKit server on UDP-capable infrastructure.

**The agent is a worker, not a web service.** It opens an outbound connection and waits for dispatch; it never listens for HTTP. Attach a public domain and the health check fails against a port nothing is serving — a broken deploy by appearance, a healthy worker in fact.

**Models must be fetched at build time.** Turn detection and VAD load local weights. Skip the download step in your build and the worker fetches them on first job — the caller sits in silence during a cold start, or it fails outright. Run the framework's `download-files` step at build so the weights ship in the image.

**Start the worker in production mode.** The framework's development command enables hot reload and single-job debugging, and the console command is terminal-only. Either one deployed as your start command produces a worker that restarts constantly or never registers at all, with no obvious error.

**Never let the worker sleep.** Registration is a held connection. Scale-to-zero or app sleeping drops it, and LiveKit has nowhere to dispatch — the room opens and no agent joins. Keep the service always-on.

**Your bill is API calls, not compute.** Three metered providers sit in the pipeline — STT, the model, TTS — and a speech-to-speech model replaces all three with one meter that usually costs more per minute. Compute is the small number.

Typical cost: **~$8–15/month** for one always-on worker at $10/GB/month RAM and $20/vCPU/month, plus whatever your STT, LLM and TTS providers charge per minute of conversation.

## How It Compares

| | LiveKit Agents (self-run worker) | Vapi | Retell AI | OpenAI Realtime direct |
| --- | --- | --- | --- | --- |
| Agent code | Yours, Python or Node | Config in vendor dashboard | Config in vendor dashboard | Yours |
| Provider choice | Any STT, LLM, TTS | Vendor's list | Vendor's list | OpenAI only |
| Cost model | Compute + provider APIs | Per minute + provider APIs | Per minute | Per minute |
| Self-hostable | Yes | No | No | No |

The honest edge: Vapi and Retell get you a working phone agent faster, and if you want a dashboard rather than a repo, take them. LiveKit Agents wins when the logic stops being a prompt — tool calls into your own systems, custom turn-taking, swapping TTS vendors without a rewrite, or keeping transcripts out of a third party. You write and run code instead of filling in a form, and the per-minute platform fee disappears.

## Deploy in Under 5 Minutes

1. Click **Deploy** and pick a workspace. The worker builds and pre-downloads its speech models.
2. Set `LIVEKIT_URL`, `LIVEKIT_API_KEY` and `LIVEKIT_API_SECRET` from your LiveKit Cloud project or your own server.
3. Set your provider keys — an LLM key at minimum, plus STT and TTS keys unless you are using a speech-to-speech model.
4. Confirm the service has **no public domain** and that sleeping is disabled. Watch the logs for the worker registering.
5. Open your LiveKit project's playground, join a room, and talk to it.

> Verify before you rely on it: redeploy, then start a call within ten seconds of the worker coming up. If the first reply is as fast as the tenth, your models are in the image rather than being downloaded on demand.

## Common Use Cases

- **Inbound support and reception** — answer calls, look up an account through a tool call, escalate to a human with context attached.
- **Outbound qualification and reminders** — appointment confirmations, renewals and follow-ups, driven from your own queue rather than a vendor's scheduler.
- **Voice front end for an existing agent** — put speech in front of tools and retrieval you already run, without rebuilding the logic in a dashboard.
- **Realtime translation and note-taking** — join a room as a silent participant, transcribe and summarise without recording to disk.

## Configuration

| Variable | Required | Description |
| --- | --- | --- |
| `LIVEKIT_URL` | Required | `wss://` URL of your LiveKit server or Cloud project. Outbound only. |
| `LIVEKIT_API_KEY` | Required | API key for the same project. |
| `LIVEKIT_API_SECRET` | Required | Matching secret. Rotating one alone silently stops dispatch. |
| `OPENAI_API_KEY` | Required | LLM provider key, or the equivalent for whichever model you use. |
| `DEEPGRAM_API_KEY` | Optional | Speech-to-text, if not using a speech-to-speech model. |
| `CARTESIA_API_KEY` | Optional | Text-to-speech, if not using a speech-to-speech model. |

> **Do not give this service a public domain.** The worker serves no HTTP. A domain attaches a health check to a port nothing is listening on, and the deploy fails while the agent is working fine.

> **Turn off app sleeping.** The worker's registration is a held connection. If the service sleeps, calls arrive at a room with no agent in it and nothing logs an error.

## Dependencies for LiveKit Voice Agent Hosting

- **Railway account** — ~$8–15/month for one always-on worker; more if you run several replicas for concurrent calls.
- **A LiveKit server** — LiveKit Cloud or your own deployment on UDP-capable infrastructure. The agent connects to it; it is not bundled here.
- **Provider accounts** — an LLM key, plus STT and TTS keys unless you use a speech-to-speech model. All metered per minute.
- **Optional** — LiveKit SIP for phone numbers, and a database if you want transcripts or conversation memory to persist.

### Deployment Dependencies

- [LiveKit Agents on GitHub](https://github.com/livekit/agents)
- [LiveKit Agents documentation](https://docs.livekit.io/agents/)
- [LiveKit server on GitHub](https://github.com/livekit/livekit)
- [Railway private networking](https://docs.railway.com/guides/private-networking)

### Implementation Details

The worker runs as a single long-lived process with no listener. On boot it authenticates to `LIVEKIT_URL` with the key and secret, registers itself as available, and then waits. When a room needs an agent, LiveKit dispatches a job over that same connection and the worker spawns a session for it. Because every connection is outbound, the service needs no domain, no TCP proxy and no inbound firewall consideration at all — which is exactly why Railway suits the worker even though it suits the media server poorly.

Model weights are the build-time concern. Turn detection and voice activity detection run locally rather than as API calls, and their weights are fetched by an explicit download step. Running that step during the build bakes them into the image, so a cold start is process startup rather than a download. Skip it and the cost lands on your first caller, as silence, at the worst possible moment.

Concurrency scales by replica. One process handles multiple sessions, but CPU per session is real once local VAD and turn detection run, so size by concurrent calls rather than total volume. Raise replicas as concurrency grows — each registers independently and LiveKit distributes jobs across them.

## Frequently Asked Questions

**Does this include the LiveKit server?** No, deliberately. This is the agent worker. Point it at LiveKit Cloud or your own server — media needs UDP, and Railway does not route it.

**Why does my deploy fail its health check?** Almost certainly a public domain on a service that serves no HTTP. The worker is outbound-only. Remove the domain and the deploy passes.

**Why is the first call slow and later ones fine?** Model weights are downloading at runtime instead of being in the image. Run the framework's download step during build.

**Why did the agent stop joining rooms?** Either the service slept and dropped its registration, or the key and secret no longer match the project. Both fail silently — check the worker logs for a registration line.

**How many concurrent calls can one worker handle?** Depends on the pipeline, but local turn detection and VAD make CPU the limit. Size by concurrent calls and add replicas rather than growing one instance.

## Why Deploy LiveKit Voice Agent on Railway?

Railway is a singular platform to deploy your infrastructure stack. Railway will host your infrastructure so you don't have to deal with configuration, while allowing you to vertically and horizontally scale it.

By deploying a LiveKit Voice Agent on Railway you get the half of the stack that belongs here — an always-on outbound worker with models baked into the image, no inbound ports to configure, and media left on infrastructure that can actually route UDP.

## Similar templates

- [Chat Chat](https://railway.com/deploy/-WWW5r) — Chat Chat, your own unified chat and search to AI platform.
- [stella](https://railway.com/deploy/stella) — Self-host stella with web, API, Postgres, Redis, and object storage.
- [Hermes Agent | OpenClaw Alternative with Dashboard](https://railway.com/deploy/hermes-agent-or-openclaw-alternative-wit) — Self-Hosted Hermes AI Agent for Telegram, Discord & Slack

Open this page in a browser: https://railway.com/deploy/livekit-agent-worker
