A production-shaped personal operations agent. Unified daily ops brain: calendar, email, tasks, and research — all driven by the model, not hand-routed code.
- Morning briefing — checks your calendar, surfaces urgent email, reviews overdue tasks, synthesizes a prioritized day plan
- Calendar management — schedules, reschedules, finds free slots, detects conflicts, manages recurring events
- Email triage — reads threads, extracts action items (composable into tasks), drafts replies, batch-archives noise
- Task management — projects, priorities, daily plans, weekly reviews, subtasks, dependencies, all in local SQLite
- Deep research — spawns an isolated subagent that searches, fetches, cross-references, and returns a structured report
aria/
├── agent/
│ ├── loop.py # Main agent loop — long-horizon execution, context management
│ ├── registry.py # Tool registry — model-driven dispatch, 62 tools
│ ├── session.py # Session persistence — save/resume across interruptions
│ └── subagent.py # Research subagent — isolated context, scoped tools
├── scaffolding/
│ ├── context.py # Explicit context window management with plan checkpoints
│ ├── observability.py # structlog + OpenTelemetry
│ └── resilience.py # Token-bucket rate limiting + tenacity retries
├── tools/
│ ├── calendar/ # 16 tools — Google Calendar API v3
│ ├── email/ # 16 tools — Gmail API
│ ├── tasks/ # 15 tools — local SQLite
│ └── research/ # 15 tools — Brave Search + HTML parsing + notes
├── evals/ # Eval harness — 13 tool evals + session evals
├── config.py # Pydantic settings
├── errors.py # Typed exception hierarchy
└── cli.py # Rich CLI
62 tools. 4 namespaces. 1 global registry. Model picks; registry dispatches.
- Python 3.11+
- Anthropic API key
- Google Cloud project with Calendar and Gmail APIs enabled (for real OAuth)
- Brave Search API key (optional — stubs work without it)
# Install
pip install -e ".[dev]"
# Configure
cp .env.example .env
# Edit .env — add ANTHROPIC_API_KEY at minimum
# First-time setup (creates dirs, validates config)
python scripts/setup.py --stub # dev mode, no Google OAuth needed
# Run a task (stub mode — no real credentials)
aria run --stub-google "Show me my overdue tasks and help me plan today"
# Interactive session
aria interactive --stub-google# Complete OAuth flow (opens browser)
aria auth
# Then use without --stub-google
aria run "What's on my calendar this week?"
aria run "Check my email for anything urgent"Every session is persisted after each turn. If a session is interrupted or hits the tool call budget, resume it:
aria run "Plan my entire week in detail" --max-calls 20
# ... hits budget, prints: Resume with: aria run --resume abc123def456
aria run --resume abc123def456 "Keep going — finish the research section"aria sessions
aria sessions --limit 20# All tools
aria tools
# By namespace
aria tools --namespace calendar
aria tools --namespace research# Full suite
python -m pytest tests/ -v
# Unit only (fast, no network)
python -m pytest tests/unit/ -v
# Integration (stubs HTTP)
python -m pytest tests/integration/ -v# Tool-level evals (no API key needed for most)
aria eval --suite tool --stub-google
# All evals (session eval needs ANTHROPIC_API_KEY)
aria eval --suite all --stub-googleARIA manages long-horizon tasks explicitly. When context approaches the configured limit:
- A plan checkpoint is generated — the model summarizes what's been done and what remains
- The checkpoint is injected at the trim boundary
- Old
tool_resultcontent is stubbed to[trimmed], oldest first - If still over target, whole tool_use/tool_result pairs are dropped
This means the agent can run 50+ tool calls without losing coherence. See aria/scaffolding/context.py.
research.deep_dive spawns a ResearchSubagent — a genuine isolated execution context:
- Its own Anthropic API client and message history
- Scoped to 5 tools:
search,fetch,extract_facts,cross_reference,synthesize - Cannot access calendar, email, or task tools
- Runs its own loop until
synthesize()is called - Returns a typed
ResearchReportto the parent agent
See MEMO.md for the full rationale, including what was cut and what a second week would have addressed.
| Variable | Default | Description |
|---|---|---|
ANTHROPIC_API_KEY |
required | Anthropic API key |
ARIA_MODEL |
claude-sonnet-4-6 |
Model to use |
GOOGLE_CLIENT_SECRETS_FILE |
config/client_secrets.json |
OAuth client secrets |
GOOGLE_TOKEN_FILE |
config/token.json |
OAuth token cache |
BRAVE_SEARCH_API_KEY |
optional | Brave Search (stubs without it) |
ARIA_MAX_TOOL_CALLS |
100 |
Per-session tool call budget |
ARIA_CONTEXT_WINDOW_LIMIT |
180000 |
Tokens before trim triggers |
ARIA_CONTEXT_TRIM_TARGET |
120000 |
Target tokens after trim |
ARIA_GMAIL_RPM |
60 |
Gmail calls/min |
ARIA_CALENDAR_RPM |
60 |
Calendar calls/min |
ARIA_SEARCH_RPM |
10 |
Search calls/min |
ARIA_LOG_LEVEL |
INFO |
Log level |
ARIA_LOG_FORMAT |
json |
json or console |
ARIA_STUB_GOOGLE |
false |
Use stub Google APIs |
ARIA_DB_PATH |
data/aria.db |
SQLite path |
ARIA_NOTES_DIR |
data/notes |
Notes directory |