Add Bulk Server Upgrades - #815#963
Conversation
…g and bulk-upgrade UI; remove duplicate type
erikdarlingdata
left a comment
There was a problem hiding this comment.
Thanks for taking this on — the core idea (Check All Versions probe + parallel InstallationService.ExecuteAllUpgradesAsync + ExecuteInstallationAsync per server) is sound and matches the pattern already used in AddServerDialog.xaml.cs:612 and the CLI installer. Most of what I'm flagging is around the edges.
Process-level blockers
-
Wrong base branch. This project's feature branches always go to
dev(anddevmerges tomainonly at release time — apologies, that's not in CONTRIBUTING.md and probably should be). Concrete impact:devis on .NET 10,mainis still .NET 8. The new test project targetsnet8.0-windows, andInstaller/packages.lock.jsonis bumped from ILLink 8.0.26 → 8.0.27 (an 8.x patch). Whendevnext merges tomain, both conflict and the test project won't build against the .NET 10 codebase. Please rebase ontodevand retarget the PR there. -
Test project versions don't match the rest of the repo.
Dashboard.Tests.csprojusesxunit 2.6.1+xunit.runner.visualstudio 3.1.5. The existingLite.TestsandInstaller.Testsusexunit.v3 3.2.2+xunit.runner.visualstudio 3.1.5. Tests do execute (I ran them locally — 2/2 pass), but it's inconsistent. Move toxunit.v3 3.2.2. -
Tests aren't wired into CI.
Dashboard.Testsisn't added to.github/workflows/build.yml— see the existingRun Lite fast tests/Run Installer testssteps for the shape. -
Solution file noise.
PerformanceMonitor.slnhas an unrelated edit (VisualStudioVersion = 17.14.36930.0 d17.14→... 17.14.36930.0) — looks like VS install drift. Revert.
Correctness
-
ServerVersionInfoproxy dropsInstalledVersionchange notifications.OnInnerServerPropertyChanged(Models/ServerConnection.cs ~290) forwardsDisplayName, ServerName, AuthenticationDisplay, MonthlyCostUsd, LastConnected, IsFavorite— but notInstalledVersion, even thoughServerConnection.InstalledVersiondoes raise PropertyChanged. The code papers over this with a defensive dual-write everywhere (entry.InstalledVersion = ...; entry.Server.InstalledVersion = ...). Cleaner: either addInstalledVersionto the switch and drop the redundant private field, or makeServerVersionInfo.InstalledVersiona pure passthrough getter/setter onServer.InstalledVersion.(
AuthenticationDisplayis the same shape — read-only computed onServerConnection, never raises PropertyChanged. The proxy forwarding for it is dead code. Not blocking, just confusing.) -
Closing the window mid-upgrade leaks running tasks.
ManageServersWindow_Closingcancels the CTS and returns; the window dies, but the upgrade tasks keep running and continue posting to a dead Dispatcher viaProgress<InstallationProgress>. The PR description already calls out this case as "not tested." Either await completion before closing or guard the Progress handlers (e.g.if (!Dispatcher.HasShutdownStarted) Dispatcher.Invoke(...)). -
Progress bar oscillates under parallel upgrades.
centralProgresswritesUpgradeProgressBar.Value = p.ProgressPercent.Valuefrom N concurrent servers reporting their own 0–100. Bar will jump randomly. Switch to a count-based bar (X of N servers complete) or average the per-server percents. -
Button bar overflows at 1024px width. Summing the left-aligned button widths + 8px margins in
ManageServersWindow.xaml:- Initial state (Upgrade/Cancel hidden): ~944px
- During an in-flight upgrade (Upgrade + Cancel both visible): ~1230px
The window is 1024px wide. Even in the initial state, with the Close button on the right + window chrome, the left-most buttons are clipped. Either grow the default width (~1280) or move the new buttons into a
WrapPanel. -
Dead variables.
ManageServersWindow.xaml.cs:643-644—int successCount = 0; int failCount = 0;declared inUpgradeAll_Clickand never used. Triggers CS0219. -
Stray editorial comments / using:
using ModelContextProtocol.Protocol;at the top ofManageServersWindow.xaml.cs— unused, looks like an IDE auto-import.// extract the existing version logic into a helperappears twice (lines 455, 641);GetAppVersion()is the helper, so the comment is stale.// existing version comparison logic follows unchanged...(line 374) is an editor note.// Replace the existing ServerVersionInfo type with this implementation...(Models/ServerConnection.cs:206) — implies a priorServerVersionInfo; onmainthere is none. Remove.
-
catch { }inManageServersWindow_Closing. Swallows everything silently. At minimum, log via the existingAppendUpgradeLog. -
PerServerUpgradeResultshould besealed(CA1852).
Design / UX
-
EntraMFA + parallel upgrades will pop N stacked auth dialogs. The PR's test plan correctly flags this as untested — at minimum, serialize EntraMFA upgrades (run them after the SQL Auth / Windows Auth batch) or warn the user up front before kicking them off in parallel.
-
Dispatcher.InvokeinsideProgress<T>handlers is redundant.Progress<T>already marshals to the captured SynchronizationContext (the UI thread, since the instances are created on the UI thread). The nestedDispatcher.InvokeincentralProgressand theDispatcher.CheckAccess()path inAppendUpgradeLogaren't wrong, just belt-and-suspenders. -
Tests cover only the aggregator.
UpgradeAggregator.Aggregateis ~25 lines of trivial counting; the orchestration inUpgradeAll_Click(cancellation, partial failure, credential lookup, EntraMFA serialization, dispatcher race on close) is where bugs will live. Not blocking — WPF code-behind is genuinely hard to unit-test — but the coverage is lighter than the PR description suggests.
TL;DR for a follow-up
- Rebase onto
devand retarget the PR. Dashboard.Tests.csproj→net10.0-windows+xunit.v3 3.2.2; wire intobuild.yml.- Revert the unrelated
.slnedit. - Drop the stale comments, the unused
using, and the two dead variables. - Fix the proxy's
InstalledVersionforwarding so the dual-write isn't needed. - Grow the default window width or
WrapPanelthe new buttons. - Either rate-limit/serialize EntraMFA upgrades or warn before launching them in parallel.
Happy to look again once these are addressed.
…g and bulk-upgrade UI; remove duplicate type
…g and bulk-upgrade UI; remove duplicate type
…nInfo, add version probing and bulk-upgrade UI; remove duplicate type
|
@erikdarlingdata, thank you for a thorough and thoughtful review. I should've mentioned that this is my first WPF project and I am still learning the intricacies of GitHub and git integration in Visual Studio. I will flag this PR as Ready for review when I think it's ready. Again, thanks for your patience :-) |
|
Thanks for the updates, @mas-mark-y — here's where things stand against the earlier review, point by point so it's easy to cross-reference. It's still a draft, so no rush — this is just a map of what's left. Done ✅
#3 — CI wiring needs three more piecesThe
Still open from the original review
One new thing
Nice progress on the core flow — the parallel |
…, ensure tests run on release and PR
Bulk Server Upgrades
This is an attempt to implement a new feature requested in #815
Which component(s) does this affect?
How was this tested?
Checklist
dotnet build -c Debug)