How to perform the tracker skill's issue operations on Jira (Cloud or Data Center) — create, update, comment, transition, search, attach — through the Atlassian MCP server if connected, otherwise the Jira REST API. Jira is a tracker only; pair it with a code host (GitHub, GitLab, Azure DevOps, Bitbucket). Load it when QA_TRACKER is jira.
Installs into .claude/skills of the current project.
Are you the author of Provider Jira?
Add the live security badge to your README. It updates with every re-scan.
[](https://www.skillsdirectory.com/skills/ghassenazzouz-provider-jira)
---
name: provider-jira
description: How to perform the tracker skill's issue operations on Jira (Cloud or Data Center) — create, update, comment, transition, search, attach — through the Atlassian MCP server if connected, otherwise the Jira REST API. Jira is a tracker only; pair it with a code host (GitHub, GitLab, Azure DevOps, Bitbucket). Load it when QA_TRACKER is jira.
---
# provider-jira
Jira is an **issue tracker only**. MRs/PRs and CI come from `QA_CODE_HOST`.
**Settings** (`.env`): `JIRA_BASE_URL` (e.g. `https://acme.atlassian.net`), `JIRA_PROJECT_KEY` (e.g. `SHOP`). For the REST path, also `JIRA_EMAIL` + `JIRA_API_TOKEN` (Cloud) or `JIRA_PAT` (Data Center). These are secrets, so load them only inside the command (`set -a; . ./.env; set +a`).
## Path A: Atlassian MCP server (preferred if connected)
If an Atlassian / Jira MCP server is connected (check `/mcp`), use its issue tools: create, edit, comment, transition, search with JQL, get issue. It accepts Markdown descriptions. The tool names depend on the server, so pick by purpose and say which you used.
## Path B: REST API with curl
Cloud uses Basic auth (`-u "$JIRA_EMAIL:$JIRA_API_TOKEN"`). Data Center uses `-H "Authorization: Bearer $JIRA_PAT"`. Use **REST v2**, which takes plain-text/wiki descriptions (v3 requires the Atlassian Document Format JSON). Endpoints below were checked against Atlassian's published Jira Cloud OpenAPI spec.
| Operation | Request |
|---|---|
| `issue.create` | `POST /rest/api/2/issue` with `{"fields":{"project":{"key":"$JIRA_PROJECT_KEY"},"issuetype":{"name":"Bug"},"summary":"<t>","description":"<wiki>","labels":["bug","sev-2","e2e"],"priority":{"name":"High"}}}`. Use issue type `Bug`, `Story` or `Task` as fits. The response holds `key` |
| `issue.get` | `GET /rest/api/2/issue/<KEY>?fields=summary,description,labels,status,fixVersions,issuelinks` |
| `issue.update` | `PUT /rest/api/2/issue/<KEY>` with `{"fields":{"description":"<wiki>"}}`. For labels: `{"update":{"labels":[{"add":"verified"},{"remove":"fix-failed"}]}}` |
| `issue.comment` | `POST /rest/api/2/issue/<KEY>/comment` with `{"body":"<wiki>"}` |
| `issue.close` / `reopen` | `GET /rest/api/2/issue/<KEY>/transitions` and pick the transition whose target is Done/Closed (or To Do/Reopened). Then `POST …/transitions` with `{"transition":{"id":"<id>"}}`, then comment why. Workflows differ per project, so never guess an ID |
| `issue.list` | **Cloud:** `GET /rest/api/2/search/jql?jql=<urlencoded>&fields=summary,labels,status,description&maxResults=100`, paging with the returned `nextPageToken` until `isLast` is true. **Data Center:** `GET /rest/api/2/search?jql=…&fields=…&maxResults=100&startAt=<n>`. The old Cloud `/search` endpoint is being removed (Atlassian CHANGE-2046), so don't use it on Cloud. Example JQL: `project = SHOP AND labels = bug AND statusCategory != Done AND fixVersion = "v2.3"` |
| `issue.link` | `POST /rest/api/2/issueLink` with `{"type":{"name":"Relates"},"inwardIssue":{"key":"A"},"outwardIssue":{"key":"B"}}` |
| `file.attach` | `POST /rest/api/2/issue/<KEY>/attachments` with `-H "X-Atlassian-Token: no-check" -F "file=@<path>"`, then reference it in the body as `!<filename>!` (image) or `[^<filename>]` |
| `project.check` | `GET /rest/api/2/project/$JIRA_PROJECT_KEY` |
## Markdown → Jira wiki markup (REST path)
Convert bodies before sending:
| Markdown | Wiki markup |
|---|---|
| `## Heading` | `h2. Heading` |
| `**bold**` | `*bold*` |
| `` `code` `` | `{{code}}` |
| ```` ```lang … ``` ```` | `{code:lang} … {code}` |
| `- item` / `1. item` | `* item` / `# item` |
| `[text](url)` | `[text\|url]` |
| `\| a \| b \|` header row | `\|\| a \|\| b \|\|` |
| `<details>` block | `{expand:title} … {expand}` (Cloud), or plain on Data Center |
| `---` | `----` |
The watermark footer becomes `----` followed by `🤖 _Generated by DevOps QA Agent — review before acting on this._`. Keep it.
## Mapping
- **Severity / priority:** keep the `sev-*` and `p*` labels, and also set `priority`: p1 → `Highest`, p2 → `High`, p3 → `Medium` (names differ per instance, so check them once: Cloud `GET /rest/api/2/priority/search`, Data Center `GET /rest/api/2/priority`)
- **Milestone:** `fixVersion` (`fixVersion = "v2.3"`), or a sprint if the team uses sprints instead. Ask once
- **Labels:** Jira creates them on first use. No spaces allowed, and the `tracker` labels have none
- **Refs:** report `SHOP-143`, never a numeric ID