BondFoundry
Platform · Policy gate

Every governed action goes through one pure function.

No I/O. No state. No eventually-consistent guesswork. Same inputs always produce the same decision — and the verbatim rule text any auditor can verify.

Signature

A function you can reason about

The gate is a single function with no side effects. The agent proposes an action, the gate decides, the caller does the I/O. The shape is small enough to fit on a slide and prove invariants from.

packages/bondfoundry_policy/decide.py python
def decide(action: Action, context: Context) -> Decision:
    """Pure. No I/O. No clock. Same inputs → same decision."""
    tier = tier_for(action)
    rule = applicable_rule(action, context, tier)
    return Decision(
        verdict=rule.evaluate(action, context),  # allow | block | hitl_required
        rule_id=rule.id,
        verbatim_text=rule.text,
        tier=tier,
        framework_ref=rule.framework_ref,
    )
Tier model

Routed by reversibility, not by category

Most "AI guardrail" systems collapse everything into one tier. BondFoundry routes by how reversible the action is — because that is what the auditor cares about.

  • T0 — read-only (price_bond, calculate_risk, run_scenario). Agent executes, written to audit, no HITL.
  • T1 — reversible writes (ingest_curve, generate_eod_report). Agent executes, written to audit.
  • T2 — single-HITL above materiality (create_trade, upload_trades_csv). Human approval required.
  • T3 — dual-HITL irreversible (delete_instrument, purge_trades, update_portfolio_policy). Manager + second approver, both distinct from the agent caller.
Verbatim citation

The text the auditor reads

When the gate blocks or routes to HITL, the response carries the exact rule text — not a paraphrase, not a model-generated explanation. The CI test suite asserts character-for-character match against the policy bundle.

A blocked-decision payload json
{
  "verdict": "hitl_required",
  "rule_id": "BF-MAT-T2-001",
  "verbatim_text": "Trades exceeding $1M notional require human approval prior to FIX submission.",
  "tier": "T2",
  "framework_ref": ["AIR-OP-6", "AIR-OP-4"]
}
Run it in your browser

Same shape. Same logic. Same JSON output.

Try it

decide(action, context)

pure · deterministic
Decisionhitl_required
{
  verdict:       "hitl_required",
  rule_id:       "BF-MAT-T2-001",
  verbatim_text: "Trades exceeding $1M notional require human approval prior to FIX submission.",
  tier:          "T2",
  framework_ref: ["AIR-OP-6", "AIR-OP-4"]
}

Demo runs the same logic shape as the production gate. Same inputs always produce the same decision.

20-minute walkthrough

See the gate fire on a $5M corporate-bond rebalance, live.