04 - Gateway and Protocol
The gateway is the central component of GoClaw, serving both WebSocket RPC (Protocol v3) and HTTP REST API on a single port. It handles authentication, role-based access control, rate limiting, and method dispatch for all client interactions.
1. WebSocket Lifecycle
Connection Parameters
| Parameter |
Value |
Description |
| Read limit |
512 KB |
Auto-close connection on exceed |
| Send buffer |
256 capacity |
Drop messages when full |
| Read deadline |
60s |
Reset on each message or pong |
| Write deadline |
10s |
Per-write timeout |
| Ping interval |
30s |
Server-initiated keepalive |
2. Protocol v3 Frame Types
| Type |
Direction |
Purpose |
req |
Client to Server |
Invoke an RPC method |
res |
Server to Client |
Response matching request by id |
event |
Server to Client |
Push events (streaming chunks, agent status, etc.) |
The first request from a client must be connect. Any other method sent before authentication results in an UNAUTHORIZED error.
Request Frame Structure
type: always "req"
id: unique request ID (client-generated)
method: RPC method name
params: method-specific parameters (JSON)
Response Frame Structure
type: always "res"
id: matches the request ID
ok: boolean success indicator
payload: response data (when ok is true)
error: error shape with code, message, details, retryable, retryAfterMs (when ok is false)
Event Frame Structure
type: always "event"
event: event name (e.g., chat, agent, status)
payload: event data
seq: ordering sequence number
stateVersion: version counters for optimistic state sync
3. Authentication and RBAC
Connect Handshake
Token comparison uses crypto/subtle.ConstantTimeCompare to prevent timing attacks.
The user_id in the connect parameters is required for per-user session scoping and context file routing. GoClaw uses the Identity Propagation pattern — it trusts the upstream service to provide accurate user identity. The user_id is opaque (VARCHAR 255); multi-tenant deployments use the compound format tenant.{tenantId}.user.{userId}. See 00-architecture-overview.md Section 5 for details.
Three Roles
Method Permissions
| Role |
Accessible Methods |
| viewer |
agents.list, config.get, sessions.list, sessions.preview, health, status, providers.models, skills.list, skills.get, channels.list, channels.status, cron.list, cron.status, cron.runs, usage.get, usage.summary |
| operator |
All viewer methods plus: chat.send, chat.abort, chat.history, chat.inject, sessions.delete, sessions.reset, sessions.patch, cron.create, cron.update, cron.delete, cron.toggle, cron.run, skills.update, send, exec.approval.list, exec.approval.approve, exec.approval.deny, device.pair.request, device.pair.list |
| admin |
All operator methods plus: config.apply, config.patch, config.permissions.*, agents.create, agents.update, agents.delete, agents.files.*, teams.*, channels.toggle, device.pair.approve, device.pair.revoke |
4. Request Handling Pipeline
5. RPC Methods
System
| Method |
Description |
connect |
Authentication handshake (must be first request) |
health |
Health check |
status |
Gateway status (connected clients, agents, channels) |
providers.models |
List available models from all providers |
Agent Evolution (v3)
| Method |
Description |
agent.evolution.suggestions |
Get evolution suggestions for an agent (requires metrics enabled) |
agent.evolution.apply |
Apply a suggested evolution to an agent configuration |
agent.evolution.rollback |
Roll back applied evolution with quality guardrails |
Chat
| Method |
Description |
chat.send |
Send a message to an agent, receive streaming response |
chat.history |
Get conversation history for a session |
chat.abort |
Abort a running agent loop |
chat.inject |
Inject a system message into a session |
Agents
| Method |
Description |
agent |
Get details for a specific agent |
agent.wait |
Wait for an agent to become available |
agent.identity.get |
Get agent identity (name, description) |
agents.list |
List all accessible agents |
agents.create |
Create a new agent |
agents.update |
Update agent configuration |
agents.delete |
Soft-delete an agent |
agents.files.list |
List agent context files |
agents.files.get |
Read a context file |
agents.files.set |
Write a context file |
Sessions
| Method |
Description |
sessions.list |
List all sessions |
sessions.preview |
Preview session content |
sessions.patch |
Update session metadata |
sessions.delete |
Delete a session |
sessions.reset |
Reset session history |
Config
| Method |
Description |
config.get |
Get current configuration (secrets redacted) |
config.apply |
Replace entire configuration |
config.patch |
Partial configuration update |
config.schema |
Get configuration JSON schema |
config.permissions.list |
List agent config permission rules |
config.permissions.check |
Preview effective permission for an agent, scope, config type, and user |
config.permissions.grant |
Add or update an agent config permission rule |
config.permissions.revoke |
Remove an agent config permission rule |
Skills
| Method |
Description |
skills.list |
List all skills |
skills.get |
Get skill details |
skills.update |
Update skill content |
Cron
| Method |
Description |
cron.list |
List scheduled jobs |
cron.create |
Create a new cron job |
cron.update |
Update a cron job |
cron.delete |
Delete a cron job |
cron.toggle |
Enable/disable a cron job |
cron.status |
Get cron system status |
cron.run |
Manually trigger a cron job |
cron.runs |
List recent run logs |
Channels
| Method |
Description |
channels.list |
List enabled channels |
channels.status |
Get channel running status |
channels.toggle |
Enable/disable a channel (admin only) |
Pairing
| Method |
Description |
device.pair.request |
Request a pairing code |
device.pair.approve |
Approve a pairing request |
device.pair.list |
List paired devices |
device.pair.revoke |
Revoke a paired device |
browser.pairing.status |
Poll browser pairing approval status |
Exec Approval
| Method |
Description |
exec.approval.list |
List pending exec approval requests |
exec.approval.approve |
Approve an exec request |
exec.approval.deny |
Deny an exec request |
Usage and Send
| Method |
Description |
usage.get |
Get token usage for a session |
usage.summary |
Get aggregated usage summary |
send |
Send a direct message to a channel |
TTS (Text-to-Speech)
| Method |
Description |
tts.status |
Get TTS system status |
tts.enable |
Enable TTS |
tts.disable |
Disable TTS |
tts.convert |
Convert text to speech |
tts.setProvider |
Set active TTS provider |
tts.providers |
List available TTS providers |
Browser
| Method |
Description |
browser.act |
Execute browser action (navigate, click, type) |
browser.snapshot |
Get DOM snapshot |
browser.screenshot |
Take screenshot |
Teams
| Method |
Description |
teams.list |
List agent teams |
teams.create |
Create a team (lead + members) |
teams.get |
Get team details with members |
teams.delete |
Delete a team |
teams.update |
Update team configuration |
teams.tasks.list |
List team tasks |
teams.tasks.get |
Get task details |
teams.tasks.create |
Create a new task |
teams.tasks.delete |
Delete a task |
teams.tasks.claim |
Claim a task (mark as in-progress) |
teams.tasks.assign |
Assign task to member |
teams.tasks.approve |
Approve completed task |
teams.tasks.reject |
Reject task submission |
teams.tasks.comment |
Add comment to task |
teams.tasks.comments |
Get task comments |
teams.tasks.events |
Get task event history |
teams.members.add |
Add member to team |
teams.members.remove |
Remove member from team |
teams.workspace.list |
List team workspace files |
teams.workspace.read |
Read workspace file content |
teams.workspace.delete |
Delete workspace file |
teams.events.list |
List team event history |
teams.known_users |
Get list of known users for team |
teams.scopes |
Get team member scopes |
Delegations
| Method |
Description |
delegations.list |
List delegation history (result truncated to 500 runes) |
delegations.get |
Get delegation detail (result truncated to 8000 runes) |
Channel Instances
| Method |
Description |
channels.instances.list |
List channel instances |
channels.instances.get |
Get channel instance details |
channels.instances.create |
Create a new channel instance |
channels.instances.update |
Update channel instance config |
channels.instances.delete |
Delete a channel instance |
API Keys
| Method |
Description |
api_keys.list |
List API keys |
api_keys.create |
Create a new API key |
api_keys.revoke |
Revoke an API key |
Usage and Quotas
| Method |
Description |
quota.usage |
Get quota usage information |
Other
| Method |
Description |
logs.tail |
Tail gateway logs |
6. HTTP API
Authentication
Authorization: Bearer <token> -- timing-safe comparison via crypto/subtle.ConstantTimeCompare
- No token configured: all requests allowed
X-GoClaw-User-Id: required for per-user scoping
X-GoClaw-Agent-Id: specify target agent for the request
Endpoints
POST /v1/chat/completions (OpenAI-compatible)
Agent resolution priority: model field with goclaw: or agent: prefix, then X-GoClaw-Agent-Id header, then "default".
POST /v1/responses (OpenResponses Protocol)
Same agent resolution and execution flow, different response format (response.started, response.delta, response.done).
POST /v1/tools/invoke
Direct tool invocation without the agent loop. Supports dryRun: true to return tool schema only.
GET /health
Returns {"status":"ok","protocol":3}.
CRUD Endpoints
All CRUD endpoints require Authorization: Bearer <token> and X-GoClaw-User-Id header for per-user scoping.
Agents (/v1/agents):
| Method |
Path |
Description |
| GET |
/v1/agents |
List accessible agents (filtered by user shares) |
| POST |
/v1/agents |
Create a new agent |
| GET |
/v1/agents/{id} |
Get agent details |
| PUT |
/v1/agents/{id} |
Update agent configuration |
| DELETE |
/v1/agents/{id} |
Soft-delete an agent |
Custom Tools (/v1/tools/custom):
| Method |
Path |
Description |
| GET |
/v1/tools/custom |
List tools (optional ?agent_id= filter) |
| POST |
/v1/tools/custom |
Create a custom tool |
| GET |
/v1/tools/custom/{id} |
Get tool details |
| PUT |
/v1/tools/custom/{id} |
Update a tool |
| DELETE |
/v1/tools/custom/{id} |
Delete a tool |
MCP Servers (/v1/mcp):
| Method |
Path |
Description |
| GET |
/v1/mcp/servers |
List registered MCP servers |
| POST |
/v1/mcp/servers |
Register a new MCP server |
| GET |
/v1/mcp/servers/{id} |
Get server details |
| PUT |
/v1/mcp/servers/{id} |
Update server config |
| DELETE |
/v1/mcp/servers/{id} |
Remove MCP server |
| POST |
/v1/mcp/servers/{id}/grants/agent |
Grant access to an agent |
| DELETE |
/v1/mcp/servers/{id}/grants/agent/{agentID} |
Revoke agent access |
| GET |
/v1/mcp/grants/agent/{agentID} |
List agent's MCP grants |
| POST |
/v1/mcp/servers/{id}/grants/user |
Grant access to a user |
| DELETE |
/v1/mcp/servers/{id}/grants/user/{userID} |
Revoke user access |
| POST |
/v1/mcp/requests |
Request access (user self-service) |
| GET |
/v1/mcp/requests |
List pending access requests |
| POST |
/v1/mcp/requests/{id}/review |
Approve or reject a request |
Agent Sharing (/v1/agents/{id}/sharing):
| Method |
Path |
Description |
| GET |
/v1/agents/{id}/sharing |
List shares for an agent |
| POST |
/v1/agents/{id}/sharing |
Share agent with a user |
| DELETE |
/v1/agents/{id}/sharing/{userID} |
Revoke user access |
Delegations (/v1/delegations):
| Method |
Path |
Description |
| GET |
/v1/delegations |
List delegation history (full records, paginated) |
| GET |
/v1/delegations/{id} |
Get delegation detail |
Skills (/v1/skills):
| Method |
Path |
Description |
| GET |
/v1/skills |
List skills |
| POST |
/v1/skills/upload |
Upload skill ZIP (configurable, default 20 MB, max 500 MB) |
| DELETE |
/v1/skills/{id} |
Delete a skill |
Traces (/v1/traces):
| Method |
Path |
Description |
| GET |
/v1/traces |
List traces (filter by agent_id, user_id, status, date range) |
| GET |
/v1/traces/{id} |
Get trace details with all spans |
Channel Instances (/v1/channel-instances):
| Method |
Path |
Description |
| GET |
/v1/channel-instances |
List channel instances |
| POST |
/v1/channel-instances |
Create a new channel instance |
| GET |
/v1/channel-instances/{id} |
Get channel instance details |
| PUT |
/v1/channel-instances/{id} |
Update channel instance config |
| DELETE |
/v1/channel-instances/{id} |
Delete a channel instance |
API Keys (/v1/api-keys):
| Method |
Path |
Description |
| GET |
/v1/api-keys |
List API keys |
| POST |
/v1/api-keys |
Create a new API key |
| DELETE |
/v1/api-keys/{id} |
Revoke an API key |
Providers & Models (/v1/providers):
| Method |
Path |
Description |
| GET |
/v1/providers |
List LLM providers |
| POST |
/v1/providers |
Create a new provider |
| GET |
/v1/providers/{id} |
Get provider details |
| PUT |
/v1/providers/{id} |
Update provider config |
| DELETE |
/v1/providers/{id} |
Delete a provider |
Memory (/v1/memory):
| Method |
Path |
Description |
| GET |
/v1/memory |
Get memory entries |
| POST |
/v1/memory |
Create memory entry |
| DELETE |
/v1/memory/{id} |
Delete memory entry |
Knowledge Graph (/v1/kg):
| Method |
Path |
Description |
| GET |
/v1/kg/entities |
List entities |
| POST |
/v1/kg/entities |
Create entity |
| GET |
/v1/kg/relations |
List relationships |
| POST |
/v1/kg/relations |
Create relationship |
Files & Storage (/v1/files, /v1/storage):
| Method |
Path |
Description |
| GET |
/v1/files |
List workspace files |
| GET |
/v1/files/{path} |
Serve file content |
| DELETE |
/v1/storage/{path} |
Delete workspace file |
Media (/v1/media):
| Method |
Path |
Description |
| POST |
/v1/media/upload |
Upload media file |
| GET |
/v1/media/{id} |
Serve media file |
Activity & Usage (/v1/activity, /v1/usage):
| Method |
Path |
Description |
| GET |
/v1/activity |
List activity audit logs |
| GET |
/v1/usage |
Get usage metrics |
| GET |
/v1/usage/summary |
Get aggregated usage summary |
OAuth & Docs (/oauth, /docs):
| Method |
Path |
Description |
| GET,POST |
/oauth/* |
OAuth authentication endpoints |
| GET |
/docs/openapi.json |
OpenAPI specification |
| GET |
/docs/swagger-ui/ |
Swagger UI |
MCP Bridge (/mcp/bridge):
| Method |
Path |
Description |
| POST |
/mcp/bridge |
MCP server bridge (Claude CLI tools) |
7. Rate Limiting
Token bucket rate limiting per user or IP address. Configured via gateway.rate_limit_rpm (0 = disabled, > 0 = enabled).
| Aspect |
WebSocket |
HTTP |
| Rate key |
client.UserID() fallback client.ID() |
RemoteAddr fallback "token:" + bearer |
| On limit |
INVALID_REQUEST "rate limit exceeded" |
HTTP 429 |
| Burst |
5 requests |
5 requests |
| Cleanup |
Every 5 min, entries inactive > 10 min |
Same |
8. Error Codes
| Code |
Description |
UNAUTHORIZED |
Authentication failed or insufficient role |
INVALID_REQUEST |
Missing or invalid fields in the request |
NOT_FOUND |
Requested resource does not exist |
ALREADY_EXISTS |
Resource already exists (conflict) |
UNAVAILABLE |
Service temporarily unavailable |
RESOURCE_EXHAUSTED |
Rate limit exceeded |
FAILED_PRECONDITION |
Operation prerequisites not met |
AGENT_TIMEOUT |
Agent run exceeded time limit |
INTERNAL |
Unexpected server error |
Error responses include retryable (boolean) and retryAfterMs (integer) fields to guide client retry behavior.
File Reference
| Module |
Path |
Purpose |
| Gateway core |
internal/gateway/ |
WS server, HTTP mux, method router, rate limiter, client lifecycle |
| RPC handlers |
internal/gateway/methods/ |
All WS RPC handlers: chat, agents, sessions, config, skills, cron, teams, channels, pairing, exec approval, usage, API keys |
| HTTP handlers |
internal/http/ |
All REST endpoints: /v1/chat/completions, /v1/agents, /v1/skills, /v1/traces, /v1/mcp, auth, OAuth, summoner |
| Protocol types |
pkg/protocol/ |
Frame types, RPC method constants, event names, error codes |
Use grep or your editor's symbol search for specific files.