Add assert that the root widget has been attached. (#32437)
diff --git a/packages/flutter/lib/src/widgets/binding.dart b/packages/flutter/lib/src/widgets/binding.dart
index 3654918..bf91401 100644
--- a/packages/flutter/lib/src/widgets/binding.dart
+++ b/packages/flutter/lib/src/widgets/binding.dart
@@ -736,6 +736,12 @@
).attachToRenderTree(buildOwner, renderViewElement);
}
+ /// Whether the [renderViewElement] has been initialized.
+ ///
+ /// This will be false until [runApp] is called (or [WidgetTester.pumpWidget]
+ /// is called in the context of a [TestWidgetsFlutterBinding]).
+ bool get isRootWidgetAttached => _renderViewElement != null;
+
@override
Future<void> performReassemble() {
assert(() {
diff --git a/packages/flutter_driver/lib/src/extension/extension.dart b/packages/flutter_driver/lib/src/extension/extension.dart
index 894d6f9..1e1f1b6 100644
--- a/packages/flutter_driver/lib/src/extension/extension.dart
+++ b/packages/flutter_driver/lib/src/extension/extension.dart
@@ -175,6 +175,8 @@
/// the result into a subclass of [Result], but that's not strictly required.
@visibleForTesting
Future<Map<String, dynamic>> call(Map<String, String> params) async {
+ assert(WidgetsBinding.instance.isRootWidgetAttached,
+ 'No root widget is attached; have you remembered to call runApp()?');
final String commandKind = params['command'];
try {
final CommandHandlerCallback commandHandler = _commandHandlers[commandKind];