Architecture
SigmaShake is designed as a deterministic rule engine that operates at the AI agent's tool-call boundary. It ships as a self-contained Go binary with a small, pinned set of modules (go.mod and go.sum in sigmashake-gov/go).
System overview
User/Agent → Tool Call → ssg eval → Engine → Decision → Audit Log
↓
Dashboard (if ASK)
Core engine
Parser (sigmashake-gov/go/internal/rules)
Parses the .rules DSL into an AST of Rule objects. Features:
- Line-by-line parsing with error recovery
- Condition group splitting (AND/OR logic)
- Validation of all fields, operators, and patterns
- Support for
input.<key>generic field syntax
Evaluator (sigmashake-gov/go/internal/goengine)
The evaluation algorithm:
- Sort rules by priority (descending — higher first)
- Filter to enabled rules only
- For each rule in priority order:
- Check target matches tool capability
- Check condition groups (OR between groups, AND within)
- Short-circuit on first match
- Default to
allowif no rule matches
Key properties:
- Deterministic — Same input always produces same output
- Low latency — design target under 2 ms per evaluation; the only published measurement is the 2026-06-10 sigmashake-bench daemon-socket run (ssg 0.29.156, n=500): p50 0.39 ms, p99 1.91 ms
- Fail-secure regex — Invalid regex patterns match (trigger the rule)
- Fail-secure licensing & database — If the
license.jwtis invalid, or if the underlying SQLite database becomes corrupted/inaccessible, the engine immediately halts all tool calls with ablockdecision to prevent governance bypasses.
Database (sigmashake-gov/go/internal/db)
SQLite storage for persistent state:
rulestable — Serialized rule definitionsaudit_logtable — Evaluation history (rotated: 50,000-row soft cap that never deletes rows newer than 24 hours, 500,000-row hard ceiling)pending_approvalstable — ASK decisions awaiting human review
Indexes on timestamp, decision, tool for fast queries.
Adapters (sigmashake-gov/go/internal/cli)
Client adapters translate between different AI agent formats and SigmaShake's internal tool-call type. Each host has its own install code (init_<host>.go) and, where the host has a hook protocol, its own hook code (hook_<host>.go). Hosts with adapter code include Claude Code, Cursor, Copilot, Codex, Antigravity, Pi, OpenCode, Aider, Grok and Replit. Run ssg init --list to see the adapters that your build installs.
Note 2026-10-13: an earlier version of this page described the legacy TypeScript tree (src/engine/*.ts) and its ClaudeCodeAdapter, CodexAdapter, PiAdapter and GenericAdapter classes. The shipped ssg CLI and daemon are Go.
Capability taxonomy
Tools are classified into 6 capability categories:
| Capability | Tool examples |
|---|---|
execute | Bash, shell, terminal, run |
read | Read, cat, head, view |
write | Write, Edit, create, save |
search | Glob, Grep, find, rg |
agent | Agent, spawn, delegate |
network | WebFetch, WebSearch, curl |
Rule targets map to capabilities: DENY execution blocks all tools with execute capability.
Data flow
Standard evaluation
stdin JSON → parse ToolCall → load rules → evaluate → audit log → stdout JSON
Each ssg eval is a separate process. The daemon reloads rules when they change: it polls the rules directories about every 2 seconds and, on Linux, watches the project rules directory. The reload does not run on every evaluation.
ASK decision flow
Decision = "ask"
→ Health probe of the dashboard (skip the wait if no live approver)
→ POST /api/pending (creates approval)
→ Long-poll GET /api/pending/{id}/wait?timeout=<ms>
→ User approves/denies in dashboard
→ Long-poll returns "decided" → hook exit 0 (allow) or exit 2 (deny)
Timeout: 20 seconds by default, 45 seconds at most (SSG_ASK_DASHBOARD_TIMEOUT_MS overrides the default, clamped to the 45-second ceiling). If the dashboard is down, has no live approver, or gives no answer in time, the hook returns the ASK decision to the host harness, and the harness applies its own ASK behavior. The wait never turns into an allow.
The Claude Code hook (ssg hook eval) sends no terminal bell and does not poll at a fixed interval. A terminal bell and an inline Allow? [y/N] prompt belong to the separate ssg eval terminal flow only (2026-10-13 note: an earlier version of this diagram showed a bell and 500 ms polling for the hook).
Safety mechanisms
| Mechanism | Protection |
|---|---|
| Regex length limit (500 chars) | ReDoS prevention |
| Nested quantifier detection | ReDoS prevention |
| Glob/regex caching (LRU, 1000) | Performance |
Loop guard (engine: 5 identical calls; ssg eval: 3) | Infinite loop prevention |
| Audit input truncation (8,192 bytes, with a length and SHA-256 marker) | Audit log size control. The engine does not truncate. The audit writer does (auditInputMaxBytes); the marker holds the original length and a short SHA-256 fingerprint. |
| Audit rotation (50K-row soft cap with a 24 h floor, 500K-row hard ceiling) | SQLite growth control |
| Parameterized SQL only | Injection prevention |