Skip to main content

Shell WebSocket API

The shell API uses WebSocket for bidirectional streaming communication.

WebSocket Endpoint

GET /agents/{agent-id}/shell?mode=tty|stream

Query Parameters

ParameterValuesDescription
modettyInteractive mode with PTY (default)
streamStreaming mode without PTY

Subprotocol

The WebSocket uses the muti-shell subprotocol.

Message Protocol

The WebSocket uses a binary message protocol. All messages have a 1-byte type prefix followed by the payload. The CLI handles this protocol automatically - you only need to understand it if building custom integrations.

Message Types

NameDirectionDescription
METAClient -> ServerJSON metadata to start session
ACKServer -> ClientJSON acknowledgment
STDINClient -> ServerKeyboard input (raw bytes)
STDOUTServer -> ClientCommand output (raw bytes)
STDERRServer -> ClientError output (raw bytes, streaming mode only)
RESIZEClient -> ServerTerminal resize notification
SIGNALClient -> ServerSignal to send (e.g., SIGINT)
EXITServer -> ClientProcess exit code
ERRORServer -> ClientJSON error message

Session Flow

1. Connect

WebSocket: ws://localhost:8080/agents/abc123/shell?mode=tty
Subprotocol: muti-shell

2. Send Metadata (META)

First message must be META with session configuration:

{
"command": "bash",
"args": ["-l"],
"env": {"TERM": "xterm-256color"},
"work_dir": "/home/user",
"password": "secret",
"tty": {
"rows": 24,
"cols": 80,
"term": "xterm-256color"
},
"timeout": 3600
}
FieldTypeDescription
commandstringCommand to execute (required)
argsstring[]Command arguments
envobjectAdditional environment variables
work_dirstringWorking directory
passwordstringAuthentication password
ttyobjectTTY settings (for interactive mode)
tty.rowsnumberTerminal rows
tty.colsnumberTerminal columns
tty.termstringTERM value (default: xterm-256color)
timeoutnumberSession timeout in seconds

3. Receive Acknowledgment (ACK)

{
"success": true,
"error": ""
}

If success is false, the session failed to start.

4. Data Exchange

After ACK, send and receive data:

  • STDIN: Send keyboard input as raw bytes
  • STDOUT: Receive command output
  • STDERR: Receive error output (streaming mode only)
  • RESIZE: Send terminal size changes
  • SIGNAL: Send signals (e.g., SIGINT = 2)

5. Session End

The server sends EXIT with the exit code, then closes the WebSocket.

Error Handling

ERROR Message

{
"message": "command not allowed"
}

Sent when:

  • Command not in whitelist
  • Authentication failed
  • Session limit reached
  • Other server errors

WebSocket Close Codes

CodeReason
1000Normal closure
1002Protocol error
1011Internal error

Custom Client Integration

For custom integrations, refer to the binary protocol implementation. The message format uses a 1-byte type prefix:

Type ByteMessage
0x01META
0x02ACK
0x03STDIN
0x04STDOUT
0x05STDERR
0x06RESIZE (4 bytes: rows, cols as uint16 BE)
0x07SIGNAL (1 byte: signal number)
0x08EXIT (4 bytes: exit code as int32 BE)
0x09ERROR

For a complete implementation example, see the CLI source code in the project repository.

See Also