🛡️ Agent Risk Analyzer (ARA)
Zero-config, fully local static security scanner for AI agents.
ARA detects 20 vulnerability categories across LangChain, CrewAI, AutoGen, and MCP agent projects — no API keys, no cloud, no LLM required.
$ ara scan ./my-agent
──────────────────────────── Agent Risk Analyzer ────────────────────────────
Target: /path/to/my-agent
Files: 3 scanned | Duration: 0.04s | Framework: langchain
Grade Score 🔴 Critical 🟠 High 🟡 Medium ⚪ Low Total
F 116 6 9 3 5 23
╭─────────────────────────────────────────────────────────────────────────────╮
│ Grade F Score: 116 — Unsafe for production — critical issues must be │
│ fixed immediately. │
╰─────────────────────────────────────────────────────────────────────────────╯
✨ Features
- 🔒 Fully local — no data leaves your machine, no API keys needed
- ⚡ Zero config — point at a directory, get a graded report
- 🎯 20 vulnerability rules mapped to MITRE ATLAS and OWASP LLM Top 10 2025
- 🧠 AST + regex — two-tier detection with CONFIRMED / SUSPECTED confidence levels
- 📊 A–F grading — weighted severity scoring for instant risk posture
- 🔌 Multi-format output — terminal (Rich), JSON, Markdown
- 🤖 CI/CD ready —
--ciflag returns exit code 1 on findings
📦 Installation
pip install arascan
Requires Python 3.11+
For development:
git clone https://github.com/Prnvlol/agent-risk-analyzer.git
cd agent-risk-analyzer
python -m venv .venv && source .venv/bin/activate
pip install -e ".[dev]"
🚀 Usage
Basic scan
ara scan ./my-agent-project
JSON report (for CI pipelines)
ara scan ./my-agent --format json --output report.json
Markdown report
ara scan ./my-agent --format markdown --output report.md
CI mode (fail on findings)
ara scan ./my-agent --ci --min-severity HIGH
Filter options
# Only show CONFIRMED findings (hide heuristic checks)
ara scan ./my-agent --no-suspected
# Disable specific rules
ara scan ./my-agent --disable VULN-017,VULN-019
# Set minimum severity threshold
ara scan ./my-agent --min-severity MEDIUM
List all rules
ara list-rules
🎯 What ARA Detects
| ID | Vulnerability | Severity | ATLAS | OWASP |
|---|---|---|---|---|
| VULN-001 | Direct Prompt Injection | CRITICAL | AML.T0051.000 | LLM01 |
| VULN-002 | Indirect Prompt Injection | CRITICAL | AML.T0051.001 | LLM01 |
| VULN-003 | Unrestricted Code Execution | CRITICAL | AML.T0050 | LLM06 |
| VULN-005 | Over-Permissioned Tools | HIGH | AML.T0053 | LLM06 |
| VULN-006 | Unbounded Agent Autonomy | HIGH | AML.T0053 | LLM06 |
| VULN-007 | Tool Result Poisoning | HIGH | AML.T0097 | LLM06 |
| VULN-008 | Memory / Context Poisoning | HIGH | AML.T0087 | LLM04 |
| VULN-009 | Insecure MCP Configuration | HIGH | AML.T0088 | LLM03 |
| VULN-010 | System Prompt Leakage | HIGH | AML.T0056.001 | LLM07 |
| VULN-011 | Insecure Tool Input | MEDIUM | AML.T0053 | LLM06 |
| VULN-012 | Sensitive Data in Logs | HIGH | AML.T0048 | LLM02 |
| VULN-013 | Missing Rate Limiting | MEDIUM | AML.T0054 | LLM10 |
| VULN-014 | Hardcoded Credentials | MEDIUM | AML.T0037 | LLM02 |
| VULN-015 | Insecure Multi-Agent Trust | MEDIUM | AML.T0087 | LLM06 |
| VULN-016 | Verbose Error Messages | LOW | AML.T0048 | LLM02 |
| VULN-017 | Missing Output Filtering | LOW | AML.T0048 | LLM05 |
| VULN-018 | Missing Human-in-the-Loop | LOW | AML.T0053 | LLM06 |
| VULN-019 | Unversioned Prompts | LOW | AML.T0088 | LLM07 |
| VULN-020 | Third-Party Plugin Risk | LOW | AML.T0010.003 | LLM03 |
📊 Grading System
Findings are scored by severity weight, then mapped to a letter grade:
| Weight | Severity |
|---|---|
| 10 | CRITICAL |
| 5 | HIGH |
| 2 | MEDIUM |
| 1 | LOW |
| Grade | Score Range | Meaning |
|---|---|---|
| A | 0 | No findings |
| B | 1 – 5 | Minor issues |
| C | 6 – 15 | Needs attention |
| D | 16 – 30 | Significant risk |
| F | 31+ | Unsafe for production |
🏗️ Architecture
src/
├── cli.py # Typer CLI (scan, list-rules, version)
├── scanner.py # File discovery, AST parsing, detector dispatch
├── models.py # Pydantic models (Finding, ScanResult, grades)
├── report.py # Rich terminal, JSON, Markdown renderers
└── detectors/
├── base.py # BaseDetector ABC + ScanContext
├── credentials.py # VULN-014: hardcoded secrets (15 regex patterns)
├── code_execution.py # VULN-003: exec/eval/subprocess (AST)
├── prompt_injection.py # VULN-001/002/010/017/019
├── tool_permissions.py # VULN-005/007/011/018/020
├── mcp_config.py # VULN-009: MCP misconfigurations
├── multi_agent.py # VULN-006/008/015
├── framework_specific.py # VULN-003/006/015/020: LangChain/CrewAI/AutoGen
├── logging_detector.py # VULN-012/016
└── rate_limiting.py # VULN-013
0.2.0 framework coverage:
- LangChain — unsafe FAISS deserialization and explicit unbounded agent loops
- CrewAI — unsafe code execution and delegation without runtime boundaries
- AutoGen — unsandboxed code execution and explicit unbounded group chat rounds
Design principles:
- No LLM dependency — all detection is deterministic (AST + regex)
- Two-tier confidence —
CONFIRMED(pattern exists verbatim) vsSUSPECTED(absence-of-safeguard heuristic) - Single-pass scan — files read once into
ScanContext, shared across all detectors - Fail-safe detectors — a crashing detector never stops the scan
🧪 Development
# Install dev dependencies
pip install -e ".[dev]"
# Run tests
pytest
# Run with coverage
pytest --cov=src --cov-report=term-missing
# Lint
ruff check src/ tests/
# Type check
mypy src/
📋 Exit Codes
| Code | Meaning |
|---|---|
0 |
Scan completed (no findings, or non-CI mode) |
1 |
Findings detected (CI mode only) |
2 |
Error (bad arguments, scan failure) |
🗺️ Roadmap
- Framework-specific detectors — LangChain, CrewAI, and AutoGen security patterns
-
--deepmode — optional local LLM analysis via Ollama for semantic prompt review - GitHub Actions workflow — pre-built CI action
- PyPI release —
pip install arascan - VS Code extension — inline findings in the editor
🔗 Related
| Tool | What it does |
|---|---|
| ARA (this) | Static scanner — find vulnerabilities before deployment |
| parry-ai | Runtime guardrail — block threats while your agent is running |
Use ARA to find the issues. Use parry to fix them at runtime.
🤝 Community
- Contributing — setup, checks, detector guidelines, and pull request expectations
- Security policy — private vulnerability reporting process
- Issues — bug reports, rule requests, and framework support requests
ARA is early alpha. Reports with minimal vulnerable examples are especially useful: false negatives, false positives, framework-specific patterns, and CI/reporting friction all help shape the roadmap.
📄 License
Built with 🐍 Python — no clouds, no APIs, no excuses.
Metadata
Release files for arascan 0.2.0
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | |
|---|---|---|---|
| arascan-0.2.0.tar.gz | 38.6 kB | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| arascan-0.2.0-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 79.9 kB
Release files / arascan-0.2.0.tar.gz
| Download URL | arascan-0.2.0.tar.gz |
|---|---|
| Size | 38.6 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
1c6f5b041226f5dd5a85a9e9336c34649656b8be7326ba4b6c0e55e9a9c4e579
|
|
BLAKE2b-256 checksum How to use checksums |
d60424bc8de312cef7b8fd953e9dc0edda47054a06ea13c4bfd8ef32d19c6a16
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/6.2.0 CPython/3.14.3
|
Release files / arascan-0.2.0-py3-none-any.whl
| Download URL | arascan-0.2.0-py3-none-any.whl |
|---|---|
| Size | 41.3 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
339fa1a61e9d99c99a49453b2de71359f6e0c554aea4870d6017884c5df84895
|
|
BLAKE2b-256 checksum How to use checksums |
e9443cc740a0a16ade34dec91392079979a3a758fd5adac05ed5c0606a5c982f
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/6.2.0 CPython/3.14.3
|