Apple Pay provides an easy and secure way for people to make payments in your iOS, iPadOS, and watchOS apps as well as on the web. We'll take you through the entire Apple Pay implementation workflow – including how you can signal support for Apple Pay, request payment and handling updates, and add order details at the end of a payment flow to help people track their purchases.
Hello. My name's Katie, and welcome to this session on implementing Apple Pay and order tracking.
Let's look at the agenda for today.
First, I will take you through the basics needed to get started with Apple Pay.
Then I will show you how to create a payment request and respond to changes in the payment sheet.
You can also add order details at the end of the payment flow so the user can track their order.
The order details will enable Wallet to retrieve an ordered package, which I will show you how to build.
Finally, I will show you how to update your order.
So let's get started.
Apple Pay is the easy, secure, and private way to pay.
If you're a developer of a website or app, you can use Apple Pay to improve your conversion and user experience.
There are two essential items to create to get started.
The first is an identifier which uniquely identifies you as a merchant able to accept payments.
To create one, you should head to the identifier section of the Apple Developer portal.
The conventional format is in reverse DNS, beginning with the word "merchant." Use your spiffy new merchant identifier to create a payment processing certificate.
Put very succinctly, Apple Pay encrypts each payload with your registered merchant identifier and public certificate.
This payload can then be decrypted and processed on your end.
You can then return whether the payment succeeded or failed.
Talk to your payment service provider for the specifics on processing the payment.
There are different steps to setting up Apple Pay between apps and websites.
To set up Apple Pay for use in your app, simply navigate to the Signing & Capabilities tab in Xcode and add your merchant identifier under the Apple Pay capability.
If you're building a website and want to set up Apple Pay there, there are some additional steps required.
You must register the domains that will process the Apple Pay transaction, which can be done in the identifier section of the Apple Developer portal.
While you're there, you can create an Apple Pay Merchant Identity Certificate linked to the merchant identifier you made earlier.
This certificate is used to authenticate your sessions to Apple Pay servers.
Whether you're integrating an app or on web, if you're working with an e-commerce platform or a payment service provider, check out their specific instructions as they may simplify some of these steps.
Now let's look at how to actually implement Apple Pay.
Before displaying Apple Pay-related content, you should check whether the user is able to make payments with the current configuration.
Capabilities denote which types of payments the sheet can currently accept, such as 3D Secure or credit or debit cards.
You will later specify the capabilities you accept when you configure the payment request.
You can check for networks the user already has available, keeping in mind that the user is able to add more cards if none are currently available.
Now that you know your user can make payments, it's time to display the Apple Pay button.
Make sure to select the best call to action and button type in alignment with the action the user needs to take.
Display the Apple Pay button prominently, above the fold, and as the first payment option.
The Apple Pay button is fully localized and can also be adapted for the user's settings.
To display an Apple Pay button in your app with the UIKit, firstly, create a PKPaymentButton, specifying the type and style of the button.
The type describes the kind of payment; for example, Donate with Apple Pay or Continue with Apple Pay.
The style controls the appearance of the button, like whether it's light or dark.
Use the automatic style for the button to dynamically change based on the user's settings.
To add one, first, load the button script into your web page on your content delivery network.
You can also use CSS to further customize the button's dimensions.
We need to create a payment request so that the payment sheet knows what to expect.
In apps, we can do that by creating a PKPaymentRequest.
There are many fields that can be set on the request depending on your needs, but the essentials include the merchant identifier you created earlier, the types of payments you can accept, the country and currency code of the payment.
Specify the networks that you accept payments from.
This should be done in order of preference so Apple Pay and choose the preferred network for cobatched cards.
Finally, summary items are included as part of this transaction.
Let's take a closer look at summary items.
To do that, we can imagine that you run an online pet goods shop and would like to offer customers the ability to check out their orders with Apple Pay.
These summary items consist of the total cost of the items your customer has selected minus any discounts.
They should help to break down the cost to a customer.
The last summary item is always the total, and the label for this total must be the company receiving the payment.
It is required that there should be at least one item set in the array here.
Now, we're ready to display the payment sheet.
First, we create a PKPayment AuthorizationViewController, sending in the request we set up moments ago.
You are in charge of presenting viewController that is returned to you.
Now, let's have a look at this delegate we're setting.
The PKPaymentAuthorization ViewControllerDelegate is how the sheet communicates changes to you, such as when the user selects a new email address or when they authorize the transaction.
You should respond to the changes that are appropriate to you; however, you are always responsible for dismissing a payment sheet and should implement paymentAuthorizationViewControll erDidFinish to handle this.
You should always try to return errors to the user as early as possible with a helpful description to help them resolve the issue.
For example, if there is a problem with the user's new shipping address, you should return an error as part of the PKPaymentRequest ShippingContactUpdate.
didAuthorizePayment is called when the user is happy with the details and uses Face ID, Touch ID, or their passcode to proceed with the transaction.
You need to handle the PKPayment sent to you either yourself or by passing it onto a payment processor.
You must call the handler with an appropriate result.
In iOS 16, we introduced the ability to easily create an Apple Pay button in SwiftUI.
All you need to do is pass in the payment request when creating a Pay with Apple Pay button and the payment sheet will display automatically when the user interacts with the button.
The type of the button, and optionally, the style can also be set.
The payment authorization change is analogous to the delegate we looked at on the previous slide.
Let's look at how to respond to user updates.
The user has just authorized a payment and the payment authorization phase change informs your app of this Your app then sends the payment information to your server and asks it to handle the payment.
Check whether the server result indicates success and handle any error returned by your server, ensuring you still call the result handler with an appropriate error.
If the server result does indicate success, complete the payment with an appropriate authorization result.
The result you return must contain what happened when attempting to process the payment; for example, if the postal address is invalid.
In most cases, the payment will have either succeeded or failed.
If the payment did fail, you can also return one or more errors ordered by importance.
That will be displayed to the user so they can try to transact again.
This authorization result can optionally contain order details, which we will look into shortly.
Now let's have a look at how to do this on the web.
The W3C payment request API is an open standard that enables you to handle payments on the web.
You can create the PaymentRequest object and populate it with methods where you can specify that Apple Pay is available; details which contains information about the transaction, like the total and the shipping methods; and options which specifies what information you want the user to provide.
You'll have to complete merchant validation on your server, so create a new merchant session and pass it into the complete function.
Just like native, you can respond to interactions the user makes in the payment sheet and you'll also need to handle the payment response when the user authenticates.
Now that you're all integrated with Apple Pay, we can start actually building an order.
In iOS 16, we introduced order tracking.
Your customers can now see order details and tracking information, all from within the Wallet app.
They'll be able to know instantly when they can pick up their orders, if the orders have been delivered, if there have been any problems, or received notifications.
So now that you've successfully integrated your pet shop business with Apple Pay, you may also like to add order tracking.
Let's see how.
You'll notice that getting started with orders is similar to setting up Apple Pay.
Head back over to the Identifiers section of the Developer portal and create an order type identifier.
This identifies your organization as an entity that provides order information.
Like with the merchant identifier, we recommend using a similar reverse DNS-style naming scheme, this time prepending the word "order." Next, create an Order Type ID certificate from the certificate section of the developer portal.
You will use a Certificate to build order packages, update orders, and send notifications.
Now that we've got that set up, we can add an order to Wallet from right within the Apple Pay purchasing flow.
To do that, let's take a look back at our simple payment processing flow you should recognize from earlier.
We already know your server is sent payment information for processing.
If the payment is successfully processed, your server should create an order.
To support order tracking in the result you return, you should also include some details about the order you created.
These order details enable the device to asynchronously request the order from your server.
Your server then turns the order package to the device, which will then be displayed in Wallet.
For now, let's take a closer look at the order details you'll need to return as part of the PKPayment authorization result.
The order details is comprised of four fields.
The order type identifier is simply the one you created earlier.
You should generate a way to identify your order, but it must be unique within the scope of your order type identifier.
Include the URL for your web service.
Finally, your server needs to generate a secure authentication token.
This is a shared secret between the user's devices and your server.
The device will use this token to authenticate itself when requesting the order package.
This example initially looks very similar to the normal payment authorization flow we saw earlier.
Let's add the order details in.
First, grab them from the serverResult, then create a PKPaymentOrderDetails object, setting the Order Type ID, order ID, web service URL, and the authentication token.
Assign this to your PKPayment authorization result.
On the web, it's also simple to add your order details using the W3C Payment Request API.
Like before, extract the order details from the server result.
Return these order details and the data you complete the payment with.
After the order details have been returned the device, those details will be synched across each of the user's devices.
Each device will request the order package from your server, providing the order details.
Verify the authentication token by matching it to the one you sent with the order details.
Provided the authentication token matches, return the order package to the device.
Now the order is ready to display in Wallet for that device.
You should attempt to repair your order as soon as possible so that it's available as soon as the device requests it.
If your server fails to return the order, the device will attempt multiple retries with an exponential backoff.
We've seen this order package referenced many times now, but what exactly is it comprised of? Orders are distributed as order packages.
They contain everything needed to display your order to the user and prove it's from you.
An order package contains a JSON dictionary that describes your order, images like your logo, and an inline image for each item in your order.
Refer to the Human Interface Guidelines and the referral sources for guidance on creating images.
Also include localized resources like strings files.
Keep an eye out for the total order size and only include what's relevant.
All of this content is described in another JSON dictionary called the "manifest." You can think of it like a table of contents.
It contains a reference to all the files in the order package.
The key for an entry is the relative file path and the value is the files' SHA256 checksum which is a different checksum to what's used in parses.
Now what we need to do is sign the package to prove its authenticity.
The signature verifies that the order package originates from a trusted source -- you.
It is a detached cryptographic message signature of the manifest, same as parses.
Sign the manifest with the private key associated with your Order Type ID certificate and with the Apple Worldwide Developer Relations Intermediate Certificate, ensuring you use the renewed version of the certificate.
To finish building the order, simply compress the package and change the file extension to order.
Now it's time to update your order.
Order information often changes over time; for example, the order of pet goodies your customer made earlier is now on its way.
Supporting automatic updates enables you to deliver this update to your customer quickly and securely.
Your customer now has their pet supplies order in Wallet, and the order indicates support for updates, so the device will register with your web service.
Later on, the customer's order is now out for delivery, so your server will notify all registered devices using the registration information.
When the customer's device receives the push notification, it will now ask for the order from your server.
Your server then returns the updated order package to the device.
Now that we know how a basic order flow works, let's break down the exact steps you'll need to take to support order updates.
First, indicate that you support updates for an order.
It's super easy to tell Wallet that your order supports updates; you just need to include two pieces of information in the order package.
In the order.json, add the webServiceURL you'd like.
This would be the same one you provided in the order details.
Also add an authenticationToken field, which Wallet will use to prove its authenticity when requesting order updates.
You'll have to manage when devices ask to add or remove themselves from being registered.
Your server must be able to handle adding or removing registration information.
It must be able to find the devices that registered for updates to an order.
This enables your server to notify these devices when you update the order.
Your server must also be able to find the orders that a device registered for so that your server knows which updated orders are relevant for that device.
There are different ways you could structure this information.
One way will be to use a relational database with two entities -- one for devices and one for orders -- and a many-to-many relationship for registrations.
When the order is updated, your server needs to notify the registered devices.
So your server needs to grab the relevant devices based on the stored registration information, then send a push notification to each device using its push token.
The Order Type ID doubles as push topic, and the payload should be empty.
You can use the Order Type ID certificate to communicate with APNs.
One more thing to note about notifications is that the enum property changeNotifications can be set on the order package to customize how you'd like order notifications to be delivered.
The options available are enabled, which will always send order update notifications and is the default value.
If you don't want Wallet to duplicate your notifications, set disableIfAppInstalled which will not send notifications if the user has apps installed that you listed in the order package.
The registered devices will each ask for the new order package which your server will provide.
When a device receives a push notification, it doesn't know yet which orders have changed, as the push notification is empty.
Together with your server, the device figures out which orders have changed since the last time it requested them.
Use the registration information your server stored to find relevant orders, then return their IDs.
Keep track of update times and include a modification tag in your response to limit the number of Order IDs returned by future requests.
You can use a timestamp, for example.
The value is opaque to the device.
The device will provide the modification tag the next time it requests changes.
Finally, the device will request the latest package for each order your server indicated is updated.
We've covered a lot today.
Follow these practices to provide the best customer experience possible.
When implementing Apple Pay, offer express checkout by displaying the Apple Pay button on the product or cart page.
Users can select shipping options and addresses directly in the payment sheet and check out without typing anything.
When implementing order tracking, use the knowledge you have about your customer preferences to provide relevant localizations only.
Additionally, be mindful of the number of assets you include to keep the order package size small.
When you update an order, promptly notify devices that registered for updates to it.
Orders in Wallet should match the actual state of the order.
Make sure to also check out the Human Interface Guidelines for order tracking and also in displaying the Apple Pay button.
Today, I've covered getting started implementing Apple Pay through the building and updating an order.
This talk is intended to introduce you to implementing Apple Pay and order tracking, but you should definitely check out the documentation linked in the session notes to dig into more details.
Additionally, you can check out our most recent WWDC video.
Thank you so much for your time today.
And I hope you enjoy the rest of your day.
Looking for something specific? Enter a topic above and jump straight to the good stuff.
An error occurred when submitting your query. Please check your Internet connection and try again.