I'm trying to write a test for a row of buttons. The buttons should be enabled / disabled depending on a flag provided by a controller class.
class UserSettingsButtonRow extends ConsumerWidget {
const UserSettingsButtonRow({Key? key}) : super(key: key);
@override
Widget build(BuildContext context, WidgetRef ref) {
ref.watch(userSettingsControllerProvider);
UserSettingsController controller =
ref.read(userSettingsControllerProvider.notifier);
...
When I test this manually in the context of the whole program everything works fine. However I'd like to automate this test.
This is my test:
@GenerateNiceMocks([MockSpec<UserSettingsController>()])
void main() {
testWidgets(
'UserSettingsButtonRow - buttons enabled',
(tester) async {
// check if two buttons are enabled
UserSettingsController settingsController = MockUserSettingsController();
when(settingsController.hasValueChanged()).thenAnswer((_) => true);
await tester.runAsync(
() async {
await tester.pumpWidget(
ProviderScope(
overrides: [
userSettingsControllerProvider
.overrideWith((ref) => settingsController),
],
child: const MaterialApp(
home: Material(
child: UserSettingsButtonRow(),
),
),
),
);
},
);
await tester.pumpAndSettle();
expect(find.byType(ElevatedButton), findsNWidgets(2));
List<ElevatedButton> buttons = find
.byType(ElevatedButton)
.evaluate()
.map((e) => e.widget as ElevatedButton)
.toList();
for (ElevatedButton button in buttons) {
expect(button.enabled, isTrue);
}
},
);
<.......>
My problem is that a assertion in the build() method of my widget is not fulfilled.
When the automated test comes to
ref.watch(userSettingsControllerProvider);
I get the following exception:
Exception has occurred.
_AssertionError ('package:riverpod/src/framework/element.dart': Failed assertion: line 439 pos 9: 'getState() != null': Bad state, the provider did not initialize. Did "create" forget to set the state?)
I can't find many examples on testing / mocking with StateNotifierProviders. Can somebody help me out and tell me what's wrong here?
Thanks for your help!
I tried the solution from what is the correct approach to test riverpod with mockito but the atttribute state is not supported any more.
Riverpod Testing: How to mock state with StateNotifierProvider? is not a solution either for me as I want to override the hasValueChanged() method from the Controller.