我正在尝试为我的 flutter 数据库 API 编写一个测试文件。我有一个预填充的数据库,我想在该数据库上执行测试,该数据库存储在 asset/database/ 中,名为database.db。
pubspec.yaml:
dev_dependencies:
flutter_lints: ^4.0.0
flutter_launcher_icons: ^0.13.1
flutter_test:
sdk: flutter
sqflite_common_ffi: ^2.3.3
flutter:
uses-material-design: true
generate: true
assets:
- assets/images/
- assets/database/
database_api.dart:
import 'dart:io';
import 'package:flutter/services.dart';
import 'package:path/path.dart';
import 'package:sqflite/sqflite.dart';
class DatabaseAPI {
static final DatabaseAPI _instance = DatabaseAPI._internal();
static Database? _db;
final String _dbName = "database.db";
DatabaseAPI._internal();
factory DatabaseAPI() {
return _instance;
}
Future<Database?> get db async {
if (_db != null) {
return _db;
} else {
_db = await _initDB();
return _db;
}
}
Future<Database> _initDB() async {
final path = join(await getDatabasesPath(), _dbName);
final exist = await databaseExists(path);
if(!exist) {
try {
ByteData data = await rootBundle.load(join('assets', 'database', _dbName));
List<int> bytes = data.buffer.asUint8List();
await File(path).writeAsBytes(bytes);
} catch (error) {
throw Exception('Error copying database: $error');
}
}
return await openDatabase(path);
}
Future<String> fetchLanguage() async {
var dbClient = await db;
final List<Map<String, Object?>> list = await dbClient!.query('language');
var lang = list[0]['selected'];
return lang.toString();
}
}
这就是我编写测试文件的方式
database_api_test.dart:
import 'package:flutter_test/flutter_test.dart';
import 'package:drinking_game/db_api/database_api.dart';
import 'package:sqflite_common_ffi/sqflite_ffi.dart';
void main() {
TestWidgetsFlutterBinding.ensureInitialized();
databaseFactory = databaseFactoryFfi;
test('fetchLanguage returns correct data', () async {
var api = DatabaseAPI();
var lang = await api.fetchLanguage();
print(lang);
expect(lang, "Italiano");
});
}
生成的错误是:
Exception: Error copying database: Unable to load asset: "assets\database\database.db".
The asset does not exist or has empty data.
package:drinking_game/db_api/new_database_api.dart 49:9 DatabaseAPI._initDB
但是这个错误是在我运行测试时出现的,当我进行正常构建时,我没有错误。我该如何解决这个问题?
测试环境不是正常的应用程序环境,这就是您在测试时看到此问题的原因。 您需要执行以下一项或两项操作:
testWidgets('myTest', (tester)
而不是 test('myTest', ()
setUp
方法中,将您想要在测试中访问的文件从资产目录复制到可访问的目录,例如 // copy the test database files from assets to documents directory
Directory directory = await getApplicationDocumentsDirectory();
for (final filename in [db1, db2, db3]) {
var uploadFilePath = join(directory.path, filename);
ByteData data = await rootBundle.load("assets/$filename");
final buffer = data.buffer;
File(uploadFilePath).writeAsBytesSync(
buffer.asUint8List(data.offsetInBytes, data.lengthInBytes));
}