Skip to content

Migrate

Migrate from LiveKit to Synento

Rooms become sessions, self-signed tokens become API-minted ones, and the egress pipeline collapses into a single export call.

LiveKit is the power tool of this space: an open-source SFU you can self-host, with simulcast, SVC, Egress and SIP in one room model. Migrating to Synento means trading that power for narrowness — a hosted relay where every session is already its own recording, with no infrastructure to run and no recording jobs to manage.

This guide is for teams who chose LiveKit Cloud rather than self-hosting, and whose workload turned out to be recorded sessions rather than real-time scale. If you self-host for data control, stop here: Synento is hosted-only and that requirement alone settles it.

Concept mapping

You haveYou getWhat changes
Room and self-signed access tokenSession and API-minted connection tokenRooms become sessions; stop signing JWTs and mint tokens through the API per participant.
Room.connect and publishTrackSynentoRoom.connect and publishCameraPublishing stays one call per track. Simulcast layers and adaptive streaming go away.
Room, track and composite egressOne export requestDelete the egress jobs. GET the export with a layout; identical requests return the same file.
room_finished and egress_endedsession.ended and export.completedThe session lifecycle plus export completion cover the pipeline triggers egress events did.
Self-hosted SFU binaryHosted onlyNothing to deploy, nothing to fork — and no data-control story beyond the hosted API.
Connection, transfer and egress metersParticipant-minutes plus storageFewer meters to reconcile. Recording and replay past the allowance are the only add-ons.

Before and after

Before

A LiveKit room: connect with a self-signed token, publish tracks, record via egress.

livekit.ts
import { Room, createLocalAudioTrack, createLocalVideoTrack } from 'livekit-client'

const room = new Room()
await room.connect('wss://project.livekit.cloud', livekitToken)
await room.localParticipant.publishTrack(await createLocalVideoTrack())
await room.localParticipant.publishTrack(await createLocalAudioTrack())

// Recording is egress: a separately metered job started server-side,
// with its output fetched afterwards.

After

The same call on Synento: tokens from the API, publishing without layers, export without jobs.

synento.ts
import { SynentoClient } from '@synento/node'
import { SynentoRoom } from '@synento/client'

// Server: no self-signed JWTs, no egress request. Tokens come from the API.
const synento = new SynentoClient()
const session = await synento.createSession({ name: 'Review' })
const token = await synento.createConnectionToken(session.id, { userId: 'bob' })

// Browser: one publish per track, same as before — minus everything around
// simulcast layers, which the relay deliberately does not have.
const room = new SynentoRoom({
  getToken: async () => ({ token: token.accessToken, wsUrl }),
  userId: 'bob',
})
await room.connect()
const stream = await navigator.mediaDevices.getUserMedia({ audio: true, video: true })
await room.publishCamera(stream)
await room.publishMicrophone(stream)

// The MP4 that egress used to produce: one export request, same layouts.
// curl -X POST $API/v1/sessions/$SESSION/export?layout=grid

The migration, step by step

  1. Create a Synento project and a restricted key. The key replaces both your API key and your token-signing secret for integration purposes.

  2. Replace token signing with the connection-token route. The room name you embedded in the JWT becomes the session id you pass to the API.

  3. Replace Room.connect with SynentoRoom: connect, publish camera and microphone, render from participantsChanged. Remove simulcast configuration — there is nothing to configure.

  4. Delete egress code and re-point webhooks: session.ended replaces room_finished, export.completed replaces egress_ended, recording.ready is the new explicit media-ready signal.

  5. Verify with two publishers and the manifest, then decommission the rooms. Keep the LiveKit project until retention on old egress files no longer matters.

What has no equivalent

What has no equivalent

Self-hosting is the big one: an open-source core you can run, fork and audit has no counterpart in a hosted-only product. If data must stay in your cloud, or per-minute fees at scale offend you, LiveKit wins outright and this migration is a mistake.

Then the real-time features: simulcast, SVC layers, adaptive per-viewer quality, and large-scale streaming. Synento sends one stream per track to everyone. Anything that needs per-viewer quality switching — big rooms, bad networks, broadcast scale — stays on LiveKit.

Common questions

We use LiveKit Agents. Is there an equivalent?

Not directly. Synento's agent story is integration-shaped — the MCP server provisions and verifies — not realtime-agent-shaped. Voice agents with combined inference stay on LiveKit.

What happens to our existing egress files?

They stay where egress put them. Download what must be kept; Synento reads its own streams, not imported files.

How large can a Synento call get?

Check the plan limits for the current numbers: calls are sized for meetings and sessions, not broadcast audiences. Large rooms are a choose-LiveKit reason, stated plainly on the comparison page.

Give your agent a video platform it can verify.

Sign up, point your agent at llms.txt, and have a recorded call running before lunch.