Skip to main content

encode

One Python entry-point for any OpenAI-compatible LLM, with an auto-agent loop, durable sessions, and the brain/hands/session primitives from Anthropic's Managed Agents post baked in.

import encode

def get_weather(city: str) -> dict:
    """Get weather by city."""
    return {"city": city, "temp_f": 72}

out = encode.relay(
    model="gpt-4o-mini",
    messages=[{"role": "user", "content": "Weather in Denver?"}],
    tools=[get_weather],
).response

print(out.content)   # "It's 72°F in Denver."

That's the whole "hello world." The model called get_weather, encode dispatched it, fed the result back, and returned the final answer.

What encode is

A Python SDK for any OpenAI-compatible inference endpoint — Courier, OpenAI, vLLM, LM Studio, Ollama, Together, Groq, and more. One relay() function spans /v1/chat/completions and /v1/responses. Pass tools and it runs the loop to completion. Pass a Session and the run is durable. Pass a Terminal and your agent has a shell.

Why encode

  • Auto tool loop. Drop a Python function in tools=; encode introspects the signature, builds the schema, runs the loop, and feeds results back. No decorators, no manual loop scaffolding.
  • Both endpoints, one API. relay() auto-routes between /v1/chat/completions and /v1/responses — same handle, same tool loop, same intercept, same streaming consumer.
  • Sessions as Pydantic event logs. Append-only, BYO storage. session.model_dump() to your DB; Session.model_validate() to resume — across processes, machines, or days.
  • Mid-loop context engineering. Intercept callbacks can append, insert, replace, edit_last_tool_result, or compact the conversation that goes into the next iteration. Real context engineering in the harness, not just observation.
  • ToolExecutor seam. Swap dispatch (local → remote → MCP → sub-agent) without touching the harness.
  • Terminal as a first-class primitive. Persistent bash subprocess that retains cwd/env/venvs across calls. Wrap one in a closure and your agent has a shell.
  • Full sync/async parity. Every helper has a *_async twin; async tool callables and async intercept callbacks just work.
  • Streaming with the loop intact. Stream tokens and tool calls in real time across both endpoints.

60-second tour

import json
import encode

# 1. Plain chat
encode.relay(
    model="gpt-4o-mini",
    messages=[{"role": "user", "content": "hi"}],
).response.content

# 2. With a tool — auto-loop runs until the model stops calling tools
def lookup(q: str) -> dict:
    """Look something up."""
    return {"q": q, "answer": "42"}

encode.relay(
    model="gpt-4o-mini",
    messages=[{"role": "user", "content": "What's the meaning of life?"}],
    tools=[lookup],
).response.content

# 3. With a Session — durable, resumable, BYO persistence
session = encode.Session.open()
encode.relay(
    model="gpt-4o-mini",
    messages=[{"role": "user", "content": "remember: my name is Alex"}],
    session=session,
).response

# Persist anywhere — file, Postgres, Redis, S3...
open("/tmp/agent.json", "w").write(json.dumps(session.model_dump(), default=str))

# Resume anywhere
resumed = encode.Session.model_validate(json.loads(open("/tmp/agent.json").read()))
encode.relay(
    model="gpt-4o-mini",
    messages=[{"role": "user", "content": "what's my name?"}],
    session=resumed,
).response.content   # → "Alex"

Install

pip install encode

Python 3.10+. Configure with a .env (auto-loaded) or kwargs:

# .env
ENCODE_API_KEY=sk-your-key
ENCODE_BASE_URL=https://api.openai.com/v1

OPENAI_API_KEY / OPENAI_BASE_URL are also picked up if ENCODE_* aren't set.

What you can build

Multi-turn chat with stateful Messages — pass a Messages instance and it grows itself across relay() calls.

m = encode.Messages().system("Be brief.")
m.user("name three colors")
encode.relay(model="m", messages=m).response   # m now has the assistant turn too

An agent that stops when it submits a final answer.

def watcher(event):
    if any(tc.name == "submit_final" for tc in event.tool_calls):
        event.stop()

encode.relay(..., tools=[search, submit_final]).intercept(watcher).response

Mid-loop context compaction — trim, summarize, redact, or rewrite history without subclassing anything.

def trim(event):
    event.edit_last_tool_result(lambda c: c[:1000])

encode.relay(..., tools=[noisy_tool], on_intercept=trim).response

Auto tool discovery — the model calls a list_tools bootstrap, an intercept registers the discovered tools on the session, the next iteration uses them.

session = encode.Session.open(tools=[list_tools])

def discover(event):
    for tc in event.tool_calls:
        if tc.name == "list_tools":
            for spec in tc.result or []:
                event.register_tool(IMPLS[spec["function"]["name"]])

encode.relay(model="m", messages=[...], session=session,
             tools=session.tools, on_intercept=discover).response

A bash sandbox tool.

class BashSandbox:
    def __init__(self):
        self._term = None
    def as_tool(self):
        sandbox = self
        def bash(command: str) -> dict:
            """Run a bash command in a persistent shell."""
            self._term = self._term or encode.Terminal()
            r = self._term.run(command, timeout=10.0)
            return {"output": r.output, "exit_code": r.exit_code, "cwd": r.cwd}
        return bash

encode.relay(..., tools=[BashSandbox().as_tool()]).response

Docs

→ docs.md is the entry point — concept map + a link grid into focused topic pages:

quickstart · concepts · relay() · messages · tools · intercept · sessions · executors · terminal · streaming · structured output · whisper · async · errors · cookbook

Status & compatibility

  • Python 3.10+
  • macOS / Linux for Terminal (pexpect-backed)
  • OpenAI-compatible endpoints: OpenAI, Courier, vLLM, LM Studio, Ollama, Together, Groq, and others

License

MIT

Metadata

Release files for courier-encode 0.1.41

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for courier-encode 0.1.41
File Size Uploaded Provenance Actions
courier_encode-0.1.41.tar.gz 139.3 kB Without provenance Details for courier_encode-0.1.41.tar.gz

Built distribution (wheel)

Table of built distributions (wheels) for courier-encode 0.1.41
File Interpreter ABI Platform Actions
courier_encode-0.1.41-py3-none-any.whl Python 3 none any Details for courier_encode-0.1.41-py3-none-any.whl

Total release size: 193.3 kB

Release files / courier_encode-0.1.41.tar.gz

Download URL courier_encode-0.1.41.tar.gz
Size 139.3 kB
Tags Source
SHA-256 checksum
How to use checksums
5673da265f80542db1c37aa3c6bdf20a746cae301648edb0767055a51fa25c6f
BLAKE2b-256 checksum
How to use checksums
b0a261f66336cd6fe60907586d74c871942a77decc376699345e7d76790bf0a9
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via uv/0.11.12 {"installer":{"name":"uv","version":"0.11.12","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"macOS","version":null,"id":null,"libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":null}

Release files / courier_encode-0.1.41-py3-none-any.whl

Download URL courier_encode-0.1.41-py3-none-any.whl
Size 54.0 kB
Tags Python 3
SHA-256 checksum
How to use checksums
5249736513a01cd370a4aaec6955d688f65c4325a3adcff0f9b7239cbbe8c953
BLAKE2b-256 checksum
How to use checksums
f2d6bc530915c8c1aff904e2509d7f948a5b028db125f2edd52cd5d3dfa075f0
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via uv/0.11.12 {"installer":{"name":"uv","version":"0.11.12","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"macOS","version":null,"id":null,"libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":null}

Security for courier-encode 0.1.41

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

No provenance found

None of the files in this release were uploaded with provenance metadata.

A note on package security

PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.

To learn more about protecting yourself from malicious actors, visit our package security documentation.

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page