如何在建立抖动之前从Firestore检索数据?

时间:2020-04-26 12:31:50

标签: firebase flutter google-cloud-firestore

我正在尝试通过存储在Cloud Firestore的用户集合中的文档获取用户名,但是我的构建方法会在接收数据之前运行。 initState(){}方法不会等待uidDetails()完成,因此在DoctorListStream(currentUserName)中传递了空值。由于无法使initState(){}`方法异步,因此我想知道可以采取哪些措施来解决此问题。我也尝试同时实现StreamBuilder和FutureBuilder,但是失败了。

import 'package:flutter/material.dart';
import 'package:cloud_firestore/cloud_firestore.dart';
import 'package:firebase_auth/firebase_auth.dart';
import '../components/doc_list_retriever.dart';

class ListOfDoctors extends StatefulWidget {
  @override
  _ListOfDoctorsState createState() => _ListOfDoctorsState();
}

class _ListOfDoctorsState extends State<ListOfDoctors> {
  final _auth = FirebaseAuth.instance;
  final _fStore = Firestore.instance;
  String currentUserUid;
  String currentUserName;

  @override
  void initState() {
    // TODO: implement initState
    super.initState();
    uidDetails();
  }

  void uidDetails() async {
    final FirebaseUser user = await _auth.currentUser();
    currentUserUid = user.uid;
    print(currentUserUid + 'from user details');
    await Firestore.instance
        .collection('users')
        .document(currentUserUid)
        .get()
        .then((DocumentSnapshot) {
      currentUserName = DocumentSnapshot.data['name'].toString();
    });
    print(currentUserName + ' from uid Details');
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      backgroundColor: Color(0xFF1D1E33),
      body: SafeArea(
        child: Column(
          children: <Widget>[
            Text(
              'Doctors:',
              textAlign: TextAlign.left,
              style: TextStyle(fontSize: 40, color: Colors.white70),
            ),
            DoctorListStream(currentUserName),
          ],
        ),
      ),
    );
  }
}

控制台:

Performing hot restart...
Syncing files to device AOSP on IA Emulator...
Restarted application in 848ms.
I/BiChannelGoogleApi(27263): [FirebaseAuth: ] getGoogleApiForMethod() returned Gms: com.google.firebase.auth.api.internal.zzaq@95a83d7
D/FirebaseAuth(27263): Notifying id token listeners about user ( 5TlH5zoCqfWDNDlAgvIsc5yAHPA3 ).
I/flutter (27263): 5TlH5zoCqfWDNDlAgvIsc5yAHPA3from user details

════════ Exception caught by widgets library ═══════════════════════════════════════════════════════
The following NoSuchMethodError was thrown building StreamBuilder<QuerySnapshot>(dirty, state: _StreamBuilderBaseState<QuerySnapshot, AsyncSnapshot<QuerySnapshot>>#044e7):
The method '+' was called on null.
Receiver: null
Tried calling: +(" from doctor list stream")

The relevant error-causing widget was: 
  StreamBuilder<QuerySnapshot> file:///D:/projects/clinic/lib/components/doc_list_retriever.dart:14:12
When the exception was thrown, this was the stack: 
#0      Object.noSuchMethod (dart:core-patch/object_patch.dart:53:5)
#1      DoctorListStream.build.<anonymous closure> (package:clinic/components/doc_list_retriever.dart:26:27)
#2      StreamBuilder.build (package:flutter/src/widgets/async.dart:509:81)
#3      _StreamBuilderBaseState.build (package:flutter/src/widgets/async.dart:127:48)
#4      StatefulElement.build (package:flutter/src/widgets/framework.dart:4623:28)
...
════════════════════════════════════════════════════════════════════════════════════════════════════
I/flutter (27263): Dhruv from uid Details

════════ Exception caught by rendering library ═════════════════════════════════════════════════════
A RenderFlex overflowed by 99670 pixels on the bottom.
The relevant error-causing widget was: 
  Column file:///D:/projects/clinic/lib/screens/list_of_doctors.dart:43:16

═══════════════════════════════════════════════ ══════════════════════════════════════════════════ ═══

1 个答案:

答案 0 :(得分:1)

我会选择使用流构建器来获取用户数据。实施示例

String username;
    body: StreamBuilder(
                    stream: Firestore.instance
                   .collection('users')                            
                        .document(userid)
                        .snapshots(),
                    builder: (context, snapshot) {
                      if (!snapshot.hasData) {
                        return SpinKitDoubleBounce(
                          color: Colors.blue,
                        );
                      }
                      var userDoc = snapshot.data;
userName = userDoc["name"];
return .... //your other widgets