Firebase DatabaseReference没有删除事件侦听器?

时间:2016-11-03 03:40:47

标签: android firebase firebase-realtime-database listener

嘿,我是否需要在某个时候删除此侦听器,还是单独删除它?我在我的活动中调用了一个片段,用户可以转到另一个视图而不会被销毁。因此,不确定我是否在某种程度上假设要在onDestroy onPause来电中将其删除?我没有看到删除它的方法,因为它是DatabaseReference

以下是代码:

private DatabaseReference mDatabase;
  mDatabase.child("projects").orderByChild("viewCount").limitToLast(15).addChildEventListener(new ChildEventListener() {
            @Override
            public void onChildAdded(DataSnapshot dataSnapshot, String s) {

6 个答案:

答案 0 :(得分:6)

当超人的回答链接到show:你确实需要在相反的生命周期事件中删除监听器。

要删除侦听器,您需要保留handle that is returned when you call addChildListener()

Query query = mDatabase.child("projects").orderByChild("viewCount").limitToLast(15);
ChildEventListener listener = query.addChildEventListener(new ChildEventListener() { ...

然后pass it to removeEventListener()

query.removeChildEventListener(listener);

您可以看到我在这里明确使用了Query,因为这是您实际附加听众的内容。但是,如果你有一个简单的DatabaseReference,则可以使用相同的方法,因为DatabaseReference继承自Query

答案 1 :(得分:4)

Firebase 对象是对Firebase数据库中位置的轻量级引用。 没有必要(也没有能力)来管理他们的生命周期。所以,你可以让Java垃圾收集器来处理它们。

然而,一旦开始附加侦听器(例如addValueEventListener()),您应该使用removeEventListener()将它们分离到相应的生命周期事件中。另请参阅Firebase adding listeners in adapters in AndroidHow stop Listening to firebase location in android

答案 2 :(得分:2)

正如Frank所说,您需要从完全 DatabaseReference中删除侦听器,而不仅仅是像我一样从根DatabaseReference中删除。

为了简化这一点,我在下面创建了一个小类:

public class FirebaseListenerRef {

    private ValueEventListener listener;
    private DatabaseReference ref;

    public FirebaseListenerRef(DatabaseReference ref, ValueEventListener listener) {
        this.listener = listener;
        this.ref = ref;

        // Start listening on this ref.
        ref.addValueEventListener(listener);
    }

    public void detach() {
        ref.removeEventListener(listener);
    }
}

要使用此功能,只需在配对的生命周期事件中创建和分离它,例如

private FirebaseListenerRef myFirebaseListenerRef;

public void onAttach(Content context) {
    super.onAttach(context);
    myFirebaseListenerRef = new FirebaseListenerRef(
        FirebaseDatabase.getInstance().getReference().child("path-to-listen-on", 
        new ValueEventListener() { 
            ... implement the listener logic
         }
      );
}

public void onDetach() {
    super.onDetach();
    if ( myFirebaseListenerRef != null ) {
    // Detach our listener from its reference
        myFirebaseListenerRef.detach();
        myFirebaseListenerRef == null;
    }
}

答案 3 :(得分:1)

如果您使用Query添加addValueEventListener。然后,您应该使用Query实例而不是DatabaseReference实例删除侦听器。

问题DatabaseReference开发人员正在使用类型为orderByChild的{​​{1}}因此要删除侦听器,我们需要引用Query实例,然后使用Query

以下是删除侦听器的示例:

removeEventListener

然后

ValueEventListener carChangesListener;
Query ownerId_Query;

现在要删除DatabaseReference bikeRef = FirebaseDatabase.getInstance().getReference().child("Cars"); ownerId_Query = bikeRef.orderByChild("ownerId").equalTo(FirebaseAuth.getInstance().getCurrentUser().getUid()); carChangesListener = new ValueEventListener() { @Override public void onDataChange(DataSnapshot dataSnapshot) { if (dataSnapshot.getValue() != null) { /*NOTE: handle cars response here*/ }else{ Toast.makeText(getActivity(), "No car found for this user.", Toast.LENGTH_LONG).show(); } } @Override public void onCancelled(DatabaseError databaseError) { Log.w(HOME_TAG, "Failed to read value.", databaseError.toException()); Toast.makeText(getActivity(), "Error!" + databaseError.toException().getMessage(), Toast.LENGTH_LONG).show(); } }; ownerId_Query.addValueEventListener(bikeChangesListener); ,我将执行以下操作:

carChangesListener

答案 4 :(得分:0)

private DatabaseReference dbRef;
ValueEventListener mSendEventListner;

dbRef = FirebaseDatabase.getInstance().getReference().child("users").child(phone);

ValueEventListener valueEventListener = new ValueEventListener() 
{
            @Override
            public void onDataChange(@NonNull DataSnapshot dataSnapshot) {
                if (dataSnapshot.exists())
                {              
                   //
                } 
            }

            @Override
            public void onCancelled(@NonNull DatabaseError databaseError) {
                //
            }
};
dbRef.addValueEventListener(valueEventListener);
mSendEventListner = valueEventListener;


//REMOVE VALUE EVENTLISTNER...
@Override
protected void onDestroy() 
{
    super.onDestroy();
    if (mSendEventListner != null) {
        dbRef.removeEventListener(mSendEventListner);
    }
}

答案 5 :(得分:0)

如果您将ValueEventListener与孩子一起使用,则必须:

ValueEventListener listener;
onCreate(....){
    listener = mDatabase.child("projects").addChildEventListener(new ChildEventListener() { ...... }
}

并删除侦听器:

mDatabase.child("projects").removeEventListener(listener);

此RemoveEventListener中最重要的是child()函数。