Integra pagos de PlacetoPay en 5 minutos. CLI para prototipar y testear, SDKs (Node.js, Python, PHP) para producción — como Stripe.
Desde crear sesiones hasta escuchar webhooks en tiempo real, el CLI cubre todo el ciclo de pagos.
Crea, consulta y gestiona sesiones de pago. Abre el enlace de pago directamente en el navegador.
Suscribe tarjetas con --subscribe y realiza cobros recurrentes con el token almacenado.
Escucha notificaciones en localhost, valida firmas SHA-1 y re-envía eventos con events resend.
Pagos directos con tarjeta sin redirect. Procesa, consulta, busca y gestiona transacciones.
Setup interactivo con login. Multi-perfil con --profile para test, staging y producción.
Siembra datos de prueba con fixtures run. Clona proyectos de ejemplo con samples create.
Monitorea todas las llamadas API con logs tail. Endpoint, status, duración y request ID.
Crea links de pago compartibles con payment-link create. Consulta y desactiva links.
Autenticación 3D Secure, reportes de transacciones, pre-autorización y reversos parciales.
npm, Homebrew, Scoop o descarga directa. Elige tu plataforma.
# Cualquier plataforma (requiere Node.js 16+)
$ npm install -g placetopay-cli
# Verificar instalacion
$ placetopay version
loginCorre placetopay login. Ingresa tu Login y Secret Key (del panel de tu comercio en PlacetoPay).
El wizard te pide el país (co, ec, cl, pa...) y el ambiente (test / production).
login valida tus credenciales, conectividad y TLS automáticamente. Sin pasos extra.
Ejecuta placetopay checkout create o clona un proyecto de ejemplo con placetopay samples create.
CLI para prototipar y debuggear. SDKs para integrar en tu aplicación. Misma API, misma plataforma.
# Instalar el SDK de Node.js
$ npm install @placetopay/node
// Inicializar el cliente
import PlaceToPay from '@placetopay/node';
const client = new PlaceToPay({
secretKey: 'sk_test_xxx',
baseUrl: 'http://localhost:3000/api/v1'
});
# Instalar el SDK de Python
$ pip install placetopay
# Inicializar el cliente
from placetopay import PlaceToPay
client = PlaceToPay(
secret_key="sk_test_xxx",
base_url="http://localhost:3000/api/v1"
)
# Instalar el SDK de PHP
$ composer require placetopay/blocks
// Inicializar el cliente
use PlaceToPay\Blocks\PlaceToPay;
$client = new PlaceToPay(
secretKey: 'sk_test_xxx',
baseUrl: 'http://localhost:3000/api/v1'
);
CLI + SDK: Usa el CLI (placetopay doctor, test-cards, checkout create) para explorar y prototipar.
Cuando estés listo para producción, usa el SDK en tu lenguaje favorito con la misma API.
Tres caminos: proyecto nuevo con CLI, agrega a tu app existente, o integra directamente con el SDK.
Paso 1 Configura credenciales (del panel de PlacetoPay)
$ placetopay login
Login: tu_login_aqui
Secret Key: ••••••••
Country: co
Environment: test
✓ All set!
Paso 2 Genera un proyecto con checkout + webhooks
$ placetopay samples create
Which sample? [1]: 1 (checkout-basic)
Language [node]: node
Directory [checkout-basic]: checkout-basic
✓ Project generated
✓ .env configured with your credentials
Paso 3 Arranca tu app
$ cd checkout-basic
$ npm install && npm start
Checkout demo running at http://localhost:3000
Paso 4 Recibe webhooks (otra terminal)
$ placetopay listen --forward-to http://localhost:3000/webhook
⚡ Ready! Forwarding to http://localhost:3000/webhook
Paso 5 Prueba el flujo completo (otra terminal)
$ placetopay test-flow
✓ Session created (requestId: 3548901)
Opening payment page in browser...
Waiting for payment result....
● Payment APPROVED
Paso 1 Configura credenciales (del panel de PlacetoPay)
$ placetopay login
Login: tu_login_aqui
Secret Key: ••••••••
Country: co
Environment: test
✓ All set!
Paso 2 Genera integracion para tu framework
$ cd mi-proyecto
$ placetopay init
Detected framework: laravel
✓ app/Http/Controllers/PlacetopayWebhookController.php
✓ routes/placetopay.php
✓ .env (PLACETOPAY_LOGIN, SECRET, BASE_URL)
Paso 3 Arranca tu app como siempre
$ php artisan serve
Starting Laravel development server: http://127.0.0.1:8000
Paso 4 Recibe webhooks (otra terminal)
$ placetopay listen --forward-to http://localhost:8000/webhook/placetopay
⚡ Ready! Forwarding to http://localhost:8000/webhook/placetopay
Paso 5 Prueba el flujo completo (otra terminal)
$ placetopay test-flow
✓ Session created (requestId: 3548901)
Opening payment page in browser...
Waiting for payment result....
● Payment APPROVED
Paso 1 Instala el SDK
$ npm install @placetopay/node
Paso 2 Inicializa el cliente
import PlaceToPay from '@placetopay/node';
const client = new PlaceToPay({
secretKey: 'sk_test_xxx',
baseUrl: 'http://localhost:3000/api/v1'
});
Paso 3 Crea un producto y precio
const product = await client.products.create({
name: 'Laptop ThinkPad',
description: 'Laptop profesional'
});
const price = await client.prices.create({
productId: product.id,
unitAmount: 150000,
currency: 'usd'
});
Paso 4 Crea una sesion de checkout
const session = await client.checkoutSessions.create({
lineItems: [{ price: price.id, quantity: 1 }],
successUrl: 'https://mitienda.com/success',
cancelUrl: 'https://mitienda.com/cancel'
});
console.log(session.url); // Redirige al usuario aqui
Paso 5 Maneja el webhook
app.post('/webhook', (req, res) => {
const event = client.webhooks.constructEvent(
req.body, req.headers['x-signature'], 'whsec_xxx'
);
if (event.type === 'checkout.completed') {
console.log('Pago exitoso!', event.data);
}
res.json({ received: true });
});
Credenciales en keyring
Proyecto con .env listo
Webhooks en localhost
Pago end-to-end
Así funciona el flujo completo de un pago con el CLI.
Tu backend llama al CLI para generar una URL de pago.
checkout create
Redirige al usuario a la processUrl para completar el pago.
processUrl
Verifica el estado de la transacción con el requestId.
checkout query
Recibe notificaciones automáticas cuando cambie el estado del pago.
listen
Genera una sesión de checkout y obtén la URL donde tu cliente completará el pago. El CLI inyecta automáticamente la autenticación WSSE en cada request.
Tip: Usa --output json para obtener la respuesta completa y extraer el requestId y processUrl desde tu aplicación.
Integración web: Tu backend ejecuta el CLI (o llama la API directamente usando la misma autenticación WSSE), obtiene el processUrl y redirige al usuario a esa URL.
# Crear sesión de pago
$ placetopay checkout create \
--reference=ORDER-2024-001 \
--description="Laptop Lenovo ThinkPad" \
--amount=150000 \
--currency=USD \
--return-url=https://mitienda.com/order/001/return \
--buyer-name="María García" \
--buyer-email=maria@email.com
✓ Session created
Request ID: 3548901
Process URL: https://checkout.placetopay.ec/spa/session/...
Status: OK
Expires: 2026-12-15T14:30:00-05:00
# Consultar después del pago
$ placetopay checkout query --request-id=3548901
✓ Session status
Request ID: 3548901
Status: APPROVED
Message: Aprobada
// Crear sesión de checkout
const session = await client.checkoutSessions.create({
lineItems: [{
price: 'price_xxx',
quantity: 1
}],
successUrl: 'https://mitienda.com/success',
cancelUrl: 'https://mitienda.com/cancel'
});
console.log(session.url);
// → https://checkout.placetopay.ec/spa/session/...
// Consultar después del pago
const result = await client.checkoutSessions.retrieve(
session.id
);
console.log(result.status); // → "completed"
# Crear sesión de checkout
session = client.checkout_sessions.create(
line_items=[{
"price": "price_xxx",
"quantity": 1
}],
success_url="https://mitienda.com/success",
cancel_url="https://mitienda.com/cancel"
)
print(session.url)
# → https://checkout.placetopay.ec/spa/session/...
# Consultar después del pago
result = client.checkout_sessions.retrieve(session.id)
print(result.status) # → "completed"
// Crear sesión de checkout
$session = $client->checkoutSessions->create([
'lineItems' => [[
'price' => 'price_xxx',
'quantity' => 1
]],
'successUrl' => 'https://mitienda.com/success',
'cancelUrl' => 'https://mitienda.com/cancel'
]);
echo $session->url;
// → https://checkout.placetopay.ec/spa/session/...
// Consultar después del pago
$result = $client->checkoutSessions->retrieve($session->id);
echo $result->status; // → "completed"
Tokeniza la tarjeta en la primera transacción con --subscribe.
Después usa el token almacenado para cobrar sin que el usuario
vuelva a ingresar sus datos de pago.
Flujo completo:
1. checkout create --subscribe → el usuario paga
2. checkout query → extraer token de subscription.instrument
3. checkout collect --token=abc... → cobros futuros sin intervención del usuario
# Paso 1: Crear sesión con suscripción
$ placetopay checkout create \
--reference=SUB-001 \
--amount=5000 \
--currency=USD \
--return-url=https://miapp.com/return \
--subscribe
# Paso 2: Consultar y extraer token
$ placetopay checkout query \
--request-id=3549012 \
--output json | jq '.subscription.instrument[0].value'
"a3b1c9d8e7f6..."
# Paso 3: Cobrar con el token
$ placetopay checkout collect \
--token=a3b1c9d8e7f6... \
--reference=COLLECT-001 \
--amount=5000 \
--currency=USD \
--payer-name=María \
--payer-surname=García \
--payer-email=maria@email.com
✓ Collection completed
Request ID: 3549034
Status: APPROVED
// Crear suscripción recurrente
const subscription = await client.subscriptions.create({
customerId: 'cust_xxx',
items: [{
price: 'price_xxx',
quantity: 1
}]
});
console.log(subscription.status);
// → "active"
// Cobro recurrente (se ejecuta automáticamente)
// O cobro manual con token:
const payment = await client.paymentIntents.create({
amount: 5000,
currency: 'usd',
customerId: 'cust_xxx',
paymentMethod: 'pm_token_xxx'
});
# Crear suscripción recurrente
subscription = client.subscriptions.create(
customer_id="cust_xxx",
items=[{
"price": "price_xxx",
"quantity": 1
}]
)
print(subscription.status)
# → "active"
# Cobro manual con token:
payment = client.payment_intents.create(
amount=5000,
currency="usd",
customer_id="cust_xxx",
payment_method="pm_token_xxx"
)
// Crear suscripción recurrente
$subscription = $client->subscriptions->create([
'customerId' => 'cust_xxx',
'items' => [[
'price' => 'price_xxx',
'quantity' => 1
]]
]);
echo $subscription->status;
// → "active"
// Cobro manual con token:
$payment = $client->paymentIntents->create([
'amount' => 5000,
'currency' => 'usd',
'customerId' => 'cust_xxx',
'paymentMethod' => 'pm_token_xxx'
]);
Recibe webhooks de PlacetoPay directamente en tu máquina de desarrollo. El CLI valida la firma SHA-1 y reenvía las notificaciones a tu aplicación local.
Validación de firma: Cada notificación incluye una firma calculada como
SHA-1(requestId + status + date + secretKey). El CLI la verifica automáticamente.
Tunnel: Usa --tunnel para exponer tu localhost con una URL pública
(usa cloudflared, ngrok o SSH automáticamente). Ideal para recibir webhooks reales desde PlacetoPay.
# Escuchar webhooks en localhost
$ placetopay listen \
--forward-to=http://localhost:3000/webhook
⚡ Ready! Forwarding to http://localhost:3000/webhook
# Cuando llega una notificación:
→ [14:32:01] APPROVED request:3548901 ref:ORDER-001
Forward → http://localhost:3000/webhook [200]
# Con tunnel (URL publica para webhooks reales)
$ placetopay listen \
--forward-to=http://localhost:3000/webhook \
--tunnel
→ Tunnel active: https://abc123.trycloudflare.com
Usa esta URL como notificationUrl
# Simular un webhook de prueba
$ placetopay trigger session.approved \
--forward-to=http://localhost:3000/webhook
// Express — Recibir y verificar webhooks
import express from 'express';
import PlaceToPay from '@placetopay/node';
const client = new PlaceToPay({
secretKey: 'sk_test_xxx'
});
app.post('/webhook', express.raw({ type: 'application/json' }), (req, res) => {
const signature = req.headers['x-signature'];
let event;
try {
event = client.webhooks.constructEvent(
req.body, signature, 'whsec_xxx'
);
} catch (err) {
return res.status(400).send(`Webhook Error: ${err.message}`);
}
switch (event.type) {
case 'checkout.completed':
console.log('Pago completado:', event.data);
break;
case 'checkout.expired':
console.log('Sesión expirada:', event.data);
break;
}
res.json({ received: true });
});
# Flask — Recibir y verificar webhooks
from flask import Flask, request, jsonify
from placetopay import PlaceToPay
client = PlaceToPay(secret_key="sk_test_xxx")
@app.route("/webhook", methods=["POST"])
def webhook():
signature = request.headers.get("X-Signature")
try:
event = client.webhooks.construct_event(
request.data, signature, "whsec_xxx"
)
except ValueError:
return jsonify(error="Invalid signature"), 400
if event.type == "checkout.completed":
print("Pago completado:", event.data)
elif event.type == "checkout.expired":
print("Sesión expirada:", event.data)
return jsonify(received=True)
// Laravel — Recibir y verificar webhooks
// routes/web.php
Route::post('/webhook', [WebhookController::class, 'handle']);
// app/Http/Controllers/WebhookController.php
use PlaceToPay\Blocks\PlaceToPay;
class WebhookController extends Controller
{
public function handle(Request $request)
{
$client = new PlaceToPay(
secretKey: config('services.placetopay.secret')
);
$signature = $request->header('X-Signature');
$event = $client->webhooks->constructEvent(
$request->getContent(), $signature, 'whsec_xxx'
);
match ($event->type) {
'checkout.completed' =>
logger('Pago completado:', $event->data),
'checkout.expired' =>
logger('Sesión expirada:', $event->data),
};
return response()->json(['received' => true]);
}
}
Procesa pagos directamente con tarjeta a través del gateway, sin redirigir al usuario. Incluye tokenización directa, consultas, búsquedas y operaciones sobre transacciones.
Operaciones soportadas:
process — Pago directo con tarjeta o token
tokenize — Crear token reutilizable
query / search — Consultar transacciones
transaction — Reverse, refund, void, capture
3ds-lookup / 3ds-query — 3D Secure
report — Reportes de transacciones
# Tokenizar una tarjeta
$ placetopay gateway tokenize \
--card-number=4110760000000008 \
--card-expiration=12/28
✓ Card tokenized
Token: tok_a3b1c9d8...
Franchise: visa
Last Digits: 0008
# Pago directo con el token
$ placetopay gateway process \
--token=tok_a3b1c9d8... \
--reference=GW-001 \
--amount=10000 \
--currency=USD \
--payer-name=María \
--payer-surname=García \
--payer-email=maria@email.com
✓ Payment processed
Status: APPROVED
Internal Ref: 987654
Authorization: AUTH123
# Reversar si es necesario
$ placetopay gateway transaction \
--action=reverse \
--internal-reference=987654
// Tokenizar una tarjeta
const token = await client.gateway.tokenize({
card: {
number: '4110760000000008',
expiration: '12/28',
cvv: '123'
}
});
console.log(token.token); // → "tok_a3b1c9d8..."
// Pago directo con el token
const payment = await client.gateway.process({
payment: {
reference: 'GW-001',
amount: { total: 10000, currency: 'USD' }
},
instrument: { token: token.token },
buyer: {
name: 'María',
surname: 'García',
email: 'maria@email.com'
}
});
console.log(payment.status); // → "APPROVED"
# Tokenizar una tarjeta
token = client.gateway.tokenize(card={
"number": "4110760000000008",
"expiration": "12/28",
"cvv": "123"
})
print(token.token) # → "tok_a3b1c9d8..."
# Pago directo con el token
payment = client.gateway.process(
payment={
"reference": "GW-001",
"amount": { "total": 10000, "currency": "USD" }
},
instrument={ "token": token.token },
buyer={
"name": "María",
"surname": "García",
"email": "maria@email.com"
}
)
print(payment.status) # → "APPROVED"
// Tokenizar una tarjeta
$token = $client->gateway->tokenize([
'card' => [
'number' => '4110760000000008',
'expiration' => '12/28',
'cvv' => '123'
]
]);
echo $token->token; // → "tok_a3b1c9d8..."
// Pago directo con el token
$payment = $client->gateway->process([
'payment' => [
'reference' => 'GW-001',
'amount' => ['total' => 10000, 'currency' => 'USD']
],
'instrument' => ['token' => $token->token],
'buyer' => [
'name' => 'María',
'surname' => 'García',
'email' => 'maria@email.com'
]
]);
echo $payment->status; // → "APPROVED"
Genera links de pago que puedes enviar por email, WhatsApp o cualquier canal. Controla cuántos pagos permite, métodos de pago y fecha de expiración.
Casos de uso:
Facturas por correo, cobros por WhatsApp, páginas de donación, suscripciones manuales, pagos recurrentes sin integración web.
# Crear un link de pago
$ placetopay payment-link create \
--name="Factura Enero 2026" \
--reference=INV-001 \
--description="Servicios enero" \
--amount=150000 \
--currency=USD \
--expiration-date="2026-02-28 23:59:59"
✓ Payment link created
Link ID: 42
URL: https://pay.placetopay.com/link/42
# Consultar estado del link
$ placetopay payment-link get \
--link-id=42
# Desactivar el link
$ placetopay payment-link disable \
--link-id=42
// Crear un link de pago
const link = await client.paymentLinks.create({
name: 'Factura Enero 2026',
lineItems: [{
price: 'price_xxx',
quantity: 1
}],
expiresAt: '2026-02-28T23:59:59Z'
});
console.log(link.url);
// → https://pay.placetopay.com/link/42
// Consultar estado del link
const status = await client.paymentLinks.retrieve(link.id);
// Desactivar el link
await client.paymentLinks.deactivate(link.id);
# Crear un link de pago
link = client.payment_links.create(
name="Factura Enero 2026",
line_items=[{
"price": "price_xxx",
"quantity": 1
}],
expires_at="2026-02-28T23:59:59Z"
)
print(link.url)
# → https://pay.placetopay.com/link/42
# Consultar estado del link
status = client.payment_links.retrieve(link.id)
# Desactivar el link
client.payment_links.deactivate(link.id)
// Crear un link de pago
$link = $client->paymentLinks->create([
'name' => 'Factura Enero 2026',
'lineItems' => [[
'price' => 'price_xxx',
'quantity' => 1
]],
'expiresAt' => '2026-02-28T23:59:59Z'
]);
echo $link->url;
// → https://pay.placetopay.com/link/42
// Consultar estado del link
$status = $client->paymentLinks->retrieve($link->id);
// Desactivar el link
$client->paymentLinks->deactivate($link->id);
Integración nativa con el SDK en tu backend. Sin subprocesos, sin CLI como dependencia.
// routes/checkout.js
import PlaceToPay from '@placetopay/node';
const client = new PlaceToPay({
secretKey: process.env.PLACETOPAY_SECRET_KEY,
baseUrl: process.env.PLACETOPAY_BASE_URL
});
app.post('/create-payment', async (req, res) => {
const session = await client.checkoutSessions.create({
lineItems: [{ price: req.body.priceId, quantity: 1 }],
successUrl: 'https://mitienda.com/success',
cancelUrl: 'https://mitienda.com/cancel'
});
// Redirigir al usuario al checkout
res.json({ url: session.url });
});
app.get('/success', async (req, res) => {
const session = await client.checkoutSessions.retrieve(
req.query.session_id
);
res.render('payment-result', { status: session.status });
});
// app/Http/Controllers/CheckoutController.php
use PlaceToPay\Blocks\PlaceToPay;
class CheckoutController extends Controller
{
private PlaceToPay $client;
public function __construct()
{
$this->client = new PlaceToPay(
secretKey: config('services.placetopay.secret'),
baseUrl: config('services.placetopay.base_url')
);
}
public function createPayment(Request $request)
{
$session = $this->client->checkoutSessions->create([
'lineItems' => [[
'price' => $request->input('priceId'),
'quantity' => 1
]],
'successUrl' => 'https://mitienda.com/success',
'cancelUrl' => 'https://mitienda.com/cancel'
]);
return redirect($session->url);
}
public function success(Request $request)
{
$session = $this->client->checkoutSessions->retrieve(
$request->query('session_id')
);
return view('payment.result', ['status' => $session->status]);
}
}
# app.py
from flask import Flask, request, redirect, render_template, jsonify
from placetopay import PlaceToPay
import os
client = PlaceToPay(
secret_key=os.environ["PLACETOPAY_SECRET_KEY"],
base_url=os.environ["PLACETOPAY_BASE_URL"]
)
@app.route("/create-payment", methods=["POST"])
def create_payment():
session = client.checkout_sessions.create(
line_items=[{
"price": request.json["priceId"],
"quantity": 1
}],
success_url="https://mitienda.com/success",
cancel_url="https://mitienda.com/cancel"
)
return jsonify(url=session.url)
@app.route("/success")
def success():
session = client.checkout_sessions.retrieve(
request.args["session_id"]
)
return render_template("payment_result.html", status=session.status)
CLI + SDK: Usa el CLI para desarrollo local, testing y debugging (placetopay listen,
test-flow, logs tail). Usa el SDK en tu código de producción para llamadas directas a la API sin dependencias externas.
Referencia rápida de los comandos disponibles. Usa --help en cualquier comando para más detalles.
| Comando | Descripción | Flags principales |
|---|---|---|
| Configuración | ||
login |
Wizard interactivo: pide credenciales, valida conectividad | --profile |
config set |
Configura país, ambiente y credenciales | <key> <value> |
config get |
Muestra un valor de configuración | <key> |
config list |
Muestra toda la configuración del perfil activo | — |
profile list |
Lista perfiles disponibles | — |
profile use |
Cambia el perfil activo | <name> |
doctor |
Verifica configuración, credenciales y conectividad | — |
auth generate |
Genera un objeto de autenticación WSSE (debug) | --output json |
| Checkout | ||
checkout create |
Crea una nueva sesión de pago | --reference --amount --currency --return-url --subscribe --type --recurring-* --tax-* --allow-partial |
checkout query |
Consulta el estado de una sesión | --request-id |
checkout cancel |
Cancela una sesión pendiente | --request-id |
checkout collect |
Cobra usando un token almacenado | --token --reference --amount --payer-* |
checkout reverse |
Reversa total o parcial | --internal-reference --amount --currency |
checkout transaction |
Operaciones sobre pre-autorizaciones | --action --internal-reference --amount |
checkout invalidate-token |
Invalida un token almacenado | --token |
| Gateway (pago directo) | ||
gateway process |
Pago directo con tarjeta o token | --card-number --token --amount --payer-* |
gateway query |
Consulta transacción por referencia interna | --internal-reference |
gateway search |
Busca transacciones por referencia + monto | --reference --amount --currency |
gateway transaction |
Reverse, refund, void, capture | --action --internal-reference |
gateway tokenize |
Crea token reutilizable desde tarjeta | --card-number --card-expiration |
gateway token-query |
Consulta detalles de un token | --token |
gateway token-invalidate |
Invalida un token del gateway | --token |
gateway info |
Info de instrumento de pago | --card-number |
gateway report request |
Solicita reporte de transacciones | --start-date --end-date --state |
gateway report download |
Descarga un reporte generado | --report-id |
gateway 3ds-lookup |
Inicia autenticación 3D Secure | --card-number --amount --return-url |
gateway 3ds-query |
Consulta resultado 3DS | --session-id |
| Payment Links | ||
payment-link create |
Crea un link de pago compartible | --name --reference --amount --expiration-date |
payment-link get |
Consulta detalles de un link | --link-id |
payment-link disable |
Desactiva un link de pago | --link-id |
| Webhooks & Eventos | ||
listen |
Escucha webhooks en localhost, almacena eventos | --forward-to --port --tunnel |
trigger |
Simula un evento webhook | session.approved session.rejected session.pending session.expired |
events list |
Lista eventos webhook recibidos | --last |
events resend |
Re-envía un evento a una URL | --forward-to --last --count |
| Developer Tools | ||
init |
Detecta framework y genera webhook handler + .env | --dir |
test-flow |
Crea sesion, abre browser, espera resultado APPROVED/REJECTED | --amount --currency --no-open --poll-interval |
samples list |
Lista proyectos de ejemplo disponibles | — |
samples create |
Genera un proyecto con tus keys auto-configuradas (offline) | — |
fixtures run |
Ejecuta un archivo de fixtures (siembra datos de prueba) | <file.json> |
fixtures init |
Crea un archivo de fixture de ejemplo | — |
logs tail |
Streaming en tiempo real de llamadas API | --json |
logs list |
Muestra las últimas llamadas API | --last |
| Utilidades | ||
test-cards |
Lista tarjetas de prueba disponibles | --status --brand |
open |
Abre una URL de sesión en el navegador | <url> |
completion |
Genera autocompletado para tu shell | bash zsh fish powershell |
version |
Muestra la versión del CLI (notifica si hay update) | — |
Instala, configura, genera tu proyecto, recibe webhooks y prueba el flujo completo.
# 1. Configura tus credenciales de sandbox
$ placetopay login
# 2. Genera un proyecto con checkout + webhooks
$ placetopay samples create
# 3. Arranca tu app
$ cd checkout-basic && npm install && npm start
# 4. Recibe webhooks (otra terminal)
$ placetopay listen --forward-to http://localhost:3000/webhook
# 5. Prueba el pago completo (otra terminal)
$ placetopay test-flow
Alternativa a config set para CI/CD y contenedores Docker.
# .env (nunca commitear al repo)
PLACETOPAY_LOGIN=tu_login_aqui
PLACETOPAY_SECRET=tu_secret_key_aqui
PLACETOPAY_BASE_URL=https://checkout-test.placetopay.com
# Docker
$ docker build -t placetopay-cli https://github.com/step-labs-2026/placetopay-cli.git
$ docker run -e PLACETOPAY_LOGIN=xxx -e PLACETOPAY_SECRET=yyy \
placetopay-cli checkout create --reference=ORDER-001 ...
Login interactivo, perfiles, fixtures, logs en tiempo real, replay de eventos y proyectos de ejemplo.
placetopay login te pide las credenciales de tu comercio
y valida todo automáticamente. Con --profile puedes mantener
múltiples ambientes (test, staging, producción) sin pisar credenciales.
Multi-perfil:
1. placetopay login --profile staging → configura staging
2. placetopay profile use staging → cambia perfil activo
3. placetopay checkout create --profile production → usa perfil puntual
# Login interactivo
$ placetopay login
▸ PlacetoPay CLI Login
Enter your API credentials (from your PlacetoPay merchant panel).
Login: mi_login
Secret Key: ••••••••
Country: ec
Environment: test
✓ Login saved to keyring
✓ Secret key saved to keyring
✓ Config saved (country=ec, environment=test)
✓ Auth generation ok
✓ API connectivity ok
# Gestionar perfiles
$ placetopay profile list
▸ default (active)
staging
production
fixtures run ejecuta un archivo JSON con llamadas API secuenciales.
Cada fixture puede referenciar resultados anteriores con ${nombre:campo}.
samples create genera un proyecto de ejemplo (bundled en el binario, sin internet)
con tus API keys pre-configuradas en .env.
Templates en fixtures:
${session:requestId} → referencia un fixture anterior
${.env:MY_VAR} → variable de entorno
# Crear fixture de ejemplo
$ placetopay fixtures init
✓ Created fixtures.json
# Ejecutar fixtures
$ placetopay fixtures run fixtures.json
▸ Running: Example checkout fixture
▸ 2 fixture(s) to execute
[1/2] POST /api/session
✓ OK — Session created
Request ID: 3549100
[2/2] POST /api/session/3549100
✓ APPROVED
# Generar proyecto de ejemplo (offline, bundled en el binario)
$ placetopay samples create
1. checkout-basic — checkout + webhooks
2. webhook-listener — solo webhook handler
Which sample? [1]: 1
Language [node]: node
✓ Project generated
✓ .env configured with your credentials
# Inicializar en proyecto existente
$ placetopay init
Detected framework: node
✓ placetopay.js
✓ placetopay-webhook.js
✓ .env
Cada llamada API se registra automáticamente. logs tail te muestra
un streaming en vivo de las requests — endpoint, status, duración y request ID.
Los eventos webhook recibidos por listen se almacenan y puedes
re-enviarlos con events resend.
Auto-update: El CLI verifica si hay versiones nuevas en cada ejecución (cache de 24h) y te notifica automáticamente.
# Streaming de logs API en tiempo real
$ placetopay logs tail
⚡ Tailing API logs... (Ctrl+C to stop)
[14:32:01] 200 POST /api/session 342ms id:3549100
[14:32:05] 200 POST /api/session/3549100 198ms id:3549100
[14:33:12] 401 POST /api/session 89ms ERR
# Listar eventos webhook recibidos
$ placetopay events list
2026-02-27 14:35:01 APPROVED req:3549100 ref:ORDER-001
# Re-enviar el último evento
$ placetopay events resend --last --forward-to http://localhost:3000/webhook
✓ Resent evt_3549100 (APPROVED) → localhost:3000 [200]