1.簡介
在Android 5.0 提供了一套新的
JobScheduler
API,它允許您定義要在以後的某個時間或在指定的條件下(例如,當裝置在充電時)異步運作的作業來優化電池壽命。
https://developer.android.com/reference/android/app/job/package-summary
https://developer.android.com/reference/android/app/job/JobScheduler
https://developer.android.com/reference/android/app/job/JobService
2.關鍵類
JobInfo 描述任務,包含各個參數.
JobScheduler 管理任務:布置、撤銷、更新等.
JobService 執行任務的服務元件.
2.1 JobScheduler
| 布置一個任務,如果任務的id相同,後者覆寫前者,如果前者正在運作,它會被打斷. 布置失敗傳回 RESULT_FAILURE ,可能job的參數有錯誤 布置成功傳回RESULT_SUCCESS |
| 撤銷指定id的任務,如果任務正在運作,它立刻停止.由于是使用者手動撤銷,是以任務的 onStopJob 的傳回值沒 有意義,被忽略. |
| 撤銷所有任務. |
| 布置任務和工作内容,如果該任務不存在,則添加一個新的任務.如果該任務正在運作,會被中斷并以新的内容 添加到隊列中. 如果jobInfo使用 附加資料,要保持它們一緻, 使用JobInfo.Builder.setClipData(ClipData, int)添加資料後的任務永遠被視為新任務,即使ClipData相同. |
| 根據id查找任務. |
| 傳回目前應用布置的所有任務.(包括已經啟動的和等待中的) |
2.2 JobInfo及JobInfo.Builder
JobInfo.Builder 構造jobinfo,設定任務的各項參數.如網絡類型,運作周期等.
JobInfo build () | 生成一個JobInfo對象 |
setBackoffCriteria (long initialBackoffMillis,int backoffPolicy) | 設定回退政策,與setRequiresDeviceIdle(boolean)沖突. initialBackoffMillis 是失敗後的等待時間, backoffPolicy 是回退方式,有BACKOFF_POLICY_LINEAR 和 BACKOFF_POLICY_EXPONENTIAL 兩種. |
setEstimatedNetworkBytes (long downloadBytes, long uploadBytes) | 預算任務網絡連接配接時使用的位元組數,如果知道具體位元組最好,如果不是固定的可用JobInfo.NETWORK_BYTES_UNKNOWN |
setExtras (PersistableBundle extras) | 設定額外資料, PersistableBundle 裡要放基本類型的資料. |
setImportantWhileForeground (boolean importantWhileForeground) | 是否臨時加入白名單,在變成前台重要任務.預設false. 與setMinimumLatency、setOverrideDeadline、setPeriodic沖突。 |
setMinimumLatency (long minLatencyMillis) | 設定最小延遲時間,與 setPeriodic 沖突. |
setOverrideDeadline (long maxExecutionDelayMillis) | 最後執行期限,條件不滿足也執行.與 setPeriodic 沖突. |
setPeriodic (long intervalMillis) | 設定任務執行周期,機關毫秒. |
setPeriodic (long intervalMillis, long flexMillis) | |
setPersisted (boolean isPersisted) | 設定是持久任務,開機後仍然有效. |
setPrefetch (boolean prefetch) | 設定任務是否預讀本地内容,如果是,則系統會放寬網絡類型限制. |
setRequiredNetwork (NetworkRequest networkRequest) | 設定任務使用的網絡類型,如果無聯網,不要調用這個方法,預設是null,這是一個非常嚴厲的限制,如果網絡類型不滿足, 任務不會被執行.這個方法有重載,隻調用其中一個就可,重複調用後面的會覆寫前面的. 常用的類型: , or . |
setRequiredNetworkType (int networkType) | |
setRequiresBatteryNotLow (boolean batteryNotLow) | 是否隻在非低電量情況下運作,true表示在非低電量運作,預設false. |
setRequiresCharging (boolean requiresCharging) | 設定是否隻在充電時運作.預設fase.注意系統在特别繁忙時,可能忽略usb充電,這時任務不會被執行. |
setRequiresDeviceIdle (boolean requiresDeviceIdle) | 在空閑時運作,預設fase,這裡的空閑狀态是個寬泛的系統定義,通常指在沒有應用與使用者互動時. |
setRequiresStorageNotLow (boolean storageNotLow) | 非低存儲空間時運作.預設false. |
setTransientExtras (Bundle extras) | 給任務添加臨時資料,與setPersisted沖突. |
addTriggerContentUri (JobInfo.TriggerContentUri uri) | 添加内容觸發器,監聽某個内容,它變化後才執行這個任務,uri指定要被ContentObserver監聽的内容,與setPeriodic(long) or setPersisted(boolean)沖突.如: |
setTriggerContentMaxDelay (long durationMs) | 設定内容變化到任務被布置間的最大延遲(毫秒). |
setTriggerContentUpdateDelay (long durationMs) | 設定内容變化到任務被布置間的延遲(毫秒). If there are more changes during that time,the delay will be reset to start at the time of the most recent change. |
JobInfo常用的方法是一些get方法,如getRequiredNetwork () , getBackoffPolicy () , isPeriodic () 等.
2.3 JobService
以startService方式啟動服務,其中幾個重要方法:
| 當scheduler添加排程任務後,任務開始執行時産生這個回調,預設在主線程. 注意這個參數,它裡面儲存了傳來的資料.通常要儲存它,當任務完成時,手動調用jobFinished 時使用. 傳回true表示任務在手動調用jobFinished結束或系統條件不滿足而停止前一直在活躍狀态, 服務斷續運作,這時系統為這個任務保留wakelock鎖.直到jobFinished或onStopJob調用. 傳回false表示任務正常結束,這時系統會釋放與這個任務關聯的wakelock鎖. 如果任務簡短并且同步的那麼應該傳回false,如果異步的應用在任務完成後手動調用jobFinished |
| 來自系統的結束任務通知.通常在任務執行條件不能被滿足時産生這個回調,如:當你在構造任務時 指定了網絡條件是wifi,在任務執行期間你關掉了wifi. 注意:一定要處理這條資訊,如釋放不用的資源,否則應用會産生異常行為. 傳回true表示你還希望在按照構造裡指定的重試政策重試,當這個任務裡有多條工作内容時, 要傳回true,表示這個任務需要重新布置執行未完成的工作.. 傳回false表示結束不重試,但是不管傳回什麼,目前這個任務必需停止. |
| 當任務完成後,手動調用這個方法通知系統任務完成,然後系統釋放相應的wakelock鎖, 第1個參數是 onStartJob 傳來的參數. 第2個參數表示是否嘗試復原政策,如果是不得以要執行的這個方法,true表示按構造時指定的復原 政策重新安排. 預設的復原政策不會讓任務在系統睡眠期間執行,而隻是把它重新添加到任務隊列中,在系統修整維護期間 才執行這個任務. |
3.實作程序保活?不可靠!
如果想用JobService實作程序保活,那麼就得設定任務為周期任務,有幾個問題,證明用它實作程序保活不可靠.
- 在最近應用清單點全部清除後,程序會被殺死,周期任務被停止.
- 在api小于24時,不支援周期任務,隻能自己用timer實作,同時要求JobService這個服務元件開啟重新開機功能,但是這個功能不在在所有系統上都能順利進行,如在emui,和miui上都被拒絕.emui:
miui:6-11 15:47:42.292 1494-13224/? I/HwPFWLogger: AppAutoStartupPolicy:prevent scheduleRestart service of package com.example.android.jobscheduler, serviceInfo com.example.android.jobscheduler.service.MyJobService 06-11 15:48:12.311 1494-1494/? I/HwPFWLogger: AppAutoStartupPolicy:prevent start package com.example.android.jobscheduler, serviceInfo com.example.android.jobscheduler.service.MyJobService by callerPid 1494, callerUid 1000, scene:jobService
06-11 16:45:05.849 1432-1443/system_process I/ActivityManager: Force stopping service ServiceRecord{bf9fd5e u0 com.example.android.jobscheduler/.service.MyJobService} 06-11 16:45:06.147 1432-1447/system_process I/AutoStartManagerService: MIUILOG- Reject service :Intent { cmp=com.example.android.jobscheduler/.service.MyJobService } userId : 0 uid : 10127
- 而api大于23時,最小周期是15分鐘,這對于實時任務來說又有點長.
4.示例
4.1 相關權限
常用權限:
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED" />
必用權限:
<service android:name="MyJobService"
android:permission="android.permission.BIND_JOB_SERVICE" >
...
</service>
4.2 下載下傳代碼
https://gitee.com/xi/JobService.git