Files
CookIT/test/recipes/repository_test.dart
T

104 lines
3.9 KiB
Dart
Raw Normal View History

import 'dart:typed_data';
import 'package:cookit/src/database/database.dart';
import 'package:cookit/src/recipes/course_repository.dart';
import 'package:cookit/src/recipes/models/course.dart';
import 'package:cookit/src/recipes/photo_store.dart';
import 'package:cookit/src/recipes/recipe_repository.dart';
import 'package:flutter_test/flutter_test.dart';
import '../support/fixtures.dart';
import '../support/test_database.dart';
void main() {
late AppDatabase db;
late PhotoStore photos;
late RecipeRepository recipes;
late CourseRepository courses;
setUp(() async {
db = testDatabase();
photos = await tempPhotoStore();
recipes = RecipeRepository(db, photos);
courses = CourseRepository(db);
});
tearDown(() async {
await db.close();
await photos.directory.delete(recursive: true);
});
test('a fresh database starts with the default Courses in order', () async {
final all = await courses.allCourses();
expect(all.map((c) => c.name), defaultCourses.map((c) => c.$1));
expect(all.first.label, '🍝 Hauptgericht');
});
test('saves and reads back a whole Recipe', () async {
final course = (await courses.allCourses()).first;
final original = recipe(courseId: course.id, tags: ['Brot'], reviewReasons: ['Portionen fehlen.']);
await recipes.saveRecipe(original);
final read = (await recipes.watchRecipe('r1').first)!;
expect(read.name, 'Focaccia');
expect(read.courseId, course.id);
expect(read.tags, ['Brot']);
expect(read.calories!.kcal, 775);
expect(
[for (final g in read.ingredientGroups) g.toJson()],
[for (final g in original.ingredientGroups) g.toJson()],
);
expect(read.stepSections.single.title, 'Teig');
expect(read.sources, ['https://example.org/focaccia']);
expect(read.needsReview, isTrue);
});
test('watchRecipes is sorted by name ignoring case', () async {
await recipes.saveRecipe(recipe(id: 'b', name: 'zwiebelkuchen'));
await recipes.saveRecipe(recipe(id: 'a', name: 'Apfelstrudel'));
await recipes.saveRecipe(recipe(id: 'c', name: 'Brot'));
final names = (await recipes.watchRecipes().first).map((r) => r.name);
expect(names, ['Apfelstrudel', 'Brot', 'zwiebelkuchen']);
});
test('favourite and clearing the Review Flag', () async {
await recipes.saveRecipe(recipe(reviewReasons: ['x']));
await recipes.setFavourite('r1', true);
await recipes.clearReview('r1');
final read = (await recipes.watchRecipe('r1').first)!;
expect(read.favourite, isTrue);
expect(read.needsReview, isFalse);
});
test('deleting a Recipe removes its Photo files', () async {
final photo = await photos.saveBytes(Uint8List.fromList([1, 2, 3]));
await recipes.saveRecipe(recipe(photos: [photo]));
await recipes.deleteRecipe((await recipes.watchRecipe('r1').first)!);
expect(await recipes.watchRecipe('r1').first, isNull);
expect(photos.file(photo).existsSync(), isFalse);
});
test('deleting a Course keeps its Recipes without one', () async {
final course = await courses.addCourse('Suppe', emoji: '🍲');
await recipes.saveRecipe(recipe(courseId: course.id));
expect(await courses.recipeCount(course.id), 1);
await courses.deleteCourse(course.id);
expect((await recipes.watchRecipe('r1').first)!.courseId, isNull);
});
test('findOrCreate matches names ignoring case', () async {
final existing = await courses.findOrCreate('dessert');
expect(existing.name, 'Dessert');
final created = await courses.findOrCreate('Suppe');
expect(created.position, defaultCourses.length);
});
test('reorder and update Courses', () async {
final all = await courses.allCourses();
await courses.reorder(all.reversed.toList());
await courses.updateCourse(all.first.id, name: 'Hauptspeise', emoji: null);
final reordered = await courses.allCourses();
expect(reordered.last.name, 'Hauptspeise');
expect(reordered.last.emoji, isNull);
});
}