Skip to content

Creating Agents

An agent is a YAML config file that tells society what handler to use and which port to listen on. Society discovers agent configs from a directory (default: agents/).

name: my-agent
description: What this agent does
port: 8010
handler: exec
backend:
command: my-tool
args: ["--flag", "value"]
session_flag: "--session"
resume_flag: "--resume"
env:
- API_KEY=sk-xxx
skills:
- id: summarize
name: Summarize
description: Summarizes documents
FieldRequiredDescription
nameYesUnique agent name
descriptionNoHuman-readable description
portNoHTTP listen port (1-65535)
handlerYesecho, greeter, or exec
backendOnly for execExternal command configuration
skillsNoList of capabilities the agent advertises

Returns the input message unchanged. Useful for testing.

name: echo
port: 8001
handler: echo

Prepends “Hello! You said: ” to every message. Another test handler.

name: greeter
port: 8002
handler: greeter

The real workhorse. Wraps any CLI tool as an agent. The tool receives the message text on its arguments and should output a response.

name: claude
port: 8003
handler: exec
backend:
command: claude
args: ["-p", "--output-format", "json"]
session_flag: "--session-id"
resume_flag: "--resume"

For each incoming message:

  1. Extracts text from the message parts
  2. Loads or creates a conversation thread (~/.society/threads/<id>.json)
  3. Builds the command: command args... <message-text>
  4. On first message: appends session_flag <session-id> if configured
  5. On follow-ups: appends resume_flag <session-id> instead
  6. Runs the command, captures stdout
  7. Parses JSON output if possible (looks for {"result": "..."} format), otherwise uses raw stdout
  8. Saves the exchange to the thread file

Wrap Claude Code:

name: claude
port: 8003
handler: exec
backend:
command: claude
args: ["-p", "--output-format", "json"]
session_flag: "--session-id"
resume_flag: "--resume"

Wrap a custom script:

name: translator
port: 8010
handler: exec
backend:
command: python3
args: ["translate.py"]
env:
- DEEPL_API_KEY=your-key

Wrap any LLM CLI:

name: ollama-llama
port: 8020
handler: exec
backend:
command: ollama
args: ["run", "llama3.2"]

Single agent:

Terminal window
society run --config agents/my-agent.yaml

All agents in a directory:

Terminal window
society daemon run --agents ./agents

Specific agents only:

Terminal window
society daemon run echo claude

Agents can also run over stdio instead of HTTP, useful for embedding:

Terminal window
society run --config agents/echo.yaml --stdio

In this mode, the agent reads JSON-RPC requests from stdin and writes responses to stdout, one per line.