Skip to main content

Reliability for LLM agents through enforcement, not model size — Agent-Contract-Kernel (ACK) + a fail-closed orchestration engine.

Project description

Ironclad

CI PyPI License: Apache-2.0 Python Status

An agent loop you run yourself — and a development process that turns a one-line idea into a finished product.

You say what you want. "A fast CLI to search files" is enough. From there the agents pin down what you actually mean, weigh the architecture, split the work into units, and write the code with its tests — on your hardware, with any open model, no cloud subscription and no vendor holding the off switch.

The bet behind the project is simple: a small model kept on a short leash beats a big one you merely trust. Ironclad supplies the leash. Every tool call is checked against a schema and retried until it's valid; the mechanical file work runs as plain code, not as something the model has to remember to do. Reliability comes from the contract, not the parameter count — which is exactly why you can swap the model whenever you like.

How the loop works

At the core is an ordinary agent loop, with two things bolted on that make it dependable instead of merely clever: a contract kernel that refuses malformed tool calls, and a memory that gets better the more the loop runs.

flowchart LR
    A(["💬 You describe<br/>what you want"]):::idea --> B["🧠 Agent decides<br/>the next step"]:::step
    B --> C{"🛠️ Tool call"}:::review
    C -->|"schema-checked"| D["▶️ Run it<br/><i>file · shell · search · panel</i>"]:::step
    C -->|"malformed"| B
    D --> E["↩️ Result back<br/>to the model"]:::step
    E --> B
    B -->|"done"| F(["✅ Answer<br/>or delivered work"]):::done
    D -.->|"learns from<br/>every run"| G[("📚 Playbook<br/>ACE")]:::mpr
    G -.->|"informs"| B
    classDef idea fill:#e0e7ff,stroke:#6366f1,color:#1e1b4b,stroke-width:2px
    classDef step fill:#f8fafc,stroke:#94a3b8,color:#1e293b,stroke-width:1.5px
    classDef mpr fill:#ede9fe,stroke:#8b5cf6,color:#4c1d95,stroke-width:2px
    classDef review fill:#fef3c7,stroke:#f59e0b,color:#78350f,stroke-width:2px
    classDef done fill:#d1fae5,stroke:#10b981,color:#065f46,stroke-width:2px

A plain question ("what is 17 × 23?") just runs the loop once and answers. Real work — anything that produces files, a design, a plan — runs the same loop but under a process that keeps it honest.

From an idea to a product

The part most agent tools skip is everything before the code: deciding what "done" means, choosing the architecture on purpose instead of by accident, and making sure the plan actually covers what you asked for. Ironclad puts that in the open, under /project.

flowchart TD
    P(["💬 a one-line idea"]):::idea
    P --> S["📋 Scope<br/><i>the agent asks, you approve</i>"]:::step
    S --> M["⚖️ Design panel<br/><i>7 lenses weigh the architecture</i>"]:::mpr
    M --> D["🧭 Design<br/><i>one proposal + trade-offs</i>"]:::step
    D --> RV{"🔍 Review"}:::review
    RV -->|"findings → revise"| D
    RV -->|"clean"| U["🧩 /plan<br/><i>epic + every unit, scope-checked</i>"]:::step
    U -->|"/auto on<br/><i>review on (default)</i>"| B["✋ Approved-plan boundary<br/><i>marker saved · hard exit</i>"]:::review
    B -->|"/auto on again<br/><i>optional: /approve plan</i>"| R["⚙️ Drain<br/><i>coders write &amp; test each unit</i>"]:::step
    U -.->|"/auto on<br/><i>review off: single run</i>"| R
    R --> X(["🎯 a working product"]):::done
    classDef idea fill:#e0e7ff,stroke:#6366f1,color:#1e1b4b,stroke-width:2px
    classDef step fill:#f8fafc,stroke:#94a3b8,color:#1e293b,stroke-width:1.5px
    classDef mpr fill:#ede9fe,stroke:#8b5cf6,color:#4c1d95,stroke-width:2px
    classDef review fill:#fef3c7,stroke:#f59e0b,color:#78350f,stroke-width:2px
    classDef done fill:#d1fae5,stroke:#10b981,color:#065f46,stroke-width:2px
    linkStyle default stroke:#94a3b8,stroke-width:1.5px

Here's what that looked like on a real run. The prompt was three words of intent, a fast file-search CLI. The agent didn't just start typing. It elicited a scope (recursive content search, ignore-file handling, stdout/stderr separation, and so on) and had you approve it. Then, instead of asserting a language out of nowhere, a multi-perspective panel scored the choice across performance, security, maintainability, ops, reversibility, team-fit and cost, recommended Rust with Go kept as the honest runner-up, and wrote a single design from that recommendation, trade-offs and dissent left in the document. A reviewer read the design back and found real gaps; those fed into a revision the review signed off before anything was approved. From the approved design the agent produced one epic and every implementation unit, each tied to the scope items it covers, and the coders built them.

You stay in the loop at the points that matter — approving the scope, approving the design, and optionally confirming the review-clean decomposition with /approve plan — while the engine drives the authoring turns in between. The plan confirmation reports stale design or unit bindings but is not another automation gate. With design and decomposition review on (the default), the first /auto on drives planning to the approved-plan boundary, saves a marker, and hard-exits with an operator notice. Re-run /auto to drain implementation to a closed epic. With review off, one /auto on can run end to end; leave it off and the engine recommends the next step and waits for you.

There's a full walkthrough in docs/nordstar.md: the same weak prompt, start to finish, with the artefacts it leaves behind.

Quickstart

git clone https://github.com/GrokBuildMJW/ironclad.git && cd ironclad
pip install -e ".[engine]"
export GX10_BASE_URL=http://localhost:8000/v1 GX10_MODEL=your-model

python engine/server.py &              # the orchestrator: the agent + its state
python engine/client.py --codedir .    # the client: drives it, keeps your code local

Then, in the client:

/project new demo          # a workspace; artefacts live under vault/<slug>/
Read README.md and summarise it.
Build add(a,b) in calc.py with a pytest test, and run it.

The orchestrator holds the agent and the state; the client runs on your machine and keeps your code there — the agent's file and shell tools are handed back to the client and execute against your local files, never a copy on a server. Anything that leaves artefacts behind needs an active project first; a plain question doesn't. That's deliberate: without a project the macros refuse rather than scatter state through your working directory.

What's under the hood

The loop above is the product. Underneath it, a few pieces do the heavy lifting:

  • A contract kernel (ACK) — one Pydantic schema per task drives the prompt, the validator and the docs, and recovers tool calls from models that can't emit them natively.
  • A design review panel — the bundled multi-perspective reasoner (MPR) that scores an architecture decision across expert lenses and hands back an approvable design with its dissent, rather than a single asserted answer.
  • Loop Intelligence (ACE) — an always-on memory that distils each run into an itemised playbook and feeds it back into later runs. No flag to turn it on; it's how the loop improves.
  • Scalable context — a bounded model window with a rolling summary and long-term vector(+graph) retrieval, so long sessions don't fall over.
  • Governed parallelism — server-side reasoning fan-out under a concurrency cap and a token budget, with optional routing across providers.
  • A plugin surface — drop a tool into a skills/ directory and the agent picks it up, no core fork; a versioned plugin API and a bring-your-own coding-agent CLI keep the extension contract stable.

Point it at a regional open model — Falcon, Jais, K2 Think over vLLM (running on other models) — and you get the same fail-closed pipelines and structured tool calls without retraining anything.

Honest status

The engine comes from an orchestrator that was already running in production; it's been rebuilt into the server + client shape above, wired and tested, and it's still early — currently v0.0.31, single-tenant by design, with one operator and no multi-user auth yet. The APIs and layout can still move. Releases ship on PyPI (ironclad-ai) and as GitHub Releases; treat main as a development snapshot.

The claims here are backed by 4626 Python tests (4617 offline + 9 live) plus 515 TypeScript client tests, and a full end-to-end run with a real coding agent. Before you rely on anything, read:

Setup

You need Python 3.10+ and any OpenAI-compatible endpoint (vLLM, for example).

pip install ironclad-ai                  # ACK library only (import ack)

# For a runnable engine, clone the repository, then choose one:
pip install -e ".[engine]"               # engine source + declared runtime dependencies
bash install/ironclad-install.sh         # full setup; Windows: install\ironclad-install.ps1

The full walkthrough — the server/client split, the reference vLLM launch, and copy-paste shortcuts for PowerShell, macOS and Linux — is in SETUP.md. If you'd rather have an AI coding agent set it up, AGENTS.md is a deterministic runbook.

Developed on an NVIDIA DGX Spark (GB10, 128 GB unified memory) running vLLM with Qwen3.6-35B-A3B; nothing is wired to that box, but the defaults reflect it. Reasoning fan-out over 8 prompts runs about 5.8× faster than serial there. See docs/dgx-spark.md.

Extend it

Ironclad is a foundation, not a finished product. Domain use cases dock on as vessels — a runnable example lives in examples/demo-vessel/, and a generator scaffolds new ones — so you build reliable, self-hosted agents for your field instead of starting from scratch. Building in your own repo? pip install ironclad-ai and import the Extension SDK (ack.sdk) to ship plugins against a versioned surface. The framework even maintains itself: its own agents scaffold new plugins, and a dev container runs the full suite as a build gate.

Layout

ack/               agent-contract kernel: schema, validated emit, registry, doctor, generator
engine/            orchestration engine: the agent loop, task store, fail-closed macros
clients/ink/       recommended TypeScript terminal client (build from source)
examples/          runnable example workspace
docs/              guides, ADRs, Apache-2.0

At runtime, engine machinery hides under .ironclad/ and every artefact lives under vault/<slug>/, so your project root stays clean — see docs/project-isolation.md.

License

Apache 2.0 — see LICENSE and NOTICE. Copyright 2026 MJWC-AI-LAB and Ironclad contributors. Built in the United Arab Emirates.

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

ironclad_ai-0.0.31.tar.gz (182.3 kB view details)

Uploaded Source

Built Distribution

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

ironclad_ai-0.0.31-py3-none-any.whl (210.6 kB view details)

Uploaded Python 3

File details

Details for the file ironclad_ai-0.0.31.tar.gz.

File metadata

  • Download URL: ironclad_ai-0.0.31.tar.gz
  • Upload date:
  • Size: 182.3 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.14

File hashes

Hashes for ironclad_ai-0.0.31.tar.gz
Algorithm Hash digest
SHA256 eaa86b09c4f457e657d1fa446ea8d152a26ee10f172a74acb0a32aca5c953080
MD5 853c6f06addd50bea6bf30791d59df5c
BLAKE2b-256 22e74891e6d1acc2ce2629408737c22eb9095fb7806644e4ab4c0bd0156ab52d

See more details on using hashes here.

Provenance

The following attestation bundles were made for ironclad_ai-0.0.31.tar.gz:

Publisher: publish.yml on GrokBuildMJW/ironclad

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

File details

Details for the file ironclad_ai-0.0.31-py3-none-any.whl.

File metadata

  • Download URL: ironclad_ai-0.0.31-py3-none-any.whl
  • Upload date:
  • Size: 210.6 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.14

File hashes

Hashes for ironclad_ai-0.0.31-py3-none-any.whl
Algorithm Hash digest
SHA256 2c9ca7e544967629547dd7f509fce94b881842f3c9174008b6cbb0cff1abc3b1
MD5 b1857589f6f0f76a88685fdc11b87c41
BLAKE2b-256 1d501a1f3b4ba60205e3cb2dc33f886e25e56e427464497fa7c1f79c7b39612b

See more details on using hashes here.

Provenance

The following attestation bundles were made for ironclad_ai-0.0.31-py3-none-any.whl:

Publisher: publish.yml on GrokBuildMJW/ironclad

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