Skip to main content
Glama
README.md
# PR-Description MCP Skill

An MCP server that generates structured PR descriptions from Jira tickets and git diffs.

## Prerequisites

- **Node.js** ≥ 18 — [nodejs.org](https://nodejs.org)
- **Git**
- **GitHub CLI (`gh`)** — [cli.github.com](https://cli.github.com) (required for `publish_pr`)
- **AI Tool** — at least one of: Augment, Cursor, Claude Desktop, VS Code (Copilot), or Windsurf

## Quick Install

```bash
curl -fsSL https://raw.githubusercontent.com/edmoura/pr-description-skill/main/scripts/install.sh | bash
```

This will clone the repo, install dependencies, build, run the setup wizard,
and **auto-register the MCP server with every detected AI tool** — all
idempotently.

### Supported AI tools (auto-detected)

| Tool | Config location | Merge behavior |
|------|----------------|----------------|
| **Augment** | `~/.augment/mcp/pr-description.json` + `~/.augment/skills/` | Standalone file (overwritten) |
| **Cursor** | `~/.cursor/mcp.json` | Merged into `mcpServers` |
| **Claude Desktop** | `~/Library/Application Support/Claude/claude_desktop_config.json` | Merged into `mcpServers` |
| **VS Code** | `~/Library/Application Support/Code/User/mcp.json` | Merged into `servers` |
| **Windsurf** | `~/.codeium/windsurf/mcp_config.json` | Merged into `mcpServers` |

The installer checks whether each tool is installed (config dir exists or
command is on PATH). Detected tools get the config entry; others are skipped.
Existing servers in the same config file are **preserved** — only the
`pr-description` entry is added or updated.

## Manual Install

```bash
git clone https://github.com/edmoura/pr-description-skill.git ~/.pr-description-skill
cd ~/.pr-description-skill
npm install          # installs deps + builds (via postinstall)
npm run setup        # interactive credential wizard
```

Then run the installer to register MCP with all detected tools:

```bash
bash scripts/install.sh
```

Or register manually with Augment by creating `~/.augment/mcp/pr-description.json`:

```json
{
  "name": "pr-description",
  "command": "node",
  "args": ["<path-to-repo>/dist/src/index.js"],
  "env": {}
}
```

And copy the skill prompt:

```bash
mkdir -p ~/.augment/skills/pr-description
cp .augment/skills/pr-description/SKILL.md ~/.augment/skills/pr-description/SKILL.md
```

## Configuration

All configuration is stored in a **global** `~/.pr-description-skill/.env` (owner-read-only), so credentials configured once apply in **every** project you open. Run `npm run setup` from anywhere to reconfigure at any time. A project-local `./.env` (if present) is layered on top and can override the global values for that repo.

| Variable | Required | Description |
|----------|----------|-------------|
| `JIRA_BASE_URL` | Yes | Jira instance URL (e.g. `https://yourcompany.atlassian.net`) |
| `JIRA_EMAIL` | Yes | Your Atlassian login email |
| `JIRA_API_TOKEN` | Yes | API token from [Atlassian](https://id.atlassian.com/manage-profile/security/api-tokens) |
| `JIRA_AC_FIELD_ID` | No | Custom field ID for Acceptance Criteria (default: `customfield_10222`) |
| `JIRA_INTEGRATION_DISABLED` | No | Set to `true` to skip Jira (paste ACs manually) |

See [`.env.example`](.env.example) for a documented template.

## Usage

In your IDE or Auggie CLI, type `/pr-description` on any feature branch. The skill will:

1. **Security scan** — check the diff for accidentally committed secrets
2. **Ask for Jira ticket** — fetch title, description, and acceptance criteria
3. **Ask clarifying questions** — breaking changes, dates, feature flags, etc.
4. **Generate the PR description** — structured Markdown following the team template
5. **Publish** — create or update the PR via `gh` (with your approval)

## Updating / Self-Update

Re-run the installer — it detects the existing clone and does a `git pull` + rebuild:

```bash
bash ~/.pr-description-skill/scripts/install.sh
```

Or with the explicit `--update` flag:

```bash
bash ~/.pr-description-skill/scripts/install.sh --update
```

## Troubleshooting

### General

| Issue | Fix |
|-------|-----|
| `fetch_jira_ticket` returns 401 | Verify `JIRA_EMAIL` and `JIRA_API_TOKEN` in `~/.pr-description-skill/.env`, or re-run `npm run setup` |
| Acceptance Criteria always empty | Your Jira instance may use a different custom field. Find the ID (see below) and set `JIRA_AC_FIELD_ID` via `npm run setup` |
| `publish_pr` fails | Ensure `gh` is installed and authenticated (`gh auth login`) |
| MCP server not found | Check `~/.augment/mcp/pr-description.json` points to the correct `dist/src/index.js` path |
| `postinstall` loop | Run `npm install --ignore-scripts` then `npm run build` separately |
| Permission denied writing `.env` | Run `chmod u+w ~/.pr-description-skill/.env` and retry |

### MCP Host-Specific Issues

| Host | Symptom | Fix |
|------|---------|-----|
| **Augment** | "Tool not found" after install | Restart Augment or reload the window. Verify `~/.augment/mcp/pr-description.json` exists. |
| **Cursor** | Server fails to connect | Check `~/.cursor/mcp.json` has a valid `mcpServers.pr-description` entry. Restart Cursor. |
| **VS Code** | Tools not appearing | VS Code uses `servers` (not `mcpServers`). Check `~/Library/Application Support/Code/User/mcp.json`. Reload window (`Cmd+Shift+P` → "Reload Window"). |
| **Claude Desktop** | Server not listed | Fully quit and relaunch Claude Desktop. Check `~/Library/Application Support/Claude/claude_desktop_config.json`. |
| **Windsurf** | Connection timeout | Verify `~/.codeium/windsurf/mcp_config.json` has the correct `node` path. Restart Windsurf. |
| **All hosts** | Server crashes on startup | Check the debug log: `cat ~/.pr-description-skill/debug.log`. Ensure Node.js ≥ 18 is on PATH. |
| **All hosts** | "ENOENT" or "spawn node" errors | The `node` binary might not be on the host's PATH. Use the full path in the config: replace `"command": "node"` with `"command": "/usr/local/bin/node"` (or wherever `which node` points). |

### Debug Log

All tool invocations are logged to `~/.pr-description-skill/debug.log`. Share this file with the support team when reporting issues. The log auto-rotates at 5 MB.

### Finding your Acceptance Criteria field ID

Acceptance Criteria is a Jira custom field, and its ID varies per instance.
To find yours, open a ticket that has AC filled in and query the API:

```bash
curl -s -u "you@example.com:$JIRA_API_TOKEN" \
  "$JIRA_BASE_URL/rest/api/3/issue/PROJ-123?expand=names" \
  | node -e 'const d=JSON.parse(require("fs").readFileSync(0));for(const[k,v]of Object.entries(d.names)){if(/accept|criteria|expected result/i.test(v))console.log(k,"=>",v)}'
```

Set the resulting `customfield_XXXXX` via `npm run setup`. If none is
configured, the tool tries a fallback chain (Acceptance Criteria → Expected
Results → Definition of Done); see [`src/config.ts`](src/config.ts).

### Notes on formatting

- Jira descriptions and AC are stored in **ADF** (Atlassian Document Format)
  and converted to plain text/Markdown. Rich elements (tables, links, inline
  emphasis) may be simplified or dropped.
- `get_sanitized_diff` performs **best-effort secret redaction** (AWS/GitHub/
  Slack/Stripe tokens, private keys, `password=`/`token=` assignments) before
  returning the diff. This is defense-in-depth — always review diffs manually
  before publishing.