1

The Android docs say this about creating a developer payload string when making an in-app purchase:

It’s good practice to pass in a string that helps your application to identify the user who made the purchase, so that you can later verify that this is a legitimate purchase by that user. For consumable items, you can use a randomly generated string, but for non-consumable items you should use a string that uniquely identifies the user.

I want some way of identifying a user so that I know that person has purchased non-consumable items, regardless of what Android device they are using. I don't want to set up a server. I don't want to use their gmail account ID because, as of Android 6.0, that means asking the user to grant the dangerous GET_ACCOUNTS permission. I know you can also run into problems if the user has more than one Google account on their device.

Does anyone know of a solution that meets all these criteria (cross-device; no server; no dangerous permissions required)?

Incidentally I did find an old blog post about Google account ID:

This will key the local data against a Google Account ID, which is unique and stable for the user even after changing an email address.

Does this require a dangerous permission to use? If not, and it's constant across a user's devices, then this may meet my criteria...

snark
  • 2,462
  • 3
  • 32
  • 63

1 Answers1

0

The developer payload has one particular use case: you need to do server side validation of the purchaseToken and, for that use case, a random string works great (you just want to confirm that the purchaseToken/randomId matches what you originally sent to your server the first time the purchase was made). Even then, it relies on that randomId making it to your server in a secure fashion (otherwise, one could still do a replay attack sending in a set purchaseToken/randomId from a hacked version of the app).

If you don't feel that is needed (or too much of a hassle to store every purchaseToken/randomId combination on a server somewhere and deal with all that), then I would say that leaving out the payload entirely and relying on Google correctly returning valid purchases made with the current Google account (which it will, whether you include a payload or not) is a solid course of action.

ianhanniballake
  • 191,609
  • 30
  • 470
  • 443
  • Thank you! I hadn't appreciated that Google will already correctly return purchases for a given user account but it must be because I already know it works on different devices using the same account. I was stupidly including the user's account in the developer payload but now I know that was utterly pointless because Google was already fetching the right purchases for a given account! So I don't need to find out the user's account and therefore I no longer need to request the `GET_ACCOUNTS` permission! Hooray! – snark Aug 08 '16 at 19:19
  • I'm still confused by something though; and I'm not the only one judging by http://stackoverflow.com/q/8947015/1843329. If Google is doing all the purchase verification for you then what is the point of the developer payload at all?! Is it just an arbitrary string I can use for whatever I want, and which Google won't themselves use other than to accept with a purchase request and then later to return with a purchase query for that same user? If you have an example elaborating on your server side use case, that would be great please. – snark Aug 09 '16 at 17:18
  • One example I can think of: you have an app and a website which has its own user ids and logins, nothing to do with Google. An app user buys a feature that applies to both the app and the website and you use the developer payload simply to record which user id (i.e., for your service, not the Google user id) has purchased that feature. When you later query a purchase in your app and retrieve the developer payload you could send it in a request to your own server to double-check that this user really bought that feature. – snark Aug 09 '16 at 17:24
  • @snark - right, you could use a developer payload to confirm that a purchase token is legitimate via the [Publisher API for purchases](https://developers.google.com/android-publisher/api-ref/#Purchases.products) – ianhanniballake Aug 09 '16 at 17:52