# Using an LLM or Agent to Build a Payments POC

This page helps you quickly build a proof of concept (POC) integration using an LLM, coding agent, or IDE assistant. The fastest POC is:

1. Create a payment using `POST /Payments/crypto`
2. Present the hosted payment page URL (`paymentUrls[0]`) in a browser tab or iframe
3. Poll status using `GET /Payments/tracking/{trackingId}` until the payment reaches a final state

This approach avoids webhook setup and is ideal for demos and early prototypes.

### What you need

To run the POC, you need these values from Bead:

* `apiKey` (terminal API key)
* `merchantId`
* `terminalId`

Sandbox defaults:

* Payments base URL: `https://api.test.devs.beadpay.io`
* Payments authentication header: `X-Api-Key: <apiKey>`
* There is no separate authentication URL for Payments when using API key authentication.

### POC flow

#### Step 1: Create a hosted payment page

Endpoint:

* `POST /Payments/crypto`

Required headers:

* `X-Api-Key: {apiKey}`
* `Content-Type: application/json`

Minimal request body (recommended for POCs):

```json
{
  "merchantId": "{merchantId}",
  "terminalId": "{terminalId}",
  "requestedAmount": 1,
  "reference": "POC-ORDER-001",
  "customer": {
    "firstName": "Test",
    "lastName": "User",
    "email": "test@example.com",
    "address": "123 Main St",
    "address2": "",
    "city": "Boston",
    "state": "MA",
    "postalCode": "02110",
    "countryCode": "US"
  }
}
```

Save these values from the response:

* `paymentUrls[0]` (hosted payment page URL)
* `trackingId` (used to check status)

#### Step 2: Present the hosted payment page

You can present the hosted payment page in one of these ways:

Option A: Open in a browser tab

* Redirect or open `paymentUrls[0]` directly in the user’s browser

Option B: Embed in an iframe (web apps)

* Render an iframe with `src=paymentUrls[0]`
* Use a full height container so QR codes and tender selection are visible
* If embedding is blocked, fall back to opening in a new tab

#### Step 3: Poll for status using trackingId

Endpoint:

* `GET /Payments/tracking/{trackingId}`

Headers:

* `X-Api-Key: {apiKey}`
* `Accept: application/json`

Example curl (Sandbox):

```bash
curl -s -X GET "https://api.test.devs.beadpay.io/Payments/tracking/{trackingId}" \
  -H "X-Api-Key: {apiKey}" \
  -H "Accept: application/json"
```

Recommended polling behavior:

* Start polling after you launch the hosted page
* Poll every 2 seconds for a POC demo
* Only log or display changes when status changes
* Stop polling when `statusCode` is in a terminal state such as:
  * `completed`
  * `expired`
  * `cancelled`
  * `invalid`
  * `underpaid`
  * `overpaid`

### POC UI flow (recommended)

Build a single page with three states:

1. Amount entry

* Amount input that accepts decimals
* Primary button: Pay with crypto

2. In progress

* Show the hosted payment page (iframe or new tab link)
* Show live status (`statusCode`) while polling

3. Complete

* Show a completion view when a terminal state is reached
* Display:
  * final `statusCode`
  * requested amount
  * `trackingId`
* Button: Start a new payment (resets to amount entry)

### Common troubleshooting

401 Unauthorized

* API key missing or invalid
* Header must be exactly `X-Api-Key`
* Ensure you are using the real `apiKey` value, not a masked value

403 Forbidden

* API key is valid but not permitted for the `merchantId` or `terminalId`
* Confirm all values are from the same environment and credential set

Environment mismatch

* Sandbox values only work with the Sandbox base URL
* Production values only work with the Production base URL

### Copy and paste prompt for an LLM or coding agent

Use the prompt below in ChatGPT, an IDE agent, or another coding assistant. It produces a minimal POC that creates a payment, presents the hosted page, polls for status, and shows a completion screen.

> Prompt
>
> You are a senior full stack engineer. Build a minimal proof of concept that integrates with Bead Payments using API key authentication only.
>
> Sandbox defaults:
>
> * Payments base URL: `https://api.test.devs.beadpay.io`
> * Payments auth header: `X-Api-Key: {apiKey}`
> * No separate authentication URL is used for Payments when using API key authentication.
>
> References (use if you need to confirm schemas and endpoints):
>
> * OpenAPI (authoritative): `https://api.test.devs.beadpay.io/apidocs/v1/api.json`
> * Developer docs (supporting): `https://developers.bead.xyz/` If there is any conflict, follow the OpenAPI. For Payments authentication, do not use OAuth. Use `X-Api-Key` only.
>
> Inputs I will provide:
>
> * `{apiKey}` (terminal API key, full value)
> * `{merchantId}`
> * `{terminalId}`
>
> UI requirements:
>
> 1. Show a simple amount entry input:
>    * Label: Amount
>    * Accept decimals
>    * Validate amount is greater than 0
>    * Default to 1.00 on first load
> 2. Show a primary button:
>    * Label: Pay with crypto
> 3. When the user clicks Pay with crypto:
>    * Call the backend to create a payment with the entered amount
>    * Display the hosted payment page in an iframe (or open a new tab if iframe embedding is blocked)
>    * Display a status panel showing the current `statusCode`
> 4. When the payment reaches a terminal state, show a Payment Complete screen:
>    * Replace the iframe view with a completion view
>    * Display the final status (completed, expired, cancelled, invalid, underpaid, overpaid)
>    * Display the amount requested
>    * Display the trackingId
>    * Provide a button to Start a new payment (resets UI back to amount entry)
>
> API requirements:
>
> 1. Create a hosted payment using:
>    * `POST https://api.test.devs.beadpay.io/Payments/crypto`
>    * Header: `X-Api-Key: {apiKey}`
>    * Header: `Content-Type: application/json`
>    * JSON body includes:
>      * `merchantId: {merchantId}`
>      * `terminalId: {terminalId}`
>      * `requestedAmount: <amount from UI>`
>      * `reference: "POC-ORDER-<unique>"`
>      * `customer` object exactly as shown below
> 2. Use this customer object in the request body:
>    * `firstName: "Test"`
>    * `lastName: "User"`
>    * `email: "test@example.com"`
>    * `address: "123 Main St"`
>    * `address2: ""`
>    * `city: "Boston"`
>    * `state: "MA"`
>    * `postalCode: "02110"`
>    * `countryCode: "US"`
> 3. From the create payment response, extract:
>    * `paymentUrls[0]` as `paymentUrl`
>    * `trackingId`
> 4. Poll for status using:
>    * `GET https://api.test.devs.beadpay.io/Payments/tracking/{trackingId}`
>    * Header: `X-Api-Key: {apiKey}`
>    * Poll every 2 seconds
>    * Only log when status changes
>    * Stop polling when `statusCode` reaches a terminal state: `completed`, `expired`, `cancelled`, `invalid`, `underpaid`, `overpaid`
>
> Deliverables:
>
> * One backend endpoint (or function/route) that:
>   * accepts `requestedAmount`
>   * calls `POST /Payments/crypto`
>   * returns `paymentUrl`, `trackingId`, and echoed `requestedAmount`
> * One backend endpoint (or function/route) that:
>   * accepts `trackingId`
>   * calls `GET /Payments/tracking/{trackingId}`
>   * returns the status JSON including `statusCode`
> * One UI page with three states:
>   1. Amount Entry state (input + Pay with crypto button)
>   2. In Progress state (iframe or new tab link + live status panel)
>   3. Payment Complete state (final status + trackingId + start over button)
>
> Constraints:
>
> * Use only API key auth for Payments (`X-Api-Key`). Do not include OAuth flows, tokens, or any authentication URL.
> * Do not include webhooks.
> * Do not include onboarding or entity management.
> * Treat `apiKey` as a secret and do not log it.
> * Keep the implementation small and readable.


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://developers.bead.xyz/reference-guide/operational-guides/using-an-llm-or-agent-to-build-a-payments-poc.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
