﻿# Direct API - ApplePay

::: tip  
This document describes the integration steps for Apple Pay using the direct API.
:::

Under the pure API integration model, merchants must build their own payment interfaces, such as the checkout page and payment results page. Furthermore, merchants must perform complex certificate configuration and encryption and decryption. Therefore, this model requires merchants to invest more in R&D costs.

## 1. Interaction Process

```mermaid
%%{init: {
  'theme': 'base',
  'themeVariables': {
    'primaryColor': '#e6f0ff',
    'primaryTextColor': '#333',
    'primaryBorderColor': '#5b9bd5',
    'lineColor': '#888',
    'actorMargin': 40,
    'noteBkgColor': '#0056b3',
    'noteTextColor': '#ffffff',
    'noteBorderColor': '#004a99'
  }
}}%%
sequenceDiagram
    participant Client as Merchant Client
    participant MServer as Merchant Server
    participant PMServer as PayerMax Server
    participant Apple as Apple

    %% Phase 1: Order and Payment Sheet
    Client->>MServer: 1.1 User places order and selects Apple Pay
    MServer->>Apple: 1.2 Merchant requests Apple Pay and invokes Payment Sheet 
using Developer Account credentials

    %% Phase 2: Card Selection and Encryption
    Client->>Apple: 2.1 User selects card/adds new card and confirms
    Apple->>Apple: 2.2 Encrypt card info using Merchant Public Key
    Apple-->>Client: 2.3 Return Encrypted Token (Payment Data)

    %% Phase 3: Payment Processing
    Client->>MServer: 3.1 Submit Payment
    MServer->>MServer: 3.2 Decrypt using Private Key
    MServer->>PMServer: 3.3 Submit Payment Request
    PMServer->>PMServer: 3.4 Complete Payment Processing
    PMServer-->>MServer: 3.5 Payment Result
```

## 2. Integration Preparation

- Follow the instructions in [Configuration and Signing](https://docs.payermax.com/en/202606-version/developer/config-settings.md) to obtain a PayerMax merchant self-service platform account, obtain the merchant appId and key, configure the asynchronous notification address, and configure the public and private keys.

- Complete the Apple Pay certificate configuration process, which mainly includes:

    - Create Merchant IDs

    - Register and validate a merchant domain

    - Create a Payment Processing Certificate

    - Create a Merchant Identity Certificate

::: warning Note:
If the merchant has already completed the Apple Pay certificate configuration process, you can proceed directly to step 3.4.
:::

### 2.1 Create Merchant IDs

Log in to Apple Developer and [Add a Merchant ID](https://developer.apple.com/account/resources/identifiers/list/merchant). Go to the corresponding module: **Certificates, Identifiers & Profiles** -> **Identifiers** -> **Merchant IDs**.

![](https://img-cdn-sg.payermax.com/public/20250811-d57f34d8-66e3-44b6-89b7-e96721aa1953.png)

### 2.2 Register and Validate a Merchant Domain

Pages using Apple Pay must be accessed using HTTPS, and the domain name of the page must have an SSL certificate. ApplePay will verify the validity of the domain's certificate during processing. Service will not be provided if the certificate expires.

1. The domain name cannot be located behind a proxy server or redirection, and must be accessible to Apple servers. For more information, please refer to [Allow Apple IP Addresses for Domain Verification](https://developer.apple.com/documentation/applepayontheweb/setting-up-your-server#3179116).

2. Multiple domains can be added to a single Merchant ID.

![](https://img-cdn-sg.payermax.com/public/20250811-dbcc1f64-e7de-4a57-969f-a5b79b088709.png)

3. After adding the domain, download the domain verification file and upload it to your server. Make sure the file is accessible at `https://yourdomain.com/.well-known/apple-developer-merchantid-domain-association.txt`. Apple verifies the legitimacy of the configured domain by accessing this file.

- Replace `yourdomain.com` with your actual domain name;

- Create a `.well-known` folder in the root directory of your web server and place the downloaded file in that folder.

![](https://img-cdn-sg.payermax.com/public/20250811-5f596f0d-338a-43a6-a1a3-62b0449cb354.png)

4. After configuring the domain verification file, verify the domain validity in the Apple Developer dashboard.

![](https://img-cdn-sg.payermax.com/public/20250811-9f43bd63-a939-45ac-957c-ad3f4d692ffc.png)

After verification is successful, the interface will display the validity period, which is equivalent to the validity period of the domain SSL certificate. The domain name certificate validity period in the example is as follows:

![](https://img-cdn-sg.payermax.com/public/20250811-d9b0b0fa-e755-4736-b364-a6bd0acea50c.png)

::: warning Note:
The time difference in the example image is due to different time zones.
:::

5. Certificate Expiration Renewal:

::: danger Special Reminder:
Apple will check for renewal of your domain name SSL certificate `30 days`, `15 days`, and `7 days` before the expiration date.
:::

- If you renew your certificate before expiration, Apple detects the updated certificate, and the domain verification is successful, you don't need to do anything else.

- If you don't renew your certificate before expiration, you'll need to re-download the domain verification file and complete verification again (see steps 2 and 3).

It's best to renew your certificate no later than `7 days` before your domain certificate expires. This way, the updated certificate information will be available during the `7-day` check.

### 2.3 Creating a Payment Processing Certificate

This certificate is used for interaction between the server and ApplePay and is a client certificate for normal HTTPS requests. For steps, please refer to the [official Apple documentation](https://developer.apple.com/help/account/capabilities/configure-apple-pay-on-the-web#create-a-merchant-identity-certificate).

#### 2.3.1 Generating a Certificate Signing Request (CSR)

There are two ways to generate a CSR: using Keychain Access, as described in the [official Apple documentation](https://developer.apple.com/help/account/certificates/create-a-certificate-signing-request), or using the command line. The following describes the second method.

1. You need to first [install OpenSSL](https://openssl-library.org/source/).

2. Generate a `private key` using the ECC algorithm and a length of `256`:

```
openssl ecparam -genkey -name prime256v1 -out applepay-ppc-ecc-256-private.key
```

You will get the file `applepay-ppc-ecc-256-private.key`. This is your `private key` and needs to be saved to your system. You will need it to decrypt the token later.

3. Generate the `CSR` file:

```
openssl req -new -key applepay-ppc-ecc-256-private.key -out applepay-pcc-ecc-256.csr
```

You will need to fill in your company information, for example:

![](https://img-cdn-sg.payermax.com/public/20250811-2b429e43-4be3-4958-ae3b-c6a392bf340b.png)

You will get the `applepay-pcc-ecc-256.csr` file.

#### 2.3.2 Uploading the Certificate

- In the **Apple Pay Payment Processing Certificate** section of the **Merchant Id** details page, click **Create Certificate** to create the certificate:

![](https://img-cdn-sg.payermax.com/public/20250811-2e75f5e6-66ab-4f3e-be89-e6cb9a4c3d16.png)

- Select the `CSR file` created in the previous step:

![](https://img-cdn-sg.payermax.com/public/20250811-757139e2-589d-48a5-b24b-ca51d794be97.png)

- After the upload is complete, click **Continue**. Apple will generate a certificate upon success. Click **Download** to download the certificate.

![](https://img-cdn-sg.payermax.com/public/20250811-8edeee3e-54b4-4354-89b8-dbfeb8fb3230.png)

### 2.4 Creating a Merchant Identity Certificate

Calling Apple Pay's `create session` API uses SSL mutual authentication and requires a client certificate, the `Merchant Identity Certificate`. Creating this certificate also requires steps such as `generating a private key` and `CSR`.

#### 2.4.1 Generate a Private Key

Here you will generate an `RSA 2048` private key:

```
openssl genrsa -out applepay-mic-rsa-2048-private.key 2048
```

You will get the `applepay-mic-rsa-2048-private.key` private key file. Save this private key; you will need it later when calling the API.

#### 2.4.2 Generate a CSR

```
openssl req -new -key applepay-mic-rsa-2048-private.key -out applepay-mic-rsa-2048.csr
```

Here again, you need to fill in the certificate owner's information. Once completed, you will get the `applepay-mic-rsa-2048.csr` file.

#### 2.4.3 Uploading the CSR

Open the **Merchant Id** details page and find the **Apple Pay Merchant Identity Certificate** section:

![](https://img-cdn-sg.payermax.com/public/20250811-351c883b-7321-40a6-82e7-0502bbaed159.png)

Click the **Create Certificate** button, select the CSR file generated in the previous step, and then click **Continue** to obtain the certificate.

![](https://img-cdn-sg.payermax.com/public/20250811-a307447c-5c9a-45dc-92d6-79e4efeb5ef2.png)

Save the certificate; it will be used during subsequent payment processing.

## 3. Integration Process

Merchants must obtain their own Apple Pay Token, decrypt the Token to obtain the card information, and then pass the decrypted card information to PayerMax.

::: warning Note:
If merchants have already integrated Apple Pay at their checkout counters, they can proceed directly to step 3.4.
:::

### 3.1 Obtaining an Apple Pay Session When Initializing the Page

Reference Links:

- [Creating an Apple Pay Session | Apple Developer](https://developer.apple.com/documentation/applepayontheweb/creating-an-apple-pay-session)

- [Requesting an Apple Pay payment session | Apple Developer](https://developer.apple.com/documentation/applepayontheweb/requesting-an-apple-pay-payment-session)

::: warning Note:
When calling Apple's API to obtain a `session`, you must use the SSL client certificate, which is the `Merchant Identity Certificate` created earlier.
:::

### 3.2 Obtaining the ApplePay Token for User Payments

You can obtain the encrypted token from the `onpaymentauthorized` callback method of `session`. For details, please refer to: [onpaymentauthorized | Apple Developer](https://developer.apple.com/documentation/applepayontheweb/applepaysession/onpaymentauthorized).

```js
...
this.session = new window.ApplePaySession(APPLE_PAY_VERSION, this.payRequest);

...

this.session.onpaymentauthorized = (event) => {
// event.payment.token is the encrypted token
};
...
```

An example of the obtained token is as follows:

![](https://img-cdn-sg.payermax.com/public/20250811-58e6d674-4299-4e53-b2c4-dea4d1a1573b.png)

```json
{
    "paymentData": {
        "data": "",
        "signature": "",
        "header": {
            "publicKeyHash": "",
            "ephemeralPublicKey": "",
            "transactionId": ""
        },
        "version": "EC_v1"
    },
    "paymentMethod": {
        "displayName": "Visa 8007",
        "network": "Visa",
        "type": "debit"
    },
    "transactionIdentifier": ""
}
```

### 3.3 Decrypt Apple Pay Token

- For details on `Apple Pay Token` structure, please refer to: [Payment Token Format Reference | Apple Developer](https://developer.apple.com/documentation/passkit/payment-token-format-reference);

- To decrypt the token, you need to use the `Payment Processing Certificate` created earlier;

- An example of decrypted `data` is as follows:

```json
{
    "applicationExpirationDate": "280228",
    "applicationPrimaryAccountNumber": "42710600003562",
    "currencyCode": "124",
    "deviceManufacturerIdentifier": "040010030273",
    "paymentData": {
        "eciIndicator": "5",
        "onlinePaymentCryptogram": "/wAAADcAv7mhHpQAAAAAgPdgE4A="
    },
    "paymentDataType": "3DSecure",
    "transactionAmount": "5564"
}
```

### 3.4 Calling PayerMax for Payment

[Create payment/orderAndPay API](https://docs.payermax.com/api.html?docName=New%20Version&docVer=v1.0&docLang=en#/paths/aggregate-pay-api-gateway-orderAndPay-delSuffixStart1/post) interface request, where the key fields are:

- `paymentDetail.paymentMethodType`: `APPLEPAY`

- `paymentDetail.applePayPaymentData`: Decrypted payment information

Interface request example:

Pass the decrypted card information from the `Apple Pay Token` to the `data.paymentDetail.applePayPaymentData` field.

```json
{
  "version": "1.5",
  "keyVersion": "1",
  "requestTime": "2022-02-25T09:23:06.473+00:00",
  "appId": "6666c8b036a24579974497c2f9800001",
  "merchantNo": "020213834421234",
  "data": {
    "outTradeNo": "Test1645780876511",
    "subject": "this is subject",
    "totalAmount": 1,
    "currency": "AED",
    "country": "AE",
    "userId": "userId001",
    "integrate": "Direct_Payment",
    "expireTime": "1800",
    "paymentDetail": {
      "paymentMethodType": "APPLEPAY",
      "buyerInfo": {
        "firstName": "James",
        "lastName": "Smith",
        "phoneNo": "903124360628",
        "email": "james@google.com",
        "clientIp": "124.156.108.193",
        "userAgent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/96.0.4664.110 Safari/537.36"
      },
      "applePayPaymentData": {
          "applicationExpirationDate": "2312",
          "applicationPrimaryAccountNumber": "4111111111111111",
          "currencyCode": "USD",
          "deviceManufacturerIdentifier": "A1B2C3D4",
          "paymentDataType": "3DSecure",
          "transactionAmount": "100.00",
          "paymentData": {
            "onlinePaymentCryptogram": "Aa0KZXFURkhF...",
            "eciIndicator": "07"
          },
          "network": "VISA",
          "type": "credit",
          "displayName": "Visa 0492"
     },
    "goodsDetails": [
      {
        "goodsId": "D002",
        "goodsName": "Key buckle",
        "quantity": "2",
        "price": "0.5",
        "goodsCurrency": "AED",
        "showUrl": "http://ttt.com",
        "goodsCategory": "电脑"
      }
    ],
    "shippingInfo": {
      "firstName": "James",
      "lastName": "Smith",
      "phoneNo": "903124360628",
      "email": "xxx@google.com",
      "address1": "address1",
      "city": "GAZIOSMANPASA/ANKAR",
      "country": "TR",
      "zipCode": "06700"
    },
    "billingInfo": {
      "firstName": "James",
      "lastName": "Smith",
      "phoneNo": "903124360628",
      "email": "xxx@google.com",
      "address1": "address1",
      "city": "GAZIOSMANPASA/ANKAR",
      "country": "TR",
      "zipCode": "06700"
    },
    "riskParams": {
      "registerName": "lily",
      "regTime": "2023-07-01 12:08:34",
      "liveCountry": "VN",
      "payerAccount": "987654XXX",
      "payerName": "lily",
      "taxId": "1234567890"
    },
    "language": "en",
    "reference": "020213827524152",
    "terminalType": "WAP",
    "frontCallbackUrl": "https://xxx.com",
    "notifyUrl": "https://yyy.com"
  }
}
```

Interface response example:

```json
{
  "code": "APPLY_SUCCESS",
  "msg": " Success.",
  "data": {
    "outTradeNo": "a1234934974321",
    "tradeToken": "T2025051210335071234567",
    "status": "SUCCESS"
  }
}
```
