在Viewmodel中访问BroadCastReceiver [英] Accessing BroadCastReceiver in Viewmodel

查看:358
本文介绍了在Viewmodel中访问BroadCastReceiver的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在努力选择正确的方法来将数据从broadcastReceiver传递到ViewModel,然后从那里将数据传递到我的存储库并更新LiveData.我使用FCM推送通知,并具有使用ActivityLifecycle的本地broadCastReceiver.

I am struggling in choosing the right way to pass data from broadcastReceiver to ViewModel and from there I pass data to my Repository and update LiveData. I use FCM push notifications and have local broadCastReceiver which uses ActivityLifecycle.

我发现从BroadcastReceiver访问ViewModel是不好的做法,但是不确定为什么吗?

I found that it is bad practice to access ViewModel from BroadcastReceiver, but not sure why?

如果我管理broadcastReceiver的生命周期,应该不会造成任何问题... 那么将接收到的数据从FCM传递到存储库的MediatorLiveData的最佳方法是什么?我使用MediatorLiveData,因为我添加了其他内容LiveData来源(API请求和FCM).

If I manage lifecycle of broadcastReceiver it should not cause any problems... So what is the best way to pass received data from FCM to my Repository's MediatorLiveData? I use MediatorLiveData, because I add different LiveData sources(API request and FCM).

感谢提供建议和正确的方法来实现broadCastReceiver.

Would be grateful for advice and correct way of implementing broadCastReceiver.

我曾经考虑过要从BroadCastReceiver访问存储库,就像这样:

I have thought about accessing Repository from BroadCastReceiver, like this:

RepositoryMain.getSingletonInstance().setResponse(state);

推荐答案

您需要定义单个事实来源( SSoT ).在您的情况下,它是Repository(如果Repository封装了数据库持久性存储,则 SSoT 它是db).现在,您需要实现从接收器实现的数据流,以通过 SSoT (Repository)进行查看,如下例所示:

You need to define single source of truth (SSoT). In your case it Repository (if Repository encapsulate db persistence storage, SSoT it is db). Now you need to implement data flow from receiver to view through SSoT (Repository) like in example below:

public class FcmReceiver extends BroadcastReceiver {

    private final MutableLiveData<MyData> mData = new MutableLiveData<>();

    public LiveData<MyData> getData() {
        return mData;
    }

    @Override
    public void onReceive(Context context, Intent intent) {
        // entry point of data
        mData.setValue(new MyData());
    }
}

存储库

public class Repository {

    private static final Repository INSTANCE = new Repository();

    private final MediatorLiveData<MyData> mData = new MediatorLiveData<>();

    private Repository() {}

    public static Repository instance() {
        return INSTANCE;
    }

    public LiveData<MyData> getData() {
        return mData;
    }

    public void addDataSource(LiveData<MyData> data) {
        mData.addSource(data, mData::setValue);
    }

    public void removeDataSource(LiveData<MyData> data) {
        mData.removeSource(data);
    }
}

查看模型

public class MyViewModel extends ViewModel {

    public LiveData<MyData> getData() {
        // for simplicity return data directly to view
        return Repository.instance().getData();
    }
}

活动

接收方数据和Repository

public class MainActivity extends AppCompatActivity {

    private FcmReceiver mReceiver;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        mReceiver = new FcmReceiver();
    }

    @Override
    protected void onStart() {
        super.onStart();
        // add data source
        Repository.instance().addDataSource(mReceiver.getData());
        registerReceiver(mReceiver, IntentFilter.create("action", "type"));
    }

    @Override
    protected void onStop() {
        super.onStop();
        // don't forget to remove receiver data source
        Repository.instance().removeDataSource(mReceiver.getData());
        unregisterReceiver(mReceiver);
    }
}

这篇关于在Viewmodel中访问BroadCastReceiver的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆