Apple’s 2021 updates to managing in-app purchases from the server

Yesterday, we covered new StoreKit 2 features that were announced on this year’s WWDC. Today, we’re going to discussing the event’s main takeaways by summing up what news Apple has shared regarding the management of in-app purchases from servers. Let’s dive in.

Should You Build Your Server?

Apple emphasizes that having a server is very useful, primarily because it helps track statuses. Overall, there are five main benefits of building your server:

  1. When you have a server, Apple can notify you, in real-time, whenever the status of your in-app purchases changes. 
  1. Also, you can call the company on-demand to check the status at any time with the help of server-to-server APIs.
  1. Having a server lets you validate customer access to content. Even if their device is offline, or the status changes outside the app.
  1. With your server, you’ll know if your customer is still subscribed after a renewal.
  1. Finally, you’re able to track refunds for in-app purchases. For instance, if the coins they bought inside your game have been refunded.

If you haven’t built a server just yet and are only considering it right now — these are some strong reasons you can place in the “pros” column.

Updates to Managing In-App Purchases in Your Server

Today, server-to-server communication involves the use of APIs like verifyReceipt or frameworks like App Store server notifications. However, Apple clearly had the goal of easing this communication process for developers. For this reason, they’ve implemented five changes to the server-side. These updates are precisely what we are going to focus on in today’s article.

Validating access with App Store receipts

Currently, Apple’s receipts are in the unified app receipt format. To get the JSON version you either have to perform an on-device receipt verification in your app or call the server-to-server verifyReceipt endpoint. When doing the latter, the decoded receipt you get looks like this:

It seems Apple figured that this amount of information might be overwhelming and decided to introduce JWS signed transactions. This will certainly enhance security, become easier to decode, and provide the ability to verify the signature without your server having to contact Apple.

Now, the JWS transaction info will look like this:

As you may notice, some data types have changed from the strings in the receipt we showed above. Instead, they are now more appropriate data types, like numbers or booleans. Date formats have been reduced to only milliseconds since the epoch time format. Moreover, a “type” field has been added. It tells you which content type the transaction applies to.

The last two fields are a simplification of some info from the previous receipt. Specifically, isTrialPeriod, isIntroOfferPeriod, promotionalOfferIdentifier, and offerCodeRefName have been merged into offerType and offerIdentifier.

offerType tells you the type of offer your customer has applied to this period:

1 = intro offer

2 = subscription offer

3 = offer code

If the value is 2 or 3, you’ll also see information in the offerIdentifier field. It’ll either contain the promotionalOfferID or offerCodeRefName.

To verify the signature portion of the signed transaction info you’ll need to use:

  • The header portion of the JWS transaction info
  • The alg claim to determine what signing algorithm was utilized
  • The certificate chain in the array in the x5c claim
  • A cryptographic library to verify the signature of the signed transaction info

That’s pretty much it for this section. You now know the changes Apple has implemented for App Store Receipts. Time to move on to checking the status with APIs.

Checking status with App Store server APIs

Apple wanted to build APIs that would help you on your server. Thus, they introduced a new library of App Store Server APIs. These will provide new features that weren’t available before. The two brand-new APIs are:

Subscription Status API

Provides the latest status of your auto-renewable subscriptions, indicated by an originalTransactionId. With this API, you’ll get a quick answer about your subscriber’s status.

As you can see, the status field gives you a quick answer about the status of the subscription:

1 = active subscription

2 = expired subscription

3 = the subscription is in the billing retry period

4 = the subscription is in the grace period

5 = the subscription access has been revoked

Thanks to the status field, you can quickly get an answer about the subscription.

In-App Purchase History API

The in-app purchase history API will provide the history of all transactions for your app. The API will be paginated to control the size of the response you receive.

// In-App Purchase History API

// request
GET /inApps/v1/history/{originalTransactionId}

// response
{
   "bundleId":"co.oceanjournal",
   "appAppleId":1231451896,
   "revision":"8a179756-e913-42fc-8629-7b051f9e1134",
   "hasMore":true,
   "environment":"Production",
   "signedTransactions":[
      "ewogICg..",
      "ewogICg.."
   ]
}

// next page request 
GET /inApps/v1/history/{originalTransactionId}?revision=8a179756-e913-42fc-8629-7b051f9e1134

It’s important to note that the App Store Server APIs will be consistent with one another by having the following features:

  • JWT authentication
  • JWS transactions
  • JSON requests and responses
  • Based on orginalTransactionId

Before moving on, here are the key take-aways for App Store Server APIs:

  • Separate status and history functions
  • Require only originalTransactionId
  • Take the signed transaction and store the individual fields
  • Don’t need to store the signed transaction

Passive tracking of status with App Store server notifications

App Store server notifications let you receive notifications when the status of one of your transactions changes. Once received, the status can be updated immediately. Moreover, you don’t need to call Apple for status. Overall, they are powerful tools for your server to leverage.

This year, however, App Store server notifications received an upgrade in the form of easy-to-use signed transactions. From now on, only one notification per subscription event will be sent. In addition, the payload will be signed using JWS to enhance security and updated based on the signed transaction. Finally, you’ll also be able to opt into the V2 notifications when you’re ready.

Besides the new notification types, Apple is also adding a substate field. Primarily, to help you narrow a more general notification type to a specific user action.

V2 notification types, combined with their applicable substates, result in over 20 different custom lifecycle events. Specifically, these:

First Time PurchaseOffer RedemptionUpgrade Offer Redemption
ResubscribeNew Purchase OfferAuto-Renew Success
Soft CancelRedemptionAuto-Renew Fails
DowngradeResubscribe OfferExit Grace Period
UpgradeRedemptionAuto-Renew Recovery
Disable Auto-RenewDowngrade OfferExit Billing Retry Period
Re-Enable Auto-RenewRedemptionExpired
Expired due to PricePrice Increase AcceptedFamily Member Lost
IncreaseRefundAccess
Price Increase PendingHard Cancel

As soon as you look at the notification type you’ll get a general idea of what has changed in your purchase. However, looking at the substate will help you get more details.

Managing family sharing

Having covered validating status with receipts, checking it with APIs, and tracking it with notifications, it’s time to move on to managing family sharing and discover the changes in this area.

In the image below, you can see the new notifications for family members.

The new changes ought to make managing family sharing for in-app purchases even easier for developers. Especially, when coupled with the existing family sharing functionality.

Testing in sandbox

Finally, we’ve reached the final update that Apple introduced at the WWDC.

Now, Apple will allow the integration with the new App Store server APIs and App Store server notifications in sandbox before production. Hence, the previously discussed APIs will be fully testable in sandbox.

Besides these features, which are already live, Apple is also enabling you to add a sandbox-specific notification URL in App Store Connect.

Moreover, there’ll be further enhancements:

  • Clear purchase history
  • Change sandbox account region
  • Adjust subscription renewal rate
  • Enhance verifyReceipt security for TestFlight

Will You Leverage the New Updates to In-App Purchases On Your Server?

We hope you’ve enjoyed our overview of Apple’s comprehensive WWDC video

The Qonversion team is closely following all of Apple’s new developments and updates and makes sure to consider each and every one of them within the delivered products and services.

More articles from WWDC 2021: