From 4c354762ab6f29447630593b17507bdfe11445b5 Mon Sep 17 00:00:00 2001 From: Kenzie Davisson Date: Fri, 13 Mar 2026 12:45:47 -0700 Subject: [PATCH 1/4] Add an agent skill for adding release notes --- .agents/skills/adding-release-notes/SKILL.md | 61 +++++++++++++++++ .../scripts/add_note.dart | 68 +++++++++++++++++++ pubspec.lock | 20 +++--- 3 files changed, 139 insertions(+), 10 deletions(-) create mode 100644 .agents/skills/adding-release-notes/SKILL.md create mode 100644 .agents/skills/adding-release-notes/scripts/add_note.dart diff --git a/.agents/skills/adding-release-notes/SKILL.md b/.agents/skills/adding-release-notes/SKILL.md new file mode 100644 index 00000000000..35560d39e60 --- /dev/null +++ b/.agents/skills/adding-release-notes/SKILL.md @@ -0,0 +1,61 @@ +--- +name: adding-release-notes +description: Adds user-facing change descriptions to DevTools release notes. Use when documenting improvements, fixes, or new features in the NEXT_RELEASE_NOTES.md file. +--- + +# Adding Release Notes + +This skill helps automate adding release notes to `packages/devtools_app/release_notes/NEXT_RELEASE_NOTES.md`. + +## Workflow +Copy this checklist into your response to track progress: + +```markdown +Release Notes Progress: +- [ ] Step 1: Formulate the entry (past tense, PR link) +- [ ] Step 2: Determine the section (Inspector, Memory, etc.) +- [ ] Step 3: Add the entry (use scripts/add_note.py) +- [ ] Step 4: Add images (if applicable) +``` + +## Guidelines + +### 1. Formulate the Entry +- **Tense**: Always use **past tense** (e.g., "Added", "Improved", "Fixed"). +- **Template**: `* . [#](https://github.com/flutter/devtools/pull/)` +- **Examples**: + - `* Added support for XYZ. [#12345](https://github.com/flutter/devtools/pull/12345)` + - `* Fixed a crash in the ABC screen. [#67890](https://github.com/flutter/devtools/pull/67890)` + +### 2. Determine Section +Match the change to the section in `NEXT_RELEASE_NOTES.md`: +- `General updates` +- `Inspector updates` +- `Performance updates` +- `CPU profiler updates` +- `Memory updates` +- `Debugger updates` +- `Network profiler updates` +- `Logging updates` +- `App size tool updates` +- `Deep links tool updates` +- `VS Code sidebar updates` +- `DevTools extension updates` +- `Advanced developer mode updates` + +### 3. Add to NEXT_RELEASE_NOTES.md +Use the provided utility script to insert the note safely. The script handles replacing the TODO placeholder if it's the first entry in that section. + +```bash +dart .agents/skills/adding-release-notes/scripts/add_note.dart "Inspector updates" "Added XYZ support" 12345 +``` + +### 4. Optional: Images +Add images to `packages/devtools_app/release_notes/images/` and reference them: +```markdown +![Accessible description](images/screenshot.png "Hover description") +``` +**Constraint**: Use **dark mode** for screenshots. + +## Resources +- [README.md](../../packages/devtools_app/release_notes/README.md): Official project guidance. diff --git a/.agents/skills/adding-release-notes/scripts/add_note.dart b/.agents/skills/adding-release-notes/scripts/add_note.dart new file mode 100644 index 00000000000..787b4e9c113 --- /dev/null +++ b/.agents/skills/adding-release-notes/scripts/add_note.dart @@ -0,0 +1,68 @@ +// Copyright 2019 The Flutter Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file or at https://developers.google.com/open-source/licenses/bsd. + +import 'dart:io'; + +void main(List args) { + if (args.length < 3) { + print('Usage: dart add_note.dart
'); + exit(1); + } + + final section = args[0].trim(); + final note = args[1].trim(); + final pr = args[2].trim(); + + final filePath = 'packages/devtools_app/release_notes/NEXT_RELEASE_NOTES.md'; + final file = File(filePath); + + if (!file.existsSync()) { + print('Error: $filePath not found.'); + exit(1); + } + + var content = file.readAsStringSync(); + + if (!content.contains('## $section')) { + print("Error: Section '$section' not found."); + exit(1); + } + + final newEntry = + '- ${note.replaceAll(RegExp(r'\.+$'), '')} [#$pr](https://github.com/flutter/devtools/pull/$pr)\n'; + + // Check for TODO placeholder. + const todoText = 'TODO: Remove this section if there are not any updates.'; + final todoPattern = RegExp( + '## ${RegExp.escape(section)}\\s*\\n\\s*${RegExp.escape(todoText)}\\s*\\n*', + ); + + if (todoPattern.hasMatch(content)) { + content = content.replaceFirst(todoPattern, '## $section\n\n$newEntry\n'); + } else { + // Append to existing list in the section. + final sectionHeader = '## $section'; + final sectionStart = content.indexOf(sectionHeader); + + // Find the next section start or the end of the file. + var nextSectionStart = content.indexOf('\n## ', sectionStart + 1); + if (nextSectionStart == -1) { + nextSectionStart = + content.indexOf('\n# Full commit history', sectionStart + 1); + } + if (nextSectionStart == -1) { + nextSectionStart = content.length; + } + + var sectionContent = + content.substring(sectionStart, nextSectionStart).trimRight(); + sectionContent += '\n$newEntry'; + + content = + '${content.substring(0, sectionStart)}$sectionContent\n${content.substring(nextSectionStart).trimLeft()}'; + } + + file.writeAsStringSync(content); + print('Successfully added note to $section.'); +} diff --git a/pubspec.lock b/pubspec.lock index 7831ae0f18f..e30fd8babfe 100644 --- a/pubspec.lock +++ b/pubspec.lock @@ -530,10 +530,10 @@ packages: dependency: transitive description: name: matcher - sha256: "12956d0ad8390bbcc63ca2e1469c0619946ccb52809807067a7020d57e647aa6" + sha256: dc0b7dc7651697ea4ff3e69ef44b0407ea32c487a39fff6a4004fa585e901861 url: "https://pub.dev" source: hosted - version: "0.12.18" + version: "0.12.19" material_color_utilities: dependency: transitive description: @@ -758,10 +758,10 @@ packages: dependency: transitive description: name: source_gen - sha256: "1d562a3c1f713904ebbed50d2760217fd8a51ca170ac4b05b0db490699dbac17" + sha256: adc962c96fffb2de1728ef396a995aaedcafbe635abdca13d2a987ce17e57751 url: "https://pub.dev" source: hosted - version: "4.2.0" + version: "4.2.1" source_map_stack_trace: dependency: transitive description: @@ -854,26 +854,26 @@ packages: dependency: transitive description: name: test - sha256: "54c516bbb7cee2754d327ad4fca637f78abfc3cbcc5ace83b3eda117e42cd71a" + sha256: "280d6d890011ca966ad08df7e8a4ddfab0fb3aa49f96ed6de56e3521347a9ae7" url: "https://pub.dev" source: hosted - version: "1.29.0" + version: "1.30.0" test_api: dependency: transitive description: name: test_api - sha256: "93167629bfc610f71560ab9312acdda4959de4df6fac7492c89ff0d3886f6636" + sha256: "8161c84903fd860b26bfdefb7963b3f0b68fee7adea0f59ef805ecca346f0c7a" url: "https://pub.dev" source: hosted - version: "0.7.9" + version: "0.7.10" test_core: dependency: transitive description: name: test_core - sha256: "394f07d21f0f2255ec9e3989f21e54d3c7dc0e6e9dbce160e5a9c1a6be0e2943" + sha256: "0381bd1585d1a924763c308100f2138205252fb90c9d4eeaf28489ee65ccde51" url: "https://pub.dev" source: hosted - version: "0.6.15" + version: "0.6.16" typed_data: dependency: transitive description: From 1ddb7eb1e02bfac3086bf521dd67ae847e4d63ba Mon Sep 17 00:00:00 2001 From: Kenzie Davisson Date: Fri, 13 Mar 2026 15:51:24 -0700 Subject: [PATCH 2/4] update skill --- .agents/skills/adding-release-notes/SKILL.md | 7 ++++--- .agents/skills/adding-release-notes/scripts/add_note.dart | 6 +++++- 2 files changed, 9 insertions(+), 4 deletions(-) diff --git a/.agents/skills/adding-release-notes/SKILL.md b/.agents/skills/adding-release-notes/SKILL.md index 35560d39e60..d0794874cce 100644 --- a/.agents/skills/adding-release-notes/SKILL.md +++ b/.agents/skills/adding-release-notes/SKILL.md @@ -12,9 +12,9 @@ Copy this checklist into your response to track progress: ```markdown Release Notes Progress: -- [ ] Step 1: Formulate the entry (past tense, PR link) +- [ ] Step 1: Formulate the entry (past tense, use "TODO" for PR number if unknown) - [ ] Step 2: Determine the section (Inspector, Memory, etc.) -- [ ] Step 3: Add the entry (use scripts/add_note.py) +- [ ] Step 3: Add the entry (use scripts/add_note.dart) - [ ] Step 4: Add images (if applicable) ``` @@ -23,6 +23,7 @@ Release Notes Progress: ### 1. Formulate the Entry - **Tense**: Always use **past tense** (e.g., "Added", "Improved", "Fixed"). - **Template**: `* . [#](https://github.com/flutter/devtools/pull/)` +- **Placeholder**: Use `TODO` if you do not have a PR number yet. - **Examples**: - `* Added support for XYZ. [#12345](https://github.com/flutter/devtools/pull/12345)` - `* Fixed a crash in the ABC screen. [#67890](https://github.com/flutter/devtools/pull/67890)` @@ -47,7 +48,7 @@ Match the change to the section in `NEXT_RELEASE_NOTES.md`: Use the provided utility script to insert the note safely. The script handles replacing the TODO placeholder if it's the first entry in that section. ```bash -dart .agents/skills/adding-release-notes/scripts/add_note.dart "Inspector updates" "Added XYZ support" 12345 +dart .agents/skills/adding-release-notes/scripts/add_note.dart "Inspector updates" "Added XYZ support" TODO ``` ### 4. Optional: Images diff --git a/.agents/skills/adding-release-notes/scripts/add_note.dart b/.agents/skills/adding-release-notes/scripts/add_note.dart index 787b4e9c113..9baf3f8ac14 100644 --- a/.agents/skills/adding-release-notes/scripts/add_note.dart +++ b/.agents/skills/adding-release-notes/scripts/add_note.dart @@ -29,8 +29,12 @@ void main(List args) { exit(1); } + final prLink = pr == 'TODO' + ? '[#TODO]' + : '[#$pr](https://github.com/flutter/devtools/pull/$pr)'; + final newEntry = - '- ${note.replaceAll(RegExp(r'\.+$'), '')} [#$pr](https://github.com/flutter/devtools/pull/$pr)\n'; + '- ${note.replaceAll(RegExp(r'\.+$'), '')} $prLink\n'; // Check for TODO placeholder. const todoText = 'TODO: Remove this section if there are not any updates.'; From 393cd63a9375245aeafe967120562d4d5c35e745 Mon Sep 17 00:00:00 2001 From: Kenzie Davisson Date: Fri, 13 Mar 2026 15:58:00 -0700 Subject: [PATCH 3/4] update skill --- .agents/skills/adding-release-notes/SKILL.md | 9 ++++++++- .../skills/adding-release-notes/scripts/add_note.dart | 8 ++------ 2 files changed, 10 insertions(+), 7 deletions(-) diff --git a/.agents/skills/adding-release-notes/SKILL.md b/.agents/skills/adding-release-notes/SKILL.md index d0794874cce..36f613b54ee 100644 --- a/.agents/skills/adding-release-notes/SKILL.md +++ b/.agents/skills/adding-release-notes/SKILL.md @@ -22,13 +22,20 @@ Release Notes Progress: ### 1. Formulate the Entry - **Tense**: Always use **past tense** (e.g., "Added", "Improved", "Fixed"). +- **Punctuation**: Always end entries with a **period**. - **Template**: `* . [#](https://github.com/flutter/devtools/pull/)` - **Placeholder**: Use `TODO` if you do not have a PR number yet. - **Examples**: - `* Added support for XYZ. [#12345](https://github.com/flutter/devtools/pull/12345)` - `* Fixed a crash in the ABC screen. [#67890](https://github.com/flutter/devtools/pull/67890)` -### 2. Determine Section +### 2. User-Facing Changes Only +- **Criteria**: Focus on **what** changed for the user, not **how** it was implemented. +- **Avoid**: Technical details like "Implemented XYZ with a new controller", "Updated the build method", or naming internal classes. +- **Example (Bad)**: `* Implemented log details search using SearchControllerMixin. [#TODO](https://github.com/flutter/devtools/pull/TODO)` +- **Example (Good)**: `* Added search support to the log details view. [#TODO](https://github.com/flutter/devtools/pull/TODO)` + +### 3. Determine Section Match the change to the section in `NEXT_RELEASE_NOTES.md`: - `General updates` - `Inspector updates` diff --git a/.agents/skills/adding-release-notes/scripts/add_note.dart b/.agents/skills/adding-release-notes/scripts/add_note.dart index 9baf3f8ac14..ec0c22eb947 100644 --- a/.agents/skills/adding-release-notes/scripts/add_note.dart +++ b/.agents/skills/adding-release-notes/scripts/add_note.dart @@ -29,12 +29,8 @@ void main(List args) { exit(1); } - final prLink = pr == 'TODO' - ? '[#TODO]' - : '[#$pr](https://github.com/flutter/devtools/pull/$pr)'; - - final newEntry = - '- ${note.replaceAll(RegExp(r'\.+$'), '')} $prLink\n'; + final noteWithPeriod = note.endsWith('.') ? note : '$note.'; + final newEntry = '- $noteWithPeriod $prLink\n'; // Check for TODO placeholder. const todoText = 'TODO: Remove this section if there are not any updates.'; From f76bc06dac4e8bbf718d572677262a0ef02f16f9 Mon Sep 17 00:00:00 2001 From: Kenzie Davisson Date: Fri, 13 Mar 2026 16:26:02 -0700 Subject: [PATCH 4/4] update skill --- .agents/skills/adding-release-notes/SKILL.md | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/.agents/skills/adding-release-notes/SKILL.md b/.agents/skills/adding-release-notes/SKILL.md index 36f613b54ee..cfb0ae86112 100644 --- a/.agents/skills/adding-release-notes/SKILL.md +++ b/.agents/skills/adding-release-notes/SKILL.md @@ -25,6 +25,12 @@ Release Notes Progress: - **Punctuation**: Always end entries with a **period**. - **Template**: `* . [#](https://github.com/flutter/devtools/pull/)` - **Placeholder**: Use `TODO` if you do not have a PR number yet. +- **Images**: If adding an image, indent it by two spaces to align with the bullet point, and ensure there is only one newline between the text and the image. + - Correct Format: + ```markdown + - Added support for XYZ. [#TODO](https://github.com/flutter/devtools/pull/TODO) + ![](images/my_feature.png) + ``` - **Examples**: - `* Added support for XYZ. [#12345](https://github.com/flutter/devtools/pull/12345)` - `* Fixed a crash in the ABC screen. [#67890](https://github.com/flutter/devtools/pull/67890)`