agentrspy
agentrspy is the Python port of the Rust project agentrs: an async-native SDK for building AI agents with a unified provider interface, composable tools, MCP integration, pluggable memory, multi-agent orchestration, and YAML-driven runtime loading.
The goal of this port is behavioral fidelity first and Python ergonomics second: keep the same core capabilities, preserve the tested runtime semantics, and expose them through idiomatic Python APIs with type hints.
Highlights
- OpenAI, Azure OpenAI, Anthropic, Gemini, and Ollama providers
- Built-in tools for calculation, web fetch/search, filesystem access, shell execution, and inline Python execution
- MCP support for local stdio servers and remote Streamable HTTP endpoints
- In-memory, sliding-window, token-aware, vector, and optional Redis memory backends
- Single-agent loops for ReAct, single-pass reasoning, plan-and-execute, and custom instruction modes
- Multi-agent orchestration with sequential, parallel, supervisor, and graph routing
- YAML loading for single agents, orchestrators, and generic runtimes
- Examples, tests, and rewritten Python-first documentation
Installation
pip install -e .
Optional extras:
pip install -e ".[redis]"
pip install -e ".[dev]"
pip install -e ".[full]"
Quick Start
from __future__ import annotations
import asyncio
from dotenv import load_dotenv
from agentrspy.prelude import Agent, CalculatorTool, LoopStrategy, OpenAiProvider
async def main() -> None:
load_dotenv()
llm = OpenAiProvider.from_env().build()
agent = (
Agent.builder()
.llm(llm)
.system("You are a concise assistant.")
.tool(CalculatorTool())
.loop_strategy(LoopStrategy.react(max_steps=4))
.build()
)
output = await agent.run("What is 7 * (8 + 1)?")
print(output.text)
if __name__ == "__main__":
asyncio.run(main())
Project Layout
agentrspy/
├── agentrspy/ # import-friendly wrapper package
├── src/agentrspy/core # shared contracts, types, errors, streaming helpers
├── src/agentrspy/llm # provider implementations
├── src/agentrspy/tools # registry, built-ins, decorator-based tools
├── src/agentrspy/mcp # MCP transport, protocol, adapters
├── src/agentrspy/memory # memory backends
├── src/agentrspy/agents # builders and execution loops
├── src/agentrspy/multi # orchestrators, graph routing, event bus
├── src/agentrspy/config.py # YAML runtime loading
├── examples/ # runnable Python examples
├── tests/ # pytest coverage for parity-critical behavior
└── docs/ # rewritten Python documentation
Core Semantics Preserved From Rust
- ReAct stores the assistant message before executing tool calls
- Tool failures are returned to the model as tool error outputs instead of raising immediately
- Sequential multi-agent routing feeds each agent the previous agent's
output.text - Parallel multi-agent routing merges outputs as
[agent_name]\n<text>blocks separated by blank lines - Agent streaming intentionally replays final whitespace-split tokens after completion to match the current Rust behavior
- YAML runtime loading accepts the same practical config shapes used by the Rust examples and integration tests
Examples
examples/simple_agent.pyexamples/custom_tool.pyexamples/streaming.pyexamples/multi_agent.pyexamples/mcp_integration.pyexamples/yaml_single_agent.pyexamples/yaml_multi_agent.pyexamples/yaml_runtime.py
Run one with:
python examples/simple_agent.py
python examples/multi_agent.py
python examples/yaml_runtime.py
Or use the module entrypoint:
python -m agentrspy --config examples/configs/single-agent.yaml --input "What is 21 * 2?"
Environment Variables
See .env.example for a ready-to-copy template.
Common values:
OPENAI_API_KEYOPENAI_BASE_URLOPENAI_MODELAZURE_OPENAI_ENDPOINTAZURE_OPENAI_KEYAZURE_OPENAI_MODELANTHROPIC_API_KEYGEMINI_API_KEYCONTEXT7_API_KEY
Documentation
docs/architecture.mddocs/providers.mddocs/tools.mddocs/memory.mddocs/multi-agent.mddocs/yaml.mddocs/migration-from-rust.mddocs/testing.md
Testing
python -m pytest
python -m compileall src agentrspy tests examples
Notes
- Python integers do not overflow like Rust integer types; where Rust relied on integer bounds, Python callers should validate explicitly.
- The Rust macro-based
#[tool]workflow becomes a Python@tool(...)decorator. - Rust feature flags become Python extras and import-time availability rather than compile-time gating.
- Anthropic and Gemini currently implement
complete()but keep streaming intentionally unsupported, matching the Rust scope.
License
MIT.
Release files for agentrspy 0.1.0
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | |
|---|---|---|---|
| agentrspy-0.1.0.tar.gz | 37.0 kB | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| agentrspy-0.1.0-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 87.3 kB
Release files / agentrspy-0.1.0.tar.gz
| Download URL | agentrspy-0.1.0.tar.gz |
|---|---|
| Size | 37.0 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
03997f02723c76e2819d5820a1a5711e9a1a843975f4b20eafe4833f75a86b68
|
|
BLAKE2b-256 checksum How to use checksums |
a8cafb6db732a09e6cc3e5304ba31edc20b1ee87981b8ccef8d22db834e47ff1
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/6.2.0 CPython/3.12.4
|
Release files / agentrspy-0.1.0-py3-none-any.whl
| Download URL | agentrspy-0.1.0-py3-none-any.whl |
|---|---|
| Size | 50.2 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
7e7e5574b0cc80bfca9c8d5d9c0083d3c707d704e37e125df0ff072e6d10706d
|
|
BLAKE2b-256 checksum How to use checksums |
3a9a1bb988484543653b052dabae00cf6bdd400a7e745320b23c87917ee20f7a
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/6.2.0 CPython/3.12.4
|