Repository navigation
Description
Summary
packages/google_fonts/test/google_fonts_text_style_test.dart: pendingFonts waits for fonts to be loaded fails on roughly 3 out of 10 runs of the Windows_x64 dart_unit_tests_shard_1 master presubmit. It only runs when a PR touches something that makes the tool run every package (.ci/, .ci.yaml, script/, Flutter rolls, ...), so it never shows up in postsubmit and it blocks exactly the PRs that can't avoid it. flutter/packages#13223 has hit it four times in a row today.
Evidence
Buildbucket history for flutter/try/Windows_x64 dart_unit_tests_shard_1 master, restricted to builds whose log contains Running for all packages and that actually ran packages/google_fonts (log: https://logs.chromium.org/logs/flutter/buildbucket/cr-buildbucket/<id>/+/u/Run_package_tests/dart_unit_tests/stdout?format=raw):
| Month (2026) | google_fonts passed | failed on pendingFonts waits for fonts to be loaded |
|---|---|---|
| April | 123 | 31 |
| May | 113 | 27 |
| June | 9 | 30 |
| July | 20 | 19 |
| August | 44 | 30 |
| September | 118 | 33 |
| October (to the 14th) | 56 | 27 |
Logs before late March don't print the per-test "Failing tests:" summary, but packages/google_fonts failures with the same shape are there every month back to January, so this is not a recent regression. There is no window where it was green.
Recent failures (all Windows_x64 dart_unit_tests_shard_1 master):
| Build | PR | Date |
|---|---|---|
| 8667943901072539905 | flutter/packages#13223 | 2026-10-14 |
| 8667946301673687617 | flutter/packages#13223 | 2026-10-14 |
| 8667946303843176033 | flutter/packages#13223 | 2026-10-14 |
| 8667948902004693537 | flutter/packages#13223 | 2026-10-14 |
| 8668033524488771169 | flutter/packages#13241 | 2026-10-13 |
| 8668036604023814513 | flutter/packages#13239 | 2026-10-13 |
| 8668039119733360769 | flutter/packages#13237 | 2026-10-13 |
| 8668106670815314625 | flutter/packages#13220 | 2026-10-12 |
| 8668111039808525249 | flutter/packages#13197 | 2026-10-12 |
| 8668111728093343217, 8668113396612381169 | flutter/packages#13212 | 2026-10-12 |
And the same test passing on the same builder in the same period, including once for flutter/packages#13223 itself: 8668026675852198609 (flutter/packages#13223, 2026-10-13), 8668034807642058801 (flutter/packages#13220, 2026-10-13), 8668018885495354161 (flutter/packages#13243, 2026-10-13). Bots are fresh VMs each time, so it is not tied to a particular machine. Linux dart_unit_test_shard_* runs the same test and has been green throughout; there is no macOS dart unit test builder for this repo.
What actually fails
The CI log never contains an [E] block for this test. What it does show is the pass counter going down by one at the moment the failure is counted, e.g. build 8667943901072539905:
00:03 +92: .../google_fonts/test/generated_font_methods_test.dart: getFont works with all fonts in GoogleFonts.asMap
00:03 +91 -1: .../google_fonts/test/generated_font_methods_test.dart: getFont works with all fonts in GoogleFonts.asMap
...
Failing tests:
C:/b/s/w/ir/x/w/packages/packages/google_fonts/test/google_fonts_text_style_test.dart: pendingFonts waits for fonts to be loaded
That is the signature of a test that passed and was then marked failed by an error that arrived after it had completed (171 of the 202 failing logs since March show the same +N to +N-1 drop; the rest are interleaved with other suites' progress lines).
The source of that late error is reproducible by keeping the test alive for a couple of seconds after its last expect:
pendingFonts flow plus a wait for late errors [E]
MissingPluginException(No implementation found for method getApplicationSupportDirectory on channel plugins.flutter.io/path_provider)
package:flutter/src/services/platform_channel.dart 363:7 MethodChannel._invokeMethod
===== asynchronous gap ===========================
package:google_fonts/src/file_io_desktop_and_mobile.dart 26:21 saveFontToDeviceFileSystem
package:google_fonts/src/google_fonts_base.dart 265:15 _httpFetchFontAndSaveToDevice
===== asynchronous gap ===========================
package:google_fonts/src/google_fonts_base.dart 168:18 loadFontIfNecessary
package:google_fonts/src/google_fonts_base.dart 107:38 googleFontsTextStyle
Sequence:
- The test calls
googleFontsTextStylefor two families (ab,cd) with a mock HTTP client and awaitsGoogleFonts.pendingFonts()twice. All threeexpects pass on every platform;pendingFontFuturesbookkeeping is fine. _httpFetchFontAndSaveToDevice(lib/src/google_fonts_base.dart) firesfile_io.saveFontToDeviceFileSystem(...)and deliberately drops the future (_unawaited). The future returned byloadFontIfNecessaryonly waits forFontLoader.load(), not for that write.- The test does not fake
PathProviderPlatform, sogetApplicationSupportDirectory()fails withMissingPluginException, once per family, inside the dropped future. Nothing catches it, so it becomes an uncaught asynchronous error in the test's zone. - The method channel reply comes back after the test body has already finished. This file has a single test, so by then the suite is being torn down. On Linux the teardown consistently wins and the error is lost silently (test passes). On Windows the error regularly lands while the runner is still attached, which flips the already-passed test to failed ("This test failed after it had already completed"). The detailed
[E]output is not in the CI logs, presumably because the runner closes the test between the state change and the error message.
So: the product code is doing what it does in any app (write the font to the application support directory in the background); the test is the problem, because it exercises the HTTP path on a desktop VM without giving path_provider an implementation. load_font_if_necessary_test.dart in the same package already installs a FakePathProviderPlatform pointing at a temp directory, which is why it does not have this problem.
Why postsubmit never catches it
Postsubmit only tests the packages touched by each commit; google_fonts is rarely touched. Presubmits for PRs that change repo-wide files run every package (Running for all packages, since a file has changed that could affect the entire repository.) and are the only place this test runs on Windows.
Activity
[google_fonts] Make the pendingFonts test deterministic (flutter#13262)
stuartmorgan commentedon Oct 15, 2026
Presubmit and postsubmit do not behave differently in this regard; a PR that touches a repo-wide file runs every package's tests in both presubmit and postsubmit.
github-actions commentedon Oct 29, 2026
This thread has been automatically locked since there has not been any recent activity after it was closed. If you are still experiencing a similar issue, please open a new bug, including the output of
flutter doctor -vand a minimal reproduction of the issue.