I am implementing IAP in a simple mobile (IOS and Android) game.
I am not planning on having a backend for validating and remembering in app purchases.
I have only non-consumable in app purchases.
I have configured the CrossPlatformValidator to validate receipts locally.
After a lot of reading, and most of the implementation - I have a few questions:
Is it a good idea after validating a product receipt, to check that the receipt contains the expected product id? i.e.
Should I check all products for receipts (and validate their receipts as mentioned above) in the UnityIAP OnInitialize() callback?
I’m thinking this would be a sensible way to handle revoked purchases.
For IOS, when would I call RefreshAppReceipt?
From reading I understand that I need to call RestoreTransactions in response to a button press to allow the user to restore purchases for new installs. So what is RefreshAppReceipt for? I’m hoping i can ignore it.
The workflow for Apple app store “Ask to buy” purchases seem a little … screwy. I get that I should notify the user that the purchase has been deferred in the callback registered via RegisterPurchaseDeferredListener. In Ask to Buy purchases, what happens if the user closes and then reopens the app before the purchase has been confirmed by a guardian? Will the product have a receipt that somehow is not in a completed state?
Let me add you some quick notes to keep you going! Note that I haven’t used Unity IAP anytime but the below answers hold good irrespective of the plugin used.
Once after you validate the receipt, It’s fine to have the extra check of productId check as it doesn’t hurt any. The crucial part is the receipt got validated or not. Also before validating, first check if hasReceipt is true or not. This will be set to false if the purchase gets revoked (as per previous threads on the same topic).
You can validate the purchases once after your Restore Purchases action.
Ignore if you don’t have time to make it perfect in sandbox/testing environment. RefreshAppReceipt call isn’t required in production as there will be appStoreReceiptURL value always.
It’s a nice move as in new Store Kit 2, it’s not required to validate the purchase as iOS does it internally. And validating on your server will be optional. Where as in the current Store Kit unity IAP is using, it’s recommended to validate on your server. But, that’s fine as you just got started and local verification will work for you and by the time you really need validation, Store Kit 2 version in unity IAP may be out!
If the transaction is not marked complete, it will still be in the transaction queue. So, as per your scenario, it won’t get lost even if the app closes. Once you confirm its complete in your ProcessPurchase callback, thats when the transaction get’s closed.
No problem. Thanks for the tip. This was why I put receipt validation into the OnInitialize routine. It seemed to me that just checking hasReceipt in OnInitialze doesn’t actually check that the receipts are in any way valid, or even for the products that I am expecting. So I’m still not clear on whether I should validate all receipts in OnInitialize.
My understanding was that once i request that the purchases be restored on IOS, the ProcessPurchase callback would get called for each purchased item. In which case the receipts should get validated in ProcessPurchase.
So if the transaction hasn’t been closed I should expect the product to have no receipt? That will make life easier.
No no no…
Lets say Transaction has three phases. Purchasing, Purchased and Finished.
Once the product is bought, it enters the Purchased phase, but it won’t enter the finished state yet. It enters finished state once you say you are done rewarding the entitlements to the user.
In Purchased Phase you will have the receipt.
This is because, this is the phase where you validate the purchase (locally or on your server) and reward the entitlement based on the verification status and then inform to finish the transaction. Imagine, if finished state doesn’t exist, there is no way to get back the transactions which are lost when a crash happens. So until you mark the transaction finish, iOS keeps sending you the transaction and once you reward the entitlements, just inform its complete and the transaction is removed from the transaction queue.
I think we’re talking about different things. Your response was in relation to my question about ask to buy purchases. If the parent hasn’t responded, my code won’t have been asked to complete the transaction yet. In this case will there be a receipt?
Ok, got it. If the transaction is not yet approved, there won’t be any receipt. Actually, this phase is called purchasing/deferred/pending. During this period the transaction won’t have the receipt as there is no purchase happened.