Skip to main content
Glama
README.md
# Athena

A local academic research assistant that runs entirely on your machine. Drop PDFs into a folder — Athena indexes them, builds a searchable vector library, and exposes tools to Claude Desktop for semantic search, claim extraction, contradiction detection, and multi-step research synthesis.

## What It Does

- **Semantic search** across your paper library with section-level filtering (search only results sections, only abstracts, etc.)
- **Contradiction detection** — surfaces conflicting claims across papers on a given topic
- **Definition extractor** — shows how different papers define the same term
- **Related paper suggestions** from Semantic Scholar for papers not in your library
- **Full research agent** — refines your query, extracts claims, detects contradictions, and returns a structured markdown report
- **Automatic metadata enrichment** — extracts titles from font analysis, verifies against Semantic Scholar, fills in authors/year/abstract

## Architecture

```
Claude Desktop
    │
    │  MCP (stdio — no tunnel needed)
    ▼
FastMCP Server (server/tools.py)
    │
    ├── ChromaDB  — vectors + chunk metadata (semantic search)
    ├── SQLite    — paper metadata (structured queries)
    └── LangGraph Agent (agent/graph.py)
            │
            └── Groq / Llama 3.3-70b  — query refinement, claim extraction, synthesis
```

**Storage split:** SQLite handles structured paper metadata (title, authors, year). ChromaDB stores chunks with their embeddings and attached metadata, enabling hybrid queries — semantic similarity + structured filters in one call.

**Parent/child chunking:** each paper section is split into large parent chunks (~512 tokens) and small child chunks (~128 tokens). Retrieval uses children for precise matching; the LLM receives parents for full context.

**Section-aware indexing:** `section_type` is stored on every chunk (`abstract`, `introduction`, `methods`, `results`, `conclusion`). Tools filter to specific sections — contradiction detection searches results/conclusions, definition extraction searches abstract/intro/methods.

## Setup

### Prerequisites
- Python 3.12+
- [uv](https://docs.astral.sh/uv/) — `pip install uv`
- A free [Groq API key](https://console.groq.com)

### Install

```bash
git clone <repo>
cd athena
uv sync
```

Create a `.env` file:
```
GROQ_API_KEY=your_key_here
```

### Index Papers

Start the file watcher — drop PDFs into `data/raw/` and they get indexed automatically:

```bash
uv run python -m pdf_ingestion.watcher
```

Papers already in `data/raw/` when the watcher starts are indexed on startup. The watcher is idempotent — restart it any time without re-indexing completed papers.

### Use the CLI

```bash
# Full research agent
uv run python cli.py "What are the main approaches to guided diffusion?"

# Quick semantic search (no LLM)
uv run python cli.py --search "score-based generative models"

# List all indexed papers
uv run python cli.py --list

# How different papers define a term
uv run python cli.py --define "latent space"
```

### Use with Claude Desktop (Recommended)

Install as a native extension — no tunnel, no URL, no re-configuration on restarts:

1. Build the extension package:
   ```bash
   uv run python build_dxt.py
   ```
2. Open Claude Desktop → Extensions → drag `athena.dxt` onto the page
3. Enter your Groq API key when prompted
4. Optionally set a Library Directory (defaults to `~/Documents/Athena`) — put your PDFs in the `raw/` subfolder inside that directory
5. Start a new chat — Athena tools are available immediately

On first use, ask Claude: *"Check if Athena is ready"* — it will call `get_status` and confirm the embedding model has finished loading before you search.

### Use with Claude Desktop (Dev / HTTP)

For local development with HTTP transport:

```bash
.\start_athena.ps1
```

This starts uvicorn on port 8000 and a Cloudflare quick tunnel. Copy the tunnel URL into Claude Desktop → Connectors → Add connector. Note the URL changes on every restart.

## Project Structure

```
athena/
├── agent/
│   └── graph.py              — LangGraph 6-node research agent
├── chunker/
│   └── chunker.py            — parent/child chunking with sentence boundaries
├── db/
│   └── database.py           — SQLite paper lifecycle management
├── embedding/
│   └── embedder.py           — sentence-transformers + ChromaDB storage
├── pdf_ingestion/
│   ├── metadata_enricher.py  — title extraction + Semantic Scholar lookup
│   ├── parser.py             — PyMuPDF extraction with font analysis
│   ├── section_detector.py   — 4-signal header detection
│   └── watcher.py            — watchdog file watcher + pipeline orchestration
├── server/
│   └── tools.py              — 8 MCP tools via FastMCP
├── cli.py                    — terminal interface
├── config.py                 — data directory configuration
├── build_dxt.py              — packages source into athena.dxt
├── manifest.json             — Claude Desktop extension manifest
└── start_athena.ps1          — dev script: uvicorn + cloudflared tunnel
```

## MCP Tools

| Tool | Description |
|---|---|
| `get_status` | Check if the embedding model has finished loading |
| `search_library` | Semantic search with section/year/paper filters |
| `get_paper_details` | Full metadata and abstract for a specific paper |
| `find_contradictions` | Conflicting claims across papers on a topic |
| `suggest_related` | Papers from Semantic Scholar not in your library |
| `list_library` | All indexed papers |
| `extract_definitions` | How each paper defines a specific term |
| `run_research_agent` | Full multi-step synthesis — query refinement, claims, contradictions, report |

## Tech Stack

| Component | Technology | Why |
|---|---|---|
| Vector store | ChromaDB | Local, no server process, hybrid metadata+vector queries |
| Metadata store | SQLite | Structured queries, zero setup, file-portable |
| Embeddings | all-MiniLM-L6-v2 | Local, CPU-friendly, 384d, ~90MB |
| LLM | Llama 3.3-70b via Groq | Free tier, fast inference, reliable JSON mode |
| Agent framework | LangGraph | Parallel fan-out, explicit state, human checkpoint support |
| PDF parsing | PyMuPDF | Fast, font-level access for structure detection |
| MCP server | FastMCP | Schema generation from type hints, stdio + HTTP transports |
| Packaging | uv + .dxt | Reproducible venvs, native Claude Desktop extension format |