应用待机桶

Android 9(API 级别 28)及更高版本支持应用待机桶。应用待机桶帮助系统根据应用程序的使用频率和最近使用时间对应用程序的资源请求进行优先级排序。根据应用程序的使用模式,每个应用程序都被放置在五个优先级之一中。系统根据应用程序所在的桶限制每个应用程序可用的设备资源。

优先级桶

系统动态地将每个应用程序分配到一个优先级桶,并在需要时重新分配应用程序。系统可能依赖于一个预加载的应用程序,该应用程序使用机器学习来确定每个应用程序被使用的可能性,并将应用程序分配到相应的桶中。

如果系统应用程序不在设备上,系统默认为根据应用程序的最近使用时间进行排序。更活跃的应用程序被分配到优先级更高的桶,使系统资源更多地可用。特别是,该桶决定应用程序作业运行的频率以及应用程序触发警报的频率。这些限制仅在设备处于电池供电状态时适用。在设备充电时,系统不会实施这些限制。

优先级桶如下所示

  • 活跃:应用程序正在使用或最近使用。
  • 工作集:应用程序经常使用。
  • 频繁:应用程序经常使用,但不是每天。
  • 罕见:应用程序不经常使用。
  • 限制:应用程序消耗大量系统资源,或者可能表现出不良行为。

除了这些优先级桶之外,还有一个特殊的从不桶,用于已安装但从未运行的应用程序。系统对这些应用程序施加了严格的限制。

以下描述适用于非预测性情况。相比之下,当预测使用机器学习来预测行为时,将根据用户的预期下一步操作来选择桶,而不是基于最近的使用情况。例如,最近使用的应用可能最终会进入“罕见”桶,因为机器学习预测该应用可能在几个小时内不会被使用。

活跃

当应用正在使用,最近使用过,或发生以下情况时,应用处于活跃桶中:

  • 启动活动。
  • 运行长时间运行的前台服务。
  • 用户从通知中点击应用。

如果应用处于活跃桶中,系统不会对应用的作业或闹钟施加任何限制。

用户交互将应用分配为活跃

在 Android 9(API 级别 28)及更高版本上,当用户以某些方式与您的应用交互时,系统会将您的应用临时置于活跃桶中。在用户停止与您的应用交互后,系统会根据使用历史将其置于某个桶中。

以下是一些触发此系统行为的交互示例:

  • 用户点击您的应用发送的通知。

  • 用户通过点击媒体按钮与您应用中的前台服务交互。

  • 用户在与Android Automotive OS交互时连接到您的应用,其中您的应用使用前台服务或CONNECTION_TYPE_PROJECTION

工作集

如果应用经常运行但不是活跃状态,则它位于工作集桶中。例如,用户几乎每天都会启动的社交媒体应用可能处于工作集中。如果应用被间接使用,它们也会被提升到工作集桶中。

如果应用位于工作集中,系统会对它运行作业和触发闹钟的能力施加轻微限制。有关详细信息,请参阅电源管理限制

频繁

如果应用定期使用但并非每天都使用,则它位于频繁桶中。例如,用户在健身房运行的健身追踪应用可能处于频繁桶中。

如果应用位于频繁桶中,系统会对它运行作业和触发闹钟的能力施加更严格的限制。有关详细信息,请参阅电源管理限制

罕见

如果应用不常使用,则它位于罕见桶中。例如,用户仅在入住酒店时才运行的酒店应用可能处于罕见桶中。

如果应用位于罕见桶中,系统会对它运行作业和触发闹钟的能力施加严格限制。系统还会限制应用连接到互联网的能力。有关详细信息,请参阅电源管理限制

受限

此桶是在 Android 12(API 级别 31)中添加的,具有所有桶中最低的优先级和最高的限制。系统会考虑您的应用的行为,例如用户与它交互的频率,来决定是否将您的应用置于受限桶中。

在 Android 13(API 级别 33)及更高版本上,除非您的应用符合豁免条件,否则系统会在以下情况下将您的应用置于受限桶中:

  • 用户在特定天数内没有与您的应用交互。在 Android 12(API 级别 31)和 12L(API 级别 32)上,天数为 45 天。Android 13 将天数减少到 8 天。

  • 您的应用在 24 小时内调用了过多的广播绑定

如果系统将您的应用置于受限桶中,则会应用以下限制:

  • 您可以在每天 10 分钟的批处理会话中运行作业一次。在此会话期间,系统会将您的应用的作业与其他应用的作业分组。
    • 受限作业不会自行运行。必须至少有另一个作业在同一时间运行或挂起,其中可以包括任何其他作业。
  • 与系统将您的应用置于限制较少的桶中相比,您的应用可以运行更少的快速作业
  • 您的应用每天可以调用一个闹钟。此闹钟可以是精确闹钟非精确闹钟

受限桶的豁免

以下类型的应用无需进入受限桶,并绕过非活动触发器,即使在 Android 12 及更高版本上也是如此:

评估优先级桶

要检查您的应用分配到的桶,请执行以下操作之一:

  • 调用getAppStandbyBucket()

  • 在终端窗口中运行以下命令:

    adb shell am get-standby-bucket PACKAGE_NAME

只要应用的 App Standby 桶的值大于STANDBY_BUCKET_ACTIVE(10),系统就会限制您的应用。

最佳实践

如果您的应用遵循 Doze 和应用待机功能的最佳实践,则较新的电源管理功能并不难。但是,以前运行良好的某些应用行为可能会导致问题。

  • 不要试图操纵系统将您的应用置于特定桶中。系统放置优先级的机制可能会发生变化,并且每个设备制造商都可能选择编写自己的桶应用,并使用其自己的算法。相反,请确保您的应用无论处于哪个桶中都能正常运行。
  • 如果应用没有启动器活动,则它可能永远不会被提升到活跃桶中。考虑重新设计您的应用以包含这样的活动。
  • 如果用户无法与应用通知进行交互,则用户将无法触发应用被提升到活跃桶中。在这种情况下,请考虑重新设计一些允许用户进行交互的通知。有关一些指南,请参阅 Material Design 的通知设计模式

  • 如果应用在收到高优先级 Firebase Cloud Messaging (FCM) 消息时没有显示通知,则用户无法与应用进行交互,从而无法将其提升到活跃桶中。实际上,高优先级 FCM 消息的唯一预期用途是向用户推送通知,因此这种情况必须避免发生。在 12L(API 级别 32)及更低版本上,如果您不适当地将 FCM 消息标记为高优先级,而它没有触发用户交互,则可能会导致未来的消息被降级。

  • 如果应用跨多个包拆分,则这些包可能处于不同的桶中,并具有不同的访问级别。测试这些应用,并将包分配到不同的桶中,以确保应用能够正常运行。