Metadata-Version: 2.4
Name: zanii-agents
Version: 0.9.0
Summary: Runtime for accountable AI agents: signed receipts for every action, human gates, injection defenses, hiring per proven task. Standard library only.
Author-email: Zanii <info@zanii.agency>
License: MIT
Project-URL: Homepage, https://www.agents.zanii.agency
Project-URL: Company, https://www.zanii.agency
Project-URL: Ledger, https://ledger.zanii.agency
Project-URL: Documentation, https://www.agents.zanii.agency/docs
Project-URL: Contact, https://www.zanii.agency/contact
Keywords: ai-agents,agent,llm,proof-of-action,zanii,agentcv,escrow,mcp,a2a
Classifier: Development Status :: 4 - Beta
Classifier: Intended Audience :: Developers
Classifier: License :: OSI Approved :: MIT License
Classifier: Programming Language :: Python :: 3
Classifier: Programming Language :: Python :: 3.10
Classifier: Programming Language :: Python :: 3.11
Classifier: Programming Language :: Python :: 3.12
Classifier: Topic :: Software Development :: Libraries
Requires-Python: >=3.10
Description-Content-Type: text/markdown
License-File: LICENSE
Provides-Extra: zanii
Requires-Dist: zanii>=0.24.0; extra == "zanii"
Provides-Extra: memory
Requires-Dist: zaniidb-agent-memory>=0.12.0; extra == "memory"
Provides-Extra: bench
Requires-Dist: agentdojo==0.1.35; extra == "bench"
Dynamic: license-file

<p align="center">
  <img src="https://www.agents.zanii.agency/assets/banner.svg" alt="zanii-agents" width="100%">
</p>

<p align="center">
  <a href="https://pypi.org/project/zanii-agents/"><img alt="PyPI" src="https://img.shields.io/pypi/v/zanii-agents.svg"></a>
  <a href="https://pypi.org/project/zanii-agents/"><img alt="Python" src="https://img.shields.io/pypi/pyversions/zanii-agents.svg"></a>
  <a href="https://pypi.org/project/zanii-agents/"><img alt="License" src="https://img.shields.io/pypi/l/zanii-agents.svg"></a>
</p>

# zanii-agents

`zanii-agents` is a Python runtime for AI agents that a company can hire for a defined job and hold to account afterwards. Each tool call, human approval and run outcome is recorded as a signed, hash-chained receipt. With the optional [Zanii](https://www.zanii.agency) packages, those receipts go to a public transparency log, the agent carries a signed CV built from the log, and payment is released per task only when the receipt is proven.

The package has no dependencies. It runs offline with a built-in mock model, and it connects to any OpenAI-compatible endpoint for real work.

## Installation

```bash
pip install zanii-agents                 # runtime only, standard library
pip install "zanii-agents[zanii]"        # ledger, identity, escrow, industry profiles
pip install "zanii-agents[memory]"       # long-term memory with a firewall (ZaniiDB)
```

Python 3.10 or newer. The import name is `agents_standard`.

## Quickstart

```python
from agents_standard import Agent, ModelGateway, MockProvider, Router, Tool, ToolRegistry

def track_order(order_id: str) -> dict:
    return {"order_id": order_id, "status": "delivered"}

registry = ToolRegistry()
registry.register(Tool("track_order", track_order, "Look up an order",
                       {"type": "object", "properties": {"order_id": {"type": "string"}}},
                       permissions=frozenset({"read:orders"})))

agent = Agent("tracker", "You track orders and report their status.",
              ModelGateway([MockProvider()]), registry, {"read:orders"}, keywords=["track"])

result = Router([agent]).run("track order ORD-100")
print(result.ok, result.output, result.receipt)
```

To use a real model, replace `MockProvider()` with `OpenAICompatProvider("model-name", base_url="https://.../v1")`. The gateway accepts a list of providers and falls back in order.

## What the runtime does

<p align="center">
  <img src="https://www.agents.zanii.agency/assets/architecture.svg" alt="Task flow" width="90%">
</p>

| Concern | Mechanism |
|---|---|
| Least privilege | A tool declares the permissions it needs; an agent only sees tools whose permissions it holds. |
| Bounded runs | Step, cost and latency budgets per run; identical repeated calls end the run. |
| Prompt injection | Untrusted text is scanned, quarantined and, when flagged, summarised by a separate model before the planner sees it. Values that first appeared inside an injection cannot be used as write arguments. |
| Hallucination | Sampled self-agreement and a fact check against tool data; low agreement routes to a human instead of shipping an answer. |
| Human oversight | A confidence floor and a signed rulebook decide which actions need approval. Every decision is receipted. |
| Proof of action | Every tool call, approval, disclosure and run outcome is a receipt in a hash chain. Locally: HMAC over a JSONL file. With Zanii: Ed25519 did:key signatures on a public Merkle log. |
| Kill switch | The owner revokes the delegation; the next run ends with `halted` and executes nothing. Peers over A2A receive a distinct error. |
| Memory | Bounded episodic and procedural memory in a JSON file, or ZaniiDB per client with a memory firewall. |
| Interop | MCP tool-server client with size caps; A2A agent card and JSON-RPC server with bearer auth, rate limiting and health endpoints. |

## Measured behaviour

The numbers below come from the benchmark scripts in `bench/` and can be reproduced against any OpenAI-compatible model. They are for `glm-4.7-flash` on the AgentDojo suites, `important_instructions` attack, defenses off and on.

| Suite | Attacked runs | Attack success, off | Attack success, on |
|---|---|---|---|
| slack | 105 | 52% | 5% |
| banking | 144 | 22% | under 1% |
| workspace | 560 | 3% | 0% |
| travel | 140 | 24% | 1% |

Utility under attack costs between zero and five points on three suites. On workspace an early version of the taint rule blocked legitimate writes; the corrected rule recovered utility from 44% to 76% on a 168-case sample with attacks still at zero. Both result files are kept.

A load test of the A2A server sustains 100 requests per second at a p99 of 28 ms on the mock model. With a live model the ceiling is model latency, roughly one task every ten seconds per process. Details, caveats and the resilience probes are in `docs/readiness-report.md` in the source distribution.

## Hiring an agent for a defined job

With the `zanii` extra, a job is a signed set of artifacts rather than a prompt.

```python
from agents_standard.core.job import Job, Offer
from agents_standard.profiles import PROFILES

job = PROFILES["logistics"].job(
    "cold-chain-monitoring",
    scopes=["tool.read_temperature_log", "tool.flag_violation", "run.*"],
    require_approval=["tool.flag_violation"],
    rate="2.00", currency="AED",
)
offer = Offer.from_files(job, "agent-identity.sealed.json", "owner-identity.sealed.json")

engagement = offer.hire(client)                  # screening, then co-signed terms
escrow = engagement.escrow_for_task(task)        # released only on a proven run.ok
agent = Agent(..., recorder=offer, policy=offer.policy)
result = agent.run(task)
engagement.settle(escrow, result.receipt)        # Merkle proof checked, client signs
```

| Job field | Backed by | Enforced |
|---|---|---|
| `scopes` | owner-signed delegation certificate | the ledger rejects receipts outside the scope |
| `forbid`, `require_approval`, `wall` | signed rulebook, hash stamped on every receipt | before each tool call, and audited afterwards |
| `deny_list` | counterparty screening | before any terms are signed |
| `rate`, commitments | co-signed SLA and per-task escrow, integer minor units | compliance computed from the receipt chain |

Seven industry profiles ship with the regulator's rule as code: public sector, healthcare, finance, tax, real estate, logistics and consumer operations. Each has a test that proves its load-bearing rule, for example that a public-sector decision cannot be issued without a rulebook hash, or that a clinical recommendation requires a named clinician's signature.

## Evidence for insurers and regulators

`agents_standard.packs` builds evidence packs from receipts: an underwriter questionnaire, DIFC Regulation 10, UAE PDPL Article 18, CBUAE guidance and the EU AI Act. Controls the runtime cannot evidence are marked as missing rather than omitted.

## Specifications and conformance

Two documents define the interoperable parts: `spec/agentcv-v1.md` (AgentCV v1) and `spec/engagement-v1.md` (Engagement v1), both in the source distribution and at https://www.agents.zanii.agency. Conformance vectors are generated from the Python reference, and an independent TypeScript implementation in `conformance/ts` passes 103 of 103 checks against them.

## Repository layout

```
agents_standard/     runtime, profiles, packs, control, identity, payments, a2a, mcp
bench/               benchmarks and their results
spec/                AgentCV v1, Engagement v1, conformance vectors
conformance/ts/      TypeScript conformance runner
deploy/              container image, compose file, backup and restore scripts
docs/                API reference, runbooks, deployment guide, readiness report
examples/            live runs against the Zanii ledger
pilot/               client-side signer and pilot runbook
```

## Development

```bash
pip download zanii-agents --no-binary :all: --no-deps   # or work from the source distribution
tar xzf zanii_agents-*.tar.gz && cd zanii_agents-*
pip install -e ".[zanii,memory]"
python test_standard.py && python test_profiles.py && python test_money.py \
  && python test_future.py && python test_ops.py && python test_hardening.py
```

Tests that need an optional extra skip when it is absent. The CI workflow runs the same suites, the TypeScript conformance runner, ruff, bandit, pip-audit and a secrets scan.

## Status

Version 0.9.0. The runtime is complete and verified against the public ledger. The production readiness gate in `docs/readiness-report.md` records 27 requirements passing, 10 not applicable and 10 open; the open items need a deployed host, a restore drill or an external penetration test rather than code changes.

## License

MIT. See the `LICENSE` file. Contact: info@zanii.agency. Product site: https://www.agents.zanii.agency.
