- TypeScript 89.6%
- Python 9.7%
- JavaScript 0.7%
* ci: author release-please PRs with a PAT to drop the CI approval gate (#70) release-please opens its release PR with the default GITHUB_TOKEN, so the PR is authored by github-actions[bot]. GitHub holds pull_request workflow runs from that bot as "action_required" (manual approval) — on every release, not once, since it's the bot-authored-PR behavior, not the one-time first-contributor gate (the release PR is same-repo, not a fork). Pass a token from a write-access identity to release-please-action so the PR is authored by a trusted user; CI then runs automatically and the approval gate is gone, while the release PR still gets tested (matching ci.yml's intent). Uses `secrets.RELEASE_PLEASE_TOKEN || secrets.GITHUB_TOKEN`, so it is a no-op until the secret is added — releases keep working unchanged in the meantime. Requires a one-time manual step: add a RELEASE_PLEASE_TOKEN repo secret (fine-grained PAT with Contents + Pull requests read/write on this repo, or a GitHub App installation token). Co-authored-by: Matt Troutman <mattt@vermontsystems.com> * chore(development): release 0.7.3 (#72) Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com> * fix: follow TestRail pagination and correct query/retry handling (#75) TestRail caps bulk-list responses at 250 items and returns a `{ offset, limit, size, _links, <list> }` envelope. The client only ever read the first page, so any item past #250 was silently invisible: search_test_cases returned count:0 for real cases (e.g. one of 1236 in a suite), list_testrail_projects/get_run_summary under-reported, and run_testrail_command's fields/max_results/truncated never applied because the response was an envelope object, not an array. - testrail.ts: add getPaginated(), which follows `_links.next` and flattens every page into one array; bare arrays and single-entity GETs pass through unchanged. - tools.ts + catalog.ts: route list reads (search_test_cases, list_testrail_projects, get_run_summary failed-tests, and the GET path of run_testrail_command) through getPaginated. Also fixes two adjacent correctness bugs in the HTTP client: - Boolean query params were serialized as "true"/"false"; TestRail's filters (is_completed, etc.) expect 1/0, so the filter was silently ignored. queryValue now maps booleans to "1"/"0". - POST writes were retried on 5xx, which can duplicate an already-applied result/comment/run when a proxy returns 502/503 on the response leg. 5xx is now retried for GET only; POST retries on 429 (rejected, not applied) as before. Adds unit coverage for pagination follow-through, boolean serialization, and the GET-vs-POST retry split. Co-authored-by: Service QA Auto <serviceqaauto@vermontsystems.com> --------- Co-authored-by: Matt Troutman <git@trtmn.com> Co-authored-by: Matt Troutman <mattt@vermontsystems.com> Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com> Co-authored-by: Service QA Auto <serviceqaauto@vermontsystems.com> |
||
|---|---|---|
| .github | ||
| docs/superpowers | ||
| scripts | ||
| src | ||
| test | ||
| .gitignore | ||
| CHANGELOG.md | ||
| CLAUDE.md | ||
| LICENSE | ||
| manifest.json | ||
| package-lock.json | ||
| package.json | ||
| README.md | ||
| tsconfig.json | ||
TestRail MCP Server
Connect Claude to TestRail — browse the API, search test cases, and manage runs and results through natural language. Built on the Model Context Protocol.
tram-mcp runs locally over stdio — your MCP client spawns it as a child
process. It's distributed as the npm package
tram-mcp and as a Claude Desktop
.mcpb bundle.
Migrating from the old Python package?
tram-mcpis now a Node/npm package, not a PyPI package. Use the install steps below;uv tool install tram-mcp/uvx tram-mcpno longer apply.
Requirements
- Claude Code / the
npxpath: Node.js ≥ 18. - Claude Desktop
.mcpb: nothing — Desktop bundles its own Node runtime.
Add to Claude Code
Run these two commands (a coworker — or Claude Code itself — can follow them verbatim):
claude mcp add tram-mcp -- npx -y tram-mcp
npx tram-mcp login
- The first command registers the server (Claude Code spawns
npx -y tram-mcpover stdio). npx tram-mcp loginopens a browser form — enter your TestRail URL, username, and API key (My Settings → API Keys in TestRail). Credentials are validated against TestRail and saved to~/.tram-mcp/credentials.json(readable only by you).
Then start a Claude Code session and run /mcp — you should see tram-mcp with its tools.
Prefer to hand it to Claude Code as a prompt? Paste this:
Add the TestRail MCP server: run
claude mcp add tram-mcp -- npx -y tram-mcp, then runnpx tram-mcp loginso I can enter my TestRail credentials in the browser.
Prefer environment variables (CI, or to skip the browser form)? Set TESTRAIL_URL,
TESTRAIL_USERNAME, and TESTRAIL_API_KEY (or TESTRAIL_PASSWORD) — they take precedence
over the saved file. You can pass them inline when adding the server:
claude mcp add tram-mcp \
-e TESTRAIL_URL=https://yourinstance.testrail.io \
-e TESTRAIL_USERNAME=you@example.com \
-e TESTRAIL_API_KEY=your-api-key \
-- npx -y tram-mcp
Manage saved credentials anytime with npx tram-mcp status and npx tram-mcp logout.
Add to Claude Desktop
- Download
tram-mcp.mcpbfrom the latest release. - Open it (or Settings → Extensions → Install from file) and confirm the install.
- Fill in your TestRail URL, username, and API key in the form. The API key is stored in your OS keychain. Done — no terminal, no config editing.
Other clients (Cursor, VS Code, …)
Any MCP client that runs a stdio command works. Use npx -y tram-mcp as the command and
supply credentials via the TESTRAIL_* env vars, e.g. ~/.cursor/mcp.json:
{
"mcpServers": {
"tram-mcp": {
"command": "npx",
"args": ["-y", "tram-mcp"],
"env": {
"TESTRAIL_URL": "https://yourinstance.testrail.io",
"TESTRAIL_USERNAME": "you@example.com",
"TESTRAIL_API_KEY": "your-api-key"
}
}
}
}
Configuration
Credentials come from npx tram-mcp login (saved to ~/.tram-mcp/), the Desktop install
form, or these environment variables (which take precedence):
| Variable | Required | Description |
|---|---|---|
TESTRAIL_URL |
Yes | Your TestRail instance URL (e.g. https://example.testrail.io) |
TESTRAIL_USERNAME |
Yes | TestRail username or email |
TESTRAIL_API_KEY |
Yes* | TestRail API key (recommended) |
TESTRAIL_PASSWORD |
Yes* | TestRail password (alternative to API key) |
*Either TESTRAIL_API_KEY or TESTRAIL_PASSWORD must be set.
Development
TypeScript; source in src/, tests in test/.
npm install
npm run check # tsc --noEmit
npm test # vitest
npm run build:cli # bundle the CLI -> dist/cli.js
Releasing
Automated by release-please. Merge a PR into development with a
Conventional Commit title; release-please opens a
Release PR that bumps the version. Merging that Release PR tags the release, publishes to
npm, and attaches the tram-mcp.mcpb to the GitHub Release. See CLAUDE.md for details.
License
MIT