Receipt verification always returns 21002 if the Base64 encoded string contains newlines

Originator:RichWChan
Number:rdar://15548542 Date Originated:25-Nov-2013
Status:Open Resolved:
Product:iOS Product Version:7.0.2
Classification:Serious Bug Reproducible:Always
 
Summary:

When validating a receipt against `https://sandbox.itunes.apple.com/verifyReceipt`, it will fail every time with the result `{"status":21002, "exception":"java.lang.IllegalArgumentException"}` if the receipt data was base 64 encoded with a line length options (e.g. `NSDataBase64Encoding64CharacterLineLength`).

It works fine, however, when you omit the option so no newlines are added, and the itunes server will return status 0 with the associated receipt data as expected.

(It may also be worth pointing out that the old deprecated method `transactionReceipt` works fine with the new lines included.)



Steps to Reproduce:

1. In the code for verifying a receipt against Apple (similar to what is described by https://developer.apple.com/library/ios/releasenotes/General/ValidateAppStoreReceipt/Chapters/ValidateRemotely.html), do the following to generate the base64-encoded receipt data in the json you send:

```
NSData *receiptData = [NSData dataWithContentsOfURL:[[NSBundle mainBundle] appStoreReceiptURL]];
NSString *receiptString = [receiptData base64EncodedStringWithOptions:NSDataBase64Encoding64CharacterLineLength];
```

2. To verify the data against Apple, send the data in a Json to https://buy.itunes.apple.com/verifyReceipt (or the sandbox url when testing).

{ "receipt-data" : "(receiptString here)" }

e.g. to simulate it manually, we can do something like:

curl -H "Accept: application/json" \
     -H "Content-Type: application/json" \
     -X POST \
     -d '{"receipt-data": "BASE 64 ENCODED DATA GOES HERE"}' \
     https://sandbox.itunes.apple.com/verifyReceipt

3. Observe the response from iTunes


Expected Results:

The expected result, assuming that the receipt is legitimate, would be a JSON with status = 0, e.g.

{
    "status" : 0,
    "receipt" : { (receipt here) }
}


Actual Results:

iTunes always returns:

{
    "status": 21002,
    "exception":"java.lang.IllegalArgumentException"
}

(Note that, if we replace the line length option NSDataBase64Encoding64CharacterLineLength with 0, everything works fine and the result returns status 0 as expected.)

Comments


Please note: Reports posted here will not necessarily be seen by Apple. All problems should be submitted at bugreport.apple.com before they are posted here. Please only post information for Radars that you have filed yourself, and please do not include Apple confidential information in your posts. Thank you!