# WebRTC Relay (/docs/experiments/webrtc-relay)



Issue **Cloudflare Realtime TURN** credentials for WebRTC. Without secrets configured, endpoints return safe demo credentials so tests and local demos still work.

## API Reference [#api-reference]

### GET /turn-credentials [#get-turn-credentials]

### GET /ice-servers [#get-ice-servers]

Both routes return the same shape.

**`ttl`** `number` (optional)

Credential lifetime in seconds (60–86400, default 86400).

#### Example Request [#example-request]

```bash
curl "https://your-worker.workers.dev/turn-credentials?ttl=3600"
curl "https://your-worker.workers.dev/ice-servers"
```

#### Success Response (demo mode) [#success-response-demo-mode]

Returned when `REALTIME_APP_ID` or `TURN_API_TOKEN` is missing:

```json
{
  "iceServers": [
    {
      "urls": ["turn:turn.cloudflare.com:3478?transport=udp"],
      "username": "demo",
      "credential": "demo"
    }
  ],
  "ttl": 86400,
  "mode": "demo",
  "note": "Configure REALTIME_APP_ID and TURN_API_TOKEN for real credentials"
}
```

#### Success Response (live mode) [#success-response-live-mode]

Calls `POST https://rtc.live.cloudflare.com/v1/turn/keys/${REALTIME_APP_ID}/credentials/generate-ice-servers` with `Authorization: Bearer ${TURN_API_TOKEN}`.

#### Error Codes [#error-codes]

* `400` - Invalid ttl (`INVALID_TTL`)
* `502` - Realtime TURN API failure (`TURN_API_ERROR`)

## Use Cases [#use-cases]

* Learn Cloudflare Realtime TURN credential issuance
* Bootstrap WebRTC ICE servers from a Worker API
* Demo clients safely when secrets are not yet configured
* Centralize TURN TTL and key rotation behind one endpoint

## Limitations [#limitations]

* Demo credentials are not usable for real peer connections
* Requires a TURN key from the Realtime dashboard for live mode
* TTL clamped to 60–86400 seconds
* No STUN-only path in this experiment beyond what the API returns

## Deployment [#deployment]

<Steps>
  <Step>
    ### Click the deploy button [#click-the-deploy-button]

    [![Deploy to Cloudflare Workers](https://deploy.workers.cloudflare.com/button)](https://deploy.workers.cloudflare.com/?url=https://github.com/shrinathsnayak/cloudflare-experiments/tree/main/apps/experiments/webrtc-relay)
  </Step>

  <Step>
    ### Configure Realtime TURN [#configure-realtime-turn]

    1. Create a TURN key in the [Cloudflare Realtime dashboard](https://developers.cloudflare.com/realtime/turn/)
    2. Set `REALTIME_APP_ID` in `wrangler.json` `vars` (or as a secret)
    3. Run `npx wrangler secret put TURN_API_TOKEN`
  </Step>

  <Step>
    ### Test your deployment [#test-your-deployment]

    ```bash
    curl "https://your-worker.workers.dev/turn-credentials?ttl=3600"
    ```
  </Step>
</Steps>

## Local Development [#local-development]

```bash
cd apps/experiments/webrtc-relay
npm install
npm run dev
```

```bash
curl "http://localhost:8787/turn-credentials?ttl=3600"
```

Without secrets, endpoints return demo credentials (safe for tests).

## Configuration [#configuration]

`wrangler.json` declares:

* **Var** `REALTIME_APP_ID` (TURN key id)
* **Secret** `TURN_API_TOKEN` (set via `wrangler secret put`)

## Cloudflare Features Used [#cloudflare-features-used]

* **[Workers](https://developers.cloudflare.com/workers/)** - Edge compute runtime
* **[Cloudflare Realtime TURN](https://developers.cloudflare.com/realtime/turn/)** - ICE / TURN credentials for WebRTC
