我正在Flutter中实现Todo应用程序。我需要在客户端中合并一个双重查询,以便在Firestore中执行OR请求。
一方面,我有执行双重查询的以下代码。
Future<Stream> combineStreams() async {
Stream stream1 = todoCollection
.where("owners", arrayContains: userId)
.snapshots()
.map((snapshot) {
return snapshot.documents
.map((doc) => Todo.fromEntity(TodoEntity.fromSnapshot(doc)))
.toList();
});
Stream stream2 = todoCollection
.where("contributors", arrayContains: userId)
.snapshots()
.map((snapshot) {
return snapshot.documents
.map((doc) => Todo.fromEntity(TodoEntity.fromSnapshot(doc)))
.toList();
});
return StreamZip(([stream1, stream2])).asBroadcastStream();
}
另一方面,我有以下代码将使用Bloc模式执行视图更新。
Stream<TodosState> _mapLoadTodosToState(LoadTodos event) async* {
_todosSubscription?.cancel();
var res = await _todosRepository.todos(event.userId);
_todosSubscription = res.listen(
(todos) {
dispatch(
TodosUpdated(todos));
},
);
}
我有以下错误。
flutter: Instance of '_AsBroadcastStream<List<List<Todo>>>'
[VERBOSE-2:ui_dart_state.cc(148)] Unhandled Exception: type 'List<List<Todo>>' is not a subtype of type 'List<Todo>'
我试图通过调试器查找更多信息,结果发现我的StreamZip源单独包含2个流。
目前,我一次只能获得一个流。
我不知道如何进行操作以获取2个流并显示它们。
答案 0 :(得分:2)
您正在制作地图的地图,该地图将返回另一个列表的列表。
创建订阅后,应压缩QuerySnapshot
流并进行映射,然后可以从中创建新的Stream<List<Todo>>
。
///private method to zip QuerySnapshot streams
Stream<List<QuerySnapshot>> _combineStreams() async {
Stream stream1 = todoCollection
.where("owners", arrayContains: userId)
.snapshots()
});
Stream stream2 = todoCollection
.where("contributors", arrayContains: userId)
.snapshots()
});
return StreamZip(([stream1, stream2])).asBroadcastStream();
}
///exposed method to be consumed by repository
Stream<List<Todo>> todosStream() {
var controller = StreamController<List<Todo>>();
_combineStreams().listen((snapshots) {
List<DocumentSnapshot> documents;
snapshots.forEach((snapshot) {
documents.addAll(snapshot.documents);
});
final todos = documents.map((document) {
return Todo.fromEntity(TodoEntity.fromSnapshot(doc));
}).toList();
controller.add(todos);
});
return controller.stream;
}