Start

Quickstart

Install agentsparty, then ask one agent and declare the same conversation yourself.

The smallest session is a request and a reply.

What the examples show

The first example uses a generated Shape; the second spells out the same route with your own message classes. Both end at a typed return value, so you can see exactly where convenience ends and the protocol begins.

Install

Core package

# Install the core package.
pip install agentsparty

Requires Python 3.10+. Core has no provider dependency.

Start with core when the model is not the point

The core package is enough for protocol construction, projection checks, Script, Machine, Policy, and ap.replies. Install a provider extra only at the boundary where a participant makes live model calls.

Choose the core package when the host supplies its own participants, when you are writing protocol and projection tests, or when model calls will be replaced with ap.replies. This is enough for the offline examples below and keeps installation small.

OpenAI-compatible backend

The examples on this page make live model calls, so install the optional OpenAI-compatible backend and set its credential:

uv add "agentsparty[openai]"
export OPENAI_API_KEY="sk-..."

Needs OPENAI_API_KEY at run time. Keep the key in the process environment or in the secret store used by the host. It is not part of a Session, a Message, or a journal decision, so a journal can be copied for replay without copying provider credentials into the replay artifact.

Verify the environment

Run the import probe below in the interpreter that will launch your service; a shell may have more than one Python on PATH. Then run the session in offline testing to exercise protocol assembly and projection without a provider key. Expose OPENAI_API_KEY and construct ap.model(...) only after both checks pass.

A live model call is deliberately absent from the installation check because it spends provider quota and depends on credentials and transport availability.

Development checkout

# Fetch the repository and install its development dependencies.
git clone https://github.com/qnbhd/agentsparty.git
cd agentsparty
uv sync --all-groups
# Run the test suite after installation.
uv run pytest -q

Verify import

import agentsparty as ap

If the import succeeds but a live example fails, read the exception family: ModelUnavailable usually points to the extra, credential, timeout, or provider name; ModelRefused means the provider answered and declined the request. See error taxonomy before changing the protocol.

One agent

# requires: api-key
import agentsparty as ap

Reader, Writer = ap.roles('Reader', 'Writer')
shape = ap.patterns.request_reply(Reader, Writer)

session = ap.Session(
    shape,
    {
        Writer: ap.Agent(
            ap.model('openai:gpt-5.6-luna'),
            'Write three paragraphs.',
        ),
    },
)
article = session.ask(
    Reader,
    shape.Ask('What does a multi-agent AI system mean?'),
    expect=shape.Answer,
)

print(article.text)

ask makes the host the Reader for one opening message. It does not remove the Reader from the protocol; it supplies that role for this call and waits until the projected endpoint delivers shape.Answer.

Roles are declared with ap.roles(...): a typo is a NameError, not a new role.

Your own conversation

# requires: api-key
import agentsparty as ap

Reader, Writer = ap.roles('Reader', 'Writer')


class Question(ap.Message):
    """What the reader asks."""

    text: str


class Article(ap.Message):
    """The answer, three paragraphs."""

    text: str


protocol = ap.Protocol(
    ap.send(Reader, Writer, Question),
    ap.send(Writer, Reader, Article),
)

session = ap.Session(
    protocol,
    {
        Writer: ap.Agent(
            ap.model('openai:gpt-5.6-luna'),
            'Write three paragraphs.',
        ),
    },
)
article = session.ask(
    Reader,
    Question('What does a multi-agent AI system mean?'),
    expect=Article,
)
print(article.text)

How it works

  1. roles names the seats; the protocol connects those seats with typed messages.
  2. The pattern returns a Shape, which contains the closed Protocol, Ask, and Answer classes.
  3. ask plays the caller role for exactly one opening message, while Writer remains in the cast.
  4. expect=shape.Answer makes the returned value typed, so the result is an Answer, not an unstructured dictionary.

The protocol owns the route. The model only fills the declared payload or picks one of the classes currently on offer.

Next steps

Read messages to see how classes become wire values, protocol to add branches and loops, and patterns for the six ready-made topologies. A deterministic version of this session uses ap.replies and needs no key; see offline testing.

Stable

On this page