# Create a payment

`POST https://api.weavpayments.com/v1/payments`

Creates a payment on one channel and returns what the customer does next (`next_action`): scan a QR code, go to a checkout page, or pay at a counter with a payment code.

With a test key, the checkout page is Weav's test checkout, where you pay, decline or expire the payment. Live payments run through the providers.

> **Warning:** Never treat a redirect to your `success_url` as proof of payment. Wait for the `PAYMENT_COMPLETED` webhook, or read the payment with `GET`.

## What your customer does next

### Payment link (the default)

By default every payment comes back as a **payment link**: send your customer to `next_action.checkout_url`, Weav's payment page. Weav sets the payment up with the provider when your customer opens it, so `expires_at` starts as the link's lifetime (24 hours) and becomes the provider's window (for example 15 minutes for a QR Ph code) from that moment. For QR Ph the page shows the code and how-to-pay steps for their bank or e-wallet app (set `qr_ph_app` to start with one). The QR Ph and Pay & Go examples ask for the raw QR string or payment code instead, with `"next_action_format": "DIRECT"`.

**Your customer's name.** Weav needs it on every payment, for anti-money-laundering and fraud checks. Send it in `customer.name` if you have it. If you don't, leave `customer` out: Weav's payment page asks your customer before anything is set up. With `DIRECT` there's no Weav page, so `customer.name` is required.

**Webhooks for this payment.** They go to your webhook URL. To send one payment's webhooks somewhere else, set `webhook_url` on it.

### QR Ph, shown by you

With the raw string, render `qr_string` as a QR code and show the steps in `next_action.instructions`. Any QR Ph bank or e-wallet app can scan it. A QR Ph code expires 15 or 60 minutes after it's made, depending on your account's QR Ph provider; `expires_at` has the exact time.

Lay it out the QR Ph way, with the QR Ph symbol in the center: bank and e-wallet apps expect it, so a code that's off may not scan. See [Showing a QR Ph code](https://docs.weavpayments.com/channels#showing-a-qr-ph-code) for the exact layout and a sample.

### Redirect: GCash, Maya and cards

Send your customer to `next_action.checkout_url`. After they pay or cancel there, they come back through Weav first: Weav checks the result with the provider right away, then sends them to your `success_url` (paid) or `cancel_url` (failed, expired or canceled). Both are optional: without them, your customer stays on Weav's result page. If the provider is still confirming, they see a Weav page that updates by itself. Always rely on the webhook or `GET /v1/payments/{reference_id}` for the final status, not on which URL they land on.

A GCash payment expires 10 minutes after it's created, Pay with Maya after 15 minutes and a card payment after 60.

> **Note:** **Mobile apps.** The GCash page has an "Open in GCash" button that uses a `gcash://` link. If you load `checkout_url` in a WebView, hand `gcash://` links to the operating system. On Android, use `shouldOverrideUrlLoading`. On iOS, use `decidePolicyForNavigationAction`. Otherwise the customer sees an unknown-scheme error.

### Over the counter

Give the customer the `payment_code`. At a Pay & Go kiosk they choose **Eplayment** on the screen, enter the code and pay in cash. With `PALAWANPAY` and `BAYAD` they go to a Palawan or Bayad counter, pay to **Eplayment** and show the code. Counter payments expire after 48 hours.

## Headers

- `Authorization` (string, required): `Bearer` plus your API key. See [Authentication](https://docs.weavpayments.com/authentication).
- `Idempotency-Key` (string): Optional. A unique value per new payment, such as a UUID. Retrying with the same key and body returns the stored response; a different body returns 409. Without it, your `external_reference_id` is the key. Up to 255 characters.

## Body

JSON, with `Content-Type: application/json`.

- `channel` (string): Required, unless you send `payment_method_id`. One of `QR_PH`, `GCASH`, `MAYA`, `CARD`, `PAY_AND_GO`, `PALAWANPAY`, `BAYAD`. The channel must be on for your account, or the response is 422 (4220101). One of: `QR_PH`, `GCASH`, `MAYA`, `CARD`, `PAY_AND_GO`, `PALAWANPAY`, `BAYAD`.
- `payment_method_id` (string | null): Charge a saved payment method instead (auto-debit), with no payer present. Leave out `channel` and `customer`. Only an `ACTIVE` one, or 422 `4220103`. A card is usually paid at once (`COMPLETED`); if the bank asks your customer to confirm again, it's `PENDING` with `next_action.type` `REDIRECT`.
- `save_payment_method` (boolean | null): `CARD` only. Also saves your customer's card for later charges (auto-debit), so you don't need `POST /v1/payment-methods` first. Send `customer.id`. On Weav's payment page, your customer agrees to future charges and pays; their bank's check (3DS) for this payment also confirms the card. The response's `payment_method_id` is the new method, `PENDING` until the payment is paid. You get `PAYMENT_COMPLETED`, then `PAYMENT_METHOD_SAVED`. If the payment isn't paid, the card isn't kept (`PAYMENT_METHOD_FAILED`). Off until Weav turns on saving cards for your account (422 `4220401`).
- `currency` (string, required): ISO 4217. PHP today; more as they're enabled for your account. One of: `PHP`.
- `amount` (number, required): Major unit, up to the currency's decimals (2 for PHP). Must be within your payment limits (GET /v1/channels; by default ₱0.01 to ₱50,000.00), or the response is 422. More than 0.
- `external_reference_id` (string, required): Your order or invoice reference. Unique across your payments in this mode (test and live are separate); reusing one returns 422. Up to 64 characters.
- `description` (string | null): Up to 255 characters. Your customer sees it on their emailed receipt (sent when you give their email). Up to 255 characters.
- `next_action_format` (string | null): `HOSTED` (default, every channel) returns `next_action.checkout_url`, Weav's payment page; the payment is set up with the provider when the customer opens it. `DIRECT` sets it up right away and returns the raw `qr_string` (with instructions), the provider's `checkout_url` or the `payment_code`. One of: `HOSTED`, `DIRECT`.
- `qr_ph_app` (string | null): QR Ph only. Tailors the how-to-pay steps to one bank or e-wallet app; any QR Ph app can still pay. One of: `BDO`, `CHINABANK`, `GOTYME`, `LANDBANK`, `METROBANK`, `PNB`, `RCBC`, `ROBINSONS_BANK`, `SECURITY_BANK`, `UNIONBANK`, `GRABPAY`, `SHOPEEPAY`.
- `customer` (object | null): The person paying. Stored encrypted; with an email, Weav emails them a receipt once the payment is paid. Weav needs the name for every payment (anti-money-laundering and fraud checks). Leave it out with `HOSTED` and Weav's payment page asks your customer before they pay; with `DIRECT` there's no Weav page, so `name` is required.
  - `id` (string): With `save_payment_method` only, and required then: your own ID for this customer. Their saved cards are listed by it (`GET /v1/payment-methods?customer_id=`). Up to 64 characters. Pattern: ^[A-Za-z0-9._:@-]+$.
  - `name` (string): One field; not split into first and last name. Up to 255 characters.
  - `email` (string (email) | null): Up to 255 characters.
  - `mobile_no` (string | null): A Philippine mobile number. Up to 20 characters.
- `webhook_url` (string | null): Optional. All of this payment's webhooks go here instead of your webhook URL, whatever its events list says. Public HTTPS only, signed with your signing key. Up to 2048 characters.
- `success_url` (string (uri) | null): Optional, HTTPS. Where your customer goes once the payment is paid. Without it, they stay on Weav's result page. Never treat this redirect as proof of payment. Up to 2048 characters.
- `cancel_url` (string (uri) | null): Optional, HTTPS. Where your customer goes if they leave without paying (the payment failed, expired or was canceled). Without it, they stay on Weav's result page. Up to 2048 characters.

## Responses

### 201 Created

Payment created (code 2010100).

What `data` holds:

- `payment` (object)
  - `reference_id` (string)
  - `external_reference_id` (string | null): Yours. For a checkout's payment, the checkout's (null when it has none).
  - `checkout_reference_id` (string | null): The checkout this payment was started from, if any.
  - `payment_method_id` (string | null): The saved payment method it was charged to, or the one it saves the card to (`save_payment_method`), if any.
  - `provider_reference_id` (string | null): The provider's transaction ID, once the provider has one.
  - `channel_reference_id` (string | null): A reference from the channel that is unique to this payment, once the payment completes. Null for channels whose numbers can repeat; those are in references.
  - `references` (object): The provider's other numbers for this payment, keyed by type: `invoice_number` (the 6-digit QR Ph invoice number), `receipt_number` (Maya) or `transaction_id` (GCash). Saved once the provider confirms the payment; {} until then. They can repeat across payments: search with them, never identify a payment by one alone.
    - `invoice_number` (string)
    - `receipt_number` (string)
    - `transaction_id` (string)
  - `channel` (string): One of `QR_PH`, `GCASH`, `MAYA`, `CARD`, `PAY_AND_GO`, `PALAWANPAY`, `BAYAD`. One of: `QR_PH`, `GCASH`, `MAYA`, `CARD`, `PAY_AND_GO`, `PALAWANPAY`, `BAYAD`.
  - `customer` (object): The person paying, as you sent it. The email and mobile number turn null once Weav's retention period ends.
    - `name` (string | null)
    - `email` (string | null)
    - `mobile_no` (string | null)
  - `currency` (string): ISO 4217. PHP today; more as they're enabled for your account. One of: `PHP`.
  - `amount` (number)
  - `fee` (number | null): Null until a rate applies.
  - `total` (number | null): `amount` plus `fee`, calculated by Weav. Null while `fee` is null.
  - `fee_bearer` (string): `MERCHANT`, the fee comes out of `amount` (default). `PAYER` (fees on top), the customer is charged `amount` + `fee` and you receive the full `amount`. One of: `MERCHANT`, `PAYER`.
  - `amount_charged` (number): What the customer is charged. `amount`, or `total` when `fee_bearer` is `PAYER`.
  - `amount_refunded` (number): The total refunded so far. The payment turns `REFUNDED` once it equals `amount`.
  - `refunds` (array of objects): Refunds Weav recorded for this payment, oldest first. Refunds are made by Weav support on request.
    - `reference_id` (string)
    - `amount` (number)
    - `provider_reference_id` (string | null)
    - `refunded_at` (string (date-time))
  - `status` (string): `PENDING`, `COMPLETED`, `FAILED`, `CANCELLED`, `REVERSED` or `REFUNDED`. See [Statuses](https://docs.weavpayments.com/statuses). One of: `PENDING`, `COMPLETED`, `FAILED`, `CANCELLED`, `REVERSED`, `REFUNDED`.
  - `description` (string | null): As you sent it.
  - `success_url` (string (uri) | null)
  - `cancel_url` (string (uri) | null)
  - `webhook_url` (string | null): Where this payment's webhooks go, when not your webhook URL.
  - `next_action` (object): What your customer does next. `type` is `DISPLAY_QR`, `REDIRECT`, `PAY_AT_COUNTER`, or null once the payment is final. `qr_string`, `checkout_url` and `payment_code` are each null unless they apply. With `HOSTED` (the default), `type` is `REDIRECT` and `checkout_url` is Weav's payment page (the test checkout with a test key), for every channel. For QR Ph, `qr_ph_app` is the app you chose, and `instructions` lists the how-to-pay steps (`title`, `description`) when you asked for `DIRECT`.
    - `type` (string | null): One of: `DISPLAY_QR`, `REDIRECT`, `PAY_AT_COUNTER`.
    - `qr_string` (string | null): QR Ph payload to render as a QR code: error correction Q (M at minimum), a white quiet zone of at least 4 modules, and the full-color QR Ph symbol on a white box 23.81% of the code width (quiet zone excluded) in the exact center.
    - `checkout_url` (string (uri) | null)
    - `payment_code` (string | null): For over-the-counter channels.
    - `qr_ph_app` (string | null): QR Ph only. The bank or e-wallet app the steps are tailored to.
    - `instructions` (array of objects | null): QR Ph with `next_action_format` `DIRECT` only. How-to-pay steps to show the customer.
      - `title` (string)
      - `description` (string)
  - `test_checkout_url` (string (uri) | null): Test mode only: the test checkout page, where you pay, decline or let this payment expire, for every channel (a counter payment with `DIRECT` has no other way to finish). Anyone with the link can open it. Null in live mode.
  - `failure` (object | null): `code` and `message` when the payment failed. Codes: `EXPIRED`, `DECLINED`, `PROVIDER_ERROR`.
    - `code` (string): One of: `EXPIRED`, `DECLINED`, `PROVIDER_ERROR`.
    - `message` (string)
  - `expires_at` (string (date-time)): When an unpaid payment fails (`failure.code` `EXPIRED`).
  - `completed_at` (string (date-time) | null): When the customer paid, as the provider reports it.
  - `failed_at` (string (date-time) | null): When the payment failed.
  - `cancelled_at` (string (date-time) | null): When the payment was canceled.
  - `reversed_at` (string (date-time) | null): When the payment was reversed.
  - `created_at` (string (date-time)): When Weav created the payment.
  - `updated_at` (string (date-time)): When the payment last changed.

```json
{
    "code": "2010100",
    "success": true,
    "message": "Payment created",
    "data": {
        "payment": {
            "reference_id": "PY7K3Q9M2X4TBA",
            "external_reference_id": "ORD-10541",
            "checkout_reference_id": null,
            "payment_method_id": null,
            "provider_reference_id": null,
            "channel_reference_id": null,
            "references": {},
            "channel": "QR_PH",
            "customer": {
                "name": "Juan dela Cruz",
                "email": null,
                "mobile_no": null
            },
            "currency": "PHP",
            "amount": 1250.0,
            "fee": 31.25,
            "total": 1281.25,
            "fee_bearer": "MERCHANT",
            "amount_charged": 1250.0,
            "amount_refunded": 0.0,
            "refunds": [],
            "status": "PENDING",
            "description": "Order ORD-10541",
            "success_url": null,
            "cancel_url": null,
            "webhook_url": null,
            "next_action": {
                "type": "DISPLAY_QR",
                "qr_string": "00020101021228…6304A1B2",
                "checkout_url": null,
                "payment_code": null,
                "qr_ph_app": null,
                "instructions": [
                    {
                        "title": "Open your bank or e-wallet app",
                        "description": "Any app that supports QR Ph works."
                    },
                    {
                        "title": "Scan the QR code",
                        "description": "Use the app's QR scanner on the code on your screen, or upload a saved copy."
                    },
                    {
                        "title": "Confirm the payment",
                        "description": "Check the amount and the merchant's name, then confirm."
                    }
                ]
            },
            "test_checkout_url": null,
            "failure": null,
            "expires_at": "2026-10-26T10:27:00+08:00",
            "completed_at": null,
            "failed_at": null,
            "cancelled_at": null,
            "reversed_at": null,
            "created_at": "2026-10-26T10:12:00+08:00",
            "updated_at": "2026-10-26T10:12:00+08:00"
        }
    }
}
```

### 401 Unauthorized

Missing, malformed or unknown API key (code 4010000).

```json
{
    "code": "4010000",
    "success": false,
    "message": "Missing or invalid API key."
}
```

### 403 Forbidden

The key can't make this request (code 4030000): an address outside the key's IP allowlist, a live key before your live mode is on, or an account that isn't active. A live key sent from a browser is refused (code 4030001): keep live keys on your server.

```json
{
    "code": "4030000",
    "success": false,
    "message": "Requests with this key must come from an address on its allowlist."
}
```

### 409 Conflict

The request conflicts with the current state, e.g. an Idempotency-Key reused with a different body (4090001), a request still in progress (4090002), a payment that can't be canceled (4090101) or can't be canceled at the provider yet (4090102, retry shortly), or a webhook still being sent (4090201).

```json
{
    "code": "4090001",
    "success": false,
    "message": "This Idempotency-Key was already used with a different request."
}
```

### 422 Unprocessable Content

One or more fields are invalid (code 4220000), or the channel is off (4220101) or doesn't take the currency (4220102).

```json
{
    "code": "4220000",
    "success": false,
    "message": "The given data was invalid.",
    "errors": {
        "channel": [
            "The channel field is required."
        ]
    }
}
```

### 429 Too Many Requests

Rate limited (code 4290000). Wait for `Retry-After` seconds.

```json
{
    "code": "4290000",
    "success": false,
    "message": "Too many requests. Wait, then retry."
}
```

### 501 Not Implemented

This channel isn't live for your account yet (code 5010100); use a test key.

```json
{
    "code": "5010100",
    "success": false,
    "message": "Live payments aren't available through the API yet. Use a test key, or contact support@weavpayments.com."
}
```

## Examples

### QR Ph

cURL:

```shell
curl -X POST https://api.weavpayments.com/v1/payments \
    -H "Authorization: Bearer $WEAV_API_KEY" \
    -H "Content-Type: application/json" \
    -d '{
    "channel": "QR_PH",
    "currency": "PHP",
    "amount": 1250.00,
    "external_reference_id": "ORD-10541",
    "description": "Order ORD-10541",
    "next_action_format": "DIRECT",
    "customer": {
        "name": "Juan dela Cruz",
        "email": null,
        "mobile_no": null
    }
}'
```

Node.js:

```js
const url = 'https://api.weavpayments.com/v1/payments';
const response = await fetch(url, {
    method: 'POST',
    headers: {
        Authorization: `Bearer ${process.env.WEAV_API_KEY}`,
        'Content-Type': 'application/json',
    },
    body: JSON.stringify({
        channel: 'QR_PH',
        currency: 'PHP',
        amount: 1250.0,
        external_reference_id: 'ORD-10541',
        description: 'Order ORD-10541',
        next_action_format: 'DIRECT',
        customer: {
            name: 'Juan dela Cruz',
            email: null,
            mobile_no: null,
        },
    }),
});

const result = await response.json();
```

JavaScript:

```js
import axios from 'axios';

const response = await axios.request({
    method: 'post',
    url: 'https://api.weavpayments.com/v1/payments',
    headers: {
        Authorization: `Bearer ${process.env.WEAV_API_KEY}`,
    },
    data: {
        channel: 'QR_PH',
        currency: 'PHP',
        amount: 1250.0,
        external_reference_id: 'ORD-10541',
        description: 'Order ORD-10541',
        next_action_format: 'DIRECT',
        customer: {
            name: 'Juan dela Cruz',
            email: null,
            mobile_no: null,
        },
    },
    // Read error answers too: their body has the error code.
    validateStatus: () => true,
});

const result = response.data;
```

PHP:

```php
use Illuminate\Support\Facades\Http;

$response = Http::withToken(config('services.weav.key'))
    ->post('https://api.weavpayments.com/v1/payments', [
        'channel' => 'QR_PH',
        'currency' => 'PHP',
        'amount' => 1250.00,
        'external_reference_id' => 'ORD-10541',
        'description' => 'Order ORD-10541',
        'next_action_format' => 'DIRECT',
        'customer' => [
            'name' => 'Juan dela Cruz',
            'email' => null,
            'mobile_no' => null,
        ],
    ]);

$result = $response->json();
```

Python:

```python
import os
import requests

response = requests.post(
    "https://api.weavpayments.com/v1/payments",
    headers={
        "Authorization": f"Bearer {os.environ['WEAV_API_KEY']}",
    },
    json={
        "channel": "QR_PH",
        "currency": "PHP",
        "amount": 1250.00,
        "external_reference_id": "ORD-10541",
        "description": "Order ORD-10541",
        "next_action_format": "DIRECT",
        "customer": {
            "name": "Juan dela Cruz",
            "email": None,
            "mobile_no": None,
        },
    },
    timeout=30,
)

result = response.json()
```

Go:

```go
package main

import (
    "fmt"
    "io"
    "net/http"
    "os"
    "strings"
)

func main() {
    body := strings.NewReader(`{
    "channel": "QR_PH",
    "currency": "PHP",
    "amount": 1250.00,
    "external_reference_id": "ORD-10541",
    "description": "Order ORD-10541",
    "next_action_format": "DIRECT",
    "customer": {
        "name": "Juan dela Cruz",
        "email": null,
        "mobile_no": null
    }
}`)

    req, err := http.NewRequest("POST", "https://api.weavpayments.com/v1/payments", body)
    if err != nil {
        panic(err)
    }
    req.Header.Set("Authorization", "Bearer "+os.Getenv("WEAV_API_KEY"))
    req.Header.Set("Content-Type", "application/json")

    res, err := http.DefaultClient.Do(req)
    if err != nil {
        panic(err)
    }
    defer res.Body.Close()

    result, err := io.ReadAll(res.Body)
    if err != nil {
        panic(err)
    }
    fmt.Println(res.Status, string(result))
}
```

Rust:

```rust
// Cargo.toml: reqwest = { version = "0.12", features = ["blocking", "json"] }, serde_json = "1"
use serde_json::json;

fn main() -> Result<(), Box<dyn std::error::Error>> {
    let key = std::env::var("WEAV_API_KEY")?;
    let body = json!({
        "channel": "QR_PH",
        "currency": "PHP",
        "amount": 1250.00,
        "external_reference_id": "ORD-10541",
        "description": "Order ORD-10541",
        "next_action_format": "DIRECT",
        "customer": {
            "name": "Juan dela Cruz",
            "email": null,
            "mobile_no": null
        }
    });

    let response = reqwest::blocking::Client::new()
        .post("https://api.weavpayments.com/v1/payments")
        .bearer_auth(key)
        .json(&body)
        .send()?;

    let status = response.status();
    let result: serde_json::Value = response.json()?;
    println!("{status} {result:#}");
    Ok(())
}
```

Java:

```java
import java.net.URI;
import java.net.http.HttpClient;
import java.net.http.HttpRequest;
import java.net.http.HttpResponse;

public class WeavExample {
    public static void main(String[] args) throws Exception {
        String url = "https://api.weavpayments.com/v1/payments";
        String body =
                """
                {
                    "channel": "QR_PH",
                    "currency": "PHP",
                    "amount": 1250.00,
                    "external_reference_id": "ORD-10541",
                    "description": "Order ORD-10541",
                    "next_action_format": "DIRECT",
                    "customer": {
                        "name": "Juan dela Cruz",
                        "email": null,
                        "mobile_no": null
                    }
                }
                """;

        HttpRequest request =
                HttpRequest.newBuilder()
                        .uri(URI.create(url))
                        .header("Authorization", "Bearer " + System.getenv("WEAV_API_KEY"))
                        .header("Content-Type", "application/json")
                        .POST(HttpRequest.BodyPublishers.ofString(body))
                        .build();

        HttpResponse<String> response =
                HttpClient.newHttpClient().send(request, HttpResponse.BodyHandlers.ofString());
        System.out.println(response.statusCode() + " " + response.body());
    }
}
```

Response (201):

```json
{
    "code": "2010100",
    "success": true,
    "message": "Payment created",
    "data": {
        "payment": {
            "reference_id": "PY7K3Q9M2X4TBA",
            "external_reference_id": "ORD-10541",
            "checkout_reference_id": null,
            "payment_method_id": null,
            "provider_reference_id": null,
            "channel_reference_id": null,
            "references": {},
            "channel": "QR_PH",
            "customer": {
                "name": "Juan dela Cruz",
                "email": null,
                "mobile_no": null
            },
            "currency": "PHP",
            "amount": 1250.0,
            "fee": 31.25,
            "total": 1281.25,
            "fee_bearer": "MERCHANT",
            "amount_charged": 1250.0,
            "amount_refunded": 0.0,
            "refunds": [],
            "status": "PENDING",
            "description": "Order ORD-10541",
            "success_url": null,
            "cancel_url": null,
            "webhook_url": null,
            "next_action": {
                "type": "DISPLAY_QR",
                "qr_string": "00020101021228…6304A1B2",
                "checkout_url": null,
                "payment_code": null,
                "qr_ph_app": null,
                "instructions": [
                    {
                        "title": "Open your bank or e-wallet app",
                        "description": "Any app that supports QR Ph works."
                    },
                    {
                        "title": "Scan the QR code",
                        "description": "Use the app's QR scanner on the code on your screen, or upload a saved copy."
                    },
                    {
                        "title": "Confirm the payment",
                        "description": "Check the amount and the merchant's name, then confirm."
                    }
                ]
            },
            "test_checkout_url": null,
            "failure": null,
            "expires_at": "2026-10-26T10:27:00+08:00",
            "completed_at": null,
            "failed_at": null,
            "cancelled_at": null,
            "reversed_at": null,
            "created_at": "2026-10-26T10:12:00+08:00",
            "updated_at": "2026-10-26T10:12:00+08:00"
        }
    }
}
```

### GCash

cURL:

```shell
curl -X POST https://api.weavpayments.com/v1/payments \
    -H "Authorization: Bearer $WEAV_API_KEY" \
    -H "Content-Type: application/json" \
    -d '{
    "channel": "GCASH",
    "currency": "PHP",
    "amount": 1250.00,
    "external_reference_id": "ORD-10542",
    "description": "Order ORD-10542",
    "customer": {
        "name": "Juan dela Cruz",
        "email": null,
        "mobile_no": null
    },
    "success_url": "https://shop.example/orders/10542/done",
    "cancel_url": "https://shop.example/orders/10542/retry"
}'
```

Node.js:

```js
const url = 'https://api.weavpayments.com/v1/payments';
const response = await fetch(url, {
    method: 'POST',
    headers: {
        Authorization: `Bearer ${process.env.WEAV_API_KEY}`,
        'Content-Type': 'application/json',
    },
    body: JSON.stringify({
        channel: 'GCASH',
        currency: 'PHP',
        amount: 1250.0,
        external_reference_id: 'ORD-10542',
        description: 'Order ORD-10542',
        customer: {
            name: 'Juan dela Cruz',
            email: null,
            mobile_no: null,
        },
        success_url: 'https://shop.example/orders/10542/done',
        cancel_url: 'https://shop.example/orders/10542/retry',
    }),
});

const result = await response.json();
```

JavaScript:

```js
import axios from 'axios';

const response = await axios.request({
    method: 'post',
    url: 'https://api.weavpayments.com/v1/payments',
    headers: {
        Authorization: `Bearer ${process.env.WEAV_API_KEY}`,
    },
    data: {
        channel: 'GCASH',
        currency: 'PHP',
        amount: 1250.0,
        external_reference_id: 'ORD-10542',
        description: 'Order ORD-10542',
        customer: {
            name: 'Juan dela Cruz',
            email: null,
            mobile_no: null,
        },
        success_url: 'https://shop.example/orders/10542/done',
        cancel_url: 'https://shop.example/orders/10542/retry',
    },
    // Read error answers too: their body has the error code.
    validateStatus: () => true,
});

const result = response.data;
```

PHP:

```php
use Illuminate\Support\Facades\Http;

$response = Http::withToken(config('services.weav.key'))
    ->post('https://api.weavpayments.com/v1/payments', [
        'channel' => 'GCASH',
        'currency' => 'PHP',
        'amount' => 1250.00,
        'external_reference_id' => 'ORD-10542',
        'description' => 'Order ORD-10542',
        'customer' => [
            'name' => 'Juan dela Cruz',
            'email' => null,
            'mobile_no' => null,
        ],
        'success_url' => 'https://shop.example/orders/10542/done',
        'cancel_url' => 'https://shop.example/orders/10542/retry',
    ]);

$result = $response->json();
```

Python:

```python
import os
import requests

response = requests.post(
    "https://api.weavpayments.com/v1/payments",
    headers={
        "Authorization": f"Bearer {os.environ['WEAV_API_KEY']}",
    },
    json={
        "channel": "GCASH",
        "currency": "PHP",
        "amount": 1250.00,
        "external_reference_id": "ORD-10542",
        "description": "Order ORD-10542",
        "customer": {
            "name": "Juan dela Cruz",
            "email": None,
            "mobile_no": None,
        },
        "success_url": "https://shop.example/orders/10542/done",
        "cancel_url": "https://shop.example/orders/10542/retry",
    },
    timeout=30,
)

result = response.json()
```

Go:

```go
package main

import (
    "fmt"
    "io"
    "net/http"
    "os"
    "strings"
)

func main() {
    body := strings.NewReader(`{
    "channel": "GCASH",
    "currency": "PHP",
    "amount": 1250.00,
    "external_reference_id": "ORD-10542",
    "description": "Order ORD-10542",
    "customer": {
        "name": "Juan dela Cruz",
        "email": null,
        "mobile_no": null
    },
    "success_url": "https://shop.example/orders/10542/done",
    "cancel_url": "https://shop.example/orders/10542/retry"
}`)

    req, err := http.NewRequest("POST", "https://api.weavpayments.com/v1/payments", body)
    if err != nil {
        panic(err)
    }
    req.Header.Set("Authorization", "Bearer "+os.Getenv("WEAV_API_KEY"))
    req.Header.Set("Content-Type", "application/json")

    res, err := http.DefaultClient.Do(req)
    if err != nil {
        panic(err)
    }
    defer res.Body.Close()

    result, err := io.ReadAll(res.Body)
    if err != nil {
        panic(err)
    }
    fmt.Println(res.Status, string(result))
}
```

Rust:

```rust
// Cargo.toml: reqwest = { version = "0.12", features = ["blocking", "json"] }, serde_json = "1"
use serde_json::json;

fn main() -> Result<(), Box<dyn std::error::Error>> {
    let key = std::env::var("WEAV_API_KEY")?;
    let body = json!({
        "channel": "GCASH",
        "currency": "PHP",
        "amount": 1250.00,
        "external_reference_id": "ORD-10542",
        "description": "Order ORD-10542",
        "customer": {
            "name": "Juan dela Cruz",
            "email": null,
            "mobile_no": null
        },
        "success_url": "https://shop.example/orders/10542/done",
        "cancel_url": "https://shop.example/orders/10542/retry"
    });

    let response = reqwest::blocking::Client::new()
        .post("https://api.weavpayments.com/v1/payments")
        .bearer_auth(key)
        .json(&body)
        .send()?;

    let status = response.status();
    let result: serde_json::Value = response.json()?;
    println!("{status} {result:#}");
    Ok(())
}
```

Java:

```java
import java.net.URI;
import java.net.http.HttpClient;
import java.net.http.HttpRequest;
import java.net.http.HttpResponse;

public class WeavExample {
    public static void main(String[] args) throws Exception {
        String url = "https://api.weavpayments.com/v1/payments";
        String body =
                """
                {
                    "channel": "GCASH",
                    "currency": "PHP",
                    "amount": 1250.00,
                    "external_reference_id": "ORD-10542",
                    "description": "Order ORD-10542",
                    "customer": {
                        "name": "Juan dela Cruz",
                        "email": null,
                        "mobile_no": null
                    },
                    "success_url": "https://shop.example/orders/10542/done",
                    "cancel_url": "https://shop.example/orders/10542/retry"
                }
                """;

        HttpRequest request =
                HttpRequest.newBuilder()
                        .uri(URI.create(url))
                        .header("Authorization", "Bearer " + System.getenv("WEAV_API_KEY"))
                        .header("Content-Type", "application/json")
                        .POST(HttpRequest.BodyPublishers.ofString(body))
                        .build();

        HttpResponse<String> response =
                HttpClient.newHttpClient().send(request, HttpResponse.BodyHandlers.ofString());
        System.out.println(response.statusCode() + " " + response.body());
    }
}
```

Response (201):

```json
{
    "code": "2010100",
    "success": true,
    "message": "Payment created",
    "data": {
        "payment": {
            "reference_id": "PY3T8N1W6R2QCD",
            "external_reference_id": "ORD-10542",
            "checkout_reference_id": null,
            "payment_method_id": null,
            "provider_reference_id": null,
            "channel_reference_id": null,
            "references": {},
            "channel": "GCASH",
            "customer": {
                "name": "Juan dela Cruz",
                "email": null,
                "mobile_no": null
            },
            "currency": "PHP",
            "amount": 1250.0,
            "fee": 31.25,
            "total": 1281.25,
            "fee_bearer": "MERCHANT",
            "amount_charged": 1250.0,
            "amount_refunded": 0.0,
            "refunds": [],
            "status": "PENDING",
            "description": "Order ORD-10542",
            "success_url": "https://shop.example/orders/10542/done",
            "cancel_url": "https://shop.example/orders/10542/retry",
            "webhook_url": null,
            "next_action": {
                "type": "REDIRECT",
                "qr_string": null,
                "checkout_url": "https://pay.weavpayments.com/pay/PY3T8N1W6R2QCD",
                "payment_code": null,
                "qr_ph_app": null,
                "instructions": null
            },
            "test_checkout_url": null,
            "failure": null,
            "expires_at": "2026-10-27T10:12:00+08:00",
            "completed_at": null,
            "failed_at": null,
            "cancelled_at": null,
            "reversed_at": null,
            "created_at": "2026-10-26T10:12:00+08:00",
            "updated_at": "2026-10-26T10:12:00+08:00"
        }
    }
}
```

### A saved card (auto-debit)

cURL:

```shell
curl -X POST https://api.weavpayments.com/v1/payments \
    -H "Authorization: Bearer $WEAV_API_KEY" \
    -H "Content-Type: application/json" \
    -d '{
    "payment_method_id": "PM8K2Q7X9KBAT4MZ3N",
    "currency": "PHP",
    "amount": 499.00,
    "external_reference_id": "SUB-USER-123-2026-11",
    "description": "November plan"
}'
```

Node.js:

```js
const url = 'https://api.weavpayments.com/v1/payments';
const response = await fetch(url, {
    method: 'POST',
    headers: {
        Authorization: `Bearer ${process.env.WEAV_API_KEY}`,
        'Content-Type': 'application/json',
    },
    body: JSON.stringify({
        payment_method_id: 'PM8K2Q7X9KBAT4MZ3N',
        currency: 'PHP',
        amount: 499.0,
        external_reference_id: 'SUB-USER-123-2026-11',
        description: 'November plan',
    }),
});

const result = await response.json();
```

JavaScript:

```js
import axios from 'axios';

const response = await axios.request({
    method: 'post',
    url: 'https://api.weavpayments.com/v1/payments',
    headers: {
        Authorization: `Bearer ${process.env.WEAV_API_KEY}`,
    },
    data: {
        payment_method_id: 'PM8K2Q7X9KBAT4MZ3N',
        currency: 'PHP',
        amount: 499.0,
        external_reference_id: 'SUB-USER-123-2026-11',
        description: 'November plan',
    },
    // Read error answers too: their body has the error code.
    validateStatus: () => true,
});

const result = response.data;
```

PHP:

```php
use Illuminate\Support\Facades\Http;

$response = Http::withToken(config('services.weav.key'))
    ->post('https://api.weavpayments.com/v1/payments', [
        'payment_method_id' => 'PM8K2Q7X9KBAT4MZ3N',
        'currency' => 'PHP',
        'amount' => 499.00,
        'external_reference_id' => 'SUB-USER-123-2026-11',
        'description' => 'November plan',
    ]);

$result = $response->json();
```

Python:

```python
import os
import requests

response = requests.post(
    "https://api.weavpayments.com/v1/payments",
    headers={
        "Authorization": f"Bearer {os.environ['WEAV_API_KEY']}",
    },
    json={
        "payment_method_id": "PM8K2Q7X9KBAT4MZ3N",
        "currency": "PHP",
        "amount": 499.00,
        "external_reference_id": "SUB-USER-123-2026-11",
        "description": "November plan",
    },
    timeout=30,
)

result = response.json()
```

Go:

```go
package main

import (
    "fmt"
    "io"
    "net/http"
    "os"
    "strings"
)

func main() {
    body := strings.NewReader(`{
    "payment_method_id": "PM8K2Q7X9KBAT4MZ3N",
    "currency": "PHP",
    "amount": 499.00,
    "external_reference_id": "SUB-USER-123-2026-11",
    "description": "November plan"
}`)

    req, err := http.NewRequest("POST", "https://api.weavpayments.com/v1/payments", body)
    if err != nil {
        panic(err)
    }
    req.Header.Set("Authorization", "Bearer "+os.Getenv("WEAV_API_KEY"))
    req.Header.Set("Content-Type", "application/json")

    res, err := http.DefaultClient.Do(req)
    if err != nil {
        panic(err)
    }
    defer res.Body.Close()

    result, err := io.ReadAll(res.Body)
    if err != nil {
        panic(err)
    }
    fmt.Println(res.Status, string(result))
}
```

Rust:

```rust
// Cargo.toml: reqwest = { version = "0.12", features = ["blocking", "json"] }, serde_json = "1"
use serde_json::json;

fn main() -> Result<(), Box<dyn std::error::Error>> {
    let key = std::env::var("WEAV_API_KEY")?;
    let body = json!({
        "payment_method_id": "PM8K2Q7X9KBAT4MZ3N",
        "currency": "PHP",
        "amount": 499.00,
        "external_reference_id": "SUB-USER-123-2026-11",
        "description": "November plan"
    });

    let response = reqwest::blocking::Client::new()
        .post("https://api.weavpayments.com/v1/payments")
        .bearer_auth(key)
        .json(&body)
        .send()?;

    let status = response.status();
    let result: serde_json::Value = response.json()?;
    println!("{status} {result:#}");
    Ok(())
}
```

Java:

```java
import java.net.URI;
import java.net.http.HttpClient;
import java.net.http.HttpRequest;
import java.net.http.HttpResponse;

public class WeavExample {
    public static void main(String[] args) throws Exception {
        String url = "https://api.weavpayments.com/v1/payments";
        String body =
                """
                {
                    "payment_method_id": "PM8K2Q7X9KBAT4MZ3N",
                    "currency": "PHP",
                    "amount": 499.00,
                    "external_reference_id": "SUB-USER-123-2026-11",
                    "description": "November plan"
                }
                """;

        HttpRequest request =
                HttpRequest.newBuilder()
                        .uri(URI.create(url))
                        .header("Authorization", "Bearer " + System.getenv("WEAV_API_KEY"))
                        .header("Content-Type", "application/json")
                        .POST(HttpRequest.BodyPublishers.ofString(body))
                        .build();

        HttpResponse<String> response =
                HttpClient.newHttpClient().send(request, HttpResponse.BodyHandlers.ofString());
        System.out.println(response.statusCode() + " " + response.body());
    }
}
```

### Pay by card and save it

cURL:

```shell
curl -X POST https://api.weavpayments.com/v1/payments \
    -H "Authorization: Bearer $WEAV_API_KEY" \
    -H "Content-Type: application/json" \
    -d '{
    "channel": "CARD",
    "currency": "PHP",
    "amount": 499.00,
    "external_reference_id": "SUB-USER-123-2026-10",
    "description": "October plan",
    "save_payment_method": true,
    "customer": {
        "id": "USER-123",
        "name": "Juan dela Cruz",
        "email": "juan@example.com"
    },
    "success_url": "https://shop.example/account/plan",
    "cancel_url": "https://shop.example/account/plan"
}'
```

Node.js:

```js
const url = 'https://api.weavpayments.com/v1/payments';
const response = await fetch(url, {
    method: 'POST',
    headers: {
        Authorization: `Bearer ${process.env.WEAV_API_KEY}`,
        'Content-Type': 'application/json',
    },
    body: JSON.stringify({
        channel: 'CARD',
        currency: 'PHP',
        amount: 499.0,
        external_reference_id: 'SUB-USER-123-2026-10',
        description: 'October plan',
        save_payment_method: true,
        customer: {
            id: 'USER-123',
            name: 'Juan dela Cruz',
            email: 'juan@example.com',
        },
        success_url: 'https://shop.example/account/plan',
        cancel_url: 'https://shop.example/account/plan',
    }),
});

const result = await response.json();
```

JavaScript:

```js
import axios from 'axios';

const response = await axios.request({
    method: 'post',
    url: 'https://api.weavpayments.com/v1/payments',
    headers: {
        Authorization: `Bearer ${process.env.WEAV_API_KEY}`,
    },
    data: {
        channel: 'CARD',
        currency: 'PHP',
        amount: 499.0,
        external_reference_id: 'SUB-USER-123-2026-10',
        description: 'October plan',
        save_payment_method: true,
        customer: {
            id: 'USER-123',
            name: 'Juan dela Cruz',
            email: 'juan@example.com',
        },
        success_url: 'https://shop.example/account/plan',
        cancel_url: 'https://shop.example/account/plan',
    },
    // Read error answers too: their body has the error code.
    validateStatus: () => true,
});

const result = response.data;
```

PHP:

```php
use Illuminate\Support\Facades\Http;

$response = Http::withToken(config('services.weav.key'))
    ->post('https://api.weavpayments.com/v1/payments', [
        'channel' => 'CARD',
        'currency' => 'PHP',
        'amount' => 499.00,
        'external_reference_id' => 'SUB-USER-123-2026-10',
        'description' => 'October plan',
        'save_payment_method' => true,
        'customer' => [
            'id' => 'USER-123',
            'name' => 'Juan dela Cruz',
            'email' => 'juan@example.com',
        ],
        'success_url' => 'https://shop.example/account/plan',
        'cancel_url' => 'https://shop.example/account/plan',
    ]);

$result = $response->json();
```

Python:

```python
import os
import requests

response = requests.post(
    "https://api.weavpayments.com/v1/payments",
    headers={
        "Authorization": f"Bearer {os.environ['WEAV_API_KEY']}",
    },
    json={
        "channel": "CARD",
        "currency": "PHP",
        "amount": 499.00,
        "external_reference_id": "SUB-USER-123-2026-10",
        "description": "October plan",
        "save_payment_method": True,
        "customer": {
            "id": "USER-123",
            "name": "Juan dela Cruz",
            "email": "juan@example.com",
        },
        "success_url": "https://shop.example/account/plan",
        "cancel_url": "https://shop.example/account/plan",
    },
    timeout=30,
)

result = response.json()
```

Go:

```go
package main

import (
    "fmt"
    "io"
    "net/http"
    "os"
    "strings"
)

func main() {
    body := strings.NewReader(`{
    "channel": "CARD",
    "currency": "PHP",
    "amount": 499.00,
    "external_reference_id": "SUB-USER-123-2026-10",
    "description": "October plan",
    "save_payment_method": true,
    "customer": {
        "id": "USER-123",
        "name": "Juan dela Cruz",
        "email": "juan@example.com"
    },
    "success_url": "https://shop.example/account/plan",
    "cancel_url": "https://shop.example/account/plan"
}`)

    req, err := http.NewRequest("POST", "https://api.weavpayments.com/v1/payments", body)
    if err != nil {
        panic(err)
    }
    req.Header.Set("Authorization", "Bearer "+os.Getenv("WEAV_API_KEY"))
    req.Header.Set("Content-Type", "application/json")

    res, err := http.DefaultClient.Do(req)
    if err != nil {
        panic(err)
    }
    defer res.Body.Close()

    result, err := io.ReadAll(res.Body)
    if err != nil {
        panic(err)
    }
    fmt.Println(res.Status, string(result))
}
```

Rust:

```rust
// Cargo.toml: reqwest = { version = "0.12", features = ["blocking", "json"] }, serde_json = "1"
use serde_json::json;

fn main() -> Result<(), Box<dyn std::error::Error>> {
    let key = std::env::var("WEAV_API_KEY")?;
    let body = json!({
        "channel": "CARD",
        "currency": "PHP",
        "amount": 499.00,
        "external_reference_id": "SUB-USER-123-2026-10",
        "description": "October plan",
        "save_payment_method": true,
        "customer": {
            "id": "USER-123",
            "name": "Juan dela Cruz",
            "email": "juan@example.com"
        },
        "success_url": "https://shop.example/account/plan",
        "cancel_url": "https://shop.example/account/plan"
    });

    let response = reqwest::blocking::Client::new()
        .post("https://api.weavpayments.com/v1/payments")
        .bearer_auth(key)
        .json(&body)
        .send()?;

    let status = response.status();
    let result: serde_json::Value = response.json()?;
    println!("{status} {result:#}");
    Ok(())
}
```

Java:

```java
import java.net.URI;
import java.net.http.HttpClient;
import java.net.http.HttpRequest;
import java.net.http.HttpResponse;

public class WeavExample {
    public static void main(String[] args) throws Exception {
        String url = "https://api.weavpayments.com/v1/payments";
        String body =
                """
                {
                    "channel": "CARD",
                    "currency": "PHP",
                    "amount": 499.00,
                    "external_reference_id": "SUB-USER-123-2026-10",
                    "description": "October plan",
                    "save_payment_method": true,
                    "customer": {
                        "id": "USER-123",
                        "name": "Juan dela Cruz",
                        "email": "juan@example.com"
                    },
                    "success_url": "https://shop.example/account/plan",
                    "cancel_url": "https://shop.example/account/plan"
                }
                """;

        HttpRequest request =
                HttpRequest.newBuilder()
                        .uri(URI.create(url))
                        .header("Authorization", "Bearer " + System.getenv("WEAV_API_KEY"))
                        .header("Content-Type", "application/json")
                        .POST(HttpRequest.BodyPublishers.ofString(body))
                        .build();

        HttpResponse<String> response =
                HttpClient.newHttpClient().send(request, HttpResponse.BodyHandlers.ofString());
        System.out.println(response.statusCode() + " " + response.body());
    }
}
```

### Pay & Go

cURL:

```shell
curl -X POST https://api.weavpayments.com/v1/payments \
    -H "Authorization: Bearer $WEAV_API_KEY" \
    -H "Content-Type: application/json" \
    -d '{
    "channel": "PAY_AND_GO",
    "currency": "PHP",
    "amount": 3500.00,
    "external_reference_id": "ORD-10543",
    "description": null,
    "next_action_format": "DIRECT",
    "customer": {
        "name": "Juan dela Cruz",
        "email": null,
        "mobile_no": null
    }
}'
```

Node.js:

```js
const url = 'https://api.weavpayments.com/v1/payments';
const response = await fetch(url, {
    method: 'POST',
    headers: {
        Authorization: `Bearer ${process.env.WEAV_API_KEY}`,
        'Content-Type': 'application/json',
    },
    body: JSON.stringify({
        channel: 'PAY_AND_GO',
        currency: 'PHP',
        amount: 3500.0,
        external_reference_id: 'ORD-10543',
        description: null,
        next_action_format: 'DIRECT',
        customer: {
            name: 'Juan dela Cruz',
            email: null,
            mobile_no: null,
        },
    }),
});

const result = await response.json();
```

JavaScript:

```js
import axios from 'axios';

const response = await axios.request({
    method: 'post',
    url: 'https://api.weavpayments.com/v1/payments',
    headers: {
        Authorization: `Bearer ${process.env.WEAV_API_KEY}`,
    },
    data: {
        channel: 'PAY_AND_GO',
        currency: 'PHP',
        amount: 3500.0,
        external_reference_id: 'ORD-10543',
        description: null,
        next_action_format: 'DIRECT',
        customer: {
            name: 'Juan dela Cruz',
            email: null,
            mobile_no: null,
        },
    },
    // Read error answers too: their body has the error code.
    validateStatus: () => true,
});

const result = response.data;
```

PHP:

```php
use Illuminate\Support\Facades\Http;

$response = Http::withToken(config('services.weav.key'))
    ->post('https://api.weavpayments.com/v1/payments', [
        'channel' => 'PAY_AND_GO',
        'currency' => 'PHP',
        'amount' => 3500.00,
        'external_reference_id' => 'ORD-10543',
        'description' => null,
        'next_action_format' => 'DIRECT',
        'customer' => [
            'name' => 'Juan dela Cruz',
            'email' => null,
            'mobile_no' => null,
        ],
    ]);

$result = $response->json();
```

Python:

```python
import os
import requests

response = requests.post(
    "https://api.weavpayments.com/v1/payments",
    headers={
        "Authorization": f"Bearer {os.environ['WEAV_API_KEY']}",
    },
    json={
        "channel": "PAY_AND_GO",
        "currency": "PHP",
        "amount": 3500.00,
        "external_reference_id": "ORD-10543",
        "description": None,
        "next_action_format": "DIRECT",
        "customer": {
            "name": "Juan dela Cruz",
            "email": None,
            "mobile_no": None,
        },
    },
    timeout=30,
)

result = response.json()
```

Go:

```go
package main

import (
    "fmt"
    "io"
    "net/http"
    "os"
    "strings"
)

func main() {
    body := strings.NewReader(`{
    "channel": "PAY_AND_GO",
    "currency": "PHP",
    "amount": 3500.00,
    "external_reference_id": "ORD-10543",
    "description": null,
    "next_action_format": "DIRECT",
    "customer": {
        "name": "Juan dela Cruz",
        "email": null,
        "mobile_no": null
    }
}`)

    req, err := http.NewRequest("POST", "https://api.weavpayments.com/v1/payments", body)
    if err != nil {
        panic(err)
    }
    req.Header.Set("Authorization", "Bearer "+os.Getenv("WEAV_API_KEY"))
    req.Header.Set("Content-Type", "application/json")

    res, err := http.DefaultClient.Do(req)
    if err != nil {
        panic(err)
    }
    defer res.Body.Close()

    result, err := io.ReadAll(res.Body)
    if err != nil {
        panic(err)
    }
    fmt.Println(res.Status, string(result))
}
```

Rust:

```rust
// Cargo.toml: reqwest = { version = "0.12", features = ["blocking", "json"] }, serde_json = "1"
use serde_json::json;

fn main() -> Result<(), Box<dyn std::error::Error>> {
    let key = std::env::var("WEAV_API_KEY")?;
    let body = json!({
        "channel": "PAY_AND_GO",
        "currency": "PHP",
        "amount": 3500.00,
        "external_reference_id": "ORD-10543",
        "description": null,
        "next_action_format": "DIRECT",
        "customer": {
            "name": "Juan dela Cruz",
            "email": null,
            "mobile_no": null
        }
    });

    let response = reqwest::blocking::Client::new()
        .post("https://api.weavpayments.com/v1/payments")
        .bearer_auth(key)
        .json(&body)
        .send()?;

    let status = response.status();
    let result: serde_json::Value = response.json()?;
    println!("{status} {result:#}");
    Ok(())
}
```

Java:

```java
import java.net.URI;
import java.net.http.HttpClient;
import java.net.http.HttpRequest;
import java.net.http.HttpResponse;

public class WeavExample {
    public static void main(String[] args) throws Exception {
        String url = "https://api.weavpayments.com/v1/payments";
        String body =
                """
                {
                    "channel": "PAY_AND_GO",
                    "currency": "PHP",
                    "amount": 3500.00,
                    "external_reference_id": "ORD-10543",
                    "description": null,
                    "next_action_format": "DIRECT",
                    "customer": {
                        "name": "Juan dela Cruz",
                        "email": null,
                        "mobile_no": null
                    }
                }
                """;

        HttpRequest request =
                HttpRequest.newBuilder()
                        .uri(URI.create(url))
                        .header("Authorization", "Bearer " + System.getenv("WEAV_API_KEY"))
                        .header("Content-Type", "application/json")
                        .POST(HttpRequest.BodyPublishers.ofString(body))
                        .build();

        HttpResponse<String> response =
                HttpClient.newHttpClient().send(request, HttpResponse.BodyHandlers.ofString());
        System.out.println(response.statusCode() + " " + response.body());
    }
}
```

Response (201):

```json
{
    "code": "2010100",
    "success": true,
    "message": "Payment created",
    "data": {
        "payment": {
            "reference_id": "PY9M4C2X7K1VHE",
            "external_reference_id": "ORD-10543",
            "checkout_reference_id": null,
            "payment_method_id": null,
            "provider_reference_id": null,
            "channel_reference_id": null,
            "references": {},
            "channel": "PAY_AND_GO",
            "customer": {
                "name": "Juan dela Cruz",
                "email": null,
                "mobile_no": null
            },
            "currency": "PHP",
            "amount": 3500.0,
            "fee": 87.5,
            "total": 3587.5,
            "fee_bearer": "MERCHANT",
            "amount_charged": 3500.0,
            "amount_refunded": 0.0,
            "refunds": [],
            "status": "PENDING",
            "description": null,
            "success_url": null,
            "cancel_url": null,
            "webhook_url": null,
            "next_action": {
                "type": "PAY_AT_COUNTER",
                "qr_string": null,
                "checkout_url": null,
                "payment_code": "EP7K2M4Q9X1TB3A",
                "qr_ph_app": null,
                "instructions": null
            },
            "test_checkout_url": null,
            "failure": null,
            "expires_at": "2026-10-28T10:12:00+08:00",
            "completed_at": null,
            "failed_at": null,
            "cancelled_at": null,
            "reversed_at": null,
            "created_at": "2026-10-26T10:12:00+08:00",
            "updated_at": "2026-10-26T10:12:00+08:00"
        }
    }
}
```
