Add tests

This commit is contained in:
Roland Geider
2025-12-18 11:13:02 +01:00
parent d187324a25
commit 40837ad1b3
5 changed files with 129 additions and 18 deletions

View File

@@ -20,12 +20,14 @@ import 'package:flutter/material.dart';
import 'package:flutter_riverpod/flutter_riverpod.dart';
import 'package:flutter_test/flutter_test.dart';
import 'package:mockito/annotations.dart';
import 'package:mockito/mockito.dart';
import 'package:provider/provider.dart' as provider;
import 'package:shared_preferences_platform_interface/in_memory_shared_preferences_async.dart';
import 'package:shared_preferences_platform_interface/shared_preferences_async_platform_interface.dart';
import 'package:wger/l10n/generated/app_localizations.dart';
import 'package:wger/models/exercises/exercise.dart';
import 'package:wger/models/workouts/day_data.dart';
import 'package:wger/models/workouts/log.dart';
import 'package:wger/models/workouts/set_config_data.dart';
import 'package:wger/models/workouts/slot_data.dart';
import 'package:wger/providers/exercises.dart';
@@ -41,7 +43,7 @@ import 'log_page_test.mocks.dart';
void main() {
TestWidgetsFlutterBinding.ensureInitialized();
group('LogPage smoke tests', () {
group('LogPage tests', () {
late List<Exercise> testExercises;
late ProviderContainer container;
@@ -51,18 +53,29 @@ void main() {
container = ProviderContainer.test();
});
Future<void> pumpLogPage(WidgetTester tester) async {
Future<void> pumpLogPage(WidgetTester tester, {RoutinesProvider? routinesProvider}) async {
final providerValue = routinesProvider ?? MockRoutinesProvider();
await tester.pumpWidget(
UncontrolledProviderScope(
container: container,
child: provider.ChangeNotifierProvider<RoutinesProvider>.value(
value: MockRoutinesProvider(),
value: providerValue,
child: MaterialApp(
locale: const Locale('en'),
localizationsDelegates: AppLocalizations.localizationsDelegates,
supportedLocales: AppLocalizations.supportedLocales,
home: Scaffold(
body: LogPage(PageController()),
// Provide a PageView so the PageController used by LogPage is attached
body: Builder(
builder: (context) {
final controller = PageController();
return PageView(
controller: controller,
children: [LogPage(controller)],
);
},
),
),
),
),
@@ -135,5 +148,91 @@ void main() {
expect(find.byType(LogPage), findsOneWidget);
});
testWidgets('copy from past log updates form fields and shows SnackBar', (tester) async {
// Arrange
final notifier = container.read(gymStateProvider.notifier);
final routine = testdata.getTestRoutine();
notifier.state = notifier.state.copyWith(
dayId: routine.days.first.id,
routine: routine,
iteration: 1,
);
notifier.calculatePages();
// Act
// Log page is at index 2
notifier.state = notifier.state.copyWith(currentPage: 2);
expect(notifier.state.getSlotEntryPageByIndex()!.type, SlotPageType.log);
await pumpLogPage(tester);
// Assert
final pastLogTile = find.byKey(const ValueKey('past-log-1'));
expect(pastLogTile, findsOneWidget);
await tester.tap(pastLogTile);
await tester.pumpAndSettle();
final editableFields = find.byType(EditableText);
expect(editableFields, findsWidgets);
// Get controller texts
final repControllerText = tester.widget<EditableText>(editableFields.at(0)).controller.text;
final weightControllerText = tester
.widget<EditableText>(editableFields.at(1))
.controller
.text;
expect(repControllerText, contains('10'));
expect(weightControllerText, contains('10'));
expect(find.byType(SnackBar), findsOneWidget);
});
testWidgets('save button calls addLog on RoutinesProvider', (tester) async {
// Arrange
final notifier = container.read(gymStateProvider.notifier);
final routine = testdata.getTestRoutine();
notifier.state = notifier.state.copyWith(
dayId: routine.days.first.id,
routine: routine,
iteration: 1,
);
notifier.calculatePages();
notifier.state = notifier.state.copyWith(currentPage: 2);
final mockRoutines = MockRoutinesProvider();
// Act
await pumpLogPage(tester, routinesProvider: mockRoutines);
final editableFields = find.byType(EditableText);
expect(editableFields, findsWidgets);
await tester.enterText(editableFields.at(0), '7');
await tester.enterText(editableFields.at(1), '77');
await tester.pumpAndSettle();
Log? capturedLog;
when(mockRoutines.addLog(any)).thenAnswer((invocation) async {
capturedLog = invocation.positionalArguments[0] as Log;
capturedLog!.id = 42;
return capturedLog!;
});
final saveButton = find.byKey(const ValueKey('save-log-button'));
expect(saveButton, findsOneWidget);
await tester.tap(saveButton);
await tester.pumpAndSettle();
// Assert
verify(mockRoutines.addLog(any)).called(1);
expect(capturedLog, isNotNull);
expect(capturedLog!.repetitions, equals(7));
expect(capturedLog!.weight, equals(77));
final currentSlotPage = notifier.state.getSlotEntryPageByIndex()!;
expect(capturedLog!.slotEntryId, equals(currentSlotPage.setConfigData!.slotEntryId));
expect(capturedLog!.routineId, equals(notifier.state.routine.id));
expect(capturedLog!.iteration, equals(notifier.state.iteration));
});
});
}