why do gcm docs recommend invalidating registration on app update? - android

From the GCM docs:
When an application is updated, it should invalidate its existing
registration ID, as it is not guaranteed to work with the new version.
Because there is no lifecycle method called when the application is
updated, the best way to achieve this validation is by storing the
current application version when a registration ID is stored. Then
when the application is started, compare the stored value with the
current application version. If they do not match, invalidate the
stored data and start the registration process again.
When the docs state that "it is not guaranteed to work with the new version" is that a GCM limitation or are they speculating about potential changes in my app's behavior from version to version?
From the app side I can more-or-less guarantee that successive versions will function properly with respect to GCM and whatever app-specific message format I concoct. Do I still need to re-register?
If so, which should I use to detect a "new version": version code or version name? My understanding is that these are "free form" and the app developer sets them to whatever values he chooses. So, what if I put an app update in the store but don't change versionName or versionCode; would I need to re-register with GCM?
It seems like what GCM actually wants is for the app to re-register each time a new installation is launched for the first time (and each time it's successively launched until registration is complete), regardless of the values in versionName and versionCode. Is that an accurate statement?

I don't remember where we've read it, but it came to our attention that when a device gets a push while an app is not installed, Google will invalidate the registration id.
This makes sense if the app is really uninstalled, but if the device was actually in the middle on an update, it quickly uninstalls and re-installs, so google might mistakenly think the registration needs to be invalidated.
The solution seems like to re-register on the first launch after an update, to guarantee your app registration id is active.
Version code is indeed a freely selected number, but you must increase it on every new version you publish to google play, so you can check if that number has changed, and know your app had been updated and you need to refresh the registration.
EDIT:
This is also relevant to C2DM's successor GCM, with a lot more docs explaining this behavior and how to properly write code.
See: http://developer.android.com/google/gcm/client.html with all the details.
Specifically this code, where getRegistrationId will return an empty string in case the version code changed forcing the client to register again:
if (checkPlayServices()) {
gcm = GoogleCloudMessaging.getInstance(this);
regid = getRegistrationId(context);
if (regid.isEmpty()) {
registerInBackground();
}
} else {
Log.i(TAG, "No valid Google Play Services APK found.");
}

I would use the Version Code to detect the app update. The Version Code is forced to change every time you submit a new version to the Google Play store, hence you can rely on it to detect the app's version.

Related

Releasing updated mobile app version

I launched a mobile app last week, both for iOS and Android (it's build with ionic framework if this could make any difference). Actually, it was much more like a beta version.
Now, there are people that have installed the app. Not that huge amount, but anyway.
I have now developed a new version. Thing is that the app relies on a server. And the server has changed a lot of things.
So the client app on the store is not really in sync with the server code.
When I release this updated version of the app, chances are huge that those people that use the "old" app will get really unpredictable results.
Is there a standard way to face with this? I cannot inform users that the app is out of date but only rely on OS telling the user there is a new version available.
This is really a general programming issue that has nothing to do with any specific platform.
Version 1 of your app requires version 1 of your server API and then you need to update the server to version 2 of its API for version 2 of your app.
Upon release of version 2 of your app, your user base will be a mix of both version 1 and version 2 of your app.
This means that your server needs to be able to respond to both versions of its API. There are a few possible ways to support this.
Have two completely different URLs for each version. Example: http://version1.server.com/... and http://version2.server.com/... Just use the proper URL in each app.
Pass a version number as part of the URL. Example: http://server.com?ver=2&other=whatever. You could have your server assume version 1 if there is no ver parameter in the URL.
The key point is that version 1 of the app is out there. The server needs to keep supporting that version of its API for a while. The server needs a way to support both. So version 2 of the app can be fixed now, before it is released, to work with whatever changes are made on the server to support both its old API and the new API.
Perhaps a little late now, but with planning:
1) Have your server "store" the latest version number of the app (I use Firebase for this). When your app runs, have it check its version number against the version number stored on the server. Thus, if the app is out of date, you can immediately display a message informing the user to update. (perhaps even with a custom message also retrieved from the server, informing them of the relative importance of this particular update)
2) If feasible, you can ensure your server maintains working code for the older versions and the newer versions simultaneously. On your Analytics, once you see everybody is on the new version, you can remove the old supporting code.
As an app developer, this needs to be at the top of your mind ALL the time. This will happen, and quite frequently too.
What you should do is every request to your server, you should supply the app version. Your backend should then use this app version to interpret the parameters of your request and service the mobile app accordingly.
On Android, you can get your app version using the following:
String vName, vCode;
try {
PackageInfo pInfo = getPackageManager().getPackageInfo(getPackageName(), 0);
vName = pInfo.versionName;
vCode = Integer.toString(pInfo.versionCode);
} catch (Exception) {
Log.d("App","Error!");
}
If you used push notification you can use it, or you can cut API service to this app to enforce people to reinstall your app.
Suppose an old version of your app tries to communicate with your server, you could detect this easily on your server and have it tell the user that the app needs updating (like how Whatsapp/other messaging clients).

Registration ID become "NotRegistered" for no reason

During April, we've start receiving a lot of 'NotRegistered' errors. According to the Google docs it should happen only if app was uninstalled or updated, but in our case token can "expire" in ~40 minutes even if absolutely nothing happen with device.
And what makes things even worth is that if, let's say reg_id_1 "expired" and server returns 'NotRegistered' error - we push client to register again, but GCM provides same token which is 'NotRegistered'. App update do not help. Only reinstall or user reset(android user) helps.
So the question is - does anyone encounter the same issue and/or has some solution ?
P.S. I wonder, can it be connected to the April ClientLogin shutdown and something gone wrong on Google servers ? https://plus.google.com/+GoogleDevelopers/posts/RK1pw9Cy4Sd
UPD See this for response from Google
https://groups.google.com/forum/#!msg/android-gcm/vkj_ph7vqRQ/b_Kq283wXUQJ
There may be several reasons why this error would be firing on the server
App was uninstalled
ID expires. Prior to that you get notifed on your server that you should reintitiate the registration.
Users's change their google account and they send the new ID
Update to your app causes a new ID, old one expires.
It's best to remove the dead ID's from your DB and stop sending messages there.
Have a look at this article. Although some information there is contradictory, there's a lot of useful non-documented stuff.
Actual answer is https://groups.google.com/d/msg/android-gcm/vkj_ph7vqRQ/b_Kq283wXUQJ
This problem was triggered under a specific configuration (the
application being installed in multiple android profile on the same
device) and a specific combination of events. Only a very limited
number of registration-ids have been affected by this problem, and
calling gcm.register() again would restore the validity of the broken
registration-id.

iOS - Update an app that has been removed from the app store

On Android I think that you can 'unpublish' an application so that no new users can download the application but that the user who already have the application will recieve new versions that are uploaded to google play (or so it seems to say here: https://support.google.com/googleplay/android-developer/answer/113476?hl=en&ref_topic=3450986 )
However I can't find any information on iOS. Can I remove the app but still update existing customers with a new version?
Just for context the update I want to issue for both OS is basically an app which displays a 'app is now closed' message.
Any help would be gratefully received.
Can I remove the app but still update existing customers with a new version?
As far as I am concerned, you can't do this in the App Store.
No, this isn't possible. Once you remove the app, nobody will see it in the app store. Existing users of the app won't see any updates that you may have published before removing it that they never installed. It's just gone if you remove it from the app store.
You could publish an app update that includes some kind of notification system within the app, and keep that in the store long enough for most users to upgrade. Then after you pull the app from the store, you could update this message (presumably it would retrieve this message from your server) to state that the app is no longer available, and maybe direct them to whatever you have that you're replacing it with (assuming you're replacing it). Otherwise, I don't see why you necessarily need to inform existing users that you've removed the app. If there are server-side components that it accesses, and you're shutting those down, I guess the app will simply cease to function for existing users.
I also don't think there is a way to offer updates without new customers being able to buy the app.
Why not increase the price of the app to the highest price allowed in the app store, so that no one will buy it? That way you can offer an update for your existing customers, but effectively stop new sales. If the new price is $1999.00 US, I doubt if you will get any takers...

how could I allow my customers to update my application

I have finished building an android application, I still have to do one last step, which is open a window for updating.
what I have thought about
there should be two scenarios:
an important update, which means a new version contains a lot of different from the last update and I don't want my users to use the old version any more so in this case whenever the user open the application, he MUST update to the newest version in order to work with the application again. for instance, the newest version contains new functionality, or contains a new data representation.
not important update, which means that the user should update the application but it is not a necessary step. for example, the newest version just contains more beautiful images.
my question
what is the best practice to allow my users to update the new version of the application.
In addition, I thing it is something about the URI which contains the package of the application in play store, for example:
Intent intent = new Intent(
Intent.ACTION_VIEW,
Uri.parse("market://details?id=com.google.android.apps.maps"));
startActivity(intent);
in that code, I allow my users to download the Google Mapapplication from play store.
any help would be appreciated
You need to have some kind of server. This server would answer users if they have current version (answers: current, supported, outdated).
You can use GCM to inform client app that it should ask server about version.
App would ask server about version on start/resume/back online and when GCM arrives.
When app receive supported it can show users information about new version available. When it gets outdated it should lock until user updates it.
Or, you could just load your app onto Google Play and let that server notify (with it's already built-in GCM of sorts) when an update is ready. You need to do nothing to ensure your users have access to updates, although you cannot force them into it

How to send notification to users that a newer version is available for my app in google play?

How to send info to already installed users about the update ?
You can use push notification here from below link you can get detail information about it
http://developer.android.com/guide/google/gcm/index.html
Here's the way I did it:
Put a text file one some server, containing the latest version's "VersionCode"
In your app, check the current version code with the one on the text file. If there's a newer version code - show a notification to the user.
You can check everytime the user starts the app, or write a service that runs every 1-2 weeks (depends how often you publish new versions)
Using this method, you don't need to have a DB with all your users' versions and GCM reg ids.
Hope this helped!

Categories

Resources