Question

I am developing a SaaS application using Ruby on Rails. Each user has to subscribe to a specific plan to start using the application. This step has been done using Stripe

The problem is I don't know how to prevent this user from using my application if the auto payment subscription is failed (he change his credit card, etc...). I am thinking of using a column in User model to mark this user as inactive and prevent him from signing in. But it does not work as I expected because I want this user to be able to sign in but he will have to update his subscription to continue.

By the way, I saw many SaaS example on Rails such as https://github.com/RailsApps/rails-stripe-membership-saas or https://github.com/railscasts/289-paypal-recurring-billing but it seems that they don't handle the postback from provider (Stripe or Paypal) whenever there is failure occurs.

Please let me know what do you think and how you guys deal with this issue in your similar projects.

Thanks in advance,

Was it helpful?

Solution

Stripe charges the card on a recurring basis for you. Your application isn't responsible for creating new charges for users who have subscribed for your service.

From the docs

Stripe makes handling failed payments easy. Stripe can automatically retry a recurring payment after it fails, and can automatically cancel the customer's subscription if it repeatedly fails. How long to wait, and how many times to retry, can be easily set in your account settings.

I might track a :subscription_active boolean or similar on my User model. When a user logs in, you can check against the API to see the status of a user's subscription. The API docs have this to say about the status of a subscription in the response (emphasis my own):

Possible values are trialing, active, past_due, canceled, or unpaid. A subscription still in its trial period is trialing and moves to active when the trial period is over. When payment to renew the subscription fails, the subscription becomes past_due. After Stripe has exhausted all payment retry attempts, the subscription ends up with a status of either canceled or unpaid depending on your retry settings. Note that when a subscription has a status of unpaid, any future invoices will not be attempted until the customer’s card details are updated.

If the response comes back as one of the above bolded states, mark the :subscription_active to false for the user. Check user.subscription_active? wherever you need to conditionally enable features of your application for a user.

OTHER TIPS

I think you should handle this in a manner similar to how Devise works. To enforce a valid signed in user you will put before_action authenticate_user! in you controllers.

If I had to solve your problem I would create similar method, for example

before_action verify_payment!

def verify_payment!
  redirect_to user_payments_path unless current_user.has_valid_payment?
end
protected :verify_payment!

and then in User#has_valid_payment? put the logic checking if an account is valid (I didn't watch those screencasts but I guess it would be something like checking if last payment is older than 30 days, etc)

EDIT:

check excellent Deefour answer for Stripe specific details!

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top