Intentservice is a background service class provided in Android, we send request commands through intent to intentservice in an external component, and then Intentservice executes commands in the command queue one after the other, and when the first command is received, Intentservice starts and starts a background thread to execute the first command, and then the command in the queue is executed sequentially, and then the service is stopped and destroyed after all the commands in the queue have been executed.
Different from the service
- The programs in the service still run in the main thread, while the programs in Intentservice run in our asynchronous background thread. Before reaching Intentservice, I mostly wrote a service myself in the project, writing a background thread in the service to deal with the related transactions, and the work of Android has already helped us encapsulate the good.
- In service, when my background service finishes executing, I need to call the StopService method destruction service in the external component, and Intentservice does not need it, it will be destroyed automatically after the work has finished executing.
The use of Intentservice
1. Write your own service class inheritance Intentservice, and override the Onhandleintent (Intent) method in it, which is an abstract method of Intentservice, To handle the services that we open through the StartService method, the incoming parameter intent is the intent that opens the service. Here I rewrite a myservice class to handle background transactions, each call to Count plus 1, and print log.
PackageCom.example.intentservicetest;ImportAndroid.app.IntentService;ImportAndroid.content.Intent;ImportAndroid.util.Log; Public class myservice extends intentservice { Private Static FinalString TAG = MyService.class.getSimpleName ();Private intCount =0; Public MyService() {Super(TAG);//TODO auto-generated constructor stub}@Override protected void onhandleintent(Intent Intent) {//TODO auto-generated method stub //Add the code we want to execute here, we can save the data we need in intent, //Every command sent via intent will be executed sequentiallyCount + +; LOG.W (TAG,"Count::"+ count); }}
2. Sign up for our service: Next add our service under the Application tab in the Androidmanifest file.
<service android:name="com.example.intentservicetest.MyService" />
3. Open the service in the external component: Here we use the intent Loop 10 times to open the service in the activity.
for (int010; i++) { new Intent(MainActivity.this, MyService.class); startService(intent);}
4. Result output:
You can see that our request commands are executed sequentially in MyService.
Principle Analysis
1. Life cycle functions:
Intentservice is also inherited from the service, and it has the same life-cycle function;
- OnCreate: Called when service is created;
- Onstartcommand (Intent, int, int) method: The service source can see that the OnStart method is called in the method. Each time a component starts a service through the StartService method, it is called once, two int parameters, one is the group identifier, one is the boot ID, and the group identifier is used to indicate whether the current intent send is a resend or a send that has never been successful. Each time the Onstartcommand method is called, the start ID is different, and the boot ID is used to distinguish between different commands;
- OnDestroy method: Called when the service is stopped.
2.onCreate method: First, let us look at the OnCreate method in Intentservice source code,
@Override publicvoidonCreate() { super.onCreate(); new HandlerThread("IntentService[""]"); thread.start(); mServiceLooper = thread.getLooper(); new ServiceHandler(mServiceLooper);}
You can see that an asynchronous thread handlerthread is turned on in the OnCreate method of Intentservice to process our request, and we use Looper and handler to manage our request command queue. For handlerthread usage, refer to the following blog post: Android source code Analysis –handler and looper mechanism detailed.
3. How to stop the service
seeing the OnCreate method we can see how Intentservice opens the async thread and how to manage the command queue, as we mentioned earlier: when the background service finishes processing, We do not need to call the StopService method destruction Service, Intentservice will automatically destroy, how is it done? Then let's see Servicehandler:
privatefinalclass ServiceHandler extends Handler { publicServiceHandler(Looper looper) { super(looper); } @Override publicvoidhandleMessage(Message msg) { onHandleIntent((Intent)msg.obj); stopSelf(msg.arg1); } }
In handler we process each command and call the stopself (int) method to stop the service: The method requires a boot ID from the Onstartcommand method and stops the service only when the latest boot ID is received, that is, Our intentservice will not stop the service until all the commands in the command queue have been executed.
Setintentredelivery method
In the source code we can find that this method changes the value of the Boolean variable mredelivery, while the Mredelivery value is related to the Onstartcommand return variable:
@OverridepublicintonStartCommandintint startId) { onStart(intent, startId); return mRedelivery ? START_REDELIVER_INTENT : START_NOT_STICKY;}
As you can see, Mredelivery will return two different flags start_redeliver_intent and start_not_sticky, so what's the difference?
The difference is that if the system shuts it down before the service is complete, the two types will behave differently:
- The Start_not_sticky service will be shut down directly, while the Start_redeliver_intent service will attempt to start the service again when the available resources are no longer in a tight spot.
- From this we can find that when our operation is not very important, we can choose Start_not_sticky, which is also the default option of Intentservice, when we think the operation is very important, we should choose Start_redeliver_intent Type of service.
Non-sticky Services and Sticky services
The Non-sticky service stops when it considers that the task is complete, and if a service is non-sticky, it should return start_redeliver_intent or start_not_ in the Onstartcommand method Sticky logo.
The sticky service persists until the external component calls the Context.stopservice method. The STICKY service returns the flag bit start_sticky.
Note: Intentservice should not handle long-running services such as music playback, and long-running services should be done by the sticky service.
Android Development--intentservice usage that you missed out on what