【发布时间】:2020-02-02 21:53:46
【问题描述】:
我有一个文件fetchPosts() 负责从服务器获取新帖子并将它们存储在本地sqlite 数据库中。
按照 sqflite doc 的建议,我将单个 ref 存储到我的数据库中。
这是我的database.dart文件的内容:
import 'dart:async';
import 'package:path/path.dart';
import 'package:sqflite/sqflite.dart';
class DBProvider {
DBProvider._();
static final DBProvider db = DBProvider._();
static Database _database;
static Future<Database> get database async {
if (_database != null) return _database;
// if _database is null, we instantiate it
_database = await _initDB();
return _database;
}
static Future<Database> _initDB() async {
final dbPath = await getDatabasesPath();
String path = join(dbPath, 'demo.db');
return await openDatabase(path, version: 1, onCreate: _onCreate);
}
static Future<String> insert(String table, Map<String, dynamic> values) async { /* insert the record*/ }
// Other functions like update, delete etc.
}
然后我在我的fetchPosts.dart 文件中使用它
import 'dart:convert';
import 'package:http/http.dart' as http;
import '../services/database.dart';
const url = 'https://myapp.herokuapp.com';
Future<void> fetchPosts() {
final client = http.Client();
return fetchPostsUsingClient(client);
}
Future<void> fetchPostsUsingClient(http.Client client) async {
final res = await client.get(url);
final posts await Post.fromJson(json.decode(response.body));
for (var i = 0; i < posts.length; i++) {
await DBProvider.insert('posts', posts[i]);
}
}
在我的测试中,我怎样才能verify DBProvider.insert() 已被调用?
fetchPosts_test.dart
import 'package:test/test.dart';
import 'package:http/http.dart' as http;
import 'package:mockito/mockito.dart';
import 'package:../services/fetchPosts.dart';
// Create a MockClient using the Mock class provided by the Mockito package.
// Create new instances of this class in each test.
class MockClient extends Mock implements http.Client {}
void main() {
group('fetchPosts', () {
test('update local db', () async {
final client = MockClient();
// Use Mockito to return a successful response when it calls the provided http.Client.
when(client.get()).thenAnswer((_) async => http.Response('{"title": "Test"}', 200));
await fetchPostsWithClient(client);
verify(/* DBProvider.insert has been called ?*/);
});
});
}
【问题讨论】:
-
你不能模拟静态成员。如果您需要模拟,请不要将它们设为静态
-
@RémiRousselet,感谢您的洞察力。我很好奇,不允许静态成员被嘲笑的原因是什么?
-
好问题。我怀疑这是不合常规的,没有任何理由。面向对象的开发者喜欢惩罚 fp 开发者的选择。
标签: unit-testing flutter sqflite