Firebase数据库侦听器检索错误信息

时间:2017-01-19 08:53:05

标签: android firebase firebase-realtime-database

我正在为数据库中的节点添加一个侦听器,如下所示:

ref = myDB.getReference("testNode/" + uID);

...


ref.addValueEventListener(new ValueEventListener() {
   @Override
   public void onDataChange(DataSnapshot dataSnapshot) {
     for (DataSnapshot singleSnapshot : dataSnapshot.getChildren()){
        Log.d("PROFILE", singleSnapshot.getKey());
     }
   }

   @Override
   public void onCancelled(DatabaseError databaseError) {}
});

这是我的数据库结构:

   "testNode" : {
     "ffggg@gmailcom" : {
       "kcd8huka0bha6md22nh1k5enj0" : 1484814690039,
       "vd4vk67n2gb7qgpol0jp8gee62" : 1484814727049
     },
     "test22@gmailcom" : {
       "8o93lpc5clhrsrst852nfm2g75" : 1484815514788,
       "a18g2u5h525nqthpqsn6askp75" : 1484814852458
     }
   }

如上所示,我有一个Log for testing,Log打印如下:

  

01-19 08:44:57.547 17531-17531 / com.firebase.android D / PROFILE:ffggg @ gmailcom   01-19 08:44:57.547 17531-17531 / com.firebase.android D / PROFILE:test22 @ gmailcom   01-19 08:45:15.446 17531-17531 / com.firebase.android D / PROFILE:8o93lpc5clhrsrst852nfm2g75   01-19 08:45:15.446 17531-17531 / com.firebase.android D / PROFILE:a18g2u5h525nqthpqsn6askp75   01-19 08:45:15.448 17531-17531 / com.firebase.android D / PROFILE:ffggg @ gmailcom   01-19 08:45:15.449 17531-17531 / com.firebase.android D / PROFILE:test22 @ gmailcom   01-19 08:45:15.587 17531-17531 / com.firebase.android D / PROFILE:8o93lpc5clhrsrst852nfm2g75   01-19 08:45:15.587 17531-17531 / com.firebase.android D / PROFILE:a18g2u5h525nqthpqsn6askp75   01-19 08:45:15.588 17531-17531 / com.firebase.android D / PROFILE:ffggg @ gmailcom   01-19 08:45:15.588 17531-17531 / com.firebase.android D / PROFILE:test22 @ gmailcom

现在假设uID是test22@gmailcom(并且我检查过字符串不为空或空)我应该只得到test22@gmailcom个孩子。然而,在这里我得到所有节点都在ref(但不是他们的孩子,除非节点是uID)。我不想要这个,因为如果我有成千上万的记录,我会下载大量不必要的数据。

我做错了什么,或者列表是如何通过firebase实现的?

更新1

当我从app抽屉打开应用程序时,它将获得我想要的节点的正确子节点。但是,当我进入此活动内部的另一个活动时,我将一个子项添加到我正在另一个类中侦听的节点,然后返回到正在侦听该节点的类,我得到了奇怪的输出。

以下是我添加到节点的其他活动的代码:

pullNewImage = myDB.getReference("testNode");
pullNewImage.child(uID).child(randomName).setValue(ServerValue.TIMESTAMP);

更新2

我更新的侦听器代码:

 //global var

 ValueEventListener profileListener = null;

//....

profileListener = ref.child(userEmail).addValueEventListener(new ValueEventListener() {
                    @Override
                    public void onDataChange(DataSnapshot dataSnapshot) {
                        for (DataSnapshot singleSnapshot : dataSnapshot.getChildren()){
                            Log.d("PROFILE", singleSnapshot.getKey());
                        }
                    }

                    @Override
                    public void onCancelled(DatabaseError databaseError) {}
                });


//...
 @Override
        public void onStop() {
            super.onStop();
            if (mAuthListener != null) {
                auth.removeAuthStateListener(mAuthListener);
            }
            if(profileListener != null)
                ref.removeEventListener(profileListener);

        }

5 个答案:

答案 0 :(得分:1)

使用ref = myDB.getReference("testNode").child(uID);

编辑:

因为你说问题是你改变活动的时候,你可能不会停止听众。

添加ValueEventListener:ValueEventListener profileListener = null;  并删除线程。然后将您的侦听器设置为ValueEventListener:

profileListener = ref.addValueEventListener(new ValueEventListener() {
    @Override
    public void onDataChange(DataSnapshot dataSnapshot) {
    for (DataSnapshot singleSnapshot : dataSnapshot.getChildren()){
        Log.d("PROFILE", singleSnapshot.getKey());
    }
}

@Override
public void onCancelled(DatabaseError databaseError) {}
});

然后覆盖onStop()方法:

@Override
public void onStop() {
    super.onStop();

    if(profileListener != null)
        ref.removeEventListener(profileListener);
}

编辑2:

仍然不确定为什么以上不起作用,但你也可以试一试:

以下假定DatabaseReference ref = FirebaseDatabase.getInstance().getReference("testNode");

Query profileQ = ref.orderByKey().equalTo(userEmail);
profileQ.addValueEventListener(new ValueEventListener() {
    @Override
    public void onDataChange(DataSnapshot dataSnapshot) {
    for (DataSnapshot singleSnapshot : dataSnapshot.getChildren()){
        Log.d("PROFILE", singleSnapshot.getKey());
    }
}

@Override
public void onCancelled(DatabaseError databaseError) {}
});

如果可行,则必须将ValueEventListener替换为Queue(Queue继承自ValueEventListener)。由于它处理的是UID,它只会返回一个......但是如果这种方法有效,我会感到惊讶,而其他方法则没有。

答案 1 :(得分:0)

要一次检索数据,请使用以下命令:

ref.addListenerForSingleValueEvent(
                    new ValueEventListener() {
                        @Override
                        public void onDataChange(DataSnapshot dataSnapshot) {
    }});

答案 2 :(得分:0)

尝试像这样更改引用和监听器:

ref = myDB.getReference().child("testnode");

ref = mDB.getReference("testnode");

如果你想继续监听节点而不是使用“addValueEventListener”,否则使用“addListenerForSingleValueEvent”。

并更改附加侦听器的代码以引用子节点。

ref.child(uid).addValueEventListener(new ValueEventListener() {
                @Override
                public void onDataChange(DataSnapshot dataSnapshot) {
                    for (DataSnapshot singleSnapshot : dataSnapshot.getChildren()){
                        Log.d("PROFILE", singleSnapshot.getKey());
                    }
                }

                @Override
                public void onCancelled(DatabaseError databaseError) {}
            });

答案 3 :(得分:0)

您的firebase数据不同步,如果您启用了持久模式,请在代码中禁用它



FirebaseDatabase.getInstance().setPersistenceEnabled(false);




Firebase Offline Capabilities

答案 4 :(得分:0)

我的聊天计数值得错了(即它总是给我一个聊天总数而不是未读消息数) 我刚做完FirebaseDatabase.getInstance().setPersistenceEnabled(false); 我的问题解决了