如何在 BroadcastReceiver 中使用房间数据库?

How to use Room Database inside BroadcastReceiver?

美好的一天。我的应用程序需要接收短信,我现在想做的是,我想在应用程序收到消息后立即将数据从 BroadcastReceiver 插入数据库,但我失败了。这是我的代码。

public class SmsReceiver extends BroadcastReceiver {
    @Override
    public void onReceive(Context context, Intent intent) {
        ViewModel model = ViewModelProviders.of((FragmentActivity) context).get(ViewModel.class);

        Bundle bundle = intent.getExtras();

        Object[] objects = (Object[]) Objects.requireNonNull(bundle).get("pdus");
        SmsMessage[] smsMessages = new SmsMessage[Objects.requireNonNull(objects).length];

        Sms sms = new Sms();
        for (int i = 0; i < smsMessages.length; i++) {
            smsMessages[i] = SmsMessage.createFromPdu((byte[]) objects[i]);
            sms = new Sms(
                    smsMessages[i].getOriginatingAddress(),
                    smsMessages[i].getMessageBody(),
                    smsMessages[i].getTimestampMillis()
            );
        }

        model.insert(new ReplyToVotersQueue(sms.getBody(),sms.getAddress()));
    }
}

如我们所见,我正在尝试将数据插入数据库,但出现了一个错误

java.lang.RuntimeException: Unable to start receiver mgb.com.smspoll.Services.SmsReceiver: java.lang.ClassCastException: android.app.ReceiverRestrictedContext cannot be cast to androidx.fragment.app.FragmentActivity

我在网上搜索这个问题的答案时发现 BroadcastReceiver 无法转换为 Activity 因为 BroadcastReceiver 可以 运行 没有上下文。如果是这样,那么有没有 如何在收到短信后使用房间数据库将数据插入数据库?由于我的应用程序是 SMS Poll,因此我需要 运行 我的应用程序处于后台进程中。

这里的问题是您试图在 activity 或片段之外检索 ViewModel,这不是一个好的做法,也不起作用。

解决方法是这样的:

Separate your Room DB operation from ViewModel in a separate singleton class. Use it in ViewModel and any other place required. When Broadcast is received, write data to DB through this singleton class rather than ViewModel.

更多请看这个post: