Skip to main content

Things 3 MCP Server

Best-in-class MCP server for Things 3 — token-efficient, full CRUD, AppleScript + URL scheme.

Built to be the most capable and efficient Things integration for Claude Desktop, Claude Code, and any MCP-compatible client.

Features

  • Token-efficient output — concise one-line-per-item by default, detailed on demand
  • 30+ tools — full coverage of every Things 3 view and operation
  • Smart Someday filtering — correctly handles inherited Someday status (matches Things UI exactly)
  • Random sampling — get_random_inbox(5) for manageable LLM context instead of dumping hundreds of items
  • Summary mode — full GTD overview (get_summary) in ~20 lines
  • AppleScript + URL scheme — reliable writes with UUID feedback; automatic fallback
  • Bulk JSON import/export — Things URL scheme JSON format
  • HTTP transport — optional remote access with API key authentication
  • SKILL.md — self-teaching instructions so Claude uses tools optimally

Requirements

  • macOS (Things 3 is macOS/iOS only)
  • Things 3 installed and running
  • Python 3.12+
  • uv (recommended) or pip

Quick Start

Install and run

# Clone and install
git clone https://github.com/Groupthink-dev/things3-blade-mcp.git
cd things3-blade-mcp
uv sync

# Run (stdio transport — for Claude Desktop)
uv run things3-blade-mcp

Claude Desktop configuration

Add to ~/Library/Application Support/Claude/claude_desktop_config.json:

{
  "mcpServers": {
    "things3": {
      "command": "uv",
      "args": ["run", "--directory", "/path/to/things3-blade-mcp", "things3-blade-mcp"]
    }
  }
}

Claude Code

# Add as MCP server
claude mcp add things3 -- uv run --directory /path/to/things3-blade-mcp things3-blade-mcp

Token-Saving Tips

The server is designed to minimize LLM context consumption:

  1. Start with get_summary() — 20-line GTD overview, not hundreds of tasks
  2. Use random sampling — get_random_inbox(5) before get_inbox(limit=100)
  3. Defaults are efficient — concise=True, limit=10 on all tools
  4. One-line format: □ Buy groceries [3F8A2B1C] | today | deadline:2026-03-01 | #errands
  5. Null fields omitted — no "Notes: None" or "Tags: []" clutter
  6. Batch lookups — no N+1 queries; project/area names resolved in bulk

All Tools (30)

List Views (9)

Tool Description
get_inbox Unprocessed tasks
get_today Today's schedule (Someday-filtered)
get_upcoming Future scheduled tasks
get_anytime Available tasks
get_someday Deferred tasks (includes inherited)
get_logbook Completed tasks (configurable period)
get_trash Trashed tasks
get_deadlines All tasks with deadlines, sorted
get_summary Full GTD overview in ~20 lines

Random Sampling (4) — recommended entry points

Tool Description
get_random_inbox Random sample from inbox
get_random_today Random sample from today
get_random_anytime Random sample from anytime
get_random_todos Random sample, optional project filter

Entity Views (5)

Tool Description
get_todos All open todos (optional project filter)
get_projects Projects with open/done counts
get_areas High-level categories
get_tags All tags
get_tagged_items Todos with a specific tag

Search & Detail (4)

Tool Description
search_todos Search by title/notes
search_advanced Multi-filter search (status, date, tag, area)
get_recent Recently created items
show_item Single item by UUID with full details

Write (4) — AppleScript primary, URL scheme fallback

Tool Description
add_todo Create a todo (returns UUID)
add_project Create a project with optional todos
update_todo Update any todo field
update_project Update any project field

Bulk & Navigation (4)

Tool Description
json_import Bulk create via Things JSON format
json_export Export todos as compact JSON
show_in_things Reveal item in Things app
search_in_things Open Things search UI

HTTP Transport

For remote access (e.g., from a different machine or mobile):

# Set environment variables
export THINGS_MCP_TRANSPORT=http
export THINGS_MCP_HOST=127.0.0.1
export THINGS_MCP_PORT=8765
export THINGS_MCP_API_KEY=your-secret-key-here  # auto-generated if empty

# Run
uv run things3-blade-mcp

Bearer Token Authentication

When exposing the server through a tunnel or reverse proxy, set THINGS_MCP_API_TOKEN to require a bearer token on every request:

export THINGS_MCP_API_TOKEN=your-secret-token-here

All HTTP requests must then include the header:

Authorization: Bearer your-secret-token-here

Requests without a valid token receive 401 Unauthorized. If the env var is unset or empty, bearer auth is disabled and the server behaves as before (suitable for localhost-only access).

Security Warning

Never expose the HTTP port directly to the internet. Use a reverse proxy with TLS:

  • Cloudflare Tunnel (recommended — free, zero-config TLS)
  • Caddy (automatic HTTPS)
  • Nginx with Let's Encrypt

Cloudflare Tunnel example

# Install cloudflared
brew install cloudflare/cloudflare/cloudflared

# Create tunnel
cloudflared tunnel create things-mcp
cloudflared tunnel route dns things-mcp things-mcp.yourdomain.com

# Run tunnel
cloudflared tunnel --url http://localhost:8765 run things-mcp

Testing the HTTP endpoint

# Health check
curl http://localhost:8765/

# Call a tool (via MCP protocol)
curl -X POST http://localhost:8765/mcp \
  -H "Content-Type: application/json" \
  -H "X-API-Key: your-secret-key-here" \
  -d '{"method": "tools/call", "params": {"name": "get_summary", "arguments": {}}}'

Environment Variables

Variable Default Description
THINGS_MCP_TRANSPORT stdio stdio or http
THINGS_MCP_HOST 127.0.0.1 HTTP bind address
THINGS_MCP_PORT 8765 HTTP port
THINGS_MCP_API_TOKEN (none) Bearer token for HTTP auth — if set, requires Authorization: Bearer <token>
THINGS_MCP_API_KEY (auto) API key for HTTP auth (X-API-Key header)
THINGS_AUTH_TOKEN (auto) Things URL scheme auth token

Architecture

src/things3_blade_mcp/
├── server.py       # FastMCP instance + all 30 @mcp.tool definitions
├── formatters.py   # Two-tier output: concise (1-line) + detailed
├── someday.py      # Someday filtering (matches Things UI behavior)
├── applescript.py   # AppleScript bridge for writes (temp-file approach)
├── url_scheme.py   # URL scheme builder (fallback writes + checklist items)
├── sampling.py     # Random sampling helpers
├── auth.py         # API key auth for HTTP transport
└── models.py       # Shared constants

Design principles:

  • Reads via things.py (direct SQLite — fast, no app needed)
  • Writes via AppleScript (reliable, returns UUIDs, no auth token needed)
  • Fallback writes via URL scheme (for checklist items or when AppleScript fails)
  • Batch lookups eliminate N+1 queries in formatters
  • Someday filtering handles the Things 3 project-inheritance edge case

Development

# Install with dev/test dependencies
uv sync --all-extras

# Run tests
uv run pytest tests/ -v

# Lint
uv run ruff check src/ tests/

License

MIT

Metadata

Release files for things3-blade-mcp 0.3.0

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for things3-blade-mcp 0.3.0
File Size Uploaded
things3_blade_mcp-0.3.0.tar.gz 112.6 kB Details

Built distribution (wheel)

Table of built distributions (wheels) for things3-blade-mcp 0.3.0
File Interpreter ABI Platform
things3_blade_mcp-0.3.0-py3-none-any.whl Python 3 none any Details

Total release size: 139.7 kB

Release files / things3_blade_mcp-0.3.0.tar.gz

Download URL things3_blade_mcp-0.3.0.tar.gz
Size 112.6 kB
Tags Source
SHA-256 checksum
How to use checksums
d6126a74d75ccd3db460fd5672b9fc6ebbe752606cc61153e2a19845c6bff02f
BLAKE2b-256 checksum
How to use checksums
da219d040c197821ec213333a4144482a7f2b84a9642c934c6b36f951f22286d
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/6.1.0 CPython/3.13.12

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Jun 11, 2026.

Transparency log

Release files / things3_blade_mcp-0.3.0-py3-none-any.whl

Download URL things3_blade_mcp-0.3.0-py3-none-any.whl
Size 27.1 kB
Tags Python 3
SHA-256 checksum
How to use checksums
38be160ab61dd968cfc751baafef46b7923ed113b740690de1e67bfecb9e275b
BLAKE2b-256 checksum
How to use checksums
94554fd60aac7d63fd4dbf8de3eed48e5bc32a1448aedb034d9997207ca99dc6
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/6.1.0 CPython/3.13.12

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Jun 11, 2026.

Transparency log

Release history Release notifications | RSS feed

This release

0.3.0 This release

2 release files

0.1.2

2 release files

0.1.1

2 release files

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page