Skip to content

Move stale tests to current API owners - #1169

Merged
trissim merged 2 commits into
mainfrom
fix/tests-follow-api-owners
Oct 23, 2026
Merged

trissim merged 2 commits into
mainfrom
fix/tests-follow-api-owners

Conversation

@trissim

@trissim trissim commented Oct 23, 2026 •

Copy link
Copy Markdown

These tests still called APIs that their owners renamed or removed. Update them directly and delete the duplicate Core coordination-snapshot test: 8 insertions, 25 deletions across five test files. No source changes; the welcome-view tests and retirement failures remain evidence only.

Changes at d30fd1e:

  • Delete tests/model/test_coordination_snapshot.py. Core owns viewer_snapshot equality and pending_counts_opened.
  • Queue scope: claimed_identity.
  • Conversation: compare NavigationTarget values; read revision from page_source.
  • Four transcript publication calls: synchronous received(page), with no replacement forwarder.

Validation: no tests run. This command produces no output (exit 1):

git grep -nE "coordination_snapshot|claim_scope|navigation_target_name|transcript\.snapshot\(|history\.revision" -- tests

The channel, DM and feed constructors correspond to ChannelTarget, DirectTarget and FeedTarget in navigation_target.py:151-174; the screen uses the same HistoryRoute declarations through :114-116. UI equality assertions await the review run; no screen comparison was executed here.

Read-only findings (Toad source base 96ab9fe, Core display/observation declarations read at 01aa67d87; existing failure log /home/ts/.claude/jobs/47220aa9/tmp/drift-run.log):

B1(a): Core ViewReading.read (ui_model/observation.py:873-879) emits ViewsRetired. Toad CoordinationAccess.views_retired (comms_root.py:464-466) calls SessionNavigation.views_retired (session_navigation.py:209-229), which schedules close_many at :227 rather than removing the view synchronously. SidebarObserved independently replaces references at comms_root.py:411 and presents at :412. A paint can therefore still reach the deleted peer through workspace_sessions.py:232. close_many also awaits tab_order.close at :446 before deleting membership at :449-453, and awaits return_to at :459 before removing the mounted view at :462. TargetTree.session_selected still resolves the previous mode at widgets/sidebar_tree.py:902-905. The existing KeyError stack is specifically a paint: selection.py:66 -> comms_sidebar.py:195 -> sidebar_tree.py:877 -> workspace_sessions.py:130,232 -> screens/comms.py:92 -> navigation_target.py:116 -> conversation_kind.py:247 -> Core display_references.py:218. It does not enumerate every mounted view.

B1(b): All three direct CurrentDisplayReferences.thread callers in Toad:

  • conversation_kind.py:247, DmConversation.destination: retained peer survives until DM view retirement. Its consumers include navigation_target.py:116, ConversationKind.label :84-85, DM unread :265-266, historical_sessions :255-256 and activity_members :120-125.
  • widgets/session_details.py:176, ConversationSessionDetails._on_collapsible_title_toggle: retained self.peer, but fresh global references at :173. A click on a retiring row can therefore name a removed birth.
  • widgets/channel_activity.py:66, ChannelActivity.update_row: peers and references both come from model_state.shown (:42-47,64). KeyedRows.reconcile_keys removes keys outside wanted before update_row (widgets/sidebar_tree.py:199-215). This caller can describe an incarnation deleted since that snapshot, but does not itself mix an old key with the new registry; no missing-key path is demonstrated here.
    Core's other .thread(...) call (history_views.py:465) is a different target method, not CurrentDisplayReferences.thread.

B1(c): The log records separate futures, not one serial failure stack. The self-wait is transcript_source_preparation.py:406-415 (cancel_node then join every worker); WorkingTranscript.execute calls source_failed within its worker at transcript_state.py:405-407, and source_failed retires at transcript_source_preparation.py:132. The closed-transcript failure is close_many :459 -> HistorySessionEntry.return_to :298 -> workspace_sessions.select :204 -> MainScreen._prepare_content :333 -> native.activate (session_presentation.py:450) -> acquire :374 -> TranscriptPresentation.bind :789. close() sets closed at transcript_publication.py:934; bind refuses it at :788-789. The saved log does not identify which close() invocation closed that owner, so it does not prove these are one retirement operation or that the self-wait caused the closed transcript. App teardown can also close all owner presentations at workspace_sessions.py:259-263.

B2:

  • Opening a thread elsewhere: welcome.py:197 selects NewSessionButton through workspace_sessions.py:212-214. Down traverses TargetTree.move_cursor/focus_row (widgets/sidebar_tree.py:923-937). WelcomeThreads constructs ThreadStatusRow at welcome.py:150-151, not ThreadRow. tests/support/ui.py:255-257 returns the actual class name; the test waits for ThreadRow. Source change 259cfba removed ThreadRow from welcome; b9bfde3 made the replacement ThreadStatusRow. This is stale test identity, not evidence that scribe is absent.
  • Closing the last tab: declared initial focus is the same welcome NewSessionButton; n is bound on WelcomeScreen (welcome.py:199-200), whose handler :269-270 invokes NewThreadAction. application_actions.py:49-68 prepares the Core creation action; thread_actions.py:135-146 opens CommandDialog, not a tab. Commit 4ecc7a2 replaced direct SessionCreate with Core creation/form collection; 8527daa changed the welcome handler to NewThreadAction. The test never submits a form. Its instant-tab expectation is stale. However the saved failure screen contains no dialog and records no focused widget: the exact receiver of that failed n is not proven by this log. Do not treat the form-path mismatch as a reproduction of that key-routing failure.
  • Named launch: no key is pressed and the test body never begins; tests/support/workspace.py:94 is still entering run_test. ApplicationLifetime.start :157-164 reads the named existing thread via launch_navigation :172-177 and ThreadNavigationRequest.read :147-148 (snapshot.require). The test supplies the string saved-session but never declares that thread or a saved session; Workspace.init only creates an empty wire (tests/support/workspace.py:23-30). Commit 1b19aea replaced direct native resume with declared-thread navigation. The fixture expectation is stale; the timeout itself does not prove which startup await is stalled or a focused widget. No new run was made to obtain that missing observation.

No last-passing run SHA was supplied. These are the source commits that changed the assumptions, not invented claims that a historical test run passed. The welcome tests moved from tests/app to tests/textual in 8da6f2b after those changes.

Assumed: the supplied drift-run.log is the run described in the order; source-only inspection cannot recover an unlogged focused widget, the exact stalled startup await, or the closer of the owner transcript. The reviewer runs the six files. No section-B edits.

@trissim
trissim marked this pull request as ready for review October 23, 2026 21:48
Copilot AI balanced review requested due to automatic review settings October 23, 2026 21:48

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copilot was unable to review this pull request because the user who requested the review has insufficient remaining quota.

An organization owner can choose the repository organization as the billing source for reviews requested by members with a paid Copilot license. Learn about Copilot code review billing.

@trissim
trissim merged commit f9aa367 into main Oct 23, 2026
3 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants