README.en.md•11.6 kB
# Persistent Terminal MCP Server
[简体中文](README.md)
Persistent Terminal MCP Server is a TypeScript implementation of a Model Context
Protocol (MCP) server that keeps terminal sessions alive for AI assistants and
automation flows. It is built on top of [`node-pty`](https://github.com/microsoft/node-pty)
so commands continue running even when the requesting client disconnects.
## Highlights
- **Persistent PTY sessions** – create, reuse, and terminate long-running shells
- **Smart output buffering** – incremental reads plus head, tail, or head-tail
  views with token estimates for large logs
- **Spinner animation compaction** – automatically detects and throttles progress
  animations (like npm install spinners) to reduce noise and preserve real logs
- **Full session management** – statistics, listing, kill signals, and automatic
  cleanup for inactive sessions
- **MCP-ready** – ships with tools, resources, and prompts compatible with
  Claude Desktop, Claude Code, and other MCP clients
- **REST API option** – optional Express server mirrors the MCP functionality
  for non-MCP integrations
## Installation
### One-off run (recommended for MCP clients)
Use `npx` to launch the server without a global install:
```bash
npx persistent-terminal-mcp
```
The REST flavor is available the same way:
```bash
npx persistent-terminal-mcp-rest
```
### Project dependency
Add the package to an existing project (CLI + TypeScript APIs):
```bash
npm install persistent-terminal-mcp
```
Now you can reference both the CLI binaries in `node_modules/.bin/` and the
TypeScript exports:
```ts
import { PersistentTerminalMcpServer } from "persistent-terminal-mcp";
```
### Global install (optional)
```bash
npm install --global persistent-terminal-mcp
persistent-terminal-mcp
```
## Local Development
Clone the repo if you want to work on the source:
```bash
npm install          # install dependencies
npm run build        # compile TypeScript → dist/
npm start            # launch the MCP server over stdio
```
During development you can run the TypeScript sources directly:
```bash
npm run dev          # MCP server (tsx)
npm run dev:rest     # REST server (tsx)
```
### Debugging Mode
To enable debug logging (output to stderr, won't interfere with MCP communication):
```bash
MCP_DEBUG=true persistent-terminal-mcp
```
### Example Scripts
```bash
npm run example:basic        # basic lifecycle (create → write → read → kill)
npm run example:smart        # demonstrates head/tail/head-tail reading
npm run test:tools           # exercises every MCP tool end-to-end
npm run test:fixes           # regression tests for recent bug fixes
```
## MCP Client Configuration
### Claude Desktop
#### macOS / Linux
**Configuration file location**: `~/Library/Application Support/Claude/claude_desktop_config.json`
Add the following configuration to your MCP settings file:
```json
{
  "mcpServers": {
    "persistent-terminal": {
      "command": "npx",
      "args": ["-y", "persistent-terminal-mcp"],
      "env": {
        "MAX_BUFFER_SIZE": "10000",
        "SESSION_TIMEOUT": "86400000",
        "COMPACT_ANIMATIONS": "true",
        "ANIMATION_THROTTLE_MS": "100"
      }
    }
  }
}
```
**Note**:
- The `-y` flag automatically confirms npx download prompts
- If globally installed (`npm install -g persistent-terminal-mcp`), change `command` to `"persistent-terminal-mcp"` and remove `-y` from `args`
#### Windows
**Configuration file location**: `%APPDATA%\Claude\claude_desktop_config.json`
```json
{
  "mcpServers": {
    "persistent-terminal": {
      "command": "cmd",
      "args": ["/c", "npx", "-y", "persistent-terminal-mcp"],
      "env": {
        "MAX_BUFFER_SIZE": "10000",
        "SESSION_TIMEOUT": "86400000",
        "COMPACT_ANIMATIONS": "true",
        "ANIMATION_THROTTLE_MS": "100"
      }
    }
  }
}
```
**Note**:
- Windows requires `cmd /c` to invoke `npx`
- If globally installed, change `args` to `["/c", "persistent-terminal-mcp"]`
---
### Claude Code
#### macOS / Linux
Use the command line to quickly add the MCP server:
```bash
claude mcp add persistent-terminal \
  --env MAX_BUFFER_SIZE=10000 \
  --env SESSION_TIMEOUT=86400000 \
  --env COMPACT_ANIMATIONS=true \
  --env ANIMATION_THROTTLE_MS=100 \
  -- npx -y persistent-terminal-mcp
```
**Or** edit the configuration file `~/.claude.json`:
```json
{
  "mcpServers": {
    "persistent-terminal": {
      "command": "npx",
      "args": ["-y", "persistent-terminal-mcp"],
      "env": {
        "MAX_BUFFER_SIZE": "10000",
        "SESSION_TIMEOUT": "86400000",
        "COMPACT_ANIMATIONS": "true",
        "ANIMATION_THROTTLE_MS": "100"
      }
    }
  }
}
```
#### Windows
> # ⚠️ **Important for Windows users**
>
> ## **Claude Code** has argument parsing issues with `claude mcp add` command on Windows
>
> ### **🚫 Command-line configuration is NOT recommended**
>
> Please refer to the dedicated setup guide:
>
> ### 📖 [Windows persistent-terminal MCP setup](docs/clients/claude-code-windows.md)
>
> This guide provides two recommended approaches:
>
> - ✅ **Project-level configuration** (recommended): Create a `.mcp.json` file in your project root
> - ✅ **Global configuration**: Use a Python script to modify `~/.claude.json`
---
### Cursor / Cline
Configuration is similar to Claude Desktop. Please refer to the MCP configuration documentation for each client.
### Codex
#### macOS / Linux
Add the following to `.codex/config.toml`:
```toml
# MCP Server Configuration (TOML Format)
# For configuring persistent-terminal MCP server
[mcp_servers.persistent-terminal]
command = "npx"
args = ["-y", "persistent-terminal-mcp"]
[mcp_servers.persistent-terminal.env]
MAX_BUFFER_SIZE = "10000"
SESSION_TIMEOUT = "86400000"
COMPACT_ANIMATIONS = "true"
ANIMATION_THROTTLE_MS = "100"
```
#### Windows
Add the following to `.codex/config.toml`:
```toml
# MCP Server Configuration (TOML Format)
# For configuring persistent-terminal MCP server
[mcp_servers.persistent-terminal]
command = "cmd"
args = ["/c", "npx", "-y", "persistent-terminal-mcp"]
[mcp_servers.persistent-terminal.env]
MAX_BUFFER_SIZE = "10000"
SESSION_TIMEOUT = "86400000"
COMPACT_ANIMATIONS = "true"
ANIMATION_THROTTLE_MS = "100"
```
**Note**: Windows requires `cmd /c` to invoke `npx`
---
### Environment Variables
| Variable                | Description                               | Default             |
| ----------------------- | ----------------------------------------- | ------------------- |
| `MAX_BUFFER_SIZE`       | Maximum number of lines to keep in buffer | 10000               |
| `SESSION_TIMEOUT`       | Session timeout in milliseconds           | 86400000 (24 hours) |
| `COMPACT_ANIMATIONS`    | Enable spinner animation compaction       | true                |
| `ANIMATION_THROTTLE_MS` | Animation throttle time in milliseconds   | 100                 |
| `MCP_DEBUG`             | Enable debug logging                      | false               |
## Programmatic Usage (TypeScript)
```ts
import {
  PersistentTerminalMcpServer,
  TerminalManager,
  RestApiServer,
} from "persistent-terminal-mcp";
const manager = new TerminalManager();
const rest = new RestApiServer(manager);
await rest.start(3001);
const mcpServer = new PersistentTerminalMcpServer();
const server = mcpServer.getServer();
await server.connect(/* transport of your choice */);
```
All core classes and type definitions are available directly from the root
module. Refer to [`src/index.ts`](src/index.ts) for the complete export list.
## MCP Tools
| Tool                    | Purpose                                                                   |
| ----------------------- | ------------------------------------------------------------------------- |
| `create_terminal`       | Create a persistent terminal session (supports `env`, `shell`, and `cwd`) |
| `create_terminal_basic` | Convenience alias for clients that can only send simple strings           |
| `write_terminal`        | Send input to a terminal; newline is added automatically if needed        |
| `read_terminal`         | Retrieve buffered output with smart truncation options                    |
| `wait_for_output`       | Wait for terminal output to stabilize (useful after running commands)     |
| `get_terminal_stats`    | Inspect buffer size, line counts, estimated tokens, and activity          |
| `list_terminals`        | Enumerate active sessions and their metadata                              |
| `kill_terminal`         | Terminate a session with an optional signal                               |
Additional MCP resources and prompts are exposed for listing sessions, viewing
output, and surfacing troubleshooting tips inside compatible clients.
## REST API (Optional)
If you prefer HTTP, start the REST variant:
```bash
npx persistent-terminal-mcp-rest
```
The server listens on port `3001` (configurable) and mirrors the MCP toolset.
Endpoints include `/api/terminals`, `/api/terminals/:id/input`, `/api/terminals/:id/output`,
`/api/terminals/:id/stats`, `/api/terminals`, and `/api/terminals/:id`.
## Project Layout
```
docs/                → Consolidated documentation index
  ├── guides/        → Usage guides and tutorials
  ├── reference/     → Technical references and fixes
  │   └── fixes/     → All fix documentation
  ├── clients/       → Client-specific setup
  └── zh/            → Chinese documentation
scripts/             → Helper scripts for local debugging
src/                 → TypeScript source code
  ├── __tests__/     → Unit tests
  └── examples/      → Example scripts
tests/               → Test suites
  └── integration/   → Integration tests
dist/                → Compiled JavaScript output
```
### Documentation Map
All documentation is organized under [`docs/`](docs/README.md):
**Quick Access:**
- 📖 [Documentation Index](docs/README.md) – Complete documentation map
- 🚨 [Fixes Index](docs/reference/fixes/README.md) – All fixes and solutions
- 🧪 [Integration Tests](tests/integration/README.md) – Test suite
**By Category:**
- **Guides**: Usage, troubleshooting, MCP configuration
- **Reference**: Technical details, tools summary, bug fixes
- **Fixes**: Stdio fix, Cursor fix, terminal fixes
- **Clients**: Claude Desktop / Claude Code setup
- **中文**: Chinese-language documentation
### Important Notes
- **Stdio Purity**: This MCP server follows the MCP protocol strictly by ensuring stdout only contains JSON-RPC messages. All logging goes to stderr. See [docs/reference/fixes/STDIO_FIX.md](docs/reference/fixes/STDIO_FIX.md) for details.
- **Cursor Compatibility**: Fully compatible with Cursor and other strict MCP clients that require clean JSON-RPC communication. See [docs/reference/fixes/QUICK_FIX_GUIDE.md](docs/reference/fixes/QUICK_FIX_GUIDE.md) for quick setup.
- **Terminal Interaction**: Supports interactive applications (vim, npm create, etc.) with proper ANSI escape sequence handling. See [docs/reference/fixes/TERMINAL_FIXES.md](docs/reference/fixes/TERMINAL_FIXES.md) for details.
- **Output Stability**: Use `wait_for_output` tool to ensure complete output capture after running commands.
## Contributing
Contributions are welcome! Please open an issue or pull request if you
encounter bugs or have ideas for new capabilities. The
[`CONTRIBUTING.md`](CONTRIBUTING.md) file outlines the recommended workflow and
coding standards.
## License
This project is released under the [MIT License](LICENSE).