argent-settings-permissions

Compare original and translation side by side

🇺🇸

Original

English
🇨🇳

Translation

Chinese

What this tool is for

工具用途

settings-permissions
edits the platform's permission store directly - the iOS simulator's TCC database, or Android's package-manager permission flags. It replaces the manual Settings → Privacy dance during test setup: pre-authorize a service so the app never has to ask, deny it up front to test the refusal path, or reset it so the first-run dialog appears again on the next launch.
It is a test-setup / out-of-band tool, not a general permissions toggle. The default way to change a permission is still through the app - this tool is the exception for the cases the app can't reach.
settings-permissions
直接修改平台的权限存储——iOS模拟器的TCC数据库,或Android的包管理器权限标记。它替代了测试设置过程中手动进入设置→隐私的繁琐操作:预先授权某项服务,让应用无需请求权限;提前拒绝权限以测试拒绝后的流程;或重置权限,让下次启动时重新显示首次运行的权限提示。
这是一款测试设置/离线操作工具,而非通用权限切换工具。更改权限的常规方式仍是通过应用本身——仅当应用无法实现权限更改时,才使用本工具。

When to use it - and when NOT to

适用场景与禁用场景

Decide with this order. The first matching row wins.
SituationDo thisWhy
The app has an in-app control for the permission (a toggle in its own settings screen)Tap it in the app (
describe
gesture-tap
) - do NOT use this tool
It's real user behavior and exercises the flow you're testing. See
argent-device-interact
.
The app is about to ask (or just asked) and the system permission dialog is on screenTap the dialog (
Allow
/
Don't Allow
/
Allow While Using App
) - do NOT use this tool
The app-triggered prompt is the natural path; answering it is what a user does.
describe
exposes the dialog buttons; fall back to
screenshot
only if it doesn't.
You need the permission already granted/denied before the app runs, so no dialog interrupts the flowUse this tool (
grant
/
deny
) before
launch-app
The app can't pre-set its own permission; a real user would do it in Settings. This is the core use case. (
deny
suppresses the prompt on iOS only - see Gotchas.)
The user already denied it and you need it on againUse this tool (
grant
)
iOS never re-shows a dialog once denied - the only in-device path is the Settings app. This tool is the shortcut.
You need the first-run dialog to appear again (test the prompt itself, or reset dirty state)Use this tool (
reset
)
Returns the permission to "not yet asked" so the app prompts on next use.
The permission is not one this tool supports on the target platform (see the support table)Do NOT use this toolIt will return an "unsupported" error. Use the app dialog if the app triggers one, or navigate the real Settings app.
The setting isn't one of the 11 runtime permissions below (e.g. Wi-Fi, cellular data, dark mode, VPN, Focus)Do NOT use this toolOut of scope - drive the Settings app or the app's own UI instead.
Rule of thumb: if a human tester could flip it inside the app, do that. Reach for
settings-permissions
only for a change a human would otherwise make in the system Settings app.
请按以下优先级判断,符合第一条即执行对应操作。
场景操作建议原因
应用内有该权限的控制开关(如应用自身设置界面中的切换按钮)在应用内点击开关(使用
describe
gesture-tap
)——请勿使用本工具
这符合真实用户行为,且能测试你关注的流程。可参考
argent-device-interact
应用即将请求(或刚请求)权限,且系统权限对话框已弹出点击对话框选项
允许
/
不允许
/
使用期间允许
)——请勿使用本工具
应用触发的提示是自然流程,用户会直接回应。
describe
可识别对话框按钮;若无法识别,再使用
screenshot
辅助。
需要在应用启动前就授予/拒绝权限,避免权限对话框打断测试流程使用本工具(执行
grant
/
deny
操作),再调用
launch-app
应用无法预先设置自身权限,真实用户需进入系统设置操作。这是本工具的核心适用场景。(注:仅iOS平台的
deny
操作会屏蔽权限提示,详见注意事项。)
用户已拒绝权限,现在需要重新启用该权限使用本工具(执行
grant
操作)
iOS平台一旦用户拒绝权限,就不会再次弹出提示——唯一的设备内操作路径是进入系统设置。本工具可实现快捷操作。
需要重新显示首次运行的权限提示(测试提示本身,或重置脏状态)使用本工具(执行
reset
操作)
将权限恢复为“未请求”状态,应用下次使用时会重新弹出提示。
目标平台不支持本工具管理该权限(详见支持表)请勿使用本工具工具会返回“不支持”错误。若应用能触发权限对话框,则使用对话框;否则进入真实系统设置操作。
该设置不属于以下11项运行时权限(如Wi-Fi、蜂窝数据、深色模式、VPN、专注模式)请勿使用本工具超出工具范围——请通过系统设置或应用自身界面操作。
经验法则:如果人工测试员可以在应用内完成权限切换,就直接操作应用。仅当人工需要进入系统设置才能更改权限时,再使用
settings-permissions

Supported permissions & platform coverage

支持的权限与平台覆盖

permission
iOS simulator (TCC service)Android (
android.permission.*
)
camera
camera
- only if the target simulator's runtime models it (varies by simruntime, not by the installed Xcode; simulators have no camera hardware)
CAMERA
microphone
microphone
RECORD_AUDIO
photos
photos
+
photos-add
(add-only access is a separate TCC service;
photos-add
is best-effort - check
applied
to see whether both changed)
READ_MEDIA_IMAGES
+
READ_MEDIA_VIDEO
+
READ_MEDIA_VISUAL_USER_SELECTED
+
READ_EXTERNAL_STORAGE
contacts
contacts
READ_CONTACTS
+
WRITE_CONTACTS
notifications
unsupported - no iOS equivalent; answer the app's dialog instead
POST_NOTIFICATIONS
calendar
calendar
READ_CALENDAR
+
WRITE_CALENDAR
location
location
ACCESS_FINE_LOCATION
+
ACCESS_COARSE_LOCATION
location-always
location-always
ACCESS_BACKGROUND_LOCATION
(a grant also adds fine + coarse - background alone can't read location)
media-library
media-library
READ_MEDIA_AUDIO
+
READ_EXTERNAL_STORAGE
motion
motion
ACTIVITY_RECOGNITION
reminders
reminders
unsupported - no Android runtime permission
One abstract permission can map to several concrete Android permissions; which ones actually exist depends on the app's manifest and the device's API level (e.g.
READ_MEDIA_*
on API 33+ vs
READ_EXTERNAL_STORAGE
below it).
permission
iOS模拟器(TCC服务)Android(
android.permission.*
camera
camera
——仅当目标模拟器的运行时环境支持该服务(取决于模拟器运行时,而非安装的Xcode;模拟器无实体相机硬件)
CAMERA
microphone
microphone
RECORD_AUDIO
photos
photos
+
photos-add
(仅添加权限是独立的TCC服务;
photos-add
为尽力支持——需查看
applied
确认是否两项均已更改)
READ_MEDIA_IMAGES
+
READ_MEDIA_VIDEO
+
READ_MEDIA_VISUAL_USER_SELECTED
+
READ_EXTERNAL_STORAGE
contacts
contacts
READ_CONTACTS
+
WRITE_CONTACTS
notifications
不支持——iOS无对应机制;请直接回应应用的权限对话框
POST_NOTIFICATIONS
calendar
calendar
READ_CALENDAR
+
WRITE_CALENDAR
location
location
ACCESS_FINE_LOCATION
+
ACCESS_COARSE_LOCATION
location-always
location-always
ACCESS_BACKGROUND_LOCATION
(执行
grant
操作时,会同时添加精确与粗略位置权限——仅后台权限无法读取位置)
media-library
media-library
READ_MEDIA_AUDIO
+
READ_EXTERNAL_STORAGE
motion
motion
ACTIVITY_RECOGNITION
reminders
reminders
不支持——Android无对应运行时权限
一项抽象权限可能对应多个具体Android权限;实际生效的权限取决于应用的清单文件和设备的API级别(例如API 33+使用
READ_MEDIA_*
,低于该版本使用
READ_EXTERNAL_STORAGE
)。

Actions

操作类型

  • grant
    - pre-authorize the permission. Requires
    bundleId
    .
  • deny
    - refuse it. Requires
    bundleId
    . Use to test the app's "permission denied" path.
  • reset
    - return to the not-yet-asked state so the dialog reappears on next use. Always per-app (
    bundleId
    required):
    • iOS: removes that app's TCC row. A device-wide reset (no bundleId) is not offered - on recent iOS runtimes it reports success but leaves existing per-app grants untouched, so it would report a change that never happened.
    • Android: revokes the grant, then best-effort clears the user-set/user-fixed flags (flag-clearing first appears in Android 13 / API 33; the revoke is what counts toward success). Below API 33 (i.e. API 23-32, everywhere a user-fixed state can exist) flag-clearing is unavailable, so a
      reset
      there revokes the grant but cannot clear a "don't ask again" (user-fixed) state - the dialog may stay suppressed on those older devices.
  • grant
    ——预先授权权限,需指定
    bundleId
  • deny
    ——拒绝权限,需指定
    bundleId
    ,用于测试应用的“权限被拒绝”流程。
  • reset
    ——将权限恢复为“未请求”状态,下次使用应用时会重新弹出提示。始终针对单个应用(必须指定
    bundleId
    ):
    • iOS:移除该应用在TCC中的记录。不提供设备级重置(无
      bundleId
      )——在新版iOS运行时中,设备级重置会返回成功,但不会更改已有的应用权限,导致工具报告虚假的更改结果。
    • Android:撤销权限授权,然后尽力清除用户设置/用户固定标记(标记清除功能从Android 13 / API 33开始支持;权限撤销是判断操作成功的标准)。在API 33以下(即API 23-32,存在用户固定状态的版本),无法清除标记,因此
      reset
      操作仅会撤销权限授权,但无法清除“不再询问”(用户固定)状态——在这些旧设备上,权限提示可能仍会被屏蔽。

Parameters

参数说明

json
{
  "udid": "<UDID-or-serial>",
  "action": "grant",
  "permission": "camera",
  "bundleId": "com.example.app"
}
  • udid
    - target from
    list-devices
    (iOS simulator UDID, or Android serial). See
    argent-ios-simulator-setup
    /
    argent-android-emulator-setup
    to get one.
  • action
    -
    grant
    |
    deny
    |
    reset
    .
  • permission
    - one of the 11 names above.
  • bundleId
    - iOS bundle id or Android package name. Required for every action.
json
{
  "udid": "<UDID-or-serial>",
  "action": "grant",
  "permission": "camera",
  "bundleId": "com.example.app"
}
  • udid
    ——目标设备标识,来自
    list-devices
    (iOS模拟器UDID或Android设备序列号)。可通过
    argent-ios-simulator-setup
    /
    argent-android-emulator-setup
    获取。
  • action
    ——可选值:
    grant
    |
    deny
    |
    reset
  • permission
    ——上述11种权限名称之一。
  • bundleId
    ——iOS应用的Bundle ID或Android应用的包名。所有操作均需指定该参数

Platform behavior

平台行为

iOS simulator only. Edits the simulator's TCC store - always per-app (
bundleId
required). There is no host-side TCC switch on a physical iPhone, so this tool does not apply to real iOS devices. The simulator must be booted first (
boot-device
) - otherwise the tool fails with a "current state: Shutdown" error and surfaces the boot hint.
Android emulator and physical device. Changes the app's
android.permission.*
runtime permissions over adb (and, for
reset
, best-effort clears the user-set/user-fixed flags - the revoke is what decides success; flag-clearing needs Android 13 / API 33+). Requirements:
  • The app must be installed - the tool probes for the package first and errors clearly if it is missing (a transport/timeout failure surfaces adb's real cause, not a false "not installed").
  • The app must declare the permission in its manifest. The package manager rejects any mapped permission the manifest doesn't request; those come back in the result's
    skipped
    list. The action succeeds if at least one mapped permission sticks, and errors only if all of them were rejected.
仅适用于iOS模拟器:修改模拟器的TCC存储——始终针对单个应用(必须指定
bundleId
)。物理iPhone上没有主机端TCC开关,因此本工具不适用于真实iOS设备。模拟器必须先启动(调用
boot-device
)——否则工具会返回“当前状态:已关机”错误,并提示启动模拟器。
适用于Android模拟器与物理设备:通过adb修改应用的
android.permission.*
运行时权限(执行
reset
操作时,会尽力清除用户设置/用户固定标记——权限撤销是判断操作成功的标准;标记清除需要Android 13 / API 33+)。要求:
  • 应用必须已安装——工具会先检测应用是否存在,若未安装会明确报错(传输/超时失败会显示adb的真实原因,而非虚假的“未安装”提示)。
  • 应用必须在清单文件中声明该权限。包管理器会拒绝所有清单文件未请求的映射权限,这些权限会出现在结果的
    skipped
    列表中。只要至少一个映射权限生效,操作即视为成功;仅当所有映射权限均被拒绝时,操作才会报错。

Gotchas

注意事项

  • Changing a permission can terminate a running app (system behavior on both platforms). Prefer setting permissions before
    launch-app
    ; if you change one while the app is running,
    restart-app
    afterward.
  • Reset is per-app on both platforms - pass
    bundleId
    ; there is no reliable device-wide reset.
  • A partial Android result is normal.
    applied
    lists what actually changed;
    skipped
    lists mapped permissions the package manager rejected (usually not in the manifest, or gated by API level). Both together tell you what happened.
  • A pre-launch
    deny
    suppresses the prompt on iOS only.
    On iOS a TCC denial answers the app's request, so no dialog appears. On Android a
    deny
    clears the grant but sets no "user-fixed" flag, so the app's next request still shows the system dialog - a pre-launch
    deny
    there tests the revoked state, not a suppressed prompt.
  • camera
    on iOS
    may be rejected by a simulator runtime that doesn't model the service (it varies by simruntime, not by the installed Xcode - a runtime can accept
    camera
    even when the platform's own service list omits it). A rejection surfaces as a generic CoreSimulator error, so a
    camera
    failure (unless it's the shutdown-simulator case, which gets the boot hint instead) is reported with a hint about the runtime's supported services.
  • grant location
    needs the app installed first (iOS).
    Location authorization isn't stored in TCC and isn't applied to a bundle id until the app exists, so a pre-install
    grant location
    /
    grant location-always
    records nothing. On a local simulator the tool checks install state and errors clearly instead of reporting a false success; on a remote simulator it cannot probe install state, so a pre-install grant there reports success while recording nothing - make sure the app is installed before granting location remotely. (TCC-backed services like
    camera
    /
    photos
    can be granted before install; they persist and apply on install.)
  • 更改权限可能会终止运行中的应用(两个平台的系统行为)。建议在调用
    launch-app
    设置权限;若在应用运行时更改权限,之后需调用
    restart-app
    重启应用。
  • 重置操作在两个平台均针对单个应用——必须传入
    bundleId
    ;不存在可靠的设备级重置方式。
  • Android平台出现部分生效结果是正常现象
    applied
    列表显示实际更改的权限;
    skipped
    列表显示被包管理器拒绝的映射权限(通常是清单文件未声明或受API级别限制)。两者结合可告知操作结果。
  • 仅iOS平台的预启动
    deny
    操作会屏蔽权限提示
    。iOS平台的TCC拒绝操作会直接响应应用的权限请求,因此不会弹出对话框。Android平台的
    deny
    操作仅会清除权限授权,但不会设置“用户固定”标记,因此应用下次请求权限时仍会弹出系统对话框——预启动
    deny
    操作测试的是权限被撤销的状态,而非屏蔽提示。
  • iOS平台的
    camera
    权限
    可能会被模拟器运行时环境拒绝(取决于模拟器运行时,而非安装的Xcode——即使平台服务列表中没有
    camera
    ,运行时仍可能支持)。拒绝会显示为通用CoreSimulator错误,因此
    camera
    操作失败(除非是模拟器关机的情况,会提示启动)时,会附带关于运行时支持服务的提示。
  • iOS平台授予
    location
    权限需先安装应用
    。位置授权不存储在TCC中,且只有应用存在时才会绑定到Bundle ID,因此在安装应用前执行
    grant location
    /
    grant location-always
    操作不会记录任何信息。在本地模拟器上,工具会检测应用安装状态并明确报错,而非报告虚假成功;在远程模拟器上,无法检测安装状态,因此预安装授予位置权限会报告成功但无实际效果——请确保远程模拟器上已安装应用,再授予位置权限。(基于TCC的服务如
    camera
    /
    photos
    在安装前授予,权限会保留并在应用安装后生效。)

Result

返回结果

Returns
{ action, permission, bundleId, applied, skipped? }
:
  • applied
    - the platform-level services/permissions actually changed (the TCC service(s) on iOS; the
    android.permission.*
    names on Android).
  • skipped
    - Android only, present when some mapped permissions were rejected but others succeeded.
The call fails when nothing could be applied - read the error; it names the reason: an unsupported permission for the platform (
notifications
on iOS,
reminders
on Android), the app not installed (including a pre-install
grant location
on iOS), a shutdown simulator (iOS), or every mapped permission being rejected (usually a missing manifest entry). A non-shutdown
camera
failure additionally hints about the simulator runtime's supported services (a shutdown-simulator failure gets the boot hint instead).
返回
{ action, permission, bundleId, applied, skipped? }
  • applied
    ——实际更改的平台级服务/权限(iOS平台为TCC服务;Android平台为
    android.permission.*
    名称)。
  • skipped
    ——仅Android平台存在,当部分映射权限被拒绝但其他权限生效时显示。
当没有任何权限生效时,调用会失败——请查看错误信息,原因包括:平台不支持该权限(iOS的
notifications
、Android的
reminders
)、应用未安装(包括iOS平台预安装时授予
location
权限)、模拟器已关机(iOS)、所有映射权限均被拒绝(通常是清单文件未声明)。非关机状态下的
camera
操作失败还会附带关于模拟器运行时支持服务的提示(关机状态下的失败会提示启动模拟器)。

Examples

示例

Pre-grant the camera before launching, so the app never prompts:
json
{ "udid": "<UDID>", "action": "grant", "permission": "camera", "bundleId": "com.example.app" }
Test the denied path - refuse location, then launch and observe the fallback:
json
{ "udid": "<serial>", "action": "deny", "permission": "location", "bundleId": "com.example.app" }
Reset notifications on Android so the first-run prompt appears again next launch:
json
{
  "udid": "<serial>",
  "action": "reset",
  "permission": "notifications",
  "bundleId": "com.example.app"
}
Grant always-on location on Android (fans out to background + foreground automatically):
json
{
  "udid": "<serial>",
  "action": "grant",
  "permission": "location-always",
  "bundleId": "com.example.app"
}
启动应用前预先授予相机权限,避免应用弹出提示:
json
{ "udid": "<UDID>", "action": "grant", "permission": "camera", "bundleId": "com.example.app" }
测试权限被拒绝的流程——拒绝位置权限,然后启动应用并观察 fallback 逻辑:
json
{ "udid": "<serial>", "action": "deny", "permission": "location", "bundleId": "com.example.app" }
重置Android应用的通知权限,让下次启动时重新显示首次运行提示:
json
{
  "udid": "<serial>",
  "action": "reset",
  "permission": "notifications",
  "bundleId": "com.example.app"
}
授予Android应用始终允许位置权限(会自动包含后台与前台权限):
json
{
  "udid": "<serial>",
  "action": "grant",
  "permission": "location-always",
  "bundleId": "com.example.app"
}