将所有firebase节点的子节点作为Map Android返回的方法

时间:2017-10-02 14:40:04

标签: android firebase firebase-realtime-database callback

我正在尝试编写一个方法,该方法返回一个应该包含Firebase中节点的所有子节点的地图,但由于我必须使用回调,因此该方法返回一个空地图。

public Map<Date, String> getChildrenAsMap(String nodeId) {
    DatabaseReference refernce= dbRoot.child("childName").child(nodeId);
    final Map<Date, String> childMap = new HashMap<>();

    refernce.addListenerForSingleValueEvent(new ValueEventListener() {
        @Override
        public void onDataChange(DataSnapshot dataSnapshot) {

            Map<Date, String> data = (Map<Date, String>) dataSnapshot.getValue();

            for (Map.Entry<Date, String> entry : data.entrySet()) {
                childMap .put(entry.getKey(), (String) entry.getValue());
            }
        }

        @Override
        public void onCancelled(DatabaseError databaseError) {
            Log.w("TAG", "onCancelled", databaseError.toException());
        }
    });
    return childMap;
}

2 个答案:

答案 0 :(得分:1)

这是因为Firebase查询是异步的,并且在您返回地图后会调用侦听器。为了简单起见:您不能创建这样的异步方法,因为ValueEventListener已经是一个完全相同的接口。如果您希望这样的方法起作用,您需要创建一个为您处理它的类,但这不是必需的,因为您拥有 Firebase for Android 提供的所有内容:

DatabaseReference refernce= dbRoot.child("childName").child(nodeId);

deviceHistory.addListenerForSingleValueEvent(new ValueEventListener() {
    @Override
    public void onDataChange(DataSnapshot dataSnapshot) {
        Map<Date, String> childMap = new HashMap<>();

        Map<Date, String> data = (Map<Date, String>) dataSnapshot.getValue();

        for (Map.Entry<Date, String> entry : data.entrySet()) {
            childMap.put(entry.getKey(), (String) entry.getValue());
        }

        // handle your childMap modifications in here, this gets executed after the value is retrieved
    }

    @Override
    public void onCancelled(DatabaseError databaseError) {
        Log.w("TAG", "onCancelled", databaseError.toException());
    }
});

我写了另一个类似的注释(虽然对于Swift,但这不是相关点)here。每次要使用它时,您都必须将逻辑写入ValueEventListener。它已经是一种方法,因此您无需创建新方法。

答案 1 :(得分:0)

要解决此问题,您需要从onDataChange()中获取数据。请参阅此post的答案。

这是由于在迭代之前调用的onDataChange()的异步行为而发生的。