3. 权限分类与映射表

Android 运行时权限体系将权限划分为三类:正常权限(Normal Permissions)、危险权限(Dangerous Permissions) 和 特殊权限(Special Permissions)。准确理解三者的定义、清单及 API 级别对应关系,是设计 Runtime 权限申请流程的前提条件。

3.1 适用场景

  • 新功能开发阶段,需要确定目标权限类型并选取正确的申请策略。
  • 遗留项目权限适配(如 targetSdkVersion 升级至 23+)时,对比现有权限与最新分类。
  • 代码审查或合规审计时,验证权限声明与用户隐私保护要求是否一致。

3.2 前置条件

  • 已配置 Android SDK 环境,了解 AndroidManifest.xml 中 <uses-permission> 标签的基本用法。
  • 明确项目当前 compileSdk、minSdk 和 targetSdk 版本。
  • 获得 Android 官方权限参考文档(或本课程提供的汇总表)。

3.3 操作步骤

步骤 1:识别权限类型定义

类型 定义 系统行为 API 版本
正常权限 不直接涉及用户隐私,不会造成严重安全风险的系统功能调用,如网络状态、蓝牙连接。 安装时自动授权,无需运行时弹窗。 API 1+
危险权限 涉及用户隐私数据(通讯录、位置、相机等),必须通过运行时弹窗显式获取用户同意。 需要调用 requestPermissions() 并处理回调。 API 23+ 引入运行时机制,但权限本身从早期版本即存在
特殊权限 系统级开关控制的功能(如“在其他应用上层显示”“无障碍服务”),需要额外跳转系统设置页面授予。 使用 Settings.ACTION_MANAGE_OVERLAY_PERMISSION 等 Intent 引导用户手动打开。 API 23+ 逐步引入

步骤 2:对照危险权限分组清单(核心映射表)

下表列出截至 Android 14 的主要危险权限组及对应权限标识。同一组中只要授权一项,组内其他权限即自动允许。

权限组 权限名 引入 API 备注
CALENDARREAD_CALENDARAPI 1日历读写
WRITE_CALENDARAPI 1
(组内无新增)–
CAMERACAMERAAPI 1相机使用
(组内仅此项)–
CONTACTSREAD_CONTACTSAPI 1通讯录读写
WRITE_CONTACTSAPI 1
GET_ACCOUNTSAPI 5
LOCATIONACCESS_FINE_LOCATIONAPI 1GPS / 网络位置
ACCESS_COARSE_LOCATIONAPI 1
(Android 10+ 拆分)ACCESS_BACKGROUND_LOCATIONAPI 29后台位置特殊处理
PHONEREAD_PHONE_STATEAPI 1电话/IMEI等
CALL_PHONEAPI 1
READ_CALL_LOG / WRITE_CALL_LOG / ADD_VOICEMAIL / USE_SIPAPI 16+子项较多
STORAGEREAD_EXTERNAL_STORAGE / WRITE_EXTERNAL_STORAGEAPI 1 (但运行时自 API 23)Android 10+ 被细化,建议改用 MediaStore / SAF
SMSSEND_SMS / RECEIVE_SMS / READ_SMS / RECEIVE_WAP_PUSH / RECEIVE_MMSAPI 1短信相关
(组内五项)–
BODY_SENSORSBODY_SENSORSAPI 20心率等传感器
BODY_SENSORS_BACKGROUNDAPI 33后台身体传感器

步骤 3:特殊权限清单及操作方式

特殊权限 权限名 (常量) 引导 Action 检查方法 引入 API
浮动窗口 SYSTEM_ALERT_WINDOW Settings.ACTION_MANAGE_OVERLAY_PERMISSION Settings.canDrawOverlays(context) API 23
修改系统设置 WRITE_SETTINGS Settings.ACTION_MANAGE_WRITE_SETTINGS Settings.System.canWrite(context) API 23
无障碍服务 BIND_ACCESSIBILITY_SERVICE Settings.ACTION_ACCESSIBILITY_SETTINGS 检查已启用的服务列表 API 18+
通知监听 BIND_NOTIFICATION_LISTENER_SERVICE Settings.ACTION_NOTIFICATION_LISTENER_SETTINGS 检查已激活监听器 API 18+
安装未知来源应用 REQUEST_INSTALL_PACKAGES Settings.ACTION_MANAGE_UNKNOWN_APP_SOURCES PackageManager.canRequestPackageInstalls() API 26
后台位置(部分视为特殊) ACCESS_BACKGROUND_LOCATION 与前台位置一同申请,或通过位置设置页面 checkSelfPermission 后单独处理 API 29
关键提醒: 特殊权限不能通过 requestPermissions() 弹窗申请,必须使用 Intent 跳转到系统设置页面,并监听 onActivityResult 判断是否成功。

3.4 输入输出物

类型输入物输出物
文档Android 官方权限清单、项目需求文档本章提供的分类对照表(可直接作为团队通用参考资料)
代码AndroidManifest.xml 中的 <uses-permission> 声明权限类型标注清单,用于后续流程设计

3.5 责任边界

  • Android 开发工程师: 负责对照表格将项目所用权限划分类别,并确保 targetSdk 对应的行为正确。
  • 技术 PM / 架构师: 审核权限分类是否覆盖所有功能,是否存在过度申请。
  • QA 测试: 验证不同 API 版本下权限行为是否与分类预期一致(如 Android 10+ 后台位置需单独处理)。

3.6 记录材料

  • 项目权限登记表:建议以 CSV 或 Markdown 格式记录“权限名 → 类型 → 引入 API → 申请方式”。
  • 版本变更记录:当 compileSdk 升级时,同步更新该表。
# 示例权限登记表片段
| 权限名                          | 类型     | API 引入 | 申请方式               |
|--------------------------------|----------|----------|------------------------|
| android.permission.CAMERA       | dangerous| API 1    | requestPermissions()   |
| android.permission.SYSTEM_ALERT_WINDOW | special | API 23 | Settings intent       |
| android.permission.INTERNET     | normal   | API 1    | 自动授权               |

3.7 异常处理

  • 权限分类混淆: 例如将 SYSTEM_ALERT_WINDOW 当作危险权限使用弹窗申请,导致始终被拒绝。解决方案:对照特殊权限清单及时修正代码逻辑。
  • API 版本兼容: 部分权限(如 ACCESS_BACKGROUND_LOCATION)仅在 API 29+ 存在,低版本机型需做条件判断,避免 NoSuchMethodError。
  • 分组误解: 误以为同组权限只要申请一项即可完全替代其他项。实际上只有同一组的权限才共享授权,跨组必须分别申请。
避坑指南: Android 14(API 34)新增 NEARBY_WIFI_DEVICES 属于危险权限但被归入 NEARBY_DEVICES 组,不再与 ACCESS_FINE_LOCATION 合并。升级时务必对照最新官方分组。

3.8 验收标准

  1. 项目所有声明的权限均能在本章表格中找到对应分类。
  2. 对特殊权限,已正确实现“跳转设置 → 返回检查”的引导逻辑。
  3. 对不同 API 版本(特别是 targetSdk 23+),危险权限的运行时申请路径已设计到位。
  4. 团队内可借助记录的权限登记表快速定位后续流程中的申请方式。
Android 权限分类层次图 Runtime 权限体系 正常权限 危险权限 特殊权限 特性 • 安装时自动授权 • 无需运行时弹窗 • 常见:INTERNET, ACCESS_NETWORK_STATE 特性 • 运行时弹窗申请 • 分组管理(同一组 授权一项即全组授权) • API 23+ 引入 特性 • 跳转系统设置授予 • 不能使用常规 requestPermissions() • 需要 onActivityResult 版本对应:API 23 引入运行时,API 26+ 细化特殊权限 危险权限组可随 API 版本变化(如 Android 14 新增 NEARBY_DEVICES)