Info.plist 权限说明怎么写?相机、相册、定位权限文案大全
Info.plist 权限说明就是 NSCameraUsageDescription 这类用途说明键,缺了 App 会崩溃,上传时还会收到 ITMS-90683。本文按权限列出键名、何时需要和中文文案示例,并讲 InfoPlist.strings 多语言写法。
Info.plist 权限说明就是 NSCameraUsageDescription 这类用途说明键:App 访问相机、相册、定位前必须写好,系统弹授权框时把这句话显示给用户。写法是一句话说清「用来做什么」,例如「用于扫描快递单上的二维码,自动填写单号」。缺了这个键,App 一访问就会崩溃或请求直接失败,上传 App Store Connect 时还会收到 ITMS-90683。
下面按权限列出键名、何时需要和中文文案示例,再讲多语言写法和在 KXBuild 里怎么添加。键名以 Apple 的 Protected resources 文档为准,下文内容截至 2026 年 10 月。
写权限说明前要知道什么?
- 键和值。每个权限对应一个 String 类型的键,比如
NSCameraUsageDescription,值就是给用户看的那句话。弹窗标题由系统生成,已经带了 App 名,文案里不用再写 App 名。 - 按用到的写,不要全加。只为 App 真正会用到的功能加键。键加多了,审核会问你为什么需要;该加的没加,访问时出问题。
- 文案要说清用途。审核指南 5.1.1(ii) 要求用途说明「清楚、完整地描述你如何使用这些数据」。Apple 在 Requesting access to protected resources 里列的硬性要求是:不能为空或全是空格,短于 4000 字节,类型正确(一般是字符串),内容准确、具体,本地化后的每种语言也要满足。
各权限对应哪个 Info.plist 键?
下表的文案是示例,照你 App 的实际功能改写,写清「用来做什么、用户能得到什么」。
| 权限 | Info.plist 键 | 何时需要 | 中文文案示例 |
|---|---|---|---|
| 相机 | NSCameraUsageDescription |
拍照、录像、扫码 | 用于扫描快递单上的二维码,自动填写单号。 |
| 麦克风 | NSMicrophoneUsageDescription |
录音、语音消息、录像带声音 | 用于录制语音留言,发送给你的联系人。 |
| 相册(读取) | NSPhotoLibraryUsageDescription |
读取相册里的照片、视频 | 用于从相册选择照片作为头像。 |
| 相册(仅添加) | NSPhotoLibraryAddUsageDescription |
只往相册里保存,不读取 | 用于把你编辑好的海报保存到相册。 |
| 定位(使用期间) | NSLocationWhenInUseUsageDescription |
前台使用定位,申请「始终」时也必须有 | 用于显示你附近的门店和距离。 |
| 定位(始终) | NSLocationAlwaysAndWhenInUseUsageDescription |
后台也要定位 | 用于在后台记录跑步轨迹,锁屏后也能继续记录。 |
| 通讯录 | NSContactsUsageDescription |
读写通讯录 | 用于从通讯录中选择联系人,快速发起转账。 |
| 日历(完全访问) | NSCalendarsFullAccessUsageDescription |
iOS 17 起,读取和修改日历 | 用于读取你的日程,在空闲时段安排会议。 |
| 日历(仅写入) | NSCalendarsWriteOnlyAccessUsageDescription |
iOS 17 起,只添加事件 | 用于把你预约的课程添加到日历。 |
| 提醒事项 | NSRemindersFullAccessUsageDescription |
iOS 17 起,读写提醒事项 | 用于把待办同步到「提醒事项」,到时间提醒你。 |
| 蓝牙 | NSBluetoothAlwaysUsageDescription |
使用蓝牙连接设备 | 用于连接你的体脂秤,同步测量数据。 |
| 本地网络 | NSLocalNetworkUsageDescription |
发现或连接局域网设备、用 Bonjour | 用于搜索同一 Wi-Fi 下的打印机。 |
| Face ID | NSFaceIDUsageDescription |
用 Face ID 验证身份 | 用于使用面容 ID 快速登录,不用每次输入密码。 |
| 运动与健身 | NSMotionUsageDescription |
读取计步、运动状态等运动数据 | 用于统计你每天的步数,生成运动周报。 |
| 语音识别 | NSSpeechRecognitionUsageDescription |
把语音转成文字 | 用于把你说的话转成文字,快速记笔记。 |
| 健康(读取) | NSHealthShareUsageDescription |
从「健康」读取数据 | 用于读取「健康」中的睡眠数据,分析你的作息。 |
| 健康(写入) | NSHealthUpdateUsageDescription |
往「健康」写入数据 | 用于把你记录的饮水量写入「健康」。 |
| 追踪(ATT) | NSUserTrackingUsageDescription |
跨 App 或网站追踪用户、读取广告标识符 | 用于向你展示更相关的广告,你可以随时在设置中关闭。 |
| 媒体资料库 | NSAppleMusicUsageDescription |
访问音乐资料库、Apple Music 数据 | 用于读取你资料库中的歌曲,作为视频的背景音乐。 |
| HomeKit | NSHomeKitUsageDescription |
读取和控制家庭配件 | 用于读取你家中的灯和插座,在 App 里一键开关。 |
| NFC | NFCReaderUsageDescription |
读取 NFC 标签 | 用于读取交通卡余额。 |
几个容易出错的地方单独说。
定位的两个键
按 Core Location 的授权说明,NSLocationWhenInUseUsageDescription 在申请「使用期间」和「始终」时都必须有,NSLocationAlwaysAndWhenInUseUsageDescription 只在申请「始终」时额外需要。所以要后台定位的 App 两个键都要写,只写「始终」那一个不够。键不全时授权请求会立即失败,不会弹窗。
两句文案分开写。使用期间那句讲前台功能,始终那句讲为什么锁屏后还要定位。用不到后台定位就别加「始终」,审核会要求你说明后台用途。
日历和提醒事项的新键
iOS 17 把日历权限拆成「完全访问」和「仅写入」两档,提醒事项改用 NSRemindersFullAccessUsageDescription。按 EventKit 的说明,在 iOS 17 及以上只写了旧键 NSCalendarsUsageDescription 时,系统会自动拒绝访问请求,App 不会弹窗。
- 只往日历里添加事件,用仅写入,不要申请完全访问。
- 最低支持 iOS 16 及以下的,再加上旧键
NSCalendarsUsageDescription和NSRemindersUsageDescription,老系统用旧键。 - 只是弹出系统的事件编辑界面让用户自己保存的,iOS 17 起可以不申请日历权限。
相册读取和仅添加
只把图片保存到相册、不读取的,用 NSPhotoLibraryAddUsageDescription。要让用户从相册选图时,用系统的照片选择器(PHPicker、SwiftUI 的 PhotosPicker)不需要相册权限,只有直接读取整个相册时才需要 NSPhotoLibraryUsageDescription。
部署目标较低时的旧键
- 最低支持 iOS 13 以下又用蓝牙的,同时加
NSBluetoothAlwaysUsageDescription和NSBluetoothPeripheralUsageDescription。 - 最低支持 iOS 11 以下又用后台定位的,再加
NSLocationAlwaysUsageDescription,文案和「始终」那句保持一致。
还要开能力的权限
健康、HomeKit、NFC 只写用途说明还不够,App ID 还要开启对应的能力,工程里的 .entitlements 文件也要有对应的项,描述文件要重新生成。本地网络用了 Bonjour 的,还要在 NSBonjourServices 数组里列出服务类型,如 _ipp._tcp。这些设置见证书与签名。
权限文案怎么写才清楚?
审核看的是这句话有没有说清用途。下面是几组对比。
| 不建议 | 建议 |
|---|---|
| 需要访问您的相机。 | 用于扫描快递单上的二维码,自动填写单号。 |
| App 需要定位权限才能正常使用。 | 用于显示你附近的门店和距离。 |
| 为了更好的用户体验。 | 用于从相册选择照片作为头像。 |
| 请允许,否则无法使用。 | 用于录制语音留言,发送给你的联系人。 |
写的时候注意这几条。
- 一句话说清楚具体功能,和 App 里实际触发授权的那个操作对得上。
- 一个权限服务多个功能的,挑最主要的一两个写,不要罗列。
- 不要写「否则无法使用」这类施压的话。用户拒绝后,App 其他功能应该照常能用。
- 文案语言和 App 界面语言一致。只有中文界面的 App 写中文,多语言 App 按下一节做本地化。
审核因为权限被拒的常见情况见审核被拒的常见原因。
权限说明怎么做多语言?
Info.plist 里写开发语言的那一句,其他语言在本地化文件里翻译,key 就是 Info.plist 的键名。Info.plist 里的键本身必须保留,只写在本地化文件里不算。
新工程用 String Catalog,文件名必须是 InfoPlist.xcstrings,放在 App 源码文件夹里并加入 target。构建一次后,用到的用途说明会出现在表里,逐行填翻译即可。
1{
2 "sourceLanguage" : "zh-Hans",
3 "strings" : {
4 "NSCameraUsageDescription" : {
5 "localizations" : {
6 "en" : {
7 "stringUnit" : { "state" : "translated", "value" : "Used to scan the QR code on your parcel and fill in the tracking number." }
8 }
9 }
10 }
11 },
12 "version" : "1.0"
13}
已经在用 InfoPlist.strings 的老工程,接着在每种语言的 xx.lproj/InfoPlist.strings 里加一行,等号两边都加双引号,行尾有分号。
1/* en.lproj/InfoPlist.strings */
2"NSCameraUsageDescription" = "Used to scan the QR code on your parcel and fill in the tracking number.";
3"NSLocationWhenInUseUsageDescription" = "Used to show stores near you and how far away they are.";
在 KXBuild 里双击 .xcstrings 或 .lproj 里的 .strings 会用国际化编辑器打开,各语言并排编辑。新建 InfoPlist.xcstrings 并加入 target 的步骤见图标、启动屏与多语言。
缺了权限键会怎样?
| 场景 | 现象 | 处理 |
|---|---|---|
| 运行时访问受保护资源 | 访问失败,多数权限会让 App 直接闪退,调试控制台的输出里写明缺少哪个键 | 按输出里的键名补上 |
| 定位缺键 | 授权请求立即失败,不弹窗 | 至少补上 NSLocationWhenInUseUsageDescription |
| iOS 17 日历只有旧键 | 系统自动拒绝,不弹窗 | 加完全访问或仅写入的新键 |
| 上传 App Store Connect | 收到 ITMS-90683: Missing purpose string in Info.plist,邮件里写明缺哪个键 | 补上键后提高构建号重新上传 |
ITMS-90683 的判断依据是代码里「引用了」访问敏感数据的 API,或者有相应的 entitlement,不是你有没有真的调用。第三方 SDK 里带了相机、定位相关的代码,即使你没用到这项功能,也会收到这封邮件。这时照样补上键,文案按 SDK 的实际用途写,或者换掉用不到的 SDK 模块。其他上传错误码见 ITMS 错误码大全。
在 KXBuild 里怎么添加权限说明?
在 Windows、Linux、macOS 上用 KXBuild 时,先看 target 有没有 Info.plist 文件。右键 target 选「KXBuild: 编辑目标设置」,General 页的「Info.plist 文件」有路径的是第一种情况,空着且「自动生成 Info.plist」打开的是第二种。
工程里有 Info.plist 文件
- 在资源管理器中双击 Info.plist,用属性列表编辑器打开。
- 在任意一行右键选「添加行」,键名填
NSCameraUsageDescription,类型选 String,值填文案。 - Ctrl+S 保存。保存时保持文件原有的格式,源码里的 plist 建议保持 XML,方便 diff。
想直接改文本的,右键选「KXBuild: 以文本方式打开 plist」,加上下面两行。
1<key>NSCameraUsageDescription</key>
2<string>用于扫描快递单上的二维码,自动填写单号。</string>
Info.plist 自动生成
这类工程把用途说明写成 INFOPLIST_KEY_ 开头的构建设置,构建时写进 App 的 Info.plist。以下两种做法任选其一。
- VS Code 插件。在工程设置编辑器切到 Build Settings 页,在值单元格上右键选「添加用户自定义设置」,名称填
INFOPLIST_KEY_NSCameraUsageDescription,值填文案,Ctrl+S 保存。 - 命令行。在工程目录执行下面的命令。
1kxbuild project add-setting -k INFOPLIST_KEY_NSCameraUsageDescription -v "用于扫描快递单上的二维码,自动填写单号。" -t MyApp -P .\MyApp.xcodeproj
NSBonjourServices 这类数组值,以及构建后没有出现在 Info.plist 里的键,新建一个 Info.plist 文件写进去,在 General 页「Info.plist 文件」填上它的路径。自动生成的值会和这个文件合并。
构建后检查
构建完成后,在 ~\DerivedData\<工程名>-<哈希>\Build\Products\Debug-iphoneos\ 下找到 MyApp.app,双击里面的 Info.plist,用属性列表编辑器确认每个键都在、文案正确。再按 F5 装到手机,把每个会触发授权的功能点一遍,看弹窗文字。测过一次的授权不会再弹,删掉 App 重装后再测。
Flutter、React Native 和 Expo
- Flutter。键写在
ios/Runner/Info.plist,插件的说明文档会列出要加哪些键。 - React Native。键写在
ios/<工程名>/Info.plist。 - Expo。写在
app.json的expo.ios.infoPlist里,生成 ios 目录时会写进 Info.plist。直接改 ios 目录下的文件,重新生成时会被覆盖。
不管哪种工程,最终都以构建产物里 App 的 Info.plist 为准。按上一节的方法打开 .app 里的 Info.plist,确认 Info.plist 权限说明一条不缺、文案和实际功能对得上,再提交审核。
常见问题
Info.plist 权限说明可以写英文吗?
可以,但最好和 App 界面语言一致。中文界面的 App 写中文更容易让用户看懂,也不容易被审核认为说明不清。多语言 App 在 InfoPlist.xcstrings 或 InfoPlist.strings 里分别翻译。
没用到相机为什么收到 ITMS-90683?
ITMS-90683 按代码里是否引用了相关 API 判断,第三方 SDK 里带的相机或定位代码也算。补上邮件里点名的键,文案写清 SDK 那项功能的真实用途,或者去掉用不到的 SDK 模块。
定位要写哪个键?
只在前台定位写 NSLocationWhenInUseUsageDescription 一个。需要后台定位时再加 NSLocationAlwaysAndWhenInUseUsageDescription,两个都要有。
iOS 17 日历权限为什么不弹窗?
在 iOS 17 及以上只写了旧的 NSCalendarsUsageDescription 时,系统会自动拒绝。按需要加 NSCalendarsFullAccessUsageDescription 或 NSCalendarsWriteOnlyAccessUsageDescription,并改用 iOS 17 的新授权接口。
权限文案写成什么样审核不会拒?
一句话写清用来做什么,和 App 里触发授权的功能对得上,例如「用于扫描快递单上的二维码,自动填写单号」。「需要访问您的相机」这类只重复权限名的写法容易被要求修改。审核结果由 Apple 决定。