DevicePolicyManager.enableSystemApp()方法无法按预期工作

时间:2017-12-22 14:13:20

标签: android android-intent provisioning

在使用设置为设备所有者模式的应用配置设备后,我尝试使用enableSystemApp方法激活默认系统应用。

有两种方法可以做到这一点:

1) void enableSystemApp(ComponentName admin,String packageName) - 在这种情况下,您需要将包名称显式地作为String传递。它工作正常,应用程序启用。

例如,调用此

devicePolicyManager.enableSystemApp(deviceAdminComponent, "com.google.android.gm");

启用默认Gmail客户端,该客户端在配置后被禁用。

2) int enableSystemApp(ComponentName admin,Intent intent) - 在这种情况下,您需要传递一个隐含的意图,Android应该启用符合此意图的所有系统应用程序。此外,此方法返回与intent相匹配的int数量的应用程序。这就是问题 - 我无法使用此方法,它总是返回0并且不启用任何内容。

以下是我尝试使用的代码段:

Intent intent = new Intent();
intent.setAction(Intent.ACTION_MAIN);
intent.addCategory(Intent.CATEGORY_APP_EMAIL);
int i = devicePolicyManager.enableSystemApp(deviceAdminComponent, intent);

它不起作用,在这种情况下i == 0。我做错了什么?

感谢任何帮助!

1 个答案:

答案 0 :(得分:1)

在幕后,接受意图查询的方法获取响应该意图的活动列表,然后循环遍历包名称字符串中的列表以启用包。它与此类似:

Intent intent = new Intent();
intent.setAction(Intent.ACTION_MAIN);
intent.addCategory(Intent.CATEGORY_APP_EMAIL);
List<ResolveInfo> infoes = getPackageManager()
    .queryIntentActivities(intent, MATCH_DIRECT_BOOT_AWARE | MATCH_DIRECT_BOOT_UNAWARE);
for (ResolveInfo info in infoes) {
  devicePolicyManager.enableSystemApp(deviceAdminComponent, info.activityInfo.packageName);
}

由于您可以使用包名称字符串启用应用程序,因此错误很可能在于解析意图的方式 - 它始终返回0的事实支持。

这是违反直觉的,但我怀疑应用程序无法解析ACTION_MAIN意图,因为应用程序已被禁用。你尝试过一般性意图吗?我会尝试以下

Intent i;

// #1
// This goes full circle, but I expect it should work
i = getPackageManager().getLaunchIntentForPackage("com.google.an‌​droid.gm")

// #2
i = new Intent(Intent.ACTION_SEND).setPackageName("com.google.android.gm");

// #3
// Generic, but should resolve _all_ email apps - not just the default one. 
// The mailto schema filters out non-email apps
i = new Intent(Intent.ACTION_VIEW , Uri.parse("mailto:"));

选项#1和#2更具学术性。两者都需要包名称,此时您也可以使用enableSystemApp的字符串重载。选项#3是我对可能仍然有效的通用内容的最佳猜测,但由于应用程序被禁用,它仍然无法正常工作。

注意:我觉得有趣的是,enableSystemApp在查询可以解析意图的活动时只传递MATCH_DIRECT_BOOT_AWAREMATCH_DIRECT_BOOT_UNAWARE标志,因为MATCH_DISABLED_COMPONENTSMATCH_SYSTEM_ONLY标志似乎在这种情况下更加相关。