diff --git a/angel_orm_generator/build.yaml b/angel_orm_generator/build.yaml index 18ab94b4..cc8cac74 100644 --- a/angel_orm_generator/build.yaml +++ b/angel_orm_generator/build.yaml @@ -3,14 +3,10 @@ builders: import: "package:angel_orm_generator/angel_orm_generator.dart" builder_factories: - ormBuilder - #- mongoDBOrmBuilder - - postgreSqlOrmBuilder auto_apply: root_package build_to: source build_extensions: .dart: - - ".orm.g.dart" - - ".mongodb.orm.g.dart" - - ".mysql.orm.g.dart" - - ".rethinkdb.orm.g.dart" - - ".postgresql.orm.g.dart" \ No newline at end of file + - ".angel_orm.g.part" + applies_builders: + ["source_gen|combining_builder", "source_gen|part_cleanup"] diff --git a/angel_orm_generator/lib/angel_orm_generator.dart b/angel_orm_generator/lib/angel_orm_generator.dart index f00f5914..a9d1dca9 100644 --- a/angel_orm_generator/lib/angel_orm_generator.dart +++ b/angel_orm_generator/lib/angel_orm_generator.dart @@ -1,5 +1,4 @@ //export 'src/mongodb_orm_generator.dart'; export 'src/orm_build_context.dart'; export 'src/orm_generator.dart'; -export 'src/postgresql_orm_generator.dart'; export 'src/readers.dart'; \ No newline at end of file diff --git a/angel_orm_generator/lib/src/mongodb_orm_generator.dart b/angel_orm_generator/lib/src/mongodb_orm_generator.dart deleted file mode 100644 index 35a7d368..00000000 --- a/angel_orm_generator/lib/src/mongodb_orm_generator.dart +++ /dev/null @@ -1,45 +0,0 @@ -import 'dart:async'; - -import 'package:analyzer/dart/element/element.dart'; -import 'package:angel_orm/angel_orm.dart'; -import 'package:build/build.dart'; -import 'package:code_builder/code_builder.dart' hide LibraryBuilder; -import 'package:path/path.dart' as p; -import 'package:source_gen/source_gen.dart'; - -import 'orm_build_context.dart'; - -Builder mongoDBOrmBuilder(_) { - return new LibraryBuilder(new MongoDBOrmGenerator(), - generatedExtension: '.mongodb.orm.g.dart'); -} - -/// Builder that generates `.orm.g.dart`, with an abstract `FooOrm` class. -class MongoDBOrmGenerator extends GeneratorForAnnotation { - final bool autoSnakeCaseNames; - final bool autoIdAndDateFields; - - MongoDBOrmGenerator({this.autoSnakeCaseNames, this.autoIdAndDateFields}); - - @override - Future generateForAnnotatedElement( - Element element, ConstantReader annotation, BuildStep buildStep) async { - if (element is ClassElement) { - var ctx = await buildOrmContext(element, annotation, buildStep, - buildStep.resolver, autoSnakeCaseNames, autoIdAndDateFields); - var lib = buildOrmLibrary(buildStep.inputId, ctx); - return lib.accept(new DartEmitter()).toString(); - } else { - throw 'The @Orm() annotation can only be applied to classes.'; - } - } - - Library buildOrmLibrary(AssetId inputId, OrmBuildContext ctx) { - return new Library((lib) { - // Add part of - var libFile = - p.setExtension(p.basename(inputId.uri.path), '.orm.g.dart'); - lib.body.add(new Code("part of '$libFile';")); - }); - } -} diff --git a/angel_orm_generator/lib/src/orm_generator.dart b/angel_orm_generator/lib/src/orm_generator.dart index 1fff92ff..85824d4f 100644 --- a/angel_orm_generator/lib/src/orm_generator.dart +++ b/angel_orm_generator/lib/src/orm_generator.dart @@ -1,18 +1,19 @@ import 'dart:async'; -import 'dart:collection'; import 'package:analyzer/dart/element/element.dart'; import 'package:angel_orm/angel_orm.dart'; +import 'package:angel_serialize_generator/angel_serialize_generator.dart'; import 'package:build/build.dart'; import 'package:code_builder/code_builder.dart' hide LibraryBuilder; -import 'package:path/path.dart' as p; -import 'package:recase/recase.dart'; import 'package:source_gen/source_gen.dart'; import 'orm_build_context.dart'; -Builder ormBuilder(_) { - return new LibraryBuilder(new OrmGenerator(), - generatedExtension: '.orm.g.dart'); +Builder ormBuilder(BuilderOptions options) { + return new SharedPartBuilder([ + new OrmGenerator( + autoSnakeCaseNames: options.config['auto_snake_case_names'] != false, + autoIdAndDateFields: options.config['auto_id_and_date_fields'] != false) + ], 'angel_orm'); } TypeReference futureOf(String type) { @@ -34,156 +35,151 @@ class OrmGenerator extends GeneratorForAnnotation { if (element is ClassElement) { var ctx = await buildOrmContext(element, annotation, buildStep, buildStep.resolver, autoSnakeCaseNames, autoIdAndDateFields); - var lib = buildOrmBaseLibrary(buildStep.inputId, ctx); + var lib = buildOrmLibrary(buildStep.inputId, ctx); return lib.accept(new DartEmitter()).toString(); } else { throw 'The @Orm() annotation can only be applied to classes.'; } } - Library buildOrmBaseLibrary(AssetId inputId, OrmBuildContext ctx) { + Library buildOrmLibrary(AssetId inputId, OrmBuildContext ctx) { return new Library((lib) { - // Necessary imports - var imports = new SplayTreeSet.from( - ['dart:async', p.basename(inputId.uri.path)]); + // Create `FooQuery` class + // Create `FooQueryWhere` class + lib.body.add(buildQueryClass(ctx)); + lib.body.add(buildWhereClass(ctx)); + }); + } - switch (ctx.ormAnnotation.type) { -// case OrmType.mongoDB: -// imports.add('package:mongo_dart/mongo_dart.dart'); -// break; - case OrmType.postgreSql: - imports.add('package:postgres/postgres.dart'); - break; - default: - break; - } + Class buildQueryClass(OrmBuildContext ctx) { + // TODO: Handle relations - lib.directives.addAll(imports.map((url) => new Directive.import(url))); - - // Add the corresponding `part` - String dbExtension; - - switch (ctx.ormAnnotation.type) { -// case OrmType.mongoDB: -// dbExtension = 'mongodb'; -// break; - case OrmType.rethinkDB: - dbExtension = 'rethinkdb'; - break; - case OrmType.mySql: - dbExtension = 'mysql'; - break; - case OrmType.postgreSql: - dbExtension = 'postgresql'; - break; - default: - throw 'Unsupported ORM type: ${ctx.ormAnnotation.type}'; - } - - var dbFile = p.setExtension( - p.basename(inputId.uri.path), '.$dbExtension.orm.g.dart'); - - lib.body.add(new Code("part '$dbFile';")); - - // Create `FooOrm` abstract class + return new Class((clazz) { var rc = ctx.buildContext.modelClassNameRecase; + var queryWhereType = refer('${rc.pascalCase}QueryWhere'); + clazz + ..name = '${rc.pascalCase}Query' + ..extend = new TypeReference((b) { + b + ..symbol = 'Query' + ..types.addAll([ + ctx.buildContext.modelClassType, + queryWhereType, + ]); + }); - lib.body.add(new Class((clazz) { - clazz - ..name = '${rc.pascalCase}Orm' - ..abstract = true; - - // Add factory constructors. - switch (ctx.ormAnnotation.type) { - case OrmType.postgreSql: - clazz.constructors.add(new Constructor((b) { - b - ..name = 'postgreSql' - ..factory = true - ..redirect = refer('PostgreSql${rc.pascalCase}Orm') - ..requiredParameters.add(new Parameter((b) { - b - ..name = 'connection' - ..type = refer('PostgreSQLConnection'); - })); - })); - dbExtension = 'postgresql'; - break; - default: - break; - } - - // Next, add method stubs. - // * getAll - // * getById - // * deleteById - // * updateX() - // * createX() - // * query() - - // getAll - clazz.methods.add(new Method((m) { - m - ..name = 'getAll' - ..returns = new TypeReference((b) => b - ..symbol = 'Future' - ..types.add(new TypeReference((b) => b - ..symbol = 'List' - ..types.add(ctx.buildContext.modelClassType)))); - })); - - // getById - clazz.methods.add(new Method((m) { - m - ..name = 'getById' - ..returns = futureOf(ctx.buildContext.modelClassName) - ..requiredParameters.add(new Parameter((b) => b - ..name = 'id' - ..type = refer('String'))); - })); - - // deleteById - clazz.methods.add(new Method((m) { - m - ..name = 'deleteById' - ..returns = futureOf(ctx.buildContext.modelClassName) - ..requiredParameters.add(new Parameter((b) => b - ..name = 'id' - ..type = refer('String'))); - })); - - // createX() - clazz.methods.add(new Method((m) { - m - ..name = 'create${ctx.buildContext.modelClassName}' - ..returns = futureOf(ctx.buildContext.modelClassName) - ..requiredParameters.add(new Parameter((b) => b - ..name = 'model' - ..type = ctx.buildContext.modelClassType)); - })); - - // updateX() - clazz.methods.add(new Method((m) { - m - ..name = 'update${ctx.buildContext.modelClassName}' - ..returns = futureOf(ctx.buildContext.modelClassName) - ..requiredParameters.add(new Parameter((b) => b - ..name = 'model' - ..type = ctx.buildContext.modelClassType)); - })); - - // query() - clazz.methods.add(new Method((m) { - m - ..name = 'query' - ..returns = refer('${rc.pascalCase}Query'); - })); + // Add tableName + clazz.methods.add(new Method((m) { + m + ..name = 'tableName' + ..annotations.add(refer('override')) + ..type = MethodType.getter + ..body = new Block((b) { + b.addExpression(literalString(ctx.tableName).returned); + }); })); - // Create `FooQuery` class - lib.body.add(new Class((clazz) { - clazz..name = '${rc.pascalCase}Query'; + // Add fields getter + clazz.methods.add(new Method((m) { + m + ..name = 'fields' + ..annotations.add(refer('override')) + ..type = MethodType.getter + ..body = new Block((b) { + var names = ctx.buildContext.fields + .map((f) => literalString(f.name)) + .toList(); + b.addExpression(literalConstList(names).returned); + }); + })); + + // Add where member + clazz.fields.add(new Field((b) { + b + ..annotations.add(refer('override')) + ..name = 'where' + ..modifier = FieldModifier.final$ + ..type = queryWhereType + ..assignment = queryWhereType.newInstance([]).code; + })); + + // Add deserialize() + clazz.methods.add(new Method((m) { + m + ..name = 'deserialize' + ..annotations.add(refer('override')) + ..requiredParameters.add(new Parameter((b) => b + ..name = 'row' + ..type = refer('List'))) + ..body = new Block((b) { + int i = 0; + var args = {}; + + for (var field in ctx.buildContext.fields) { + var type = convertTypeReference(field.type); + args[field.name] = (refer('row').index(literalNum(i))).asA(type); + } + + b.addExpression( + ctx.buildContext.modelClassType.newInstance([], args).returned); + }); })); }); } + + Class buildWhereClass(OrmBuildContext ctx) { + return new Class((clazz) { + var rc = ctx.buildContext.modelClassNameRecase; + clazz + ..name = '${rc.pascalCase}QueryWhere' + ..extend = refer('QueryWhere'); + + // Build expressionBuilders getter + clazz.methods.add(new Method((m) { + m + ..name = 'expressionBuilders' + ..annotations.add(refer('override')) + ..type = MethodType.getter + ..body = new Block((b) { + var references = ctx.buildContext.fields.map((f) => refer(f.name)); + b.addExpression(literalList(references).returned); + }); + })); + + // Add builders for each field + for (var field in ctx.buildContext.fields) { + // TODO: Handle fields with relations + Reference builderType; + + if (const TypeChecker.fromRuntime(String).isExactlyType(field.type)) { + builderType = refer('StringSqlExpressionBuilder'); + } else if (const TypeChecker.fromRuntime(bool) + .isExactlyType(field.type)) { + builderType = refer('BooleanSqlExpressionBuilder'); + } else if (const TypeChecker.fromRuntime(DateTime) + .isExactlyType(field.type)) { + builderType = refer('DateTimeSqlExpressionBuilder'); + } else if (const TypeChecker.fromRuntime(int) + .isExactlyType(field.type) || + const TypeChecker.fromRuntime(double).isExactlyType(field.type)) { + builderType = new TypeReference((b) => b + ..symbol = 'NumericSqlExpressionBuilder' + ..types.add(refer(field.type.name))); + } else { + throw new UnsupportedError( + 'Cannot generate ORM code for field of type ${field.type.name}.'); + } + + clazz.fields.add(new Field((b) { + b + ..name = field.name + ..modifier = FieldModifier.final$ + ..type = builderType + ..assignment = builderType.newInstance([ + literalString(ctx.buildContext.resolveFieldName(field.name)) + ]).code; + })); + } + }); + } } diff --git a/angel_orm_generator/lib/src/postgresql_orm_generator.dart b/angel_orm_generator/lib/src/postgresql_orm_generator.dart deleted file mode 100644 index 99d0af45..00000000 --- a/angel_orm_generator/lib/src/postgresql_orm_generator.dart +++ /dev/null @@ -1,348 +0,0 @@ -import 'dart:async'; - -import 'package:analyzer/dart/element/element.dart'; -import 'package:angel_orm/angel_orm.dart'; -import 'package:angel_serialize_generator/angel_serialize_generator.dart'; -import 'package:angel_serialize_generator/build_context.dart'; -import 'package:build/build.dart'; -import 'package:code_builder/code_builder.dart' hide LibraryBuilder; -import 'package:path/path.dart' as p; -import 'package:source_gen/source_gen.dart'; - -import 'orm_build_context.dart'; - -Builder postgreSqlOrmBuilder(_) { - return new LibraryBuilder(new PostgreSqlOrmGenerator(), - generatedExtension: '.postgresql.orm.g.dart'); -} - -/// Builder that generates `.orm.g.dart`, with an abstract `FooOrm` class. -class PostgreSqlOrmGenerator extends GeneratorForAnnotation { - final bool autoSnakeCaseNames; - final bool autoIdAndDateFields; - - PostgreSqlOrmGenerator({this.autoSnakeCaseNames, this.autoIdAndDateFields}); - - @override - Future generateForAnnotatedElement( - Element element, ConstantReader annotation, BuildStep buildStep) async { - if (element is ClassElement) { - var ctx = await buildOrmContext(element, annotation, buildStep, - buildStep.resolver, autoSnakeCaseNames, autoIdAndDateFields); - var lib = buildOrmLibrary(buildStep.inputId, ctx); - return lib.accept(new DartEmitter()).toString(); - } else { - throw 'The @Orm() annotation can only be applied to classes.'; - } - } - - Library buildOrmLibrary(AssetId inputId, OrmBuildContext ctx) { - return new Library((lib) { - // Add part of - var libFile = p.setExtension(p.basename(inputId.uri.path), '.orm.g.dart'); - lib.body.add(new Code("part of '$libFile';")); - - // Add _PostgresqlFooOrmImpl - lib.body.add(buildOrmClass(ctx)); - }); - } - - Class buildOrmClass(OrmBuildContext ctx) { - return new Class((clazz) { - var rc = ctx.buildContext.modelClassNameRecase; - clazz - ..name = 'PostgreSql${rc.pascalCase}Orm' - ..implements.add(refer('${rc.pascalCase}Orm')) - - // final PostgreSQLConnection connection; - ..fields.add(new Field((b) { - b - ..modifier = FieldModifier.final$ - ..name = 'connection' - ..type = refer('PostgreSQLConnection'); - })) - - // _PostgresqlFooOrmImpl(this.connection); - ..constructors.add(new Constructor((b) { - b - ..requiredParameters.add(new Parameter((b) => b - ..name = 'connection' - ..toThis = true)); - })) - ..methods.add(buildParseRowMethod(ctx)) - ..methods.add(buildGetById(ctx)) - ..methods.add(buildDeleteById(ctx)) - ..methods.add(buildGetAll(ctx)) - ..methods.add(buildCreate(ctx)) - ..methods.add(buildUpdate(ctx)) - ..methods.add(buildQuery(ctx)); - }); - } - - Method buildQuery(OrmBuildContext ctx) { - return new Method((m) { - m - ..name = 'query' - ..returns = refer('${ctx.buildContext.modelClassName}Query') - ..body = new Block((b) => b.addExpression(literalNull.returned)); - }); - } - - Method buildParseRowMethod(OrmBuildContext ctx) { - return new Method((m) { - m - ..name = 'parseRow' - ..static = true - ..returns = ctx.buildContext.modelClassType - ..requiredParameters.add(new Parameter((b) => b - ..name = 'row' - ..type = refer('List'))) - ..body = new Block((b) { - var args = {}; - - for (int i = 0; i < ctx.buildContext.fields.length; i++) { - var field = ctx.buildContext.fields[i]; - args[field.name] = refer('row') - .index(literalNum(i)) - .asA(convertTypeReference(field.type)); - } - - var returnValue = - ctx.buildContext.modelClassType.newInstance([], args); - b.addExpression(returnValue.returned); - }); - }); - } - - String buildFieldString(OrmBuildContext ctx) { - var queryString = new StringBuffer(); - int i = 0; - - for (var field in ctx.buildContext.fields) { - if (i++ > 0) queryString.write(','); - queryString.write(' ' + ctx.buildContext.resolveFieldName(field.name)); - } - return queryString.toString(); - } - - String buildQuotedFieldString(OrmBuildContext ctx) { - var queryString = new StringBuffer(); - int i = 0; - - for (var field in ctx.buildContext.fields) { - if (i++ > 0) queryString.write(','); - queryString - .write(' "' + ctx.buildContext.resolveFieldName(field.name) + '"'); - } - return queryString.toString(); - } - - String buildInsertionValueString(OrmBuildContext ctx) { - var buf = new StringBuffer('('); - - int i = 0; - - for (var field in ctx.buildContext.fields) { - if (i++ > 0) buf.write(','); - if (dateTimeTypeChecker.isAssignableFromType(field.type)) - buf.write( - 'CAST (@${field.name} AS ${ctx.columns[field.name].type.name})'); - else - buf.write('@${field.name}'); - } - - return buf.toString() + ')'; - } - - Expression buildSubstitutionValues(OrmBuildContext ctx) { - var values = {}; - - for (var field in ctx.buildContext.fields) { - values[literalString(field.name)] = refer('model').property(field.name); - } - - return literalMap(values); - } - - void applyQuery( - BlockBuilder b, String queryString, Expression substitutionValues) { - b.statements.add(refer('connection') - .property('query') - .call( - [literalString(queryString)], - substitutionValues == null - ? {} - : {'substitutionValues': substitutionValues}) - .awaited - .assignVar('r') - .statement); - } - - void applyQueryAndReturnOne( - BlockBuilder b, String queryString, Expression substitutionValues) { - applyQuery(b, queryString, substitutionValues); - b.addExpression( - (refer('parseRow').call([refer('r').property('first')])).returned); - } - - void applyQueryAndReturnList( - BlockBuilder b, String queryString, Expression substitutionValues) { - applyQuery(b, queryString, substitutionValues); - b.statements.add(new Code('return r.map(parseRow).toList();')); - } - - Method buildGetById(OrmBuildContext ctx) { - /* - @override - Future getById(id) async { - var r = await connection.query(''); - return parseRow(r.first); - } - */ - return new Method((m) { - m - ..name = 'getById' - ..annotations.add(refer('override')) - ..modifier = MethodModifier.async - ..requiredParameters.add(new Parameter((b) => b - ..name = 'id' - ..type = refer('String'))) - ..returns = new TypeReference((b) => b - ..symbol = 'Future' - ..types.add(ctx.buildContext.modelClassType)) - ..body = new Block((b) { - var fields = buildFieldString(ctx); - var queryString = - 'SELECT $fields FROM "${ctx.tableName}" WHERE id = @id LIMIT 1;'; - applyQueryAndReturnOne( - b, - queryString, - literalMap({ - 'id': refer('int').property('parse').call([refer('id')]) - })); - }); - }); - } - - Method buildDeleteById(OrmBuildContext ctx) { - /* - @override - Future getById(id) async { - var r = await connection.query(''); - return parseRow(r.first); - } - */ - return new Method((m) { - m - ..name = 'deleteById' - ..annotations.add(refer('override')) - ..modifier = MethodModifier.async - ..requiredParameters.add(new Parameter((b) => b - ..name = 'id' - ..type = refer('String'))) - ..returns = new TypeReference((b) => b - ..symbol = 'Future' - ..types.add(ctx.buildContext.modelClassType)) - ..body = new Block((b) { - var fields = buildQuotedFieldString(ctx); - var queryString = - 'DELETE FROM "${ctx.tableName}" WHERE id = @id RETURNING $fields;'; - applyQueryAndReturnOne( - b, - queryString, - literalMap({ - 'id': refer('int').property('parse').call([refer('id')]) - })); - }); - }); - } - - Method buildGetAll(OrmBuildContext ctx) { - /* - @override - Future> getAll() async { - var r = await connection - .query('SELECT id, name, created_at, updated_at FROM "authors";'); - return r.map(parseRow).toList(); - } - */ - return new Method((method) { - method - ..name = 'getAll' - ..modifier = MethodModifier.async - ..returns = refer('Future>') - ..annotations.add(refer('override')) - ..body = new Block((block) { - var fields = buildFieldString(ctx); - var queryString = 'SELECT $fields FROM "${ctx.tableName}";'; - applyQueryAndReturnList(block, queryString, null); - }); - }); - } - - Method buildCreate(OrmBuildContext ctx) { - /* - @override - Future createAuthor(Author model) async { - // ... - } - */ - return new Method((method) { - method - ..name = 'create${ctx.buildContext.modelClassName}' - ..modifier = MethodModifier.async - ..annotations.add(refer('override')) - ..returns = refer('Future<${ctx.buildContext.modelClassName}>') - ..requiredParameters.add(new Parameter((b) => b - ..name = 'model' - ..type = ctx.buildContext.modelClassType)) - ..body = new Block((block) { - if (ctx.buildContext.autoIdAndDateFields != false) { - // If we are auto-managing created+updated at, do so now - block.statements.add(new Code( - 'model = model.copyWith(createdAt: new DateTime.now(), updatedAt: new DateTime.now());')); - } - - var fields = buildQuotedFieldString(ctx); - var fieldSet = buildInsertionValueString(ctx); - var queryString = - 'INSERT INTO "${ctx.tableName}" ($fields) VALUES $fieldSet RETURNING $fields;'; - applyQueryAndReturnOne( - block, queryString, buildSubstitutionValues(ctx)); - }); - }); - } - - Method buildUpdate(OrmBuildContext ctx) { - /* - @override - Future updateAuthor(Author model) async { - // ... - } - */ - return new Method((method) { - method - ..name = 'update${ctx.buildContext.modelClassName}' - ..modifier = MethodModifier.async - ..annotations.add(refer('override')) - ..returns = refer('Future<${ctx.buildContext.modelClassName}>') - ..requiredParameters.add(new Parameter((b) => b - ..name = 'model' - ..type = ctx.buildContext.modelClassType)) - ..body = new Block((block) { - if (ctx.buildContext.autoIdAndDateFields != false) { - // If we are auto-managing created+updated at, do so now - block.statements.add(new Code( - 'model = model.copyWith(updatedAt: new DateTime.now());')); - } - - var fields = buildQuotedFieldString(ctx); - var fieldSet = buildInsertionValueString(ctx); - var queryString = - 'UPDATE "${ctx.tableName}" SET ($fields) = $fieldSet RETURNING $fields;'; - applyQueryAndReturnOne( - block, queryString, buildSubstitutionValues(ctx)); - }); - }); - } -} diff --git a/angel_orm_generator/lib/src/readers.dart b/angel_orm_generator/lib/src/readers.dart index f14e6f2f..00d5c18d 100644 --- a/angel_orm_generator/lib/src/readers.dart +++ b/angel_orm_generator/lib/src/readers.dart @@ -5,10 +5,7 @@ import 'package:source_gen/source_gen.dart'; const TypeChecker columnTypeChecker = const TypeChecker.fromRuntime(Column); Orm reviveORMAnnotation(ConstantReader reader) { - return Orm( - OrmType.values[reader.read('type').objectValue.getField('index').toIntValue()], - tableName: reader.peek('tableName')?.stringValue, - ); + return Orm(tableName: reader.peek('tableName')?.stringValue); } class ColumnReader { diff --git a/angel_orm_generator/pubspec.yaml b/angel_orm_generator/pubspec.yaml index f0a72467..ccba3d07 100644 --- a/angel_orm_generator/pubspec.yaml +++ b/angel_orm_generator/pubspec.yaml @@ -8,7 +8,7 @@ environment: dependencies: angel_orm: ^2.0.0-dev angel_serialize_generator: ^2.0.0 - build: ^0.12.0 + build: ">=0.12.0 <2.0.0" build_config: ^0.3.0 code_builder: ^3.0.0 inflection: @@ -23,6 +23,6 @@ dev_dependencies: angel_framework: ^2.0.0-alpha #angel_migration: ^1.0.0-alpha #angel_test: ^1.0.0 - build_runner: ^0.10.0 + build_runner: ^1.0.0 postgres: ^1.0.0 test: ^1.0.0 diff --git a/angel_orm_generator/test/models/author.dart b/angel_orm_generator/test/models/author.dart index bb103d0c..ed045366 100644 --- a/angel_orm_generator/test/models/author.dart +++ b/angel_orm_generator/test/models/author.dart @@ -9,7 +9,7 @@ part 'author.g.dart'; part 'author.serializer.g.dart'; @serializable -@postgreSqlOrm +@orm class _Author extends Model { @Column(length: 255, indexType: IndexType.unique, defaultValue: 'Tobe Osakwe') String name; diff --git a/angel_orm_generator/test/models/author.g.dart b/angel_orm_generator/test/models/author.g.dart index 1f4abf5f..6111e407 100644 --- a/angel_orm_generator/test/models/author.g.dart +++ b/angel_orm_generator/test/models/author.g.dart @@ -2,6 +2,52 @@ part of angel_orm.generator.models.author; +// ************************************************************************** +// OrmGenerator +// ************************************************************************** + +class AuthorQuery extends Query { + @override + final AuthorQueryWhere where = new AuthorQueryWhere(); + + @override + get tableName { + return 'authors'; + } + + @override + get fields { + return const ['id', 'name', 'createdAt', 'updatedAt']; + } + + @override + deserialize(List row) { + return new Author( + id: (row[0] as String), + name: (row[0] as String), + createdAt: (row[0] as DateTime), + updatedAt: (row[0] as DateTime)); + } +} + +class AuthorQueryWhere extends QueryWhere { + final StringSqlExpressionBuilder id = new StringSqlExpressionBuilder('id'); + + final StringSqlExpressionBuilder name = + new StringSqlExpressionBuilder('name'); + + final DateTimeSqlExpressionBuilder createdAt = + new DateTimeSqlExpressionBuilder('created_at'); + + final DateTimeSqlExpressionBuilder updatedAt = + new DateTimeSqlExpressionBuilder('updated_at'); + + @override + get expressionBuilders { + return [id, name, createdAt, updatedAt]; + } +} + // ************************************************************************** // JsonModelGenerator // ************************************************************************** @@ -39,6 +85,11 @@ class Author extends _Author { other.updatedAt == updatedAt; } + @override + int get hashCode { + return hashObjects([id, name, createdAt, updatedAt]); + } + Map toJson() { return AuthorSerializer.toMap(this); } diff --git a/angel_orm_generator/test/models/book.dart b/angel_orm_generator/test/models/book.dart index 4180471a..fa675b3c 100644 --- a/angel_orm_generator/test/models/book.dart +++ b/angel_orm_generator/test/models/book.dart @@ -8,7 +8,7 @@ part 'book.g.dart'; part 'book.serializer.g.dart'; @serializable -@postgreSqlOrm +@orm class _Book extends Model { @belongsTo Author author; diff --git a/angel_orm_generator/test/models/book.g.dart b/angel_orm_generator/test/models/book.g.dart index 72fc7961..e9f59c6f 100644 --- a/angel_orm_generator/test/models/book.g.dart +++ b/angel_orm_generator/test/models/book.g.dart @@ -67,6 +67,12 @@ class Book extends _Book { other.updatedAt == updatedAt; } + @override + int get hashCode { + return hashObjects( + [id, author, partnerAuthor, authorId, name, createdAt, updatedAt]); + } + Map toJson() { return BookSerializer.toMap(this); } diff --git a/angel_orm_generator/test/models/car.dart b/angel_orm_generator/test/models/car.dart index 714be540..3cf1a7b8 100644 --- a/angel_orm_generator/test/models/car.dart +++ b/angel_orm_generator/test/models/car.dart @@ -7,7 +7,7 @@ part 'car.g.dart'; part 'car.serializer.g.dart'; @serializable -@postgreSqlOrm +@orm class _Car extends Model { String make; String description; diff --git a/angel_orm_generator/test/models/car.g.dart b/angel_orm_generator/test/models/car.g.dart index c4f53c6b..021a386d 100644 --- a/angel_orm_generator/test/models/car.g.dart +++ b/angel_orm_generator/test/models/car.g.dart @@ -2,6 +2,80 @@ part of angel_orm.generator.models.car; +// ************************************************************************** +// OrmGenerator +// ************************************************************************** + +class CarQuery extends Query { + @override + final CarQueryWhere where = new CarQueryWhere(); + + @override + get tableName { + return 'cars'; + } + + @override + get fields { + return const [ + 'id', + 'make', + 'description', + 'familyFriendly', + 'recalledAt', + 'createdAt', + 'updatedAt' + ]; + } + + @override + deserialize(List row) { + return new Car( + id: (row[0] as String), + make: (row[0] as String), + description: (row[0] as String), + familyFriendly: (row[0] as bool), + recalledAt: (row[0] as DateTime), + createdAt: (row[0] as DateTime), + updatedAt: (row[0] as DateTime)); + } +} + +class CarQueryWhere extends QueryWhere { + final StringSqlExpressionBuilder id = new StringSqlExpressionBuilder('id'); + + final StringSqlExpressionBuilder make = + new StringSqlExpressionBuilder('make'); + + final StringSqlExpressionBuilder description = + new StringSqlExpressionBuilder('description'); + + final BooleanSqlExpressionBuilder familyFriendly = + new BooleanSqlExpressionBuilder('family_friendly'); + + final DateTimeSqlExpressionBuilder recalledAt = + new DateTimeSqlExpressionBuilder('recalled_at'); + + final DateTimeSqlExpressionBuilder createdAt = + new DateTimeSqlExpressionBuilder('created_at'); + + final DateTimeSqlExpressionBuilder updatedAt = + new DateTimeSqlExpressionBuilder('updated_at'); + + @override + get expressionBuilders { + return [ + id, + make, + description, + familyFriendly, + recalledAt, + createdAt, + updatedAt + ]; + } +} + // ************************************************************************** // JsonModelGenerator // ************************************************************************** @@ -67,6 +141,19 @@ class Car extends _Car { other.updatedAt == updatedAt; } + @override + int get hashCode { + return hashObjects([ + id, + make, + description, + familyFriendly, + recalledAt, + createdAt, + updatedAt + ]); + } + Map toJson() { return CarSerializer.toMap(this); } diff --git a/angel_orm_generator/test/models/customer.dart b/angel_orm_generator/test/models/customer.dart index 1c25c441..0808bdfa 100644 --- a/angel_orm_generator/test/models/customer.dart +++ b/angel_orm_generator/test/models/customer.dart @@ -6,7 +6,7 @@ import 'package:angel_serialize/angel_serialize.dart'; part 'customer.g.dart'; part 'customer.serializer.g.dart'; -@postgreSqlOrm +@orm @serializable class _Customer extends Model { } \ No newline at end of file diff --git a/angel_orm_generator/test/models/customer.g.dart b/angel_orm_generator/test/models/customer.g.dart index b9938637..c97ac796 100644 --- a/angel_orm_generator/test/models/customer.g.dart +++ b/angel_orm_generator/test/models/customer.g.dart @@ -2,6 +2,48 @@ part of angel_orm_generator.test.models.customer; +// ************************************************************************** +// OrmGenerator +// ************************************************************************** + +class CustomerQuery extends Query { + @override + final CustomerQueryWhere where = new CustomerQueryWhere(); + + @override + get tableName { + return 'customers'; + } + + @override + get fields { + return const ['id', 'createdAt', 'updatedAt']; + } + + @override + deserialize(List row) { + return new Customer( + id: (row[0] as String), + createdAt: (row[0] as DateTime), + updatedAt: (row[0] as DateTime)); + } +} + +class CustomerQueryWhere extends QueryWhere { + final StringSqlExpressionBuilder id = new StringSqlExpressionBuilder('id'); + + final DateTimeSqlExpressionBuilder createdAt = + new DateTimeSqlExpressionBuilder('created_at'); + + final DateTimeSqlExpressionBuilder updatedAt = + new DateTimeSqlExpressionBuilder('updated_at'); + + @override + get expressionBuilders { + return [id, createdAt, updatedAt]; + } +} + // ************************************************************************** // JsonModelGenerator // ************************************************************************** @@ -33,6 +75,11 @@ class Customer extends _Customer { other.updatedAt == updatedAt; } + @override + int get hashCode { + return hashObjects([id, createdAt, updatedAt]); + } + Map toJson() { return CustomerSerializer.toMap(this); } diff --git a/angel_orm_generator/test/models/foot.dart b/angel_orm_generator/test/models/foot.dart index 6199a134..39c57947 100644 --- a/angel_orm_generator/test/models/foot.dart +++ b/angel_orm_generator/test/models/foot.dart @@ -7,7 +7,7 @@ part 'foot.g.dart'; part 'foot.serializer.g.dart'; @serializable -@postgreSqlOrm +@orm class _Foot extends Model { int legId, nToes; } \ No newline at end of file diff --git a/angel_orm_generator/test/models/foot.g.dart b/angel_orm_generator/test/models/foot.g.dart index 6147fc76..e7f01d0a 100644 --- a/angel_orm_generator/test/models/foot.g.dart +++ b/angel_orm_generator/test/models/foot.g.dart @@ -2,6 +2,56 @@ part of angel_orm_generator.test.models.foot; +// ************************************************************************** +// OrmGenerator +// ************************************************************************** + +class FootQuery extends Query { + @override + final FootQueryWhere where = new FootQueryWhere(); + + @override + get tableName { + return 'foots'; + } + + @override + get fields { + return const ['id', 'legId', 'nToes', 'createdAt', 'updatedAt']; + } + + @override + deserialize(List row) { + return new Foot( + id: (row[0] as String), + legId: (row[0] as int), + nToes: (row[0] as int), + createdAt: (row[0] as DateTime), + updatedAt: (row[0] as DateTime)); + } +} + +class FootQueryWhere extends QueryWhere { + final StringSqlExpressionBuilder id = new StringSqlExpressionBuilder('id'); + + final NumericSqlExpressionBuilder legId = + new NumericSqlExpressionBuilder('leg_id'); + + final NumericSqlExpressionBuilder nToes = + new NumericSqlExpressionBuilder('n_toes'); + + final DateTimeSqlExpressionBuilder createdAt = + new DateTimeSqlExpressionBuilder('created_at'); + + final DateTimeSqlExpressionBuilder updatedAt = + new DateTimeSqlExpressionBuilder('updated_at'); + + @override + get expressionBuilders { + return [id, legId, nToes, createdAt, updatedAt]; + } +} + // ************************************************************************** // JsonModelGenerator // ************************************************************************** @@ -48,6 +98,11 @@ class Foot extends _Foot { other.updatedAt == updatedAt; } + @override + int get hashCode { + return hashObjects([id, legId, nToes, createdAt, updatedAt]); + } + Map toJson() { return FootSerializer.toMap(this); } diff --git a/angel_orm_generator/test/models/fruit.dart b/angel_orm_generator/test/models/fruit.dart index f9d812ac..3af538ed 100644 --- a/angel_orm_generator/test/models/fruit.dart +++ b/angel_orm_generator/test/models/fruit.dart @@ -7,7 +7,7 @@ part 'fruit.g.dart'; part 'fruit.serializer.g.dart'; @serializable -@postgreSqlOrm +@orm class _Fruit extends Model { int treeId; String commonName; diff --git a/angel_orm_generator/test/models/fruit.g.dart b/angel_orm_generator/test/models/fruit.g.dart index 71521cf5..613bb016 100644 --- a/angel_orm_generator/test/models/fruit.g.dart +++ b/angel_orm_generator/test/models/fruit.g.dart @@ -2,6 +2,56 @@ part of angel_orm_generator.test.models.fruit; +// ************************************************************************** +// OrmGenerator +// ************************************************************************** + +class FruitQuery extends Query { + @override + final FruitQueryWhere where = new FruitQueryWhere(); + + @override + get tableName { + return 'fruits'; + } + + @override + get fields { + return const ['id', 'treeId', 'commonName', 'createdAt', 'updatedAt']; + } + + @override + deserialize(List row) { + return new Fruit( + id: (row[0] as String), + treeId: (row[0] as int), + commonName: (row[0] as String), + createdAt: (row[0] as DateTime), + updatedAt: (row[0] as DateTime)); + } +} + +class FruitQueryWhere extends QueryWhere { + final StringSqlExpressionBuilder id = new StringSqlExpressionBuilder('id'); + + final NumericSqlExpressionBuilder treeId = + new NumericSqlExpressionBuilder('tree_id'); + + final StringSqlExpressionBuilder commonName = + new StringSqlExpressionBuilder('common_name'); + + final DateTimeSqlExpressionBuilder createdAt = + new DateTimeSqlExpressionBuilder('created_at'); + + final DateTimeSqlExpressionBuilder updatedAt = + new DateTimeSqlExpressionBuilder('updated_at'); + + @override + get expressionBuilders { + return [id, treeId, commonName, createdAt, updatedAt]; + } +} + // ************************************************************************** // JsonModelGenerator // ************************************************************************** @@ -49,6 +99,11 @@ class Fruit extends _Fruit { other.updatedAt == updatedAt; } + @override + int get hashCode { + return hashObjects([id, treeId, commonName, createdAt, updatedAt]); + } + Map toJson() { return FruitSerializer.toMap(this); } diff --git a/angel_orm_generator/test/models/leg.dart b/angel_orm_generator/test/models/leg.dart index f20e8815..365fa357 100644 --- a/angel_orm_generator/test/models/leg.dart +++ b/angel_orm_generator/test/models/leg.dart @@ -8,7 +8,7 @@ part 'leg.g.dart'; part 'leg.serializer.g.dart'; @serializable -@postgreSqlOrm +@orm class _Leg extends Model { @hasOne Foot foot; diff --git a/angel_orm_generator/test/models/leg.g.dart b/angel_orm_generator/test/models/leg.g.dart index 386a68b7..0d7916d6 100644 --- a/angel_orm_generator/test/models/leg.g.dart +++ b/angel_orm_generator/test/models/leg.g.dart @@ -48,6 +48,11 @@ class Leg extends _Leg { other.updatedAt == updatedAt; } + @override + int get hashCode { + return hashObjects([id, foot, name, createdAt, updatedAt]); + } + Map toJson() { return LegSerializer.toMap(this); } diff --git a/angel_orm_generator/test/models/order.dart b/angel_orm_generator/test/models/order.dart index 28861222..b59c6fca 100644 --- a/angel_orm_generator/test/models/order.dart +++ b/angel_orm_generator/test/models/order.dart @@ -7,7 +7,7 @@ import 'customer.dart'; part 'order.g.dart'; part 'order.serializer.g.dart'; -@postgreSqlOrm +@orm @serializable class _Order extends Model { @Join(Customer, CustomerFields.id) diff --git a/angel_orm_generator/test/models/order.g.dart b/angel_orm_generator/test/models/order.g.dart index 76b0adba..7c95f97b 100644 --- a/angel_orm_generator/test/models/order.g.dart +++ b/angel_orm_generator/test/models/order.g.dart @@ -2,6 +2,80 @@ part of angel_orm_generator.test.models.order; +// ************************************************************************** +// OrmGenerator +// ************************************************************************** + +class OrderQuery extends Query { + @override + final OrderQueryWhere where = new OrderQueryWhere(); + + @override + get tableName { + return 'orders'; + } + + @override + get fields { + return const [ + 'id', + 'customerId', + 'employeeId', + 'orderDate', + 'shipperId', + 'createdAt', + 'updatedAt' + ]; + } + + @override + deserialize(List row) { + return new Order( + id: (row[0] as String), + customerId: (row[0] as int), + employeeId: (row[0] as int), + orderDate: (row[0] as DateTime), + shipperId: (row[0] as int), + createdAt: (row[0] as DateTime), + updatedAt: (row[0] as DateTime)); + } +} + +class OrderQueryWhere extends QueryWhere { + final StringSqlExpressionBuilder id = new StringSqlExpressionBuilder('id'); + + final NumericSqlExpressionBuilder customerId = + new NumericSqlExpressionBuilder('customer_id'); + + final NumericSqlExpressionBuilder employeeId = + new NumericSqlExpressionBuilder('employee_id'); + + final DateTimeSqlExpressionBuilder orderDate = + new DateTimeSqlExpressionBuilder('order_date'); + + final NumericSqlExpressionBuilder shipperId = + new NumericSqlExpressionBuilder('shipper_id'); + + final DateTimeSqlExpressionBuilder createdAt = + new DateTimeSqlExpressionBuilder('created_at'); + + final DateTimeSqlExpressionBuilder updatedAt = + new DateTimeSqlExpressionBuilder('updated_at'); + + @override + get expressionBuilders { + return [ + id, + customerId, + employeeId, + orderDate, + shipperId, + createdAt, + updatedAt + ]; + } +} + // ************************************************************************** // JsonModelGenerator // ************************************************************************** @@ -67,6 +141,19 @@ class Order extends _Order { other.updatedAt == updatedAt; } + @override + int get hashCode { + return hashObjects([ + id, + customerId, + employeeId, + orderDate, + shipperId, + createdAt, + updatedAt + ]); + } + Map toJson() { return OrderSerializer.toMap(this); } diff --git a/angel_orm_generator/test/models/role.dart b/angel_orm_generator/test/models/role.dart index dcef4bc4..ae27ec7a 100644 --- a/angel_orm_generator/test/models/role.dart +++ b/angel_orm_generator/test/models/role.dart @@ -7,7 +7,7 @@ part 'role.g.dart'; part 'role.serializer.g.dart'; @serializable -@postgreSqlOrm +@orm class _Role extends Model { String name; } \ No newline at end of file diff --git a/angel_orm_generator/test/models/role.g.dart b/angel_orm_generator/test/models/role.g.dart index f2ef978e..a7f339df 100644 --- a/angel_orm_generator/test/models/role.g.dart +++ b/angel_orm_generator/test/models/role.g.dart @@ -2,6 +2,52 @@ part of angel_orm_generator.test.models.role; +// ************************************************************************** +// OrmGenerator +// ************************************************************************** + +class RoleQuery extends Query { + @override + final RoleQueryWhere where = new RoleQueryWhere(); + + @override + get tableName { + return 'roles'; + } + + @override + get fields { + return const ['id', 'name', 'createdAt', 'updatedAt']; + } + + @override + deserialize(List row) { + return new Role( + id: (row[0] as String), + name: (row[0] as String), + createdAt: (row[0] as DateTime), + updatedAt: (row[0] as DateTime)); + } +} + +class RoleQueryWhere extends QueryWhere { + final StringSqlExpressionBuilder id = new StringSqlExpressionBuilder('id'); + + final StringSqlExpressionBuilder name = + new StringSqlExpressionBuilder('name'); + + final DateTimeSqlExpressionBuilder createdAt = + new DateTimeSqlExpressionBuilder('created_at'); + + final DateTimeSqlExpressionBuilder updatedAt = + new DateTimeSqlExpressionBuilder('updated_at'); + + @override + get expressionBuilders { + return [id, name, createdAt, updatedAt]; + } +} + // ************************************************************************** // JsonModelGenerator // ************************************************************************** @@ -39,6 +85,11 @@ class Role extends _Role { other.updatedAt == updatedAt; } + @override + int get hashCode { + return hashObjects([id, name, createdAt, updatedAt]); + } + Map toJson() { return RoleSerializer.toMap(this); } diff --git a/angel_orm_generator/test/models/tree.dart b/angel_orm_generator/test/models/tree.dart index be77b171..ceb93600 100644 --- a/angel_orm_generator/test/models/tree.dart +++ b/angel_orm_generator/test/models/tree.dart @@ -8,7 +8,7 @@ part 'tree.g.dart'; part 'tree.serializer.g.dart'; @serializable -@postgreSqlOrm +@orm class _Tree extends Model { @Column(indexType: IndexType.unique, type: ColumnType.smallInt) int rings; diff --git a/angel_orm_generator/test/models/tree.g.dart b/angel_orm_generator/test/models/tree.g.dart index 2e3b5542..5cf2a90a 100644 --- a/angel_orm_generator/test/models/tree.g.dart +++ b/angel_orm_generator/test/models/tree.g.dart @@ -55,6 +55,11 @@ class Tree extends _Tree { other.updatedAt == updatedAt; } + @override + int get hashCode { + return hashObjects([id, rings, fruits, createdAt, updatedAt]); + } + Map toJson() { return TreeSerializer.toMap(this); } diff --git a/angel_orm_generator/test/models/user.dart b/angel_orm_generator/test/models/user.dart index 33ba9beb..7588cf62 100644 --- a/angel_orm_generator/test/models/user.dart +++ b/angel_orm_generator/test/models/user.dart @@ -8,7 +8,7 @@ part 'user.g.dart'; part 'user.serializer.g.dart'; @serializable -@postgreSqlOrm +@orm class _User extends Model { String username, password, email; diff --git a/angel_orm_generator/test/models/user.g.dart b/angel_orm_generator/test/models/user.g.dart index 82b96a87..ec880b55 100644 --- a/angel_orm_generator/test/models/user.g.dart +++ b/angel_orm_generator/test/models/user.g.dart @@ -69,6 +69,12 @@ class User extends _User { other.updatedAt == updatedAt; } + @override + int get hashCode { + return hashObjects( + [id, username, password, email, roles, createdAt, updatedAt]); + } + Map toJson() { return UserSerializer.toMap(this); } diff --git a/angel_orm_generator/test/standalone_test.dart b/angel_orm_generator/test/standalone_test.dart index 2ff469ac..7114af5f 100644 --- a/angel_orm_generator/test/standalone_test.dart +++ b/angel_orm_generator/test/standalone_test.dart @@ -5,18 +5,17 @@ import 'package:angel_orm/angel_orm.dart'; import 'package:postgres/postgres.dart'; import 'package:test/test.dart'; import 'models/car.dart'; -import 'models/car.orm.g.dart'; import 'common.dart'; -final DateTime MILENNIUM = new DateTime.utc(2000, 1, 1); +final DateTime y2k = new DateTime.utc(2000, 1, 1); main() { test('to where', () { var query = new CarQuery(); query.where ..familyFriendly.equals(true) - ..recalledAt.lessThanOrEqualTo(MILENNIUM, includeTime: false); - var whereClause = query.where.toWhereClause(); + ..recalledAt.lessThanOrEqualTo(y2k, includeTime: false); + var whereClause = query.where.compile(tableName: 'cars'); print('Where clause: $whereClause'); expect(whereClause, 'WHERE cars.family_friendly = TRUE AND cars.recalled_at <= \'2000-01-01\''); @@ -28,23 +27,20 @@ main() { 'Mazda', 'CX9', true, - dateYmdHms.format(MILENNIUM), - dateYmdHms.format(MILENNIUM), - dateYmdHms.format(MILENNIUM) + dateYmdHms.format(y2k), + dateYmdHms.format(y2k), + dateYmdHms.format(y2k) ]; print(row); - var car = PostgreSqlCarOrm.parseRow(row); + var car = new CarQuery().deserialize(row); print(car.toJson()); expect(car.id, '0'); expect(car.make, 'Mazda'); expect(car.description, 'CX9'); expect(car.familyFriendly, true); - expect(MILENNIUM.toIso8601String(), - startsWith(car.recalledAt.toIso8601String())); - expect(MILENNIUM.toIso8601String(), - startsWith(car.createdAt.toIso8601String())); - expect(MILENNIUM.toIso8601String(), - startsWith(car.updatedAt.toIso8601String())); + expect(y2k.toIso8601String(), startsWith(car.recalledAt.toIso8601String())); + expect(y2k.toIso8601String(), startsWith(car.createdAt.toIso8601String())); + expect(y2k.toIso8601String(), startsWith(car.updatedAt.toIso8601String())); }); group('queries', () { @@ -56,7 +52,7 @@ main() { group('selects', () { test('select all', () async { - var cars = await CarQuery.getAll(connection).toList(); + var cars = await CarQuery.getAll(connection); expect(cars, []); }); @@ -72,12 +68,12 @@ main() { test('where clause is applied', () async { var query = new CarQuery()..where.familyFriendly.equals(true); - var cars = await query.get(connection).toList(); + var cars = await query.get(connection); expect(cars, isEmpty); var sportsCars = new CarQuery()..where.familyFriendly.notEquals(true); - cars = await sportsCars.get(connection).toList(); - print(cars.map((c) => c.toJson()).toList()); + cars = await sportsCars.get(connection); + print(cars.map((c) => c.toJson())); var car = cars.first; expect(car.make, ferrari.make); @@ -93,27 +89,26 @@ main() { query1 ..union(query2) ..unionAll(query3); - print(query1.toSql()); + print(query1.compile()); - var cars = await query1.get(connection).toList(); + var cars = await query1.get(connection); expect(cars, hasLength(1)); }); test('or clause', () async { var query = new CarQuery() ..where.make.like('Fer%') - ..or(new CarQueryWhere() - ..familyFriendly.equals(true) - ..make.equals('Honda')); - print(query.toSql()); - var cars = await query.get(connection).toList(); + ..orWhere((where) => + where..familyFriendly.equals(true)..make.equals('Honda')); + print(query.compile()); + var cars = await query.get(connection); expect(cars, hasLength(1)); }); test('limit obeyed', () async { - var query = new CarQuery()..limit = 0; - print(query.toSql()); - var cars = await query.get(connection).toList(); + var query = new CarQuery()..limit(0); + print(query.compile()); + var cars = await query.get(connection); expect(cars, isEmpty); }); @@ -126,28 +121,28 @@ main() { var car = await CarQuery.deleteOne(int.parse(ferrari.id), connection); expect(car.toJson(), ferrari.toJson()); - var cars = await CarQuery.getAll(connection).toList(); + var cars = await CarQuery.getAll(connection); expect(cars, isEmpty); }); test('delete stream', () async { var query = new CarQuery()..where.make.equals('Ferrari'); query.or(new CarQueryWhere()..familyFriendly.equals(true)); - print(query.toSql('DELETE FROM "cars"')); - var cars = await query.delete(connection).toList(); + print(query.compile('DELETE FROM "cars"')); + var cars = await query.delete(connection); expect(cars, hasLength(1)); expect(cars.first.toJson(), ferrari.toJson()); }); test('update', () async { var query = new CarQuery()..where.id.equals(int.parse(ferrari.id)); - var cars = await query.update(connection, make: 'Hyundai').toList(); + var cars = await query.update(connection, make: 'Hyundai'); expect(cars, hasLength(1)); expect(cars.first.make, 'Hyundai'); }); test('update car', () async { - var cloned = ferrari.clone()..make = 'Angel'; + var cloned = ferrari.copyWith(make: 'Angel'); var car = await CarQuery.updateCar(connection, cloned); print(car.toJson()); expect(car.toJson(), cloned.toJson()); @@ -166,8 +161,7 @@ main() { expect(car.make, 'Honda'); expect(car.description, 'Hello'); expect(car.familyFriendly, isTrue); - expect( - dateYmdHms.format(car.recalledAt), dateYmdHms.format(recalledAt)); + expect(dateYmdHms.format(car.recalledAt), dateYmdHms.format(recalledAt)); expect(car.createdAt, allOf(isNotNull, equals(car.updatedAt))); });