Skip to main content

Python SDK for the Agent Orchestration API.

Project description

trelent-agents

Python SDK for the Trelent Agent Orchestration API.

Installation

pip install trelent-agents

Quick Start

Without authentication

from trelent_agents import Client

client = Client(api_url="http://localhost:8000")

sandboxes = client.sandboxes.list()
print(sandboxes)

run = client.runs.create(
    sandbox="example-agent:latest",
    prompt="Create hello.txt with a greeting",
)
print(run.id, run.status, run.harness.kind)

With authentication

When the API has authentication enabled, provide your OAuth2 client credentials:

from trelent_agents import Client

client = Client(
    api_url="https://agents.trelent.com",
    client_id="your-client-id",
    client_secret="your-client-secret",
)

sandboxes = client.sandboxes.list()
run = client.runs.create(
    sandbox="my-sandbox:latest",
    prompt="Do something useful",
)

The SDK handles token acquisition automatically — it exchanges your client credentials for a JWT via the API's /token endpoint before making authenticated requests.

If you need to call the token proxy directly, use client.tokens.create(...).

The client also supports context manager usage:

with Client(api_url="https://agents.trelent.com", client_id="...", client_secret="...") as client:
    runs = client.runs.list()

Client Options

client = Client(
    api_url="https://agents.trelent.com",  # API base URL (default: https://agents.trelent.com)
    client_id="...",                        # OAuth2 client ID (optional)
    client_secret="...",                    # OAuth2 client secret (optional)
    scope="...",                            # Override default OAuth2 scope (optional)
)

Both client_id and client_secret must be provided together, or both omitted.

Resources

client.sandboxes

sandboxes = client.sandboxes.list()
# => list[RegistrySandbox] — [RegistrySandbox(name="my-sandbox", tags=["latest", "v1"])]

When auth is enabled, sandboxes are automatically filtered to your namespace. Sandbox names are returned without the namespace prefix.

client.tokens

token = client.tokens.create(
    client_id="your-client-id",
    client_secret="your-client-secret",
    scope="AgentOrchestrator:runs:list",
)

client.runs

from trelent_agents import ClaudeCodeHarnessSpec, LocalImporter, RunSecretBinding, S3Exporter

# Create a run
run = client.runs.create(
    sandbox="my-sandbox:latest",
    prompt="Build a web server",
    harness=ClaudeCodeHarnessSpec(),  # optional, default: ClaudeCodeHarnessSpec()
    workdir="/workspace",          # optional, default: image WORKDIR or /workspace
    timeout_seconds=3600,          # optional, default: 3600
    imports=[LocalImporter(path="./data")],  # optional
    exports=[S3Exporter()],                  # optional
    secrets=[                                # optional
        RunSecretBinding(name="openai", env_var="OPENAI_API_KEY"),
    ],
)

# List runs (optionally filter by sandbox)
runs = client.runs.list()
filtered = client.runs.list(sandbox="my-sandbox:latest")

# Get a specific run
run = client.runs.get("run-id")

# Check status
status = client.runs.get_status("run-id")

# Cancel a run
cancel = client.runs.cancel("run-id")

# Get checkpoints
chain = client.runs.get_checkpoint_chain("run-id")
checkpoint = client.runs.get_checkpoint("run-id", "checkpoint-id")

Run operations

# Fork (resume from checkpoint)
forked = run.fork(
    "Continue from where you left off",
    workdir="/workspace/project",
    timeout_seconds=1800,
)

# Refresh run state
run.refresh()
print(run.status)  # updated status

Streaming Events

Subscribe to real-time events from a run using Server-Sent Events (SSE). Events are streamed as the agent executes, providing live visibility into reasoning, messages, and tool usage.

Basic streaming

from trelent_agents import Client, EventType

client = Client(api_url=api_url, client_id=client_id, client_secret=client_secret)

run = client.runs.create(
    sandbox="my-sandbox:latest",
    prompt="Build a simple web server",
)

# Subscribe to the event stream
for event in run.stream():
    match event.type:
        case EventType.MESSAGE_DELTA:
            print(event.data.delta.text, end="", flush=True)
        case EventType.TOOL_CALL_STARTED:
            print(f"\nTool: {event.data.name}")
        case EventType.SESSION_COMPLETED:
            print(f"\nCompleted with exit code: {event.data.exit_code}")

Streaming via client

You can also stream using the run ID directly:

for event in client.runs.stream_events("run-abc123"):
    print(event.type, event.seq)

Event types

Event Type Description
SESSION_STARTED Agent session initialized
SESSION_COMPLETED Session finished (includes exit_code and usage)
TURN_STARTED New conversation turn began
TURN_COMPLETED Turn finished
TURN_FAILED Turn failed with error
MESSAGE_STARTED Assistant message started
MESSAGE_DELTA Incremental text content
MESSAGE_COMPLETED Full message content available
REASONING_STARTED Extended thinking started
REASONING_DELTA Incremental reasoning text
REASONING_COMPLETED Reasoning block finished
TOOL_CALL_STARTED Tool invocation started (includes name and kind)
TOOL_CALL_INPUT_DELTA Streaming tool input JSON
TOOL_CALL_INPUT_COMPLETE Full tool input available
TOOL_CALL_OUTPUT_DELTA Streaming tool output
TOOL_CALL_COMPLETED Tool execution finished (includes exit_code)
ERROR Error occurred

Event structure

Every event has a common envelope:

class CommonEvent(BaseModel):
    seq: int           # Sequence number (monotonically increasing)
    timestamp: str     # ISO 8601 timestamp
    type: EventType    # Event type discriminator
    data: EventData    # Type-specific payload

client.health()

health = client.health()
# => HealthResponse(status="ok")

Connectors

Importing local files

from trelent_agents import LocalImporter

run = client.runs.create(
    sandbox="my-sandbox:latest",
    prompt="Process the data",
    imports=[LocalImporter(path="./my-data-dir")],
)

The LocalImporter tarballs and base64-encodes the local path, sending it inline with the request. The API stages large payloads onto a shared volume server-side, so the run-creation request itself stays the only network hop you need.

Exporting to S3

from trelent_agents import S3Exporter

run = client.runs.create(
    sandbox="my-sandbox:latest",
    prompt="Generate a report",
    exports=[S3Exporter(bucket="my-bucket", path="reports/")],
)

Shared workspaces

Shared workspaces mount a user-scoped shared directory into the sandbox at /mnt/shared/<name>.

from trelent_agents import SharedWorkspaceExporter, SharedWorkspaceImporter

run = client.runs.create(
    sandbox="my-sandbox:latest",
    prompt="Read and write files in /mnt/shared/my-drive",
    imports=[SharedWorkspaceImporter(name="my-drive")],
    exports=[SharedWorkspaceExporter(name="my-drive")],
)

To export a subdirectory from the shared workspace:

exports=[SharedWorkspaceExporter(name="my-drive", directory="reports")]

Secrets

Create a user-scoped secret once. The API stores the value in the deployment's configured secret backend and only stores metadata in the database.

client.secrets.create("openai", "sk-...")

secrets = client.secrets.list()
secret = client.secrets.get("openai")
client.secrets.update("openai", "sk-new")
client.secrets.delete("openai")

Use secrets in runs by logical name. A string shorthand injects the secret as an environment variable with the same name:

run = client.runs.create(
    sandbox="my-sandbox:latest",
    prompt="Use the injected secret",
    secrets=["openai"],
)

For a custom environment variable:

from trelent_agents import RunSecretBinding

secrets=[RunSecretBinding(name="openai", env_var="OPENAI_API_KEY")]

To mount a secret as a file instead of an env var:

secrets=[RunSecretBinding(name="openai", mount=True)]

The runner writes mounted secrets to /mnt/secrets/<secret_name> inside the sandbox. You can also set both env_var and mount=True to expose both forms.

Docker Registry Setup

When auth is enabled, push sandbox images to your user namespace on the registry:

# Login with your OAuth2 credentials
docker login registry.example.com -u <client_id> -p <client_secret>

# Push to your namespace
docker tag my-sandbox:latest registry.example.com/<client_id>/my-sandbox:latest
docker push registry.example.com/<client_id>/my-sandbox:latest

When creating runs via the SDK, just use the sandbox name without the namespace prefix:

run = client.runs.create(
    sandbox="my-sandbox:latest",  # not "<client_id>/my-sandbox:latest"
    prompt="...",
)

The API resolves the full registry path automatically based on your authenticated identity.

Types

The SDK exports the following types:

from trelent_agents import (
    Client,
    ClaudeCodeHarnessSpec,
    CodexHarnessSpec,
    CommonEvent,
    EventType,
    Run,
    RunStatus,
    RunResult,
    RunStatusResponse,
    RegistrySandbox,
    CheckpointResponse,
    CancelRunResponse,
    ChatHistoryEntry,
    FileOutput,
    OutputFile,
    HealthResponse,
    HarnessInfo,
    HarnessKind,
    HarnessSpec,
    TokenRequest,
    TokenResponse,
    ToolKind,
    WorkflowIds,
    LocalImporter,
    SharedWorkspaceExporter,
    SharedWorkspaceImporter,
    S3Exporter,
    RunSecretBinding,
    SecretResponse,
    APIError,
    NotFoundError,
    ValidationError,
)

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

trelent_agents-0.2.8.tar.gz (14.5 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

trelent_agents-0.2.8-py3-none-any.whl (23.2 kB view details)

Uploaded Python 3

File details

Details for the file trelent_agents-0.2.8.tar.gz.

File metadata

  • Download URL: trelent_agents-0.2.8.tar.gz
  • Upload date:
  • Size: 14.5 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: uv/0.11.16 {"installer":{"name":"uv","version":"0.11.16","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}

File hashes

Hashes for trelent_agents-0.2.8.tar.gz
Algorithm Hash digest
SHA256 e709418f596d0c31c394f89fdb8ffeda782baa5870014e16fa795abf810d6ab8
MD5 5e9ba2b97cdc1e59c5e13ced00df6823
BLAKE2b-256 6491b4473716b07678be105364776e01a0b3e13ebe72897f49158bc7e8e348b4

See more details on using hashes here.

File details

Details for the file trelent_agents-0.2.8-py3-none-any.whl.

File metadata

  • Download URL: trelent_agents-0.2.8-py3-none-any.whl
  • Upload date:
  • Size: 23.2 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: uv/0.11.16 {"installer":{"name":"uv","version":"0.11.16","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}

File hashes

Hashes for trelent_agents-0.2.8-py3-none-any.whl
Algorithm Hash digest
SHA256 90fbb8893125d01b0e72fac1f6a36f165f0d12d82096301ef0d0a48f2d6e0602
MD5 8024bbe7e2138a605ad6b8134487f3e8
BLAKE2b-256 155a3ea3dc3d5e33f362369e5536ad23b6af5eead9aac1ae1bba22199ca5fa91

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page