如何将Stream<QuerySnapshot<Map<String, dynamic>>>转为List及Firestore查询报错排查
报错原因与修复方案
你遇到的类型报错是因为2.0.0及以上版本的cloud_firestore引入了空安全和泛型校验,未指定泛型的QuerySnapshot返回的data()结果为Object?类型,和fromMap方法要求的Map<String, dynamic>参数类型不匹配。
修复后的查询代码
Future <List<kako.User>> fetchAllUsers(User currentUser) async { // 原初始化逻辑会生成20个空User对象混入结果,建议直接初始化空列表 List<kako.User> userList = []; // 给collection查询指定泛型,明确返回文档的格式为Map<String, dynamic> QuerySnapshot<Map<String, dynamic>> querySnapshot = await fireStore.collection("users").get(); for (var i = 0; i < querySnapshot.docs.length ; i++) { if(querySnapshot.docs[i].id != currentUser.uid){ userList.add(kako.User.fromMap(querySnapshot.docs[i].data())); } } return userList; }
Stream<QuerySnapshot<Map<String, dynamic>>> 转List方法 根据使用场景有两种实现方式:
- 单次获取流的最新数据转List
Future<List<kako.User>> getListFromStream(User currentUser, Stream<QuerySnapshot<Map<String, dynamic>>> userStream) async { List<kako.User> userList = []; // 获取流的最新一次快照数据 QuerySnapshot<Map<String, dynamic>> snapshot = await userStream.first; for (var doc in snapshot.docs) { if (doc.id != currentUser.uid) { userList.add(kako.User.fromMap(doc.data())); } } return userList; }
- 持续监听流转为实时更新的List流(适合列表实时刷新场景)
Stream<List<kako.User>> transformToUserListStream(User currentUser) { return fireStore.collection("users").snapshots().map((snapshot) { List<kako.User> userList = []; for (var doc in snapshot.docs) { if (doc.id != currentUser.uid) { userList.add(kako.User.fromMap(doc.data())); } } return userList; }); } // 调用时可直接用StreamBuilder监听该流,实现列表实时更新
内容的提问来源于stack exchange,提问作者bricend96
相关产品推荐
相关产品推荐

