Docs

Buscar na documentação

Guias, endpoints e eventos

Ir ao painel

Troca de plano

Escopo write. Troca a oferta de uma assinatura.

curl -X POST "https://api.ribbo.app/v1/subscriptions/sub_01J…/change-plan" \
  -H "Authorization: Bearer bk_..." -H "Content-Type: application/json" \
  -d '{ "offer_id": "offer_01KZ9R...", "keep_coupon": true }'
  • Mesmo ciclo, mais caro (upgrade): entra na hora, com proração cobrada no cartão salvo. Se a proração fica abaixo do mínimo do gateway (Stripe R$ 0,50, Asaas R$ 5,00), a troca é aplicada sem cobrar.
  • Mesmo ciclo, mesmo preço: troca na hora, sem cobrança.
  • Mesmo ciclo, mais barato (downgrade): agendado para o fim do período atual.
  • Troca de ciclo (mensal↔anual): vale o preço por ano (mensal x 12). Se o novo plano custa mais por ano, a troca é na hora: de mensal para anual cobra o anual menos o crédito do período que sobra; de anual para mensal o crédito vira tempo. Se custa o mesmo ou menos por ano, é agendada para o fim do período.
  • Oferta de outro gateway: o cartão salvo não atravessa gateways, então a troca vira um link de pagamento no gateway novo (evento subscription.migration_link_issued quando é agendada).
  • Só assinaturas active ou trialing trocam de plano.
  • keep_coupon (opcional): leva o cupom ativo para a nova oferta (não vale com troca de gateway).

Resposta 200 { "subscription": {...}, "plan_change": {...} }. Sem offer_id → 400; regra de negócio inválida → 422 {"error":"..."}.

A troca agendada aparece em pending_offer (offer_id, plan_id, plan_name, interval, amount_cents, effective_at) no payload da assinatura e no webhook subscription.plan_change_scheduled. Quando entra em vigor, chega subscription.plan_changed.

Cancelar troca agendada

curl -X POST "https://api.ribbo.app/v1/subscriptions/sub_01J…/cancel-plan-change" -H "Authorization: Bearer bk_..."

422 se não houver troca agendada. Emite subscription.plan_change_canceled.