Skip to content

Fix stale anchor preserved when clearing transient nodes#14251

Merged
lukasmasuch merged 2 commits intodevelopfrom
lukasmasuch/fix-stale-transient-anchor
Mar 11, 2026
Merged

Fix stale anchor preserved when clearing transient nodes#14251
lukasmasuch merged 2 commits intodevelopfrom
lukasmasuch/fix-stale-transient-anchor

Conversation

@lukasmasuch
Copy link
Copy Markdown
Collaborator

@lukasmasuch lukasmasuch commented Mar 6, 2026

Describe your changes

Fixes a regression introduced in #13849 where stale elements from previous script runs could persist after spinner completion.

Root cause: When a transient node (spinner) captured an element from a previous run as its anchor, and the transient was cleared, the anchor was restored directly without checking if it was stale.

The fix: Change return node.anchor to return node.anchor.accept(this) so the anchor is also checked for staleness before being restored.

GitHub Issue Link (if applicable)

Closes #14249

Testing Plan

  • Unit tests: Added test case for stale anchor scenario
  • Manual testing: Verified fix using reproduction steps from issue
Agent metrics
Type Name Count
subagent fixing-pr 1

When a transient node (spinner) captured an element from a previous run
as its anchor, and the transient was cleared, the anchor was restored
directly without checking if it was stale. This caused UI elements from
previous runs to incorrectly persist after spinner completion.

The fix checks if the anchor is stale before restoring it by calling
`node.anchor.accept(this)` instead of returning `node.anchor` directly.

Closes #14249
@lukasmasuch lukasmasuch added change:bugfix PR contains bug fix implementation impact:users PR changes affect end users labels Mar 6, 2026
Copilot AI review requested due to automatic review settings March 6, 2026 18:57
@lukasmasuch lukasmasuch added change:bugfix PR contains bug fix implementation impact:users PR changes affect end users labels Mar 6, 2026
@snyk-io
Copy link
Copy Markdown
Contributor

snyk-io bot commented Mar 6, 2026

Snyk checks have passed. No issues have been found so far.

Status Scanner Critical High Medium Low Total (0)
Open Source Security 0 0 0 0 0 issues
Licenses 0 0 0 0 0 issues

💻 Catch issues earlier using the plugins for VS Code, JetBrains IDEs, Visual Studio, and Eclipse.

@github-actions
Copy link
Copy Markdown
Contributor

github-actions bot commented Mar 6, 2026

✅ PR preview is ready!

Name Link
📦 Wheel file https://core-previews.s3-us-west-2.amazonaws.com/pr-14251/streamlit-1.55.0-py3-none-any.whl
📦 @streamlit/component-v2-lib Download from artifacts
🕹️ Preview app pr-14251.streamlit.app (☁️ Deploy here if not accessible)

Copy link
Copy Markdown
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

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

Pull request overview

Fixes a frontend render-tree regression where clearing a transient node (e.g., spinner) could restore an anchor element from a previous script run without re-checking whether that anchor is stale, causing unexpected “old” UI content to reappear.

Changes:

  • Update ClearStaleNodeVisitor.visitTransientNode to restore a cleared transient’s anchor via anchor.accept(this) so the anchor is also filtered for staleness.
  • Adjust and extend unit tests to cover the “cleared transient with stale anchor” scenario.

Reviewed changes

Copilot reviewed 2 out of 2 changed files in this pull request and generated 1 comment.

File Description
frontend/lib/src/render-tree/visitors/ClearStaleNodeVisitor.ts Ensures restored transient anchors are also visited/filtered for staleness before being returned.
frontend/lib/src/render-tree/visitors/ClearStaleNodeVisitor.test.ts Updates the existing “restore anchor” test and adds coverage for stale-anchor restoration returning undefined.

@lukasmasuch lukasmasuch added the ai-review If applied to PR or issue will run AI review workflow label Mar 6, 2026
@github-actions github-actions bot removed the ai-review If applied to PR or issue will run AI review workflow label Mar 6, 2026
@github-actions
Copy link
Copy Markdown
Contributor

github-actions bot commented Mar 6, 2026

Summary

This PR fixes a regression (from #13849) where clearing a transient node (e.g., a spinner) could restore a stale anchor element from a previous script run. The root cause was that ClearStaleNodeVisitor.visitTransientNode() returned node.anchor directly without checking whether the anchor itself was stale. The fix changes return node.anchor to return node.anchor.accept(this), recursively delegating staleness validation to the same visitor pattern used by all other node types.

Files changed (2):

  • frontend/lib/src/render-tree/visitors/ClearStaleNodeVisitor.ts — 1 functional line change + 2 comment lines
  • frontend/lib/src/render-tree/visitors/ClearStaleNodeVisitor.test.ts — 1 test corrected + 1 new test added

Code Quality

Reviewers agreed unanimously: The fix is minimal, surgical, and idiomatic. It leverages the existing visitor pattern — node.anchor.accept(this) delegates staleness checking to the same visitor methods (visitElementNode, visitBlockNode, visitTransientNode) that handle all other nodes. No new abstractions or complexity were introduced.

The added comments at lines 144-147 clearly explain the non-obvious reasoning for why the anchor must be checked for staleness, which both reviewers found appropriate.

Test Coverage

Reviewers agreed that the unit test changes are well-structured:

  • The existing test was corrected — it previously validated the buggy behavior (asserting a stale anchor would be returned). It now uses currentRunId for the anchor, testing the valid case.
  • A new regression test explicitly verifies the fix: a stale anchor is properly filtered out, returning undefined.

Minor point of divergence on E2E coverage: One reviewer (gpt-5.3-codex-high) suggested an optional follow-up E2E test, while the other (opus-4.6-thinking) noted existing E2E coverage. Verification confirms that test_simple_transient_spinner_does_not_leave_stale_elements in e2e_playwright/appnode_hierarchy_test.py already exercises the user-facing scenario from issue #14249. Additional E2E tests are not necessary for this change.

Backwards Compatibility

Reviewers agreed: Fully backwards compatible. The previous behavior (returning stale anchors) was a bug, not a feature. No API changes, no protobuf changes, and no changes to the public st.* interface.

Security & Risk

Reviewers agreed: No security concerns. The change is entirely within the frontend render tree visitor logic and does not touch WebSocket handling, authentication, session management, file operations, CORS, or any external-facing surface. Regression risk is low and localized.

External test recommendation

  • Recommend external_test: No
  • Triggered categories: None
  • Confidence: High
  • Both reviewers independently reached the same conclusion.

Accessibility

Reviewers agreed: No UI changes, no new components, no DOM structure modifications. Accessibility is not impacted.

Recommendations

No blocking changes requested by either reviewer. The only suggestion was an optional E2E follow-up (gpt-5.3-codex-high), which was resolved by confirming existing E2E coverage already addresses the scenario.

Missing Reviews

All expected models submitted reviews:

  • gpt-5.3-codex-high: Submitted (APPROVED)
  • opus-4.6-thinking: Submitted (APPROVED)

Verdict

APPROVED: Both reviewers unanimously approved. The fix is a clean, minimal one-line change that correctly addresses a regression in transient node staleness checking, with proper unit test coverage and existing E2E coverage for the user-facing scenario. No blocking quality, compatibility, or security concerns were raised.


This is a consolidated AI review by opus-4.6-thinking. It synthesizes reviews from: gpt-5.3-codex-high, opus-4.6-thinking.


📋 Review by `gpt-5.3-codex-high`

Summary

This PR fixes a regression where clearing a transient node (for example, a spinner) could restore a stale anchor element from a previous script run. The core change in frontend/lib/src/render-tree/visitors/ClearStaleNodeVisitor.ts now re-runs stale filtering on the anchor before restoration, and the test suite adds coverage for both current and stale anchor cases.

Code Quality

The implementation is minimal and targeted, with good locality and clear intent:

  • frontend/lib/src/render-tree/visitors/ClearStaleNodeVisitor.ts:153 changes return node.anchor to return node.anchor.accept(this), which aligns behavior with the visitor's stale-node contract.
  • frontend/lib/src/render-tree/visitors/ClearStaleNodeVisitor.ts:144-147 adds explanatory comments documenting the stale-anchor edge case.
  • frontend/lib/src/render-tree/visitors/ClearStaleNodeVisitor.test.ts:270-295 adds explicit positive/negative test cases for current vs stale anchors.

No maintainability or pattern concerns found.

Test Coverage

Unit coverage for the modified behavior is good:

  • The existing "anchor restored" test is preserved for a current-run anchor.
  • A new regression test verifies stale anchors are dropped when a transient is cleared in the current run.

E2E coverage was not added in this PR. Given the change is in internal render-tree stale filtering and is now directly unit-tested at the decision point, this is acceptable; residual risk is low but non-zero for full UI flow interactions.

Backwards Compatibility

No public API changes or protocol changes were introduced. The behavior change is corrective (removing stale UI artifacts) and should be backwards compatible for users relying on expected rerun semantics.

Security & Risk

No security-sensitive surfaces were modified (no auth/session, transport, routing, storage, CSP/CORS, upload/asset handling, or dynamic code execution changes). Regression risk appears low and localized to transient-node cleanup behavior.

External test recommendation

  • Recommend external_test: No
  • Triggered categories: None
  • Key evidence from changed files:
    • frontend/lib/src/render-tree/visitors/ClearStaleNodeVisitor.ts: internal render-tree visitor logic only; no external hosting/embedding/network boundary behavior touched.
    • frontend/lib/src/render-tree/visitors/ClearStaleNodeVisitor.test.ts: unit tests only, focused on stale-node filtering behavior.
  • Suggested external test focus areas: None required for this patch.
  • Confidence: High
  • Assumptions and gaps: Assessment is based on the two-file diff only; no hidden runtime-path changes outside this PR.

Accessibility

No UI component markup, keyboard interaction, ARIA semantics, or focus behavior changed. No accessibility concerns identified.

Recommendations

  1. Optional follow-up: add an e2e regression test reproducing the issue scenario (transient spinner + tab/section switching) to guard against future integration regressions across render-tree updates.

Verdict

APPROVED: The fix addresses the reported root cause with targeted code and solid unit regression coverage, with no blocking quality, compatibility, or security concerns.


This is an automated AI review by gpt-5.3-codex-high. Please verify the feedback and use your judgment.

📋 Review by `opus-4.6-thinking`

Summary

This PR fixes a regression introduced in #13849 where stale elements from previous script runs could persist after spinner (transient node) completion. The root cause was that ClearStaleNodeVisitor.visitTransientNode() returned a transient node's anchor directly when the transient was cleared in the current run, without checking whether the anchor itself was stale. The fix changes return node.anchor to return node.anchor.accept(this) so the anchor is recursively validated for staleness.

Only two files are changed:

  • frontend/lib/src/render-tree/visitors/ClearStaleNodeVisitor.ts (1 functional line change + 2 comment lines)
  • frontend/lib/src/render-tree/visitors/ClearStaleNodeVisitor.test.ts (1 test corrected + 1 new test added)

Code Quality

The fix is minimal, surgical, and idiomatic. It leverages the existing visitor pattern — node.anchor.accept(this) delegates staleness checking to the same visitor that already handles ElementNode, BlockNode, and TransientNode, so the behavior is consistent regardless of anchor type. No new abstractions or complexity introduced.

The updated comments at lines 144-147 of ClearStaleNodeVisitor.ts clearly explain why the anchor must be checked for staleness, which is appropriate for non-obvious logic.

The test changes are well-structured:

  • The existing test (line 270) was correctly updated — it previously asserted that a stale anchor ("old_run") would be returned, which was actually validating the buggy behavior. It now uses currentRunId for the anchor, testing the valid case.
  • The new test (line 281) explicitly verifies the bug fix scenario: a stale anchor is properly filtered out, returning undefined.

Test Coverage

Unit tests: The new test at line 281-295 directly covers the regression scenario. Together with the corrected existing test, both positive (current anchor restored) and negative (stale anchor filtered) paths are covered for the early-return branch.

E2E tests: The existing E2E test test_simple_transient_spinner_does_not_leave_stale_elements in e2e_playwright/appnode_hierarchy_test.py exercises the exact user-facing scenario from issue #14249 — a spinner wrapping content, followed by a rerun without a spinner, verifying no stale elements remain. Additional E2E tests cover complex and chat-based transient spinner scenarios. No new E2E tests are needed.

The test coverage is adequate for this change.

Backwards Compatibility

This change is fully backwards compatible. The previous behavior (returning stale anchors) was a bug, not a feature. There are no API changes, no protobuf changes, and no changes to the public st.* interface. The fix restores the correct semantic: stale elements should never survive a stale-clearing pass.

Security & Risk

No security concerns. The change is entirely within the frontend render tree visitor logic and does not touch:

  • WebSocket handling, authentication, or session management
  • File upload/download, asset serving, or path traversal
  • Cookies, XSRF, CORS, or security headers
  • External dependencies, runtime JS execution, or command injection
  • HTML/Markdown rendering or sanitization

Regression risk is low. The accept(this) call delegates to the same well-tested visitor methods (visitElementNode, visitBlockNode, visitTransientNode) that handle all other nodes in the tree. The only behavioral change is in the specific code path where a transient node is cleared in the current run and has an anchor — previously the anchor was returned unchecked, now it is validated.

External test recommendation

  • Recommend external_test: No
  • Triggered categories: None
  • Evidence:
    • ClearStaleNodeVisitor.ts: Internal render tree visitor logic only; no routing, auth, embedding, asset serving, CORS, storage, or security header changes.
    • ClearStaleNodeVisitor.test.ts: Unit test changes only.
  • Suggested external_test focus areas: N/A
  • Confidence: High
  • Assumptions and gaps: None. This is a pure frontend render tree management fix with no external integration surface.

Accessibility

No UI changes, no new components, and no DOM structure modifications. This fix only affects which render tree nodes survive the stale-clearing pass. Accessibility is not impacted.

Recommendations

No changes requested. The fix is correct, minimal, well-tested, and follows existing patterns.

Verdict

APPROVED: A clean, minimal one-line fix for a regression in transient node staleness checking, with proper unit test coverage and existing E2E test coverage for the user-facing scenario.


This is an automated AI review by opus-4.6-thinking.

Add unit test to verify that a stale anchor without fragmentId is
preserved during a fragment run when the transient node is cleared.
This addresses a review comment requesting explicit coverage for the
fragment-run edge case to prevent regressions.
@lukasmasuch lukasmasuch added the ai-review If applied to PR or issue will run AI review workflow label Mar 6, 2026
@github-actions github-actions bot removed the ai-review If applied to PR or issue will run AI review workflow label Mar 6, 2026
@github-actions
Copy link
Copy Markdown
Contributor

github-actions bot commented Mar 6, 2026

Summary

This PR fixes a regression (from #13849) in transient-node cleanup where stale elements from previous script runs could persist after spinner completion. The root cause was in ClearStaleNodeVisitor.visitTransientNode: when a transient node was explicitly cleared in the current run, its anchor was restored directly via return node.anchor without checking whether the anchor itself was stale. The fix changes this to return node.anchor.accept(this), ensuring the anchor passes through the same staleness-checking visitor logic applied everywhere else.

The change is a single-line fix in ClearStaleNodeVisitor.ts with three well-targeted unit tests added in ClearStaleNodeVisitor.test.ts.

Reviewer agreement: Both gpt-5.3-codex-high and opus-4.6-thinking independently arrived at APPROVED with no blocking issues. Their analyses are fully aligned across all review dimensions.

Code Quality

The fix is minimal, precise, and follows the established visitor pattern. Replacing return node.anchor with return node.anchor.accept(this) makes the early-return path consistent with the general path (which already calls node.anchor?.accept(this)). The updated comment on lines 146-147 clearly explains the reasoning behind the additional check.

Both reviewers confirmed no code quality issues. No disagreements.

Test Coverage

Unit coverage is strong and well-targeted:

  1. Happy path: Anchor from the current run is correctly restored when transient is cleared (existing test updated to use currentRunId for the anchor, correcting an inadvertent reliance on buggy behavior).
  2. Bug fix regression test: Stale anchor returns undefined when transient is cleared — directly covers the reported issue.
  3. Fragment edge case: During a fragment run, a stale anchor without fragmentId is preserved (consistent with visitElementNode behavior).

Both reviewers noted the absence of an e2e test for the exact reproduction scenario from #14249 (segmented control + cached function with spinner + tabs). Both agreed this is acceptable given the direct unit-level coverage of the buggy code path, and recommended it as an optional future hardening step.

Backwards Compatibility

No public API or protocol changes. The behavior change is corrective: stale anchors that were previously (incorrectly) retained are now filtered out, aligning with expected stale-node semantics. Both reviewers agreed this is fully backwards compatible.

Security & Risk

No security-sensitive surfaces were modified. The change is entirely within frontend render-tree visitor logic — no auth, session, websocket, routing, CORS/CSP/XSRF, file handling, or external service paths were touched. Regression risk is low due to the minimal logic delta and targeted unit tests.

Both reviewers agreed. No disagreements.

External test recommendation

  • Recommend external_test: No
  • Triggered categories: None
  • Confidence: High — the code path is entirely client-side with no external dependencies.

Both reviewers agreed. No disagreements.

Accessibility

No accessibility impact. The change only affects which elements are included in or excluded from the render tree (stale element cleanup). No UI components, ARIA attributes, focus management, or keyboard handling were modified.

Both reviewers agreed. No disagreements.

Reviewer Consensus

Dimension gpt-5.3-codex-high opus-4.6-thinking Agreement
Code Quality No issues No issues Full
Test Coverage Strong, optional e2e Strong, optional e2e Full
Backwards Compat Fully compatible Fully compatible Full
Security & Risk Low risk Low risk Full
External Tests Not needed Not needed Full
Accessibility No impact No impact Full
Verdict APPROVED APPROVED Full

Missing reviews: None. Both expected models (gpt-5.3-codex-high and opus-4.6-thinking) completed their reviews.

Recommendations

  1. Optional: Consider adding an e2e test for the exact reproduction scenario from UI element appearing unexpectedly since v1.55.0 #14249 (segmented control + cached function with spinner + tabs) to serve as an end-to-end regression guard. Not a blocker.

Verdict

APPROVED: Both reviewers unanimously approved. The fix is a clean, minimal one-line change that correctly applies staleness checking to transient node anchors, with well-targeted unit tests covering the fix and relevant edge cases. No blocking or critical issues were raised.


This is a consolidated AI review by opus-4.6-thinking, synthesizing reviews from gpt-5.3-codex-high and opus-4.6-thinking.


📋 Review by `gpt-5.3-codex-high`

Summary

This PR fixes a stale-render regression in transient-node cleanup by ensuring a cleared transient's anchor is also passed through stale-node filtering before restoration. The implementation change in frontend/lib/src/render-tree/visitors/ClearStaleNodeVisitor.ts is small and focused, and the accompanying test updates in frontend/lib/src/render-tree/visitors/ClearStaleNodeVisitor.test.ts cover both the reported stale-anchor case and a fragment-run edge case.

Code Quality

The code change is precise and follows existing visitor patterns: replacing direct anchor return with node.anchor.accept(this) ensures consistent staleness handling across node types. Test additions are clear, scenario-driven, and improve maintainability by documenting expected transient/fragment behavior.

No code quality issues were identified.

Test Coverage

Unit coverage is strong for this fix:

  • Adds a regression test for a stale anchor on a cleared transient (expects undefined).
  • Preserves behavior coverage for current-run anchor restoration.
  • Adds explicit fragment-run coverage where an anchor without fragmentId should remain preserved.

No e2e tests were added. Given the tightly scoped render-tree visitor logic and direct unit-level regression coverage, this is acceptable for this PR, though a future user-flow e2e around spinner clear behavior could further harden against integration regressions.

Backwards Compatibility

No public API or protocol changes are introduced. Behavior change is corrective: stale anchors that were previously (incorrectly) retained are now filtered, aligning with expected stale-node semantics. This should be backwards compatible for users and reduces unintended stale UI persistence.

Security & Risk

No security-sensitive surfaces were modified (no auth/session, websocket transport, routing, cookies/XSRF, asset serving, external networking, or dynamic code execution changes). Regression risk appears low due to:

  • Minimal logic delta in a single branch.
  • Added targeted unit tests for both main regression and edge-case behavior.

External test recommendation

  • Recommend external_test: No
  • Triggered categories: None
  • Evidence:
    • frontend/lib/src/render-tree/visitors/ClearStaleNodeVisitor.ts: Internal render-tree stale filtering logic only; no routing/auth/websocket/embed/cross-origin/storage/security-header paths changed.
    • frontend/lib/src/render-tree/visitors/ClearStaleNodeVisitor.test.ts: Unit-test-only additions validating transient/fragment stale-node behavior.
  • Suggested external_test focus areas:
    • No additional @pytest.mark.external_test coverage is required for this branch.
    • Optional future hardening: a non-external e2e regression flow around spinner/transient clear to validate end-user behavior.
  • Confidence: High
  • Assumptions and gaps: Assessment is based on the PR diff (two frontend files) and assumes no related runtime behavior changes exist outside this branch.

Accessibility

No accessibility-impacting UI markup, interaction handlers, semantics, focus behavior, or styling were changed. A11y risk is effectively none for this PR scope.

Recommendations

  1. Optional: add a focused e2e regression test for spinner/transient anchor cleanup in a realistic app flow to complement the existing unit coverage.

Verdict

APPROVED: The fix is targeted, regression-tested at unit level, low risk, and ready to merge.


This is an automated AI review by gpt-5.3-codex-high. Please verify the feedback and use your judgment.

📋 Review by `opus-4.6-thinking`

Summary

This PR fixes a regression introduced in #13849 where stale elements from previous script runs could persist after spinner (transient node) completion. The root cause was in ClearStaleNodeVisitor.visitTransientNode: when a transient node was explicitly cleared in the current run, its anchor was restored directly via return node.anchor without checking whether the anchor itself was stale. The fix changes this to return node.anchor.accept(this) so the anchor passes through the same staleness-checking visitor logic.

The change is a single-line fix in ClearStaleNodeVisitor.ts with three well-targeted unit tests.

Code Quality

The fix is minimal, precise, and follows the established visitor pattern already used elsewhere in the same file. Specifically:

  • Line 153 of ClearStaleNodeVisitor.ts: return node.anchor.accept(this) is consistent with how the anchor is handled in the non-early-return path (line 157: const anchorNode = node.anchor?.accept(this)). The early-return path was the only place that skipped the staleness check.
  • The updated comment on lines 146-147 clearly explains the reasoning behind the additional check.
  • The test file changes are well-structured with descriptive test names and useful inline comments explaining each scenario.

The pre-existing test ("restores anchor for transient cleared in current run") was correctly updated to use currentRunId for the anchor, since the old test was inadvertently relying on the buggy behavior (returning a stale anchor without checking).

Test Coverage

Unit tests are good and cover the critical code paths:

  1. Happy path (line 270): Anchor from the current run is correctly restored when transient is cleared.
  2. Bug fix path (line 281): Stale anchor is correctly filtered out (returns undefined) when transient is cleared — this is the core regression test.
  3. Fragment edge case (line 297): During a fragment run, a stale anchor without a fragmentId is preserved (not cleared), since visitElementNode intentionally keeps such elements during fragment runs.

E2E test coverage: While the existing st_spinner_test.py has extensive tests for spinner scenarios (including fragments, containers, and tabs), it does not have a test that exactly reproduces the #14249 scenario (segmented control switching + cached function with spinner between tab creation and content writing). However, this is a minor gap — the unit tests directly cover the buggy code path, and the existing e2e suite covers the broader spinner/transient behavior. Adding a dedicated e2e test for this specific scenario would further guard against future regressions in this area, but is not a blocker.

Backwards Compatibility

This change is fully backwards compatible. The previous behavior was a bug — stale elements were unintentionally preserved. Users affected by the regression (#14249) will see the correct behavior restored: elements from previous script runs will no longer "leak through" after spinner completion. There is no API surface change.

Security & Risk

No security concerns. The change is entirely within frontend render-tree visitor logic. It does not touch:

  • WebSocket/server endpoints, authentication, or session management
  • File handling, asset serving, or path traversal
  • CORS, CSP, XSRF, or cookie handling
  • HTML/Markdown rendering or sanitization
  • External services or dependencies
  • Runtime JavaScript execution (eval, Function(), etc.)

Regression risk is low. The fix makes the early-return path consistent with the general path that already calls node.anchor.accept(this). The only behavioral change is that stale anchors are now correctly filtered out instead of being incorrectly preserved.

External test recommendation

Recommendation: No@pytest.mark.external_test coverage is not needed.

  • Triggered categories: None
  • Key evidence: The change is purely in the frontend render-tree visitor (ClearStaleNodeVisitor.ts), which is internal logic for managing the DOM render tree. It does not involve external services, network requests, embedding, or any infrastructure that differs between local and external deployment.
  • Confidence: High. The code path is entirely client-side and has no external dependencies.

Accessibility

No accessibility impact. The change only affects which elements are included in or excluded from the render tree (stale element cleanup). It does not modify any UI components, ARIA attributes, focus management, or keyboard handling.

Recommendations

No blocking issues. One minor suggestion:

  1. Consider adding an e2e test for the exact reproduction scenario from UI element appearing unexpectedly since v1.55.0 #14249 (segmented control + cached function with spinner + tabs). This would serve as an end-to-end regression guard for this specific user-reported issue. The app script would look similar to the reproduction code in the issue. However, this is optional since the unit tests directly cover the buggy code path.

Verdict

APPROVED: Clean, minimal one-line bug fix that correctly applies staleness checking to transient node anchors, with well-targeted unit tests covering the fix and relevant edge cases.


This is an automated AI review by opus-4.6-thinking.

@lukasmasuch lukasmasuch requested a review from kmcgrady March 8, 2026 09:16
Copy link
Copy Markdown
Collaborator

@kmcgrady kmcgrady left a comment

Choose a reason for hiding this comment

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

The change feels reasonable. Perhaps we can confirm with the user. If there's anyway the AI could have caught this better, that would be great.

@lukasmasuch
Copy link
Copy Markdown
Collaborator Author

Checked it with the problematic issue.

If there's anyway the AI could have caught this better, that would be great.

Maybe with a bit more "architectural" information on how the frontend tree rendering works. But not sure if this would have caught it

@lukasmasuch lukasmasuch merged commit 7988856 into develop Mar 11, 2026
56 checks passed
@lukasmasuch lukasmasuch deleted the lukasmasuch/fix-stale-transient-anchor branch March 11, 2026 15:16
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

change:bugfix PR contains bug fix implementation impact:users PR changes affect end users

Projects

None yet

Development

Successfully merging this pull request may close these issues.

UI element appearing unexpectedly since v1.55.0

3 participants