Skip to content
hamidmatinyPublic

About

Open-source AI security gateway + AEGIS-for-SMB copilot — defense-in-depth against prompt injection, jailbreaks, data exfiltration, and tool abuse; policy-as-code, tamper-evident audit, human approval for high-risk actions. Live at defenseaegis.org.

Topics

Resources

Contributing

Security policy

Stars

1 star

Watchers

0 watching

Forks

Latest commit

 

History

226 Commits

Folders and files

NameName
Last commit message
Last commit date
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

AEGIS

AI-native LLM security gateway / enforcer for applications and agentic systems — policy-as-code (CEL), human approval for high-risk tool calls, and tamper-evident Ed25519 audit trails between your app and any LLM provider.

AEGIS sits between your application and any LLM provider, enforcing defense-in-depth against prompt injection, jailbreaks, data exfiltration, tool/MCP abuse, and supply-chain tampering — with full tamper-evident audit trails.

Live site: defenseaegis.org — gateway-first landing; hosted advisory Q&A is an applied example on the same stack, not the headline product.

# Try the gateway locally (mock model — no paid API key required)
./scripts/demo.sh

Applied example: hosted advisory Q&A

defenseaegis.org also hosts an advisory infrastructure Q&A surface (inventory + plain-language answers + curated CVE context; optional paid walkthroughs). That path is secondary — built on the same policy and audit primitives. Autonomous action-taking / “digital employee” marketing stays shelved until a real competence bar passes.

Surface URL Audience
Live site (gateway landing + Q&A example) defenseaegis.org Operators evaluating the gateway; optional Q&A trial
CVE checklist (legacy SEO) /guides/smb-cve-exposure-checklist Small-business CVE readers — not the gateway buyer
Open-source platform this repo Developers integrating the gateway

Implementation: smb-copilot/ (FastAPI backend), smb-portal/ (React customer UI). See each service README for ports, env vars, and smoke tests.

Why AEGIS

  • Defense-in-depth, not a single filter — input defense, policy-as-code (CEL), output defense, and agent-gate tool authorization in one pipeline
  • OpenAI-compatible gateway — drop-in base_url for existing SDKs
  • Human approval for high-risk tools — agent-gate blocks irreversible actions until a reviewer allows them
  • Tamper-evident audit — Ed25519-signed receipts in Postgres
  • Built for operators — Docker Compose deploy, dashboard, continuous red-team harness

Architecture

Application → [SDK / Reverse Proxy] → Gateway (Go)
                                         ├── Input Defense (Python)
                                         ├── Policy Engine (Go + CEL)
                                         ├── Model Router (Go)
                                         ├── Output Defense (Python)
                                         ├── Agent Gate (Go)
                                         └── Audit (Go + Postgres)

See ARCHITECTURE.md for the full system design.

Phase 2 evidence: Adaptive red-team campaigns and detector ablation are summarized in RESULTS.md. Report R1 BR and Adapt BR separately (see the campaign methodology note) — not a single blended “overall bypass” headline. See COMPARISON.md for how AEGIS differs from NeMo Guardrails, Guardrails AI, and LLM Guard, and ARCHITECTURE.md for which layers are load-bearing for content vs tool-misuse outcomes.

Governed agent loop: the harness/ package is a shipped starter loop + 7-tool library that will not execute a tool without an agent-gate allow decision — see harness/README.md.

Monorepo layout

Path Language Purpose Stage
shared/ Protobuf + JSON Schema Cross-service schemas and codegen 0
gateway/ Go HTTP orchestration (defended chat pipeline) H4
input-defense/ Python Input-side detectors + fusion 2
policy-engine/ Go CEL policy evaluation 3
model-router/ Go Provider-agnostic LLM routing 4
output-defense/ Python Output-side detectors + LLM judge 5
agent-gate/ Go Tool/MCP permission + taint tracking 6
redteam/ Python Continuous adversarial testing 7
audit/ Go Ed25519-signed audit receipts 8
dashboard/ React + TS Operations UI 9
smb-copilot/ Python SMB tenant onboarding, Q&A, usage —
smb-portal/ React + TS Customer-facing SMB Copilot UI —
corp-orchestrator/ Python Multi-department agent corporation mesh (Phase 12) —
sdk/ Python + TS Drop-in SDK wrappers 10
examples/ Mixed Reference integrations 11
harness/ Python Governed multi-step agent loop + 7-tool starter library, all 4 risk tiers (operator-platform phases 1-2) 12
deploy/ Helm + SQL Production deployment 0

Quick start

# 1. Generate credentials — there is no static default password or API key
#    anywhere in this repo. This creates .env (from .env.example) and fills
#    in a random dashboard password and gateway API key.
chmod +x scripts/generate-credentials.sh
./scripts/generate-credentials.sh
# Edit .env further if you want to set LLM provider keys, ports, etc.

# 2. Install dev dependencies and generate protobuf code
chmod +x scripts/*.sh
./scripts/dev-setup.sh

# 3. Start the full local stack
docker compose up -d --build

# 4. Run smoke tests
make test-integration

Use docker compose --env-file .env up -d if your shell does not auto-load .env.

If you skip step 1, the gateway and dashboard each generate a one-time random credential at container startup and print it once to their logs (docker compose logs gateway / docker compose logs dashboard) — it changes on every restart until you persist one via .env. Default username admin; the dashboard password is generated by ./scripts/generate-credentials.sh or emitted once on container startup — there is no static changeme default.

Every request to the gateway other than /health and /ready requires an API key, sent as Authorization: Bearer <key> (OpenAI-SDK compatible) or X-API-Key: <key>:

curl -H "Authorization: Bearer $AEGIS_API_KEY" \
  -H 'Content-Type: application/json' \
  -d '{"model":"mock-model","messages":[{"role":"user","content":"Hello"}]}' \
  http://localhost:8080/v1/chat/completions

Or skip straight to seeing it work: ./scripts/demo.sh generates credentials if needed, starts the gateway, and sends a benign request and a prompt-injection attempt side by side so you can see AEGIS catch the difference — no test fixtures, no reading code first.

Service endpoints

Service Port Health Docs
Gateway 8080 /health requires Authorization: Bearer <key> on all routes except /health and /ready — see Quick start
Policy Engine 8081 /health policy-engine/README.md
Model Router 8082 /health model-router/README.md
Agent Gate 8083 /health agent-gate/README.md
Audit 8084 /health audit/README.md
Input Defense 8090 /health input-defense/README.md
Output Defense 8091 /health output-defense/README.md
Red Team 8092 /health redteam/README.md
Dashboard 3000 / (UI) dashboard/README.md
SMB Copilot 8093 /healthz smb-copilot/README.md
Corp Orchestrator 8094 /healthz corp-orchestrator/README.md
SMB Portal 3001 / (UI) smb-portal/README.md
SDK Proxy (gateway) 8080 /v1/chat/completions sdk/README.md

Development

make proto              # Lint + generate from shared/proto
make lint               # Go + Python linters
make test               # Unit tests (Go + Python)
make test-integration   # Docker smoke tests
make chaos              # Fault-injection tests against FAILURE_MODES.md's contract
make backup             # Encrypted postgres snapshot (see DR-RUNBOOK.md)
make bench              # Load test the defended chat-completion pipeline (stub backends)

Running tests without local Go

docker run --rm -v "$(pwd)/model-router:/app" -w /app golang:1.22-alpine go test ./...
docker run --rm -v "$(pwd)/policy-engine:/app" -w /app golang:1.22-alpine go test ./...

Running Python service tests

cd input-defense && pip install -e '.[dev]' && pytest
cd output-defense && pip install -e '.[dev]' && pytest

Load testing

Two load-testing scripts, both built on vegeta:

  • make bench / scripts/benchmark.sh -- CI-safe profile. Runs against whatever stack is already up (CI runs it with stub detector backends, same as the rest of the suite, so it measures the pipeline's own overhead -- auth, defense calls, policy evaluation, JSON marshaling -- not real-model inference latency). Writes benchmark-results/gateway-chat.json (vegeta report) plus a text summary.
  • scripts/load-test-ml.sh -- real-ML-backend profile. Not run in CI (CI never has the ML overlay up). Run this manually against a box running docker-compose.demo-ml.yml, with AEGIS_INTERNAL_TOKEN and AEGIS_API_KEYS set. It load-tests input-defense and output-defense directly (isolating each detector's real inference cost) as well as the full gateway pipeline, writing benchmark-results/ml-*.json.

Tracked for future work: neither script currently gates CI on any latency/throughput/success-rate threshold -- these numbers are informational only for now. There's no real baseline yet to set a sane threshold against; once a few real runs (especially from load-test-ml.sh) establish what "normal" looks like, this should be revisited and the CI-safe profile wired up to fail the build on a real regression.

Chaos / fault-injection testing

scripts/chaos-test.sh automates the manual procedure described in FAILURE_MODES.md's own "Verification" section: it stops one real dependency at a time against the running stack and asserts the documented contract actually holds, restoring and health-checking before moving to the next one.

  • Stopping input-defense, output-defense, policy-engine, or model-router must make the gateway's /v1/chat/completions fail closed (502/500) -- no response is ever released with a decision dependency down. Stopping policy-engine additionally checks that agent-gate's /v1/evaluate fails closed too, never APPROVED.
  • Stopping audit must NOT break anything -- the gateway chat pipeline keeps succeeding (fail-open), per FAILURE_MODES.md's explicit fail-open table.

Unlike the load-testing scripts above, this is pass/fail correctness against a contract this repo already publishes, not a numeric measurement -- it runs in CI (a dedicated chaos job) and a failure here fails the build. Run it locally with ./scripts/chaos-test.sh against an already-running stack.

Disaster recovery

See DR-RUNBOOK.md for the full procedure. Short version: docker-compose.yml has exactly one persistent volume (postgres_data -- the audit trail and the redteam's learned attack corpus); everything else is reproducible from GitHub/GHCR. scripts/backup-postgres.sh runs daily via a cron job installed by deploy/oracle/setup.sh, encrypting a snapshot with the same SOPS+age setup as the credential backup (Stage B.1). scripts/restore-postgres.sh restores it. Off-box redundancy (surviving a total VM loss, not just data corruption on a live box) is a deliberate manual step, not automated -- see the runbook for why.

Build order

Stage Component Status
0 Scaffold, shared schemas, CI, docker-compose Done
2 Input defense Done
3 Policy engine Done
4 Model router Done
5 Output defense Done
6 Agent gate Done
7 Red-team engine Done
8 Audit service Done
9 Dashboard Done
10 SDKs Done
11 Example apps Done
H4 Go gateway restored as the HTTP orchestrator (was Python) Done
12 Harness: governed multi-step agent loop + starter tool library (operator-platform phases 1-2, see ARCHITECTURE.md) Done

Production hardening (post-launch)

A second pass, after the initial build order above, closing real gaps found by direct investigation of the running system rather than a pre-written checklist — see ARCHITECTURE.md and each linked doc for the full detail on any of these.

Stage Component Status
A.1 Internal service-to-service auth (AEGIS_INTERNAL_TOKEN) Done
A.2 Model-router auth enforcement Done
B.1 Encrypted, opt-in credentials backup (SOPS + age) Done
B.2 Audit signing-key rotation with historical-key verification Done
B.3 Audit cursor-pagination fix (composite keyset, no dropped/duplicated rows) Done
C.1 Domain + HTTPS via Cloudflare — see Domain + HTTPS via Cloudflare Done
C.2 Dormant self-hosted WAF scaffold (Coraza + CRS, CrowdSec) — not wired into the default deploy, see deploy/oracle/waf/README.md Done (dormant, opt-in)
D.1 Load testing (CI-safe + manual real-ML profile), see Load testing Done
D.2 Chaos / fault-injection testing against FAILURE_MODES.md's contract, see Chaos / fault-injection testing Done
D.3 Disaster recovery: encrypted postgres backup/restore + daily cron, see Disaster recovery Done
E.1 Fixed a real credential-leak bypass in taint tracking (server-detected credentials now always block) Done
E.2 Agent-identity fingerprinting + spoofing-detection script (scripts/asi07-identity-consistency-query.py) Done

Environment variables

See .env.example for the full list. Key variables by service:

Variable Service Purpose
XAI_API_KEY model-router xAI Grok API key (not GROK_API_KEY) — set only in .env; never export in shell
AEGIS_DASHBOARD_USER / AEGIS_DASHBOARD_PASSWORD dashboard HTTP basic auth. No static default — generated at container startup if unset; use scripts/generate-credentials.sh to persist one
AEGIS_API_KEYS gateway Comma-separated API keys accepted by the gateway. No static default — generated at container startup if unset; use scripts/generate-credentials.sh to persist one
AEGIS_INTERNAL_TOKEN policy-engine, audit, input-defense, output-defense, model-router (enforce) + gateway, agent-gate, redteam, dashboard, SDK embedded mode (send) Shared internal service-to-service token. The five "enforce" services refuse to start without it — no default, no ephemeral fallback (it's shared across processes, so a per-process generated value would just disagree with everyone else's copy). Set via scripts/generate-credentials.sh
OPENAI_API_KEY, ANTHROPIC_API_KEY, GOOGLE_API_KEY model-router Cloud LLM providers
AEGIS_MODEL_ROUTER_CONFIG model-router Path to providers.yaml
AEGIS_POLICY_DIR policy-engine YAML policy pack directory
AEGIS_INPUT_DEFENSE_PORT input-defense HTTP port (default 8090)
AEGIS_OUTPUT_DEFENSE_PORT output-defense HTTP port (default 8091)
AEGIS_POLICY_ENGINE_URL agent-gate Policy-engine base URL
AEGIS_APPROVAL_TTL_HOURS agent-gate Pending approval TTL
AEGIS_REDTEAM_INPUT_DEFENSE_URL redteam Input defense base URL for campaigns
AEGIS_REDTEAM_OUTPUT_DEFENSE_URL redteam Output defense base URL for campaigns
AEGIS_AUDIT_SIGNING_KEY audit Ed25519 signing key (PEM or base64 seed)
AEGIS_AUDIT_SIGNING_KEY_ID audit Signer key identifier on receipts
AEGIS_AUDIT_SIGNING_KEYS_HISTORY audit Retired keys' public halves (keyID:base64pub, comma-separated), so receipts signed before a rotation stay verifiable. Maintained automatically by scripts/generate-credentials.sh on rotation — see "Rotating the audit signing key" below
AEGIS_INPUT_DEFENSE_URL sdk-proxy / gateway Input defense URL for SDK pipeline
AEGIS_MODEL_ROUTER_URL sdk-proxy / gateway Model router URL for SDK pipeline
OPENAI_BASE_URL your app Set to http://localhost:8080/v1 for reverse-proxy mode
DATABASE_URL redteam, audit Postgres connection

Rotating the audit signing key

Every audit receipt is signed and records which key signed it (AEGIS_AUDIT_SIGNING_KEY_ID). Rotating AEGIS_AUDIT_SIGNING_KEY used to break verification of every receipt signed under the old key — the audit service only ever held one public key to check against. It no longer does: scripts/generate-credentials.sh --rotate (or a backfill run that happens to catch the key still on its public dev default) now derives the outgoing key's public half and appends it to AEGIS_AUDIT_SIGNING_KEYS_HISTORY before generating a new key and a new AEGIS_AUDIT_SIGNING_KEY_ID — old receipts keep verifying, new receipts sign under the new key. This is automatic; you don't need to do anything beyond running the script. Redeploy afterward so the audit service picks up the new environment.

Backing up credentials

.env is gitignored and exists only on the box that generated it — losing that disk means losing every credential in it, with no history. Optional, opt-in encrypted backup via SOPS + age: see .sops.yaml for one-time setup, scripts/generate-credentials.sh for the (automatic, once configured) backup step, and scripts/decrypt-credentials.sh for recovery. Skipped entirely if you haven't set it up — nothing changes about the default flow.

Container images (GHCR)

Published under ghcr.io/hamidmatiny (compose pulls ghcr.io/hamidmatiny/aegis-*:${AEGIS_IMAGE_TAG:-latest}):

Image Service
aegis-gateway Gateway
aegis-policy-engine Policy engine
aegis-model-router Model router
aegis-agent-gate Agent gate
aegis-audit Audit
aegis-input-defense Input defense
aegis-output-defense Output defense
aegis-redteam Red team
aegis-smb-copilot SMB Copilot API
aegis-smb-portal SMB portal UI
aegis-dashboard Ops dashboard

Local builds: docker compose build (see Quick start). Production Oracle deploy: deploy/oracle/SMB-DEPLOY.md.

License

Apache 2.0 — see LICENSE.

About

Open-source AI security gateway + AEGIS-for-SMB copilot — defense-in-depth against prompt injection, jailbreaks, data exfiltration, and tool abuse; policy-as-code, tamper-evident audit, human approval for high-risk actions. Live at defenseaegis.org.

Topics

Resources

Contributing

Security policy

Stars

1 star

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages