Android Service解析

Android Service是一個能夠在後臺執行長時間運行操做而不提供用戶界面的應用組件,它分爲兩種工做狀態,一種是啓動狀態,主要用於執行後臺計算;另外一種是綁定狀態,主要用於其餘組件和Service的交互。須要注意的兩點:android

  • 兩種狀態是共存的,即Service能夠是啓動狀態也能夠同時是綁定狀態
  • 防止ANR風險,主線程運行的Service在執行耗時操做,則應在服務內建立新線程來完成這項工做,這能夠下降發生「應用無響應」(ANR) 錯誤的風險。app

    使用

    要建立服務,您必須建立 Service 的子類。在實現中,須要重寫一些回調方法,以處理服務生命週期的某些關鍵方面並提供一種機制將組件綁定到服務。
public class MyService extends Service {
    @Override
    public IBinder onBind(Intent intent) {
        return null;
    }
}

Service須要重寫重要的回調方法有如下幾個ide

  • onStartCommand():經過調用 startService() 請求啓動服務時,系統將調用此方法,bindService無需實現該方法
  • onBind():經過調用 bindService() 與服務綁定(例如執行 RPC)時,系統將調用此方法,經過返回 IBinder 提供一個接口,供客戶端用來與服務進行通訊
  • onCreate():首次建立服務時,系統將調用此方法來執行一次性設置程序(在調用 onStartCommand() 或 onBind() 以前)
  • onDestroy():當服務再也不使用且將被銷燬時,系統將調用此方法。服務應該實現此方法來清理全部資源,如線程、註冊的偵聽器、接收器等。 這是服務接收的最後一個調用

像Activity(以及其餘組件)同樣,您必須在應用AndroidManifest.xml清單文件中聲明全部服務函數

<service android:name=".MyService"/>

經過Context啓動一個Service,這會致使對 onStartCommand() 的調用,則服務將一直運行,直到服務使用 stopSelf() 自行中止運行,或由其餘組件經過調用 stopService() 中止,以下所示ui

startService(new Intent(this, MyService.class));

但在Android8.0的應用嘗試在不容許其建立後臺服務的狀況下使用 startService() 函數,則該函數將引起一個 IllegalStateException。 新的 Context.startForegroundService() 函數將啓動一個前臺服務。this

if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
    startForegroundService(intent);
} else {
    startService(intent);
}

而且在在service裏再調用startForeground方法,否則就會出現ANR線程

context.startForeground(SERVICE_ID, builder.getNotification());

經過Context綁定一個Service,且未調用 onStartCommand(),則服務只會在該組件與其綁定時運行,一旦該服務與全部客戶端之間的綁定所有取消,系統便會銷燬它,以下所示代理

bindService(new Intent(this, MyService.class), connection, BIND_AUTO_CREATE);

注意:系統內存不足時,Android會強制中止優先級低的Service來提供內存給Activity使用,但持有Activity的Service可能不會終止,或者前臺運行的Service幾乎永遠不會終止。code

Service啓動

首先咱們先看下Service的類的調用流程

相關類說明xml

  • ContextWrapper:代理Context的實現,簡單地將其全部調用委託給另外一個Context
  • ContextImpl:Context API的通用實現,爲Activity和其餘應用程序組件提供基本上下文對象
  • ActivityManager:此類提供有關活動,服務和包含過程的信息和交互
  • IActivityManager.aidl:用於與ActivityManagerService交談的系統專用API,提供了從應用程序返回到活動管理器的調用
  • ActivityManagerService:負責系統中四大組件的啓動、切換、調度及應用進程的管理和調度等工做
  • ActivityThread:管理應用程序進程中主線程的執行,根據ActivityManager請求調度和執行Activitys、broadcasts和其餘操做
  • ApplicationThread:ActivityThread內部類,IApplicationThread.aidl的具體實現,提供給ActivityManager,ActivityManager經過它告知應用程序將要作的事
  • IApplicationThread:用於與應用程序通訊的系統專用API

Service最終建立須要須要經過Handler進行消息發送來實現建立,並把建立好的servic存儲在ArrayMap中。接下來看下Service的生命週期是怎樣的。

須要注意的是,在整個生命週期內,只有startCommand()能被屢次調用。其餘方法只能被調用一次。

Service綁定

Service綁定跟Service的啓動了類調用流程基本一致,只是相關方法改成bind,但其最後會調用ServiceConnection對象的onServiceConnected方法。接下來看下Service的生命週期是怎樣的 但其有一個特性,屢次綁定同一個Service時,Service的onBind方法只會執行一次,除非Service被終止了。

相關文章
相關標籤/搜索