Skip to content

[flutter_tools] Fix flakiness in widget_preview_detection_test#187938

Merged
auto-submit[bot] merged 5 commits into
flutter:masterfrom
bkonyi:fix-flutter-issue-187514
Jun 15, 2026
Merged

[flutter_tools] Fix flakiness in widget_preview_detection_test#187938
auto-submit[bot] merged 5 commits into
flutter:masterfrom
bkonyi:fix-flutter-issue-187514

Conversation

@bkonyi

@bkonyi bkonyi commented Jun 12, 2026

Copy link
Copy Markdown
Contributor

Description

Fixes flakiness in widget_preview_detection_test.dart by introducing a robust polling mechanism when querying DTD for previews.

Previously, the integration tests were flaking on slow CI environments because they queried DTD immediately after a file modification, without waiting for the background Dart Analysis Server to finish re-analyzing the changes. This led to stale (empty) preview results and assertion failures like Bad state: Preview was lost after modification!.

Changes

  • Introduced waitForPreviews Helper: Added a robust polling helper in widget_preview_test_helpers.dart that repeatedly queries DTD for previews until a user-specified predicate is met (or a 10-second timeout occurs).
  • Error Resilience: The helper gracefully ignores all Objects (including DTD connection issues, RPC errors, or temporary parsing errors) during the polling loop, as these are common transient states while the Analysis Server is re-analyzing.
  • Test Refactoring: Updated all four integration tests in widget_preview_detection_test.dart to use waitForPreviews with appropriate predicates (waiting for previews to be non-empty, empty, or containing specific updated content).
  • Documentation: Added comprehensive Dartdoc comments to the new public helper.

Related Issues

The integration tests in `widget_preview_detection_test.dart` were flaking
on slow CI environments because the test was querying DTD for previews
immediately after a file modification, without waiting for the background
Analysis Server to finish re-analyzing the change.

This patch introduces a robust `waitForPreviews` polling helper in the
integration test suite. This helper repeatedly queries DTD for previews
until a user-specified predicate is met (or a timeout occurs), and
gracefully handles temporary DTD or JSON RPC errors during the polling.

All tests in `widget_preview_detection_test.dart` have been updated to
use this helper, ensuring they wait for the expected state (e.g. preview
added, removed, or updated) before asserting.

Fixes flutter#187514
@flutter-dashboard flutter-dashboard Bot added the CICD Run CI/CD label Jun 12, 2026
@github-actions github-actions Bot added the tool Affects the "flutter" command-line tool. See also t: labels. label Jun 12, 2026

@gemini-code-assist gemini-code-assist Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Code Review

This pull request refactors the widget preview integration tests to use a new polling helper function, waitForPreviews, which waits for a specific preview condition to be met. Feedback on these changes suggests catching Exception instead of Object in the polling loop to avoid swallowing programming errors, and adding documentation comments to the new public helper function to comply with the repository style guide.

Comment thread packages/flutter_tools/test/integration.shard/widget_preview_test_helpers.dart Outdated
@github-actions github-actions Bot removed the CICD Run CI/CD label Jun 12, 2026
@flutter-dashboard flutter-dashboard Bot added the CICD Run CI/CD label Jun 12, 2026
@bkonyi bkonyi requested a review from jtmcdole June 12, 2026 18:40
if (previews.previews.isNotEmpty) {
throw StateError('Preview was still detected after deletion!');
}
await waitForPreviews(dtdConnection, (FlutterWidgetPreviews p) => p.previews.isEmpty);

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

Does this one just instantly succeed because the default is empty? Meaning on a slow bot, you could eventually get a preview, but you check ahead of time and just bail out.

i.e. should there be a minimum timeout before bailing?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

We're safe from premature success here because of how the test is synchronized.

Before we call waitForPreviews to check for the empty state, we await the reload trigger:

await deleteReloadCompleter.future.timeout(...);

This completer only completes when the tool prints 'Triggering reload...' to stdout. The tool only does this after it has detected the deletion, waited for the Analysis Server to finish re-analyzing, and successfully retrieved the updated (empty) previews from DTD.

So by the time the test resumes and calls waitForPreviews(..., isEmpty), the entire deletion and analysis cycle has already completed, and DTD is guaranteed to be in its final empty state. If the bot is slow, the waiting happens at the deleteReloadCompleter line (which has a 60-second timeout), not in waitForPreviews.

Comment thread packages/flutter_tools/test/integration.shard/widget_preview_test_helpers.dart Outdated
return previews;
}
} on Object {
// Ignore DTD errors or JSON parsing errors during polling, as they might be temporary

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

Did you hit JSON parsing errors? Its free to log these right so we could maybe later figure out if something is happening?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

It's more to handle transient failures that we expect to clear. I've added some logging, but the test should eventually fail if the failures don't clear.

@github-actions github-actions Bot removed the CICD Run CI/CD label Jun 12, 2026
@flutter-dashboard flutter-dashboard Bot added the CICD Run CI/CD label Jun 12, 2026
@jtmcdole jtmcdole added the autosubmit Merge PR when tree becomes green via auto submit App label Jun 15, 2026
@auto-submit auto-submit Bot added this pull request to the merge queue Jun 15, 2026
Merged via the queue into flutter:master with commit 8cffb53 Jun 15, 2026
166 checks passed
@flutter-dashboard flutter-dashboard Bot removed the autosubmit Merge PR when tree becomes green via auto submit App label Jun 15, 2026
@bkonyi bkonyi deleted the fix-flutter-issue-187514 branch June 16, 2026 15:14
auto-submit Bot pushed a commit to flutter/packages that referenced this pull request Jun 16, 2026
flutter/flutter@5827d5f...3a0420c

2026-06-16 Rusino@users.noreply.github.com Implement font fallback (flutter/flutter#187520)
2026-06-16 amhurtado@protonmail.com Add FlatBuffers Verifier checks to Impeller asset loading (flutter/flutter#187878)
2026-06-16 engine-flutter-autoroll@skia.org Roll Packages from aa964a3 to 8286d39 (1 revision) (flutter/flutter#188067)
2026-06-16 engine-flutter-autoroll@skia.org Roll Skia from 9c2b83788409 to d7196b0b4939 (1 revision) (flutter/flutter#188066)
2026-06-16 engine-flutter-autoroll@skia.org Roll Skia from ef17057bb776 to 9c2b83788409 (1 revision) (flutter/flutter#188061)
2026-06-16 engine-flutter-autoroll@skia.org Roll Skia from 500025456bb5 to ef17057bb776 (1 revision) (flutter/flutter#188058)
2026-06-16 engine-flutter-autoroll@skia.org Roll Skia from cb1035ff14bf to 500025456bb5 (5 revisions) (flutter/flutter#188057)
2026-06-16 engine-flutter-autoroll@skia.org Roll Fuchsia Linux SDK from TbB86Po_HDe1dvXvT... to VeLhhlDcod09NR4Hb... (flutter/flutter#188055)
2026-06-16 engine-flutter-autoroll@skia.org Roll Skia from 70acf6a5e7c9 to cb1035ff14bf (3 revisions) (flutter/flutter#188054)
2026-06-16 41930132+hellohuanlin@users.noreply.github.com [pv]skip non-tappable web view workaround on ios 26.4 (flutter/flutter#185424)
2026-06-16 mdebbar@google.com [web] RenderParagraph needs paint after a DPR change (flutter/flutter#186968)
2026-06-16 30870216+gaaclarke@users.noreply.github.com Adds gamma correction to windows text. (flutter/flutter#187871)
2026-06-15 98614782+auto-submit[bot]@users.noreply.github.com Reverts "Add a platform view test to android_hardware_smoke_test (#187913)" (flutter/flutter#188051)
2026-06-15 awolff@google.com Add a platform view test to android_hardware_smoke_test (flutter/flutter#187913)
2026-06-15 codefu@google.com feat: linux_analyze in a workflow (flutter/flutter#187889)
2026-06-15 mdebbar@google.com [web] Changes to WebParagraph configuration (flutter/flutter#187188)
2026-06-15 matt.boetger@gmail.com Fail gracefully on Android AVD lock errors during startup (flutter/flutter#187200)
2026-06-15 bkonyi@google.com [flutter_tools] Fix flakiness in widget_preview_detection_test (flutter/flutter#187938)
2026-06-15 jason-simmons@users.noreply.github.com Exclude fuchsia-sdk/sdk/.build-id from the builder cache archive (flutter/flutter#187826)
2026-06-15 engine-flutter-autoroll@skia.org Roll Skia from c8d9f80f13e4 to 70acf6a5e7c9 (4 revisions) (flutter/flutter#188020)
2026-06-15 engine-flutter-autoroll@skia.org Roll Packages from b78ad83 to aa964a3 (7 revisions) (flutter/flutter#188021)

If this roll has caused a breakage, revert this CL and stop the roller
using the controls here:
https://autoroll.skia.org/r/flutter-packages
Please CC bmparr@google.com,stuartmorgan@google.com on the revert to ensure that a human
is aware of the problem.

To file a bug in Packages: https://github.com/flutter/flutter/issues/new/choose

To report a problem with the AutoRoller itself, please file a bug:
https://issues.skia.org/issues/new?component=1389291&template=1850622

Documentation for the AutoRoller is here:
https://skia.googlesource.com/buildbot/+doc/main/autoroll/README.md
via-guy pushed a commit to via-guy/flutter that referenced this pull request Jun 26, 2026
…er#187938)

### Description
Fixes flakiness in `widget_preview_detection_test.dart` by introducing a
robust polling mechanism when querying DTD for previews.

Previously, the integration tests were flaking on slow CI environments
because they queried DTD immediately after a file modification, without
waiting for the background Dart Analysis Server to finish re-analyzing
the changes. This led to stale (empty) preview results and assertion
failures like `Bad state: Preview was lost after modification!`.

### Changes
* **Introduced `waitForPreviews` Helper**: Added a robust polling helper
in `widget_preview_test_helpers.dart` that repeatedly queries DTD for
previews until a user-specified predicate is met (or a 10-second timeout
occurs).
* **Error Resilience**: The helper gracefully ignores all `Object`s
(including DTD connection issues, RPC errors, or temporary parsing
errors) during the polling loop, as these are common transient states
while the Analysis Server is re-analyzing.
* **Test Refactoring**: Updated all four integration tests in
`widget_preview_detection_test.dart` to use `waitForPreviews` with
appropriate predicates (waiting for previews to be non-empty, empty, or
containing specific updated content).
* **Documentation**: Added comprehensive Dartdoc comments to the new
public helper.

### Related Issues
*   Fixes flutter#187514
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

CICD Run CI/CD tool Affects the "flutter" command-line tool. See also t: labels.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Flaky: widget_preview_detection_test

2 participants