Skip to main content

MCP server for secure local browser history access

Project description

ChronicleMCP

Secure, local-first Model Context Protocol (MCP) server for browser history

PyPI Version License Tests Coverage


Table of Contents

  1. Quick Start
  2. Features
  3. Installation
  4. Usage
  5. Configuration
  6. Security & Privacy
  7. Supported Browsers
  8. Troubleshooting
  9. Development
  10. Contributing
  11. License

Quick Start

# Install
pip install chronicle-mcp

# Run MCP server (stdio mode for AI agents like Claude, Cursor)
chronicle-mcp mcp

# Or start an HTTP server
chronicle-mcp http --port 8080

# Check available browsers
chronicle-mcp list-browsers

Features

Feature Description
🔒 Privacy-First All data stays on your machine. No cloud sync, no data collection.
🌐 Multi-Browser Chrome, Firefox, and Edge support
🔍 Multiple Search Tools Search by query, date range, domain, or recent history
📊 Output Formats Markdown (default) or JSON
Fast Performance Built with Python and SQLite
🔐 Secure URL sanitization removes sensitive query parameters
🐳 Docker Support Run as a container
🔧 CLI Interface Full command-line control
🌐 HTTP API RESTful API for integrations

Installation

pip (Recommended)

pip install chronicle-mcp

pipx (Isolated Installation)

pipx install chronicle-mcp

Docker

# Pull the latest image
docker pull ghcr.io/nikolasil/chronicle-mcp:latest

# Run the server
docker run -p 8080:8080 ghcr.io/nikolasil/chronicle-mcp

From Source

git clone https://github.com/nikolasil/chronicle-mcp.git
cd chronicle-mcp
pip install -e .

Homebrew (macOS)

brew tap nikolasil/chronicle-mcp
brew install chronicle-mcp

Usage

CLI Commands

chronicle-mcp mcp

Run the MCP server for AI agents.

# Stdio mode (default for AI assistants)
chronicle-mcp mcp

# SSE mode for HTTP clients
chronicle-mcp mcp --sse --port 8080
Option Description
--sse Use SSE transport instead of stdio
--host Host to bind (SSE mode only)
--port Port to listen on (SSE mode only)

chronicle-mcp http

Start a long-running HTTP REST API server.

# Default (foreground, port 8080)
chronicle-mcp http

# Custom port
chronicle-mcp http --port 9000

# Daemon mode
chronicle-mcp http --port 8080 --daemon

# Different browser
chronicle-mcp http --browser firefox
Option Description
--host Host to bind (default: 127.0.0.1)
--port Port to listen on (default: 8080)
--browser Default browser (default: chrome)
--foreground Run in foreground (default: true)
--daemon Run as daemon

chronicle-mcp status

Check if the server is running.

chronicle-mcp status --port 8080

chronicle-mcp logs

View server logs.

chronicle-mcp logs --port 8080 --lines 100

chronicle-mcp version

Show version information.

chronicle-mcp version

chronicle-mcp list-browsers

List available browsers on the system.

chronicle-mcp list-browsers
# Output: Available browsers: chrome, edge

chronicle-mcp completion

Generate shell completion scripts.

# Bash
chronicle-mcp completion bash >> ~/.bashrc

# Zsh
chronicle-mcp completion zsh >> ~/.zshrc

# Fish
chronicle-mcp completion fish > ~/.config/fish/completions/chronicle-mcp.fish

MCP Tools

search_history

Search browser history for keywords in titles or URLs.

def search_history(
    query: str,
    limit: int = 5,
    browser: str = "chrome",
    format_type: str = "markdown"
) -> str

Example:

# Markdown output (default)
search_history("python tutorial", limit=10, browser="chrome")

# JSON output
search_history("github", limit=5, format_type="json")

get_recent_history

Get recent browsing history from the last N hours.

def get_recent_history(
    hours: int = 24,
    limit: int = 20,
    browser: str = "chrome",
    format_type: str = "markdown"
) -> str

Example:

# Last 24 hours
get_recent_history(hours=48, limit=20)

count_visits

Count total visits to a specific domain.

def count_visits(
    domain: str,
    browser: str = "chrome"
) -> str

Example:

count_visits("github.com", browser="chrome")
# Output: Visits to 'github.com' in chrome: 42

list_top_domains

Get the most visited domains.

def list_top_domains(
    limit: int = 10,
    browser: str = "chrome",
    format_type: str = "markdown"
) -> str

Example:

list_top_domains(limit=20)

search_history_by_date

Search history within a date range.

def search_history_by_date(
    query: str,
    start_date: str,  # ISO format: YYYY-MM-DD
    end_date: str,    # ISO format: YYYY-MM-DD
    limit: int = 10,
    browser: str = "chrome",
    format_type: str = "markdown"
) -> str

Example:

search_history_by_date(
    "python",
    start_date="2024-01-01",
    end_date="2024-12-31",
    limit=20
)

list_available_browsers

Returns a list of browsers with detected history databases.

def list_available_browsers() -> str

Example:

list_available_browsers()
# Output: Available browsers: chrome, edge

HTTP API

Endpoints

Method Endpoint Description
GET /health Health check
GET /ready Readiness check
GET /metrics Basic metrics
GET /api/browsers List available browsers
POST /api/search Search history
POST /api/recent Recent history
POST /api/count Count domain visits
POST /api/top-domains Top domains
POST /api/search-date Search by date

Request/Response Examples

POST /api/search

curl -X POST http://localhost:8080/api/search \
  -H "Content-Type: application/json" \
  -d '{"query": "python tutorial", "limit": 10, "browser": "chrome", "format": "markdown"}'

Response:

{
  "results": [
    {
      "title": "Python Tutorial",
      "url": "https://docs.python.org/3/tutorial/",
      "timestamp": "2024-01-15T10:30:00+00:00"
    }
  ],
  "count": 1
}

GET /health

curl http://localhost:8080/health

Response:

{
  "status": "healthy",
  "service": "chronicle-mcp",
  "version": "1.1.0",
  "timestamp": "2024-01-15T10:30:00+00:00"
}

Configuration

ChronicleMCP can be configured using environment variables or a config file.

Environment Variables

Variable Description Default
CHRONICLE_CONFIG Path to config file ~/.config/chronicle-mcp/config.toml
CHRONICLE_PORT Default port 8080
CHRONICLE_HOST Default host 127.0.0.1
CHRONICLE_BROWSER Default browser chrome

Config File

Create ~/.config/chronicle-mcp/config.toml:

[default]
browser = "chrome"
limit = 10
format = "markdown"
log_level = "INFO"

Security & Privacy

  • Local-Only: All data stays on your machine
  • URL Sanitization: Sensitive query parameters are automatically removed:
    • token, session, key, password, auth, sid, access_token
  • Temp Files: History is copied to temporary files that are cleaned up after each query
  • No Data Collection: Your browsing data is never sent to any server
  • Error Messages: No sensitive file paths are exposed

Supported Browsers

Browser Windows macOS Linux
Chrome %LocalAppData%\Google\Chrome\User Data\Default\History ~/Library/Application Support/Google/Chrome/Default/History ~/.config/google-chrome/Default/History
Edge %LocalAppData%\Microsoft\Edge\User Data\Default\History ~/Library/Application Support/Microsoft Edge/Default/History ~/.config/microsoft-edge/Default/History
Firefox %AppData%\Mozilla\Firefox\Profiles\*.default\places.sqlite ~/Library/Mozilla/Firefox/Profiles/*.default/places.sqlite ~/.mozilla/firefox/*.default/places.sqlite

Troubleshooting

"Browser history not found"

  • Ensure the browser is installed
  • Check that Chrome/Edge isn't currently open (locks the database)
  • Run chronicle-mcp list-browsers to see detected browsers

"Permission denied"

  • Check file permissions on the browser's history database
  • On Windows, ensure the browser is closed before querying

Empty results

  • Try a more specific search term
  • Check the date range for search_history_by_date
  • Verify the browser has history data

Performance issues

  • Large history databases may take longer to query
  • Consider reducing the limit parameter

Development

Running Tests

# Run all tests
pytest

# Verbose output
pytest -v

# Specific test file
pytest tests/test_database.py

# Single test
pytest -k test_name

# With coverage
pytest --cov=chronicle_mcp

Development Server

# Run MCP server (stdio mode)
python -m chronicle_mcp mcp

# Run HTTP server
python -m chronicle_mcp http --port 8080

Code Quality

# Linting
ruff check .

# Formatting
ruff format .

# Type checking
mypy chronicle_mcp/

Contributing

Contributions are welcome! Please read our Contributing Guide for details.


License

MIT License - See LICENSE file for details.


Built with ❤️ for AI agents and developers

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

chronicle_mcp-1.3.4.tar.gz (37.1 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

chronicle_mcp-1.3.4-py3-none-any.whl (39.9 kB view details)

Uploaded Python 3

File details

Details for the file chronicle_mcp-1.3.4.tar.gz.

File metadata

  • Download URL: chronicle_mcp-1.3.4.tar.gz
  • Upload date:
  • Size: 37.1 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.1.0 CPython/3.13.7

File hashes

Hashes for chronicle_mcp-1.3.4.tar.gz
Algorithm Hash digest
SHA256 1da3826f1752ad2343a2d120fe6f054ebc34d26819473ad719723f93e1cf1df7
MD5 2da350d876196f2cfb82373cc546e678
BLAKE2b-256 5a8dea4d0b62547d384473574cc8ccd026d94d41f7755b4b97cfadc8c44f21dc

See more details on using hashes here.

File details

Details for the file chronicle_mcp-1.3.4-py3-none-any.whl.

File metadata

  • Download URL: chronicle_mcp-1.3.4-py3-none-any.whl
  • Upload date:
  • Size: 39.9 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.1.0 CPython/3.13.7

File hashes

Hashes for chronicle_mcp-1.3.4-py3-none-any.whl
Algorithm Hash digest
SHA256 a65a5b08e192c868039f080b95aa359259e8cfff6bec7ee833910a23563cdd7e
MD5 c1b7714546a5df2a55eefc4a73561ea0
BLAKE2b-256 7ad801a08e6f47de0e85b57dd3ac7965f1a4dc12f947348bf7b164e842a558d3

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page