You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Flutter Google登录成功后无法自动跳转到底部导航栏页面

问题分析

登录成功后无法自动跳转至BottomNavigationBarPage,仅点击返回按钮可见,核心原因可能是:

  1. ChangeNotifierProvider层级过低,导致状态变化无法正确触发页面重建
  2. 登录流程中异步操作的时序问题,未确保认证状态更新后再完成状态通知
  3. StreamBuilder未正确监听Firebase认证状态的变化
解决方案

1. 调整Provider层级

将ChangeNotifierProvider移至MaterialApp外层,确保全局状态可被所有页面正确监听:

修改main.dart的build方法:

@override
Widget build(BuildContext context) {
  return ChangeNotifierProvider(
    create: (context) => GoogleSignInProvider(),
    child: MaterialApp(
      title: 'appTitle',
      home: const CheckIsLogged(),
    ),
  );
}

同时移除CheckIsLogged内部的ChangeNotifierProvider:

class CheckIsLogged extends StatelessWidget {
  const CheckIsLogged({Key? key}) : super(key: key);

  @override
  Widget build(BuildContext context) => Scaffold(
        body: StreamBuilder(
          stream: FirebaseAuth.instance.authStateChanges(),
          builder: (context, snapshot) {
            final provider = Provider.of<GoogleSignInProvider>(context);
            if (provider.isSigningIn) {
              return const Center(
                  child: CircularProgressIndicator(color: primaryColor));
            } else if (snapshot.hasData) {
              return const BottomNavigationBarPage();
            } else {
              return const FirstPage();
            }
          },
        ),
      );
}

2. 优化登录方法的异步流程

将登录方法中的回调改为await,确保认证状态完全更新后再修改加载状态,避免时序问题:

修改GoogleSignInProvider的login方法:

Future login() async {
  isSigningIn = true;

  final user = await googleSignIn.signIn();
  if (user == null) {
    isSigningIn = false;
    return;
  } 

  final googleAuth = await user.authentication;
  final credential = GoogleAuthProvider.credential(
    accessToken: googleAuth.accessToken,
    idToken: googleAuth.idToken,
  );

  // 确保认证完成,Firebase状态更新
  await FirebaseAuth.instance.signInWithCredential(credential);

  // 用await替代then,避免回调嵌套导致的时序问题
  var db = Mysql();
  var conn = await db.getConnection();
  uid = FirebaseAuth.instance.currentUser?.email;
  debugPrint('User ID: $uid');
  
  String sql = 'select uid from users where uid = "$uid"';
  var results = await conn.query(sql);
  userAlready = '';
  for (var row in results) {
    userAlready = row[0].toString();
  }

  if (userAlready != uid) {
    debugPrint('Is empty...');
    debugPrint('User Saving :' + uid!);
    String insertSql = 'insert into users (uid) values ("$uid")';
    await conn.query(insertSql);
  } else {
    debugPrint('Is not empty...');
    debugPrint('User Already Saved :' + userAlready);
  }

  // 所有操作完成后再关闭加载状态
  isSigningIn = false;
}

3. 验证StreamBuilder状态监听

在CheckIsLogged的StreamBuilder中添加日志,确认认证状态变化是否被正确捕获:

builder: (context, snapshot) {
  debugPrint('认证状态:${snapshot.connectionState},是否有用户:${snapshot.hasData}');
  final provider = Provider.of<GoogleSignInProvider>(context);
  // ... 原有逻辑
}

登录成功后,控制台应输出认证状态:Active,是否有用户:true,此时StreamBuilder会自动切换至BottomNavigationBarPage。

内容的提问来源于stack exchange,提问作者DLC

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.11 11:40:36