Self-Hosted Core
Core is the control plane for the self-hosted stack. It provides token issuance, app management, and a Web UI for configuring your self-hosted deployment.
What Core Does
Core is responsible for:
- App and session configuration
- Issuing short-lived session tokens
- Holding the configuration used when sessions are created
- Providing the browser-facing or backend-facing token entry point
- Encrypting and storing provider API keys
- Managing publishable API keys for client authentication
API Endpoints
Health Check
GET http://localhost:3000/healthResponse:
{
"status": "ok"
}Token Generation
The primary endpoint for client applications to request ephemeral tokens.
POST http://localhost:3000/vowel/api/generateTokenHeaders:
Content-Type: application/jsonX-API-Key: vkey_your_bootstrap_publishable_key
Request Body:
{
"appId": "default",
"provider": "vowel-prime",
"language": "en-US",
"initialGreetingPrompt": "Hello! How can I help you today?"
}Response:
{
"token": "ek_eyJhbGciOiJIUzI1NiIs...",
"expiresAt": "2024-01-15T10:30:00Z",
"wsUrl": "ws://localhost:8787/v1/realtime"
}Example curl:
curl -X POST http://localhost:3000/vowel/api/generateToken \
-H "Content-Type: application/json" \
-H "X-API-Key: vkey_your_bootstrap_publishable_key" \
-d '{
"appId": "default",
"provider": "vowel-prime"
}'Web UI
Core provides a web interface for managing apps and API keys:
http://localhost:3000The Web UI allows you to:
- Create and manage apps
- Generate and revoke API keys
- View token usage statistics
- Configure endpoint presets
Bootstrap Process
On first boot, Core automatically creates an app and publishable API key based on environment variables in stack.env:
- App Creation: Creates an app with ID from
CORE_BOOTSTRAP_APP_ID - API Key Generation: Creates a publishable key from
CORE_BOOTSTRAP_PUBLISHABLE_KEY - Endpoint Preset: Configures the engine endpoint for the
stagingpreset
Verify Bootstrap:
bun run stack:logs | grep bootstrapExpected output:
[core] bootstrap publishable key created for app=defaultBootstrap Configuration Variables:
| Variable | Default | Purpose |
|---|---|---|
CORE_BOOTSTRAP_APP_ID | default | App identifier |
CORE_BOOTSTRAP_APP_NAME | Local Stack App | Display name |
CORE_BOOTSTRAP_PUBLISHABLE_KEY | - | API key value (64 char hex with vkey_ prefix) |
CORE_BOOTSTRAP_SCOPES | mint_ephemeral | Key capabilities |
Token Flow
1. Client Requests Token
2. Client Connects to Engine
When You Interact With Core
You interact with Core when you need to:
- Configure a self-hosted app
- Request a session token
- Control how new sessions are initialized
- Manage API keys and their scopes
- View app configuration and usage
In many deployments, the browser does not talk directly to the realtime engine first. It fetches a token from Core or from your backend, then uses that token to start the live session.
How Core Fits Into The Flow
- Your app or backend requests a session token from Core
- Core validates the publishable API key and app permissions
- Core generates a short-lived JWT token (5-minute expiration)
- Core returns the token and WebSocket URL
- The client connects to the realtime engine with that token
- The engine validates the JWT and starts the session
Configuration Reference
Core Environment Variables
Core reads these environment variables from stack.env:
Required:
ENCRYPTION_KEY: For encrypting stored API keysENGINE_URL: Internal URL to reach engine (http://engine:8787)ENGINE_WS_URL: External WebSocket URL for clientsENGINE_API_KEY: Shared secret with engine
Optional:
DB_PATH: SQLite database location (/app/data/core.db)PORT: Service port (default: 3000)OPENAI_API_KEY: For OpenAI provider (if using)XAI_API_KEY: For xAI provider (if using)DEEPGRAM_API_KEY: Enables Deepgram STT/TTS choices in Core app settingsOPENAI_COMPATIBLE_BASE_URL: Enables OpenAI-compatible audio choices in Core app settingsDEFAULT_STT_PROVIDER: Default STT provider for bootstrap and new app defaultsDEFAULT_TTS_PROVIDER: Default TTS provider for bootstrap and new app defaultsCORE_ENABLE_DEV_VOICE_OVERRIDES: Allows hidden client_voiceConfigoverrides for development only
Note: The ability to override STT/TTS providers via token configuration is a development-only feature. In production, speech providers should be configured through app presets, not client token overrides. This ensures consistent behavior across sessions and prevents configuration drift.
Core does not store speech-provider secrets in app settings. Operators keep those secrets in the stack environment, and apps store only provider selections plus non-secret model, language, and voice defaults.
Endpoint Presets
Core supports multiple engine endpoint presets for different environments:
ENDPOINT_PRESET_VOWEL_PRIME_STAGING_HTTP_URL=http://engine:8787
ENDPOINT_PRESET_VOWEL_PRIME_STAGING_WS_URL=ws://localhost:8787/v1/realtimeDemo Application Connection
To connect the demo application to your self-hosted Core:
1. Configure Demo Environment
Create demos/demo/.env.local:
VITE_USE_CORE_COMPOSE=1
VITE_CORE_BASE_URL=http://localhost:3000
VITE_CORE_TOKEN_ENDPOINT=http://localhost:3000/vowel/api/generateToken
VITE_CORE_API_KEY=vkey_your_bootstrap_publishable_key
VITE_CORE_APP_ID=default2. Start the Demo
cd demos/demo
bun run dev3. Test the Connection
- Open the demo URL (usually
http://localhost:5173) - Click the microphone button
- Speak - the demo should connect to Core, get a token, then connect to the engine
Demo Configuration Values
| Variable | Value | Source |
|---|---|---|
VITE_CORE_BASE_URL | http://localhost:3000 | CORE_HOST_PORT from stack.env |
VITE_CORE_API_KEY | Your bootstrap key | CORE_BOOTSTRAP_PUBLISHABLE_KEY |
VITE_CORE_APP_ID | default | CORE_BOOTSTRAP_APP_ID |
What Core Does Not Replace
Core is not the realtime runtime itself. It does not:
- Process audio streams
- Run voice activity detection
- Execute speech-to-text or text-to-speech
- Handle WebSocket connections
- Run the AI model inference
That role belongs to the realtime engine.
Source Repository
Core is open source at github.com/usevowel/core.
Next Steps
- Architecture - Understand how Core fits in the stack
- Realtime Engine - Learn about the voice runtime
- Configuration - Configure environment variables
- Deployment - Deploy the full stack
- Troubleshooting - Debug common issues