Firebase身份验证用户信息流

时间:2020-08-14 05:53:18

标签: firebase flutter firebase-authentication

我有一个个人资料页面,该页面向用户显示他当前注册的电子邮件,以及一个编辑图标,该用户将其带到可以编辑电子邮件的页面。 用户成功更改电子邮件后,将返回上一页,向他显示已注册的电子邮件。

我希望用户看到新电子邮件。但是用户一直看到旧的电子邮件,直到重新加载页面为止。

所以我的第一个想法是用StreamBuilder自然地替换FutureBuilder。 我不确定如何获取当前用户的流,而不是未来的流,所以我将FirebaseUser使用的唯一流-> onAuthStateChanged

  Widget buildEmail() {
    return StreamBuilder(
      stream: FirebaseAuth.instance.onAuthStateChanged,
      builder: (BuildContext context, AsyncSnapshot<FirebaseUser> snapshot) {
        if (snapshot.connectionState == ConnectionState.waiting)
          return Center(
              child: SpinKitRing(
            color: Colors.white,
            size: 30,
          ));
        else if (snapshot.hasError)
          return Center(child: Text(snapshot.error));
        else {
          // final email = snapshot.data.data['email'];
          final email = snapshot.data.email;
          return Padding(
            padding: const EdgeInsets.only(left: 25.0),
            child: Text('$email', style: TextStyle(color: Colors.black)),
          );
        }
      },
    );
  }

此StreamBuilder的行为与我之前使用的FutureBuilder相同

  Widget buildEmail() {
    return FutureBuilder(
      future: FirebaseAuth.instance.currentUser(),
      builder: (BuildContext context, AsyncSnapshot<FirebaseUser> snapshot) {
        if (snapshot.connectionState == ConnectionState.waiting)
          return Center(
              child: SpinKitRing(
            color: Colors.white,
            size: 30,
          ));
        else if (snapshot.hasError)
          return Center(child: Text(snapshot.error));
        else {
          // final email = snapshot.data.data['email'];
          final email = snapshot.data.email;
          return Padding(
            padding: const EdgeInsets.only(left: 25.0),
            child: Text('$email', style: TextStyle(color: Colors.black)),
          );
        }
      },
    );
  }
}

所以我查看了onAuthStateChanged的文档,它指出:

  /// Receive [FirebaseUser] each time the user signIn or signOut

这导致我检查我的更新电子邮件方法,并检查我的用户是否再次登录到该应用程序。

static Future<void> updateEmail(String password, String newEmail, BuildContext context) async {
    final user = await CurrentUser.getCurrentUser();
    final ref = Firestore.instance.collection('users');

    try {
      AuthCredential credential = EmailAuthProvider.getCredential(email: user.email, password: password);
      AuthResult result = await user.reauthenticateWithCredential(credential);  // Sign in?
      result.user.updateEmail(newEmail);
      ref.document(user.uid).updateData({'email': newEmail});
      Navigator.of(context).pop();
      Fluttertoast.showToast(msg: 'Success!');
    } on PlatformException catch (error) {
      print(error);
      changeEmailErrorDialog(context, error: error.message);
    } catch (error) {
      print(error);
      changeEmailErrorDialog(context, error: error);
    }
  }

我认为我正在登录用户,因为此方法可以防止ERROR_REQUIRES_RECENT_LOGIN异常

  AuthResult result = await user.reauthenticateWithCredential(credential);  // Sign in?

我做错什么了吗? 如何获得用户流? 用于获取当前用户的Firebase方法将返回一个未来

FirebaseAuth.instance.currentUser();

该方法没有流版本吗?

1 个答案:

答案 0 :(得分:0)

有一个流版本;

FirebaseAuth.instance.userChanges(),

示例;

StreamBuilder<User>(
              stream: FirebaseAuth.instance.userChanges(),
              builder: (context, snapshot) {
                if (snapshot.connectionState == ConnectionState.waiting) {
                  return Center(child: CircularProgressIndicator());
                }
                return Text(snapshot.data.displayName);
              },
            ),