The app I'm currently developing has recently been showing problems when users update to 7.1.1 om Sony mobiles
On a Sony XZ we can see this in the log when trying to addAccountExplicitly:
AccountManagerService( 1503): insertAccountIntoDatabase: Account {name=something#something.com, type=com.myapplication.go}, skipping since the account already exists
The application was installed and the account was added by our app prior to upgrade. It seems as if the account has not been completely removed/readded.
How can we in our app recover from this?
Why is this happening?
I have read of similar problems in Nougat preview but we can not recover from it with removeAccountExplicitly and then add it again as suggested in link below. The result is the same as above and uninstallation of the app does not clear the account and neither does a phone restart.
AccountManager does not add custom account in Android N preview
We found a possible cause and solution for the problem.
Symptoms
TL;DR It's Sony's fault.
From our user base, it looked like only Sony XZ users who used our app prior to upgrading their device to 7.1.1.
We went as far as buying several Sony XZ devices (and eventually returning them back to the shop), upgrading them from Android 6.0 to 7.1.1 and trying to reproduce the issue. But with no luck.
However, we found another way to achieve the same "symptoms" using the Android emulator. The steps are:
Launch emulator
Login into your app (so that user is added to AccountManager)
Go to the terminal, and do the following
Steps:
adb shell
su
cd /data/system_de/0/
rm accounts_de.db
Restart your emulator
From now on your issue is reproducible.
Moreover, if you'll check /data/system_ce/0/accounts_ce.db you will see that this is a database which still contains your previous user. That is most likely why AccountManager does not allow you to insert same user again.
It looks like that during update to Android 7.1.1, Sony somehow corrupted accounts_de.db which contained the original account.
Solution
Since account with the same name is already in the database (and you can't really remove it from there), we basically can't insert user with the same username again. However, we can insert account with slightly updated username:
if (!accountManager.addAccountExplicitly(account, password, bundle)) {
// We failed to add the account. Fallback to workaround.
accountManager.addAccountExplicitly(
new Account(username + "\n", accountType), // this line solves the issue
password,
bundle
);
}
Since this account is now different from original account (thanks to \n character), it can be inserted into AccountManager database.
The issue is known by Google: https://issuetracker.google.com/issues/142699760
Related
I'm essentially in the "Hello, World" phase of implementing Google's upcoming Android Management API (beta) for devices. I've gone through the Android Management API (beta) introduction and several guides and I'm stuck at the very basic step of enrolling a device. Following Google's Quickstart guide, and the general outline of the code embedded in the linked IPython Notebook, I've managed to:
create a project,
create an enterprise,
create a policy,
script the process of generating an enrollment token and displaying the resulting qrCode.
It's step 4 that appears to be the problem: I'm stuck in actually enrolling a device. Doing a factory reset of a 7.1 device, I'm six-times tapping on the welcome screen, and getting to the qrCode scan. That appears to work, and the device gives some indications that it is managed, but I am so far unable to see the device ID listed when I request all devices via method enterprises.devices.list. That API call returns 200 OK and an empty list:
[]
Even waiting 24 hours, that list is still empty.
I'm assuming that I've misconfigured something with the JSON/qrCode, but I'm currently at a loss as to what. Help please; through the linked Android Management API (beta), how do I properly list the enrolled devices?
Looks like this is a bug with the particular Android device with which I'm currently working: Lenovo Tab 4 10 X304F (2G, 32GB). We can utilize the manual workflow of afw#setup as the username, and then type (not QR scan) the 20 character code enrollment token and it works as expected, but any attempt to QR scan results in enrollment failure.
For future web searchers, the actual failure presents as an "iZat" location consent prompt which interrupts the provisioning process. The provisioning process is apparently not robust, and can't be restarted or continued. The only recourse is to factory reset and go the manual code entry route. In short, a paperweight for our purposes.
I have implemented a sync adapter in my app which requires an account to be added in the device account settings. I followed the same approach given in the Android docs. It works fine till Marshmallow and I can see my account listed in the device accounts. But in Android N preview, account does not add to the device accounts. AccountManager's addAccountExplicitly() method always returns false. Has anyone faced this problem?
Not sure if this is the same issue, but there's an issue with AccountManager on the current version of the Android N image. Basically, if you:
Add an account to AccountManager
Uninstall the app
Reinstall the app
Try to add account again
This will fail and you'll see the following in the log:
W/AccountManagerService( 1503): insertAccountIntoDatabase: Account {name=foo#bar.com, type=com.foo.bar}, skipping since the account already exists
This is a known issue and it's been reported to Google:
https://code.google.com/p/android/issues/detail?id=210992
https://code.google.com/p/android/issues/detail?id=210951
I have totally the same issue.
I could fix it by manually going to the application settings and enabling Сontacts permission. I don't know how, but after that I was able to use addAccountExplicitly() method without issues. I even disabled that permission again and cleared app data but it still was working properly...
After app was reinstalled - problem appeared again.
Has this been fixed now in the latest Android N release.
The developer console for android has functionality for reporting runtime crashes if users decide to report a crash. Other frameworks has similar features that sends crash-reports without involving the user.
Does anyone know of a way to report installations or upgrades that has failed? With android 5.0 I am getting more and more user-reports of failed installs, but it is hard to obtain logs from non-technical users of my app.
You cannot detect whether or not an installation has failed yourself, because there is no way to execute code before your app is actually installed. So the logical app to do such a thing would be the market app triggering the install (i.e. Google Play). This not only knows when each installation starts, but also knows all details about the apk to report to the right developer.
Unfortunately however, Google play does not support this currently (as far as I know) and hence you cannot detect failed installs.
On older Android phones you could ask users is to install a "logcat app" and email the logs to you for analysis, but this will only work for devices older than Jelly bean. (Read this Link)
The best solution I can come up with (Mac only) is to ask users to install AndroidTool, press one button to generate a bugreport and email that to you. Not great, but for now the best you can do.
You can build an api that reports successful installation. Just call the api in onCreate of first activity. I don't think there is need to collect log on why the installation failed, is it needed ? You can do the same for upgrade, call an api one time from upgraded code.
I have an android app uploaded in google marketplace.
I have been reported an error from a user, which happens only in a specific device.
It is not a crash, the application just doesn't work exactly as expected. I have tried to reproduce the error using the emulator with the exact android version he's using and it works fine.
I am sure I could determine the problem If I'd have access to the Logcat entries.
I suppose the answer is negative, but it is any way the user can get these entries and send them to me? ( of course I cannot tell him to install eclipse or adb to gather the log entries ).
What is the best practice to be able to get error information from your app, once it is uploaded to the market? ( I don't mean crashes where an error report can be sent by android, just something that it is not working as expected ).
The application aLogcat can do the trick.
https://play.google.com/store/apps/details?id=org.jtb.alogcat&feature=nav_result#?t=W251bGwsMSwxLDMsIm9yZy5qdGIuYWxvZ2NhdCJd
And I tested it on my 4.1.1 device.
(I don't know how to post this as a comment instead of answer)
there are several apps on android market that allows to get logs and send them by email or upload them to dropbox... I used this one: https://play.google.com/store/apps/details?id=com.xtralogic.android.logcollector
How come I can get license verification on my physical test device, but not on the emulator running on my pc?
When testing from an emulator, no matter what I do, I get NOT_MARKET_MANAGED error. From an actual phone, it passes through with no issues.
Is it because my emulator doesn't have the market app installed and my test device does?
Well, turns out that my emulator did not have a google account setup before trying to run the LVL code. Obviously, if there isn't a google account already setup on the emulator, the LVL has no account to check against for validation.
LVL will still run on an emulator without the Android market installed.
Edit
*Only tested on emulators running Android 2.2*
*LVL will NOT work on emulators running 2.3 or greater, evidently it's a known bug*
Well, you got a real problem: it's a known bug. There's a way out, although. You must separate the MVC code from the license check routines(there's an pretty good example here). Once you have finished to test your code in multiple emulated API versions, you can add the licence check activity to you project and mark it as MAIN and LAUNCHER in the manifest, upload the app to your phone and test the authentication. Follow the instructions in the comments and don't forget to make the necessary adjustments (e.g. i had to change the libraries from com.android to com.google.android in the java file, but keep the com.android.vending.LICENSE_CHECK in the manifest uses-permission tags.)
I know this is an old question, but I just had this problem and thought I would update the answer.
I repeatedly got Error Code 291 (error contacting server) for the license check running an emulator on API 15. According to the "accepted" answer at the time I write this, it says "LVL will not work on emulators over API 8 / 2.2 - it is a known bug".
For API 15 I used the Google API's emulator (to include the LVL libraries) and had to go into the Settings and add a test user account and it worked. I now get the appropriate error responses from the Google Play license server according to my account settings in my Google Play account.
The Google Play / Market app is not required if you do both (use a Google API emulator and set up a test account in the emulator). Here is the reference:
http://developer.android.com/google/play/licensing/setting-up.html#acct-signin
During testing, to ensure that your application can successfully query the licensing server, you must make sure that you sign in to an account on the device or emulator using:
The credentials of a publisher account, or
The credentials of a test account that is registered with a publisher account