clawdesk-gateway
The HTTP and WebSocket gateway server built on Axum. Exposes the REST API, OpenAI-compatible endpoints, WebSocket streaming, and admin endpoints. This is the main application server crate.
Dependencies
Internal: clawdesk-types, clawdesk-domain, clawdesk-storage, clawdesk-agents, clawdesk-providers, clawdesk-channel, clawdesk-channels, clawdesk-plugin, clawdesk-security, clawdesk-cron, clawdesk-skills, clawdesk-observability
External: axum, tokio, tower, serde, tracing, uuid, arc-swap
Modules
| Module | Description |
|---|---|
admin | Admin API endpoints (plugins, cron, skills, channels, metrics) |
bootstrap | Server startup, dependency wiring, graceful shutdown |
middleware | Authentication, logging, rate limiting, CORS middleware |
openai_compat | OpenAI-compatible /v1/chat/completions and /v1/models |
rate_limiter | Request rate limiting per session/IP |
responses_api | Responses API endpoints (/v1/responses) |
routes | Core REST API route definitions (/api/v1/*) |
rpc | Internal RPC for inter-service communication |
skills_admin | Skill management admin endpoints |
state | AppState — shared application state |
watcher | Config file watcher for hot-reload |
ws | WebSocket upgrade handler and message routing |
Key Types
/// Shared application state passed to all handlers
pub struct AppState {
pub pipeline: Arc<Pipeline>,
pub session_store: Arc<dyn SessionStore>,
pub conversation_store: Arc<dyn ConversationStore>,
pub config: Arc<ArcSwap<AppConfig>>,
pub provider_registry: Arc<ProviderRegistry>,
pub channel_registry: Arc<ChannelRegistry>,
pub plugin_registry: Arc<PluginRegistry>,
pub skill_registry: Arc<SkillRegistry>,
pub cron_manager: Arc<CronManager>,
}
/// Build the Axum router with all routes
pub fn build_router(state: AppState) -> Router {
Router::new()
// Core API
.route("/api/v1/health", get(health))
.route("/api/v1/message", post(send_message))
.route("/api/v1/sessions", get(list_sessions))
.route("/api/v1/sessions/:id", get(get_session).delete(delete_session))
.route("/api/v1/sessions/:id/messages", get(get_messages))
.route("/api/v1/sessions/:id/compact", post(compact_session))
.route("/api/v1/channels", get(list_channels))
.route("/api/v1/config", get(get_config))
.route("/api/v1/models", get(list_models))
// OpenAI-compatible
.route("/v1/chat/completions", post(chat_completions))
.route("/v1/models", get(openai_models))
.route("/v1/responses", post(create_response))
.route("/v1/responses/:id", get(get_response))
// Admin
.nest("/api/v1/admin", admin_routes())
// WebSocket
.route("/ws", get(ws_upgrade))
.with_state(state)
}
Example Usage
use clawdesk_gateway::{bootstrap, AppState};
#[tokio::main]
async fn main() -> anyhow::Result<()> {
// Bootstrap wires all dependencies together
let state = bootstrap::initialize().await?;
let router = clawdesk_gateway::build_router(state);
let listener = tokio::net::TcpListener::bind("0.0.0.0:1420").await?;
axum::serve(listener, router)
.with_graceful_shutdown(shutdown_signal())
.await?;
Ok(())
}
tip
The gateway supports hot-reload of configuration via the file watcher. Changes to config.toml are picked up without restart using ArcSwap.