fix: stop report cells accepting typing that goes nowhere - #2117
Merged
Conversation
Ten text cells across App Updates and Windows Update entered edit mode on a double-click. Typing changed the in-memory row and nothing else, so the app appeared to accept an edit it discarded. One of them is App Updates' Id, which is what WingetService.UpgradeAsync builds "winget upgrade --id" from -- retyping it turns a row that would have upgraded into a row that reports an error. Per-column, NOT grid-level. #2105 read this as "20 views set IsReadOnly on the DataGrid, these forgot", which was backwards: every grid lacking it has a DataGridCheckBoxColumn for row selection, and DataGrid.IsReadOnly="True" renders those checkboxes untickable -- it would have disabled Upgrade selected. None of the 20 read-only grids has a checkbox column, which is why they can afford it. The issue's count was also inflated. Its pattern matched <DataGridTextColumn.CellStyle> as well -- a property element, not a column, and there are 43 of them -- so 27 typeable cells across seven views was really 10 across two. Shortcut Cleaner, Uninstaller, Context Menu and Startup already carry the attribute per column. Environment Variables' Value column stays editable and is named as the exception with its reason: that tab is an editor, with Apply/Discard/Restore beside the grid and UpdateSourceTrigger=PropertyChanged carrying each keystroke to the view-model. Guarded by EveryReportTextColumn_IsReadOnly, floor 118 of 125 measured, with the property-element trap written into the remark so the next measurement avoids it. Closes #2105
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Closes #2105 — and corrects that issue's numbers, which I had inflated.
What was wrong
Ten text cells across
AppUpdatesViewandWindowsUpdateViewentered edit mode on a double-click. Typing there changed the in-memory row and nothing else, so the app appeared to accept an edit it silently discarded.One of them carries a consequence: App Updates' Id is the value
WingetService.UpgradeAsyncbuildswinget upgrade --id "…"from, so retyping it turns a row that would have upgraded into a row that reports an error.Per-column, not grid-level — and the issue got this backwards
#2105 read the situation as "20 views set
IsReadOnlyon the DataGrid, these forgot". That was wrong, and setting it globally would have broken the feature:Every grid lacking
IsReadOnlyhas a selection mechanism that needs the grid editable. Six useDataGridCheckBoxColumn(App Updates, Windows Update, App Blocker, DNS & Hosts, Shortcut Cleaner, Uninstaller) and two use aDataGridTemplateColumnwith a CheckBox.DataGrid.IsReadOnly="True"renders aDataGridCheckBoxColumnuntickable — it would have disabled "Upgrade selected" outright. None of the 20 read-only grids has a checkbox column, which is why they can afford the grid-level form.So the fix is
IsReadOnly="True"on the ten text columns, leaving every checkbox, button and template column exactly as it was.The count in #2105 was inflated, and by what
The issue's table said App Updates 6, Windows Update 10 of 11, plus five more views — 27 typeable cells in total. Re-measured: 10 cells across 2 views.
The pattern I measured with,
<DataGridTextColumn[^>]*?/?>, also matches<DataGridTextColumn.CellStyle>— a property element, not a column. There are 43 of those across the views, so the population read as 168 instead of 125, and every per-view number carried a share of them. Shortcut Cleaner, Uninstaller, Context Menu and Startup were listed as having typeable cells and have none; their text columns already carry the attribute per column.Recording it here rather than quietly shipping the smaller fix, because the same pattern is now in the guard and its floor documents the trap.
Environment Variables is the one deliberate exception
Its
Valuecolumn stays editable, and the tab settles it:Apply/Discard/Restore backupsit beside the grid, and the binding isUpdateSourceTrigger=PropertyChanged, which exists to carry each keystroke to the view-model forApplyto write. Inline editing is the feature. Marked with a comment in the XAML and named in the guard's exception list with that reason, so a uniformity sweep cannot "fix" it.The guard
EveryReportTextColumn_IsReadOnly— aDataGridTextColumnmust be read-only via its own attribute or via a grid whose every<DataGrid>tag sets it, with the exception list keyed to view + column header. Vacuity floor at 118 against 125 measured, and the remark records the property-element trap so the next person measuring does not repeat it.Verification
Mutation proof, three files restored byte-for-byte:
IdlosesIsReadOnlyAppUpdatesView.xaml: IdStatusloses itWindowsUpdateView.xaml: StatusEnvironmentVariablesView.xaml: ValueThe third confirms the allowlist is load-bearing rather than decoration. Baseline and post-restore green.
265 cases green across
ArchitectureTests,AppUpdatesViewModelTests,WindowsUpdate*andEnvironmentVariables*. Builds 0 errors / 0 warnings,dotnet format --verify-no-changesclean on both, version consistency csproj 1.76.14 = CHANGELOG 1.76.14 = SECURITY 1.76.x.Not verified here: that the cells are actually inert on screen, which needs the app running. What is verified is that the attribute is on all ten columns and that no checkbox column was touched — the XAML parses, and the grid-level form (which would have broken selection) is explicitly rejected by the guard's failure message.