AUTOPSY
AI-powered incident diagnosis for engineering teams. Pull production error logs and recent deploys, send them to an LLM, and get a structured root cause analysis in the terminal in under a minute. Zero-trust: your data never leaves your environment.
30-Second Diagnosis
Pull logs, correlate deploys, get a structured root cause with confidence score.
Zero-Trust
Your data stays in your environment. API keys in local .env, never committed.
Multi-Source
CloudWatch, Datadog, GitHub, GitLab. All collectors run in parallel.
Slack & Post-Mortem
Post to Slack or generate markdown post-mortems instantly.
Prerequisites
| Area | Requirement |
|---|---|
| AWS | CloudWatch Logs access; credentials via aws configure or AWS_PROFILE; IAM:
logs:DescribeLogGroups, logs:StartQuery, logs:GetQueryResults. |
| Datadog | Optional. API key + Application key; site (e.g. datadoghq.com). |
| GitHub | Personal Access Token with repo scope. |
| GitLab | Optional. Personal Access Token with read_api scope. Supports self-hosted. |
| AI Provider | OpenAI or Anthropic account + API key + credits. |
| Local | Python 3.10+, pip, terminal, internet. |
Installation
From PyPI
pip install autopsy-cli
From Source
git clone https://github.com/zaappy/autopsy.git && cd autopsy
pip install -e ".[dev]"
Verify Installation
autopsy --version
# autopsy 0.3.0
# prompt v1
# python 3.12.x
Quick Start
Three steps: install → init → diagnose.
1. Configure
autopsy init # Interactive wizard — creates ~/.autopsy/config.yaml + .env
2. Diagnose
autopsy diagnose # Run full pipeline: collect → reduce → AI → render
3. Or Use the TUI
autopsy # Interactive menu: Diagnose, History, Setup, Validate, Config
TUI Shortcuts
| Key | Action |
|---|---|
d |
Diagnose |
i |
Init / Setup |
v |
Validate |
c |
Config |
q |
Quit |
Esc |
Back |
Configuration
After autopsy init, edit ~/.autopsy/config.yaml or re-run the wizard. Credentials are
stored in ~/.autopsy/.env.
Config Sections
| Section | Purpose |
|---|---|
| aws | CloudWatch region, log groups, time window (minutes). Uses your AWS CLI credentials. |
| datadog | Optional. Site, service/source filters, time window. Uses DD_API_KEY /
DD_APP_KEY. |
| github | Repo (owner/repo), branch, number of recent commits. Uses GITHUB_TOKEN. |
| gitlab | Optional. URL, project ID, branch, deploy count. Uses GITLAB_TOKEN. Can coexist
with GitHub. |
| ai | Provider (anthropic or openai), model, API keys. |
| slack | Optional. Webhook integration for posting diagnoses to Slack. |
Managing Config
autopsy config show # Print config (secrets masked)
autopsy config show --reveal # Show secrets
autopsy config validate # Check env vars and connectivity
~/.autopsy/.env to .gitignore.
Never commit credentials.How It Works
Collect
CloudWatch, Datadog, GitHub, GitLab — all in parallel
Reduce
Log dedup, token budget, diff filters
Diagnose
Single prompt to LLM → structured JSON
Render
Rich panels, JSON, post-mortem, or Slack
Pipeline Details
Step 1: Collect
All configured collectors run in parallel by default using asyncio.to_thread with
a ThreadPoolExecutor fallback. Each collector creates its own API client instance (thread-safe).
Partial failures are handled gracefully.
- CloudWatch: Logs Insights queries, error-level log extraction
- Datadog: Logs API search with site support (us1, eu1, us3, us5, ap1)
- GitHub: Last N commits + diffs via PyGitHub
- GitLab: Commits, diffs, MRs, deployment events via python-gitlab
Step 2: Reduce
4-stage log reduction pipeline:
- Query filter — regex at query level (~90% reduction)
- Deduplication — hash message templates, keep 1 + count (~60%)
- Truncation — 500 char/entry, stack traces to top 5 frames (~40%)
- Token budget — hard cap at 6000 tokens, FIFO eviction
Step 3: Diagnose
The AI engine receives all collected data in a single prompt. Logs and deploys are grouped, and each collector
is labeled in the prompt (e.g. per-source blocks) so the model can correlate across systems. When more than one
collector runs, the prompt includes cross-source instructions. The LLM returns structured JSON with root cause,
correlated deploy, suggested fix, timeline, and a sources array.
Step 4: Render
Output to Rich terminal panels (default), raw JSON (--json), markdown post-mortem
(--postmortem), or Slack webhook (--slack).
- Terminal & Slack: A Sources summary panel/line appears only when there are multiple log sources and/or multiple deploy sources.
- Post-mortem: Data Sources markdown table only appears when more than one source contributed.
- JSON & History: Always includes the
sourcesarray structure when present (name,data_type,entry_count).
CLI Reference
| Command | Description |
|---|---|
autopsy |
Interactive TUI — menu with Diagnose, Setup, Validate, Config |
autopsy init |
Interactive config wizard |
autopsy init --slack |
Configure only Slack integration |
autopsy diagnose |
Run full diagnosis pipeline |
autopsy diagnose --source <name> |
Restrict to named collector(s); repeat flag for multiple. |
autopsy diagnose --json |
Output raw JSON |
autopsy diagnose --postmortem |
Generate markdown post-mortem |
autopsy diagnose --slack |
Post diagnosis to Slack webhook |
autopsy diagnose --time-window 15 |
Override log window (minutes) |
autopsy diagnose --log-group /aws/lambda/foo |
Override log groups (repeatable) |
autopsy diagnose --provider openai |
Use OpenAI instead of Anthropic |
autopsy diagnose --sequential |
Run collectors sequentially (debugging) |
autopsy history list |
List saved diagnoses (newest first) |
autopsy history show <id> |
Show a saved diagnosis |
autopsy history search "query" |
Search saved diagnoses |
autopsy history stats |
Show history statistics |
autopsy history export ./h.json |
Export history to JSON or CSV |
autopsy config show |
Print config (secrets masked) |
autopsy config validate |
Check credentials and connectivity |
autopsy version |
CLI, prompt, and Python version |
Collectors
All collectors implement the BaseCollector ABC and run in parallel by default.
CloudWatch
Uses boto3 to run CloudWatch Logs Insights queries. Polls with backoff until results are ready.
Applies the 4-stage log reduction pipeline.
- Config: region, log_groups, time_window
- Auth: AWS CLI credentials
- Errors:
AWSAuthError,AWSPermissionError
Datadog
Optional. Uses the Datadog Logs Search API. Shares the same log reduction pipeline as CloudWatch.
- Config: site (us1/eu1/us3/us5/ap1), service, source, time_window
- Auth:
DD_API_KEY+DD_APP_KEY - Behavior: Skips with warning when keys not set
GitHub
Uses PyGithub to fetch recent commits and diffs. Smart diff reduction: filter by file extension,
exclude lockfiles/generated, cap per file and per commit.
- Config: repo, branch, deploy_count, token_env
- Auth:
GITHUB_TOKEN - Errors:
GitHubAuthError,GitHubRateLimitError
GitLab
Optional. Uses python-gitlab to pull commits, diffs, merge requests, and deployment
events. Supports self-hosted instances.
- Config: url, project_id, branch, deploy_count, token_env
- Auth:
GITLAB_TOKEN - Errors:
GitLabAuthError,GitLabRateLimitError
Parallel Execution
All active collectors run concurrently using asyncio.to_thread with asyncio.gather.
Falls back to ThreadPoolExecutor if a running event loop is detected.
- Single collector → sequential (no asyncio overhead)
- Multiple → parallel (wall-clock ≈ slowest collector)
- Partial failure → warn and continue
- All fail → raises
CollectorError - Use
--sequentialfor debugging
AI Engine
The orchestrator calls the AIEngine interface — never calls provider APIs directly.
Supported Providers
| Provider | Default Model | API Key Env |
|---|---|---|
| Anthropic | claude-sonnet-4-20250514 | ANTHROPIC_API_KEY |
| OpenAI | gpt-4o | OPENAI_API_KEY |
How It Works
- Build prompt: System prompt + user prompt from all collected data
- Call LLM: Single API call with structured JSON output instructions
- Parse response: Validate JSON against Pydantic models
- Retry: Once on malformed JSON. Falls back to raw text on second failure.
Output Structure
- Root Cause — summary, category, confidence (0.0–1.0), evidence
- Correlated Deploy — commit SHA, author, PR title, changed files
- Suggested Fix — immediate action + long-term recommendation
- Timeline — chronological event reconstruction
Interface Contracts
BaseCollector collectors/base.py
class CollectedData(BaseModel):
source: str # "cloudwatch", "github", "gitlab"
data_type: str # "logs" | "deploys" | "metrics"
entries: list[dict] # Normalized data entries
time_range: tuple[datetime, datetime]
raw_query: str # The query used (for debugging)
entry_count: int # Total before dedup/truncation
truncated: bool # Whether data was reduced
class BaseCollector(ABC):
@abstractmethod
def validate_config(self, config: dict) -> bool: ...
@abstractmethod
def collect(self, config: dict) -> CollectedData: ...
@property
@abstractmethod
def name(self) -> str: ...
AIEngine ai/engine.py
class AIEngine:
def diagnose(self, collected_data: list[CollectedData]) -> DiagnosisResult:
"""Build prompt, call LLM, parse response.
Retries once on malformed JSON."""
def _build_prompt(self, collected_data) -> tuple[str, str]: ...
def _parse_response(self, raw: str) -> DiagnosisResult: ...
DiagnosisOrchestrator diagnosis.py
class DiagnosisOrchestrator:
def run(self, *, time_window=None, log_groups=None,
provider=None, sequential=False) -> DiagnosisResult:
"""Full pipeline: validate → collect → diagnose → return"""
Data Models
All models are Pydantic BaseModel subclasses.
DiagnosisResult ai/models.py
class RootCause(BaseModel):
summary: str
category: str # code_change | config_change | infra | dependency | traffic | unknown
confidence: float # 0.0 - 1.0
evidence: list[str]
class CorrelatedDeploy(BaseModel):
commit_sha: str | None = None
author: str | None = None
pr_title: str | None = None
changed_files: list[str] = []
class SuggestedFix(BaseModel):
immediate: str
long_term: str
class TimelineEvent(BaseModel):
time: str
event: str
class DiagnosisResult(BaseModel):
root_cause: RootCause
correlated_deploy: CorrelatedDeploy
suggested_fix: SuggestedFix
timeline: list[TimelineEvent]
prompt_version: str = "v1"
raw_response: str | None = None
Error Hierarchy
All custom exceptions inherit from AutopsyError.
Error Display
[ERROR] CloudWatch query timeout after 60s.
[FIX] Check that the log group exists: aws logs describe-log-groups
[DOCS] https://docs.aws.amazon.com/...
Changelog
Unreleased
Added
- Multi-source diagnosis: All collected data goes into one LLM prompt with cross-source correlation instructions when multiple collectors run.
autopsy diagnose --source <name>flag to restrict to named collector(s).- JSON output (
--json) and saved history now include asourcesarray. - UX gating for Sources summary panel, Slack line, and post-mortem Data Sources table (only appear when multiple sources contribute).
- GitLab collector: optional integration via
python-gitlab— commits, diffs, merge requests, deployment events; supports self-hosted; smart diff reduction. - Datadog log collector: optional integration with Datadog Logs API; supports us1/eu1/us3/us5/ap1.
- Shared log reduction pipeline used by CloudWatch and Datadog.
- Parallel collector execution: all collectors run concurrently by default.
autopsy diagnose --sequentialflag for debugging.
0.3.0 — 2026-03-11
Added
- Demo mode (
--demo) with bundled fixture data. - Datadog log collector.
- Shared log reduction pipeline (
utils/log_reduction.py).
0.2.2 — 2026-03-10
Added
- Diagnosis history with local SQLite storage.
- Markdown post-mortem via
--postmortem. - Slack webhook output via
--slack.
0.2.0
Added
- Interactive TUI with menu.
- CloudWatch Logs Insights and GitHub collectors.
- AI diagnosis engine (Anthropic / OpenAI).
- Terminal and JSON renderers.
Contributing
Development Setup
- Fork and clone
git clone https://github.com/YOUR_USERNAME/autopsy.git && cd autopsy - Virtual environment
python -m venv .venv && source .venv/bin/activate - Install with dev dependencies
pip install -e ".[dev]"
Code Style
| Tool | Command | Purpose |
|---|---|---|
| Ruff | ruff check . |
Linting |
| mypy | mypy autopsy |
Type checking (strict) |
| pytest | pytest -v |
All tests must pass |
Project Layout
| Path | Purpose |
|---|---|
autopsy/cli.py |
CLI entrypoint; no business logic |
autopsy/collectors/ |
CloudWatch, Datadog, GitHub, GitLab |
autopsy/ai/ |
AI engine (prompts, models, diagnosis) |
autopsy/renderers/ |
Terminal and JSON output |
autopsy/config.py |
Config loading and validation |
tests/ |
Pytest tests (including VCR for HTTP) |
Submitting Changes
- Create a branch from
main - Make changes and add/update tests
- Run
ruff check .andpytestlocally - Push to your fork and open a PR against
main
Security Policy
Supported Versions
| Version | Supported |
|---|---|
| 0.2.x+ | Yes |
| < 0.2 | No |
Reporting a Vulnerability
Email: zaappy@users.noreply.github.com with a clear description, steps to reproduce, and impact.
What We Care About
- Credential or token leakage (config, env, or logs)
- Insecure handling of
~/.autopsy/.envor API keys - Issues in data sent to/from third-party APIs
- Any behavior that could expose user or deployment data