Skip to main content

Autonomous AI agent with subprocess orchestration, dynamic tool creation, and a local-first web interface

Project description

Plutus — Autonomous AI Agent with Subprocess Orchestration

A better, easier-to-use AI agent that spawns subprocesses to edit code, analyze files, and create new tools on the fly.

FeaturesQuick StartArchitectureToolsDynamic ToolsConfiguration


What is Plutus?

Plutus is an autonomous AI agent system that gives Claude (or any LLM) the ability to spawn isolated subprocesses for file editing, code analysis, shell execution, and dynamic tool creation. Think of it as Claude Code on steroids — the AI can not only run commands and edit files, but also create entirely new tools at runtime to solve problems it wasn't originally designed for.

Key Differentiators

Feature OpenClaw Plutus
File editing Basic read/write Subprocess-isolated surgical edits with diff output
Code analysis None Full AST analysis (functions, classes, complexity, call graphs)
Subprocess spawning None Parallel worker pool with JSON protocol
Dynamic tool creation None Create, validate, and hot-load new Python tools at runtime
CLI experience Basic Rich interactive REPL with slash commands
Guardrails Basic 4-tier system (observer → autonomous) with audit logging
Planning None Built-in plan/step tracking with auto-progress

Features

Subprocess Orchestration

The agent spawns isolated worker subprocesses for every operation — file edits, code analysis, shell commands, and custom scripts all run in their own process with resource limits and timeouts.

Intelligent Code Editing

Surgical find/replace edits with diff output. The agent reads files, applies precise changes, and verifies the result — all in subprocess isolation.

Deep Code Analysis

AST-based analysis of Python files:

  • Function and class extraction with signatures
  • Cyclomatic complexity scoring (A–F ratings)
  • Import dependency mapping
  • Call graph generation
  • TODO/FIXME/HACK detection
  • Module summarization

Dynamic Tool Creation

The agent can write new Python tools at runtime:

  1. Writes the tool code
  2. Validates it (syntax check)
  3. Saves it to ~/.plutus/custom_tools/
  4. Hot-loads it into the tool registry
  5. Uses it immediately

4-Tier Guardrail System

  • Observer — Read-only, AI can only observe
  • Assistant — Every action requires user approval
  • Operator — Pre-approved actions run autonomously
  • Autonomous — Full control, no restrictions

Multiple Interfaces

  • Terminal REPL (plutus chat) — Rich interactive chat with slash commands
  • Single prompt (plutus run "...") — Execute one task and exit
  • Web UI (plutus start) — Full web interface with WebSocket streaming

Quick Start

Installation

# Clone the repository
git clone https://github.com/Crypt0nly/plutus.git
cd plutus

# Install with pip
pip install -e .

# Run setup wizard
plutus setup

First Run

# Interactive terminal chat
plutus chat

# Or run a single prompt
plutus run "Create a Python script that sorts a CSV file by the second column"

# Or launch the web UI
plutus start

Chat Commands

Inside plutus chat, use slash commands:

Command Description
/help Show available commands
/tools List all available tools
/plan Show current execution plan
/clear Start a new conversation
/tier Show or change guardrail tier
/workers Show active subprocesses
/exit Exit the chat

Architecture

┌─────────────────────────────────────────────────────┐
│                   Agent Runtime                      │
│  ┌──────────┐  ┌──────────┐  ┌──────────────────┐  │
│  │   LLM    │  │ Planner  │  │   Guardrails     │  │
│  │ (Claude) │  │          │  │ (4-tier system)  │  │
│  └────┬─────┘  └──────────┘  └──────────────────┘  │
│       │                                              │
│  ┌────▼──────────────────────────────────────────┐  │
│  │              Tool Registry                     │  │
│  │  ┌────────┐ ┌────────────┐ ┌───────────────┐  │  │
│  │  │ Shell  │ │ Code Editor│ │ Code Analysis │  │  │
│  │  └────────┘ └────────────┘ └───────────────┘  │  │
│  │  ┌────────────┐ ┌──────────────┐ ┌─────────┐  │  │
│  │  │ Subprocess │ │ Tool Creator │ │ Browser │  │  │
│  │  └────────────┘ └──────────────┘ └─────────┘  │  │
│  │  ┌──────────┐ ┌─────────┐ ┌─────────────────┐ │  │
│  │  │Filesystem│ │ Process │ │ Custom Tools... │ │  │
│  │  └──────────┘ └─────────┘ └─────────────────┘ │  │
│  └───────────────────┬───────────────────────────┘  │
│                      │                               │
│  ┌───────────────────▼───────────────────────────┐  │
│  │           Subprocess Manager                   │  │
│  │  ┌─────────────┐  ┌──────────────────────┐    │  │
│  │  │ Worker Pool │  │  JSON stdin/stdout    │    │  │
│  │  │ (max: 8)    │  │  protocol             │    │  │
│  │  └─────────────┘  └──────────────────────┘    │  │
│  └───────────────────────────────────────────────┘  │
│                      │                               │
│  ┌───────────────────▼───────────────────────────┐  │
│  │           Worker Subprocesses                  │  │
│  │  ┌──────┐ ┌──────────┐ ┌──────────┐ ┌──────┐ │  │
│  │  │Shell │ │File Edit │ │Code Anal.│ │Custom│ │  │
│  │  │Worker│ │Worker    │ │Worker    │ │Worker│ │  │
│  │  └──────┘ └──────────┘ └──────────┘ └──────┘ │  │
│  └───────────────────────────────────────────────┘  │
└─────────────────────────────────────────────────────┘

Subprocess Communication Protocol

Workers communicate via JSON over stdin/stdout (one JSON object per line):

Agent → Worker:  {"action": "edit", "path": "/file.py", "edits": [...]}
Worker → Agent:  {"success": true, "result": {"changes": 2, "diff": "..."}}

This design provides:

  • Isolation — each operation runs in its own process
  • Safety — crashes in workers don't affect the agent
  • Parallelism — multiple workers can run simultaneously
  • Simplicity — JSON protocol is easy to debug and extend

Tools

Built-in Tools

Tool Description
shell Execute shell commands
filesystem File system operations (legacy, still available)
code_editor Create, read, and edit files via subprocess
code_analysis AST-based Python code analysis via subprocess
subprocess Direct subprocess spawning for parallel tasks
tool_creator Create new tools at runtime
process System process management
system_info System information queries
browser Web browsing (Playwright)
clipboard Clipboard operations
desktop Desktop/window management
app_manager Application management

Code Editor Operations

read       — Read file content (with optional line range)
write      — Create or overwrite a file
append     — Append content to a file
edit       — Apply surgical find/replace edits
delete     — Delete a file or directory
move       — Move/rename a file
copy       — Copy a file or directory
mkdir      — Create directories
list       — List directory contents
find       — Find files by glob pattern
grep       — Search file contents with regex
diff       — Show diff between two files

Code Analysis Operations

analyze        — Full analysis (everything below combined)
find_functions — List all function/method definitions with signatures
find_classes   — List all class definitions with methods
find_imports   — Extract all import statements
find_todos     — Find TODO/FIXME/HACK/NOTE comments
complexity     — Calculate cyclomatic complexity per function
symbols        — Extract all top-level symbols
call_graph     — Build function call graph
summarize      — Generate human-readable summary

Dynamic Tool Creation

The agent can create new tools when it encounters a task that requires capabilities it doesn't have:

# Example: Agent creates a CSV processor tool
tool_creator(
    operation="create",
    tool_name="csv_processor",
    description="Process and transform CSV files",
    code="""
import csv
from pathlib import Path

def main(args):
    path = args.get('path', '')
    operation = args.get('operation', 'read')
    
    if operation == 'read':
        with open(path) as f:
            reader = csv.DictReader(f)
            rows = list(reader)
        return {'success': True, 'result': {'rows': rows, 'count': len(rows)}}
    
    elif operation == 'sort':
        column = args.get('column', '')
        with open(path) as f:
            reader = csv.DictReader(f)
            rows = sorted(list(reader), key=lambda r: r.get(column, ''))
        return {'success': True, 'result': {'rows': rows, 'count': len(rows)}}
    
    return {'success': False, 'error': f'Unknown operation: {operation}'}
"""
)

Created tools are:

  • Validated — syntax-checked before saving
  • Persisted — saved to ~/.plutus/custom_tools/ across sessions
  • Hot-loaded — immediately available in the tool registry
  • Isolated — executed in subprocess workers

Configuration

Config File: ~/.plutus/config.json

{
  "model": {
    "provider": "anthropic",
    "model": "claude-sonnet-4-6",
    "temperature": 0.7,
    "max_tokens": 4096
  },
  "guardrails": {
    "tier": "operator",
    "audit_enabled": true
  },
  "agent": {
    "max_tool_rounds": 25
  },
  "planner": {
    "enabled": true,
    "auto_plan": true
  },
  "gateway": {
    "host": "127.0.0.1",
    "port": 7777
  }
}

Supported Providers

Provider Models Config
Anthropic Claude 4 Sonnet, Claude 4 Opus, etc. ANTHROPIC_API_KEY
OpenAI GPT-4.1, GPT-4.1-mini, etc. OPENAI_API_KEY
Ollama Llama 3.2, Mistral, etc. Local, no key needed
Custom Any OpenAI-compatible endpoint API_KEY + base URL

API Keys

Keys are stored securely in ~/.plutus/.secrets.json (chmod 600) and never exposed via the API. Set them via:

# Setup wizard
plutus setup

# Environment variable
export ANTHROPIC_API_KEY=sk-ant-...

# Or via the web UI settings page

CLI Reference

plutus                  # Show help
plutus start            # Launch web UI + API server
plutus chat             # Interactive terminal chat
plutus run "prompt"     # Run a single prompt
plutus setup            # Setup wizard
plutus status           # Show configuration
plutus tools            # List available tools
plutus set-tier <tier>  # Change guardrail tier
plutus audit            # Show audit log
plutus config-show      # Display full config as JSON

Development

# Install dev dependencies
pip install -e ".[dev]"

# Run tests
pytest tests/ -v

# Run specific test file
pytest tests/test_subprocess.py -v

# Lint
ruff check plutus/

Project Structure

plutus/
├── plutus/
│   ├── __init__.py
│   ├── __main__.py
│   ├── cli.py                      # CLI with chat REPL
│   ├── config.py                   # Configuration management
│   ├── core/
│   │   ├── agent.py                # Main agent runtime
│   │   ├── conversation.py         # Conversation management
│   │   ├── heartbeat.py            # Heartbeat system
│   │   ├── llm.py                  # LLM client (LiteLLM)
│   │   ├── memory.py               # SQLite memory store
│   │   ├── planner.py              # Plan management
│   │   └── subprocess_manager.py   # Subprocess orchestrator
│   ├── gateway/                    # Web API + WebSocket
│   ├── guardrails/                 # Permission tiers + audit
│   ├── skills/                     # YAML skill definitions
│   ├── tools/
│   │   ├── base.py                 # Tool base class
│   │   ├── registry.py             # Tool registry with hot-reload
│   │   ├── code_analysis.py        # AST-based code analysis
│   │   ├── code_editor.py          # File creation and editing
│   │   ├── subprocess_tool.py      # Direct subprocess spawning
│   │   ├── tool_creator.py         # Dynamic tool creation
│   │   ├── shell.py                # Shell commands
│   │   ├── filesystem.py           # File system operations
│   │   ├── process.py              # Process management
│   │   ├── browser.py              # Web browsing
│   │   └── ...
│   └── workers/
│       ├── shell_worker.py         # Shell command worker
│       ├── file_edit_worker.py     # File editing worker
│       ├── code_analysis_worker.py # Code analysis worker
│       └── custom_worker.py        # Dynamic tool worker
├── ui/                             # React web interface
├── bridge/                         # Local ↔ cloud workspace sync
├── shared/                         # Shared models and memory (used by local + cloud)
├── tests/
│   ├── test_subprocess.py          # 34 comprehensive tests
│   ├── test_config.py
│   ├── test_guardrails.py
│   └── test_tools.py
├── pyproject.toml
└── README.md

Cloud Version

A hosted, fully managed version of Plutus is available at useplutus.ai for users who want a zero-setup cloud experience. The cloud version includes:

  • Persistent cloud workspace with push/pull sync to your local Plutus
  • Multi-device access via any browser
  • Managed infrastructure — no API keys or server setup required
  • Priority support

The cloud backend is closed-source and maintained in a private repository. If you are interested in self-hosting the full cloud stack, please get in touch.

License

MIT License — see LICENSE for details.

Project details


Release history Release notifications | RSS feed

Download files

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

Source Distributions

No source distribution files available for this release.See tutorial on generating distribution archives.

Built Distributions

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

plutus_ai-0.3.200-cp314-cp314-win_amd64.whl (1.5 MB view details)

Uploaded CPython 3.14Windows x86-64

plutus_ai-0.3.200-cp314-cp314-manylinux_2_28_x86_64.whl (7.8 MB view details)

Uploaded CPython 3.14manylinux: glibc 2.28+ x86-64

plutus_ai-0.3.200-cp314-cp314-macosx_11_0_arm64.whl (1.6 MB view details)

Uploaded CPython 3.14macOS 11.0+ ARM64

plutus_ai-0.3.200-cp314-cp314-macosx_10_15_x86_64.whl (1.6 MB view details)

Uploaded CPython 3.14macOS 10.15+ x86-64

plutus_ai-0.3.200-cp313-cp313-win_amd64.whl (1.5 MB view details)

Uploaded CPython 3.13Windows x86-64

plutus_ai-0.3.200-cp313-cp313-manylinux_2_28_x86_64.whl (7.8 MB view details)

Uploaded CPython 3.13manylinux: glibc 2.28+ x86-64

plutus_ai-0.3.200-cp313-cp313-macosx_11_0_arm64.whl (1.6 MB view details)

Uploaded CPython 3.13macOS 11.0+ ARM64

plutus_ai-0.3.200-cp313-cp313-macosx_10_13_x86_64.whl (1.6 MB view details)

Uploaded CPython 3.13macOS 10.13+ x86-64

plutus_ai-0.3.200-cp312-cp312-win_amd64.whl (1.5 MB view details)

Uploaded CPython 3.12Windows x86-64

plutus_ai-0.3.200-cp312-cp312-manylinux_2_28_x86_64.whl (7.9 MB view details)

Uploaded CPython 3.12manylinux: glibc 2.28+ x86-64

plutus_ai-0.3.200-cp312-cp312-macosx_11_0_arm64.whl (1.6 MB view details)

Uploaded CPython 3.12macOS 11.0+ ARM64

plutus_ai-0.3.200-cp312-cp312-macosx_10_13_x86_64.whl (1.6 MB view details)

Uploaded CPython 3.12macOS 10.13+ x86-64

plutus_ai-0.3.200-cp311-cp311-win_amd64.whl (1.5 MB view details)

Uploaded CPython 3.11Windows x86-64

plutus_ai-0.3.200-cp311-cp311-manylinux_2_28_x86_64.whl (7.9 MB view details)

Uploaded CPython 3.11manylinux: glibc 2.28+ x86-64

plutus_ai-0.3.200-cp311-cp311-macosx_11_0_arm64.whl (1.6 MB view details)

Uploaded CPython 3.11macOS 11.0+ ARM64

plutus_ai-0.3.200-cp311-cp311-macosx_10_9_x86_64.whl (1.6 MB view details)

Uploaded CPython 3.11macOS 10.9+ x86-64

File details

Details for the file plutus_ai-0.3.200-cp314-cp314-win_amd64.whl.

File metadata

File hashes

Hashes for plutus_ai-0.3.200-cp314-cp314-win_amd64.whl
Algorithm Hash digest
SHA256 61c22c9b867cf56b581ab73ac500e2ee8fc41d55b0d64a699dfefbe3bb29b4c3
MD5 fd3254d08d91745b449f2f79661c1d56
BLAKE2b-256 e0d59b36a6d1cf9059341cf59db7f99a3ffada533aa619fd6b0752b5a8681470

See more details on using hashes here.

File details

Details for the file plutus_ai-0.3.200-cp314-cp314-manylinux_2_28_x86_64.whl.

File metadata

File hashes

Hashes for plutus_ai-0.3.200-cp314-cp314-manylinux_2_28_x86_64.whl
Algorithm Hash digest
SHA256 dfb953d4dbc166dc2abaffc6b0b1955044b963135a592493a5348379fb8840ce
MD5 6f801693abc27114a2ca8c4088573ae5
BLAKE2b-256 5c4e46fedf77354a23ae3ca73c2791d7594ab6427a4aad5f585ebe21cc910564

See more details on using hashes here.

File details

Details for the file plutus_ai-0.3.200-cp314-cp314-macosx_11_0_arm64.whl.

File metadata

File hashes

Hashes for plutus_ai-0.3.200-cp314-cp314-macosx_11_0_arm64.whl
Algorithm Hash digest
SHA256 1be9255d93b384de4def8444a4623ddd0635ebc973d7dead5eb6709dab839ac7
MD5 16d2f73d582c5917ad1e6b2269efccb7
BLAKE2b-256 6632adc7b9c4d3892188435ec4ec44be13a13a1583b7ff39c46c0557bcaeb8fa

See more details on using hashes here.

File details

Details for the file plutus_ai-0.3.200-cp314-cp314-macosx_10_15_x86_64.whl.

File metadata

File hashes

Hashes for plutus_ai-0.3.200-cp314-cp314-macosx_10_15_x86_64.whl
Algorithm Hash digest
SHA256 2e8e8275b0d4ebb6c66a70d22322da965bad85ea1f2870c695de895a256d55e0
MD5 118a196105012c57014dc75949043fbc
BLAKE2b-256 c4c9b71394c4d5cf8f132574bea05bdecf50bdf45097b3cf08d9fd096ce92802

See more details on using hashes here.

File details

Details for the file plutus_ai-0.3.200-cp313-cp313-win_amd64.whl.

File metadata

File hashes

Hashes for plutus_ai-0.3.200-cp313-cp313-win_amd64.whl
Algorithm Hash digest
SHA256 546494d3af566cef5a8b860f579c18773997e704d0082f3612141c3c030f87bd
MD5 96d5e4e75a8ab876501d6e65ec6e8954
BLAKE2b-256 6e0fc672c147de69fd56a65b088e26bfd319681aea230b7c2e8fb280319631d4

See more details on using hashes here.

File details

Details for the file plutus_ai-0.3.200-cp313-cp313-manylinux_2_28_x86_64.whl.

File metadata

File hashes

Hashes for plutus_ai-0.3.200-cp313-cp313-manylinux_2_28_x86_64.whl
Algorithm Hash digest
SHA256 33899921eedbd9658cc7d6a08fd913eb0ecdc6811dc813fffcbbbb897da2b9ef
MD5 3f3a2db5644ac21a71673c427cfcaa60
BLAKE2b-256 002f82beec3250228db68345dc273171ce672968975d695132452b9e6de616a5

See more details on using hashes here.

File details

Details for the file plutus_ai-0.3.200-cp313-cp313-macosx_11_0_arm64.whl.

File metadata

File hashes

Hashes for plutus_ai-0.3.200-cp313-cp313-macosx_11_0_arm64.whl
Algorithm Hash digest
SHA256 7324b340b2abbec853849347ed2f238756e95ba47dab04e96f104e4bc717f345
MD5 5c7ef2c446942f5ddeb98e48a22b4db3
BLAKE2b-256 ad08e1b9841e22704220498e010460596b6bc0798d3040516e7b22b71803fa85

See more details on using hashes here.

File details

Details for the file plutus_ai-0.3.200-cp313-cp313-macosx_10_13_x86_64.whl.

File metadata

File hashes

Hashes for plutus_ai-0.3.200-cp313-cp313-macosx_10_13_x86_64.whl
Algorithm Hash digest
SHA256 c7a92bf21477021005f5206e50fc04b776b84c40a57728af29d2280de74ed8bb
MD5 92cded1ebe5a0e887af87bffe32dfe73
BLAKE2b-256 209b0aaa651781805d85a6970ffd62f85c8042104ce69de23f3ea2f3cd68f37e

See more details on using hashes here.

File details

Details for the file plutus_ai-0.3.200-cp312-cp312-win_amd64.whl.

File metadata

File hashes

Hashes for plutus_ai-0.3.200-cp312-cp312-win_amd64.whl
Algorithm Hash digest
SHA256 d5a3960688a16509cf4f05ba6f2130b37fedd7cdb6fdd864bc6fd01534c81878
MD5 bf71bdd0deddc3a4db3d8df649daece9
BLAKE2b-256 4256476244ca3321a3edb290c37fb0013b82db45a3821ea4aa3fe12a0649bda5

See more details on using hashes here.

File details

Details for the file plutus_ai-0.3.200-cp312-cp312-manylinux_2_28_x86_64.whl.

File metadata

File hashes

Hashes for plutus_ai-0.3.200-cp312-cp312-manylinux_2_28_x86_64.whl
Algorithm Hash digest
SHA256 f0f2fec6d316cdebff06665319ed7aa5d3026e6d420fcb79295d4311be3297af
MD5 000eae3b97e64925c4b0bcfbde13bc98
BLAKE2b-256 d3a81329bd699a99ed465ec82f4d55288918f34512a6c7ad1da39cf3dd9f0297

See more details on using hashes here.

File details

Details for the file plutus_ai-0.3.200-cp312-cp312-macosx_11_0_arm64.whl.

File metadata

File hashes

Hashes for plutus_ai-0.3.200-cp312-cp312-macosx_11_0_arm64.whl
Algorithm Hash digest
SHA256 797a8682b07a5008626332e26df0983358681d68a6d2bcbc0a516c2d5ec18575
MD5 993a0e929f299dc399540802c85dab82
BLAKE2b-256 5bae27ec97689418b77c342ec989e02ba6f56d351ef23d0c0f796dd20d16fe6a

See more details on using hashes here.

File details

Details for the file plutus_ai-0.3.200-cp312-cp312-macosx_10_13_x86_64.whl.

File metadata

File hashes

Hashes for plutus_ai-0.3.200-cp312-cp312-macosx_10_13_x86_64.whl
Algorithm Hash digest
SHA256 abd771d9224752dc5da49c9ebbf8636fb1eb476e2f4be854748717b213048cf1
MD5 665cbc74ea20f6d415640c4a43fc040e
BLAKE2b-256 2d9c26daba7b428e4024c0e641878fa75b8873a88ac5ae7edb12654328a4bd19

See more details on using hashes here.

File details

Details for the file plutus_ai-0.3.200-cp311-cp311-win_amd64.whl.

File metadata

File hashes

Hashes for plutus_ai-0.3.200-cp311-cp311-win_amd64.whl
Algorithm Hash digest
SHA256 987d9fe81f6f7f64ebaa60fcff1bb983f7a5d523767069c7661d24173bb2e643
MD5 89218d2219ea348179aa8bde0a821c81
BLAKE2b-256 7e4eb53489a3f1bcca6d0561020c560fe170e24686718800288167e445debe32

See more details on using hashes here.

File details

Details for the file plutus_ai-0.3.200-cp311-cp311-manylinux_2_28_x86_64.whl.

File metadata

File hashes

Hashes for plutus_ai-0.3.200-cp311-cp311-manylinux_2_28_x86_64.whl
Algorithm Hash digest
SHA256 6486094a4dd0c03198dc25f6105d22a76b03831771561e39624fe27c915579e2
MD5 bb8d6a2a61912df68163d69f234dc621
BLAKE2b-256 8071aa2da6c5271b29b4d48bd6fbe1b27ef1e8324bb51cf4183539f0bce1ccdd

See more details on using hashes here.

File details

Details for the file plutus_ai-0.3.200-cp311-cp311-macosx_11_0_arm64.whl.

File metadata

File hashes

Hashes for plutus_ai-0.3.200-cp311-cp311-macosx_11_0_arm64.whl
Algorithm Hash digest
SHA256 43504d76adab135995cd2423e0fb7e0ed63c43349686ae79da5ca409ab7664c8
MD5 048282a2d2eeafb9d8e90c340205ae62
BLAKE2b-256 ffdd5cd9f1e19b0b0356e7bde8ab694c5534511291b175f0ba47825d5767da27

See more details on using hashes here.

File details

Details for the file plutus_ai-0.3.200-cp311-cp311-macosx_10_9_x86_64.whl.

File metadata

File hashes

Hashes for plutus_ai-0.3.200-cp311-cp311-macosx_10_9_x86_64.whl
Algorithm Hash digest
SHA256 e3ba3c150bf2789a178345983cff77c234a65b50cfa53f1286128ef0de0aa79e
MD5 dddf083dccf8df533c2ef0f44a67e2c2
BLAKE2b-256 352cbbb07165f1cd7ff0862d0bf58587cdd9d2d754db5e79e01ae1f2c4353bca

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