HPP Outcomes
This page describes how to determine the final payment outcome after a customer completes (or abandons) the HPP flow.
Result Page Behaviour
Section titled “Result Page Behaviour”After the transaction is processed, the result page behaviour depends on the resultPage value set in your Payment Request:
resultPage: "show"(default): HPP displays a hosted result page. The page shows transaction details on approval, or a decline/failure message with the option to retry (if attempts remain). WhenredirectUrlis provided, the result page includes a link back to the merchant site.resultPage: "redirect": On approved transactions, the customer is automatically redirected to the merchant’sredirectUrl. On declined or failed transactions, the hosted result page is displayed.resultPage: "none": Accepted API value.
Server-Side Reconciliation
Section titled “Server-Side Reconciliation”Critical: Do not rely on the customer reaching your redirect URL to confirm payment. Always verify the outcome server-side using webhooks or polling.
Option 1: Webhooks (Recommended)
Section titled “Option 1: Webhooks (Recommended)”Subscribe to transactions and payment_requests webhook events. When a payment completes via HPP, you will receive:
- A transaction webhook with the transaction outcome.
- A payment request webhook with the updated
paymentRequestStatus.
For webhook setup, signing verification, and payload structure, see Webhooks.
Webhook flow:
sequenceDiagram
participant GP as Single API
participant Webhook as Your Webhook Endpoint
participant DB as Your Database
GP->>Webhook: POST callbackUrl (X-Signature + JSON payload)
Webhook->>Webhook: Verify X-Signature (HMAC-SHA256)
alt signature valid
Webhook->>Webhook: Parse event and payload
alt event = 'transactions'
Webhook->>DB: Persist transaction state
else event = 'payment_requests'
Webhook->>DB: Persist payment request state
end
Webhook->>GP: HTTP 200 OK
else signature invalid
Webhook->>GP: HTTP 401/403
end
Option 2: Polling (Fallback)
Section titled “Option 2: Polling (Fallback)”If webhooks are not available, poll the Payment Request after a reasonable delay:
GET /paymentrequests/{paymentRequestId}— checkpaymentRequestStatusand locate the transaction.GET /transactions/{transactionId}— verify final status, amount, and currency.
How to locate the transaction:
- Successful payment:
paymentRequestStatusiscompletedandtransactionResultcontains the transactionidandlocation. - Failed payment:
paymentRequestStatusiscompleted,transactionResultis not populated, andtransactionAttemptscontains the failed transaction details.
You can also retrieve transactions via GET /transactions?paymentrequestid={paymentRequestId}.
Polling flow:
sequenceDiagram
participant Server as Your Server
participant API as Single API
Server->>API: GET /paymentrequests/{paymentRequestId}
API-->>Server: Payment Request (status + transactionResult)
Server->>Server: Extract transactionId
Server->>API: GET /transactions/{transactionId}
API-->>Server: Transaction (final status, amount, codes)
Server->>Server: Verify outcome and update database
Payment Request Lifecycle
Section titled “Payment Request Lifecycle”stateDiagram-v2
[*] --> created: POST /paymentrequests
created --> completed: Transaction approved or declined
created --> cancelled: Merchant cancellation
completed --> [*]
cancelled --> [*]
HPP-Specific Status Scenarios
Section titled “HPP-Specific Status Scenarios”| Scenario | What the customer sees | Payment Request status |
|---|---|---|
| Payment approved | Result page or redirect (depends on resultPage) |
completed |
| Payment declined (retries remaining) | Hosted result page with retry option | Remains created |
| Payment declined (no retries) | Hosted result page — attempts exhausted | completed |
| Payment request cancelled | Hosted page indicating the request has been cancelled | cancelled |
| Payment request already completed | Redirects to the transaction result page | completed |