【问题标题】:StreamBuilder's Firebase query appears and disappears instantlyStreamBuilder 的 Firebase 查询出现并立即消失
【发布时间】:2021-10-09 23:50:57
【问题描述】:

我正在尝试查询一个 Stream,其中文档应该在 'unit' 数组中包含 'UretimKurulum' 和 '日期'应该等于或大于今天的日期。

在流式传输此查询时,我确实在短短几秒钟内得到了我想要的正确结果,然后它显示“无可用数据”。

下面是实际代码:

  final FirebaseFirestore _db = FirebaseFirestore.instance;

  final DateTime _now = DateTime.now();
  final String val = 'UretimKurulum';

  @override
  Widget build(BuildContext context) {
    return StreamBuilder<QuerySnapshot<Object>>(
      stream: _db.collection('Schedule').where('date', isGreaterThanOrEqualTo: _now).where('unit', arrayContains: val).snapshots(),
      builder: (context, snapshot) {
        if (snapshot.connectionState == ConnectionState.waiting) {
          return Center(child: LinearProgressIndicator());
        } else {
          if (!snapshot.hasData) {
            return Center(child: Text('No Data Available'));
          } else {
            return ListView.builder(
              itemCount: snapshot.data!.docs.length,
              itemBuilder: (context, index) {
                var docSnap = snapshot.data!.docs[index];
                return Text(docSnap.id);
              },
            );
          }
        }
      },
    );
  }
}

如果我尝试删除:

if (!snapshot.hasData) {
            return Center(child: Text('No Data Available'));
          }

我收到以下错误:

════════ Exception caught by widgets library ═══════════════════════════════════
The following TypeErrorImpl was thrown building StreamBuilder<QuerySnapshot<Object>>(dirty, state: _StreamBuilderBaseState<QuerySnapshot<Object>, AsyncSnapshot<QuerySnapshot<Object>>>#0508a):
Unexpected null value.

【问题讨论】:

  • 这个问题是否与 Firestore 中的复合查询索引有关?调试控制台不显示添加索引的链接。
  • 您可以尝试将|| snapshot.data == null 添加到if (!snapshot.hasData) { 行。不知道会不会有什么效果,但值得一试。
  • @JaffaKetchup 不幸的是它没有效果

标签: firebase flutter google-cloud-firestore stream-builder


【解决方案1】:

第一件事

 //instead of DateTime 
 final DateTime _now = DateTime.now();
 //you should use Timestamp which is provided by Firebase Firestore
 final Timestamp timeNow = Timestamp.now();

第二件事

//instead of
where('unit', arrayContains: val)
//try this
where("unit", "arrayContains", val)

希望它应该可以工作,如果没有然后回复我,我会尝试找到其他解决方案。

【讨论】:

    【解决方案2】:

    当您没有在 Firestore 中创建必要的索引时,您会闪烁。您需要为涉及 >、>=、

    {
      "collectionGroup": "Schedule",
      "queryScope": "COLLECTION",
      "fields": [
        {
          "fieldPath": "unit",
          "arrayConfig": "CONTAINS"
        },
        {
          "fieldPath": "date",
          "order": "ASCENDING"
        }
      ]
    },
    

    或者,如果您愿意,也可以从 Firestore 控制台手动执行。

    【讨论】:

      【解决方案3】:

      确实,正如@blaneyneil 和我之前所说的那样,这是一个索引问题。

      解决方案是从 Firebase 控制台创建一个复合集合索引,并将字段“todoUnit”索引为数组,将“日期”索引为升序。

      【讨论】:

        【解决方案4】:
        1. 为什么要尝试删除检查数据?,如果数据为空或为空,一般标准的 UX 应该不显示任何数据。为了避免 null,您可以使用像 data ?? 'default-data'data == null ? 'no-data' : 'found-data' 这样的 elvis 运算符
        2. 适合日期时间的条件是使用DateTime.now().microsecondsSinceEpoch 而不是DateTime.now() 这个可选但更精确的数据有效 https://docs.w3cub.com/dart~2/dart-core/datetime/microsecondssinceepoch
        3. 你可以试试改变
        // instead of
               if (!snapshot.hasData) {
                    return Center(child: Text('No Data Available'));
                  } else {
                    return ListView.builder(
                      itemCount: snapshot.data!.docs.length,
                      itemBuilder: (context, index) {
                        var docSnap = snapshot.data!.docs[index];
                        return Text(docSnap.id);
                      },
                    );
                  }
        
        // try this
               if (!snapshot.hasData) {
                    return Center(child: Text('No Data Available'));
               } 
               return ListView.builder(
                   itemCount: snapshot.data!.docs.length,
                   itemBuilder: (context, index) {
                      var docSnap = snapshot.data!.docs[index];
                      return Text(docSnap.id);
                   },
                );
                  
        

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2019-10-17
          • 1970-01-01
          • 1970-01-01
          • 2022-06-21
          相关资源
          最近更新 更多