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

Flutter集成Firebase实时数据库问题:获取firstname值为空

解决Flutter Firebase实时数据库查询返回Null的问题

看起来你遇到的问题主要来自两个方面:Firebase查询API的使用错误,以及对查询返回的DataSnapshot结构理解有误。我来一步步帮你修正:

1. 先修正Firebase查询的API方法名

你代码里的childOrderBy和equals是错误的——Firebase实时数据库的正确方法名是orderByChild和equalTo,这会导致你的查询根本没按预期执行,可能返回不符合条件的数据或者空结果。

2. 理解查询返回的DataSnapshot结构

当你使用orderByChild+equalTo进行查询时,返回的DataSnapshot包含的是所有匹配条件的节点,而非单个节点。它的value是一个Map<String, dynamic>:其中每个键是用户节点的唯一key,对应的值才是单个用户的具体数据。

你之前直接把整个snapshot.value传给User.fromSnapShot,相当于把一个包含多个用户的集合当成了单个用户的数据,自然找不到Firstname字段,所以返回null。

3. 修正User类的构造函数

你的User类里有几个明显的低级错误,这也是导致null的原因之一:

  • 构造函数误写成了Todo.fromJson,应该是User.fromJson
  • 变量名firstName和firstname大小写不一致,导致赋值失败

修正后的User类:

class User {
  final String key;
  String firstName;

  User.fromJson(this.key, Map<String, dynamic> data) {
    firstName = data['Firstname'] ?? ''; // 用空值合并运算符简化空值判断
  }
}

4. 重构获取用户的方法

这里分两种场景处理:如果你的查询预期返回单个用户,就取匹配结果的第一个;如果可能返回多个,就返回用户列表。

场景1:获取第一个匹配的用户

static Future<User?> getUser(String userKey) async {
  String accountKey = await Preferences.getAccountKey();
  DataSnapshot snapshot = await FirebaseDatabase.instance
      .reference()
      .child("accounts")
      .child(accountKey)
      .child("users")
      .orderByChild("Group_id")
      .equalTo("54")
      .once();

  // 遍历查询结果的Map,取第一个用户数据
  if (snapshot.value != null) {
    Map<String, dynamic> usersMap = snapshot.value as Map<String, dynamic>;
    final firstEntry = usersMap.entries.first;
    return User.fromJson(firstEntry.key, firstEntry.value);
  }
  return null; // 无匹配用户时返回null
}

场景2:获取所有匹配的用户

static Future<List<User>> getUsers() async {
  String accountKey = await Preferences.getAccountKey();
  DataSnapshot snapshot = await FirebaseDatabase.instance
      .reference()
      .child("accounts")
      .child(accountKey)
      .child("users")
      .orderByChild("Group_id")
      .equalTo("54")
      .once();

  List<User> users = [];
  if (snapshot.value != null) {
    Map<String, dynamic> usersMap = snapshot.value as Map<String, dynamic>;
    usersMap.forEach((userKey, userData) {
      users.add(User.fromJson(userKey, userData));
    });
  }
  return users;
}

额外提示:简化异步代码

你之前用Completer的方式可以直接用async/await替代,代码会更简洁易读,上面的示例已经采用了这种写法。

现在再测试一下,应该就能正确获取到firstName的值了!

内容的提问来源于stack exchange,提问作者Jérôme Bonjour

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.28 09:51:32