调用resetPasswordWithToken时遇"Calling identity is not authorized"权限异常
解决Device Admin修改密码时的SecurityException问题
你遇到的java.lang.SecurityException: Calling identity is not authorized错误,大概率是因为resetPasswordWithToken的权限要求比普通设备管理API更高,或者调用流程存在问题,以下是具体排查方向:
核心原因:普通设备管理员权限不足
lockNow()这类API普通设备管理员就能调用,但resetPasswordWithToken要求你的应用必须是设备所有者(Device Owner)或配置文件所有者(Profile Owner),而非普通的设备管理应用。这是触发该错误最常见的原因。
验证权限身份
用代码检查你的应用是否具备对应身份:
DevicePolicyManager dpm = (DevicePolicyManager) getSystemService(Context.DEVICE_POLICY_SERVICE); String packageName = getPackageName(); boolean isDeviceOwner = dpm.isDeviceOwnerApp(packageName); boolean isProfileOwner = dpm.isProfileOwnerApp(packageName); Log.d("DPM_CHECK", "Is Device Owner: " + isDeviceOwner + ", Is Profile Owner: " + isProfileOwner);
如果两者均为false,则需要将应用设置为设备所有者。
设置设备所有者的方法
通过ADB命令执行(需设备处于调试模式,且无其他设备所有者应用):
dpm set-device-owner com.your.package/.YourDeviceAdminReceiver
替换com.your.package为你的应用包名,YourDeviceAdminReceiver为你注册的设备管理接收器类。
其他排查点
- 令牌调用上下文不一致:
setResetPasswordToken和resetPasswordWithToken必须在同一进程、同一用户上下文下连续执行,不能将令牌存储后跨进程或跨用户调用(比如不能在Service生成令牌,再到其他进程的Activity中使用)。 - 令牌有效性问题:确保令牌是随机生成的有效字符串(例如用
UUID.randomUUID().toString()生成),不要使用固定字符串,且生成后立即调用重置密码方法,避免长期存储令牌。 - Android版本适配:Android 11+对设备所有者的权限管控更严格,需确保目标SDK版本适配对应规则,避免因系统权限限制触发错误。
你的代码与错误信息参考
修改密码代码:
dpm.setResetPasswordToken(mDeviceAdminSample, token); dpm.resetPasswordWithToken(mDeviceAdminSample, "4567", token, 0);
报错信息:
java.lang.SecurityException: Calling identity is not authorized at android.os.Parcel.createExceptionOrNull(Parcel.java:3057)
设备管理配置:
<?xml version="1.0" encoding="utf-8"?> <device-admin xmlns:android="http://schemas.android.com/apk/res/android"> <uses-policies> ... <reset-password/> ... </uses-policies> </device-admin>
内容的提问来源于stack exchange,提问作者Lucius
相关产品推荐
相关产品推荐

