A fake IAP receipt can pass Apple store's validating

We found a new IAP-free plug-in on jailbreak device could generate a receipt which couls pass the validating receipts with the App Store.


We pretty sure some purchases are fake, but when we verify those receipt with App store, the status show those receipt is valid, status is 0, no error code, the only different is no in-app feild in the response’s JSON object.


following is the response JSON of a fake receipt, ( i had replaced some data, xxxxxxx is our App's apple id, com.yyyy.yyyy is correct bundle_id)


{"environment":"Production","status":0,"receipt":{"app_item_id":xxxxxxxxx,"receipt_type":"Production","request_date_pst":"2015-07-06 03:24:47 America/Los_Angeles","original_purchase_date_ms":"1402181168000","request_date":"2015-07-06 10:24:47 Etc/GMT","original_purchase_date":"2014-06-07 22:46:08 Etc/GMT","adam_id":xxxxxxxxx,"original_purchase_date_pst":"2014-06-07 15:46:08 America/Los_Angeles","in_app":[],"download_id":22016699383110,"application_version":"2.0.5","version_external_identifier":812437604,"bundle_id":"com.yyyy.yyyy","original_application_version":"1.0.0","request_date_ms":"1436178287898"}}


how can it pass App Store's validating?

Are you sure it is not a receipt from an iOS6 device ?


on iOS6 the receipt format is different, no in_app as it can only contain a single purchase, but you still have the main fields that are in in_app just at the receipt level:


original_purchase_date;

original_purchase_date_ms;

original_purchase_date_pst;

original_transaction_id;

product_id;

purchase_date;

purchase_date_ms;

purchase_date_pst;

quantity;

transaction_id;


Your verification process needs to handle both formats. All I do is check if the receipt contains item_id and no in_app, and if so I move the details into a new in_app item and process it the same as iOS7+

In the cases where I've seen this reported, the receipt was a valid receipt made with a different in app purchase app. None of the date/time stamps matched nor did the productIdentifier nor adamID. Are you seeing a "fake" receipt being returned that has valid data being returned??


For this case, the application receipt should show the in_app array does not include this purchase. When this happens, I refer you to Tech Note 2413, In-App Purchase FAQ

<https://developer.apple.com/library/ios/technotes/tn2413/_index.html#//apple_ref/doc/uid/DTS40016228-CH1-RECEIPT-MY_APP_VALIDATES_ITS_RECEIPT_WITH_THE_APP_STORE_VIA_PAYMENTQUEUE_UPDATEDTRANSACTIONS__AFTER_A_SUCCESSFUL_PURCHASE__HOWEVER__THE_RETURNED_RECEIPT_CONTAINS_AN_EMPTY_IN_APP_ARRAY_RATHER_THAN_THE_EXPECTED_PRODUCTS_


rich kubota - rkubota@apple.com

developer technical support CoreOS/Hardware/MFI

This appears to be the receipt that will come with the app before any IAP is purchased. All apps have a receipt (although sometimes it needs to be refreshed). Apps that purchase IAPs have a receipt that includes an IAP purchase when StoreKit calls the uipdatedTransactions method. Perhaps this user is trying to fake a purchase of an IAP by injecting a call that appears to come from StoreKit falsely claiming that they have made a purchase of an IAP. Your app responds to that call by grabing its receipt (which will not show any IAP purchases) and sending it to your servers for validation. Your servers then validate the receipt, as they have, and should discover that no IAP has been purchased, as you note above. Everything is working as it should - assuming you don't credit the user with the IAP they didn't purchase.

I believe that reference is wrong. I believe the receipt is always refreshed when StoreKit has called updatedTransactions. Refresh receipt is necessary only when the app itself is loaded into the device or when the user is claiming an autorenewable subscription without having gotten a call from StoreKit.

Any updates on this issue?

We see something similar

A fake IAP receipt can pass Apple store's validating
 
 
Q