osTicket MCP Server
README.md
# osTicket MCP Server
<div align="center">
**Manage your [osTicket](https://osticket.com) helpdesk with AI — from Claude Code, Cursor, Windsurf, or any MCP client.**
[](LICENSE)
[](https://modelcontextprotocol.io)
[](https://osticket.com)
[](https://www.npmjs.com/package/mcp-osticket)
</div>
---
Talk to your helpdesk in natural language. Reply to tickets, add internal notes, assign agents, transfer departments, close tickets — all without leaving your editor.
```
> show me the open tickets
> reply to ticket 32 saying we're investigating the issue
> assign it to Sarah
> close all the automated notification tickets
```
## Why?
osTicket doesn't have a public API. This MCP server reverse-engineers the staff panel to give AI tools full access to your helpdesk — using the same session-based auth as the web UI. No API keys, no plugins, no osTicket modifications needed.
## Quick Start
### 1. Install
```bash
npm install -g mcp-osticket
```
Or clone and build from source:
```bash
git clone https://github.com/tecnologicachile/mcp-osticket.git
cd mcp-osticket
npm install && npm run build
```
### 2. Configure
Add to your MCP client config:
<details>
<summary><strong>Claude Desktop</strong> — <code>claude_desktop_config.json</code></summary>
**macOS**: `~/Library/Application Support/Claude/claude_desktop_config.json`
**Windows**: `%APPDATA%\Claude\claude_desktop_config.json`
```json
{
"mcpServers": {
"osticket": {
"command": "npx",
"args": ["-y", "mcp-osticket"],
"env": {
"OSTICKET_URL": "https://helpdesk.example.com",
"OSTICKET_EMAIL": "agent@example.com",
"OSTICKET_PASSWORD": "your-password"
}
}
}
}
```
</details>
<details>
<summary><strong>Claude Code</strong> — <code>~/.claude/settings.json</code></summary>
```json
{
"mcpServers": {
"osticket": {
"command": "mcp-osticket",
"env": {
"OSTICKET_URL": "https://helpdesk.example.com",
"OSTICKET_EMAIL": "agent@example.com",
"OSTICKET_PASSWORD": "your-password"
}
}
}
}
```
If installed from source, use `"command": "node"` with `"args": ["/path/to/mcp-osticket/dist/mcp-server.js"]`.
</details>
<details>
<summary><strong>Cursor</strong> — <code>.cursor/mcp.json</code></summary>
```json
{
"mcpServers": {
"osticket": {
"command": "mcp-osticket",
"env": {
"OSTICKET_URL": "https://helpdesk.example.com",
"OSTICKET_EMAIL": "agent@example.com",
"OSTICKET_PASSWORD": "your-password"
}
}
}
}
```
</details>
<details>
<summary><strong>Windsurf</strong> — <code>~/.codeium/windsurf/mcp_config.json</code></summary>
```json
{
"mcpServers": {
"osticket": {
"command": "mcp-osticket",
"env": {
"OSTICKET_URL": "https://helpdesk.example.com",
"OSTICKET_EMAIL": "agent@example.com",
"OSTICKET_PASSWORD": "your-password"
}
}
}
}
```
</details>
### 3. Use
Restart your editor. The tools are available immediately — just ask in natural language.
## Tools
| Tool | Description |
|------|-------------|
| `list_tickets` | List tickets by queue — `open`, `my`, or `closed` |
| `get_ticket` | Full ticket detail with conversation thread |
| `reply_ticket` | Reply to a ticket with email control (`all`, `user`, or `none`) |
| `add_note` | Add an internal note (not visible to the end user) |
| `change_ticket_status` | Change status to `open`, `resolved`, or `closed` |
| `assign_ticket` | Assign a ticket to a staff member |
| `transfer_ticket` | Transfer a ticket to another department |
| `list_agents` | List available staff for assignment |
| `list_departments` | List available departments for transfer |
| `search_users` | Search users by name or email |
| `get_queue_counts` | Get ticket counts per queue |
### Reply Control
When replying, you control who gets the email:
| `reply_to` | Behavior |
|------------|----------|
| `all` | Email all active recipients (default) |
| `user` | Email only the ticket owner |
| `none` | No email — just post the reply in the thread |
## Examples
**Triage your inbox:**
```
> list open tickets and summarize them by priority
```
**Bulk operations:**
```
> close all the automated notification tickets (ZohoMail, BaseAPI, etc.)
```
**Reply without email:**
```
> reply to ticket 15 with "Fixed in latest deploy" but don't send an email
```
**Assign and transfer:**
```
> assign ticket 8 to Sarah and transfer it to the Sales department
```
**Search users:**
```
> find all users with @example.com emails
```
## Environment Variables
| Variable | Required | Description |
|----------|----------|-------------|
| `OSTICKET_URL` | Yes | Base URL of your osTicket instance (e.g. `https://helpdesk.example.com`) |
| `OSTICKET_EMAIL` | Yes | Staff agent email for login |
| `OSTICKET_PASSWORD` | Yes | Staff agent password |
## How It Works
This server authenticates as a staff agent through osTicket's web panel and operates using the same internal endpoints the browser uses:
- **Session auth** — logs in via `/scp/login.php`, maintains session cookie
- **CSRF handling** — automatically extracts and refreshes CSRF tokens
- **Ticket locking** — acquires and releases locks for write operations (reply, note)
- **AJAX endpoints** — uses `/scp/ajax.php/*` for assign, transfer, and status changes
- **HTML scraping** — parses ticket data from the staff panel using Cheerio
No osTicket plugins, API keys, or server modifications required.
## Compatibility
| osTicket Version | Status |
|------------------|--------|
| v1.18.x | Tested |
| v1.17.x | Should work (not verified) |
| v1.15–1.16 | May work with minor differences |
The server adapts to dynamic form field names that osTicket generates per-session, so it should be resilient across minor versions.
## Integration Tests
Run the test suite against a live osTicket instance:
```bash
OSTICKET_URL=http://localhost:8082 \
OSTICKET_EMAIL=agent@example.com \
OSTICKET_PASSWORD=secret \
npx tsx src/test-integration.ts
```
## Contributing
PRs welcome. The main files:
- `src/mcp-server.ts` — MCP tool definitions
- `src/osticket-client.ts` — osTicket HTTP client (session, scraping, AJAX)
- `src/test-integration.ts` — integration tests against a live instance
## License
MIT
This server cannot be deployed