Android 进程保活(实战)

一、双进程绑定—相互唤起(适用于Android5.0以下,5.0以上需要配合使用策略二)

(1)创建两个service,分别注册在不同的进程中
(2)以启动方式绑定service时,A服务用B服务中的ServiceConnection实例,B服务用A服务的ServiceConnection实例。
(3)在ServiceConnection的onServiceDisconnected方法,去启动另一个服务。如A服务中的conn去启动B服务。

二、Android 5.0以上用JobScheduler保活兼容7.0(若主动多次结束进程后,便无法唤起,需要配合策略三)

示例代码如下:

@RequiresApi(api = Build.VERSION_CODES.LOLLIPOP)
public class KeepJobService extends JobService {
    private static final String TAG = "KeepJobService";
    /**
     *
     */
    public static final int PERIODIC_TIME = 5 * 60 * 1000;
    private int jobId;

    @Override
    public int onStartCommand(Intent intent, int flags, int startId) {
        Log.d(TAG, "keep-> onStartCommand: job");
        JobScheduler mJobScheduler = (JobScheduler) getSystemService(Context.JOB_SCHEDULER_SERVICE);
        if (mJobScheduler != null) {
            mJobScheduler.cancel(jobId);
            JobInfo.Builder builder = new JobInfo.Builder(startId++,
                    new ComponentName(getPackageName(), KeepJobService.class.getName()));

            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
                //执行的最小延迟时间
                builder.setMinimumLatency(PERIODIC_TIME);
                //执行的最长延时时间
                builder.setOverrideDeadline(PERIODIC_TIME);
                builder.setMinimumLatency(PERIODIC_TIME);
                //线性重试方案
                builder.setBackoffCriteria(PERIODIC_TIME, JobInfo.BACKOFF_POLICY_LINEAR);
            } else {
                //每隔5秒运行一次
                builder.setPeriodic(PERIODIC_TIME);
                builder.setRequiresDeviceIdle(true);
            }
            builder.setRequiresCharging(true);
            builder.setRequiredNetworkType(JobInfo.NETWORK_TYPE_ANY);
            //设置设备重启后,是否重新执行任务
            builder.setPersisted(true);
            jobId = mJobScheduler.schedule(builder.build());
            if (jobId <= 0) {
                Log.d(TAG, "keep-> schedule failed");
            } else {
                Log.d(TAG, "keep-> schedule success");
            }
        }

        return START_STICKY;
    }

    @Override
    public boolean onStartJob(JobParameters params) {
        Log.d(TAG, "keep-> onStartJob");
        //启动双进程的服务
        return false;
    }

    @Override
    public boolean onStopJob(JobParameters params) {
        return false;
    }

}
//注册
<service
            android:name=".service.KeepJobService"
            android:enabled="true"
            android:exported="true"
            android:permission="android.permission.BIND_JOB_SERVICE" />

三、Workmanager保活策略(三种策略一起使用效果才更佳)

WorkManager引用库地址:

compile ’android.arch.work:work-runtime:1.0.0-alpha02‘

示例代码如下:
KeepLiveWork.java类


public class KeepLiveWork extends Worker {
    private static final String TAG = "KeepLiveWork";

    @NonNull
    @Override
    public WorkerResult doWork() {
        Log.d(TAG, "keep-> doWork: startKeepService");
        //启动job服务
        startJobService();
        //启动相互绑定的服务
        startKeepService();
        return WorkerResult.SUCCESS;
    }
}

启动keepWork方法:

    public void startKeepWork() {
        WorkManager.getInstance().cancelAllWorkByTag(TAG_KEEP_WORK);
        Log.d(TAG, "keep-> dowork startKeepWork");
        OneTimeWorkRequest oneTimeWorkRequest = new OneTimeWorkRequest.Builder(KeepLiveWork.class)
                .setBackoffCriteria(BackoffPolicy.LINEAR, 5, TimeUnit.SECONDS)
                .addTag(TAG_KEEP_WORK)
                .build();
        WorkManager.getInstance().enqueue(oneTimeWorkRequest);

    }

四、无声背景音乐保活(仅限用户点击清理全部时,不被结束)

最近下载了趣头条,每次玩游戏的时候,习惯性结束全部应用,发现了趣头条没有被结束,而且还在不停的播放无声音乐。然后写了demo在真机上测试了一下,果然好使。

五、保活策略真机测试

  1. 华为荣耀8 lite(8.0)、OPPO r9s(6.0):多次试验kill子进程和主进程,进程都可以被重新启动。
  2. 小米6(8.0):kill子进程,子进程会被立即重新启动。主进程被kill,不会立即启动,测试发现解锁屏幕或者切换网络后,主进程会被立即拉起。

你可能感兴趣的:(Android)