1 /* 2 * Copyright (C) 2015 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package com.android.packageinstaller.permission.model; 18 19 import android.content.Context; 20 import android.content.pm.PackageInfo; 21 import android.content.pm.PackageManager; 22 import android.text.BidiFormatter; 23 24 import java.util.ArrayList; 25 import java.util.Collections; 26 import java.util.LinkedHashMap; 27 import java.util.List; 28 29 public final class AppPermissions { 30 private final ArrayList<AppPermissionGroup> mGroups = new ArrayList<>(); 31 32 private final LinkedHashMap<String, AppPermissionGroup> mNameToGroupMap = new LinkedHashMap<>(); 33 34 private final Context mContext; 35 36 private final String[] mFilterPermissions; 37 38 private final CharSequence mAppLabel; 39 40 private final Runnable mOnErrorCallback; 41 42 private final boolean mSortGroups; 43 44 private PackageInfo mPackageInfo; 45 AppPermissions(Context context, PackageInfo packageInfo, String[] filterPermissions, boolean sortGroups, Runnable onErrorCallback)46 public AppPermissions(Context context, PackageInfo packageInfo, String[] filterPermissions, 47 boolean sortGroups, Runnable onErrorCallback) { 48 mContext = context; 49 mPackageInfo = packageInfo; 50 mFilterPermissions = filterPermissions; 51 mAppLabel = BidiFormatter.getInstance().unicodeWrap( 52 packageInfo.applicationInfo.loadSafeLabel( 53 context.getPackageManager()).toString()); 54 mSortGroups = sortGroups; 55 mOnErrorCallback = onErrorCallback; 56 loadPermissionGroups(); 57 } 58 getPackageInfo()59 public PackageInfo getPackageInfo() { 60 return mPackageInfo; 61 } 62 refresh()63 public void refresh() { 64 loadPackageInfo(); 65 loadPermissionGroups(); 66 } 67 getAppLabel()68 public CharSequence getAppLabel() { 69 return mAppLabel; 70 } 71 getPermissionGroup(String name)72 public AppPermissionGroup getPermissionGroup(String name) { 73 return mNameToGroupMap.get(name); 74 } 75 getPermissionGroups()76 public List<AppPermissionGroup> getPermissionGroups() { 77 return mGroups; 78 } 79 isReviewRequired()80 public boolean isReviewRequired() { 81 if (!mContext.getPackageManager().isPermissionReviewModeEnabled()) { 82 return false; 83 } 84 final int groupCount = mGroups.size(); 85 for (int i = 0; i < groupCount; i++) { 86 AppPermissionGroup group = mGroups.get(i); 87 if (group.isReviewRequired()) { 88 return true; 89 } 90 } 91 return false; 92 } 93 loadPackageInfo()94 private void loadPackageInfo() { 95 try { 96 mPackageInfo = mContext.getPackageManager().getPackageInfo( 97 mPackageInfo.packageName, PackageManager.GET_PERMISSIONS); 98 } catch (PackageManager.NameNotFoundException e) { 99 if (mOnErrorCallback != null) { 100 mOnErrorCallback.run(); 101 } 102 } 103 } 104 loadPermissionGroups()105 private void loadPermissionGroups() { 106 mGroups.clear(); 107 108 if (mPackageInfo.requestedPermissions == null) { 109 return; 110 } 111 112 if (mFilterPermissions != null) { 113 for (String filterPermission : mFilterPermissions) { 114 for (String requestedPerm : mPackageInfo.requestedPermissions) { 115 if (!filterPermission.equals(requestedPerm)) { 116 continue; 117 } 118 addPermissionGroupIfNeeded(requestedPerm); 119 break; 120 } 121 } 122 } else { 123 for (String requestedPerm : mPackageInfo.requestedPermissions) { 124 addPermissionGroupIfNeeded(requestedPerm); 125 } 126 } 127 128 if (mSortGroups) { 129 Collections.sort(mGroups); 130 } 131 132 mNameToGroupMap.clear(); 133 for (AppPermissionGroup group : mGroups) { 134 mNameToGroupMap.put(group.getName(), group); 135 } 136 } 137 addPermissionGroupIfNeeded(String permission)138 private void addPermissionGroupIfNeeded(String permission) { 139 if (hasGroupForPermission(permission)) { 140 return; 141 } 142 143 AppPermissionGroup group = AppPermissionGroup.create(mContext, 144 mPackageInfo, permission); 145 if (group == null) { 146 return; 147 } 148 149 mGroups.add(group); 150 } 151 hasGroupForPermission(String permission)152 private boolean hasGroupForPermission(String permission) { 153 for (AppPermissionGroup group : mGroups) { 154 if (group.hasPermission(permission)) { 155 return true; 156 } 157 } 158 return false; 159 } 160 } 161