SecurityException:调用者uid XXXX与身份验证者的uid不同

Pau*_*aul 84 android

我在尝试实现Sample Sync Adapter应用程序时收到了上述异常.我看过很多与此问题相关的帖子,但没有令人满意的答复.

所以我会在这里记下我的解决方案,以防其他人遇到同样的问题.

Jan*_*kel 54

调试这样的问题的一些其他有用的技巧.

首先为某些标记启用详细日志记录:

$ adb shell setprop log.tag.AccountManagerService VERBOSE
$ adb shell setprop log.tag.Accounts VERBOSE
$ adb shell setprop log.tag.Account VERBOSE
$ adb shell setprop log.tag.PackageManager VERBOSE
Run Code Online (Sandbox Code Playgroud)

你会看到这样的记录:

V/AccountManagerService: initiating bind to authenticator type com.example.account
V/Accounts: there is no service connection for com.example.account
V/Accounts: there is no authenticator for com.example.account, bailing out
D/AccountManagerService: bind attempt failed for Session: expectLaunch true, connected false, stats (0/0/0), lifetime 0.002, addAccount, accountType com.example.account, requiredFeatures null
Run Code Online (Sandbox Code Playgroud)

这意味着没有为此帐户类型注册身份验证器.要查看注册了哪些验证器,请在安装软件包时查看日志:

D/PackageManager: encountered new type: ServiceInfo: AuthenticatorDescription {type=com.example.account}, ComponentInfo{com.example/com.example.android.AuthenticatorService}, uid 10028
D/PackageManager: notifyListener: AuthenticatorDescription {type=com.example.account} is added
Run Code Online (Sandbox Code Playgroud)

我遇到的问题是authenticator xml描述符引用了一个在安装过程中没有得到正确解析的字符串资源:

android:accountType="@string/account_type"
Run Code Online (Sandbox Code Playgroud)

日志显示

encountered new type: ServiceInfo: AuthenticatorDescription {type=@2131231194}, ...
Run Code Online (Sandbox Code Playgroud)

用普通字符串(不是资源)替换它解决了这个问题.这似乎是Android 2.1特有的.

android:accountType="com.example.account"
Run Code Online (Sandbox Code Playgroud)


Pau*_*aul 43

首先,检查这篇文章中解释的条件:

[...]如果您从AccountManagerService表单中看到错误caller uid XXXX is different than the authenticator's uid,则可能会有点误导.该消息中的"身份验证者"不是您的身份验证者类,它是Android所理解的帐户类型的注册身份验证器.AccountManagerService看起来像这样的检查:

 private void checkCallingUidAgainstAuthenticator(Account account) {
     final int uid = Binder.getCallingUid();
     if (account == null || !hasAuthenticatorUid(account.type, uid)) {
         String msg = "caller uid " + uid + " is different than the authenticator's uid";
         Log.w(TAG, msg);
         throw new SecurityException(msg);
     }
     if (Log.isLoggable(TAG, Log.VERBOSE)) {
         Log.v(TAG, "caller uid " + uid + " is the same as the authenticator's uid");
     }
 }
Run Code Online (Sandbox Code Playgroud)

请注意,hasAuthenticatorUid()采取account.type.这是我搞砸的地方.我Account用一个常量指定的类型创建我:

 class LoginTask {
     Account account = new Account(userId, AuthenticatorService.ACCOUNT_TYPE);
     ...
 }

 class AuthenticatorService extends Service {
     public static final String ACCOUNT_TYPE = "com.joelapenna.foursquared";
     ...
 }
Run Code Online (Sandbox Code Playgroud)

但是这个常量与我的身份验证器的XML定义不匹配:

 <account-authenticator xmlns:android="/web/20150729061818/http://schemas.android.com/apk/res/android"
        android:accountType="com.joelapenna.foursquared.account" ... />
Run Code Online (Sandbox Code Playgroud)

其次,如果您像我一样想要将示例嵌入到现有应用程序中进行测试,请确保使用Constants属于此示例的类而不是android.provider.SyncStateContract包.因为这两个类使用ACCOUNT_TYPE创建Account对象时使用的相同属性名称.

  • 我仍然看到这个问题,但仅限于我的一些用户.我已经仔细检查过authenticator.xml文件中的android:accountType是否与GenericAccountsService中的常量匹配.我也知道绝大多数应用程序用户都不会发生此异常,但在我的崩溃日志中,我偶尔会看到少数用户崩溃.任何的想法?可以以某种方式修改authenticator.xml文件以导致此问题吗? (7认同)
  • @clu你有没有能够解决你的问题?我面临着同样的情况.这个错误只适用于我的一小部分用户:主要是HTC One X,HTC One SV和HTC Desire 500,以及许多其他设备. (3认同)

Far*_*jmi 25

在我的情况下,问题很简单地ACCOUNTTYPE错配中声明res/xml/authenticator.xmlandroid:accountType="com.foo",但错误引用作为"foo.com"创建帐户:

Account newAccount = new Account("dummyaccount", "foo.com");
Run Code Online (Sandbox Code Playgroud)

卫生署!


小智 10

实现自定义帐户的部分很少......

要在您的Activity中调用AccountManager,就像您已经实现的那样......

Account account = new Account(username, ACCESS_TYPE);
AccountManager am = AccountManager.get(this);
Bundle userdata = new Bundle();
userdata.putString("SERVER", "extra");

if (am.addAccountExplicitly(account, password, userdata)) {
    Bundle result = new Bundle();
    result.putString(AccountManager.KEY_ACCOUNT_NAME, username);
    result.putString(AccountManager.KEY_ACCOUNT_TYPE, ACCESS_TYPE);
    setAccountAuthenticatorResult(result);
}
Run Code Online (Sandbox Code Playgroud)

在res/xml/authenticator.xml中,您必须定义AccountAuthenticator数据(负责您的Authenticator UID).ACCESS_TYPE必须与此xml中定义的accountType相同的字符串!

<account-authenticator xmlns:android="http://schemas.android.com/apk/res/android"
    android:accountType="de.buecherkiste"
    android:icon="@drawable/buecher"
    android:label="@string/app_name"
    android:smallIcon="@drawable/buecher" >
</account-authenticator>
Run Code Online (Sandbox Code Playgroud)

最后,您必须定义您的Manifest服务.请不要忘记管理帐户的相关权限(AUTHENTICATE_ACCOUNTS/USE_CREDENTIALS/GET_ACCOUNTS/MANAGE_ACCOUNTS)

<service android:name=".AuthenticationService">
    <intent-filter>
        <action android:name="android.accounts.AccountAuthenticator" />
    </intent-filter>
    <meta-data android:name="android.accounts.AccountAuthenticator"
        android:resource="@xml/authenticator" />
</service>
Run Code Online (Sandbox Code Playgroud)


PLA*_*PLA 5

我的错误是假设AccountManager getAccounts()方法返回仅与我的应用程序上下文相关联的帐户.我改变了

AccountManager accountManager = AccountManager.get(context);
Account[] accounts = accountManager.getAccounts();
Run Code Online (Sandbox Code Playgroud)

AccountManager accountManager = AccountManager.get(context);
Account[] accounts = accountManager.getAccountsByType(Constants.ACCOUNT_TYPE);
Run Code Online (Sandbox Code Playgroud)