Flutter集成Sign In with Apple登录Firebase无法获取用户名
Flutter 对接 Firebase + sign_in_with_apple 无法获取Apple用户姓名的解决方案
核心问题说明
Apple登录的特性决定了:仅在用户首次授权登录你的应用时,才会返回姓名信息,后续重复登录即使请求了fullName权限,也不会再返回该字段。你的代码目前没有处理首次登录时的姓名提取与存储逻辑,也没有从返回的appleCredential中直接获取姓名。
代码修正与解决方案
1. 提取Apple登录返回的姓名(仅首次有效)
在获取appleCredential后,立即提取姓名字段,同时结合Firebase Auth的additionalUserInfo.isNewUser判断是否为首次登录,将姓名保存到Firebase用户信息或你的数据库中:
Future<UserCredential> appleSignIn() async { if (kIsWeb) { final provider = OAuthProvider("apple.com") ..addScope('email') ..addScope('name'); final userCredential = await FirebaseAuth.instance.signInWithPopup(provider); // Web端处理首次登录的姓名 if (userCredential.additionalUserInfo?.isNewUser == true) { final profile = userCredential.additionalUserInfo?.profile; final firstName = profile?['given_name']; final lastName = profile?['family_name']; if (firstName != null || lastName != null) { await userCredential.user?.updateDisplayName('$firstName $lastName'.trim()); // 可选:将姓名存入Firestore等数据库 // await FirebaseFirestore.instance.collection('users').doc(userCredential.user?.uid).set({ // 'displayName': '$firstName $lastName'.trim(), // 'email': userCredential.user?.email, // }); } } return userCredential; } final rawNonce = generateNonce(); final nonce = sha256ofString(rawNonce); // 请求Apple授权凭证 final appleCredential = await SignInWithApple.getAppleIDCredential( scopes: [ AppleIDAuthorizationScopes.email, AppleIDAuthorizationScopes.fullName, ], nonce: nonce, ); // 创建Firebase OAuth凭证 final oauthCredential = OAuthProvider("apple.com").credential( idToken: appleCredential.identityToken, rawNonce: rawNonce, ); // 登录Firebase final userCredential = await FirebaseAuth.instance.signInWithCredential(oauthCredential); // 仅首次登录时保存姓名 if (userCredential.additionalUserInfo?.isNewUser == true) { final firstName = appleCredential.givenName; final lastName = appleCredential.familyName; if (firstName != null || lastName != null) { // 更新Firebase用户的displayName await userCredential.user?.updateDisplayName('$firstName $lastName'.trim()); // 可选:将姓名存入数据库持久化 // await FirebaseFirestore.instance.collection('users').doc(userCredential.user?.uid).set({ // 'displayName': '$firstName $lastName'.trim(), // 'email': userCredential.user?.email, // }); } } return userCredential; } Future<User?> signInWithApple(BuildContext context) => signInOrCreateAccount(context, appleSignIn, 'APPLE');
2. 测试注意事项
- 如果之前已经用Apple登录过你的应用,需要在设备的
设置 -> Apple ID -> 密码与安全性 -> 使用Apple ID的应用中找到你的应用,点击「停止使用Apple ID」,然后重新登录才能触发首次授权流程,获取姓名信息。 - 确保
sign_in_with_apple插件使用最新稳定版本,避免版本兼容问题。
关键提示
- 不要依赖后续登录获取姓名,必须在首次登录时完成姓名的提取与存储。
- 若用户首次授权时未提供姓名(Apple允许用户隐藏姓名),则
givenName和familyName会为null,需做好空值处理。
内容的提问来源于stack exchange,提问作者xG00gle
相关产品推荐
相关产品推荐

