.agents/commands/comet/create-jira-ticket.md
Create a new Jira ticket in the OPIK project following the standard template structure.
When the user wants to create a Jira ticket, gather the following information through conversation and then use the mcp__Jira__home___jira_create_issue tool to create the ticket.
mcp__Jira__home___jira_get_sprints_from_board with board ID 524.YYYY-MM-DD.Every Task or Story must have a parent epic. Follow this logic:
mcp__Jira__home___jira_search to find open epics in the OPIK project (JQL: project = OPIK AND issuetype = Epic AND status != Done ORDER BY updated DESC).AskUserQuestion to let the user pick by number.Set the parent via "parent": "OPIK-XXXX" in additional_fields.
After an assignee is chosen, also add that assignee's pod-<name> label alongside any other labels on the ticket.
pod-whale, pod-frontier, pod-andromeda, pod-air, pod-iberi.pod-<name> label automatically — no need to ask.AskUserQuestion to let the user pick the pod from the list above. Include a final "Skip (no pod label)" option.pod-* label.The ticket description contains exactly two sections: WHY and WHAT. Implementation details ("HOW") do NOT go in the description — they go in a separate Jira comment after the ticket is created (see "Post-Creation: HOW Comment" below).
The intent of this split:
The WHAT and the title must agree. The ticket summary is a one-line version of the WHAT. After drafting the description, re-read the title and the first sentence of the WHAT side by side — if they describe different things, fix one of them. The WHAT shouldn't introduce scope the title doesn't promise, and the title shouldn't promise scope the WHAT doesn't cover.
## WHY
[Why this ticket needs to exist. The motivation, the problem being solved, the context the implementer would otherwise miss. 2-6 sentences usually. Long enough to be clear, short enough that a reviewer doesn't skim past it.]
## WHAT
[High-level description of what needs to be implemented. Phrased so QA can derive test cases. Must describe the same thing the ticket title promises — title and WHAT are two views of the same scope. Avoid implementation specifics here — those belong in the HOW comment.]
### Functional Requirements (optional)
[Include when the WHAT has more than a couple of distinct behaviors worth enumerating, or when the acceptance criteria alone won't carry the full picture for a reader. Skip for simple tickets where the WHAT prose already says everything.]
- [What the system should DO]
- [Another behavior]
### Non-Functional Requirements (optional)
[Include when the ticket has performance, security, scalability, accessibility, or compatibility constraints that don't naturally fit in acceptance criteria. Skip when there are none worth calling out.]
- [Performance / security / scalability / accessibility / compatibility constraint]
### Acceptance Criteria
- [ ] [Criterion 1 — observable behavior or outcome]
- [ ] [Criterion 2]
- [ ] [Criterion 3]
- [ ] No lint errors or TypeScript errors (if applicable)
- [ ] Unit tests added (if applicable)
- [ ] Documentation updated (if applicable)
### Out of Scope (optional)
- [Things the reader might assume are in scope but aren't]
pod-<name> label. If uncertain, ask the user to pick from the known pods (see Assignee Pod Label).Once all information is gathered, use the Jira MCP tool:
mcp__Jira__home___jira_create_issue(
project_key="OPIK",
summary="[PREFIX] Title of the ticket",
issue_type="Story|Task|Bug|Epic",
description="[Formatted description using template above]",
additional_fields={
"priority": {"name": "Medium"},
"labels": ["label1", "label2"],
"customfield_10028": <fibonacci_number>,
"customfield_10020": <sprint_id>,
"duedate": "YYYY-MM-DD",
"parent": "OPIK-670" // only for tech debt tickets without another epic
}
)
customfield_10028 directly (the story_points alias does NOT work at creation time)customfield_10020 with the sprint ID (a plain number). Look up sprints via mcp__Jira__home___jira_get_sprints_from_board (board ID 524), filter by "Opik Sprint" prefix, and pick the active or next future sprint based on user choice.duedate with format YYYY-MM-DD. Calculate relative to today's date."parent": "OPIK-XXX" (plain string, not an object) when creating under an epic.After creating the ticket:
mcp__Jira__home___jira_get_issue to check the ticket's status. A Jira automation will move it to BACKLOG status automatically.AskUserQuestion tool (not inline text) to prompt: "The ticket is now in Backlog. Would you like me to move it to TO DO?"mcp__Jira__home___jira_transition_issue to move it to "TO DO".After the status transition, decide whether to post a HOW comment. The HOW lives in a Jira comment, not in the description.
Post a HOW only when there is substance worth surfacing that the implementer wouldn't already get from the WHAT and from reading the code. If there isn't — skip it. A missing HOW comment is better than a filler one, and /comet:work-on-jira-ticket handles the no-HOW case gracefully.
A HOW is worth posting when the creator has one or more of:
A HOW should NOT contain:
Length follows substance. Two sentences of real insight beats fifteen lines of generic scaffolding. Be specific when you are confident; be brief when you aren't.
Use mcp__Jira__home___jira_add_comment with the ticket key and a body that starts with # HOW on the first line. Plain Markdown is fine — #, ##, backticks for inline code, - for bullets. Jira renders these as real headers / inline code / bullets.
Example shape (for a hypothetical [BE] Add an endpoint to bulk-delete experiments ticket):
# HOW
Pieces likely still relevant:
- Traces and spans already have batch-delete endpoints — mirror that shape.
- Shared `BatchDelete` record in `com.comet.opik.api` is reused by other batch endpoints.
- Workspace scoping is enforced at the DAO layer across this area — keep that invariant.
- Cascading deletes touch `experiment_items`; existing DAO code already handles that relationship.
Open questions for the implementer:
- Feedback scores: traces null them out on delete; do experiments need the same treatment?
- Partial-failure semantics: 404 if any id is missing, or best-effort delete of valid ones?
If /comet:create-jira-ticket is run again against an existing ticket (e.g., to update the HOW), prefer editing the previous HOW comment over piling up new ones:
mcp__Jira__home___jira_get_issue with comment_limit greater than zero.^#\s*HOW\b (case-insensitive) and whose author.email matches the authenticated user's email.mcp__Jira__home___jira_edit_comment with the new HOW body.mcp__Jira__home___jira_add_comment a new one.The author check matters: jira_edit_comment does not enforce ownership at the MCP layer (Jira permissions decide), so without it a user with "Edit All Comments" could clobber a teammate's HOW.
Use these prefixes in the summary based on the work area:
[FE] - Frontend changes[BE] - Backend changes[SDK] - SDK changes (Python or TypeScript)[DOCS] - Documentation updates[INFRA] - Infrastructure/DevOps changesAfter successfully creating a ticket, always display the ticket key as a clickable markdown link in the confirmation message:
[OPIK-{number}](https://comet-ml.atlassian.net/browse/OPIK-{number})
For example, if the created ticket key is OPIK-5316, display:
[OPIK-5316](https://comet-ml.atlassian.net/browse/OPIK-5316)
Never display the ticket key as plain text — always wrap it in a markdown link to the Jira ticket URL.
OPIK## for headers, - for bullets, backticks for inline code). Jira renders Markdown as real headers / formatting.- [ ] syntax