[android] JobIntentService 소개 (tutorial) |
https://medium.com/til-kotlin/jobintentservice-for-background-processing-on-android-o-39535460e060
https://developer.android.com/reference/android/support/v4/app/JobIntentService
-
JobIntentService 는 SupportLib 에 들어있다.
-
JobIntentService 는 Android O 부터는 JobScheduler 를 사용하고, Android O 이전 단말에서는 background service 를 사용한다.
-
Android O 이전 단말에서는 background 서비스가 즉각적으로 실행된다.
그리고 각각의 job 이 순차적으로 수행된다.
기존의 IntentService 와 동일하다고 보면 된다.
-
Android O 이상에서는 job 이 JobScheduler 를 통해 순차적으로 수행된다.
내부적으로는 jobInfo.setOverrideDeadline(0).build() 를 사용하는데,
dealine 이 0 이라는 의미는 사실 즉각 수행하라는 의미와 동일하다.
( 그러나 요청자체는 저렇지만 무조건 바로 수행됨이 보장되지는 않는다. )
-
그리고 JobScheduler 를 사용하기 때문에 android.permission.BIND_JOB_SERVICE permission 을 주어야 한다. 안 주면 SecurityException 이 발생한다.
<service
android:name=“com.example.MyJobIntentService”
android:permission=“android.permission.BIND_JOB_SERVICE" />
-
WakefulBroadcastReceiver 를 쓸 필요가 없다.
JobIntentService 는 Wakelock 을 알아서 관리해준다.
O 미만에서는 wakelock 을 관리하기 떄문에 permission 은 여전히 필요하다.
<uses-permission android:name=”android.permission.WAKE_LOCK” />`
-
적용하기 위해서는 우선 gradle 에 google maven repo 를 연결해야 한다.
allprojects {
repositories {
jcenter ()
maven {
url "https://maven.google.com"
}
}
}
-
dependency 로 support-compat:26 이상이 필요하다.
dependencies {
...
compile 'com.android.support:support-compat:26.0.0'
}
-
JobIntentService 의 시작은 startService 가 아니라 enqueueWork 를 통해 시작한다.
그리고 job 의 handle 은 onHandleIntent 대신 onHandleWork 를 통해 한다.
한 가지 큰 차이점이 있다면, JobIntentService 는 system 에 의해 언제든지 onStopCurrentWork() 가 불릴 수 있다는 것이다.
-
enqueueWork(Context context, Class cla, int jobId, Intent work)
Android O 이상에서는 deadline 이 0 으로 설정된다.
그러나 완전 즉각 수행되는것이 perfect 하게 보장되지는 않는다.
doze 모드나 out of memory 등의 상황에서는 이슈가 될 수 있기 때문이다.
Android O 미만에서는 background service 가 startService 를 통해 수행된다.
doze 모드와 관계 없이 작동하기 때문에 doze 모드의 network timeout 등은 알아서 관리되어야 한다.
동일한 class 를 target 하는 경우 jobId 는 항상 같아야 한다.
만약 새로운 jobId 를 주려면 새로운 class 를 정의해야 한다.
이 규칙을 따르지 않는다면, O 미만에서는 문제가 없지만, O 이상에서는 IllegalArgumentException 을 마딱뜨리게 될 것이다.
work Intent 는 null 일 수 없다. (work intent 는 handle 될 녀석이다, onHandleWork 에 전달될 녀석이다.)
null 이면 IllegalArgumentException 이 발생한다.
-
onHandleWork(Intent intent)
여기에 전달되는 intent 는 enqueueWork 를 통해 주입된 intent 이며, queue 에 들어가있다가 순차적으로 처리된다.
Wakelock 은 자동으로 관리가 된다.
그러므로 그냥 job 처리에만 신경쓰면 된다.
onHandleWork 가 마무리되면 queue 에 다음 내용이 있으면 다시 onHandleWork 가 불린다.
이 함수는 bg thread 에서 불린다.
-
onStopCurrentWork()
이 녀석은 job 이 멈춰야 할 때 불린다.
JobService.onStopJob() 과 마찬가지로, 이 녀석은 system 이 job 을 shutdown 시킬 때 부른다.
이녀석이 불리면 work 를 중단하면서 현재 상태를 저장한 후, 다음 기회에 job 을 이어나가야 한다.
reschedule 이 필요하면 true 를 return 한다.
scheduling 이 다시 필요하지 않는다면 false 를 return 한다.
-
위 링크를 보면 얼마나 시간이 지나야 onStopCurrentWork 가 불리는지 감을 잡을 수 있다. (10분)
-
최대한 미뤄라!!
JobScheduler 를 쓰던 뭐던 결국 bg 에서 뭔가 하는 것은 나쁜 UX 일 수 있다.
원하지 않는 타이밍에 battery, memory 등을 사용하기 때문이다.
그래서 최대한 미룰 수 있는 만큼 미룬 후에 수행하라.
'프로그래밍 놀이터 > 안드로이드, Java' 카테고리의 다른 글
[android] NoClassDefFoundError for SafeBrowsingResponse (0) | 2018.11.30 |
---|---|
[android] Cookie 는 android 단말에서 world wide 한가? (0) | 2018.11.29 |
[android] AAC 로 app 의 background, foreground 상태 알기 (1) | 2018.11.24 |
[android] code 와 resource shrink 하자! (0) | 2018.11.23 |
[android] D8 이 뭐야? (0) | 2018.11.22 |
댓글