2

Android 文档提到了操作系统对以下每个存储桶的应用程序施加的限制:“活动”、“工作集”、“频繁”和“稀有” 。

我为“从不”存储桶(从未启动的应用程序启动的存储桶)找到的唯一文档提到:

此外,对于已安装但从未运行过的应用程序,还有一个特殊的 never 存储桶。系统对这些应用程序施加了严格的限制。

有谁知道操作系统对“从不”存储桶中的应用程序施加了哪些限制?(桶 50)

4

1 回答 1

2

首先关于我的回答的一点免责声明:我的回答基于 AOSP 代码,可能会因版本或制造商而异。

此外,我们或许可以推断制造商对其行为方式有发言权:

每个制造商都可以为如何将非活动应用程序分配到存储桶设置自己的标准。您不应该尝试影响您的应用程序分配到哪个存储桶。相反,应专注于确保您的应用在它可能位于的任何存储桶中表现良好。您的应用可以通过调用新方法 UsageStatsManager.getAppStandbyBucket() 找出它当前所在的存储桶。

作业将无法运行(带或不带充电器)

如果您查看 QuotaController,这是实现作业的存储桶限制的地方:frameworks/base/apex/jobscheduler/service/java/com/android/server/job/controllers/QuotaController.java

您会看到 NEVER_INDEX 只是关闭了作业可用性,并且不会隐式地继续/升级到更好的存储桶,除非某些东西会显式更改存储桶(例如,启动活动)。这也适用于连接充电器时,您可以在 isWithinQuotaLocked() 中看到:

if (standbyBucket == NEVER_INDEX) return false;

    // Quota constraint is not enforced while charging.
    if (mChargeTracker.isCharging()) {
        // Restricted jobs require additional constraints when charging, so don't immediately
        // mark quota as free when charging.
        if (standbyBucket != RESTRICTED_INDEX) {
            return true;
        }

警报不会运行(带或不带充电器)

查看AlarmManagerService:frameworks/base/services/core/java/com/android/server/AlarmManagerService.java

在那里,您可以看到当充电器连接/断开时调用 reorderAlarmsBasedOnStandbyBuckets()。

它根据配额对警报重新排序,对于存储桶,它永远不会为 0。

private final int[] DEFAULT_APP_STANDBY_QUOTAS = {
                720,    // Active
                10,     // Working
                2,      // Frequent
                1,      // Rare
                0       // Never
        };

代码将其延迟一天,直到它超过 0:

      if (quotaForBucket <= 0) {
         // Just keep deferring for a day till the quota changes
          minElapsed = mInjector.getElapsedRealtime() + MILLIS_IN_DAY;
      }

网络无法在后台运行

因为没有可用的作业和警报,所以没有可以使用网络的端点。

只有当前台服务/活动将备用存储桶更改为活动时,它才会开始工作,如文档中所述:

如果用户当前正在使用该应用程序或最近使用该应用程序,则该应用程序位于活动存储桶中。例如: • 应用程序启动了一个活动 • 应用程序正在运行前台服务 • 应用程序具有与前台应用程序使用的内容提供程序关联的同步适配器 • 用户单击来自应用程序的通知

于 2021-02-02T10:17:23.243 回答