Metadata-Version: 2.4
Name: kanon-langgraph
Version: 0.1.0
Summary: Crash-resumable LangGraph agents with tamper-evident, cryptographically signed checkpoints. Drop-in KanonCheckpointer for LangGraph.
Author: Rags Srinivasan
License: MIT
Project-URL: Homepage, https://github.com/ragsvasan/kanon
Project-URL: Repository, https://github.com/ragsvasan/kanon
Classifier: Development Status :: 3 - Alpha
Classifier: Intended Audience :: Developers
Classifier: License :: OSI Approved :: MIT License
Classifier: Operating System :: OS Independent
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 :: Python Modules
Classifier: Topic :: System :: Monitoring
Requires-Python: >=3.10
Description-Content-Type: text/markdown
Requires-Dist: alembic>=1.13.0
Requires-Dist: cryptography>=42.0.0
Provides-Extra: langgraph
Requires-Dist: langgraph>=0.2.0; extra == "langgraph"
Requires-Dist: langchain-core>=0.2.0; extra == "langgraph"
Requires-Dist: httpx>=0.27.0; extra == "langgraph"

# Kanon

## Your LangGraph agent crashed at step 38. Kanon resumes it at step 38.

```python
# Before
from langgraph.checkpoint.memory import MemorySaver
graph = builder.compile(checkpointer=MemorySaver())

# After — agents resume from last signed checkpoint on restart
from kanon.langgraph import KanonCheckpointer
graph = builder.compile(checkpointer=KanonCheckpointer(api_key="kn_..."))
```

```
pip install kanon[langgraph]
```

Every checkpoint is cryptographically signed. If the stored state is altered
between save and resume, Kanon raises `KanonTamperedError` before returning
state to LangGraph.

[Run the demo →](demo/crash_resume_demo.py)

---

## Crash-resume demo

```
$ python demo/crash_resume_demo.py --demo

[kanon-demo] Starting 5-step research agent  thread=demo-thread-1
  Step 1/5  node=gather_sources        ✓  snap=snap_a1b2c3  (signed)
  Step 2/5  node=summarise_sources     ✓  snap=snap_d4e5f6  (signed)
  Step 3/5  node=draft_findings        ✓  snap=snap_g7h8i9  (signed)
💥 Simulated crash after step 3. Process state wiped.

[kanon-demo] Resuming  thread=demo-thread-1  from=snap_g7h8i9
  Step 4/5  node=verify_findings       ✓  snap=snap_j0k1l2  (signed)
  Step 5/5  node=write_report          ✓  snap=snap_m3n4o5  (signed)

[kanon-demo] Complete. Signed receipt chain:
  snap_a1b2c3  →  snap_d4e5f6  →  snap_g7h8i9  (crash)  →  snap_j0k1l2  →  snap_m3n4o5
  proof_bundle hash: e3b0c442...  agent=kanon-demo  tenant=demo
```

Or as two separate processes:

```bash
bash demo/run_demo.sh
```

---

## How it works

`KanonCheckpointer` is a drop-in replacement for LangGraph's `MemorySaver`.
After each node, LangGraph calls `put()` — Kanon signs the checkpoint and
stores it server-side. On resume, `get_tuple()` calls `restore_snapshot`,
the server verifies the HMAC proof bundle, and LangGraph continues from the
last good state.

The signed receipt chain links every checkpoint to its predecessor. After a
crash, the resume linkage (`work_artifacts[resume_linkage]`) keeps the
server-side audit graph connected across the recovery boundary.
