Documentation

Getting Started

Getting Started

This quickstart shows the standard PerfectPay web checkout flow: create a customer, create a payment, confirm it, and handle the result.

1. Collect Your Credentials

In the dashboard at https://app.perfectpay.ai:

  • Open Developers -> API Keys
  • Create a secret API key
  • Copy your publishable key
  • If you plan to use the hosted checkout, copy your environment's SDK loader URL from Developers -> Settings

2. Create a Customer

POST /customers

GET //sandbox.perfectpay.ai/customers
curl https://sandbox.perfectpay.ai/customers \
  -X POST \
  -H "api-key: YOUR_SECRET_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "name": "Jane Doe",
    "email": "[email protected]",
    "phone": "5555550100",
    "phone_country_code": "+1",
    "metadata": {
      "segment": "beta"
    }
  }'

Response excerpt:

JSON
{
  "customer_id": "cus_abc123",
  "name": "Jane Doe",
  "email": "[email protected]",
  "created_at": "2026-03-22T14:35:42Z"
}

3. Create a Payment

POST /payments

GET //sandbox.perfectpay.ai/payments
curl https://sandbox.perfectpay.ai/payments \
  -X POST \
  -H "api-key: YOUR_SECRET_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "amount": 4999,
    "currency": "USD",
    "customer_id": "cus_abc123",
    "capture_method": "automatic",
    "authentication_type": "no_three_ds",
    "return_url": "https://example.com/checkout/complete",
    "confirm": false,
    "description": "Order 1001",
    "metadata": {
      "order_id": "1001"
    }
  }'

Response excerpt:

JSON
{
  "payment_id": "pay_mbabizu24mvu3mela5njyhpit4",
  "client_secret": "pay_mbabizu24mvu3mela5njyhpit4_secret_abc123",
  "amount": 4999,
  "currency": "USD",
  "status": "requires_payment_method"
}

Keep the following fields for the next step:

  • payment_id
  • client_secret

4. Confirm the Payment

You have two supported patterns:

  • Recommended: Use the hosted Web SDK to handle card collection, wallets, redirects, and confirmation in the browser.
  • Server-side confirm: Send payment method data directly from your server.

Server-Side Confirm Example

POST /payments/{payment_id}/confirm

GET //sandbox.perfectpay.ai/payments/pay_mbabizu24mvu3mela5njyhpit4/confirm
curl https://sandbox.perfectpay.ai/payments/pay_mbabizu24mvu3mela5njyhpit4/confirm \
  -X POST \
  -H "api-key: YOUR_SECRET_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "payment_method": "card",
    "payment_method_type": "credit",
    "payment_method_data": {
      "card": {
        "card_number": "4242424242424242",
        "card_exp_month": "10",
        "card_exp_year": "25",
        "card_cvc": "123",
        "card_holder_name": "Jane Doe"
      }
    }
  }'

Response excerpt:

JSON
{
  "payment_id": "pay_mbabizu24mvu3mela5njyhpit4",
  "status": "succeeded",
  "amount": 4999,
  "currency": "USD"
}

Use raw card data in sandbox or controlled PCI environments only. For production browser flows, use the Web SDK.

5. Listen for Outcomes

For async payment methods and post-payment operations:

  • Configure outgoing webhooks in the dashboard
  • Inspect delivery history through Events & Webhooks

6. Add Refund Handling

Once you can charge successfully, wire up Refunds.

Test Cards

Use these card numbers in the sandbox environment with any future expiry date and any 3-digit CVC:

Card NumberBrandNotes
4242424242424242VisaStandard test card, always succeeds
4111111111111111VisaAlternative test card

See the Testing & Sandbox guide for more test scenarios and card numbers.