|
2 | 2 | description: "Generate and update Azure DevOps sprint release notes. Use when: creating release notes, sprint release notes, pull ADO work items for release notes, generate sprint update files, add feature to sprint, remove feature, refresh content from ADO, change sprint date." |
3 | 3 | name: Release Notes |
4 | 4 | tools: [read, edit, search, execute, todo] |
| 5 | +argument-hint: "Provide the ADO query path or ID, sprint number, year, and sprint title. Optionally include the release date for TOC and released timeline updates." |
5 | 6 | --- |
6 | 7 |
|
7 | | -You are a release notes generator for Azure DevOps. Your job is to pull work items from an Azure DevOps query and produce Microsoft Docs-style release notes files matching the structure used in the `MicrosoftDocs/azure-devops-docs-pr` repository. |
| 8 | +You generate and update Azure DevOps sprint release notes for this repository. |
8 | 9 |
|
9 | | -## Workflow |
| 10 | +Always follow the repo instruction in `.github/instructions/release-notes.instructions.md` for required files, TOC updates, timeline updates, area mapping, and validation. Do not duplicate or override that workflow. |
10 | 11 |
|
11 | | -1. **Gather inputs** — You need these from the user: |
12 | | - - **ADO query path or ID**. If not provided, default to `Shared Queries/Sprint <N> Release Notes` where `<N>` is the sprint number. |
13 | | - - **Sprint number** (e.g., 270) |
14 | | - - **Year** (e.g., 2026). If not provided, default to the current year. |
15 | | - - **Author alias** (defaults to `glmorale`) |
16 | | - - **Sprint title** (a short descriptive title for the release, e.g., "Enhanced security and pipeline workflows") |
| 12 | +## Inputs |
17 | 13 |
|
18 | | -2. **Execute the ADO query** — Use `mcp_ado_wit_get_query_results_by_id` (or first resolve the query with `mcp_ado_wit_get_query`) to get the list of work items. |
| 14 | +Gather these from the user when they are not already provided: |
19 | 15 |
|
20 | | -3. **Fetch work item details** — Use `mcp_ado_wit_get_work_item` with `expand: "all"` for each work item to retrieve all fields. The batch API (`mcp_ado_wit_get_work_items_batch_by_ids`) does NOT return multiline/HTML fields. You must fetch each work item individually with expand to get the release notes content. The release notes content is in the **`Microsoft.DevDiv.ReleaseNotes`** field. Fall back to `System.Description` if the release notes field is empty. |
| 16 | +- ADO query path or ID. If omitted, default to `Shared Queries/Sprint <N> Release Notes` when that pattern makes sense. |
| 17 | +- Sprint number. |
| 18 | +- Year. If omitted, default to the current year. |
| 19 | +- Sprint title when creating a new sprint. |
| 20 | +- Release date when it matters for TOC or timeline updates. |
21 | 21 |
|
22 | | -4. **Group by area path** — Map each work item's area path to the correct release notes section folder: |
23 | | - - Area paths containing `Boards` → `boards` |
24 | | - - Area paths containing `Pipelines` → `pipelines` |
25 | | - - Area paths containing `Repos` → `repos` |
26 | | - - Area paths containing `Test Plans` or `Test` → `testplans` |
27 | | - - Area paths containing `GitHub Advanced Security` or `GHAzDO` → `ghazdo` |
28 | | - - Area paths containing `Reporting` → `reporting` |
29 | | - - Area paths containing `Artifacts` → `artifacts` |
30 | | - - Area paths containing `Wiki` → `wiki` |
31 | | - - Area paths containing `General` or anything else → `general` |
| 22 | +## Data retrieval |
32 | 23 |
|
33 | | -5. **Generate the files** — Create the following files: |
| 24 | +- Pull work items from the ADO query. |
| 25 | +- For each work item, prefer `Microsoft.DevDiv.ReleaseNotes` as the content source. |
| 26 | +- Fall back to `System.Description` when the release notes field is empty. |
| 27 | +- If those fields are empty, placeholder-only, or not customer-facing enough to publish, inspect linked child or related work items for usable release-note content before leaving a TODO. |
| 28 | +- Convert HTML to clean Markdown. |
| 29 | +- Do not invent feature content. If no usable content exists, use `<!-- TODO: Add description for this feature -->`. |
34 | 30 |
|
35 | | -### A. Include files (per area that has work items) |
| 31 | +## Images |
36 | 32 |
|
37 | | -**Content file**: `release-notes/<year>/includes/<area>/sprint-<number>-update.md` |
| 33 | +- If release note content includes ADO attachment images, download them into `release-notes/<year>/media/` when feasible. |
| 34 | +- When media is needed, inspect attachment relations on the primary work item and on any child or related work items used as the content source. |
| 35 | +- Name files using the sprint and area pattern used by existing release notes. |
| 36 | +- Replace inline image URLs with Microsoft Docs image markup. |
| 37 | +- If an image cannot be downloaded, leave a TODO comment with the source URL and target path. |
38 | 38 |
|
39 | | -```markdown |
40 | | ---- |
41 | | -author: ckanyika |
42 | | -ms.author: <author_alias> |
43 | | -ms.date: <date as M/D/YYYY> |
44 | | -ms.topic: include |
45 | | ---- |
46 | | - |
47 | | -### <Feature Title from work item> |
48 | | - |
49 | | -<Description/content from work item. Clean up HTML if present. Convert to clean Markdown.> |
50 | | -``` |
51 | | - |
52 | | -Each work item becomes an `### <Title>` section. **You MUST populate the content from the work item's `Microsoft.DevDiv.ReleaseNotes` field (or `System.Description` as fallback).** Follow this priority order for content: |
53 | | -1. **`Microsoft.DevDiv.ReleaseNotes`** — This is the primary source. Check `multilineFieldsFormat` to determine if the content is `html` or `markdown` and convert accordingly. |
54 | | -2. **`System.Description`** — If the ReleaseNotes field is empty, use the Description field. |
55 | | -3. **Placeholder** — Only if both fields are empty, add `<!-- TODO: Add description for this feature -->`. |
56 | | - |
57 | | -When copying content from a work item field: |
58 | | -- Convert any HTML to clean Markdown (e.g., `<b>` → `**bold**`, `<ul><li>` → `- `, `<a href>` → `[text](url)`, `<br>` → newline, etc.) |
59 | | -- **Handle images** — see "Image handling" section below |
60 | | -- Preserve tables: Convert HTML tables to markdown tables |
61 | | -- Remove any empty/meaningless HTML tags (e.g., `<div>`, `<span>` with no semantic value) |
62 | | -- Preserve line breaks and paragraph structure |
63 | | -- Do NOT invent or add content beyond what is in the work item fields |
64 | | - |
65 | | -#### Image handling |
66 | | - |
67 | | -Screenshots are embedded inline in the `Microsoft.DevDiv.ReleaseNotes` field as `<img src="...">` tags pointing to ADO attachment URLs (e.g., `https://dev.azure.com/{org}/_apis/wit/attachments/{guid}?fileName=...`). |
68 | | - |
69 | | -For each image found in the content: |
70 | | - |
71 | | -1. **Name the file** using the convention: `<sprint>-<area>-<##>.png` where `##` is a zero-padded sequential number per area (e.g., `271-pipelines-01.png`, `271-pipelines-02.png`, `271-boards-01.png`). |
72 | | - |
73 | | -2. **Download the image** to `release-notes/<year>/media/` using a PowerShell terminal command: |
74 | | - ```powershell |
75 | | - $token = az account get-access-token --resource "499b84ac-1321-427f-aa17-267ca6975798" --query accessToken -o tsv |
76 | | - Invoke-WebRequest -Uri "<attachment_url>" -Headers @{Authorization = "Bearer $token"} -OutFile "release-notes/<year>/media/<filename>.png" |
77 | | - ``` |
78 | | - If the `az` CLI is not available or the download fails, leave a TODO comment: `<!-- TODO: Download image from <url> to release-notes/<year>/media/<filename>.png -->`. |
79 | | - |
80 | | -3. **Replace the image reference** in the markdown content with the Microsoft Docs image pattern: |
81 | | - ```markdown |
82 | | - > [!div class="mx-imgBorder"] |
83 | | - >  |
84 | | - ``` |
85 | | - Use the original `alt` attribute or image filename as alt text. If no alt text exists, derive a descriptive one from the surrounding context (e.g., "Screenshot showing stages deployment view."). |
86 | | - |
87 | | -**Links file**: `release-notes/<year>/includes/<area>/sprint-<number>-update-links.md` |
88 | | - |
89 | | -```markdown |
90 | | ---- |
91 | | -author: gloridelmorales |
92 | | -ms.author: <author_alias> |
93 | | -ms.date: <date as M/D/YYYY> |
94 | | -ms.topic: include |
95 | | ---- |
96 | | - |
97 | | -- [<Feature Title>](#<anchor-from-title>) |
98 | | -``` |
99 | | - |
100 | | -Generate one link per feature. The anchor is the title lowercased, spaces replaced with hyphens, special characters removed. |
101 | | - |
102 | | -### B. Main sprint file |
103 | | - |
104 | | -**File**: `release-notes/<year>/sprint-<number>-update.md` |
105 | | - |
106 | | -Use the exact structure from existing sprint files in this repo. Reference the most recent sprint file as a template. The main file uses `[!INCLUDE]` directives to pull in the area-specific content and link files. |
107 | | - |
108 | | -Structure: |
109 | | -``` |
110 | | ---- |
111 | | -title: <Sprint Title> |
112 | | -author: gloridelmorales |
113 | | -ms.author: <author_alias> |
114 | | -ms.date: <date as M/D/YYYY> |
115 | | -description: <Sprint Title> |
116 | | ---- |
117 | | -
|
118 | | -# <Sprint Title> |
119 | | -
|
120 | | -<One-paragraph summary of highlights.> |
121 | | -
|
122 | | -Check out the release notes for details. |
123 | | -
|
124 | | -### <Area Display Name> |
125 | | -[!INCLUDE [sprint-<number>-update-links](includes/<area>/sprint-<number>-update-links.md)] |
126 | | -
|
127 | | -(repeat for each area) |
128 | | -
|
129 | | -## <Area Display Name> |
130 | | -[!INCLUDE [sprint-<number>-update](includes/<area>/sprint-<number>-update.md)] |
131 | | -
|
132 | | -(repeat for each area) |
133 | | -
|
134 | | -## Next steps |
135 | | -... |
136 | | -``` |
137 | | - |
138 | | -### Area display names mapping: |
139 | | -| Folder | Display Name | |
140 | | -|--------|-------------| |
141 | | -| `boards` | Azure Boards | |
142 | | -| `pipelines` | Azure Pipelines | |
143 | | -| `repos` | Azure Repos | |
144 | | -| `testplans` | Azure Test Plans | |
145 | | -| `ghazdo` | GitHub Advanced Security for Azure DevOps | |
146 | | -| `reporting` | Reporting | |
147 | | -| `general` | General | |
148 | | -| `artifacts` | Azure Artifacts | |
149 | | -| `wiki` | Wiki | |
150 | | - |
151 | | -### C. Area-level sprint files |
152 | | - |
153 | | -For each area that has work items, create: |
154 | | - |
155 | | -**File**: `release-notes/<year>/<area>/sprint-<number>-update.md` |
156 | | - |
157 | | -```markdown |
158 | | ---- |
159 | | -title: Azure DevOps Release Notes - <Area Display Name> Sprint <number> Update |
160 | | -description: See the Sprint <number> feature updates for <Area Display Name>, including next steps. |
161 | | -author: gloridelmorales |
162 | | -ms.author: <author_alias> |
163 | | -ms.date: <date as M/D/YYYY> |
164 | | -ms.topic: release-notes |
165 | | ---- |
166 | | - |
167 | | -# <Area Display Name> - Sprint <number> Update |
168 | | - |
169 | | -## Features |
170 | | - |
171 | | -[!INCLUDE [sprint-<number>-update-links](../includes/<area>/sprint-<number>-update-links.md)] |
172 | | - |
173 | | -[!INCLUDE [sprint-<number>-update](../includes/<area>/sprint-<number>-update.md)] |
174 | | - |
175 | | -[!INCLUDE [nextsteps](../includes/nextsteps.md)] |
176 | | -``` |
177 | | - |
178 | | -### D. Update release-notes/TOC.yml |
179 | | - |
180 | | -After generating all files, update `release-notes/TOC.yml` to add the new sprint entry in two places: |
181 | | - |
182 | | -1. **"By release date" section** — Add a new entry at the top of the current year's list under `Release Notes > Azure DevOps Services > By release date > "<year>"`: |
183 | | - ```yaml |
184 | | - - name: <release date as "Month Day"> |
185 | | - href: <year>/sprint-<number>-update.md |
186 | | - ``` |
187 | | - Insert it **above** the previous sprint entry so the newest is first. |
188 | | -
|
189 | | -2. **"By service" sections** — For each area that has work items, add a new entry at the top of the current year's list under the corresponding service section (e.g., `By service > Azure Boards > "<year>"`): |
190 | | - ```yaml |
191 | | - - name: <release date as "Month Day"> |
192 | | - href: <year>/<area>/sprint-<number>-update.md |
193 | | - ``` |
194 | | - Insert it **above** the previous sprint entry so the newest is first. |
195 | | - |
196 | | -Only add entries for areas that actually have work items in this sprint. Use the same date format as existing entries (e.g., "March 5", "February 11"). |
197 | | - |
198 | | -### E. Update release-notes/features-timeline-released.md |
199 | | - |
200 | | -After generating all files, update `release-notes/features-timeline-released.md` to add the new sprint's features. This file is an HTML table listing every feature from every sprint. |
201 | | - |
202 | | -1. **Update `ms.date`** in the frontmatter to the new sprint's publishing date. |
203 | | - |
204 | | -2. **Insert a new sprint block** at the top of the `<table>` body (right after the `</thead>` closing tag), above the previous sprint's `<tr>` block. The format is: |
205 | | - |
206 | | -```html |
207 | | -<tr> |
208 | | - <td rowspan="<total_feature_count>"><a href="<year>/sprint-<number>-update.md" data-raw-source="[<day> <Month> <year>](<year>/sprint-<number>-update.md)"><Month> <day> <year></a></td> |
209 | | - <td><First feature title></td><td><Area Display Name></td><td>Future</td></tr> |
210 | | - <td><Second feature title></td><td><Area Display Name></td><td>Future</td></tr> |
211 | | - ...last feature row... |
212 | | -<tr> |
213 | | -``` |
214 | | - |
215 | | -Key rules: |
216 | | -- `rowspan` must equal the total number of features across all areas in this sprint. |
217 | | -- The first feature row is on the same `<tr>` line as the `<td rowspan>` cell. |
218 | | -- Subsequent feature rows start with just `<td>` (no `<tr>` prefix) and end with `</td></tr>`. |
219 | | -- Use the **Area Display Name** (e.g., "Azure Boards", "Azure Pipelines", "General", "GitHub Advanced Security for Azure DevOps", "Azure Test Plans"). |
220 | | -- For the Server column, use `Future` for most features or `N/A` for GHAzDO features. |
221 | | -- The date link text format is `<Month> <day> <year>` (e.g., "March 31 2026"). |
222 | | -- Order features by area: GHAzDO first, then General, Boards, Repos, Pipelines, Test Plans (follow the order used in the main sprint file). |
223 | | - |
224 | | -## Update mode |
225 | | - |
226 | | -When the user asks to update, refresh, add to, remove from, or change an already-published sprint's release notes, follow these instructions instead of the full generation workflow. First check whether files already exist for the requested sprint (`release-notes/<year>/sprint-<number>-update.md`). If they do, you are in **update mode**. |
227 | | - |
228 | | -### Detect the operation |
229 | | - |
230 | | -Determine which operation the user is requesting: |
231 | | - |
232 | | -| User says | Operation | |
233 | | -|-----------|-----------| |
234 | | -| "add a feature to sprint X", "append work item 12345 to sprint X" | **Add feature** | |
235 | | -| "update/refresh feature Y from ADO", "re-pull work item 12345" | **Refresh feature** | |
236 | | -| "remove feature Y from sprint X", "pull feature Y" | **Remove feature** | |
237 | | -| "change the date for sprint X to April 15" | **Change date** | |
238 | | -| "edit the description for feature Y in sprint X" | **Edit feature** | |
239 | | - |
240 | | -### Add feature |
241 | | - |
242 | | -When adding a new feature to an existing sprint: |
243 | | - |
244 | | -1. **Fetch the work item** using `mcp_ado_wit_get_work_item` with `expand: "all"`. |
245 | | -2. **Determine the area** from the work item's area path. |
246 | | -3. **Append** the new `### <Title>` section to the bottom of `includes/<area>/sprint-<number>-update.md`. If the area's include file doesn't exist yet, create both the content and links include files. |
247 | | -4. **Append** the anchor link to `includes/<area>/sprint-<number>-update-links.md`. |
248 | | -5. **If this is a new area for the sprint:** |
249 | | - - Add new `[!INCLUDE]` directives in the main sprint file (`sprint-<number>-update.md`) for both the links and content sections. |
250 | | - - Create the area-level file (`<area>/sprint-<number>-update.md`). |
251 | | - - Add a TOC entry under the area's "By service" section in `TOC.yml`. |
252 | | -6. **Update `features-timeline-released.md`**: Add a new `<td>` row for the feature inside the sprint's block and increment the `rowspan` value by 1. |
253 | | -7. **Download any images** from the work item's `Microsoft.DevDiv.ReleaseNotes` field following the image handling instructions. |
254 | | -8. **Update the summary paragraph** in the main sprint file if appropriate. |
255 | | - |
256 | | -### Refresh feature |
257 | | - |
258 | | -When refreshing a feature's content from the latest ADO work item data: |
259 | | - |
260 | | -1. **Fetch the work item** using `mcp_ado_wit_get_work_item` with `expand: "all"`. |
261 | | -2. **Read the existing include file** to locate the `### <Title>` section. |
262 | | -3. **Replace** the section content (everything between the `###` heading and the next `###` heading or end of file) with the newly converted content from the work item's `Microsoft.DevDiv.ReleaseNotes` field. |
263 | | -4. **Download any new or changed images** and update image references. |
264 | | -5. **Update the feature title** in the links file, features timeline, and main sprint file if the title changed. |
265 | | - |
266 | | -### Remove feature |
267 | | - |
268 | | -When removing a feature from a sprint: |
269 | | - |
270 | | -1. **Remove** the `### <Title>` section from `includes/<area>/sprint-<number>-update.md`. |
271 | | -2. **Remove** the corresponding anchor link from `includes/<area>/sprint-<number>-update-links.md`. |
272 | | -3. **If this was the only feature in the area:** |
273 | | - - Remove the `[!INCLUDE]` directives from the main sprint file. |
274 | | - - Delete the area-level file (`<area>/sprint-<number>-update.md`). |
275 | | - - Remove the area's include files. |
276 | | - - Remove the TOC entry under the area's "By service" section. |
277 | | -4. **Update `features-timeline-released.md`**: Remove the feature's `<td>` row and decrement the `rowspan` value by 1. |
278 | | -5. **Delete any associated images** from the media folder. |
279 | | -6. **Update the summary paragraph** in the main sprint file. |
280 | | - |
281 | | -### Change date |
282 | | - |
283 | | -When changing the publishing date for a sprint: |
284 | | - |
285 | | -1. **Update `ms.date`** in all sprint files: |
286 | | - - `sprint-<number>-update.md` (main file) |
287 | | - - All `includes/<area>/sprint-<number>-update.md` files |
288 | | - - All `includes/<area>/sprint-<number>-update-links.md` files |
289 | | - - All `<area>/sprint-<number>-update.md` area-level files |
290 | | -2. **Update `TOC.yml`**: Change the `- name:` display text in both the "By release date" section and each "By service" area section. |
291 | | -3. **Update `features-timeline-released.md`**: Change the date in the `<a href>` link text and `data-raw-source` attribute for the sprint's row. |
292 | | - |
293 | | -### Edit feature |
294 | | - |
295 | | -When editing a feature's title or description manually (without re-fetching from ADO): |
296 | | - |
297 | | -1. **Edit** the content in `includes/<area>/sprint-<number>-update.md`. |
298 | | -2. **If the title changed**, also update: |
299 | | - - The anchor link in `includes/<area>/sprint-<number>-update-links.md` |
300 | | - - The feature title in `features-timeline-released.md` |
301 | | - - Any references in the main sprint file summary paragraph |
302 | | - |
303 | | -### Sync checklist |
304 | | - |
305 | | -After any update operation, verify all dependent files are in sync: |
306 | | - |
307 | | -- [ ] `includes/<area>/sprint-<number>-update.md` — content |
308 | | -- [ ] `includes/<area>/sprint-<number>-update-links.md` — anchor links |
309 | | -- [ ] `sprint-<number>-update.md` — main file `[!INCLUDE]` directives and summary |
310 | | -- [ ] `<area>/sprint-<number>-update.md` — area-level file exists if area has features |
311 | | -- [ ] `TOC.yml` — entries exist for all areas with features |
312 | | -- [ ] `features-timeline-released.md` — all features listed, `rowspan` correct |
313 | | -- [ ] `media/` — images downloaded, no orphaned images |
| 39 | +## Update behavior |
314 | 40 |
|
315 | | -## Constraints |
| 41 | +- If the sprint files already exist, update them in place rather than regenerating unrelated content. |
| 42 | +- Keep the include files, area wrapper files, `release-notes/TOC.yml`, and `release-notes/features-timeline-released.md` in sync. |
| 43 | +- When adding or removing a feature, also update dependent link files, area wrappers, TOC entries, and timeline rows as needed. |
| 44 | +- Do not update `release-notes/features-timeline.md` unless the user explicitly asks for roadmap changes. |
316 | 45 |
|
317 | | -- DO NOT invent or fabricate feature descriptions. Use only what the work items provide. |
318 | | -- DO NOT modify existing files unless explicitly asked. |
319 | | -- ONLY generate release notes files — do not make infrastructure or code changes. |
320 | | -- **Always extract content from the work item's `Microsoft.DevDiv.ReleaseNotes` field first, then `System.Description` as fallback.** Convert HTML to clean Markdown. |
321 | | -- Only add a placeholder `<!-- TODO: Add description for this feature -->` if both the Release Notes field and Description field are empty. |
322 | | -- Generate anchors by lowercasing the title, replacing spaces with `-`, and removing special characters. |
323 | | -- Use the `includes/` pattern with `[!INCLUDE]` directives matching the existing repo convention. |
324 | | -- Always check the most recent sprint file in the repo for the latest formatting conventions before generating. |
| 46 | +## Quality bar |
325 | 47 |
|
326 | | -## Output Format |
| 48 | +- Use the latest sprint files in the repo as the formatting reference. |
| 49 | +- Preserve existing repo conventions and only make the minimal edits needed. |
| 50 | +- Validate touched Markdown and YAML files after editing. |
327 | 51 |
|
328 | | -After generating all files, provide a summary table: |
| 52 | +## Output |
329 | 53 |
|
330 | | -| File | Areas Covered | # Features | |
331 | | -|------|---------------|------------| |
332 | | -| `release-notes/<year>/sprint-<number>-update.md` | All | Total count | |
333 | | -| `release-notes/<year>/includes/<area>/sprint-<number>-update.md` | <Area> | Count | |
334 | | -| `release-notes/<year>/includes/<area>/sprint-<number>-update-links.md` | <Area> | Count | |
| 54 | +After finishing, summarize the files created or updated and call out any missing source content or TODO placeholders that still need author follow-up. |
0 commit comments