Skip to main content

A framework to build powerful AI agent teams.

Project description

🐮 Calfkit

Build powerful teams of AI agents that freely discover each other and collaborate on work, automatically.

License PyPI version PyPI downloads Python versions codecov Ask DeepWiki

Calfkit agents dynamically find each other at runtime and choreograph work. No hard-coded orchestrator or extra wiring. The framework for building free-flowing and powerful multi-agent teams.


Installation

pip install calfkit

Quickstart

An agent (that can discover other agents)

from calfkit import Agent, Messaging, Tools, OpenAIResponsesModelClient

general = Agent(
    name="general",
    description="Answers simple questions and routes requests to whoever can handle it.",
    system_prompt="You are a general assistant. Defer technical questions to other agents.",
    model_client=OpenAIResponsesModelClient(model_name="gpt-5.4-mini"),
    peers=[Messaging(discover=True)],   # discover and collaborate w/ any agent at runtime
)

Runtime discoverability allows you to add new agents and tools to the team at any time

from calfkit import Agent, agent_tool, Tools, ToolContext, OpenAIResponsesModelClient

finance = Agent(
    name="finance",
    description="Answers the user's personal finance questions.",
    system_prompt="You are the personal finance specialist. Use tools to look up user data.",
    model_client=OpenAIResponsesModelClient(model_name="gpt-5.4-mini"),
    tools=[Tools(discover=True)],   # discover and use any tool at runtime
)

@agent_tool
def lookup_account_balance(ctx: ToolContext) -> str:
    """Look up the user's current account balance in USD."""
    return f"Account balance: ${ctx.deps.get('balance', '0.00')}"

Running your agents

Start the general assistant independently. Assuming it's saved in general_help.py.

# using the ck CLI
ck run general_help:general

Separately, start the finance agent and the lookup_account_balance tool node. Assuming it's saved in finance_help.py.

ck run finance_help:finance finance_help:lookup_account_balance

Ask the general assistant a question. Notice it's able to dynamically discover and consult the finance agent for help without any hard-coded configuration of finance agent's existence.

import asyncio
from calfkit import Client

async def main():
    async with Client.connect("<calfkit_agent_mesh>") as client:
        result = await client.agent("general").execute("Do I have enough money to afford a new car?")
        print(result.output)
        # LOL nah twin

if __name__ == "__main__":
    asyncio.run(main())
python ask.py

Calfkit agents discover and communicate over an agent mesh, provided by either Calfkit Cloud (in alpha) or your own self-hosted version.

Start one locally with Docker:

git clone https://github.com/calf-ai/calfkit-broker && cd calfkit-broker && make dev-up

Or skip the self-hosting with Calfkit Cloud — a fully-managed agent mesh your agents can join from anywhere.

Why Calfkit?

  • Dynamic agent-to-agent discovery and collaboration. Agents find each other at runtime and work together — messaging each other and handing off tasks — so you build multi-agent systems without complex wiring or orchestration, and extend team capabilities at any time.
  • No bottleneck, no single point of failure. Every agent runs and scales as an independent microservice, so your agent teams are resilient and scalable from day one.
  • Act on live data in realtime. Agents are event-driven so they act on realtime data streams, sending live results wherever they're needed — build agents that work like continuous workflows, not one-off requests.

Examples

See examples/ for more examples.

  • Agent, tool & consumer — a weather agent and its get_weather tool deployed as separate services and invoked over the broker, with a consumer node tapping the agent's output stream.
  • Multi-agent panel — three persona agents (optimist, skeptic, pragmatist) debate over one shared transcript, each automatically seeing the thread from its own point of view.
  • MCP toolbox — give an agent a live web-fetch tool from an MCP server, deployed as its own node and referenced by name — the agent's code never imports it.

Documentation

In-repo documentation lives under docs/.

New to building agent teams? Start with the tutorial Build a multi-agent support desk — build and run three agents that discover each other and collaborate by messaging and handoff.

How-to guides — goal-oriented walkthroughs:

  • How to call agents from a client — the agent(name) gateway and its send / start / execute triad, multi-turn conversations, runtime dependency injection (deps), temporary instructions, the events() firehose, and the typed client errors.
  • How to tap a topic with a consumer node — terminal sinks that run arbitrary Python against every event on a topic; tap an agent's publish_topic to log, persist, or fan out.
  • How to guard and transform node invocations — guard an invocation with before_node (transform the input, short-circuit the body, or raise to block), and validate or reshape its output with after_node.
  • How to handle errors and faults — recover from a failed node or callee with on_node_error / on_callee_error, mint typed faults with NodeFaultError, and inspect an ErrorReport.
  • How to let agents discover and use tools at runtime — reference deployed function tool nodes by name (or every live one with discover=True) with Tools; agents discover their schemas at runtime, so an agent's deployment never imports the tool's code.
  • How to give agents MCP tools — deploy an MCPToolboxNode fronting an MCP server and pass it to agents like a tool node; tools are discovered and kept fresh across processes automatically.
  • How to let agents find and reach each other at runtime — agents discover each other by name (no hardcoded addresses) and collaborate two ways: consult a peer and keep control (Messaging), or transfer control to a specialist (Handoff).
  • Worker lifecycle & embedding — open long-lived resources at startup and close them on shutdown, publish presence events, and run with run(), the embeddable start()/stop(), or async with worker:.

Reference:

  • API reference — the public surface re-exported from the top-level calfkit package, with the key entry-point signatures.
  • CLI reference — the ck run and ck topics commands.
  • Topic provisioning — the experimental, opt-in topic-creation helper for dev/CI.

Contributing

Issues and pull requests are welcome. Please open an issue to discuss substantial changes before sending a PR.

See CONTRIBUTING.md for development setup, the quality gates (make fix / make check / make test), PR conventions, and how to write and run tests — including the real-broker integration tests.

License

This project is licensed under the Apache License 2.0. See the LICENSE file for details.

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

calfkit-0.12.0.tar.gz (1.4 MB view details)

Uploaded Source

Built Distribution

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

calfkit-0.12.0-py3-none-any.whl (749.9 kB view details)

Uploaded Python 3

File details

Details for the file calfkit-0.12.0.tar.gz.

File metadata

  • Download URL: calfkit-0.12.0.tar.gz
  • Upload date:
  • Size: 1.4 MB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.12

File hashes

Hashes for calfkit-0.12.0.tar.gz
Algorithm Hash digest
SHA256 f628e0678c4dff6e2eeb8823d5ca87d52181f00309cd376c574ba241fe17537e
MD5 2dcc7c51b66d97423d749f76b0500a23
BLAKE2b-256 ccfc5e55a36c8ec60fbbe9cd04cb277d5ac7320e465f15073a496d2629b1d026

See more details on using hashes here.

Provenance

The following attestation bundles were made for calfkit-0.12.0.tar.gz:

Publisher: release.yml on calf-ai/calfkit-sdk

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file calfkit-0.12.0-py3-none-any.whl.

File metadata

  • Download URL: calfkit-0.12.0-py3-none-any.whl
  • Upload date:
  • Size: 749.9 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.12

File hashes

Hashes for calfkit-0.12.0-py3-none-any.whl
Algorithm Hash digest
SHA256 325188a6ec2b40c218288b19f9187a76087926d8b16f1143c7a45b0adb8b14fb
MD5 c93bc66dc17c2b53ae8a3370fa9d3d57
BLAKE2b-256 045a65491171af9b090a9045b4803c3b558d1a76aac962b055beac7f5ca5ab73

See more details on using hashes here.

Provenance

The following attestation bundles were made for calfkit-0.12.0-py3-none-any.whl:

Publisher: release.yml on calf-ai/calfkit-sdk

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

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