Ich habe eine App als Lernprogramm gemacht, um zu lernen, wie gelöschte Alarme nach dem Neustart des Telefons neu gestartet werden. Nach dem Neustart empfängt BroadcastReceiver die Aktion BOOT_COMPLETED und startet einen Dienst, der alle Alarme neu startet. Alarme erstellen Benachrichtigungen, wenn sie angerufen werden. Nach ersten Tests habe ich Benachrichtigungen zur erwarteten Zeit erhalten und dann diese Tutorial-App vergessen und das Telefon nicht ausgeschaltet.App empfängt BOOT_COMPLETED mehrmals und Alarme werden erneut erstellt
Ich bekomme jedoch immer noch Benachrichtigungen auf meinem Bildschirm, als ob die App erneut Alarme ausgelöst hat. Während des Tages habe ich zweimal erhalten und alle sind unklar, warum. Das einzige, was den Neustart von Alarmen auslösen kann, ist die Aktion BOOT_COMPLETED. Was läuft hier falsch?
Manifest:
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.example.marat.recyclerviewtutorial">
<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED" />
<application
android:allowBackup="true"
android:icon="@mipmap/ic_launcher"
android:label="@string/app_name"
android:supportsRtl="true"
android:theme="@style/AppTheme">
<activity
// list of activities
<service android:name=".BootService"/>
<receiver android:name=".AlarmBroadcastReceiver"/>
<receiver android:name=".RestartAlarmsReceiver" android:enabled="true">
<intent-filter>
<action android:name="android.intent.action.BOOT_COMPLETED" />
</intent-filter>
</receiver>
</application>
</manifest>
RestartAlarmsReceiver.java
public class RestartAlarmsReceiver extends BroadcastReceiver {
private static final String TAG = "myTag";
@Override
public void onReceive(Context context, Intent intent) {
if ("android.intent.action.BOOT_COMPLETED".equals(intent.getAction())) {
Intent i = new Intent(context, BootService.class);
ComponentName service = context.startService(i);
if (null == service) {
// something really wrong here
Log.e(TAG, "Could not start service ");
}
else {
Log.e(TAG, "Successfully started service ");
}
} else {
Log.e(TAG, "Received unexpected intent " + intent.toString());
}
}
}
BootService.java
public class BootService extends Service {
private static final String TAG = "myTag";
@Nullable
@Override
public IBinder onBind(Intent intent) {
return null;
}
@Override
public int onStartCommand(Intent intent, int flags, int startId) {
Log.d(TAG, "onStartCommand");
Database db = new Database(this);
db.open();
ArrayList<ArrayList<String>> data = new ArrayList<ArrayList<String>>();
data = db.getData();
db.close();
Log.d(TAG, "db is openned");
for (int i=0; i<data.size(); i++) {
Intent notif = new Intent(this, AlarmBroadcastReceiver.class);
notif.putExtra("Text", data.get(i).get(2));
notif.putExtra("Position", data.get(i).get(0));
int sec = Integer.parseInt(data.get(i).get(3));
Log.d(TAG, "intent is openned");
PendingIntent pendingIntent = PendingIntent.getBroadcast(this, Integer.parseInt(data.get(i).get(0)), notif, PendingIntent.FLAG_CANCEL_CURRENT);
AlarmManager am = (AlarmManager) this.getSystemService(Context.ALARM_SERVICE);
am.set(AlarmManager.RTC_WAKEUP, System.currentTimeMillis() + (sec * 1000), pendingIntent);
Log.d(TAG, "Alarm is restarted");
}
Log.d(TAG, "before returning service");
return Service.START_STICKY;
}
}
Es ist bereits eine riesige Portion Code. Aber wenn Sie andere Teile meiner App benötigen, werde ich sie einschließen.
Vielen Dank im Voraus!
Wenn Sie mit dem Grund recht haben ('onStartCommand()' kehrt mit START_STICKY zurück), dann wäre die Lösung, die Absicht zu prüfen: Es wird null sein, wenn der Dienst nach dem Absturz neu gestartet wird. – 0X0nosugar
zumindest Überprüfung Intent. Aber trotzdem - es ist nicht nötig, den Service hier weiter zu betreiben. –
Ja, du bist genau da. Ich denke, in diesem Fall würde ich einen IntentService wie Sie vorgeschlagen bevorzugen. Oder der Dienst sollte 'stopSelf()' aufrufen, sobald es fertig ist. – 0X0nosugar