Stop your AI agents from
doing dumb sh*t. And prove it.

Enact is an action firewall for AI agents. Define what they're allowed to touch, enforce policies on every request, generate a signed receipt for every run — and undo any reversible action when something slips through.

Open source · enact.cloud · Self-host free · Cloud from $299/mo

Minimal setup — add to any agent in minutes

# 1. install
pip install enact-sdk

# 2. add to your agent
from enact import EnactClient
from enact.connectors.postgres import PostgresConnector
from enact.policies.db import block_ddl, dont_delete_without_where

enact = EnactClient(
    secret="...",
    systems={"postgres": PostgresConnector(dsn="postgresql://...")},
    policies=[block_ddl, dont_delete_without_where],
)

# 3. your agent calls this — policy-gated, receipt-backed
result, receipt = enact.run(workflow="...", user_email="agent@co.com", payload={...})
Works with
Claude tool_use OpenAI Responses API LangChain CrewAI AutoGen MCP servers Any Python agent

Your framework connects agents to tools.
Nothing tells them what they're allowed to do.

LangChain, CrewAI, OpenAI, Claude — they all route agent calls to your systems. Not one of them answers: "Should this agent be doing this at all?"

Enact is the layer that does. Every action is policy-checked before it touches anything real.

Your agent framework Connects agents to tools. Routes calls. Returns results. Does not answer: "Should this agent be doing this at all?"
+
🔒
Enact on top Policy-gates every action before execution. Allowlists what's callable. Generates a signed receipt for every run. Blocks at 3:57am so you don't get paged.

Real AI agent disasters that could've been prevented

Production incident · 13 hours down

Amazon Kiro Agent — AWS Outage

An AI agent optimizing resource allocation had broader permissions than anyone realized. It began terminating critical EC2 instances across availability zones. No human approval. No safety check. Cascading failures took down major AWS services for 13 hours.

Root cause: "The agent should never have had write access to production compute resources."

Data loss · Customer records gone

Replit Agent — Deleted Production Database

An AI agent doing "database maintenance" identified what it thought were unused tables and deleted them. They were critical production tables. When questioned, the agent generated plausible explanations for why the deletion was safe. The data was gone.

Root cause: Full write access to production schema. No approval workflow. No audit trail.

With Enact: pre-action row capture means enact.rollback(run_id) restores every deleted record in one command. See the rollback receipt below.

Your agents have the same vulnerabilities.

The blast radius problem

Your agents have access to everything. You've defined access to nothing. One bad prompt away from a production database wipe or irreversible data loss.

No decision logic

There's no code that says "don't drop a table outside a maintenance window" or "don't bulk-email every customer from a draft." Every agent is one prompt away from a live incident.

No proof

When your auditor or VP asks "what did the agent actually do?", you're digging through CloudWatch logs at 2am. No audit trail. No compliance path.

Running in 5 minutes

Install, connect your systems, define policies, call enact.run(). That's it.

1

Install

One package. No infra required to start.

2

Connect your systems

GitHub, Postgres, Filesystem — pass your credentials, get policy-gated, receipt-backed actions back.

3

Define policies

Deterministic Python functions. No LLMs. Versioned in Git. Testable with pytest.

4

Call enact.run()

Your agent gets a result and a receipt. Blocked actions are logged with a reason.

# 1. install
pip install enact-sdk

# 2. set up your client
from enact import EnactClient
from enact.connectors.postgres import PostgresConnector
from enact.policies.db import block_ddl, dont_delete_without_where

enact = EnactClient(
    secret="your-secret",
    systems={"postgres": PostgresConnector(dsn="postgresql://...")},
    policies=[block_ddl, dont_delete_without_where],
)

# 3. your agent calls this — policy-gated, receipt-backed
result, receipt = enact.run(
    workflow="safe_insert",
    user_email="agent@company.com",
    payload={"table": "users", "data": {...}},
)

Already have an agent? See the Migration section ↓ for before/after code.

Migration takes 10 minutes.

Your agent's reasoning and planning logic doesn't change. You're adding a safety layer between it and your systems. Same calls, same results — now with policy enforcement, a full audit trail, and rollback.

1

Register your systems

Swap your existing SDK clients for Enact connectors. GitHub, Postgres, Filesystem — same credentials, now policy-gated and receipt-backed.

2

Move your guard logic

Any if/else checks you already write become Python policy functions. Or just use ours — 20+ ship out of the box.

3

Replace direct calls

tool.do_thing() becomes enact.run(). That's the whole migration.

Before — raw tool calls
# your agent today — calling tools directly
import github_sdk
import psycopg2

# direct call — zero policy check
github_sdk.create_pr(
    repo="myorg/app",
    branch="agent/fix-123",
    title="Fix bug",
)

# no WHERE protection — deletes everything
db.execute("DELETE FROM sessions")

# no audit trail. no rollback. no proof.
After — wrapped with Enact
# one-time setup — replaces your SDK clients
from enact import EnactClient
from enact.connectors.github import GitHubConnector
from enact.connectors.postgres import PostgresConnector
from enact.policies.git import dont_push_to_main
from enact.policies.db import dont_delete_without_where

enact = EnactClient(
    secret="...",
    systems={
        "github":   GitHubConnector(token="..."),
        "postgres": PostgresConnector(dsn="postgresql://..."),
    },
    policies=[dont_push_to_main, dont_delete_without_where],
)

# same intent — now policy-gated + receipt-backed
result, receipt = enact.run(
    workflow="agent_pr_workflow",
    user_email="agent@company.com",
    payload={"repo": "myorg/app", "branch": "agent/fix-123"},
)
Works with LangChain, CrewAI, OpenAI, Claude — any framework that calls Python
Your agent's reasoning, planning, and prompting logic stays exactly the same
No infra changes — self-host for free or point to enact.cloud in 30 seconds

20+ policies, shipped today

Pure Python functions — no LLMs, versioned in Git, testable with pytest. Register any combination on your EnactClient.

Database Safety

Blocks the Replit incident pattern — schema drops, unsafe deletes, unfiltered updates
block_ddl
Blocks DROP, TRUNCATE, ALTER, CREATE — word-boundary regex, catches semicolon-joined statements
dont_delete_row
Sentinel — unconditionally blocks all row deletions regardless of table or WHERE clause
dont_delete_without_where
Blocks DELETE with empty or missing WHERE clause — prevents deleting all rows
dont_update_without_where
Blocks UPDATE with empty or missing WHERE clause — prevents overwriting every record
protect_tables(list) Factory — blocks any operation on a named table. Exact, case-sensitive match. Pass-through if no table in payload.

Code Freeze & Time

code_freeze_active
Blocks all agent actions when ENACT_FREEZE=1 — enforces "do not touch" at the action layer, not the prompt layer
within_maintenance_window(start, end)
Restricts actions to a UTC time window — midnight-crossing windows supported (e.g. 22:00–06:00 UTC)

Access Control

dont_read_sensitive_tables(list)
Blocks SELECT on named tables — agents can't read credit_cards, audit_log, etc.
dont_read_sensitive_paths(list)
Blocks read_file on paths under sensitive prefixes (/etc, /root, secrets/) — traversal-safe
require_user_role(*roles)
ABAC: blocks if user_attributes["role"] not in allowed set — reads structured identity, not payload
require_clearance_for_path(paths, min)
ABAC: blocks if user_attributes["clearance_level"] below minimum for sensitive path
contractor_cannot_write_pii
Blocks contractors from writing any field in the caller-defined pii_fields list
require_actor_role(list)
Blocks actors without an allowed role — reads payload["actor_role"]

Git Safety

dont_push_to_main
Blocks direct pushes to main or master — the Kiro pattern
dont_merge_to_main
Blocks PR merges targeting main or master
dont_delete_branch
Sentinel — unconditionally blocks all branch deletions
max_files_per_commit(n)
Caps blast radius — blocks commits touching more than n files
require_branch_prefix(prefix)
Enforces branch naming — blocks branches not starting with required prefix

Filesystem Safety

dont_delete_file
Sentinel — unconditionally blocks all file deletions
restrict_paths(list)
Confines operations to allowed directories — traversal-safe prefix matching
block_extensions(list)
Blocks operations on .env, .key, .pem and other sensitive file types

CRM

dont_duplicate_contacts
Live lookup before workflow runs — blocks creating a contact that already exists
limit_tasks_per_contact
Rate-limits tasks per contact per rolling time window
Write your own in 5 lines of Python

Any callable (WorkflowContext) -> PolicyResult can be registered. No SDK extension needed.

def only_on_weekdays(ctx: WorkflowContext) -> PolicyResult:
    ok = datetime.now(timezone.utc).weekday() < 5
    return PolicyResult(
        policy="only_on_weekdays", passed=ok,
        reason="weekday OK" if ok else "no weekend ops"
    )

Blocked. Approved. Rolled back.

Three outcomes every production team needs to handle. Enact documents all of them — and gives you the receipt to prove it.

Request ID
REQ-08472
Timestamp
2026-02-22 03:57:42 UTC
Decision
DENIED

REQUEST DETAILS

WHO
infra-agent@company.com
WHAT
rotate_db_credentials on prod-us-east-1
REASON
cleanup old users, reduce attack surface

POLICY EVALUATION

Protect_Prod_Primary_DB BLOCKED: Attempt to modify primary production database outside approved maintenance window (02:00–03:00 UTC) by non-DBA role.
Valid Credentials Format Rotation payload format valid
Database Target Exists Database "prod-us-east-1" found in registry

ACTIONS EXECUTED

Result
No actions executed (policy violation)
Alert sent
PagerDuty #P847291 created · Slack #security-incidents notified

TECHNICAL LOG

Execution time
89ms
Policy checks
2 passed, 1 failed
Actions run
0 (blocked by policy)
Request ID
REQ-08471
Timestamp
2026-02-22 06:22:15 UTC
Decision
APPROVED

REQUEST DETAILS

WHO
revops-agent@company.com
WHAT
new_lead_workflow for jane@acme.com
REASON
outbound prospecting — ICP match

POLICY EVALUATION

Duplicate Contact CheckNo existing contact with email jane@acme.com
ICP Company MatchCompany "Acme Inc" matches ICP criteria (tech, 50–500 employees)
Task Limit CheckContact has 0 tasks (limit: 3 per week)
Contractor Write RestrictionAgent is FTE (contractors cannot create deals)

ACTIONS EXECUTED

HubSpot
Created contact (ID: 847291)
HubSpot
Created deal (ID: 938471, value: $25,000)
HubSpot
Created task for AE → sales@company.com

TECHNICAL LOG

Execution time
1,247ms
Policy checks
4 passed, 0 failed
Actions run
3 (all succeeded)
Rollback ID
REQ-08476
Timestamp
2026-02-22 14:35:12 UTC
Type
ROLLBACK of REQ-08473
Decision
PARTIAL ROLLBACK

ORIGINAL RUN

Run ID
REQ-08473
Workflow
db_cleanup_workflow
Actor
cleanup-agent@company.com
Executed
2026-02-22 14:31:44 UTC — 3 minutes ago

ROLLBACK ACTIONS (last → first)

postgres.delete_row → REVERSED Re-inserted 47 rows into table "customers" from pre-action capture. All records restored.
github.push_commit → COULD NOT REVERSE push_commit is irreversible. Commit abc1234 "chore: cleanup inactive records" remains on remote. Manual action required.

RESULT

Status
Partial — 1 of 2 actions reversed
Rows restored
47 customer records back in prod
Manual action
Revert or delete commit abc1234 from remote
Alert sent
PagerDuty #P847294 updated · Slack #data-team notified

TECHNICAL LOG

Execution time
612ms
Actions reversed
1 of 2 (1 irreversible)
Signature
sha256:d4e8f2a193c7...b3c9 (rollback receipt signed)

Stop writing boilerplate connector code

Think Zapier — but for AI agents, built by engineers who've seen what goes wrong. Every workflow is pre-built, red-teamed, idempotent, and ready to deploy in minutes. We write them. We maintain them. You just register and run.

No more figuring out connector quirks, handling rate limits, or writing the same duplicate-check logic for the fifth time. The library grows with every release.

Why pre-built workflows matter

Idempotent by design. If step 1 succeeds and step 2 fails, a retry won't create duplicates. Every connector checks before it acts.

Red-teamed. We run adversarial prompts against every workflow before it ships. If an agent can break it, we fix it first.

Policy-ready. Every workflow ships with a recommended policy set. You can tighten them. You can't accidentally skip them.

agent_pr_workflow live Create branch → open PR. Aborts if branch creation fails — never a PR pointing at nothing.
db_safe_insert live Check constraint → insert row. Returns explanatory failure instead of letting DB raise.
new_lead_workflow coming soon Dedup check → create contact → create deal → assign task to AE. Full CRM pipeline.
issue_triage_workflow coming soon Label → assign → comment → create branch. Triage a GitHub issue in one agent call.
deploy_to_staging coming soon Policy gate → tag release → trigger deploy → verify health check. With rollback on failure.
credential_rotation coming soon Maintenance window check → rotate → verify → notify on-call. Never runs outside hours.
deal_stage_update coming soon Role check → update deal stage → create follow-up task → log to Slack.
batch_data_export coming soon Row-count gate → export → PII scrub → deliver. Agent can't export what it shouldn't.

Coming in v0.3

v0.3+

These are the capabilities teams ask for most. Building them in the order that saves the most production incidents first.

Human-in-Loop Gates coming soon

High-risk actions pause and wait for a human to approve before continuing. Slack DM, email, or web UI — your choice. Timeout = auto-abort with receipt. No more "the agent just did it while I was asleep."

One-Step Rollback live

Undo reversible agent actions in one command. enact.rollback(run_id) reverses what it can (branches, DB rows, files, open PRs), explicitly records what it can't (merged PRs, pushed commits), and generates a signed PASS / PARTIAL rollback receipt. Your undo button — with honest limits.

Vertical Policy Packs coming soon

Pre-built policy sets for your industry — FinTech (no trading outside market hours, PII in transit controls), Healthcare (HIPAA field protection, PHI access audit), DevOps (prod deploy gates, blast-radius limits). Install, tune, done.

Compliance Export coming soon

Generate SOC2, ISO27001, or HIPAA audit reports directly from your receipt database. Every agent action already logged and signed — turn it into a compliance artifact in one click. Hand it to your auditor, not your engineers.

Anomaly Detection coming soon

Learn your agents' normal behavior. Flag deviations automatically — an agent touching 10x its usual number of records, a new action it's never called before, activity at unusual hours. Catch the subtle stuff before it becomes a postmortem.

Multi-Agent Arbitration coming soon

When multiple agents want to modify the same resource simultaneously, Enact serializes and arbitrates — not your database. Define merge strategies, conflict policies, and priority rules. Your agents stop stepping on each other.

Want early access to any of these?

We're working with a handful of teams to validate each capability before shipping. Tell us which one you need most.

Get early access →

Simple, value-based pricing

What's it worth to avoid a 2am call with your CEO?

Self-Hosted

Free
Forever. Run on your infra.
  • Full policy engine + SDK
  • All canonical actions
  • 1–2 reference workflows
  • Local receipt generation (HMAC)
  • You manage infra + backups
  • grep receipts, no search UI
  • Console logs, no alerts
View on GitHub

Enterprise

$999/mo
For orgs with compliance requirements
  • Everything in Professional
  • 1+ year retention (audit trails)
  • SIEM export (Splunk, Sentinel)
  • SSO (SAML, Okta, Google)
  • SOC2 / ISO27001 compliance export coming soon
  • Vertical policy packs coming soon
  • Anomaly detection coming soon
  • Unlimited receipts
  • Priority support (4hr response)
Contact sales
vs. Noma Security ($200k/year)

Professional is $3,600/year. Enterprise is $12,000/year. Same category, 95% cheaper. Prevention beats detection.

vs. SOC2 audit pain

40 hours of engineer time explaining "what did agents do" = $10k+ opportunity cost. Hand auditors a searchable receipt database instead.

vs. one production incident

The Kiro outage cost millions. The Replit deletion was career-limiting. Preventing one incident pays for Enact for years.