Android应用权限相关问题

1.给应用添加默认权限,不再弹出授权提示框

如有些应用打开后根本不需要弹出授权添加权限的提示框,而是已经拥有了Calendar、Contact等权限。

一般的做法是:在frameworks/base/services/core/java/com/android/server/pm/DefaultPermissionGrantPolicy.java文件grantDefaultSystemHandlerPermissions方法中添加:

String appPkgStr = "xxx.com.xxx"; //包名
PackageParser.Package appPkg = getPackageLPr(appPkgStr);
if(appPkg != null){
    grantRuntimePermissionsLPw(appPkg, PHONE_PERMISSIONS, userId);
    grantRuntimePermissionsLPw(appPkg, STORAGE_PERMISSIONS, userId);
    grantRuntimePermissionsLPw(appPkg, LOCATION_PERMISSIONS, userId);
    grantRuntimePermissionsLPw(appPkg, CONTACTS_PERMISSIONS, userId);
}

2.在应用中判断权限并申请权限

最近遇到一个比较奇怪的问题:Exchange一直提示没有READ_CALENDAR权限,导致Email登录Exchange账号后日历同步失败。但是看代码中已经做了以下权限的判断及申请:

public static void checkPermissionsForXXX(Activity activity, Intent fIntent) {
        ArrayList<String> requestList = new ArrayList<>();
        requestList.add(android.Manifest.permission.READ_CONTACTS);
        requestList.add(android.Manifest.permission.READ_PHONE_STATE);
        requestList.add(Manifest.permission.WRITE_CALENDAR);
        try {
            PackageInfo info = activity.getApplicationContext()
                    .getPackageManager()
                    .getPackageInfo("xxx.xxx.xxx", PackageManager.GET_PERMISSIONS); //通过包名获得PackageInfo信息
					
            boolean needsPermission = false;
			
            for (int i = 0; i < info.requestedPermissions.length; i++) {
                String requestedPermission = info.requestedPermissions[i];
                if (requestList.contains(requestedPermission)) {
                    int requestedPermissionsFlag = info.requestedPermissionsFlags[i];
                    boolean granted = (requestedPermissionsFlag & PackageInfo.REQUESTED_PERMISSION_GRANTED) != 0;
                    if (!granted) {
                        needsPermission = true;
                        break;
                    }
                }
            }
            if (needsPermission) {
                final Intent intent = new Intent("com.xxx.xxx.xxxxxx");//new 一个Intent,准备相应的Activity来进行权限申请
                intent.putStringArrayListExtra(PermissionUtil.EXTRA_PERMISSIONS_EXCHANGE, requestList);
                Intent fromIntent = activity.getIntent();
                if (fromIntent != null) {
                    intent.putExtra(PermissionUtil.EXTRA_INTENT_EXCHANGE, fromIntent);
                }
                try {
                    activity.startActivityForResult(intent, PERMISSION_EXCHANGE);
                } catch (ActivityNotFoundException e) {
                    LogUtils.e(LogUtils.TAG, "Activity not found for certificate request in incomming setting");
                }
            } else {
                launchXxxActivity(activity, fIntent);
            }
        } catch (PackageManager.NameNotFoundException e) {
            LogUtils.w(LogUtils.TAG, e, e.getMessage());
        }
    }

因为(1)权限这一块基本没有改动过,而以前释放的版本没有报出这个问题,最近的版本报出了这个问题后,所以一致认为应该不是应用本身问题。但是又重新安装了以前的版本,发现以前的版本也有同样的问题,这样就不能确定到底是哪里导致了问题。(2)因为一直以来说的关于危险权限的授权都是:

If any permission in a Permission Group is granted. Another permission in the same group will be automatically granted as well. In this case, once WRITE_CONTACTS is granted, application will also grant READ_CONTACTS and GET_ACCOUNTS.

所以默认的是已经申请了WRITE_CALENDAR,应该来说READ_CALENDAR应该也是有的,所以也就没有在这个权限判断及申请上多琢磨。

但是事实证明,确实是这里出现了问题:应用没有获得READ_CALENDAR权限。故,建议在应用中判断权限并申请权限时不管是否属于Permission Group,都还是判断及申请一遍啊~

修改后如下:

ArrayList<String> requestList = new ArrayList<>();
requestList.add(android.Manifest.permission.READ_CONTACTS); 
//Fix email Contacts&Calendar sync issue
requestList.add(Manifest.permission.WRITE_CONTACTS);
requestList.add(Manifest.permission.GET_ACCOUNTS);
requestList.add(Manifest.permission.READ_CALENDAR);
//add end
requestList.add(android.Manifest.permission.READ_PHONE_STATE);
requestList.add(Manifest.permission.WRITE_CALENDAR);

另附一段上面提到的Intent来打开的相应的Activity来进行申请权限的代码:

 protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.permission_block_activity);
        List<String> permissions = getIntent().getStringArrayListExtra(PermissionUtil.EXTRA_PERMISSIONS_EXCHANGE);
        if (permissions == null || permissions.isEmpty()){
            this.finish();
            return;
        }
        boolean isSkip = false;
        List<String> requestList = new ArrayList<>();
        for (String perm : permissions) {
            if (PermissionChecker.checkSelfPermission(this, perm) != PackageManager.PERMISSION_GRANTED) {
                requestList.add(perm);
                isSkip = isSkip || ActivityCompat.shouldShowRequestPermissionRationale(this, perm);
            }
        }

        if (!requestList.isEmpty()) {
            //not entrance activity
            if (savedInstanceState == null) {
                final String[] permissons = requestList.toArray(new String[requestList.size()]);
                ActivityCompat.requestPermissions(PermissionExchangeActivity.this, permissons, REQ_CODE_CHECK_PERMISSION);
            }
        } else {
            finish();
        }
    }

    @Override
    public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
        if(REQ_CODE_CHECK_PERMISSION == requestCode){
            finish();
        }
    }

猜你喜欢

转载自blog.csdn.net/hanhan1016/article/details/85094652