找出其他 API 建立的喚醒鎖定

多個程式庫和系統 API 都可以取得可歸因於您應用程式的喚醒鎖定,因此很難找出應用程式中可能導致問題的喚醒鎖定。如果誤用 API,應用程式可能會持有喚醒鎖定過久,即使您並未直接呼叫喚醒鎖定 API 也是如此。

如果其他 API 已取得喚醒鎖定,您應避免手動取得喚醒鎖定。

本文列出使用喚醒鎖定偵錯工具時可能會看到的一些常見喚醒鎖定名稱。您也可能會在 Vitals 報表中看到這些名稱。在某些情況下,喚醒鎖定可能是由程式庫或系統 API 建立。在其他情況下,工具會將應用程式中使用的 Wake Lock 名稱混淆處理,這是因為有其他原因。您可以利用偵錯工具找出行為異常的 Wake Lock,然後在本文件中搜尋該 Wake Lock 名稱,找出可能導致問題的 API,以及解決方法。

本文涵蓋可能建立喚醒鎖的情境。在上述兩種情況中,雖然喚醒鎖定可能由其他程式庫或 API 建立,但鎖定會歸因於呼叫該 API 的應用程式。

AlarmManager

AlarmManager 會取得 Wake Lock,並將其歸因於呼叫應用程式。鬧鐘響起時,AlarmManager 會取得 Wake Lock,並在鬧鐘廣播的 onReceive() 方法執行完畢時釋放鎖定。

Wake Lock 名稱

AlarmManager 會建立名為 *alarm* 的喚醒鎖定。(星號是喚醒鎖定名稱的一部分,不代表萬用字元)。

建議

建議您採取下列做法,將警報行為調整至最佳狀態:

  • 使用 AlarmManager 調整鬧鐘排程頻率。
  • 只在必要時使用 RTC_WAKEUP 鬧鐘 (會喚醒裝置)。
  • 盡量減少使用鬧鐘,並避免在 onReceive() 方法中執行長時間的工作。

音訊和媒體

媒體 API 可以在錄製或播放音訊時取得喚醒鎖定。 喚醒鎖定會歸因於呼叫應用程式。

Wake Lock 名稱

媒體 API 會取得各種名稱開頭為 Audio 的喚醒鎖定:

  • AudioBitPerfect:用於無損 USB 音訊播放。
  • AudioDirectOut:用於在電視或特殊裝置上播放無損音訊。
  • AudioDup:透過藍牙或 USB 連線時,用於播放通知。
  • AudioIn:在攝影機模式下,麥克風處於啟用狀態時,用於擷取音訊。
  • AudioMix:用於在一般裝置上播放音訊。
  • AudioOffload:用於長期播放純音樂,適用於支援此模式的應用程式。
  • AudioSpatial:用於在支援環場音效的裝置上播放多聲道電影或音樂音訊。
  • AudioUnknown:適用於其他情況。
  • MmapCapture:用於低延遲音訊擷取。
  • MmapPlayback:用於低延遲播放,例如遊戲或專業音訊應用程式。

建議

建議您採取下列做法:

  • 請勿使用以 Audio 開頭的 Wake Lock 名稱。
  • 如果您使用媒體 API,應該不需要直接取得喚醒鎖定,可以依賴 API 為您取得必要的喚醒鎖定。
  • 使用媒體 API 時,不再需要媒體工作階段時,請結束工作階段。

藍牙

藍牙動作發生時,平台藍牙 API 不會保留任何可歸因於應用程式的喚醒鎖定。如要協助驗證藍牙傳輸是否在背景進行,請使用 WorkManager 排定工作。

建議

  • 使用「隨附裝置配對」配對藍牙裝置,避免在藍牙配對期間取得手動喚醒鎖定。
  • 請參閱在背景中通訊指南,瞭解如何進行背景藍牙通訊。
  • 如果認為必須手動保留喚醒鎖定,請只在藍牙動作期間保留喚醒鎖定。

裝置感應器

您可以透過多種方法追蹤裝置感應器資料,例如步數、加速計或陀螺儀資料。

在 Wear OS 上,使用 Wear 健康照護服務擷取裝置資料,例如海拔高度、心率和移動距離。

如果資料是由其他應用程式收集,您可以搭配使用 「健康資料同步」和 WorkManager 擷取資料。

如要追蹤步數或移動距離的變化量等情境,可以搭配 WorkManager 使用行動裝置上的 Recording API 來擷取資料。

在某些情況下,您可能需要使用 SensorManager 追蹤自訂裝置感應器。除非感應器是喚醒感應器 (可使用 isWakeUpSensor API 識別),否則 SensorManager 不會代表應用程式取得喚醒鎖定。

建議

使用感應器以高取樣率記錄資料可能會大幅耗用電量,以下是減少耗電和喚醒鎖定用量的建議:

  • 如要追蹤步數或移動距離,請使用 Recording API 以省電的方式記錄資料。
  • 如要在 Wear OS 上被動追蹤感應器,請使用 Wear 健康照護服務,盡量節省電量。
  • 將感應器頻率調降至 200 Hz 以下。
  • SensorManager 註冊感應器時,請定義超過 30 秒的 maxReportLatencyUs,以便使用感應器批次處理邏輯,並減少應用程式收到的中斷次數。
  • 請避免在感應器追蹤的整個期間持有長時間的喚醒鎖定,而是使用 AlarmManager 排定鬧鐘,每 30 秒以上輪詢感應器資料。

Firebase 雲端通訊 (FCM)

將 Firebase 雲端訊息 (FCM) 廣播傳送至應用程式時,系統會取得喚醒鎖定。FCM 廣播的 onMessageReceived() 方法執行完畢後,系統就會釋出喚醒鎖定。

Wake Lock 名稱

取得名為 GOOGLE_C2DM 的 Wake Lock。

建議

建議您採取下列做法,將 FCM 行為調整至最佳狀態:

  • 調整 FCM 傳送頻率。
  • 除非訊息確實需要立即傳送,否則請勿使用高優先順序 FCM
  • 請盡快完成 onMessageReceived() 方法。 詳情請參閱 Firebase 指南

JobScheduler

JobScheduler 工作會在背景執行工作時取得 Wake Lock。喚醒鎖定會歸因於建立工作者的應用程式。

Wake Lock 名稱

JobScheduler 取得的喚醒鎖定名稱取決於執行的 Android 系統版本和工作用途。

角括號括住的項目是變數。舉例來說,「<package_name>」是應用程式套件的名稱,而非實際文字 <package name>。不過,*job* 是字元序列 *job*,其中包含星號,星號並非做為萬用字元使用。

Android 15 以下版本

使用者啟動的作業會建立喚醒鎖定,名稱遵循下列模式:

*job*u/@<name_space>@/<package_name>/<classname>

其他工作使用這個模式:

*job*/@<name_space>@/<package_name>/<classname>
Android 16 以上版本

使用者啟動的作業會建立喚醒鎖定,名稱模式如下:

*job*u/@<name_space>@/#<trace_tag>#/<package_name>/<classname>

急件作業會使用以下模式:

*job*e/@<name_space>@/#<trace_tag>#/<package_name>/<classname>

一般工作會使用這個模式:

*job*r/@<name_space>@/#<trace_tag>#/<package_name>/<classname>
範例

假設有名為 backup 的命名空間,以及名為 started 的追蹤標記,且有項工作需要加快處理速度。套件名稱為 com.example.app,而建立工作的類別為 com.backup.BackupFileService

在搭載 Android 15 以下版本的裝置上,喚醒鎖定會命名為:

*job*/@backup@/com.example.app/com.backup.BackupFileService

在搭載 Android 16 以上版本的裝置上,喚醒鎖定會命名為:

*job*e/@backup@/#started#/com.example.app/com.backup.BackupFileService

建議

稽核 JobScheduler 工作的使用情形。請特別注意,請按照我們的指南,盡量減少工作排程 API 的電池用量

位置

LocationManagerFusedLocationProviderClient 會使用喚醒鎖定功能取得及傳送裝置位置資訊。喚醒鎖定會歸因於呼叫這些 API 的應用程式。

Wake Lock 名稱

定位服務使用下列名稱:

  • CollectionLib-SigCollector
  • NetworkLocationLocator
  • NetworkLocationScanner
  • NlpCollectorWakeLock
  • NlpWakeLock
  • *location*

建議

  • 最佳化位置資訊的使用方式。例如設定逾時、批次處理位置資訊要求,或使用被動位置資訊更新。
  • 如果您使用位置資訊 API,應該不需要直接取得喚醒鎖定,可以依賴 API 為您取得必要的喚醒鎖定。

WorkManager

WorkManager worker 會在背景執行工作時取得 Wake Lock。喚醒鎖定會歸因於建立工作者的應用程式。

Wake Lock 名稱

WorkManager 取得的喚醒鎖定名稱取決於執行的 Android 系統版本。

Android 15 以下版本

WorkManager 工作會建立喚醒鎖定,名稱遵循下列模式:

*job*/<package_name>/androidx.work.impl.background.systemjob.SystemJobService
Android 16 以上版本

急件工作會建立名稱符合下列模式的喚醒鎖定:

*job*e/#<trace_tag>#/<package_name>/androidx.work.impl.background.systemjob.SystemJobService

一般工作會遵循下列模式:

*job*r/#<trace_tag>#/<package_name>/androidx.work.impl.background.systemjob.SystemJobService

預設情況下,<trace_tag> 是工作站名稱。

範例

假設有名為 BackupFileWorker 的快速工作者,套件名稱為 com.example.app

在搭載 Android 15 以下版本的裝置上,喚醒鎖定會命名為:

*job*/com.example.app/androidx.work.impl.background.systemjob.SystemJobService

在搭載 Android 16 以上版本且使用 WorkManager 2.10.0+ 的裝置上,喚醒鎖定會命名為:

*job*e/#BackupFileWorker#/com.example.app/androidx.work.impl.background.systemjob.SystemJobService

建議

  • 升級 WorkManager 版本,讓 Android 16 以上版本的喚醒鎖定標記更詳細。
  • 稽核 WorkManager worker 的使用情況。請特別注意,請按照我們的指南最佳化工作排程 API 的電池用量

_UNKNOWN

如果偵錯工具認為 Wake Lock 名稱含有個人識別資訊 (PII),就不會顯示實際的 Wake Lock 名稱。而是將 Wake Lock 標示為 _UNKNOWN。舉例來說,如果喚醒鎖定名稱包含電子郵件地址,工具可能會這麼做。

建議

遵循 Wake Lock 命名最佳做法,並避免在 Wake Lock 名稱中使用個人識別資訊。如果發現應用程式有 _UNKNOWN 名稱的喚醒鎖定,請嘗試找出該喚醒鎖定,並改用其他名稱。