Catalog PyPI
Back to packageRELEASE DETAILS

14.0.0

PyPI

agent-relay-sdk

Python SDK for Agent Relay workflows

Published13 Oct 2026
Direct dependencies11
Transitive dependenciesNot calculated

README

Version 14.0.0 documentation

Agent Relay Python SDK

Python SDK for two workflows:

  • Orchestrate mode spawns and manages AI agents from Python.
  • Communicate mode puts an existing agent framework on Relaycast with Relay + on_relay().

Installation

Orchestrate

pip install agent-relay-sdk

Communicate

pip install "agent-relay-sdk[communicate]"

The SDK ships per-platform wheels with the broker binary embedded. pip install is the network boundary — no downloads happen at import or first use. Communicate mode also needs the framework package you want to wrap, such as claude-agent-sdk, google-adk, agno, swarms, or crewai.

Requirements

  • Python 3.10+

  • A supported platform (the wheel ships a prebuilt agent-relay-broker):

    PlatformWheel tag
    macOS Apple Siliconmacosx_11_0_arm64
    macOS Intelmacosx_10_12_x86_64
    Linux x86_64manylinux_2_17_x86_64.manylinux2014_x86_64
    Linux aarch64manylinux_2_17_aarch64.manylinux2014_aarch64

    Linux binaries are built statically against musl, so they install on glibc and musl distros (Debian, Ubuntu, RHEL, Alpine, …). Other platforms (Windows, FreeBSD, linux-armv7) are unsupported — pip install will fail with "no matching distribution found".

    To override the bundled binary (e.g. for local development against a custom broker build), set BROKER_BINARY_PATH or AGENT_RELAY_BIN to an absolute path.

Development

For an editable install (pip install -e packages/sdk-py), build the broker locally and copy it into the wheel tree:

cargo build --release --bin agent-relay-broker
packages/sdk-py/scripts/sync-broker-dev.sh

The destination (src/agent_relay/bin/) is gitignored. Alternatively, set BROKER_BINARY_PATH=$(pwd)/target/release/agent-relay-broker in your shell.

Choose a Mode

Orchestrate

Use AgentRelay when you want Python to spawn agents, wait for readiness, route messages, and shut everything down.

import asyncio
from agent_relay import AgentRelay, Models

async def main():
    relay = AgentRelay(channels=["dev"])
    relay.on_message_received = lambda msg: print(f"[{msg.from_name}]: {msg.text}")

    await relay.claude.spawn(
        name="Reviewer",
        model=Models.Claude.OPUS,
        channels=["dev"],
        task="Review the PR and suggest improvements",
    )
    await relay.codex.spawn(
        name="Builder",
        model=Models.Codex.GPT_5_3_CODEX,
        channels=["dev"],
        task="Implement the suggestions",
    )

    await asyncio.gather(
        relay.wait_for_agent_ready("Reviewer"),
        relay.wait_for_agent_ready("Builder"),
    )
    await relay.shutdown()

asyncio.run(main())

Communicate

Use Relay + on_relay() when your framework already owns the runtime and you only want Relaycast messaging.

relay = Relay("Researcher")
agent = FrameworkAgent(...)
agent = on_relay(agent, relay)

Supported Python adapters:

  • OpenAI Agents
  • Claude Agent SDK
  • Google ADK
  • Agno
  • Swarms
  • CrewAI

The wrapped agent gets Relay tools for direct messages, channel posts, inbox reads, and agent discovery. Framework-specific receive hooks are added automatically.

API

AgentRelay

The main Orchestrate entry point. Pass channels to subscribe to message channels.

relay = AgentRelay(channels=["dev", "planning"])

Spawning Agents

Use runtime-specific spawners:

await relay.claude.spawn(name="Agent1", model=Models.Claude.SONNET, channels=["dev"], task="...")
await relay.codex.spawn(name="Agent2", model=Models.Codex.GPT_5_3_CODEX, channels=["dev"], task="...")
await relay.gemini.spawn(name="Agent3", model=Models.Gemini.GEMINI_2_5_PRO, channels=["dev"], task="...")

worker = await relay.claude.spawn(
    name="HookedWorker",
    channels=["dev"],
    on_start=lambda ctx: print(f"spawning {ctx['name']}"),
    on_success=lambda ctx: print(f"spawned {ctx['name']} ({ctx['runtime']})"),
    on_error=lambda ctx: print(f"failed to spawn {ctx['name']}: {ctx['error']}"),
)

await worker.release(
    "done",
    on_start=lambda ctx: print(f"releasing {ctx['name']}"),
    on_success=lambda ctx: print(f"released {ctx['name']}"),
)

Relay

The Communicate-mode client. Configure it directly or via RELAY_WORKSPACE, RELAY_API_KEY, and RELAY_BASE_URL.

from agent_relay import Relay

relay = Relay("Researcher")
await relay.send("Lead", "Status update")
await relay.post("docs", "Wave 5.1 complete")
messages = await relay.inbox()

human = relay.system()
await human.send_message(
    to="Agent1",
    text="Please start the analysis",
    # wait (default) queues for the next safe idle boundary and can remain
    # unread while the recipient is busy. steer requests immediate injection
    # and may interrupt active work. Send success confirms enqueue only.
    mode="wait",
)

on_relay()

Wrap a framework-owned agent or options object and keep the runtime you already use.

from agent_relay import Relay, on_relay

relay = Relay("Researcher")
wrapped = on_relay(framework_agent_or_options, relay)

Event Hooks

relay.on_message_received = lambda msg: ...       # New message
relay.on_agent_ready = lambda agent: ...          # Agent connected
relay.on_agent_exited = lambda agent: ...         # Agent exited
relay.on_agent_spawned = lambda agent: ...        # Agent spawned
relay.on_worker_output = lambda data: ...         # Agent output
relay.on_agent_idle = lambda agent: ...           # Agent idle

Models

Models.Claude.OPUS
Models.Claude.SONNET
Models.Claude.HAIKU

Models.Codex.GPT_5_2_CODEX
Models.Codex.GPT_5_3_CODEX

Models.Gemini.GEMINI_2_5_PRO
Models.Gemini.GEMINI_2_5_FLASH

License

Apache-2.0

Downloads & popularity

Awaiting observations

No metric observations yet

Download counts and popularity will appear here as the collector receives them.

Declared dependencies 15

Native requirements
11 direct targetsNot calculated transitive count
Package / targetRequirementRelationship
pyyaml
Environment
{
  "extras": "",
  "marker": null,
  "requires_python": ">=3.10",
  "evaluation": "NOT_EVALUATED"
}
pyyaml>=6.0runtime
agno
Environment
{
  "extras": "",
  "marker": "extra == \"agno\"",
  "requires_python": ">=3.10",
  "evaluation": "NOT_EVALUATED"
}
agno>=0.1; extra == "agno"runtime
claude-agent-sdk
Environment
{
  "extras": "",
  "marker": "extra == \"claude-sdk\"",
  "requires_python": ">=3.10",
  "evaluation": "NOT_EVALUATED"
}
claude-agent-sdk>=0.1; extra == "claude-sdk"runtime
aiohttp
Environment
{
  "extras": "",
  "marker": "extra == \"communicate\"",
  "requires_python": ">=3.10",
  "evaluation": "NOT_EVALUATED"
}
aiohttp>=3.9; extra == "communicate"runtime
relaycast-sdk
Environment
{
  "extras": "",
  "marker": "extra == \"communicate\"",
  "requires_python": ">=3.10",
  "evaluation": "NOT_EVALUATED"
}
relaycast-sdk>=1.0.0; extra == "communicate"runtime
crewai
Environment
{
  "extras": "",
  "marker": "extra == \"crewai\"",
  "requires_python": ">=3.10",
  "evaluation": "NOT_EVALUATED"
}
crewai>=0.1; extra == "crewai"runtime
aiohttp
Environment
{
  "extras": "",
  "marker": "extra == \"dev\"",
  "requires_python": ">=3.10",
  "evaluation": "NOT_EVALUATED"
}
aiohttp>=3.9; extra == "dev"runtime
pytest-asyncio
Environment
{
  "extras": "",
  "marker": "extra == \"dev\"",
  "requires_python": ">=3.10",
  "evaluation": "NOT_EVALUATED"
}
pytest-asyncio>=0.23; extra == "dev"runtime
pytest-cov
Environment
{
  "extras": "",
  "marker": "extra == \"dev\"",
  "requires_python": ">=3.10",
  "evaluation": "NOT_EVALUATED"
}
pytest-cov>=5.0; extra == "dev"runtime
pytest
Environment
{
  "extras": "",
  "marker": "extra == \"dev\"",
  "requires_python": ">=3.10",
  "evaluation": "NOT_EVALUATED"
}
pytest>=8.0; extra == "dev"runtime
relaycast-sdk
Environment
{
  "extras": "",
  "marker": "extra == \"dev\"",
  "requires_python": ">=3.10",
  "evaluation": "NOT_EVALUATED"
}
relaycast-sdk>=1.0.0; extra == "dev"runtime
google-adk
Environment
{
  "extras": "",
  "marker": "extra == \"google-adk\"",
  "requires_python": ">=3.10",
  "evaluation": "NOT_EVALUATED"
}
google-adk>=0.1; extra == "google-adk"runtime
aiohttp
Environment
{
  "extras": "",
  "marker": "extra == \"node\"",
  "requires_python": ">=3.10",
  "evaluation": "NOT_EVALUATED"
}
aiohttp>=3.9; extra == "node"runtime
relaycast-sdk
Environment
{
  "extras": "",
  "marker": "extra == \"node\"",
  "requires_python": ">=3.10",
  "evaluation": "NOT_EVALUATED"
}
relaycast-sdk>=1.0.0; extra == "node"runtime
openai-agents
Environment
{
  "extras": "",
  "marker": "extra == \"openai-agents\"",
  "requires_python": ">=3.10",
  "evaluation": "NOT_EVALUATED"
}
openai-agents>=0.1; extra == "openai-agents"runtime

Distribution files

4 collected
agent_relay_sdk-14.0.0-py3-none-macosx_10_12_x86_64.whl

bdist_wheel · 7,791.12 KB · Python py3

Source file
agent_relay_sdk-14.0.0-py3-none-macosx_11_0_arm64.whl

bdist_wheel · 7,175.32 KB · Python py3

Source file
agent_relay_sdk-14.0.0-py3-none-manylinux2014_aarch64.manylinux_2_17_aarch64.whl

bdist_wheel · 8,872.06 KB · Python py3

Source file
agent_relay_sdk-14.0.0-py3-none-manylinux2014_x86_64.manylinux_2_17_x86_64.whl

bdist_wheel · 8,015.25 KB · Python py3

Source file

Metadata history

Meaningful changes
Current collected state Current

Observed since 20 Oct, 23:11 UTC

No superseded metadata states collected. Unchanged observations do not create new revisions.

Record identity

package_version:470a1506a0d55fed62ae3f5dff763593477e2cc4f2d7d89f6f3c66214b2dfcdc

Other collected versions

View all collected versions →