带有 Firebase 的 Android 架构组件,特别是 Firestore

Posted

技术标签:

【中文标题】带有 Firebase 的 Android 架构组件,特别是 Firestore【英文标题】:Android Architecture Components with Firebase specifically Firestore 【发布时间】:2018-09-22 17:45:59 【问题描述】:

我正在通过Doug Stevenson(Firebase 开发人员倡导者)查看此blog 该博客讨论了如何将 firebase 实时数据库android 架构组件一起使用。

有一个类 FirebaseQueryLiveData 形成一个可重用的类来管理所有 Firebase 查询以及实现 LiveData。虽然这完全适用于 Firebase RealTime 数据库,我似乎无法更改或更改它以支持云 Firestore 数据库。

这里是代码

public class FirebaseQueryLiveData extends LiveData<DataSnapshot> 
    private static final String LOG_TAG = "FirebaseQueryLiveData";

    private final Query query;
    private final MyValueEventListener listener = new MyValueEventListener();

    public FirebaseQueryLiveData(Query query) 
        this.query = query;
    

    public FirebaseQueryLiveData(DatabaseReference ref) 
        this.query = ref;
    

    @Override
    protected void onActive() 
        Log.d(LOG_TAG, "onActive");
        query.addValueEventListener(listener);
    

    @Override
    protected void onInactive() 
        Log.d(LOG_TAG, "onInactive");
        query.removeEventListener(listener);
    

    private class MyValueEventListener implements ValueEventListener 
        @Override
        public void onDataChange(DataSnapshot dataSnapshot) 
            setValue(dataSnapshot);
        

        @Override
        public void onCancelled(DatabaseError databaseError) 
            Log.e(LOG_TAG, "Can't listen to query " + query, databaseError.toException());
        
    

【问题讨论】:

请解释其中的困难或错误。运行代码时会发生什么? 嘿鲍勃。 Firestore 没有类似 Firebase Realtime 的方法,即 ValueEventListener、addValueEventListener。它还有其他相同的实现,在上述逻辑中很难使用 当我在 Firebase RealTime 数据库上工作时它运行良好,但我不能在 Firestore 上使用它。 Firestore 有一个带有快照侦听器的查询。 firebase.google.com/docs/reference/android/com/google/firebase/… 如何使用android架构组件(Jetpack)写入数据库(Firestore)?谁能指点我一些代码? 【参考方案1】:

这是@JobM 帖子的查询版本。谢谢@JobM!为了清楚起见,我建议将 @JobM 的版本重命名为 FirebaseDocumentLiveData。

import android.arch.lifecycle.LiveData;
import android.os.Handler;
import android.util.Log;

import com.google.firebase.firestore.EventListener;
import com.google.firebase.firestore.FirebaseFirestoreException;
import com.google.firebase.firestore.ListenerRegistration;
import com.google.firebase.firestore.Query;
import com.google.firebase.firestore.QuerySnapshot;

import javax.annotation.Nullable;

public class FirebaseQueryLiveData extends LiveData<QuerySnapshot> 
    public static final String TAG = "FbaseQueryLiveData";

    private Query query;
    private final MyValueEventListener listener = new MyValueEventListener();
    private ListenerRegistration listenerRegistration;

    private boolean listenerRemovePending = false;
    private final Handler handler = new Handler();

    public FirebaseQueryLiveData(Query query) 
        this.query = query;
    

    private final Runnable removeListener = new Runnable() 
        @Override
        public void run() 
            listenerRegistration.remove();
            listenerRemovePending = false;
        
    ;

    @Override
    protected void onActive() 
        super.onActive();

        Log.d(TAG, "onActive");
        if (listenerRemovePending) 
            handler.removeCallbacks(removeListener);
        
        else 
            listenerRegistration = query.addSnapshotListener(listener);
        
        listenerRemovePending = false;
    

    @Override
    protected void onInactive() 
        super.onInactive();

        Log.d(TAG, "onInactive: ");
        // Listener removal is schedule on a two second delay
        handler.postDelayed(removeListener, 2000);
        listenerRemovePending = true;
    

    private class MyValueEventListener implements EventListener<QuerySnapshot> 
        @Override
        public void onEvent(@Nullable QuerySnapshot querySnapshot, @Nullable FirebaseFirestoreException e) 
            if (e != null)
                Log.e(TAG, "Can't listen to query snapshots: " + querySnapshot + ":::" + e.getMessage());
                return;
            
            setValue(querySnapshot);
        
    

【讨论】:

是的,这适用于 firebase 查询,谢谢@Brian Begun 更新为包括处理程序和延迟分离侦听器,以防止对 Firestore 的不必要调用(设备方向更改) 工作正常!我们需要 Kotlin 版本。 请同时发布 ViewModel 类 请同时发布 ViewModel (with transformations.map) 类【参考方案2】:

对于 Kotlin 的爱好者 :)

import android.os.Handler
import androidx.annotation.Nullable
import androidx.lifecycle.LiveData
import com.google.firebase.firestore.*
import timber.log.Timber

class FirebaseQueryLiveData(private val query: Query) : LiveData<QuerySnapshot>() 
    private val listener = MyValueEventListener()
    private var listenerRegistration: ListenerRegistration? = null

    private var listenerRemovePending = false
    private val handler = Handler()

    private val removeListener = Runnable 
        listenerRegistration!!.remove()
        listenerRemovePending = false
    

    override fun onActive() 
        super.onActive()

        Timber.d( "onActive")
        if (listenerRemovePending) 
            handler.removeCallbacks(removeListener)
         else 
            listenerRegistration = query.addSnapshotListener(listener)
        
        listenerRemovePending = false
    

    override fun onInactive() 
        super.onInactive()

        Timber.d("onInactive: ")
        // Listener removal is schedule on a two second delay
        handler.postDelayed(removeListener, 2000)
        listenerRemovePending = true
    

    private inner class MyValueEventListener : EventListener<QuerySnapshot> 
        override fun onEvent(@Nullable querySnapshot: QuerySnapshot?, @Nullable e: FirebaseFirestoreException?) 
            if (e != null) 
                Timber.e(e, "Can't listen to query snapshots: %s", querySnapshot)
                return
            
            value = querySnapshot
        
    

【讨论】:

以上是关于带有 Firebase 的 Android 架构组件,特别是 Firestore的主要内容,如果未能解决你的问题,请参考以下文章

带有范围的Android Firebase查询(上方,中间,下方)

Android上带有长字符串的Firebase异常

firebase 一个项目和 2 个带有应用程序动态链接的 android

Firebase Cloud Messaging 无法在带有 Flutter 应用程序的 Android 上运行

带有 Firebase 云消息传递的 Flutter 2.0:onMessage 未在 Android 上调用

使用带有 android firebase 短信认证的模拟器