设备重启后重启计划通知(需要 Firebase 数据)
Restart scheduled notifications (that require Firebase data) after device reboot
我的应用目前在特定时间(由用户选择)安排任务通知。任务的标题和提醒日期保存在 Firebase 实时数据库中。
重点是,当设备重新启动时,所有这些都将丢失。所以需要重新启动过去安排的所有相关通知。
因此,我有一个可以获取 BOOT_COMPLETED 意图的 BroadcastReceiver。
但是,我无法访问 Firebase DB,因为当前没有用户登录 - 而且我也无法启动 Firebase 身份验证(无法识别 startActivityForResult 并且导入它会导致更多错误)。我认为这是因为 BroadcastReceiver 不是 activity.
我想知道是否有办法解决这个问题。
我目前尝试设置 intent 以启动 MainActivity(对用户进行身份验证),然后执行我的相关任务,但这没有用。
我想知道是否有办法解决这个问题,获取经过身份验证的用户(或在设备重启时对其进行身份验证),然后从 Firebase 获取数据。
AlarmReceiver 代码(扩展 BroadcastReceiver)- 有点乱,但它有助于获取上下文。
public class AlarmReceiver extends BroadcastReceiver {
private ChildEventListener mChildEventListener;
private FirebaseDatabase mFirebaseDatabase;
private DatabaseReference mTaskDatabaseReference;
private FirebaseAuth mFirebaseAuth;
private FirebaseAuth.AuthStateListener mAuthStateListener;
private int i;
@Override
public void onReceive(final Context context, Intent intent) {
mFirebaseDatabase = FirebaseDatabase.getInstance();
mFirebaseAuth = FirebaseAuth.getInstance();
if (intent.getAction() != null && context != null) {
if (intent.getAction().equals("android.intent.action.BOOT_COMPLETED")) {
TaskInfoFragment.showReminderNotification(context, MainActivity.class, "hoooo",1000);
onSignedOutCleanup(context);
mTaskDatabaseReference=mFirebaseDatabase.getReference().child("users").child(MainActivity.getCurrentUserId());
attachDatabaseReadListener(context);
//TODO - HANDLE DEVICE REBOOT
}
}
//Trigger the notification
Bundle extras = intent.getExtras();
String taskTitle = "Error, no task title!";
int taskIntId=-1;
if (extras != null) {
taskTitle = extras.getString("taskTitle");
taskIntId=extras.getInt("taskIntId");
}
TaskInfoFragment.showReminderNotification(context, MainActivity.class, taskTitle,taskIntId);
}
private void attachDatabaseReadListener(final Context context) {
i=0;
mChildEventListener = new ChildEventListener() {
@Override
public void onChildAdded(DataSnapshot dataSnapshot, String s) {
i++;
TaskList task = dataSnapshot.getValue(TaskList.class);
TaskInfoFragment.showReminderNotification(context, MainActivity.class, task.getTitle(),i);
Log.d("here is another task","title: "+task.getTitle());
}
public void onChildChanged(DataSnapshot dataSnapshot, String s) {}
public void onChildRemoved(DataSnapshot dataSnapshot) {
}
public void onChildMoved(DataSnapshot dataSnapshot, String s) {}
public void onCancelled(DatabaseError databaseError) {}
};
mTaskDatabaseReference.addChildEventListener(mChildEventListener);
}
private void onSignedInInitialize(final String userId,Context context) {
//Get reference for the task list for the logged in user and attach the database listener
mTaskDatabaseReference=mFirebaseDatabase.getReference().child("users").child(userId);
attachDatabaseReadListener(context);
}
private void onSignedOutCleanup(Context context) {
Intent taskIntent = new Intent(context,MainActivity.class);
// Send the intent to launch a new activity
context.startActivity(taskIntent);
}
private void detachDatabaseReadListener() {
if (mChildEventListener != null) {
mTaskDatabaseReference.removeEventListener(mChildEventListener);
mChildEventListener = null;
}
}
如果您想甚至在用户登录之前就显示这些通知,那么显然它们不应该与用户相关联。我会将它们与另一个值相关联,可能是一个标识设备的值。 James 评论的 InstanceIdToken
可能是一个很好的解决方案,因为它可以识别特定设备上的特定应用程序。
当然也可以查看 Firebase Cloud Messaging,它允许您在设备启动后立即向其发送通知。由于 FCM 消息由 Google Play 服务中的接收器处理,因此与尝试从您自己的接收器中的远程数据库加载它们相比,这通常是一种更可靠的传递此类消息的方法。
并非巧合:FCM 依靠实例 ID 令牌来识别 device/app 以向其发送消息。
所以总而言之,我使用 SharedPreferences 保存了当前登录的用户。
(之所以有效,是因为通知与用户相关,因此我们可以安全地假设最后登录的用户是相关用户)。
然后我更改了我的 Firebase 数据库树,以允许我使用当前登录的用户 ID 访问任务。多一点编码和错误修复就可以了。
感谢大家的帮助!
我的应用目前在特定时间(由用户选择)安排任务通知。任务的标题和提醒日期保存在 Firebase 实时数据库中。
重点是,当设备重新启动时,所有这些都将丢失。所以需要重新启动过去安排的所有相关通知。
因此,我有一个可以获取 BOOT_COMPLETED 意图的 BroadcastReceiver。 但是,我无法访问 Firebase DB,因为当前没有用户登录 - 而且我也无法启动 Firebase 身份验证(无法识别 startActivityForResult 并且导入它会导致更多错误)。我认为这是因为 BroadcastReceiver 不是 activity.
我想知道是否有办法解决这个问题。 我目前尝试设置 intent 以启动 MainActivity(对用户进行身份验证),然后执行我的相关任务,但这没有用。
我想知道是否有办法解决这个问题,获取经过身份验证的用户(或在设备重启时对其进行身份验证),然后从 Firebase 获取数据。
AlarmReceiver 代码(扩展 BroadcastReceiver)- 有点乱,但它有助于获取上下文。
public class AlarmReceiver extends BroadcastReceiver {
private ChildEventListener mChildEventListener;
private FirebaseDatabase mFirebaseDatabase;
private DatabaseReference mTaskDatabaseReference;
private FirebaseAuth mFirebaseAuth;
private FirebaseAuth.AuthStateListener mAuthStateListener;
private int i;
@Override
public void onReceive(final Context context, Intent intent) {
mFirebaseDatabase = FirebaseDatabase.getInstance();
mFirebaseAuth = FirebaseAuth.getInstance();
if (intent.getAction() != null && context != null) {
if (intent.getAction().equals("android.intent.action.BOOT_COMPLETED")) {
TaskInfoFragment.showReminderNotification(context, MainActivity.class, "hoooo",1000);
onSignedOutCleanup(context);
mTaskDatabaseReference=mFirebaseDatabase.getReference().child("users").child(MainActivity.getCurrentUserId());
attachDatabaseReadListener(context);
//TODO - HANDLE DEVICE REBOOT
}
}
//Trigger the notification
Bundle extras = intent.getExtras();
String taskTitle = "Error, no task title!";
int taskIntId=-1;
if (extras != null) {
taskTitle = extras.getString("taskTitle");
taskIntId=extras.getInt("taskIntId");
}
TaskInfoFragment.showReminderNotification(context, MainActivity.class, taskTitle,taskIntId);
}
private void attachDatabaseReadListener(final Context context) {
i=0;
mChildEventListener = new ChildEventListener() {
@Override
public void onChildAdded(DataSnapshot dataSnapshot, String s) {
i++;
TaskList task = dataSnapshot.getValue(TaskList.class);
TaskInfoFragment.showReminderNotification(context, MainActivity.class, task.getTitle(),i);
Log.d("here is another task","title: "+task.getTitle());
}
public void onChildChanged(DataSnapshot dataSnapshot, String s) {}
public void onChildRemoved(DataSnapshot dataSnapshot) {
}
public void onChildMoved(DataSnapshot dataSnapshot, String s) {}
public void onCancelled(DatabaseError databaseError) {}
};
mTaskDatabaseReference.addChildEventListener(mChildEventListener);
}
private void onSignedInInitialize(final String userId,Context context) {
//Get reference for the task list for the logged in user and attach the database listener
mTaskDatabaseReference=mFirebaseDatabase.getReference().child("users").child(userId);
attachDatabaseReadListener(context);
}
private void onSignedOutCleanup(Context context) {
Intent taskIntent = new Intent(context,MainActivity.class);
// Send the intent to launch a new activity
context.startActivity(taskIntent);
}
private void detachDatabaseReadListener() {
if (mChildEventListener != null) {
mTaskDatabaseReference.removeEventListener(mChildEventListener);
mChildEventListener = null;
}
}
如果您想甚至在用户登录之前就显示这些通知,那么显然它们不应该与用户相关联。我会将它们与另一个值相关联,可能是一个标识设备的值。 James 评论的 InstanceIdToken
可能是一个很好的解决方案,因为它可以识别特定设备上的特定应用程序。
当然也可以查看 Firebase Cloud Messaging,它允许您在设备启动后立即向其发送通知。由于 FCM 消息由 Google Play 服务中的接收器处理,因此与尝试从您自己的接收器中的远程数据库加载它们相比,这通常是一种更可靠的传递此类消息的方法。
并非巧合:FCM 依靠实例 ID 令牌来识别 device/app 以向其发送消息。
所以总而言之,我使用 SharedPreferences 保存了当前登录的用户。 (之所以有效,是因为通知与用户相关,因此我们可以安全地假设最后登录的用户是相关用户)。
然后我更改了我的 Firebase 数据库树,以允许我使用当前登录的用户 ID 访问任务。多一点编码和错误修复就可以了。
感谢大家的帮助!