stripe-firebase-extensions icon indicating copy to clipboard operation
stripe-firebase-extensions copied to clipboard

Concurrency issue when updating role / claims

Open ehildebrandt opened this issue 3 years ago • 4 comments

Extension name: firestore-stripe-subscriptions

There is a concurrency issue in how the role is handled. I recently have witnessed the following behavior:

03.05.2021, 17:43

  • user tries to subscribe to our service
  • a new checkout session was created
  • user tries to pay with his VISA credit card
  • a new subscription A was created
  • a new invoice A was created
  • webhook was called and a subscription was created in Firebase
  • 3D Secure fails
  • payment for invoice A fails
  • user stops and does not proceed with the payment

03.05.2021, 21:01

  • a few hours later the user tries to subscribe again
  • a new checkout session was created
  • user tries to pay with his VISA credit card
  • a new subscription B was created
  • a new invoice B was created
  • webhook was called and a subscription was created in Firebase
  • payment for invoice B is successful
  • webhook was called and a subscription status was synced in Firebase
  • role was set as claim in Firebase
  • user can now access all features as he has the correct role in this JWT claims

04.05.2021, 16:48

  • Stripe calls a webhook that the payment at 03.05.2021, 17:43 failed and therefore the subscription was canceled
  • role was removed from the claims in Firebase even though the user has a valid active subscription (payment on 03.05.2021, 21:01)
  • user is losing all his permissions

ehildebrandt avatar May 04 '21 20:05 ehildebrandt

Claim roles can also be lost when a user is subscribed to many products but cancels one of them. This is with the same claim role across all products, not tested with products having different claim roles

DCSnip3r avatar May 04 '21 21:05 DCSnip3r

I'm afraid I'm not too sure how to best prevent this edge case. For the time being, you could change your settings (https://dashboard.stripe.com/settings/billing/automatic), to not automatically cancel the subscription if the payment fails, but that might be more overhead than managing this edge case. image

thorsten-stripe avatar Jun 17 '21 14:06 thorsten-stripe

The best way to handle this edge case (in the case of cancellation of one product subscription but retain another) is to update the existing user subscription to the same quantity it currently has. This will reset the claim role. Setting up this functionality for the user is not very difficult with a cloud function (this is what I did). I wonder if it's doable through the customer portal.

In the case of billing failure, it's likely that the customer's billing will fail for all of their subscriptions. So, revoking their claim generally is the right move here.

I believe that In the original post, this is referencing a failed initial payment that persists due to an open invoice or subscription that has a failed payment method. It sounds like this invoice/subscription will have to be deleted, either by the user on the customer portal or by an admin.

Currently I see this as a manageable edge case

DCSnip3r avatar Jun 17 '21 16:06 DCSnip3r

I am experiencing this as well. A user will end up with multiple subscriptions on their document in Firestore -- one is active (with their successful payment) while they may have n number of incomplete/inactive subscriptions from failed payment attempts.

I've resolved this by deleting the failed ones from their Firestore record, then in Stripe adding a dummy metadata to the good subscription that triggers a resync via webhook.

But then a few days later the "bad" subscriptions end up in the user's Firestore document again -- likely because it seems Stripe hangs on to these failed subscriptions for some amount of time and them marks them canceled -- which triggers the webhook again, bringing them back into the user's Firestore document.

Even if this happened, I would expect the user's claim to be there when there is at least one good, active subscription on their record.

Please advise/resolve. 🙏

Chaddeus avatar Dec 29 '21 18:12 Chaddeus