Conversation
Migration NoteThis PR replaces #79 which was opened from
All prior review feedback from #79 still applies — please see that PR for the full discussion history. |
There was a problem hiding this comment.
Pull request overview
Adds a new refactoring-to-async skill to the dotnet plugin, along with an evaluation scenario and fixture project intended to test bottom-up async conversion guidance.
Changes:
- Added
refactoring-to-asyncskill documentation underplugins/dotnet/skills/. - Added a new eval scenario plus C# fixture project under
tests/dotnet/refactoring-to-async/. - Updated
.github/CODEOWNERSto assign ownership for the new skill and test directory.
Reviewed changes
Copilot reviewed 5 out of 5 changed files in this pull request and generated 6 comments.
Show a summary per file
| File | Description |
|---|---|
| plugins/dotnet/skills/refactoring-to-async/SKILL.md | New skill content describing async refactoring workflow and pitfalls. |
| tests/dotnet/refactoring-to-async/eval.yaml | New eval scenarios/assertions for async refactoring and CPU-bound non-async guidance. |
| tests/dotnet/refactoring-to-async/UserService.cs | Fixture code containing sync I/O and blocking patterns to be refactored by the model. |
| tests/dotnet/refactoring-to-async/SyncService.csproj | Fixture project enabling dotnet build-style validation. |
| .github/CODEOWNERS | Adds code owners for the new skill and tests. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
You can also share your feedback on Copilot code review. Take the survey.
Feedback carried over from #79 (refactoring-to-async)Code Review Comments (10 threads)@copilot —
@copilot —
@copilot —
@danmoseley —
@danmoseley —
@danmoseley —
@danmoseley —
@danmoseley —
@danmoseley —
@danmoseley —
Discussion Comments (5)
|
|
/evaluate |
Skill Validation Results
Model: claude-opus-4.6 | Judge: claude-opus-4.6 |
|
/evaluate |
|
✅ Evaluation completed. View results | View workflow run |
|
@danmoseley - could you please take another look? I believe I have addressed your feedback. |
|
@mrsharm check the one scenario in which the skill doesn't get activated. |
@ViktorHofer: Intentional - is a negative test and is the correct outcome. The eval suggests optimizing matrix multiplication (CPU-bound), not about converting I/O to async. The skill's description targets I/O-bound async refactoring, so the agent should recognize this isn't an async problem and not load the skill. That's exactly what happened in all 3 runs. |
|
@mrsharm such tests must be annotated with Otherwise we have no way to distinguish between intentionally not activated and unintentionally not activated. |
|
/evaluate |
|
✅ Evaluation completed. View results | View workflow run |
|
@ViktorHofer - thanks! Been implemented for this and the other PRs. |
|
@mrsharm - the repo has undergone some restructuring to make everything more organized. Hence, we are asking all open PRs to update the branch. Sorry about this. @jasonmalinowski @jaredpar - please review. |
Teaches bottom-up async conversion patterns: identifying sync-over-async, CancellationToken propagation, ConfigureAwait usage, and ValueTask selection. Eval results: +46.9% improvement over baseline (threshold: 10%) Includes eval.yaml with positive scenario + negative test and fixture files.
The 'should not apply to CPU-bound code' scenario was dropping agents into an empty workspace, causing them to give up instead of engaging with the problem. Now provides MatrixMultiplier.cs and .csproj so the agent has actual code to optimize.
SKILL.md changes: - Move when-to-use/not-use into description for lazy-loading activation - Clarify ConfigureAwait(false) guidance: app code vs library code - Streamline decision tree section eval.yaml changes: - Fix CPU-bound negative scenario: inline MatrixMultiplier.cs fixture - Make negative test prompt realistic (user doesn't state 'CPU-bound') - Add ConfigureAwait(false) library code scenario - Add partial async conversion scenario Eval results (3 runs, 4 scenarios): Refactor sync to async: 3.0 -> 5.0 (+2.0) PASS CPU-bound negative: 2.0 -> 5.0 (+3.0) PASS ConfigureAwait library code: 4.0 -> 4.0 ( 0.0) FAIL Partial async conversion: 3.3 -> 3.7 (+0.4) PASS Overall: +33.8% (3/4 passed)
…/IAsyncEnumerable, fix overfitting - Shorten skill description to be more concise (jaredpar feedback) - Replace grep commands with method name lists (danmoseley feedback) - Add Step 5: IAsyncDisposable / await using guidance (danmoseley feedback) - Add IAsyncEnumerable/await foreach and ValueTask sections (danmoseley feedback) - Fix ConfigureAwait wording: Winforms/WPF/ASP.NET (danmoseley suggestion) - De-overfit controller scenario prompt (jaredpar feedback) - Prefer sequential awaits over Task.WhenAll in rubric (danmoseley feedback) - Add output_not_matches assertion for controller scenario (copilot feedback) - Add await using assertion and rubric item to scenario 1 (danmoseley feedback) Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
- Move refactoring-to-async CODEOWNERS entries from dotnet-upgrade to dotnet section - Add .GetAwaiter().GetResult() to scenario 1 output_not_matches assertion Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
- Add using var to HttpResponseMessage in both async code examples - Remove .GetAwaiter().GetResult() from controller output_not_matches (too brittle for prose) Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
…, clarify queryAsync - After example now uses SendAsync to match the Before's Send(HttpRequestMessage) - MatrixMultiplier.csproj: net10.0 -> net8.0 for consistency with other fixtures - IAsyncEnumerable example: queryAsync(ct) -> db.QueryAsync() for clarity Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
…iter from IAsyncDisposable list, tighten CPU-bound regex - Add refactoring-to-async to plugins/dotnet/README.md skill inventory - Handle null from JsonSerializer.Deserialize with ?? [] - Remove StreamReader/Writer from IAsyncDisposable examples (they only implement IDisposable) - CPU-bound scenario: narrow regex to specifically detect Multiply being made async Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Removes contradictory Task.Run advice from anti-patterns table. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
e31c31d to
2fa9826
Compare
SKILL.md: - Shorten frontmatter description (jaredpar) - Replace grep-style patterns with example method names (danmoseley) - Add Task.WhenAll concurrency caveat with sequential-await default (danmoseley) - Fix WinForms casing (danmoseley) - Expand ValueTask restrictions section (danmoseley) - Clarify IAsyncDisposable vs IDisposable for StreamReader/Writer (danmoseley) - Improve fire-and-forget guidance to recommend IHostedService (danmoseley) eval.yaml: - Make scenario prompts more natural to reduce overfitting (jaredpar/danmoseley) - Fix file I/O prompt to reliably trigger skill activation - Add Task.WhenAll concurrency caveat to controller rubric
|
/evaluate |
There was a problem hiding this comment.
Pull request overview
Copilot reviewed 6 out of 6 changed files in this pull request and generated no new comments.
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
Skill Validation Results
[1]
Model: claude-opus-4.6 | Judge: claude-opus-4.6 🔍 Full Results - additional metrics and failure investigation steps ▶ Sessions Visualisation -- interactive replay of all evaluation sessions |
Thanks - done! Evals look good - can merge if things look good. |
2fa9826 to
00ae665
Compare
Adds the refactoring-to-async skill for bottom-up async conversion patterns in .NET.
Note: Replaces #79 (migrated from skills-old repo to new plugins/ structure).
What the Skill Teaches