Ir al contenido

Agregar la integración de Stripe

Stripe es una plataforma de procesamiento de pagos en línea diseñada para negocios en internet. Integrar Stripe permite que tu aplicación maneje transacciones, suscripciones y datos financieros de forma segura.

Después de seleccionar Stripe de la lista de integraciones, aparecerá un modal de configuración. Debes proporcionar las siguientes credenciales desde tu Panel de Stripe para establecer la conexión:

  • Entrada: Ingresa tu Clave Secreta de Stripe privada (generalmente comienza con sk_) en el campo Secret Key. Esta clave permite al backend autenticar solicitudes seguras.
  • Entrada: Ingresa tu Clave Publicable de Stripe pública (generalmente comienza con pk_) en el campo Publishable Key. Esta clave se utiliza para la implementación en el frontend.
  • Entrada: Selecciona el contexto de entorno apropiado del menú desplegable (por ejemplo, Test para desarrollo/modo sandbox o Production para procesamiento en vivo).

Una vez configuradas las claves y el entorno:

  1. Revisa la barra de estado (actualmente muestra Not Connected).
  2. Haz clic en el botón negro Add en la parte inferior derecha para guardar las credenciales y activar la integración de pagos.

Configuración de Stripe

Integración de Stripe


Crea una nueva configuración de Stripe para el proyecto y entorno.

Mutation:

mutation ConfigureStripe (
$input: ConfigureStripeInput!
) {
configureStripe (
input: $input
) {
id
publishableKey
webhookUrl
}
}

Input:

input ConfigureStripeInput {
secretKey: String! # Stripe secret key (sk_test_... or sk_live_...)
publishableKey: String! # Stripe publishable key (pk_test_... or pk_live_...)
environment: StripeEnvironment! # TEST or LIVE
webhookSecret: String # Webhook signing secret (optional)
}

Response:

type ConfigureStripePayload {
id: ID! # Configuration ID
publishableKey: String! # Publishable key
webhookUrl: String! # Generated webhook URL
}

Example:

{
"input": {
"secretKey": "sk_test_...",
"publishableKey": "pk_test_...",
"environment": "TEST",
"webhookSecret": "whsec_..."
}
}

Notas:

  • La clave secreta se cifra con AES-256-GCM antes del almacenamiento
  • Solo una configuración por combinación de proyecto/entorno
  • Devuelve error si la configuración ya existe

Actualiza una configuración de Stripe existente.

Mutation:

mutation UpdateStripeConfig (
$input: UpdateStripeConfigInput!
) {
updateStripeConfig (
input: $input
) {
id
publishableKey
webhookUrl
}
}

Input:

input UpdateStripeConfigInput {
secretKey: String # Optional
publishableKey: String # Optional
environment: StripeEnvironment # Optional
webhookSecret: String # Optional
}

Response:

type UpdateStripeConfigPayload {
id: ID!
publishableKey: String!
webhookUrl: String!
}

Notas:

  • Todos los campos son opcionales
  • Solo se actualizan los campos proporcionados
  • La clave secreta se cifra si se proporciona

Recupera un solo cliente por ID.

Query:

query stripe_customer{
stripe_customer(
id: "cus_Ts..."
)
{
id
name
email
phone
description
metadata
object
createdAt
}
}

Lista clientes con paginación y filtrado opcional.

Query:

query stripe_customers (
$first: Int,
$after: String,
$customerId: String
) {
stripe_customers (
first: $first,
after: $after,
customerId: $customerId
) {
edges {
node {
id
name
email
phone
description
createdAt
}
cursor
}
pageInfo {
hasNextPage
hasPreviousPage
startCursor
endCursor
}
}
}

Parameters:

  • first: Número de elementos a devolver (predeterminado: 10)
  • after: Cursor para paginación
  • customerId: Filtrar por ID de cliente (opcional)

Crea un nuevo cliente.

Mutation:

mutation stripe_createCustomer {
stripe_createCustomer (
input: {
name: "Customer",
email: "example@archie.com",
phone: "+573001230001",
description: "Description Example"
metadata: {
data1: "Example data1",
data2: "Example data2"
}
}
)
{
id
name
email
phone
description
metadata
object
createdAt
}
}

Actualiza un cliente existente.

Mutation:

mutation stripe_updateCustomer {
stripe_updateCustomer(
id: "cus_Ts...",
input: {
name: "Customer",
email: "example@archie.com",
phone: "+573001230001",
description:"Description Example",
metadata: {
data1: "Example data1 updated",
data2: "Example data2 updated"
}
}
)
{
id
name
email
phone
description
metadata
object
createdAt
}
}

Notas:

  • Todos los campos son opcionales
  • Solo se actualizan los campos proporcionados

Elimina un cliente.

Mutation:

mutation stripe_deleteCustomer {
stripe_deleteCustomer (
id: "cus_Ts...")
}

Response:

  • Devuelve true en caso de éxito
  • Devuelve error si no se encuentra el cliente

Recupera una sola intención de pago por ID.

Query:

query stripe_paymentIntent {
stripe_paymentIntent (
id: "pi_3Su..."
)
{
id
customerId
paymentMethodId
currency
amount
status
metadata
object
clientSecret
createdAt
}
}

Lista intenciones de pago con paginación y filtrado opcional.

Query:

query stripe_paymentIntents (
$first: Int,
$after: String,
$customerId: String
) {
stripe_paymentIntents (
first: $first,
after: $after,
customerId: $customerId
) {
edges {
node {
id
customerId
paymentMethodId
currency
amount
status
metadata
object
clientSecret
createdAt
}
cursor
}
pageInfo {
hasPreviousPage
hasNextPage
startCursor
endCursor
}
}
}

Parameters:

  • first: Número de elementos a devolver (predeterminado: 10)
  • after: Cursor para paginación
  • customerId: Filtrar por ID de cliente (opcional)

Crea una nueva intención de pago.

Mutation:

mutation stripe_createPaymentIntent {
stripe_createPaymentIntent (
input: {
amount: 12.35,
currency: "usd",
customerId: "cus_Ts...",
paymentMethodId: "pm_1Su...",
automaticPaymentMethods: true
}
)
{
id
customerId
paymentMethodId
currency
amount
status
metadata
object
clientSecret
createdAt
}
}

Notas:

  • Se devuelve clientSecret para confirmación en el frontend
  • Usa automaticPaymentMethods: true para integración con Stripe.js

Actualiza una intención de pago antes de la confirmación.

Mutation:

mutation stripe_updatePaymentIntent{
stripe_updatePaymentIntent(
id: "pi_3S...",
input: {
amount: 36.92,
currency: "usd",
paymentMethodId: "pm_1Su..."
metadata:{
data1: "Example data1"
}
}
) {
id
customerId
paymentMethodId
currency
amount
status
metadata
object
clientSecret
createdAt
}
}

Notas:

  • Solo se puede actualizar antes de la confirmación
  • Todos los campos son opcionales

Confirma una intención de pago.

Mutation:

mutation stripe_confirmPaymentIntent{
stripe_confirmPaymentIntent(
id: "pi_3Su..."
input: {
paymentMethodId: "pm_1Su...",
returnUrl: "http://localhost:3000/successful-payment"
}
) {
id
customerId
paymentMethodId
currency
amount
status
metadata
object
clientSecret
createdAt
}
}

Notas:

  • Requerido para completar el pago
  • Puede requerir autenticación 3D Secure
  • Devuelve estado actualizado (succeeded, requires_action, etc.)

Cancela una intención de pago.

Mutation:

mutation stripe_cancelPaymentIntent {
stripe_cancelPaymentIntent(
id: "pi_3Su..."
) {
id
customerId
paymentMethodId
currency
amount
status
metadata
object
clientSecret
createdAt
}
}

Notas:

  • Solo puede cancelar intenciones de pago que no hayan tenido éxito o sido canceladas
  • El estado cambia a “canceled”

Recupera una sola suscripción por ID.

Query:

query stripe_subscription {
stripe_subscription(id: "sub_1Su...") {
id
customerId
status
currentPeriodStart
currentPeriodEnd
createdAt
cancelAtPeriodEnd
metadata
object
items {
data {
id
priceId
quantity
}
}
}
}

Lista suscripciones con paginación y filtrado opcional.

Query:

query stripe_subscriptions (
$first: Int,
$after: String,
$customerId: String
) {
stripe_subscriptions (
first: $first,
after: $after,
customerId: $customerId
) {
edges {
node {
id
customerId
status
currentPeriodStart
currentPeriodEnd
createdAt
cancelAtPeriodEnd
metadata
object
items {
data {
id
priceId
quantity
}
}
}
cursor
}
pageInfo {
hasPreviousPage
hasNextPage
startCursor
endCursor
}
}
}

Parameters:

  • first: Número de elementos a devolver (predeterminado: 10)
  • after: Cursor para paginación
  • customerId: Filtrar por ID de cliente (opcional)
  • status: Filtrar por estado (opcional)

Crea una nueva suscripción.

Mutation:

mutation stripe_createSubscription {
stripe_createSubscription (
input: {
customerId: "cus_TsQ...",
items: {
priceId: "price_1Su...",
quantity: 1
},
metadata: {
data1: "Example data1"
},
trialPeriodDays: 0
}
) {
id
customerId
status
currentPeriodStart
currentPeriodEnd
createdAt
cancelAtPeriodEnd
metadata
object
items {
data {
id
priceId
quantity
}
}
}
}

Notas:

  • paymentBehavior puede ser “default_incomplete” para suscripciones que requieren método de pago
  • El periodo de prueba se especifica en días
  • La última factura e intención de pago se expanden automáticamente

Actualiza una suscripción existente.

Mutation:

mutation stripe_updateSubscription {
stripe_updateSubscription(
id: "sub_1Sv..."
input: {
cancelAtPeriodEnd: false
metadata: {
data2: "Example data2"
}
}
) {
id
customerId
status
currentPeriodStart
currentPeriodEnd
createdAt
cancelAtPeriodEnd
metadata
object
items {
data {
id
priceId
quantity
}
}
}
}

Cancela una suscripción.

Mutation:

mutation stripe_cancelSubscription {
stripe_cancelSubscription (
cancelAtPeriodEnd: true,
id: "sub_1Sv..."
) {
id
customerId
status
currentPeriodStart
currentPeriodEnd
createdAt
cancelAtPeriodEnd
metadata
object
items {
data {
id
priceId
quantity
}
}
}
}

Parameters:

  • id: ID de suscripción (requerido)
  • cancelAtPeriodEnd: Si es true, cancela al final del periodo; si es false, cancela inmediatamente (predeterminado: false)

Notas:

  • Cancelación inmediata: la suscripción termina ahora
  • Cancelación al final del periodo: la suscripción continúa hasta que termina el periodo actual

Lista productos con paginación.

Query:

query stripe_products (
$first: Int,
$after: String
) {
stripe_products (
first: $first,
after: $after
) {
edges {
node {
id
name
description
active
metadata
object
createdAt
}
cursor
}
pageInfo {
hasPreviousPage
hasNextPage
startCursor
endCursor
}
}
}

Crea un nuevo producto.

Mutation:

mutation stripe_createProduct {
stripe_createProduct (
input: {
name: "Product 01",
description: "Description product 01",
metadata: {
data1: "Example data1"
}
}
) {
id
name
description
active
metadata
object
createdAt
}
}

Lista precios con paginación y filtrado opcional.

Query:

query stripe_prices (
$first: Int,
$after: String,
$productId: String
) {
stripe_prices (
first: $first,
after: $after,
productId: $productId
) {
edges {
node {
id
productId
active
currency
unitAmount
object
metadata
createdAt
recurring {
interval
intervalCount
}
}
cursor
}
pageInfo {
hasPreviousPage
hasNextPage
startCursor
endCursor
}
}
}

Parameters:

  • first: Número de elementos a devolver (predeterminado: 10)
  • after: Cursor para paginación
  • productId: Filtrar por ID de producto (opcional)

Crea un nuevo precio.

Mutation:

mutation stripe_createPrice {
stripe_createPrice (
input: {
productId: "prod_Tst...",
unitAmount: 25.85,
currency: "usd",
recurring: {
interval: "month",
intervalCount: 1
},
metadata: {
data1: "Example data1"
}
}
) {
id
productId
currency
unitAmount
active
object
createdAt
metadata
recurring {
interval
intervalCount
}
}
}

Notas:

  • Omitir recurring para precios únicos
  • interval debe ser uno de: “day”, “week”, “month”, “year”

Recupera una sola factura por ID.

Query:

query stripe_invoice {
stripe_invoice (
id: "in_1Su..."
) {
id
customerId
subscriptionId
currency
amountPaid
amountDue
status
object
metadata
createdAt
lineItems {
data {
id
description
currency
amount
quantity
}
}
}
}

Notas:

  • El ID de suscripción se llena mediante expansión de API cuando está disponible

Lista facturas con paginación y filtrado opcional.

Query:

query stripe_invoices (
$first: Int,
$after: String,
$customerId: String,
$status: String
) {
stripe_invoices (
first: $first,
after: $after,
customerId: $customerId,
status: $status
) {
edges {
node {
id
customerId
subscriptionId
currency
amountPaid
amountDue
status
object
metadata
createdAt
lineItems {
data {
id
description
currency
amount
quantity
}
}
}
cursor
}
pageInfo {
hasPreviousPage
hasNextPage
startCursor
endCursor
}
}
}

Parameters:

  • first: Número de elementos a devolver (predeterminado: 10)
  • after: Cursor para paginación
  • customerId: Filtrar por ID de cliente (opcional)
  • status: Filtrar por estado (opcional)

Paga una factura programáticamente.

Mutation:

mutation stripe_payInvoice {
stripe_payInvoice (
id: "in_1Sv..."
) {
id
customerId
subscriptionId
currency
amountPaid
amountDue
status
object
metadata
createdAt
lineItems {
data {
id
description
currency
amount
quantity
}
}
}
}

Notas:

  • Intenta pagar la factura utilizando el método de pago predeterminado del cliente
  • Devuelve error si el pago falla
  • Actualiza el estado de la factura a “paid” en caso de éxito

Lista reembolsos con paginación y filtrado opcional.

Query:

query stripe_refunds (
$first: Int,
$after: String,
$paymentIntentId: String
) {
stripe_refunds (
first: $first,
after: $after,
paymentIntentId: $paymentIntentId
) {
edges {
node {
id
paymentIntentId
reason
status
currency
amount
metadata
object
createdAt
}
cursor
}
pageInfo {
hasPreviousPage
hasNextPage
startCursor
endCursor
}
}
}

Parameters:

  • first: Número de elementos a devolver (predeterminado: 10)
  • after: Cursor para paginación
  • paymentIntentId: Filtrar por ID de intención de pago (opcional)

Crea un reembolso para una intención de pago.

Mutation:

mutation stripe_createRefund {
stripe_createRefund (
input: {
paymentIntentId: "pi_3Sv...",
amount: 200,
reason: "requested_by_customer"
}
) {
id
reason
paymentIntentId
status
currency
amount
object
metadata
createdAt
}
}

Notas:

  • Omitir amount para reembolso completo
  • reason puede ser: “duplicate”, “fraudulent”, “requested_by_customer”
  • El estado del reembolso comienza como “pending” y se actualiza a “succeeded” o “failed”

Lista métodos de pago con paginación y filtrado opcional.

Query:

query stripe_paymentMethods (
$first: Int,
$after: String,
$customerId: String
) {
stripe_paymentMethods(
first: $first,
after: $after,
customerId: $customerId
) {
edges {
node {
id
customerId
type
object
metadata
createdAt
card {
brand
expMonth
expYear
last4
}
}
cursor
}
pageInfo {
hasPreviousPage
hasNextPage
startCursor
endCursor
}
}
}

Parameters:

  • first: Número de elementos a devolver (predeterminado: 10)
  • after: Cursor para paginación
  • customerId: Filtrar por ID de cliente (opcional)

Notas:

  • Solo se devuelve información segura de la tarjeta (últimos 4, marca, vencimiento)
  • Los números completos de tarjetas nunca se exponen

Adjunta un método de pago a un cliente.

Mutation:

mutation stripe_attachPaymentMethod {
stripe_attachPaymentMethod (
id: "pm_1Sv...",
input: {
customerId: "cus_Ts4..."
}
) {
id
customerId
type
card {
brand
expMonth
expYear
last4
}
metadata
object
createdAt
}
}

Notas:

  • El método de pago debe crearse primero (típicamente a través de Stripe.js)
  • Los métodos de pago adjuntos se pueden usar para suscripciones y pagos

Separa un método de pago de un cliente.

Mutation:

mutation stripe_detachPaymentMethod {
stripe_detachPaymentMethod (
id: "pm_1Sv..."
) {
id
customerId
type
card {
brand
expYear
expMonth
last4
}
metadata
object
createdAt
}
}

Notas:

  • Los métodos de pago separados ya no se pueden usar para pagos
  • Devuelve el método de pago con customerId establecido en null

Lista eventos de webhook recibidos por el servicio.

Query:

query ListWebhookEvents (
$first: Int,
$after: String
) {
stripe_webhookEvents (
first: $first,
after: $after
) {
edges {
node {
id
type
data
processed
createdAt
}
cursor
}
pageInfo {
hasNextPage
hasPreviousPage
endCursor
}
}
}

Response:

type StripeWebhookEvent {
id: ID!
type: String! # Event type (e.g., "payment_intent.succeeded")
data: String! # JSON string of event data
processed: Boolean! # Whether event has been processed
createdAt: Time!
}

Parameters:

  • first: Número de elementos a devolver (predeterminado: 10)
  • after: Cursor para paginación

Notas:

  • Los eventos se reciben automáticamente a través del endpoint de webhook
  • Los eventos se almacenan después de la verificación de firma
  • El campo data contiene la carga útil completa del evento como cadena JSON

Todas las consultas de lista admiten paginación basada en cursor utilizando el patrón de conexión Relay.

type PageInfo {
hasNextPage: Boolean!
hasPreviousPage: Boolean!
startCursor: String
endCursor: String
}
query ListCustomers (
$first: Int,
$after: String
) {
stripe_customers (
first: $first,
after: $after
) {
edges {
node {
id
email
}
cursor
}
pageInfo {
hasNextPage
endCursor
}
}
}

Flujo de paginación:

  1. Solicitud inicial: first: 10, after: null
  2. Usa pageInfo.endCursor de la respuesta como after en la siguiente solicitud
  3. Verifica hasNextPage para determinar si existen más páginas

Valores predeterminados:

  • first: Predeterminado a 10 si no se proporciona
  • after: Comienza desde el principio si no se proporciona

Todas las operaciones devuelven errores GraphQL con mensajes amigables para el usuario. Los errores se mapean desde los errores de API de Stripe para proporcionar comentarios claros.

Errores de configuración:

  • 400: Formato de claves de Stripe inválido
  • 404: Proyecto o configuración no encontrados
  • 400: La configuración ya existe

Errores de cliente:

  • 404: Cliente no encontrado
  • 400: Datos de cliente inválidos

Errores de intención de pago:

  • 404: Intención de pago no encontrada
  • 400: Monto o moneda inválidos
  • 402: Pago fallido (tarjeta rechazada, fondos insuficientes, etc.)

Errores de suscripción:

  • 404: Suscripción no encontrada
  • 400: Parámetros de suscripción inválidos
  • 400: No se puede actualizar una suscripción cancelada

Códigos de error de Stripe: Los códigos de error comunes de Stripe se mapean a mensajes amigables:

  • card_declined: “Tu tarjeta fue rechazada”
  • insufficient_funds: “Fondos insuficientes”
  • invalid_number: “Número de tarjeta inválido”
  • expired_card: “La tarjeta ha caducado”
  • incorrect_cvc: “Código CVC incorrecto”
{
"errors": [
{
"message": "Customer not found",
"extensions": {
"code": "NOT_FOUND",
"stripeErrorCode": "resource_missing"
}
}
],
"data": null
}

enum StripeEnvironment {
TEST # Test mode
LIVE # Live/production mode
}

El tipo escalar Map representa un mapa clave-valor donde:

  • Las claves son cadenas
  • Los valores pueden ser cadenas, números, booleanos o mapas anidados
  • Se usa para campos de metadatos

Ejemplo:

{
"metadata": {
"order_id": "12345",
"user_id": "67890",
"premium": true
}
}

El tipo escalar Time representa marcas de tiempo con formato ISO 8601.

Ejemplo: "2025-11-16T00:28:48.081Z"