Reputation: 516
I have a widget that takes a callback which is called when a button is pressed. I am trying to test that the callback is correctly invoked by the button.
I've tried mocking a Function
class:
class MockCallback extends Mock implements Function {
call() {}
}
Then passing an instance of the mock class to my widget and simulating a tap:
final mocked = MockCallback();
await tester.pumpWidget(
MyWidget(myCallback: mocked),
);
final clearButtonFinder = find.byType(IconButton);
await tester.tap(clearButtonFinder);
verify(mocked()).called(1);
This results in an error on the verify
call saying Used on a non-mockito object
. If I put a print statement inside the mocked call
, I can see that the tap is indeed calling it.
How can I verify that the callback passed to my widget is getting called once when the button is tapped?
Upvotes: 7
Views: 3679
Reputation: 6413
This is how I solved this problem.
class MockCallback {
int _callCounter = 0;
void call() {
_callCounter += 1;
}
bool called(int expected) => _callCounter == expected;
void reset() {
_callCounter = 0;
}
}
No mockito needed.
Upvotes: 3
Reputation: 11
Probably it is not the best solution - use a stream:
final callbackCalled = BehaviorSubject<void>.seeded(null);
await tester.pumpWidget(
MyWidget(myCallback: () { callbackCalled.add(null); }),
);
//... actions to trigger the callback
await expectLater(callbackCalled, emitsInOrder(<void>[null, null]));
You can use something meaningful instead of 'void' and 'null'.
Upvotes: 1