Skip to content

Commit b4371a7

Browse files
committed
address bugbot comments
1 parent 8a6eea4 commit b4371a7

File tree

2 files changed

+29
-16
lines changed

2 files changed

+29
-16
lines changed

apps/sim/app/api/organizations/[id]/seats/route.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -213,7 +213,7 @@ export async function PUT(request: NextRequest, { params }: { params: Promise<{
213213
oldSeats: currentSeats,
214214
newSeats: newSeatCount,
215215
updatedBy: session.user.id,
216-
prorationBehavior: 'create_prorations',
216+
prorationBehavior: 'always_invoice',
217217
})
218218

219219
return NextResponse.json({

apps/sim/lib/billing/webhooks/invoices.ts

Lines changed: 28 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -503,24 +503,37 @@ export async function handleInvoicePaymentSucceeded(event: Stripe.Event) {
503503
wasBlocked = row.length > 0 ? !!row[0].blocked : false
504504
}
505505

506-
if (isOrgPlan(sub.plan)) {
507-
await unblockOrgMembers(sub.referenceId, 'payment_failed')
508-
} else {
509-
// Only unblock users blocked for payment_failed, not disputes
510-
await db
511-
.update(userStats)
512-
.set({ billingBlocked: false, billingBlockedReason: null })
513-
.where(
514-
and(
515-
eq(userStats.userId, sub.referenceId),
516-
eq(userStats.billingBlockedReason, 'payment_failed')
506+
// For proration invoices (mid-cycle upgrades/seat changes), only unblock if real money
507+
// was collected. A $0 credit invoice from a downgrade should not unblock a user who
508+
// was blocked for a different failed payment.
509+
const isProrationInvoice = invoice.billing_reason === 'subscription_update'
510+
const shouldUnblock = !isProrationInvoice || (invoice.amount_paid ?? 0) > 0
511+
512+
if (shouldUnblock) {
513+
if (isOrgPlan(sub.plan)) {
514+
await unblockOrgMembers(sub.referenceId, 'payment_failed')
515+
} else {
516+
await db
517+
.update(userStats)
518+
.set({ billingBlocked: false, billingBlockedReason: null })
519+
.where(
520+
and(
521+
eq(userStats.userId, sub.referenceId),
522+
eq(userStats.billingBlockedReason, 'payment_failed')
523+
)
517524
)
518-
)
525+
}
526+
} else {
527+
logger.info('Skipping unblock for zero-amount proration invoice', {
528+
invoiceId: invoice.id,
529+
billingReason: invoice.billing_reason,
530+
amountPaid: invoice.amount_paid,
531+
})
519532
}
520533

521-
// Only reset usage for cycle renewals — proration invoices (subscription_update) should
522-
// unblock the user but not wipe their accumulated usage mid-cycle.
523-
if (wasBlocked && invoice.billing_reason !== 'subscription_update') {
534+
// Only reset usage for cycle renewals — proration invoices should not wipe
535+
// accumulated usage mid-cycle.
536+
if (wasBlocked && !isProrationInvoice) {
524537
await resetUsageForSubscription({ plan: sub.plan, referenceId: sub.referenceId })
525538
}
526539
} catch (error) {

0 commit comments

Comments
 (0)