Android 6.0 在运转时要权限

1. Android 6.0 在运作时恳求权限介绍

起 Android 6.0(API 级别
23)开始,用户开始当使用运行时为该与权限,而休是于采用设置时赋予。此措施好简化使用设置过程,因为用户在安或更新应用时无欲给权限。它还深受用户可对利用的法力拓展双重多控制;例如,用户可以择呢相机应用提供相机访问权限,而非提供设备位置的看权限。用户可以天天进入下之装页面修改权限。

1.1、为什么用周转时伸手权限

iPhone上之App都是默认下载安装的,然后运行App时需要什么权限就弹窗向用户申请,这对用户来说即使怪好。因为用户不思量让App权限就无深受,而Android
6.0以前是这样的,我下载了一个App安装,系统就弹出这个App需要运用的百分之百底权位,就深受自家看一下,我索要者App
的语句,只能容所有的权柄都为这个App,要么我非设置之App。

1.2、 Android权限介绍

系权限分为两类:例行权限高危权限

健康权限不见面直接为用户隐私权带来风险。如果你的施用在该manifest中列有了健康权限,系统将机关与该权限。

高危权限会授予应用访问用户机密数据的权杖。如果你的使用在那manifest中列有了正规权限,系统以活动与该权限。如果你列有了惊险权限,则用户要旗帜鲜明准予你的使使用这些权限,也就是说manifest文件中定义的生死存亡权限将非会见趁机安装自动与。

表 1.高危权限和权限组。

权限组权限

CALENDAR
: 
READ_CALENDAR

WRITE_CALENDAR

CAMERA 
: 
CAMERA

CONTACTS 
: 
READ_CONTACTS 
 
WRITE_CONTACTS 
, 
GET_ACCOUNTS

LOCATION
: 
ACCESS_FINE_LOCATION 
, 
ACCESS_COARSE_LOCATION

MICROPHONE
: 
RECORD_AUDIO

PHONE 
 
READ_PHONE_STATE,CALL_PHONE,READ_CALL_LOG,
WRITE_CALL_LOG,ADD_VOICEMAIL,USE_SIP,PROCESS_OUTGOING_CALLS

SENSORS 
: 
BODY_SENSORS

SMS 
: 
SEND_SMS,RECEIVE_SMS,READ_SMS,RECEIVE_WAP_PUSH,RECEIVE_MMS

STORAGE 
: 
READ_EXTERNAL_STORAGE,WRITE_EXTERNAL_STORAGE

于达图备受我们好观看,Android系统将危险权限分了9大组,这样也是为简化权限的申请机制。如果您报名了android.permission.READ_CONTACTS读取联系人之权位,那6.0
系统便会拿当下同组吃其他的权柄也卷入给你
。我道这个与iOS的隐私管理机制非常相像,在iOS系统设置的“隐私->通讯录”中可看,如果你叫一个App通讯录的权,那么这App既好读也可形容的

Android 6.0里面只有危险权限才用周转时获得之

1.3、android系统针对权力的处理场景分析

倘若设备运行的是 Android 6.0(API 级别
23)或另行胜似版本,并且采用的targetSdkVersion
23
或还胜版本,则以在运作时于用户要权限。用户可随时调用权限,因此利用在历次运行时均用检查自身是否拥有所欲的权位。

倘设备运转的凡 Android 5.1(API 级别
22)或重新不比版本,并且采取之targetSdkVersion
22
或重没有版本,则网会当用户设置使用时讲求用户给权限。如果以新权力添加到创新的施用版本,系统会以用户更新应用时要求予以该权限。用户若设置使用,他们撤销权限的绝无仅有方法是卸载应用。

万一设备运转的凡 Android 6.0(API 级别
23)或重复胜版本,并且动的targetSdkVersion举凡
22
或又低版本,此时Android系统会把您报名之普权都于你用户依然得以上App的装置界面把权限关闭!

如以下图片被用户以android6.0的本子的设置中管权关闭,此时若的权就因此不了了。那么程序用考虑针对6.0暨以上版本的匹配,具体参考下面的(android.support.v4.content.PermissionChecker)。

值得注意的是Android系统发生同样模仿机动权限调整的机制,我们清楚android每次sdk升级来或会见加入新的权,而你的app已经颁布到用户手机上安装了,除了升级不可能修改Androidmanifest文件了,此时而可能担心自己之app能够以这些新的sdk版本的手机上运行如常啊,其实android已经考虑了这种光景,Android
将依据呢targetSdkVersion性提供的价值决定采用是否要权限。如果该值低于在中添加权限的本,则
Android 会为App自动添加该权限。

比如,API 级别 4
中入了WRITE_EXTERNAL_STORAGE权限,用以限制访问共享存储空间。如果您的targetSdkVersion
3 或再小版本,则会于创新 Android 版本设备及之应用添加这个权限。

2、如何申请权限

提请权限过程包括以下几独步骤:

反省权

恳请权限

拍卖权限请求响应

解说下为什么用权限

2.1、检查权

假使你的使用得危险权限,则每次执行要马上等同权的操作时您还必检查自己是否具有该权限。用户一直可以随便调用此权限,因此,即使用昨天运了相机,它不克如自己今天以持有该权限,因为用户或当装置中关闭了。

一旦反省你是否享有某起权力,请调用ContextCompat.checkSelfPermission()主意。例如,以下代码段显示了安检查
Activity 是否有所在日历中进行摹写副的权柄:

// 假设thisActivity是时下屏幕最前端正在与用户交互的activity

int permissionCheck = ContextCompat.checkSelfPermission(thisActivity,

        Manifest.permission.WRITE_CALENDAR);

假使用拥有此权限,方法以回来PackageManager.PERMISSION_GRANTED,并且使可继承操作。如果使用不拥有此权限,方法以返回PERMISSION_DENIED,且下得明确向用户要求权限。

也得以用ActivityCompat,它们简单单底checkSelfPermission方法是与一个,因为ActivityCompat继承自ContextCompat,而checkSelfPermission是ContextCompat中之方式。

反省权会起有特别的问题要专注,主要发生以下简单单:

如果App的targetSdkVersion小于23又运行在Android
6.0系统及,怎么去检测用户关闭了权力呢?

国内小手机厂商自己一定制了手机权限管理(例如:小米),普通的checkSelfPermission已经不精确了,该怎么处理?

问题一:

android.support.v4.content.PermissionChecker好协助咱解决这个题材。这个看似的文档是这样描述的:

For apps targeting API lower
thanandroid.os.Build.VERSION_CODES.Mthese permissions are always
granted as such apps do not expect permission revocations and would
crash. Therefore, when the user disables a permission for a legacy app
in the UI the platform disables the APIs guarded by this permission
making them a no-op which is doing nothing or returning an empty result
or default error.

翻一下是:

当app的targetsdkversion小于23底时候,这些权限默认都见面活动为当下app,但如app没有考虑于6.0装备遭遇让用户积极撤回该权限的面貌,那么可能导致app的崩溃。于是app在使该权限过程遭到网权限检查时一旦这个权力被用户撤销了,那么相应请求的API会什么还未开要返回一个缺损的结果,或者出错。

PermissionChecker.checkSelfPermission道就是用以检查App自身发生没发某个一个权,这个艺术的返结果就发生三种植:

PERMISSION_GRANTED: 已授权

PERMISSION_DENIED: 没有吃授权

PERMISSION_DENIED_APP_OP: 没有于授权

PERMISSION_DENIEDPERMISSION_DENIED_APP_OP犹代表从未受授权,但是它们的分别就是在于targetSdkVersion的值,如果targetSdkVersion小于23,就返回PERMISSION_DENIED_APP_OP,否则即回来PERMISSION_DENIED

故而,如果您的App的targetSdkVersion仅次于23,但是运行在Android
6.0及后的网及,你可以用底的代码来检测app是否发某个权限:

PermissionChecker.checkSelfPermission(context, permission) ==
PermissionChecker. PERMISSION_DENIED_APP_OP

问题二:

国很多无线电话在google之前都召开了温馨的权力管理,例如小米,所以此时下ContextCompat的checkSelfPermission方法就是回到PackageManager.PERMISSION_GRANTED也恐怕不纯粹。如果起这种情景我们需要做同次特别处理,此时我们用采取android的隐藏API
AppOpsManager

AppOpsManager法定的讲是网里使用,不提供给APP开发者使用。一个小米设备相当判断的代码如下:

@TargetApi(Build.VERSION_CODES.M)private static boolean
hasSelfPermissionForXiaomi(Context context, String permission) {   
AppOpsManager appOpsManager = (AppOpsManager)
context.getSystemService(Context.APP_OPS_SERVICE);    String op =
AppOpsManager.permissionToOp(permission);    if (!TextUtils.isEmpty(op))
{        int checkOp = appOpsManager.checkOp(op, Process.myUid(),
context.getPackageName());        return checkOp ==
AppOpsManager.MODE_ALLOWED &&
ActivityCompat.checkSelfPermission(context, permission) ==
PackageManager.PERMISSION_GRANTED;    }    return true;}

2.2、请求权限

倘您的用得动用manifest文件中列有的高危权限,那么,它要要求用户与该权限。Android
为你提供了强权请求方式。调用这些方法将显示一个正式的 Android
对话框,不过,您不可知针对其进行自定义。

若果点的权力检查手续中结果是使用还无所需的权,则以得调用一个requestPermissions()方,以告适用的权杖。应用将传递其所待的权力,以及若指定用于识别是权限请求的整型央代码。此道异步运行:它见面立马回到,并且以用户应对话框之后,系统会利用结果调用应用的回调方法,将运用传递的如出一辙请求代码传递至requestPermissions()

提醒用户给或拒绝权限的网对话框如下:

以下代码可以检查下是否持有读取用户联系人之权杖,并基于需要请该权限:

// 这里的 thisActivity 是现阶段屏幕最前端正在和用户交互的activity

if (ContextCompat.checkSelfPermission(thisActivity,

                Manifest.permission.READ_CONTACTS)

        != PackageManager.PERMISSION_GRANTED) {

    // 是否需要吃用户一个诠释?

    if
(ActivityCompat.shouldShowRequestPermissionRationale(thisActivity,

            Manifest.permission.READ_CONTACTS)) {

        //
显示为用户要以此权力的说辞,这个需要是异步的(不克围堵时线程去等用户的应!)
,在用户看罢这个解释后,继续尝试要这些权限

    } else {

        // 不待讲, 我们得起请权限

        ActivityCompat.requestPermissions(thisActivity,

                new String[]{Manifest.permission.READ_CONTACTS},

                MY_PERMISSIONS_REQUEST_READ_CONTACTS);

        // MY_PERMISSIONS_REQUEST_READ_CONTACTS
这个是app定义之整形常量,用于标识一个央,回调方法被会获得此要对应之结果

    }

}

:当你的行使调用requestPermissions()时常,系统以向用户展示一个正经对话框。您的使无法配备或者变更此对话框。如果你得也用户提供其他音讯或者说明,您应于调用requestPermissions()事先进行,如说下为什么用权限。

2.3、处理权限请求响应

当用请求权限时,系统以为用户展示一个对话框。当用户应时,系统以调用应用之onRequestPermissionsResult()艺术,向那传递用户应。您的应用得覆写该措施,以询问是否已经落对应权限。回调会拿你传递的一律请求代码传递给requestPermissions()。例如,如果采用请求READ_CONTACTS走访权限,则它恐怕用以下回调方法:

@Override

public void onRequestPermissionsResult(int requestCode,

        String permissions[], int[] grantResults) {

    switch (requestCode) {

        case MY_PERMISSIONS_REQUEST_READ_CONTACTS: {

            // 如果授权取消 这个结果数组是空

            if (grantResults.length > 0

                && grantResults[0] ==
PackageManager.PERMISSION_GRANTED) {

                // 权限已经授权, 很棒!可以继承联系人相关的操作了

            } else {

                // 权限被拒绝了,很糟糕! 禁用和拖欠权限相关的效力

            }

            return;

        }

        // 其它的’case’ 代码去处理任何的权位请求回调

    }

}

注意:

当系统要求用户给权限时,用户可选取指示系统不再要求提供该权限(即勾选对话框里的未以提示)。这种景象下,无论使用在啊时用requestPermissions()重要求该权限,系统都见面立刻拒绝这个要。系统会调用您的onRequestPermissionsResult()回调方法,并传递PERMISSION_DENIED

2.4 解释以为什么要权限

在好几情况下,您可能得帮助用户了解你的以为什么用有项权力。例如,如果用户启动一个照应用,用户对用要求下相机的权杖可能无见面感到震惊,但用户可能无法了解为什么这个以想要拜访用户的职要联系人。在求权限之前,不妨也用户提供一个解释。请牢记,您不欲通过解释来说服用户;如果你提供最多讲,用户可能发现用使得人失望并将该移除。

卿可以采用的一个法是不过以用户就拒绝某起权力请求时供解释。如果用户继续品尝用得有项权力的法力,但连续拒绝权限请求,则恐表明用户不亮使为什么用这权限才能够提供相关力量。对于这种状态,比较好的做法是显得解释。

为拉寻找用户可能得说明的状况,Android
提供了一个实用程序方法,即shouldShowRequestPermissionRationale()。如果采取之前要了这权限但用户拒绝了央,此方以赶回true

:如果用户在过去拒了权请求,并于权力请求系统对话框中精选了Don’t
ask
again
选,此方将返回false。如果设备正式禁止采取具有该权限,此方法为会回到false

That’s all
感谢阅读,原文地址http://www.huahuaxie.com/android-6-0-runtime-permission/

相关文章