diff --git a/lib/providers/nutrition.dart b/lib/providers/nutrition.dart index dad470b6..a2f9abb2 100644 --- a/lib/providers/nutrition.dart +++ b/lib/providers/nutrition.dart @@ -48,7 +48,7 @@ class NutritionPlansProvider with ChangeNotifier { late IngredientDatabase database; List _plans = []; List ingredients = []; - + // Track current search to prevent multiple concurrent requests String? _currentSearchQuery; int _searchCounter = 0; @@ -306,9 +306,7 @@ class NutritionPlansProvider with ChangeNotifier { await database.deleteEverything(); } - - - /// Saves an ingredient to the cache + /// Saves an ingredient to the cache Future cacheIngredient(Ingredient ingredient, {IngredientDatabase? database}) async { database ??= this.database; @@ -344,7 +342,7 @@ class NutritionPlansProvider with ChangeNotifier { // Try to fetch from local db if (ingredientDb != null) { ingredient = Ingredient.fromJson(jsonDecode(ingredientDb.data)); - ingredients.add(ingredient); + ingredients.add(ingredient); _logger.info("Loaded ingredient '${ingredient.name}' from db cache"); // Prune old entries @@ -427,7 +425,6 @@ class NutritionPlansProvider with ChangeNotifier { // TODO we should probably add it to ingredient cache. return Ingredient.fromJson(data['results'][0]); - } /// Log meal to nutrition diary diff --git a/test/nutrition/nutrition_provider_test.dart b/test/nutrition/nutrition_provider_test.dart index 81a03bec..e7a1a75b 100644 --- a/test/nutrition/nutrition_provider_test.dart +++ b/test/nutrition/nutrition_provider_test.dart @@ -207,11 +207,13 @@ void main() { description: 'Old active plan', startDate: now.subtract(const Duration(days: 10)), endDate: now.add(const Duration(days: 10)), + creationDate: now.subtract(const Duration(days: 10)), ); final newerPlan = NutritionalPlan( description: 'Newer active plan', startDate: now.subtract(const Duration(days: 5)), endDate: now.add(const Duration(days: 5)), + creationDate: now.subtract(const Duration(days: 1)), ); nutritionProvider = NutritionPlansProvider(mockWgerBaseProvider, [ olderPlan, @@ -222,6 +224,19 @@ void main() { }); group('Ingredient cache DB', () { + test('cacheIngredient saves to both in-memory and database cache', () async { + nutritionProvider.ingredients = []; + final ingredient = Ingredient.fromJson(ingredient59887Response); + + await nutritionProvider.cacheIngredient(ingredient, database: database); + + expect(nutritionProvider.ingredients.length, 1); + expect(nutritionProvider.ingredients.first.id, 59887); + + final rows = await database.select(database.ingredients).get(); + expect(rows.length, 1); + expect(rows.first.id, ingredient.id); + }); test('that if there is already valid data in the DB, the API is not hit', () async { // Arrange nutritionProvider.ingredients = []; diff --git a/test/nutrition/nutritional_meal_item_form_test.dart b/test/nutrition/nutritional_meal_item_form_test.dart index 9b4a0100..eb28f0b0 100644 --- a/test/nutrition/nutritional_meal_item_form_test.dart +++ b/test/nutrition/nutritional_meal_item_form_test.dart @@ -331,5 +331,31 @@ void main() { verify(mockNutrition.addMealItem(any, meal1)); }, ); + + testWidgets('selecting ingredient from autocomplete calls cacheIngredient', ( + WidgetTester tester, + ) async { + await tester.pumpWidget(createMealItemFormScreen(meal1, '', true)); + await tester.pumpAndSettle(); + + clearInteractions(mockNutrition); + + when( + mockNutrition.searchIngredient( + any, + languageCode: anyNamed('languageCode'), + searchEnglish: anyNamed('searchEnglish'), + ), + ).thenAnswer((_) => Future.value([ingredient1])); + + await tester.enterText(find.byType(TextFormField).first, 'Water'); + await tester.pumpAndSettle(const Duration(milliseconds: 600)); + await tester.pumpAndSettle(); + + await tester.tap(find.byType(ListTile).first); + await tester.pumpAndSettle(); + + verify(mockNutrition.cacheIngredient(ingredient1)).called(1); + }); }); }