checkSelfPermission 返回 PERMISSION_GRANTED 用于 targetSdkVersion <= 22 的撤销权限
checkSelfPermission returning PERMISSION_GRANTED for revoked permission with targetSdkVersion <= 22
我正在研究 Android Marshmallow 的新权限模型,但我遇到了一个我觉得很奇怪的问题。
具有 targetSdkVersion
22 的应用程序(因此尚未使用 Android Marshmallow 的新权限模型)在清单中声明 READ_CONTACTS
权限:
<uses-permission android:name="android.permission.READ_CONTACTS" />
并尝试通过 Intent.ACTION_PICK
:
读取联系人的 phone 号码
Intent intent = new Intent(Intent.ACTION_PICK);
intent.setType(ContactsContract.CommonDataKinds.Phone.CONTENT_TYPE);
startActivityForResult(intent, PICK_CONTACT_REQUEST);
当运行在装有Marshmallow MRA58K的设备上时,我通过ADB安装应用程序后撤销权限后,ContextCompat.checkSelfPermission()
方法仍然returnsPERMISSION_GRANTED
,但是稍后访问联系人时操作失败,因为返回了没有记录的游标。据我了解,这是避免遗留应用程序崩溃的默认 "retrocompatibility" 策略。
@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
if (requestCode == PICK_CONTACT_REQUEST && resultCode == Activity.RESULT_OK) {
Log.i("", "Permission granted: " + (ContextCompat.checkSelfPermission(this, Manifest.permission.READ_CONTACTS) == PackageManager.PERMISSION_GRANTED));
Uri contactUri = data.getData();
Cursor c = null;
try {
c = getContentResolver().query(contactUri, new String[]{ContactsContract.CommonDataKinds.Phone.NUMBER}, null, null, null);
if (c != null && c.moveToFirst()) {
Log.i("", "got phone number: " + c.getString(0));
} else {
Log.w("", "No data received");
}
} catch (Exception e) {
e.printStackTrace();
} finally {
if (c != null) {
c.close();
}
}
} else {
super.onActivityResult(requestCode, resultCode, data);
}
}
如何在尝试操作之前安全地检测用户是否在许可之前明确?
我还尝试了 https://github.com/googlesamples/android-RuntimePermissions 处的官方 Google 示例,将 targetSdkVersion
设置为 22,结果相同:即使用户撤销了权限,它也会记录权限已被授予,然后操作失败。
谢谢 ;)
为了使用新的权限模型(并检查您的应用程序是否具有权限),您需要将目标 SDK 更新为 23。保留目标 22 没有任何意义。
使用android.support.v4.content.PermissionChecker
https://developer.android.com/reference/android/support/v4/content/PermissionChecker.html
我正在研究 Android Marshmallow 的新权限模型,但我遇到了一个我觉得很奇怪的问题。
具有 targetSdkVersion
22 的应用程序(因此尚未使用 Android Marshmallow 的新权限模型)在清单中声明 READ_CONTACTS
权限:
<uses-permission android:name="android.permission.READ_CONTACTS" />
并尝试通过 Intent.ACTION_PICK
:
Intent intent = new Intent(Intent.ACTION_PICK);
intent.setType(ContactsContract.CommonDataKinds.Phone.CONTENT_TYPE);
startActivityForResult(intent, PICK_CONTACT_REQUEST);
当运行在装有Marshmallow MRA58K的设备上时,我通过ADB安装应用程序后撤销权限后,ContextCompat.checkSelfPermission()
方法仍然returnsPERMISSION_GRANTED
,但是稍后访问联系人时操作失败,因为返回了没有记录的游标。据我了解,这是避免遗留应用程序崩溃的默认 "retrocompatibility" 策略。
@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
if (requestCode == PICK_CONTACT_REQUEST && resultCode == Activity.RESULT_OK) {
Log.i("", "Permission granted: " + (ContextCompat.checkSelfPermission(this, Manifest.permission.READ_CONTACTS) == PackageManager.PERMISSION_GRANTED));
Uri contactUri = data.getData();
Cursor c = null;
try {
c = getContentResolver().query(contactUri, new String[]{ContactsContract.CommonDataKinds.Phone.NUMBER}, null, null, null);
if (c != null && c.moveToFirst()) {
Log.i("", "got phone number: " + c.getString(0));
} else {
Log.w("", "No data received");
}
} catch (Exception e) {
e.printStackTrace();
} finally {
if (c != null) {
c.close();
}
}
} else {
super.onActivityResult(requestCode, resultCode, data);
}
}
如何在尝试操作之前安全地检测用户是否在许可之前明确?
我还尝试了 https://github.com/googlesamples/android-RuntimePermissions 处的官方 Google 示例,将 targetSdkVersion
设置为 22,结果相同:即使用户撤销了权限,它也会记录权限已被授予,然后操作失败。
谢谢 ;)
为了使用新的权限模型(并检查您的应用程序是否具有权限),您需要将目标 SDK 更新为 23。保留目标 22 没有任何意义。
使用android.support.v4.content.PermissionChecker
https://developer.android.com/reference/android/support/v4/content/PermissionChecker.html