【问题标题】:Android - Getting an Object from DataSnapShot - firebase databaseAndroid - 从 DataSnapShot 获取对象 - firebase 数据库
【发布时间】:2018-01-19 09:11:57
【问题描述】:

我创建了一个帮助类,其中包括我想对 FirebaseDatabase 中的数据执行的功能和流程。

以下函数旨在获取 fireabseDataBase 中帖子节点中的所有帖子:

public static Jobs getAllJobs() {

    Posts posts= new Posts();
    postsDBRef= FirebaseDatabase.getInstance().getReference("posts").getRef();

    postsDBRef.addValueEventListener(new ValueEventListener() {
        @Override
        public void onDataChange(DataSnapshot dataSnapshot) {
            for (DataSnapshot jobSnapshot: dataSnapshot.getChildren()) {
                // TODO: handle the post
               String key = jobSnapshot.getKey();
               //here 
               Post post= jobSnapshot.child(key).getValue(Post.class);
              // and here  
               posts.add(post);
            }
        }

        @Override
        public void onCancelled(DatabaseError databaseError) {
            Log.i(getClass().getName().toString(), ": " + databaseError.getMessage());
        }
    });

    return posts;
}

在onDataChange 函数中,我试图遍历数据并检索它,虽然在记录时我确实获取了数据,但 post 对象不断给出 Null

这是 firebase 数据库中数据的样子

 {
  "posts" : {
    "-Kr9-ii-ArpC3fLuuGnb" : {
      "address" : "sfhhfg",
      "applied" : false,
      "currency" : "le",
      "description" : "ehdhyf",
      "latitude" : 0,
      "longitude" : 0,
      "noOfWorkers" : 2,
      "rating" : 0,
      "reported" : false,
      "salary" : "1250",
      "title" : "rgchu",
      "userId" : 0
    },
    "-Kr94BDkdEZrmxmjxv_Z" : {
     /../
    },
    "-Kr9Dz3S0BQEYv4VO2l3" : {
   /../
    },
    "-Kr9XqDPUvCRcv0lwFy_" : {
    /../
    }
  }
}

这就是调试器在一个循环中得到的结果

DataSnapshot { key = -Kr9-ii-ArpC3fLuuGnb, value = {address=sfhhfg, rating=0,title=rgchu,reported=false,description=ehdhyf,userId=0, 经度=0,noOfWorkers=2,纬度=0,货币=le,应用=false, 工资=1250} }

知道我做错了什么吗?

【问题讨论】:

  • 我们无法知道getDataBaseReference("posts") 返回什么,也无法知道posts 的JSON 是什么样子。请确保您的问题包含minimum complete information that is needed to reproduce the problem。分享 JSON 时,请务必以文本形式分享(不要截图)。您可以通过单击 Firebase Database console 中的“导出 JSON”链接来获取此信息。
  • @FrankvanPuffelen 添加了额外信息,感谢您指出缺失的信息
  • getReference("posts").getRef() -> getReference("posts")。结果是一样的,但它会节省我的双重考虑。
  • 我们仍然不知道 Post 是什么,但它似乎与您的 JSON 不匹配。请将类和 JSON 都减少到重现问题所需的最小值。例如:您很可能可以使用一两个属性来重现它,这样可以节省相当多的空间和时间。
  • 另外:我假设key 为每个子快照获取正确的值。真的是这样吗?

标签: android firebase firebase-realtime-database


【解决方案1】:

我已经编辑了你的代码,现在应该可以正常工作了,我之前在几个项目中使用过相同的代码 sn-ps。确保您的 pojo 与 json 数据匹配,您可以使用this 工具让自己更轻松。

最重要的是,不要将 Firebase 用作返回值的函数——这违背了它的异步特性。让 Firebase 执行它的任务,然后在闭包(块)内进行下一步。

P.S:在使用ValueEventListener 或ChildEventListener 之前,请从here 中读取它们之间的区别。

public void getAllJobs() {

Posts posts= new Posts();

postsDBRef= FirebaseDatabase.getInstance();

postsDBRef.child("posts").addValueEventListener(new ValueEventListener() {
    @Override
    public void onDataChange(DataSnapshot dataSnapshot) {
        for (DataSnapshot jobSnapshot: dataSnapshot.getChildren()) { 
           Post post= jobSnapshot.getValue(Post.class);
           posts.add(post);
        }
     // go to next step from here e.g handlePosts(posts);
    }

    @Override
    public void onCancelled(DatabaseError databaseError) {
        Log.i(getClass().getName().toString(), ": " + databaseError.getMessage());
    }
});

}

【讨论】:

    【解决方案2】:

    经过多次试验

    .addChildEventListener(new ChildEventListener() {
                @Override
                public void onChildAdded(DataSnapshot dataSnapshot, String s) {
                    for (DataSnapshot snapshot : dataSnapshot.getChildren()) {
                        Job job = snapshot.getValue(Job.class);
                        System.out.println(job.getTitle());
                    }
                }
    
                @Override
                public void onChildChanged(DataSnapshot dataSnapshot, String s) {
    
                }
    
                @Override
                public void onChildRemoved(DataSnapshot dataSnapshot) {
    
                }
    
                @Override
                public void onChildMoved(DataSnapshot dataSnapshot, String s) {
    
                }
    
                @Override
                public void onCancelled(DatabaseError databaseError) {
                    Log.i(getClass().getName().toString(), ": " + databaseError.getMessage());
                }
            });
    

    使用 .addChildEventListener 是我的问题的唯一解决方案,仍在调查原因。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2018-11-30
      • 2018-10-03
      • 2016-12-10
      • 2015-12-29
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多