Skip to content

Commit 87aa842

Browse files
authored
Fix test that leaks images. (#148494)
Contributes to flutter/flutter#145599 Repro: `flutter test test/cupertino/tab_scaffold_test.dart --dart-define LEAK_TRACKING=true --plain-name "Adding new tabs does not crash the app"` What is going on: 1. ImageCache.putIfAbsent, in case the image already existed in the cache, invokes ImageCache._trackLiveImage, that creates _LiveImage and passes the image's completer as parameter `completer` 3. _LiveImage constructor invokes super constructor (of _CachedImageBase) that initializes the member `handle` 4. `handle` is disposed [using scheduler](https://github.com/polina-c/flutter/blob/c698e694c871278fd00dc52394a91323494b6395/packages/flutter/lib/src/painting/image_cache.dart#L633), and disposal does not happen in time of test completion. Adding delay to the test increases number of not disposed objects from 30 to 120. Should we force schedule at the end of the widget tests somehow to make scheduler switched to right state? Creation call stack: ``` #9______new_ImageStreamCompleterHandle.__(package:flutter/src/painting/image_stream.dart:465:41) #10_____ImageStreamCompleter.keepAlive_(package:flutter/src/painting/image_stream.dart:655:39) #11_____new__CachedImageBase_(package:flutter/src/painting/image_cache.dart:609:27) #12_____new__LiveImage_(package:flutter/src/painting/image_cache.dart:647:9) #13_____ImageCache._trackLiveImage.<anonymous_closure>_(package:flutter/src/painting/image_cache.dart:302:14) #14______LinkedHashMapMixin.putIfAbsent_(dart:collection-patch/compact_hash.dart:543:23) #15_____ImageCache._trackLiveImage_(package:flutter/src/painting/image_cache.dart:296:17) #16_____ImageCache.putIfAbsent_(package:flutter/src/painting/image_cache.dart:378:7) #17_____ImageProvider.resolveStreamForKey_(package:flutter/src/painting/image_provider.dart:517:81) #18_____ScrollAwareImageProvider.resolveStreamForKey_(package:flutter/src/widgets/scroll_aware_image_provider.dart:104:19) #19_____ImageProvider.resolve.<anonymous_closure>_(package:flutter/src/painting/image_provider.dart:366:9) #20_____ImageProvider._createErrorHandlerAndKey.<anonymous_closure>_(package:flutter/src/painting/image_provider.dart:479:24) #21_____SynchronousFuture.then_(package:flutter/src/foundation/synchronous_future.dart:43:39) #22_____ImageProvider._createErrorHandlerAndKey_(package:flutter/src/painting/image_provider.dart:476:9) #23_____ImageProvider.resolve_(package:flutter/src/painting/image_provider.dart:363:5) #24______ImageState._resolveImage_(package:flutter/src/widgets/image.dart:1111:16) #25______ImageState.didChangeDependencies_(package:flutter/src/widgets/image.dart:1061:5) #26_____StatefulElement._firstBuild_(package:flutter/src/widgets/framework.dart:5630:11) #27_____ComponentElement.mount_(package:flutter/src/widgets/framework.dart:5457:5) #28_____Element.inflateWidget_(package:flutter/src/widgets/framework.dart:4334:16) #29_____Element.updateChild_(package:flutter/src/widgets/framework.dart:3843:18) #30_____SingleChildRenderObjectElement.mount_(package:flutter/src/widgets/framework.dart:6763:14) ```
1 parent 24979ab commit 87aa842

File tree

1 file changed

+7
-1
lines changed

1 file changed

+7
-1
lines changed

packages/flutter/test/cupertino/tab_scaffold_test.dart

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,10 @@ void main() {
4747
selectedTabs = <int>[];
4848
});
4949

50+
tearDown(() {
51+
imageCache.clear();
52+
});
53+
5054
BottomNavigationBarItem tabGenerator(int index) {
5155
return BottomNavigationBarItem(
5256
icon: ImageIcon(MemoryImage(Uint8List.fromList(kTransparentImage))),
@@ -632,7 +636,9 @@ void main() {
632636
});
633637

634638
// Regression test for https://github.com/flutter/flutter/issues/33455
635-
testWidgets('Adding new tabs does not crash the app', (WidgetTester tester) async {
639+
testWidgets('Adding new tabs does not crash the app',
640+
experimentalLeakTesting: LeakTesting.settings.withTrackedAll(),
641+
(WidgetTester tester) async {
636642
final List<int> tabsPainted = <int>[];
637643
final CupertinoTabController controller = CupertinoTabController();
638644
addTearDown(controller.dispose);

0 commit comments

Comments
 (0)