IntentService源码解析 | Tianbin’s Notes
本文主要分析IntentService
的内部实现流程,涉及Service
,HandlerThread
,Handler
,Looper
,MessageQueue
等相关内容。
示例代码
public class JobIntentService extends IntentService {
public static void start(Context context) {
Intent intent = new Intent(context, JobIntentService.class);
intent.setAction("com.tianbin.service.jobintentservice");
context.startService(intent);
}
public JobIntentService() {
super("JobIntentService");
}
@Override
protected void onHandleIntent(@Nullable Intent intent) {
if (intent == null) {
return;
}
Log.e("tag", intent.getAction());
}
}
源码分析
调用以上示例中的start
方法后,Logcat
中会输出com.tianbin.service.jobintentservice
,也就是在start
方法中为Intent
设置的action
。
下面就以start
方法为入口进行梳理。
IntentService
IntentService
继承自Service
,从Service
的生命周期可以了解到,调用Context.startService
方法会创建Service
并调用它的onStartCommand
方法。
以下是IntentService.onStartCommand
相关源码
@Override
public void onStart(@Nullable Intent intent, int startId) {
Message msg = mServiceHandler.obtainMessage();
msg.arg1 = startId;
msg.obj = intent;
mServiceHandler.sendMessage(msg);
}
@Override
public int onStartCommand(@Nullable Intent intent, int flags, int startId) {
onStart(intent, startId);
return mRedelivery ? START_REDELIVER_INTENT : START_NOT_STICKY;
}
onStartCommand
方法调用了Service
的onStart
方法,而在onStart
方法内,则是调用ServiceHandler
发送了一个Message
。
ServiceHandler
是IntentService
的内部类,继承自Handler
源码如下
private final class ServiceHandler extends Handler {
public ServiceHandler(Looper looper) {
super(looper);
}
@Override
public void handleMessage(Message msg) {
onHandleIntent((Intent)msg.obj);
stopSelf(msg.arg1);
}
}
这里的onHandleIntent是一个抽象方法,示例JobService
中实现了该方法,log
信息也是在这里输出的。
可以看出,onHandleIntent
方法之后会调用Service
的stopSelf
方法来停止服务。
接下来分析mServiceHandler.sendMessage(msg)
到onHandleIntent((Intent)msg.obj)
之间的执行内容。
ServiceHandler
ServiceHandler
的sendMessage
方法最终会调用到它的enqueueMessage
方法,源码如下
private boolean enqueueMessage(MessageQueue queue, Message msg, long uptimeMillis) {
msg.target = this;
if (mAsynchronous) {
msg.setAsynchronous(true);
}
return queue.enqueueMessage(msg, uptimeMillis);
}
从这里可以发现Handler
使用了一个MessageQueue
对象来保存msg
,而MessageQueue
实例是属于Handler
的
下面分析下ServiceHandler
的实例化,源码如下
@Override
public void onCreate() {
super.onCreate();
HandlerThread thread = new HandlerThread("IntentService[" + mName + "]");
thread.start();
mServiceLooper = thread.getLooper();
mServiceHandler = new ServiceHandler(mServiceLooper);
}
从上面源码中可以看到ServiceHandler
的Looper
实例来自HandlerThread
对象,先来看下handlerThread
的源码。
HandlerThread
HandlerThread
继承自Thread
,下面是它的run
方法源码
@Override
public void run() {
mTid = Process.myTid();
Looper.prepare();
synchronized (this) {
mLooper = Looper.myLooper();
notifyAll();
}
Process.setThreadPriority(mPriority);
onLooperPrepared();
Looper.loop();
mTid = -1;
}
Looper
下面是Looper
的prepare
方法
public static void prepare() {
prepare(true);
}
private static void prepare(boolean quitAllowed) {
if (sThreadLocal.get() != null) {
throw new RuntimeException("Only one Looper may be created per thread");
}
sThreadLocal.set(new Looper(quitAllowed));
}
prepare
方法中使用sThreadLocal
来存储Looper
对象,保证了Looper
对象是线程私有的。
接下来看run
方法中的Looper.loop
方法
public static void loop() {
final Looper me = myLooper();
...
final MessageQueue queue = me.mQueue;
Binder.clearCallingIdentity();
final long ident = Binder.clearCallingIdentity();
for (;;) {
Message msg = queue.next(); // might block
if (msg == null) {
// No message indicates that the message queue is quitting.
return;
}
...
final long slowDispatchThresholdMs = me.mSlowDispatchThresholdMs;
...
final long start = (slowDispatchThresholdMs == 0) ? 0 : SystemClock.uptimeMillis();
final long end;
try {
msg.target.dispatchMessage(msg);
end = (slowDispatchThresholdMs == 0) ? 0 : SystemClock.uptimeMillis();
} finally {
if (traceTag != 0) {
Trace.traceEnd(traceTag);
}
}
...
msg.recycleUnchecked();
}
}
loop
方法的功能主要用来分发MessageQueue
链表中存储的Message
。顺便说明一下msg.recycleUnchecked()
方法用来重置msg
,方便后续调用Handler.obtainMessage
方法时进行复用。
接下来分析下msg.target.dispatchMessage(msg);
从上面ServiceHandler
的enqueueMessage
代码中可以了解到,这里的target
就是ServiceHandler
实例。
直接来看Handler
的dispatchMessage
源码
public void dispatchMessage(Message msg) {
if (msg.callback != null) {
handleCallback(msg);
} else {
if (mCallback != null) {
if (mCallback.handleMessage(msg)) {
return;
}
}
handleMessage(msg);
}
}
这里的handleMessage
是一个空实现,需要Handler
子类进行重写,比如ServiceHandler
@Override
public void handleMessage(Message msg) {
onHandleIntent((Intent)msg.obj);
stopSelf(msg.arg1);
}
这就是从mServiceHandler.sendMessage(msg)
到onHandleIntent((Intent)msg.obj)
的代码执行流程。
MessageQueue
以上流程中关于MessageQueue
保存Message
对象没有深入分析,这里做个补充
下面的MessageQueue
的enqueueMessage
方法源码
boolean enqueueMessage(Message msg, long when) {
...
synchronized (this) {
if (mQuitting) {
IllegalStateException e = new IllegalStateException(
msg.target + " sending message to a Handler on a dead thread");
Log.w(TAG, e.getMessage(), e);
msg.recycle();
return false;
}
msg.markInUse();
msg.when = when;
Message p = mMessages;
boolean needWake;
// 在链表头插入msg
if (p == null || when == 0 || when < p.when) {
// New head, wake up the event queue if blocked.
msg.next = p;
mMessages = msg;
needWake = mBlocked;
}
// 按执行时间顺序插入msg
else {
needWake = mBlocked && p.target == null && msg.isAsynchronous();
Message prev;
for (;;) {
prev = p;
p = p.next;
if (p == null || when < p.when) {
break;
}
if (needWake && p.isAsynchronous()) {
needWake = false;
}
}
msg.next = p; // invariant: p == prev.next
prev.next = msg;
}
// We can assume mPtr != 0 because mQuitting is false.
if (needWake) {
nativeWake(mPtr);
}
}
return true;
}
从上面代码可以了解到,Message
的插入操作主要分两种情况,一种是调用没有指定执行时间的,直接在表头插入,另一种是指定执行时间的,需要按执行时间顺序进行插入。
以上就是IntentService
代码的整个执行流程。