Console
Docs/Start

Quickstart

From an empty account to a player talking in a channel. About ten minutes, no credit card.

1. Create a project#

  1. Sign up at /console/ and confirm your e-mail.
  2. Create an organisation (your studio) if you did not name one at sign-up.
  3. New project → name, plan, home region. Start on Free: 50 concurrent participants on the shared EU pool (200 during the launch offer), every SDK, no card.

The console shows the SDK key (aurx_…) exactly once. Store it in your backend's secret store. It must never ship in a game build — anyone holding it can mint tokens for your project. You can rotate it at any time.

Also note the cell endpoint under Keys & SDK, e.g. https://eu-central.cell.aurix.run. Your backend mints tokens there; browser clients use it as apiUrl.

2. Mint a token for a player#

When a player enters a match, your game server asks the cell for a session token. The token is short-lived and bound to the player id you pass.

Your
curl -X POST "$AURIX_CELL/v1/tokens" \
  -H "x-api-key: $AURIX_API_KEY" \
  -H "content-type: application/json" \
  -d '{
    "external_id": "player-42",
    "display_name": "Ann",
    "channels": [
      { "ad_hoc": { "name": "match-7",     "channel_type": "positional" } },
      { "ad_hoc": { "name": "match-7-red", "channel_type": "team" } }
    ]
  }'
Response
{
  "token": "eyJ…",
  "user_id": "a3c1…",
  "expires_at": "2026-10-21T20:15:00Z",
  "channels": [
    { "channel_id": "6f0d…", "join": true, "speak": true, "receive": true, "moderate": false, "priority": false,
      "ad_hoc": { "name": "match-7", "channel_type": "positional" } },
    { "channel_id": "9b21…", "join": true, "speak": true, "receive": true, "moderate": false, "priority": false,
      "ad_hoc": { "name": "match-7-red", "channel_type": "team" } }
  ],
  "endpoint": { "region": "eu_central", "node_id": "…", "ws_url": "wss://eu-central.cell.aurix.run/ws", "probe_url": "https://…", "nodes": 1, "load_factor": 0.1 },
  "location_source": "none"
}

Hand token, endpoint.ws_url and the channel ids to the client. If the project runs in several regions, mint through the control plane instead — POST /v1/projects/{id}/tokens on the console host with an organisation API token picks the nearest region for the player and returns the same shape. Every field is described in Player tokens. With Node, Python, Go or C# you can use the server SDKs instead of raw HTTP — see the token server examples.

3. Connect from the game#

Unreal
UAurixVoiceSubsystem* Voice = GetGameInstance()->GetSubsystem<UAurixVoiceSubsystem>();
FAurixVoiceSettings S; S.WebSocketUrl = Endpoint.WsUrl; S.Token = Token;
Voice->OnSessionReady.AddDynamic(this, &AMyPC::OnVoiceReady);   // join once the session is up
Voice->Connect(S);
// OnVoiceReady:
FGuid Ch; UAurixVoiceSubsystem::ParseUuid(PositionalChannelId, Ch);
int64 Req; Voice->JoinChannel(Ch, TEXT(""), Req);
Voice->StartCapture();
Unity
var voice = GetComponent<AurixVoiceBehaviour>();        // microphone, playback and PTT handled for you
voice.WebSocketUrl = endpoint.ws_url; voice.Token = token;
voice.ChannelId = channels[0].channel_id;
await voice.Connect();
Godot
var voice := AurixVoiceClient.new()
add_child(voice)
voice.session_ready.connect(func(_s): voice.join_channel(channels[0].channel_id))
voice.connect_to_server(endpoint.ws_url, token)
Web
import { AurixClient } from '@aurix/web-sdk';
const voice = new AurixClient({ apiUrl: 'https://eu-central.cell.aurix.run', wsUrl: endpoint.ws_url, token });
await voice.connect();
await voice.joinChannel(channels[0].channel_id);

Positional channels need the player's position a few times a second (updatePosition / UpdateOwnPosition / update_transforms depending on the SDK); team channels need nothing else. Capture devices, push-to-talk, VAD and mute are covered per engine in the integration guides.

4. Watch it#

Open the project's Overview in the console: participants, participant-minutes and traffic appear within five minutes — the running hour is metered live and becomes final when it ends. Usage has the per-hour breakdown and a CSV export.

Next#

  • Concepts — what a cell, a channel and a participant are, and how limits are counted.
  • Spending limit — for paid plans, what happens at 100 / 105 / 110 / 120 %.
  • Webhooks — get limit and node events into your own systems.

What you just built#

text
game client ──(1) login──▶ your backend ──(2) POST /v1/tokens, x-api-key──▶ cell
     ▲                          │
     └──(3) token + endpoint────┘
game client ──(4) QUIC / WebTransport / WebRTC / WS──▶ media node   (audio never touches your backend)

Your backend is the only place the SDK key lives. The token carries the endpoint, the channels and the grants, so a client build never contains a server address or a secret, and moving between regions, cells or self-hosted nodes is a change on the token server only.

Common first-run problems#

SymptomCauseFix
401 from /v1/tokenskey pasted with whitespace, or a rotated keycopy again from Keys & SDK; rotation invalidates the old key immediately
token works, client never connectscorporate / campus network blocks UDPthe SDK falls back to WebRTC over TURN, then WebSocket; check the transport in the quality panel of the rooms demo
players hear nothing in a positional channelno update_position calls, so everyone is at the origin at far_distancesend positions ~10 Hz; test with team first
connect refused with QUOTA_EXCEEDEDFree (50, 200 during the launch offer) / Indie (300) concurrency cap, or spending ladder step 4wait for someone to leave, upgrade, or raise the limit
second tab joins as the same player and kicks the firstsame external_idone voice user per id; use a device suffix for multi-device testing
no usage in Overviewfirst metering pass is still pendingrows appear within 5 minutes and rewrite until the hour closes

Before you ship#

  • Tokens live 60 minutes: wire the SDK's refresh hook (refreshToken / TokenRefresher / SetToken / set_token) to your token endpoint so reconnects after an hour just work.
  • Set a spending limit before announcing a launch date; autoscale respects it.
  • Give moderators moderate and your event hosts priority; everything else stays default.
  • Put the webhook endpoint for spend_cap.step in your ops chat.
  • Read What you pay for once — it is short and it is the whole invoice.