The hell of testing Google Play In-app billing

We've recently ported our platform to Android. We had some issues with it, but version for free magazines (just downloading issues, without any payments) was ready quite fast. Next on our roadmap were paid magazines with purchasing single issues and subscriptions. Seems easy right? Well, it is. Maybe a little more code in comparison to iOS, but still pretty straightforward. But after implementing, you have to test it and this is where the pain and agony begins...

Testing workflow in iOS

Let me describe how testing of IAP works in iOS:

  1. Create test user in iTunes Connect
  2. Sign out from the App Store on the device / Remove directory in iOS Simulator's Application Data
  3. Launch your app from Xcode
  4. Perform purchase
  5. Sign in with test user

Just couple notes about this process:

  1. All purchases will be in sandbox environment. No credit card required.
  2. You can create as many test users as you want. For fresh start just create new one.
  3. Subscriptions in sandbox have shortened expiration time where 1 month ~= 5 minutes

Holy comfortable testing environment, Batman! I wish such workflow was in every mobile app store! Well it isn't in Google Play.

Testing workflow in Google Play

First of all you can't test IAB in emulator. You need a physical device. This is not that bad, you have to test your app on the device either way and using emulator is like gazillion times slower.
Official documentation for testing in-app billing, divides testing into two parts:

Testing in-app purchases with static responses

Hmmm... it looks that I need to modify my code to use fake IDs instead of desired ones and remember to throw this away for production. Maybe it's not perfect solution, but it works and I can test all possible return codes. It does work, but not with everything. Subscriptions can't be tested using static responses... Bummer... Ok, let's try using my own IDs then.

Testing In-app Purchases Using Your Own Product IDs

If the primary account on your device is not a test account, you must do a factory reset of the device and then sign in with one of your test accounts.

Whaaaa?! But, but I have everything here! Sigh... Another reminder not to use personal devices for testing.
After factory reset we try again.

This version of the application is not configured for billing through Google Play.

Huh? Everything is set in Google Play Developer Console and I even waited 24h for data propagation. Well this is probably caused because you can't test using application launched from Eclipse. So what do you do? You export signed APK and transfer it to the device.
Now I realize that this will take a lot more time that I hoped. Iterating this way is going to be a real PITA.

I Need A Dollar

Fortunately this works and I can even see Google Plays purchase confirmation intent! It looks like I have to fill credit card information. That's strange, I'm just testing. Can Google just use some fake card? No:

When you use a test account to purchase items, the test account is billed through Google Checkout and your Google Checkout Merchant account receives a payout for the purchase. Therefore, you may want to refund purchases that are made with test accounts, otherwise the purchases will show up as actual payouts to your merchant account

Are you kidding me? You want to charge my card every time I test my purchases? Of course I want to refund those! Oops, looks like it's not possible... Well, f****k... I just pay this to myself giving away 20% to Google for mother flippin testing... As Carl pointed out in comments, it actually is possible to refund purchase! Just go to your Google Checkout, select order you want to refund and click Cancel entire order :)
Looks like it worked on the first try. Yay! Now it's time for...

Subscriptions

Implementing is basically identical with IAP, just replace "inapp" with "subs" when geting intent. Unfortunately, like I previously mentioned, static responses don't work with subscriptions. So only way to test it is to actually purchase a monthly or a yearly subscription. First thing to do is to change all subscription prices to lowest possible. I'm sure as hell, I won't pay 20% to Google for testing $29 items... But what happens when I purchased this subscription and want to test it again? You have two choices:

  • wait until subscription expires (month/year + trial period)
  • do a factory reset again and use another test user

Now I'm like...

Srsly? I don't even...

Epilogue

This is without a doubt the worst testing environment I ever encountered... It made me so angry that I had to write this post. So, if you think about implementing IAB, prepare for a long and painful journey...