Files
pi_mcps/zoo_backup/work/rules/skills/skill-sprint-report.md
T
2026-06-24 19:27:14 +02:00

6.1 KiB

Skill: sprint-report

Generate sprint status report from Jira data.

Invoked by

🎫 JiraOps mode (or 🪃 Orchestrator delegating to JiraOps)

Required Inputs

Input Source Example
PROJECT_KEY Jira project key ESIDEPAISY
SPRINT_ID Sprint ID (optional — auto-detected if omitted) 1234
OUTPUT_FORMAT Report format (optional) markdown, confluence, teams

Output

  • Markdown report: docs/sprint-reports/sprint-<sprint_name>-<date>.md
  • Optionally: Confluence page or Teams message

Steps

1. Get active sprint

If SPRINT_ID is not provided, auto-detect:

# Get the board
boards = get_agile_boards(project_key="ESIDEPAISY")
board_id = boards[0]["id"]

# Get active sprint
sprints = get_sprints_from_board(board_id=board_id, states="active")
sprint = sprints[0]
sprint_id = sprint["id"]
sprint_name = sprint["name"]

2. Get sprint tickets

tickets = get_tickets_from_sprint(
    sprint_id=sprint_id,
    fields="project,summary,status,issuetype,assignee,customfield_10001,customfield_10106"
)

Key fields:

  • status — current ticket status
  • assignee — who's working on it
  • issuetype — Story, Bug, Task
  • customfield_10106 — Story Points (if configured)
  • customfield_10001 — Feature Link (Epic)

3. Categorize tickets by status

Group tickets into workflow buckets:

Category Statuses
To Do Open, Backlog, To Do
In Progress In Progress, In Development
In Review In Review, Code Review
Done Done, Accepted, Closed
Blocked Any ticket with Blocked flag or label

4. Calculate metrics

total = len(tickets)
done = len([t for t in tickets if t["status"] in DONE_STATUSES])
in_progress = len([t for t in tickets if t["status"] in PROGRESS_STATUSES])
todo = len([t for t in tickets if t["status"] in TODO_STATUSES])
completion_pct = round(done / total * 100) if total > 0 else 0

5. Group by assignee

by_assignee = {}
for ticket in tickets:
    assignee = ticket.get("assignee", "Unassigned")
    by_assignee.setdefault(assignee, []).append(ticket)

6. Group by Epic/Feature

by_epic = {}
for ticket in tickets:
    epic = ticket.get("customfield_10001", "Kein Epic")
    by_epic.setdefault(epic, []).append(ticket)

7. Generate report

Write docs/sprint-reports/sprint-<sprint_name>-<date>.md:

# Sprint Report: <sprint_name>

**Datum:** <today>
**Sprint:** <sprint_name>
**Zeitraum:** <start_date> — <end_date>
**Projekt:** ESIDEPAISY

---

## Übersicht

| Metrik | Wert |
|--------|------|
| Tickets gesamt | <total> |
| Erledigt | <done> (<completion_pct>%) |
| In Bearbeitung | <in_progress> |
| Offen | <todo> |
| In Review | <in_review> |

## Fortschritt

[████████████░░░░░░░░] 60% (/)


## Nach Status

### ✅ Erledigt (<done>)

| Ticket | Typ | Zusammenfassung | Bearbeiter |
|--------|-----|----------------|------------|
| <key> | Story | <summary> | <assignee> |

### 🔄 In Bearbeitung (<in_progress>)

| Ticket | Typ | Zusammenfassung | Bearbeiter |
|--------|-----|----------------|------------|
| <key> | Bug | <summary> | <assignee> |

### ⏳ Offen (<todo>)

| Ticket | Typ | Zusammenfassung | Bearbeiter |
|--------|-----|----------------|------------|
| <key> | Task | <summary> | <assignee> |

## Nach Bearbeiter

| Bearbeiter | Gesamt | Erledigt | In Bearbeitung | Offen |
|-----------|--------|----------|---------------|-------|
| <name> | <n> | <done> | <wip> | <todo> |

## Nach Feature/Epic

| Epic | Tickets | Erledigt | Fortschritt |
|------|---------|----------|-------------|
| <epic_name> | <n> | <done> | <pct>% |

## Blocker / Risiken

| Ticket | Beschreibung | Seit | Auswirkung |
|--------|-------------|------|-----------|
| <key> | <blocker description> | <date> | <impact> |

<If no blockers: "Keine Blocker im aktuellen Sprint.">

8. Publish to Confluence (optional)

If OUTPUT_FORMAT includes confluence:

create_page(
    space_key="ESIDEPAISY",
    title=f"Sprint Report: {sprint_name}{date}",
    content=<html_converted_content>,
    parent_id="<sprint-reports-parent-page-id>"
)

9. Send Teams summary (optional)

If OUTPUT_FORMAT includes teams:

teams_send_channel_message(
    team_id="<team_id>",
    channel_id="<channel_id>",
    content=f"📊 *Sprint Report: {sprint_name}*\n\n"
            f"Fortschritt: {done}/{total} ({completion_pct}%)\n"
            f"In Bearbeitung: {in_progress}\n"
            f"Offen: {todo}\n"
            f"Blocker: {blocked}\n\n"
            f"Vollständiger Bericht: <confluence_link or file path>"
)

10. Store in BigMind

memory_store_fact(
    category="codebase",
    fact=f"Sprint report for {sprint_name}: {done}/{total} done ({completion_pct}%), {in_progress} in progress, {blocked} blocked."
)

Expected Output

  • Markdown sprint report with ticket breakdown
  • Metrics: completion %, by-status, by-assignee, by-epic
  • Blocker/risk section
  • Optionally published to Confluence and/or Teams

Error Handling

Error Resolution
No active sprint found Check states="active" — may need states="active,future"
No tickets in sprint Sprint may be empty or newly created — report "0 tickets"
Board not found Verify project key, try get_agile_boards with different key
Story points not configured Skip story point metrics, use ticket count only
Confluence publish fails Save markdown locally, report Confluence error

Report Variants

Variant When Content
Daily standup Mid-sprint Focus on in-progress + blockers only
Sprint review End of sprint Full report with all sections
Management summary On request Metrics + epic progress only, no ticket details

Adjust the template based on the variant requested.

Language

  • Report content: German
  • Ticket keys, branch names: English as-is
  • Teams messages: German
  • Confluence page: German