mirror of https://github.com/AMT-Cheif/drift.git
Improve test coverage for query generation
This commit is contained in:
parent
85fa0d4764
commit
bea001bb16
|
@ -5,4 +5,5 @@ targets:
|
|||
options:
|
||||
override_hash_and_equals_in_result_sets: true
|
||||
use_column_name_as_json_key_when_defined_in_moor_file: true
|
||||
generate_connect_constructor: true
|
||||
generate_connect_constructor: true
|
||||
write_from_json_string_constructor: true
|
|
@ -29,6 +29,11 @@ class Category extends DataClass implements Insertable<Category> {
|
|||
description: serializer.fromJson<String>(json['description']),
|
||||
);
|
||||
}
|
||||
factory Category.fromJsonString(String encodedJson,
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) =>
|
||||
Category.fromJson(
|
||||
DataClass.parseJson(encodedJson) as Map<String, dynamic>,
|
||||
serializer: serializer);
|
||||
@override
|
||||
Map<String, dynamic> toJson(
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) {
|
||||
|
@ -204,6 +209,10 @@ class Recipe extends DataClass implements Insertable<Recipe> {
|
|||
category: serializer.fromJson<int>(json['category']),
|
||||
);
|
||||
}
|
||||
factory Recipe.fromJsonString(String encodedJson,
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) =>
|
||||
Recipe.fromJson(DataClass.parseJson(encodedJson) as Map<String, dynamic>,
|
||||
serializer: serializer);
|
||||
@override
|
||||
Map<String, dynamic> toJson(
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) {
|
||||
|
@ -438,6 +447,11 @@ class Ingredient extends DataClass implements Insertable<Ingredient> {
|
|||
caloriesPer100g: serializer.fromJson<int>(json['caloriesPer100g']),
|
||||
);
|
||||
}
|
||||
factory Ingredient.fromJsonString(String encodedJson,
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) =>
|
||||
Ingredient.fromJson(
|
||||
DataClass.parseJson(encodedJson) as Map<String, dynamic>,
|
||||
serializer: serializer);
|
||||
@override
|
||||
Map<String, dynamic> toJson(
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) {
|
||||
|
@ -644,6 +658,11 @@ class IngredientInRecipe extends DataClass
|
|||
amountInGrams: serializer.fromJson<int>(json['amountInGrams']),
|
||||
);
|
||||
}
|
||||
factory IngredientInRecipe.fromJsonString(String encodedJson,
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) =>
|
||||
IngredientInRecipe.fromJson(
|
||||
DataClass.parseJson(encodedJson) as Map<String, dynamic>,
|
||||
serializer: serializer);
|
||||
@override
|
||||
Map<String, dynamic> toJson(
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) {
|
||||
|
|
|
@ -6,7 +6,7 @@ part of '../query_builder.dart';
|
|||
Expression<bool, BoolType> isIn<X extends SqlType<T>, T>(
|
||||
Expression<T, X> expression, Iterable<T> values,
|
||||
{bool not = false}) {
|
||||
if (not == false) {
|
||||
if (not == true) {
|
||||
return expression.isNotIn(values);
|
||||
} else {
|
||||
return expression.isIn(values);
|
||||
|
|
|
@ -25,6 +25,10 @@ class NoId extends DataClass implements Insertable<NoId> {
|
|||
payload: serializer.fromJson<Uint8List>(json['payload']),
|
||||
);
|
||||
}
|
||||
factory NoId.fromJsonString(String encodedJson,
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) =>
|
||||
NoId.fromJson(DataClass.parseJson(encodedJson) as Map<String, dynamic>,
|
||||
serializer: serializer);
|
||||
@override
|
||||
Map<String, dynamic> toJson(
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) {
|
||||
|
@ -156,6 +160,11 @@ class WithDefault extends DataClass implements Insertable<WithDefault> {
|
|||
b: serializer.fromJson<int>(json['b']),
|
||||
);
|
||||
}
|
||||
factory WithDefault.fromJsonString(String encodedJson,
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) =>
|
||||
WithDefault.fromJson(
|
||||
DataClass.parseJson(encodedJson) as Map<String, dynamic>,
|
||||
serializer: serializer);
|
||||
@override
|
||||
Map<String, dynamic> toJson(
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) {
|
||||
|
@ -315,6 +324,11 @@ class WithConstraint extends DataClass implements Insertable<WithConstraint> {
|
|||
c: serializer.fromJson<double>(json['c']),
|
||||
);
|
||||
}
|
||||
factory WithConstraint.fromJsonString(String encodedJson,
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) =>
|
||||
WithConstraint.fromJson(
|
||||
DataClass.parseJson(encodedJson) as Map<String, dynamic>,
|
||||
serializer: serializer);
|
||||
@override
|
||||
Map<String, dynamic> toJson(
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) {
|
||||
|
@ -499,6 +513,10 @@ class Config extends DataClass implements Insertable<Config> {
|
|||
configValue: serializer.fromJson<String>(json['config_value']),
|
||||
);
|
||||
}
|
||||
factory Config.fromJsonString(String encodedJson,
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) =>
|
||||
Config.fromJson(DataClass.parseJson(encodedJson) as Map<String, dynamic>,
|
||||
serializer: serializer);
|
||||
@override
|
||||
Map<String, dynamic> toJson(
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) {
|
||||
|
@ -674,6 +692,11 @@ class MytableData extends DataClass implements Insertable<MytableData> {
|
|||
somedate: serializer.fromJson<DateTime>(json['somedate']),
|
||||
);
|
||||
}
|
||||
factory MytableData.fromJsonString(String encodedJson,
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) =>
|
||||
MytableData.fromJson(
|
||||
DataClass.parseJson(encodedJson) as Map<String, dynamic>,
|
||||
serializer: serializer);
|
||||
@override
|
||||
Map<String, dynamic> toJson(
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) {
|
||||
|
|
|
@ -47,6 +47,11 @@ class TodoEntry extends DataClass implements Insertable<TodoEntry> {
|
|||
category: serializer.fromJson<int>(json['category']),
|
||||
);
|
||||
}
|
||||
factory TodoEntry.fromJsonString(String encodedJson,
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) =>
|
||||
TodoEntry.fromJson(
|
||||
DataClass.parseJson(encodedJson) as Map<String, dynamic>,
|
||||
serializer: serializer);
|
||||
@override
|
||||
Map<String, dynamic> toJson(
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) {
|
||||
|
@ -318,6 +323,11 @@ class Category extends DataClass implements Insertable<Category> {
|
|||
description: serializer.fromJson<String>(json['description']),
|
||||
);
|
||||
}
|
||||
factory Category.fromJsonString(String encodedJson,
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) =>
|
||||
Category.fromJson(
|
||||
DataClass.parseJson(encodedJson) as Map<String, dynamic>,
|
||||
serializer: serializer);
|
||||
@override
|
||||
Map<String, dynamic> toJson(
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) {
|
||||
|
@ -497,6 +507,10 @@ class User extends DataClass implements Insertable<User> {
|
|||
creationTime: serializer.fromJson<DateTime>(json['creationTime']),
|
||||
);
|
||||
}
|
||||
factory User.fromJsonString(String encodedJson,
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) =>
|
||||
User.fromJson(DataClass.parseJson(encodedJson) as Map<String, dynamic>,
|
||||
serializer: serializer);
|
||||
@override
|
||||
Map<String, dynamic> toJson(
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) {
|
||||
|
@ -768,6 +782,11 @@ class SharedTodo extends DataClass implements Insertable<SharedTodo> {
|
|||
user: serializer.fromJson<int>(json['user']),
|
||||
);
|
||||
}
|
||||
factory SharedTodo.fromJsonString(String encodedJson,
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) =>
|
||||
SharedTodo.fromJson(
|
||||
DataClass.parseJson(encodedJson) as Map<String, dynamic>,
|
||||
serializer: serializer);
|
||||
@override
|
||||
Map<String, dynamic> toJson(
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) {
|
||||
|
@ -943,6 +962,11 @@ class TableWithoutPKData extends DataClass
|
|||
custom: serializer.fromJson<MyCustomObject>(json['custom']),
|
||||
);
|
||||
}
|
||||
factory TableWithoutPKData.fromJsonString(String encodedJson,
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) =>
|
||||
TableWithoutPKData.fromJson(
|
||||
DataClass.parseJson(encodedJson) as Map<String, dynamic>,
|
||||
serializer: serializer);
|
||||
@override
|
||||
Map<String, dynamic> toJson(
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) {
|
||||
|
@ -1151,6 +1175,11 @@ class PureDefault extends DataClass implements Insertable<PureDefault> {
|
|||
txt: serializer.fromJson<String>(json['txt']),
|
||||
);
|
||||
}
|
||||
factory PureDefault.fromJsonString(String encodedJson,
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) =>
|
||||
PureDefault.fromJson(
|
||||
DataClass.parseJson(encodedJson) as Map<String, dynamic>,
|
||||
serializer: serializer);
|
||||
@override
|
||||
Map<String, dynamic> toJson(
|
||||
{ValueSerializer serializer = const ValueSerializer.defaults()}) {
|
||||
|
|
|
@ -0,0 +1,19 @@
|
|||
import 'package:test/test.dart';
|
||||
|
||||
import 'data/tables/todos.dart';
|
||||
|
||||
void main() {
|
||||
test('data classes can be serialized', () {
|
||||
final entry = TodoEntry(
|
||||
id: 13,
|
||||
title: 'Title',
|
||||
content: 'Content',
|
||||
targetDate: DateTime.now(),
|
||||
);
|
||||
|
||||
final serialized = entry.toJsonString();
|
||||
final deserialized = TodoEntry.fromJsonString(serialized);
|
||||
|
||||
expect(deserialized, equals(deserialized));
|
||||
});
|
||||
}
|
|
@ -1,6 +1,7 @@
|
|||
import 'package:test/test.dart';
|
||||
import 'package:moor/moor.dart';
|
||||
|
||||
import 'data/tables/todos.dart';
|
||||
import 'data/utils/mocks.dart';
|
||||
|
||||
class _FakeDb extends GeneratedDatabase {
|
||||
|
@ -66,4 +67,22 @@ void main() {
|
|||
verify(executor.runSelect('opened: 3 to 4', []));
|
||||
});
|
||||
});
|
||||
|
||||
test('creates and attaches daos', () async {
|
||||
final executor = MockExecutor();
|
||||
final db = TodoDb(executor);
|
||||
|
||||
await db.someDao.todosForUser(1);
|
||||
|
||||
verify(executor.runSelect(argThat(contains('SELECT t.* FROM todos')), [1]));
|
||||
});
|
||||
|
||||
test('closing the database closes the executor', () async {
|
||||
final executor = MockExecutor();
|
||||
final db = TodoDb(executor);
|
||||
|
||||
await db.close();
|
||||
|
||||
verify(executor.close());
|
||||
});
|
||||
}
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
import 'package:moor/moor.dart';
|
||||
import 'package:test/test.dart';
|
||||
|
||||
import '../data/tables/todos.dart';
|
||||
import '../data/utils/expect_generated.dart';
|
||||
|
||||
void main() {
|
||||
final i1 = GeneratedIntColumn('i1', 'tbl', true);
|
||||
|
@ -10,18 +10,15 @@ void main() {
|
|||
final s2 = GeneratedTextColumn('s2', 'tbl', true);
|
||||
|
||||
test('arithmetic test', () {
|
||||
_expectSql(i1 + i2 * i1, 'i1 + i2 * i1');
|
||||
_expectSql((i1 + i2) * i1, '(i1 + i2) * i1');
|
||||
(i1 + i2 * i1).expectGenerates('i1 + i2 * i1');
|
||||
(i1 + i2 * i1).expectGenerates('i1 + i2 * i1');
|
||||
((i1 + i2) * i1).expectGenerates('(i1 + i2) * i1');
|
||||
(i1 - i2).expectGenerates('i1 - i2');
|
||||
(i1 - -i2).expectGenerates('i1 - -i2');
|
||||
(i1 / i2).expectGenerates('i1 / i2');
|
||||
});
|
||||
|
||||
test('string concatenation', () {
|
||||
_expectSql(s1 + s2, 's1 || s2');
|
||||
(s1 + s2).expectGenerates('s1 || s2');
|
||||
});
|
||||
}
|
||||
|
||||
void _expectSql(Expression e, String expected) {
|
||||
final ctx = GenerationContext.fromDb(TodoDb(null));
|
||||
e.writeInto(ctx);
|
||||
|
||||
expect(ctx.sql, expected);
|
||||
}
|
||||
|
|
|
@ -0,0 +1,23 @@
|
|||
import 'package:moor/moor.dart';
|
||||
import 'package:test/test.dart';
|
||||
|
||||
import '../data/utils/expect_generated.dart';
|
||||
|
||||
// ignore_for_file: deprecated_member_use_from_same_package
|
||||
|
||||
void main() {
|
||||
final a = GeneratedBoolColumn('a', 'tbl', false);
|
||||
final b = GeneratedBoolColumn('b', 'tbl', false);
|
||||
|
||||
test('boolean expressions via operators', () {
|
||||
(a | b).expectGenerates('a OR b');
|
||||
(a & b).expectGenerates('a AND b');
|
||||
a.not().expectGenerates('NOT a');
|
||||
});
|
||||
|
||||
test('boolean expressions via top-level methods', () {
|
||||
or(a, b).expectGenerates('a OR b');
|
||||
and(a, b).expectGenerates('a AND b');
|
||||
not(a).expectGenerates('NOT a');
|
||||
});
|
||||
}
|
|
@ -0,0 +1,26 @@
|
|||
import 'package:test/test.dart';
|
||||
|
||||
import 'package:moor/moor.dart';
|
||||
import '../data/utils/expect_generated.dart';
|
||||
|
||||
class _UnknownExpr extends Expression {
|
||||
@override
|
||||
void writeInto(GenerationContext context) {
|
||||
context.buffer.write('???');
|
||||
}
|
||||
}
|
||||
|
||||
void main() {
|
||||
test('precedence ordering', () {
|
||||
expect(Precedence.plusMinus < Precedence.mulDivide, isTrue);
|
||||
expect(Precedence.unary <= Precedence.unary, isTrue);
|
||||
expect(Precedence.postfix >= Precedence.bitwise, isTrue);
|
||||
expect(Precedence.postfix > Precedence.primary, isFalse);
|
||||
});
|
||||
|
||||
test('puts parentheses around expressions with unknown precedence', () {
|
||||
final expr = _UnknownExpr().equalsExp(_UnknownExpr());
|
||||
|
||||
expr.expectGenerates('(???) = (???)');
|
||||
});
|
||||
}
|
|
@ -96,4 +96,24 @@ void main() {
|
|||
await db.customStatement('some custom statement');
|
||||
verify(mockExecutor.runCustom('some custom statement'));
|
||||
});
|
||||
|
||||
test('upgrading a database without schema migration throws', () async {
|
||||
final db = _DefaultDb(MockExecutor());
|
||||
expect(
|
||||
() => db.handleDatabaseVersionChange(
|
||||
executor: MockQueryExecutor(), from: 1, to: 2),
|
||||
throwsA(const TypeMatcher<Exception>()));
|
||||
});
|
||||
}
|
||||
|
||||
class _DefaultDb extends GeneratedDatabase {
|
||||
_DefaultDb(QueryExecutor executor)
|
||||
// ignore: prefer_const_constructors
|
||||
: super(SqlTypeSystem.withDefaults(), executor);
|
||||
|
||||
@override
|
||||
List<TableInfo<Table, DataClass>> get allTables => [];
|
||||
|
||||
@override
|
||||
int get schemaVersion => 2;
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue