报警意图进入快速无限循环

时间:2018-05-22 15:26:10

标签: android

我试图编写一段代码,每天必须唤醒几次并通知服务器。我试图使用警报意图和广播接收器,但接收器正在无限快速触发,我似乎无法阻止它。

我的所有代码都在一个文件中。流程很简单。 在启动时唤醒,检查我们是否应该通信,尝试通信其他设置两个等待条件之一,激活警报。 唤醒警报,尝试通信,必要时重新激活警报,否则将其杀死。

当我在我的设备上构建和部署此apk时,会发生以下流程:
重启
接收器接收启动意图就好了 警报得到预定 警报意图在80秒后按预期触发 然后在接下来的80秒后,
然后log-cat显示广播接收器被非常快速地触发。
每秒几次好像被垃圾邮件一样。

我完全不知道为什么它的表现如此

private PendingIntent pendingIntent;
/**
 * Receive a signal, in our case, the device has booted up
 * @param context The Context in which the receiver is running.
 * @param intent  The Intent being received.
 */
@SuppressLint("UnsafeProtectedBroadcastReceiver")
@Override
public void onReceive(Context context, Intent intent) {
    Log.d("autostart", "broadcast received");
    if(intent.getAction()==null)return;
    Intent alarmIntent = new Intent(context, autostart.class);
    alarmIntent.setAction("device.activation.alarm");
    pendingIntent = PendingIntent.getBroadcast(context, 0, alarmIntent, PendingIntent.FLAG_CANCEL_CURRENT);//cancel flag seems to be ignored
    cancel(context);//cancel command seems to be ignored
    if (intent.getAction().equals("android.intent.action.BOOT_COMPLETED")) {
        // Set the alarm here.
        Log.d("autostart","We have booted");
        RegisterActivation registerActivation = new RegisterActivation(context);
        if(registerActivation.AlreadyActivated())
            return;//no need
        if(registerActivation.ActivationPending()){
            //perform regular activation
            return;
        }
        if(registerActivation.canComplete()){
            boolean success = registerActivation.sendActivation();//talk to server
            if(success) {
                registerActivation.markCompleted();
                cancel(context);
            }
            else {
                registerActivation.markFileWaiting();
                startPending(context);
            }
            return;
        }
        if(registerActivation.shouldWait()){//if can complete fails, then shouldWait will immediately return true
            Log.d("autostart", "waiting");
            registerActivation.markFileSimWait();
            startWait(context);
            return;
        }
    }
    if(intent.getAction().equals("device.activation.alarm")){
        Log.d("autostart","alarm triggered");
        cancel(context);
        RegisterActivation registerActivation = new RegisterActivation(context);
        if(registerActivation.AlreadyActivated()){//for now always false
            cancel(context);
            return;
        }
        if(registerActivation.ActivationPending()){//for now always false
            //same as before
            return;
        }
        if(registerActivation.canComplete()){//glitch happens here
            if(registerActivation.sendActivation()){
                registerActivation.markCompleted();
                cancel(context);
            }else{
                registerActivation.markFileWaiting();
                startPending(context);//this immediatly triggers the broadcast recieve
            }
            return;
        }
        if(registerActivation.shouldWait()){
            registerActivation.markFileSimWait();
            startWait(context);
        }
    }
}

public void startPending(Context context) {
    AlarmManager manager = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
    int interval = 80000;//will later become 4 hours
    manager.set(AlarmManager.RTC_WAKEUP,interval,pendingIntent);
    Log.d("autostart", "alarm activated");
}

public void startWait(Context context) {//same function but different time interval
    AlarmManager manager = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
    int interval = 90000;// will later become 12 hours
    manager.set(AlarmManager.RTC_WAKEUP, interval, pendingIntent);
}

public void cancel(Context context) {
    AlarmManager manager = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
    manager.cancel(pendingIntent);
}

1 个答案:

答案 0 :(得分:0)

谢谢Mike M. https://stackoverflow.com/users/2850651/mike-m

我会将您的评论标记为答案,但您只是评论

我从

开始
manager.set(AlarmManager.RTC_WAKEUP,interval,pendingIntent);

为:

manager.setInexactRepeating(AlarmManager.RTC_WAKEUP, System.currentTimeMillis()+interval, interval, pendingIntent);

我必须将间隔添加到intervalMillis参数中 经过测试,manager.set(...)函数实际上并没有像我想要的那样做得很好,所以我只需要在开始时触发取消。

再次感谢迈克:)