flutter - 使用 Flutter 从一个未来获取价值并在另一个未来使用它
问题描述
我有一个收藏夹收藏夹保存在用户收藏夹下。每个收藏文档都有一个包含 product_Id 的字段。我想检索这个 product_id 值并用它来查询另一个集合。第二个集合包含实际的产品文档。
检索收藏夹集合中的所有文档。接下来我该怎么做才能将 product_id 字段的值作为字符串获取?
getIdsfromUserFavs(userId) async {
var _favData = await _usersCollectionReference
.doc(userId)
.collection('favourites')
.get();
}
这是用于查询产品集合的第二种方法。此方法需要上面的字符串值才能成功进行查询。
Future<QuerySnapshot<Object?>> queryFavsCollection(value) async {
var _favedProducts = await _productsCollectionReference
.where('prod_id', isEqualTo: value)
.get();
print(value);
return _favedProducts;
}
我在 UI 中使用了 futureBuilder。
这是我尝试过的一种方法(问题是我没有返回任何数据):
getIdsfromUserFavs(userId) async {
var _favData = await _usersCollectionReference
.doc(userId)
.collection('favourites')
.get();
var allData = _favData.docs.map((doc) => doc.data()).toList();
allData.forEach((element) async {
String value = element['prod_id'];
print(value);
await queryFavsCollection(value);
});
}
Future<QuerySnapshot<Object?>> queryFavsCollection(value) async {
var _favedProducts = await _productsCollectionReference
.where('prod_id', isEqualTo: value)
.get();
print(value);
return _favedProducts;
}
我可以看到上述方法将 id 打印到控制台。但是 FutureBuilder 没有收到任何数据:
I/flutter ( 4628): 3nHHEWuCDXvbhYfT8ljY
I/flutter ( 4628): MptYFV1oXhflDYkdQyIP
I/flutter ( 4628): Fd2ntXyNVmjn0D6mG3RA
解决方案
下面的函数将返回收藏夹中的所有数据
Future<QuerySnapshot<Map<String, dynamic>>> getIdsfromUserFavs(userId) async {
QuerySnapshot<Map<String, dynamic>> _favData = await _usersCollectionReference
.doc(userId)
.collection('favourites')
.get();
return _favData; // This will return all data of favourite collection
}
之后,您可以返回所需数据列表,如下面的函数所示
Future<List<QueryDocumentSnapshot<Map<String, dynamic>>>> queryFavsCollection(userId) async {
// Will store data in this list so at the end we can return this
List<QueryDocumentSnapshot<Map<String, dynamic>>> favData = [];
QuerySnapshot<Map<String, dynamic>> _favData =
await getIdsfromUserFavs(userId);
for (QueryDocumentSnapshot<Map<String, dynamic>> data in _favData.docs) {
String value = data['prod_id'];
QuerySnapshot<Map<String, dynamic>> _fav = await
_productsCollectionReference
.where('prod_id', isEqualTo: value)
.get();
if (_fav.docs.isNotEmpty) {
_fav.docs.forEach((element) {
favData.add(element);
});
}
}
return favData;
}
现在您可以使用 FutureBuilder 如下所示
FutureBuilder<List<QueryDocumentSnapshot<Map<String, dynamic>>>>(
future: queryFavsCollection(userId),
builder: (context, snapshot) {
if (!snapshot.hasData) {
return Text('Loading...');
}
return Text('you data');
},
);
为了更好的实践,请参考这个。这是来自颤振文档
"future 必须更早获得,例如在 State.initState、State.didUpdateWidget 或 State.didChangeDependencies 期间。在构造 FutureBuilder 时,不能在 State.build 或 StatelessWidget.build 方法调用期间创建。如果创建了 future与FutureBuilder同时,那么每次重建FutureBuilder的父级时,异步任务都会重新启动。”
推荐阅读
- scala - 窗口函数将一列中的 n 行转换为单行
- ios - 如何将当年的月份和日期转换为分钟?
- flutter - 在某些设备上调用 null 方法“+”
- sql-server - 如何合并 2 列以将两列中的数据显示为单列?
- sql - SQL查询从日期获取周数,同时设置从星期日开始的星期
- python-3.x - 有条件的 Pandas 数据框操作
- python - 如何在 python 中创建堆积线图?
- html - 使用 Bootstrap 4 创建 2 个导航栏
- regex - 在模式之后匹配单词并使用sed在文件中附加后缀?
- php - 如何找出 HH:MM 的当前时间是否在两个区间 HH:MM - HH:MM