> ## Documentation Index
> Fetch the complete documentation index at: https://docs.pay-me.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Ejemplos de integración

> Ejemplos en cURL, Java, C#, Python y Node.js para consumir Pay-me PinPAD.

El sistema central del comercio actúa como **cliente HTTP**. La aplicación Pay-me PinPAD instalada en el Wiseasy P5L actúa como **servidor HTTP** sobre la red local.

En los ejemplos, reemplaza `192.168.68.121` y `8080` por la IP y el puerto configurados en tu terminal.

<Info>
  Consulta la [referencia de endpoints](/procesamiento-fisico/alignet-transit/referencia-de-endpoints) y el contrato de cada operación antes de adaptar estos ejemplos.
</Info>

## cURL

### Disponibilidad

```bash theme={"system"}
curl "http://192.168.68.121:8080/health"
```

### Autorización

```bash theme={"system"}
curl --request POST "http://192.168.68.121:8080/authorize" \
  --header "Content-Type: application/json" \
  --max-time 110 \
  --data '{
    "operationNumber": "44992528",
    "amount": "100",
    "currency": "604",
    "paymentMethod": "QR",
    "additionalFields": {
      "plate": "ABC-123",
      "tollPointId": "PEAJE-01",
      "laneId": "VIA-03"
    }
  }'
```

Las claves de `additionalFields` son ilustrativas. Confirma con Alignet el catálogo admitido para tu implementación.

### Consulta

```bash theme={"system"}
curl -i "http://192.168.68.121:8080/payments/44992528"
```

Usa `-i` durante las pruebas para comprobar `Retry-After` en una respuesta `202`.

## Java 11 o posterior

```java theme={"system"}
import java.net.URI;
import java.net.http.HttpClient;
import java.net.http.HttpRequest;
import java.net.http.HttpResponse;
import java.time.Duration;

public final class PinpadClient {
    private final HttpClient http = HttpClient.newHttpClient();
    private final String baseUrl;

    public PinpadClient(String baseUrl) {
        this.baseUrl = baseUrl;
    }

    public HttpResponse<String> authorize(
            String operationNumber, String amount, String currency,
            String paymentMethod) throws Exception {
        String json = String.format(
            "{\"operationNumber\":\"%s\",\"amount\":\"%s\",\"currency\":\"%s\",\"paymentMethod\":\"%s\"}",
            operationNumber, amount, currency, paymentMethod);

        HttpRequest request = HttpRequest.newBuilder()
            .uri(URI.create(baseUrl + "/authorize"))
            .header("Content-Type", "application/json")
            .timeout(Duration.ofSeconds(110))
            .POST(HttpRequest.BodyPublishers.ofString(json))
            .build();

        return http.send(request, HttpResponse.BodyHandlers.ofString());
    }

    public HttpResponse<String> query(String operationNumber) throws Exception {
        HttpRequest request = HttpRequest.newBuilder()
            .uri(URI.create(baseUrl + "/payments/" + operationNumber))
            .timeout(Duration.ofSeconds(10))
            .GET()
            .build();

        return http.send(request, HttpResponse.BodyHandlers.ofString());
    }
}
```

## C# con .NET

```csharp theme={"system"}
using System.Net.Http.Json;

public sealed class PinpadClient
{
    private readonly HttpClient _http;

    public PinpadClient(string baseUrl)
    {
        _http = new HttpClient
        {
            BaseAddress = new Uri(baseUrl),
            Timeout = TimeSpan.FromSeconds(110)
        };
    }

    public async Task<(int StatusCode, string Body)> AuthorizeAsync(
        string operationNumber, string amount, string currency, string paymentMethod)
    {
        var payload = new
        {
            operationNumber,
            amount,
            currency,
            paymentMethod
        };

        using var response = await _http.PostAsJsonAsync("/authorize", payload);
        return ((int)response.StatusCode, await response.Content.ReadAsStringAsync());
    }

    public async Task<(int StatusCode, string Body)> QueryAsync(string operationNumber)
    {
        using var response = await _http.GetAsync($"/payments/{operationNumber}");
        return ((int)response.StatusCode, await response.Content.ReadAsStringAsync());
    }
}
```

## Python con requests

```python theme={"system"}
import requests

BASE_URL = "http://192.168.68.121:8080"


def authorize(operation_number, amount, currency, payment_method):
    payload = {
        "operationNumber": operation_number,
        "amount": amount,
        "currency": currency,
        "paymentMethod": payment_method,
    }
    response = requests.post(
        f"{BASE_URL}/authorize",
        json=payload,
        timeout=110,
    )
    return response.status_code, response.json()


def query_status(operation_number):
    response = requests.get(
        f"{BASE_URL}/payments/{operation_number}",
        timeout=10,
    )
    return response.status_code, response.json(), response.headers.get("Retry-After")


http_status, body = authorize("44992528", "100", "604", "QR")
if http_status == 200 and body.get("status") == "APPROVED" \
        and body.get("resultCode") == "00":
    print("Pago aprobado", body.get("authorizationCode"))
elif http_status == 202:
    http_status, body, retry_after = query_status("44992528")
```

## Node.js 18 o posterior

```javascript theme={"system"}
const BASE_URL = "http://192.168.68.121:8080";

async function authorize(operationNumber, amount, currency, paymentMethod) {
  const controller = new AbortController();
  const timeout = setTimeout(() => controller.abort(), 110_000);

  try {
    const response = await fetch(`${BASE_URL}/authorize`, {
      method: "POST",
      headers: { "Content-Type": "application/json" },
      body: JSON.stringify({ operationNumber, amount, currency, paymentMethod }),
      signal: controller.signal,
    });

    return {
      statusCode: response.status,
      body: await response.json(),
      retryAfter: response.headers.get("retry-after"),
    };
  } finally {
    clearTimeout(timeout);
  }
}

async function queryStatus(operationNumber) {
  const response = await fetch(`${BASE_URL}/payments/${operationNumber}`);
  return {
    statusCode: response.status,
    body: await response.json(),
    retryAfter: response.headers.get("retry-after"),
  };
}
```

## Reglas para cualquier lenguaje

* Persiste `operationNumber` antes del `POST`.
* Envía `operationNumber`, `amount` y `currency` como Strings numéricos, y un único `paymentMethod`: `CARD` o `QR`.
* Configura al menos 100 a 110 segundos para la autorización.
* Conserva por separado el código HTTP y el JSON.
* Confirma únicamente `200` + `APPROVED` + `00`.
* Ante `202`, timeout o pérdida de conexión, consulta la misma referencia.
* Respeta `Retry-After` si está presente.
* Serializa los cobros dirigidos al mismo terminal.
* No registres datos sensibles de tarjeta.

Los ejemplos de extorno y su recuperación están en [Extorno de una venta aprobada](/procesamiento-fisico/alignet-transit/extorno).

<Warning>
  Los ejemplos se concentran en el contrato HTTP. En producción, serializa JSON con la biblioteca estándar del lenguaje, valida las respuestas y persiste el estado antes de ejecutar una acción de negocio irreversible.
</Warning>
