我们的app经常会包含一些继承自Service或者IntentService的类。这些类的经常会用来处理系统或者app自身产生的一些Intent事件。
这是一种很方便的事件驱动模型。这里我定义了一个IntentService的子类。这个类用来接收一个由AlarmManager产生的定时事件。这个类工作的很好。直到有一天,我很惊讶的发现这个类有的时候会很诡异的不工作,或者刚开始进入处理逻辑就退出了。于是就花了一些时间去定位和寻找原因。现在原因已经基本清楚了。
先上一段代码:
public class EventService extends IntentService { private static final String TAG = "EventService"; private PowerManager.WakeLock wl; public SchedulerEventService(String name) { super(name); } public SchedulerEventService() { super(TAG); } @Override public void onCreate() { Log.d(TAG, " EventService onCreate."); super.onCreate(); PowerManager pm = (PowerManager) getSystemService(Context.POWER_SERVICE); wl = pm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "EventService"); wl.acquire(); } @Override public void onDestroy() { Log.d(TAG, " EventService onDestroy."); super.onDestroy(); wl.release(); } @Override public int onStartCommand(Intent intent, int flags, int startId) { super.onStartCommand(intent, flags, startId); return (START_REDELIVER_INTENT); } @Override protected void onHandleIntent(Intent intent) { Log.d(TAG, "event received at: " + new Date().toString()); if (intent != null) { executeTask(); } }}
当我的测试手机在玩一个游戏的时候,问题出来了。这个EventService在开始真正执行任务的时候:executeTask,诡异的退出来了。
最终发现了问题:当游戏的前台运行的时候,非常耗费内存。当我的APP在后台试图启动EventService的时候因为内存吃紧,被Android 系统杀死了。
这里有几个链接也说明了类似问题:
解决的一个办法是对OnStartCommand方法的Override。当这个方法返回
START_REDELIVER_INTENT
的时候,系统重新启动service之后会把最后一个intent重新再传递给我们的service来处理。
如果碰到这种service被系统杀死的情况,通过这种方式可以给service一个机会重新再把最后一次没做的事情做完。