npm package: @sneub/pair
Description: A personal AI assistant powered by Claude Code — connects Telegram and Slack to Claude with persistent memory and custom tools
Author: Shane
Latest version: 0.0.5

# pair

A personal AI assistant powered by Claude. Connects Telegram and Slack to
Claude with persistent memory, a workspace of notes, and custom tools — all
running as a long-lived daemon on your own machine.

## Install

Pair is a Bun CLI. Install it globally:

```bash
bun install -g @sneub/pair
```

## Quick start

```bash
mkdir my-agent && cd my-agent
pair init                 # scaffolds config.json, workspace/, .env, .gitignore
# edit .env with your API keys / bot tokens
pair run                  # foreground
pair run -d               # background daemon
```

`pair init` is non-interactive and creates everything in the current directory.
After editing `.env`, point it at Telegram or Slack and start chatting.

For an interactive setup that writes to `~/.pair/` instead, use `pair setup`.

## Commands

| Command | Description |
|---|---|
| `pair init` | Bootstrap a new agent directory in the current working dir (non-interactive) |
| `pair setup` | Interactive setup wizard — creates config, workspace, prompts for keys |
| `pair doctor` | Run diagnostic checks on your configuration |
| `pair tool list` | Show packaged and user tools, and which are enabled |
| `pair tool enable <name>` | Enable a packaged tool by adding it to `config.tools.enabled` |
| `pair tool disable <name>` | Disable a packaged tool |
| `pair run` | Start Pair in the foreground (alias: `pair start`) |
| `pair run -d` | Start Pair as a background daemon |
| `pair stop` | Stop the running daemon (SIGTERM, then SIGKILL after 10s) |
| `pair status` | Show running state, workspace stats, and config summary |

## Configuration

Pair stores its configuration under its resolved home directory:

1. `$PAIR_HOME` — explicit override (used by Docker and multi-instance setups)
2. `./config.json` in the current working directory → **local mode**
3. `~/.pair/` → **global mode** (default)

Within that home directory, Pair reads `config.json` (non-secret settings)
and `.env` (secrets). Environment variables always override values from
`config.json`, so you can keep non-secret settings in JSON and inject
secrets at deploy time.

### config.json

| Field | Type | Default | Description |
|---|---|---|---|
| `pair.sessionTimeoutMinutes` | number | `30` | Idle time before a session expires |
| `pair.logLevel` | string | `"info"` | `debug`, `info`, `warn`, `error` |
| `pair.model` | string | `"claude-sonnet-4-6"` | Claude model to use |
| `pair.workspaceDir` | string | `"~/.pair/workspace"` | Path to workspace directory |
| `pair.healthCheckPort` | number | _(unset)_ | Port for HTTP health check endpoint |
| `pair.authMode` | string | `"api-key"` | `"api-key"` or `"oauth"` (Claude Max/Pro) |
| `telegram.allowedUsers` | number[] | `[]` | Telegram user IDs allowed to interact |
| `slack.allowedUsers` | string[] | `[]` | Slack user IDs allowed to interact |
| `mcp.servers` | object | `{}` | MCP server configurations |
| `tools.enabled` | string[] | `["examples"]` | Packaged tool names to enable |

### Environment variables

| Variable | Required | Description |
|---|---|---|
| `ANTHROPIC_API_KEY` | api-key mode only | Anthropic API key for Claude |
| `PAIR_AUTH_MODE` | No | `api-key` (default) or `oauth` (Claude Max/Pro) |
| `PAIR_API_KEY_HELPER` | No | Path to a script that outputs fresh credentials |
| `TELEGRAM_BOT_TOKEN` | No | Telegram Bot API token |
| `TELEGRAM_ALLOWED_USERS` | No | Comma-separated Telegram user IDs |
| `SLACK_BOT_TOKEN` | No | Slack bot OAuth token (`xoxb-...`) |
| `SLACK_APP_TOKEN` | No | Slack app-level token (`xapp-...`) |
| `SLACK_SIGNING_SECRET` | No | Slack signing secret |
| `PAIR_MODEL` | No | Override the Claude model |
| `PAIR_LOG_LEVEL` | No | Override the log level |
| `PAIR_WORKSPACE_DIR` | No | Override the workspace directory |
| `PAIR_HEALTH_PORT` | No | Override the health check port |
| `PAIR_HOME` | No | Override the Pair home directory |

## Workspace

After `pair init`, your workspace lives at `./workspace/` (or
`~/.pair/workspace/` in global mode) and contains files Claude reads on every
turn:

- `CLAUDE.md` — canonical instructions; how the agent operates, memory rules, red lines
- `SOUL.md` — values and personality
- `IDENTITY.md` — name, vibe, how the agent presents itself
- `USER.md` — information about you (the agent updates this as it learns)
- `MEMORY.md` — curated long-term memory (the agent can update this)
- `tasks.md` — your current task list
- `HEARTBEAT.md` — short recurring reminders (optional)
- `BOOTSTRAP.md` — first-run ritual (self-deletes after use)

Edit them freely — they're how you customize Pair's behavior.

## Tools

Tools are the quickest way to add custom capabilities. You have two options:
enable one of the packaged tools that ship with Pair, or drop your own
executable into `<pair home>/tools/`.

**Enable a packaged tool:**

```bash
pair tool list             # see what's available
pair tool enable todoist   # adds "todoist" to config.tools.enabled
echo "TODOIST_API_TOKEN=..." >> .env
pair stop && pair run -d
```

**Write a custom tool** by dropping a file into `./tools/`:

```bash
#!/usr/bin/env bash
# name: uk-holiday
# description: Return whether today is a UK bank holiday.
# usage: uk-holiday

curl -s https://www.gov.uk/bank-holidays.json | jq -r \
  --arg today "$(date +%Y-%m-%d)" '
    .["england-and-wales"].events
    | map(select(.date == $today))
    | if length > 0 then "yes — \(.[0].title)" else "no" end
  '
```

```bash
chmod +x ./tools/uk-holiday
pair stop && pair run -d
```

Now DM Pair _"is today a UK bank holiday?"_ and it'll run the tool. Any
language works (bash, Bun, Node, Python, Ruby). Pair parses a short header
comment at the top of each file for the description it shows to Claude.

## MCP servers

Pair supports [Model Context Protocol](https://modelcontextprotocol.io/)
servers for extending Claude's capabilities. Configure them in `config.json`:

```json
{
  "mcp": {
    "servers": {
      "filesystem": {
        "command": "npx",
        "args": ["-y", "@modelcontextprotocol/server-filesystem", "/path/to/dir"]
      }
    }
  }
}
```

## Requirements

- [Bun](https://bun.sh) ≥ 1.1.0
- An Anthropic API key (or a Claude Max/Pro account for OAuth mode)

## License

MIT