aboutsummaryrefslogtreecommitdiffstats
path: root/docs/superpowers/plans
diff options
context:
space:
mode:
Diffstat (limited to 'docs/superpowers/plans')
-rw-r--r--docs/superpowers/plans/2026-08-03-post-0.1.0-usability-closed.md46
-rw-r--r--docs/superpowers/plans/2026-08-03-post-0.1.0-usability.md45
2 files changed, 47 insertions, 44 deletions
diff --git a/docs/superpowers/plans/2026-08-03-post-0.1.0-usability-closed.md b/docs/superpowers/plans/2026-08-03-post-0.1.0-usability-closed.md
index 6613059..bcb6431 100644
--- a/docs/superpowers/plans/2026-08-03-post-0.1.0-usability-closed.md
+++ b/docs/superpowers/plans/2026-08-03-post-0.1.0-usability-closed.md
@@ -10232,3 +10232,49 @@ sends, and asserts the row arrives with no further gesture: no second
against the defect. Mutation-checked by disabling the connection, which fails
on the row count.
+## 101. Sync is account-aware for edits but not for the account the user is looking at
+
+**Done 2026-09-08.** The user chose BOTH halves the entry offered, and then
+narrowed the first one: not a second action beside Sync, but the existing Sync
+made account-aware. "If 'All Accounts' is selected, Sync works as today, if
+'work' is selected, hitting Sync works only for 'work'."
+
+**What was built.** `pendingSyncChannels()` now reads the account dropdown as
+well as `m_editedAccounts`, and the two are a UNION rather than one replacing
+the other. That union is the whole safety property and is the constraint the
+original entry named: looking at one account while having edited another is
+ordinary, and a run that dropped the edited account's channel would strand that
+write with nothing on screen to say so. All accounts is the empty key and
+narrows nothing, so a full fetch is still what an unselected window asks for,
+which is what keeps item 49's reasoning intact. The existing fallback survives
+untouched: an account whose section names no channel still widens the run to
+everything rather than being silently skipped.
+
+The visibility half is `syncStartedText()`, called from `setSyncBusy()`. A run
+used to open with "Syncing..." whether it covered one account or all of them,
+which is precisely the invisibility the entry complained about; it now reads
+"Syncing all accounts..." or "Syncing work-channel, personal-channel...". The
+exit paths pass no channels and overwrite the label with their own wording
+immediately, so the parameter is defaulted rather than threaded through them.
+
+**Four tests**, three on the channel resolution and one on the generated
+string. `syncNarrowsToTheSelectedAccount` asserts the list is EMPTY before the
+gesture, which matters more than it looks: empty is what a full fetch looks
+like, so a test starting from a narrowed state could not tell the fix from a
+window that had never widened. `aNarrowedSyncStillCarriesAnEditFromAnotherAccount`
+is the union, and it is the one that fails under the plausible wrong
+implementation. `theStatusLineNamesWhatASyncWillCover` asserts on the generated
+string rather than on a label after a real run, which would be a test of
+QProcess timing.
+
+Mutation-checked twice: ignoring the selection fails all three channel tests,
+and replacing the pending set instead of unioning with it fails the third one
+alone. That second mutation is the one worth having, since it is the version
+that looks correct and loses a write.
+
+**One thing deliberately not done.** The separator in the channel list is a
+plain `", "`, not a translated string. `lupdate` picked it up as translatable
+when it was written with `tr()`, and a comma joins a list the same way in
+Italian; a translatable separator is a string for a translator to get wrong for
+no gain.
+
diff --git a/docs/superpowers/plans/2026-08-03-post-0.1.0-usability.md b/docs/superpowers/plans/2026-08-03-post-0.1.0-usability.md
index 681200e..47c46fb 100644
--- a/docs/superpowers/plans/2026-08-03-post-0.1.0-usability.md
+++ b/docs/superpowers/plans/2026-08-03-post-0.1.0-usability.md
@@ -167,7 +167,7 @@ taking that too literally.
| 98 | "Important" adds the tag but cannot remove it, unlike every other toggle | defect | XS | **done** 2026-08-17, unreleased. Calls `everySelectedRowHasTag()`, as the entry required. Its reply test needed THREE different states (list-first thread, the reply's own thread, the reply) before it could tell the two wrong answers apart; with the reply defaulted to its thread's state the item 105 mutation stayed green, measured |
| 99 | The unread action is labelled "Toggle unread" whichever way it will go | presentation | S | **done 2026-08-25**, unreleased, with 112: the user's note is ONE design across both. The label names the direction it will go, and the entry is hidden on a selection with no single state. `refreshUnreadAction()` reads the new three-valued `selectionTagPresence()` |
| 100 | The message pane offers Back, Forward, Reload and Save page, none of which mean anything | defect | XS | **done** 2026-08-17, unreleased. `MessageView::removeBrowserActions()` filters the standard menu by `pageAction()` POINTER, never by text; `ViewSource` went with them, and stranded separators are swept |
-| 101 | Sync is account-aware for edits but not for the account the user is looking at | workflow | S | open; item 49 built the edit half deliberately. Needs a decision, see the entry |
+| 101 | Sync is account-aware for edits but not for the account the user is looking at | workflow | S | **done 2026-09-08**, unreleased. The user chose both halves the entry offered and narrowed the first: no second action, the existing Sync reads the account dropdown. Selected account narrows the run, All accounts is a full fetch as before, and the edited accounts are a UNION with the selection so a narrowed run cannot strand a write. The status line names what a run covers. See the closed entry |
| 102 | The rules table shows no note, so the field explaining a rule is invisible until it is opened | workflow | XS | **done** 2026-08-17, unreleased. A Note column before `ColumnCount`, so the appended Matches column stays last. Found a second defect on the way: `restoreState` REFUSES a header state with a different column count, and the sized flags were being set regardless |
| 103 | What Delete does to mail on the server is undocumented and unverified | clarification | S+M | done; Delete moves to the account trash, with Restore and a stranded-mail cleanup. Section in the closed file |
| 104 | Mail visible in Thunderbird never reaches qtmaildir | defect | XS | **done 2026-08-25**, hand-tested. The worker never reopened its read-only notmuch handle, so no query saw mail indexed after startup. Confirmed on a sync run from the application that added 20 messages: they appeared without a restart |
@@ -484,49 +484,6 @@ literals `lupdate` can see; a string built by concatenation is not translatable.
**Size: S.** Mostly the mixed-selection and toolbar decisions, not the code.
-## 101. Sync is account-aware for edits but not for the account the user is looking at
-
-**Observed (user, from the notes):** "sync button should be account-aware."
-
-**Cause (verified in the code).** `MainWindow::pendingSyncChannels()`
-(`src/mainwindow.cpp:3550`) resolves channels from `m_editedAccounts`, the set of
-accounts the user has made EDITS in, and from nothing else. The account dropdown
-is not consulted. With nothing pending it returns empty on purpose, and
-`mailsync.sh` turns that into `mbsync -a`, every channel.
-
-**Item 49 built exactly this and the reasoning still holds.** The comment states
-it: with nothing pending the run is a FETCH, and narrowing a fetch to wherever
-the last edit happened would "quietly stop collecting mail everywhere else".
-Fetching is global by nature; carrying edits is not.
-
-**So this needs a decision, not a fix.** The note does not say which of two
-things the user means, and they are different features:
-
-*Sync only the selected account, on demand.* A deliberate "sync this account"
-that ignores the pending set, presumably beside the existing Sync rather than
-replacing it. Useful when one account is slow and the user wants their mail from
-another one now. The risk is the one item 49 named: a button that looks like
-Sync and quietly does not collect the rest of the mail.
-
-*Show which accounts a sync will cover.* No behaviour change at all, just making
-the existing account-awareness visible, since today the user cannot tell whether
-a run is narrowed or full. The status bar already names each channel as mbsync
-reaches it (item 42), so most of this exists.
-
-**Constraints.**
-
-- The account dropdown is a VIEW filter. Making it also steer sync couples two
- things the user may reasonably want apart: looking at one account while
- fetching all of them is the normal case, not an edge case.
-- Whatever narrows a run must still carry every pending edit, or an edit is
- stranded with nothing on screen to say so. `pendingSyncChannels()` already
- falls back to a full sync when it cannot resolve a channel for an edited
- account, and that safety must survive.
-- An account with no `[account.<key>]` section, or one whose section names no
- channel, has no channel to sync. The fallback covers it today.
-
-**Size: S** for the on-demand button, XS for the visibility half. Ask which.
-
## 113. No way to see a message's HTML source
**Observed (user, 2026-08-17):** reviewing item 100's removals, "view source