Preencher paid_at da sessão quando a invoice é marcada como paga

TLDR: Quando uma invoice passa a :paid, atualizar paid_at e paid_total em todas as sessões associadas — esses campos nunca são preenchidos hoje, fazendo “Faturado” persistir no Avo mesmo depois do pagamento.

Contexto

Quando uma ProfessionalPaymentInvoice é marcada como paga (via webhook, marcação manual ou pull do gateway), as sessões associadas continuam com paid_at = nil e paid_total = 0. O badge do Avo lê o status da invoice corretamente, mas o campo Meeting#paid_at — que existe no schema — nunca é preenchido. Isso causa inconsistência de dados: todas as invoices pagas historicamente têm sessões com paid_at = nil.

Além disso, a invoice invoice_1777604504... da terapeuta anaclaudiacamargo01@gmail.com está travada em :pending — a transfer nunca completou. Esse é um problema de dado, resolvido separadamente pelo Avo admin (Pull from Gateway / Execute Transfer).

Objetivos

  • Preencher meeting.paid_at e meeting.paid_total sempre que uma invoice passar a :paid
  • Cobrir os três caminhos de código que marcam uma invoice como paga

Fora de escopo

  • Corrigir a invoice travada da Ana Claudia — é problema de dado, tratado via Avo admin

Mudanças

1. app/use_cases/transfers/update_invoice.rb

Quando new_transfer.done?, após atualizar a invoice, atualizar todas as sessões associadas:

ruby invoice.meetings.update_all(paid_at: Time.current, paid_total: ???)

O paid_total de cada sessão vem de ProfessionalPaymentInvoiceMeeting#total.

2. app/use_cases/professional_payment_invoices/mark_as_paid/confirm_payment.rb

Após salvar a invoice, atualizar as sessões associadas com paid_at e paid_total.

3. app/avo/actions/professional_invoices/pull_from_gateway.rb

Após record.update!(status: :paid, paid_at: ...), atualizar as sessões associadas.

Nota sobre paid_total: cada sessão tem seu próprio total em ProfessionalPaymentInvoiceMeeting. Usar esse valor por sessão — não dá para usar update_all com um único valor; é preciso atualizar registro a registro ou fazer um UPDATE com join em SQL.

Como verificar

  1. Rodar os testes: make test
  2. No console: criar uma invoice com sessões, transicioná-la para paga e afirmar que meeting.paid_at e meeting.paid_total foram preenchidos
  3. Em produção: após o deploy, rodar “Pull from Gateway” em uma invoice paga e verificar que as sessões foram atualizadas (ou verificar via query no console)

Documentação

  • Atualizar invoice_payment_flow: registrar que as sessões recebem paid_at/paid_total quando a invoice passa a :paid
  • Corrigir os nomes de status desatualizados no mesmo documento (o doc descrevia created/failed/blocked/done, mas o enum da invoice é pending/paid/canceled)