Skip to content

About

Aether is a hybrid state-transition framework for AI coding agents. It replaces full-file regeneration with focused, validated patches, automatic rollback, and smart routing. Benchmarks across Python and JavaScript showed 75% fewer output tokens with 100% success in the tested scope.

Resources

Security policy

Stars

4 stars

Watchers

0 watching

Forks

Latest commit

 

History

55 Commits

Folders and files

Repository files navigation

Aether → AI-Safe Execution Infrastructure

Rust Python License Platforms

Note

This repository has evolved from a Cranelift-based systems language compiler into an AI-Safe Execution Infrastructure — a structured, sandboxed, and reversible runtime for AI-driven code modification.


🚀 What is this?

AI coding agents (LLMs, Copilots, AutoGPT, etc.) currently modify codebases by generating raw text diffs or source code and applying them directly.

Warning

This approach—relying entirely on token generation—is fundamentally expensive, brittle, and unsafe:

  • Expensive Token Generation: Agents waste context window and compute re-generating entire files or large chunks of code just to change a few lines.
  • No Schema: The change is freeform text with no verifiable structure.
  • No Isolation: The change executes in the live process with full filesystem access.
  • No Rollback: Recovery depends on git reset or manual intervention.
  • No Contract: Ambiguity about what the agent intended vs. what it wrote.

Aether's AI-Safe Execution Infrastructure introduces a massive architectural shift: moving from token generation to AST-based state transitions.

Instead of asking an LLM to "write code", you ask it to output a compact JSON patch describing the logical changes (e.g., "replace the body of function X"). The infrastructure parses the target code into an Abstract Syntax Tree (AST), applies the exact transformations requested, and serialises it back.

This fixes the fundamental flaws of token-based generation by treating code modification as a controlled state transition:

❌ Before (Token Generation):  AI agent ──(raw text/diff)──▶ git apply ──▶ hope it works

✅ After (AST State Transition): AI agent ──(JSON AST Patch)──▶ Validate ──▶ Snapshot ──▶ Sandbox ──▶ Commit/Rollback

Tip

Why this matters for your Agents:

  • Massive Cost Efficiency: You only pay to generate the exact AST instructions needed in a compact JSON payload, not entire files.
  • Deterministic and Verifiable: Changes are applied via exact AST transformations (using tools like libcst), ensuring syntax is always perfectly valid.
  • Atomic & Reversible: Because patches are structured state transitions, they can be flawlessly snapshotted and rolled back if sandbox execution fails.

📊 Benchmark Status

The repository now includes a reproducible benchmark program under benchmarks/. It records raw JSON and CSV results for deterministic correctness checks, failure injection, replay-agent patch ingestion, and a local real-repository smoke fixture.

Current evidence supports the benchmark infrastructure, tested patch/rollback behaviors, and a small live Gemini provider smoke run. Broad LLM-agent success rates, token savings across real repositories, and latency/cost tradeoffs still require repeated provider-backed benchmarks. See benchmark_evidence.md for the current evidence status and limitations.

🔌 Healing Agent Integration

Aether includes a check-only adapter for Healing Agent's propose -> verify -> apply pipeline. Healing Agent can run Aether as a VERIFY_COMMAND before live files are changed, while Aether reports a compact JSON verdict and exits 0/nonzero for pass/fail. See integrations/healing_agent/ for the adapter.

🧠 Agent Skill Pack

Aether now includes an agent-facing skill pack under agent_skills/aether/. It gives coding agents a compact decision policy, patch schema examples, and prompt instructions for choosing structured state transitions instead of raw full-file rewrites when that is cheaper or safer.

⚡ Fast Start

Install the public Python runtime:

pip install aether-lang-runtime

Use the agent-facing CLI:

aether validate patch.json
aether apply patch.json
aether snapshots
aether rollback <snapshot-id>

For cloud-synced workspaces such as OneDrive or Dropbox, keep Aether runtime state outside the synced project folder:

aether --runtime-dir ~/.cache/aether/my-project apply patch.json
aether --runtime-dir ~/.cache/aether/my-project rollback <snapshot-id>

Install the bundled Codex skill after pip install:

aether skill install-codex

For Python and JavaScript examples, see docs/public/QUICKSTART.md.


📁 Repository Layout

graph TD
    A[aether-lang/] --> B[sdk/python/ <br> AI-Safe Runtime v1.0]
    A --> C[sdk/node/ <br> AI-Safe Runtime Node.js]
    A --> D[crates/ <br> Cranelift Compiler + T1 FFI]
    
    B --> B1[Validation Layer]
    B --> B2[Snapshot System]
    B --> B3[Sandbox T3 Subprocess]
    B --> B4[Sandbox T2 Wasmtime]
    B --> B5[Sandbox T1 Cranelift JIT]
    B --> B6[AST Engine LibCST]
    B --> B7[Observability Audit Log]
    
    C --> C1[Validation Layer]
    C --> C2[Snapshot System]
    C --> C3[Sandbox T3 Node20]
    C --> C4[AST Engine Recast]
    C --> C5[Security Rules JSON]

    D --> D1[ae-codegen - JIT + C FFI]
    D --> D2[ae-sema - Semantic Analysis]
    D --> D3[ae-syntax - Parser/AST]
Loading
aether-lang/
│
├── sdk/
│   ├── python/                  ← AI-Safe Runtime (Python SDK)
│   │   ├── ai_runtime/
│   │   │   ├── patch_engine.py      ← PatchEngine: validate() + apply() orchestrator
│   │   │   ├── sandbox.py           ← Sandbox: T1/T2/T3 tier dispatcher
│   │   │   ├── sandbox_t1.py        ← T1: Cranelift JIT via ctypes FFI
│   │   │   ├── sandbox_t2.py        ← T2: Wasmtime/WASI WASM sandbox
│   │   │   ├── sandbox_t3.py        ← T3: subprocess + OS resource limits
│   │   │   ├── sandbox_runner.py    ← Worker script (runs inside child process)
│   │   │   ├── _types.py            ← Shared dataclasses (ExecutionResult w/ isolation_level)
│   │   │   ├── validation/
│   │   │   │   ├── patch_schema.json  ← JSON Schema Draft 2020-12 contract
│   │   │   │   ├── schema.py          ← Gate 1: schema validation
│   │   │   │   └── rules.py           ← Gate 2: loads patterns from security_rules.json
│   │   │   ├── snapshot/
│   │   │   │   ├── store.py           ← SnapshotStore: capture/restore/commit/prune
│   │   │   │   ├── gitignore.py       ← .gitignore-aware file collector
│   │   │   │   └── lock.py            ← Cross-platform write lock
│   │   │   ├── ast/                   ← AST Apply Engine (LibCST)
│   │   │   └── observability/         ← Audit log (JSONL), diff, structured events
│   │   └── tests/                   ← 174 tests (all passing, 1 xfailed)
│   │
│   ├── node/                    ← AI-Safe Runtime (Node.js SDK + aether-js CLI)
│   │   ├── src/
│   │   │   ├── security.ts          ← Loads rules from shared security_rules.json
│   │   │   ├── validation/          ← Ajv JSON Schema + security rules
│   │   │   ├── snapshot/            ← tar.gz snapshots
│   │   │   ├── sandbox/
│   │   │   │   ├── ae_sandbox_napi.cpp  ← N-API C++ wrapper for Rust FFI
│   │   │   │   └── sandbox.js           ← T3 subprocess sandbox
│   │   │   └── ast/                 ← Recast AST engine (JS/TS)
│   │   ├── tests/                   ← Jest tests incl. rollback-fault.test.ts
│   │   └── binding.gyp              ← node-gyp build config for T1 N-API addon
│   │
│   └── security_rules.json      ← Shared security patterns (both SDKs load from here)
│
├── crates/                      ← Aether language compiler (Rust/Cranelift)
│   ├── ae/                      ← CLI binary (ae run, ae build, ae check)
│   ├── ae-codegen/
│   │   ├── src/
│   │   │   ├── lib.rs           ← Tree-walking interpreter (T1 fast path)
│   │   │   ├── jit.rs           ← Cranelift JIT (BoolLit/ArrayLit/Return hardened)
│   │   │   ├── aot.rs           ← Cranelift AOT (same hardening)
│   │   │   └── ffi.rs           ← C-ABI guard ring (ae_sandbox_execute/free)
│   │   └── Cargo.toml           ← cdylib + rlib dual output
│   ├── ae-sema/                 ← Semantic analysis + stability levels
│   └── ae-syntax/               ← Parser / AST (ContentHash via BLAKE3)
│
├── SECURITY.md                  ← Honest threat model for all 3 sandbox tiers
└── README.md                    ← This file

🏗️ System Architecture

flowchart TD
    Agent["🤖 AI Agent"] -->|JSON Patch| Validation
    
    subgraph Validation["🛡️ VALIDATION LAYER"]
        G1{"Gate 1: JSON Schema"} 
        G2{"Gate 2: Security Rules\n(loaded from security_rules.json)"}
        G1 -->|Valid| G2
    end
    
    subgraph Snapshot["📸 SNAPSHOT SYSTEM"]
        Lock["Acquire Write Lock"]
        Tar["Create .tar.gz Archive"]
        DB["Log to SQLite (WAL)"]
        Lock --> Tar --> DB
    end
    
    subgraph Sandbox["⚙️ SANDBOX EXECUTION (3-Tier)"]
        T1["Tier 1: Cranelift JIT (Zero-syscall, native speed)"]
        T2["Tier 2: Wasmtime/WASM (WASI, epoch timeout)"]
        T3["Tier 3: Subprocess (OS Limits, universal)"]
        T1 -.->|fallback| T2
        T2 -.->|fallback| T3
    end
    
    subgraph AST["🌳 AST ENGINE"]
        PyAST["Python LibCST"]
        NodeAST["Node.js Recast"]
    end

    subgraph Observability["📊 OBSERVABILITY"]
        AuditLog["Append-only JSONL Audit Log\n(7 event kinds, query by patch_id)"]
    end
    
    Validation -->|Valid| Snapshot
    Validation -->|Invalid| Reject["❌ Reject"]
    
    Snapshot --> Sandbox
    Sandbox -->|Success| AST
    Sandbox -->|Failure| Rollback["⏪ Rollback + ROLLBACK audit event"]
    
    AST -->|Success| Commit["✅ Commit + COMMITTED audit event"]
    AST -->|Failure| Rollback

    Sandbox --> Observability
    AST --> Observability
Loading

⚡ Python SDK — Quick Start

pip install aether-lang-runtime
import uuid
from ai_runtime import PatchEngine, Sandbox

# 1. Build a structured patch
patch = {
    "schema_version": "1.0",
    "patch_id": str(uuid.uuid4()),
    "action": "modify_function",
    "target": {
        "file": "src/app.py",
        "symbol": "calculate_total",
        "symbol_type": "function",
    },
    "changes": {
        "operation": "replace_body",
        "payload": "    return sum(items)",
    },
}

# 2. Validate — two-gate, < 1ms
engine = PatchEngine()
report = engine.validate(patch)

if report.ok:
    # 3. Snapshot — capture project state (tar.gz + SQLite)
    sb     = Sandbox(project_root=".")
    handle = sb.snapshot(patch_id=patch["patch_id"])

    # 4. Apply + check execution result
    result = engine.apply(patch)

    if result and result.failed:
        sb.restore(handle)           # 5a. Rollback on failure → audit log records ROLLBACK
    else:
        sb.commit_snapshot(handle)   # 5b. Commit on success → audit log records COMMITTED
else:
    print(f"Rejected: {report.first_error}")

Agent-friendly CLI:

aether validate patch.json
aether apply patch.json
aether rollback <snapshot-id>

aether apply runs validation, captures a snapshot, applies the patch, and rolls back on failure. The older ae-safe command remains available as a compatibility alias.

Node.js CLI

cd sdk/node
npm install
npm run build
node dist/cli.js --project ../../examples/aether_js_cli validate ../../examples/aether_js_cli/patch.json
node dist/cli.js --project ../../examples/aether_js_cli apply ../../examples/aether_js_cli/patch.json

When packaged, the Node CLI is exposed as aether-js.

Tier Selection

from ai_runtime import Sandbox

sb = Sandbox(preferred_tier="t1_cranelift")  # Fastest — Cranelift JIT native
sb = Sandbox(preferred_tier="t2_wasm")       # Isolated — Wasmtime WASI sandbox
sb = Sandbox(preferred_tier="t3_subprocess") # Universal — OS-level subprocess

Note

Full SDK documentation: sdk/python/README.md


📖 Patch Schema Reference

All patches must conform to the JSON Schema at sdk/python/ai_runtime/validation/patch_schema.json.

Prefer symbol-level AST operations such as modify_function, modify_class, add_function, remove_function, and update_import whenever the target has a clear Python symbol. Use replace_block only when no symbol-level operation fits, because contextual text anchors are less robust than CST symbol matching. When replace_block is necessary, provide both context_before and context_after, and make the start anchor unique.

Field Required Description
schema_version ✅ "1.0"
patch_id ✅ UUID v4 — for idempotency and audit
action ✅ One of 7 supported actions
target.file ✅ Relative path — no / prefix, no ..
changes.operation ✅ Must be in allow-list for the action
changes.payload ✅ Source code, max 64 KB
constraints.timeout_ms ○ 100 – 30000 ms
constraints.memory_limit_mb ○ Memory cap for sandbox
metadata.* ○ Agent provenance, model, confidence

🔒 Security Model

Important

Threat model and limitations are documented in SECURITY.md.

In summary:

Sandbox Tier Isolation When to Use
T1 — Cranelift JIT Process-local, zero-syscall Trusted compiler-verified Aether code only
T2 — Wasmtime/WASI WASM capability sandbox, epoch timeout Untrusted scripts needing strong isolation
T3 — Subprocess OS resource limits + audit hook Universal fallback, widest compatibility

All results carry an isolation_level field for observability and audit.


⚙️ Phase 8: T1 Cranelift JIT FFI Integration

Phase 8 bridges the Rust Cranelift compiler into the Python/Node SDKs via a panic-safe C-ABI guard ring.

Architecture

flowchart TD
    SDK["Python / Node.js SDK"] -->|ctypes / N-API| GuardRing
    
    subgraph GuardRing["🛡️ Panic-Safe ABI Guard Ring"]
        E1["extern 'C' ae_sandbox_execute()<br>(std::panic::catch_unwind)"]
        E2["extern 'C' ae_sandbox_free()<br>(deterministic heap dealloc)"]
    end
    
    GuardRing --> Parse
    
    subgraph AetherCompiler["📦 Aether Compiler"]
        Parse["ae-syntax::parse"] --> Analyze["ae-sema::analyze"]
        Analyze --> Run["Interpreter::run"]
        Run -.->|JIT via cranelift-jit| JIT["JIT Execution"]
    end
Loading

Build

# Compile the Rust shared library
cargo build --release -p ae-codegen

# Output:
# Windows: target/release/ae_codegen.dll
# Linux:   target/release/libae_codegen.so
# macOS:   target/release/libae_codegen.dylib

Python Usage

from ai_runtime.sandbox_t1 import T1CraneliftSandbox

# Library is auto-discovered from target/release/ or AE_CODEGEN_LIB env var
sb = T1CraneliftSandbox()
result = sb.run("let x = 1 + 2;")
print(result.success, result.isolation_level, result.elapsed_ms)
# True  cranelift_jit  0.12

Safety Contract

Property Implementation
No Rust panics cross FFI boundary std::panic::catch_unwind wraps all execution
No memory leaks ae_sandbox_free reclaims every ae_sandbox_execute result
NULL safety NULL input returns JSON error; NULL free is a no-op
Deterministic dealloc Python uses c_void_p + explicit free in finally block
BoolLit / ArrayLit / Return Hardened: no more unimplemented!() panics in JIT/AOT

📦 T2 Sandbox: Wasmtime/WASI

Phase 7 implemented epoch-based timeout control (not instruction-fuel) for accurate wall-clock enforcement:

from ai_runtime.sandbox_t2 import T2WasmSandbox

sb = T2WasmSandbox()
result = sb.run(python_script, timeout_ms=5000)
  • Epoch ticking via background thread — accurate wall-clock timeouts
  • WASI exit code detection — sys.exit(N) maps correctly to exit_code
  • python.wasm fetched lazily and cached in .ai_runtime/cache/

🛡️ Shared Security Rules

Both the Python and Node.js SDKs load security patterns from a single canonical file:

sdk/security_rules.json

This file controls:

  • sensitive_path_patterns — regex list of paths that are always blocked (.env, .git, etc.)
  • blocked_payload_patterns — code patterns rejected at Gate 2 (exec, eval, etc.)
  • max_payload_size_bytes — maximum patch payload size (default: 64 KB)
  • run_script_requires_trust — whether run_script actions require explicit trust elevation

Tip

To add or update a security rule, edit security_rules.json once — both SDKs pick it up automatically.


🧪 Test Suite

# Rust tests (FFI guard ring + JIT — 8 tests)
cargo test -p ae-codegen

# Python tests (174 tests)
cd sdk/python
pip install -e ".[dev]"
pytest tests/ -v

# Node.js tests
cd sdk/node
npm test

Rust (ae-codegen)

running 8 tests
test ffi::tests::ffi_free_null_is_noop              ... ok
test ffi::tests::ffi_null_pointer_returns_error     ... ok
test ffi::tests::ffi_parse_error_returns_failure    ... ok
test ffi::tests::ffi_valid_source_returns_success   ... ok
test jit::tests::test_jit_basic_math                ... ok
test jit::tests::test_jit_let_and_if               ... ok
test jit::tests::test_jit_bool_lit_no_panic         ... ok  ← A1 regression guard
test jit::tests::test_jit_array_lit_no_panic        ... ok  ← A1 regression guard

test result: ok. 8 passed; 0 failed

Python SDK

174 tests collected (8 passed, 1 xfailed)
├── test_validation.py            34 tests  (Phase 1: Validation Layer)
├── test_sandbox.py               26 tests  (Phase 2: Sandbox T3)
├── test_sandbox_t3_windows.py     3 tests  (Phase 2: Windows Job Objects)
├── test_snapshot.py              31 tests  (Phase 3: Snapshot System)
├── test_observability.py          8 tests  (Phase 4: Audit Log)
├── test_ast_engine.py             7 tests  (Phase 5: LibCST AST Engine)
├── test_sandbox_t2.py             5 tests  (Phase 7: Wasmtime WASI)
├── test_ffi_fuzz.py              51 tests  (Phase 8: T1 FFI Fuzz Suite)
└── test_rollback_fault.py         9 tests  (Phase A3: Fault-Injection Rollback)
     └─ 1 xfail: new-file removal on rollback (Phase B: manifest diffing)

🗺️ Roadmap

Phase Component Status
1 Validation Layer (JSON Schema + Rules) ✅ Complete
2 T3 Sandbox (subprocess + OS limits) ✅ Complete
3 Snapshot System (tar.gz + SQLite + locks) ✅ Complete
4 Observability (audit log, diffs, CLI status) ✅ Complete
5 AST Apply Engine (modify_function via LibCST) ✅ Complete
6 Node.js SDK (sdk/node/) + aether-js CLI ✅ Complete
7 T2 Sandbox (Wasmtime/WASI + epoch timeout) ✅ Complete
8 T1 Sandbox (Cranelift JIT C-ABI FFI) ✅ Complete
8.5 Node.js T1 N-API addon (ae_sandbox_napi.cpp) ✅ Scaffolded
A — Harden JIT panics fixed, security_rules.json, isolation_level, SECURITY.md ✅ Complete
A3 Fault-injection rollback tests (9 tests, 1 xfail documented) ✅ Complete
B Semantic Bridge (content-hash patch targeting, ae check --diff-impact) 🔲 Planned
C2 Node.js SDK: SemanticGate + PatchOrchestrator parity 🔲 Planned
D Docker-based T4 Sandbox (production isolation) 🔲 Future

💻 Requirements

  • Python SDK: Python ≥ 3.11, no Docker, no root
  • Rust compiler: Required to build crates/ae-codegen for T1 (rustup target add x86_64-pc-windows-msvc)
  • Platforms: Windows 10+, Linux, macOS

📜 License

Aether is provided under a Dual License model:

  • Open Source: GNU AGPLv3 for open-source, personal, educational, or internal non-networked use.
  • Commercial: A commercial license is required for proprietary applications, SaaS products, or AI tooling platforms where AGPLv3 obligations cannot be met.

For commercial licensing and other inquiries, please contact: ashallt232005@gmail.com

See the LICENSE file for full details.

About

Aether is a hybrid state-transition framework for AI coding agents. It replaces full-file regeneration with focused, validated patches, automatic rollback, and smart routing. Benchmarks across Python and JavaScript showed 75% fewer output tokens with 100% success in the tested scope.

Resources

Security policy

Stars

4 stars

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages