# #233 Build your next B2B SaaS with Moneygun SaaS Multitenancy boilerplate!

- URL: https://superails.com/posts/233-build-your-next-b2b-saas-with-moneygun-saas-multitenancy-boilerplate
- Published: 2025-03-24
- Duration: 16:55
- Access: free
- Topics: moneygun

Previously Moneygun was just an example app of how to implement secure route-based Multitenancy without any gems.

Now I've added Subscriptions on Organization level. Meaning, it's now a legit template for building B2B SaaS apps.

B2B app - app where a team of users with different roles have access to shared resources.

Feel free to use this as a template for your next app, or just as inspiration!

PR adding subscriptions: https://github.com/yshmarov/moneygun/pull/197

## Transcript

Hello friends, it's been quite a while, but I have some nice news. So remember previously I made a video about Multitenancy, and I also created a basic multitenancy boilerplate named Monon, and made a couple of videos about, uh, how it, uh, works and now have improved monon. So it is now not just a multitenancy boiler plate, but it is a software as a service multitenancy boiler plate, meaning that it accepts subscriptions. So here's the actual pull request where I added the g pay to make money on be not just more 10, but more 10 subscriptions. Lemme demonstrate what this means. So at the moment, let's try to create a new account, just the device sign in form, and I can create an organization. Let's create an organization. Let's name it super. Let's add a logo. Okay? So I've created the organization and there's the dashboard. There's like a project page where this will be the models within the organization. And now we have this pay vault page, and I cannot access the pay vault page because I need to be subscribed to access this, uh, uh, controller or controller action. So here is the pricing page that is, uh, visible in the billing. And, uh, let's hook up, uh, payments at the moment. If I click on Get Started, uh, you see there's no price and, uh, I need to create the prices and connect my stripe. API. So here I have a new Stripe account. I'm going to develop a mode, and, uh, I'm going to, uh, see my API keys. So, uh, I will go and, uh, add my API keys, I will say rails, credentials, edit, environment development. Uh, I need to say, uh, editor. So I will say, uh, editor equals Vim. Okay, here I can access and edit my credentials. And you see, by default, I already have Stripe credentials set. Now, there's also a template, so credentials, VML t that shows which credentials you need to run the application. Here I have already added the stripe, uh, uh, private key. So this one, the public key, this one, and, uh, web hook secret. Now, uh, development doesn't matter much, but I took it from going to Web hooks add endpoint. And here you have this example, endpoint secret. So I added it, uh, here. Okay, let's click. So I've got the credentials, and now I need to ensure that I have, uh, the plans available in my application. Now, uh, where do these, uh, plans come from? They actually come from, let's open our, uh, pricing. Here it is, it comes from, uh, okay, let's add down using tabs. It comes from Rails application config for settings. So I will go to settings, and here I, uh, inputted the plans. So the price id, they amount the currency, here's the currency, uh, the interval, and most importantly the price. Uh, id. So I have two prices a monthly and the early plan. Let's create this kind of prices in our Stripe dashboard. So here I'm in the test mode. I will go to product catalog. I will, uh, say pro subscription, And, uh, I will create a recurrent price. Let it be in the USD, let's make it, uh, $99 per month. Add the product. Uh, and I will create one more price within this product. So, uh, it'll be a yellow price. Let's, uh, add recurring USD 999, and let's make it, uh, yearly. Okay, create price. Now I have two prices and I can update, uh, my setting for these prices. Uh, so we have this 99. I will cope with the price id. Uh, it is $99, so I need to also have the cents here. The currency is, uh, USD for both. And I will go with the second, uh, price for the yearly. Let's open it. Here's the price id, I will paste it here. Okay, so I have updated the plans that I'm going to use locally. And, uh, let's refer this page. I'm going to click on get started on the monthly plan. And you see I have this checkout page. Now, uh, I want to be able to upgrade from the monthly plan to the yellow plan directly on the checkout page. So to do this, I'm going to go to, uh, the product, uh, the monthly plan, and here we can add an upsell. So the monthly plan, upsells to year plan, that's update it. And now if I go, uh, back and, uh, initiate a new checkout session, You see, uh, it offers to, uh, upsell automatically in the checkout, uh, from monthly to yearly. I can add promotional codes. Uh, tax ion is included by default. Also does this, uh, I'm positioned as a business check that, uh, lets business customers to subscribe to it, for example. Okay, let's try subscribing to the yellow plan. Now, the email here is the email of the owner of an organization, okay? Pay and subscribe and, uh, each send the, uh, VA hook to the organization model and update its subscription to be active. You see paper hooks are happening, okay? You see I have, uh, now subscribed. So subscription is active, he has the price, he has the next billing date. Looks wonderful. Now I can click on this pay vault page. And you see, uh, congrats. If you see this, you are subscribed. So wonderful there. Subscription, uh, works. Uh, there are a few different subscription states. So let's try to unsubscribe now. Okay, inval request error. Um, I need to configure the billing portal. Okay, let's configure the billing portal in that test mode. Um, no safe changes. Let's, uh, try once again. Yeah. So I just needed to like, uh, initialize this billing portal, and now you see I can, uh, manage my, uh, uh, subscriptions. So let's, uh, say I want to cancel the subscription, and, uh, I think it's going to cancel, uh, at the period end by default. So here, you see, we can allow customers to switch plans. Um, Yeah, you see there are many second things that the customers can, uh, have or not have in the billing portal. This is, uh, really cool. So you don't have to manage all this, uh, in your app. You, let's try to manage it for you. Anyway, let's cancel the subscription. Let's go back to the application. And you see, so the subscription is canceled, but you will lose access still in a year from now because, uh, you have already paid for a year and you'll be able to, uh, still use the application for a year. Just the subscription will not be renewed at the end of that subscription. And you see the status batch has been updated to kind of orange. So, uh, standby. Okay, uh, let's go to our pay page. And you see now, uh, I can still access it because, uh, this subscription is active. It's just not going to be renewed. Let's go and create another organization. So, uh, uh, let's name it avo. I'll add, uh, logo. Okay, so here I have two organizations. If I have a look at both organizations, you see this one is, uh, uh, unsubscribed but active. This one is, uh, uh, not subscribed at all, and this organization doesn't have access to the, uh, pay page, so it directs to the pricing page. Um, let's have a look, uh, a bit deeper at how the pay, uh, rails GEM is, uh, installed. So, uh, first of all, this is a multitenancy organization, uh, application. And the, the subscriber is, uh, not just a user, it is the organization that the user belongs to. So the subscriptions are on organization level, not user level. Let's go to our organization, rb. And uh, here we will have, uh, pay customer. So the pay customer is not a user, it is their organization. And, uh, in this application, we allow just Stripe and, uh, there are a couple of Stripe attributes that we, uh, send. It's their pay customer ID and user id. Um, let's, uh, yeah, here we could actually have organization id. This would be better. Okay, if we go to our Stride dashboard, let's have a look at the customers. So here's the customer. Here we have the pay customer id and the, well, this should be the organization id. I have just updated it so we know which, uh, records this, uh, Stripe customer references in our application. We can go and have a look at the pay customer. Let's run the rail console, Uh, pay customer. There are two. All you see there is, uh, a pay customer on an organization level. Okay? So, uh, the pay customer is the, on the organization level. And then we have this, uh, subscriptions, uh, controller or the billing as we say it here. So let's open it. Let's open subscriptions. Uh, controller it, the route are defined. The here in the application. So there are just three routes. The index, the checkout page that the opens and you checkout session. So lets you pay. And the billing portal that lets you manage an active, uh, subscription. So, uh, going back to the subscriptions controller, we, uh, check if the user is subscribed or not. And based on this, we can display, uh, different page. So here we have avo. Let's open the S organization, go into Billion. You see in uh, s and in avo, we have, uh, different states. Here it is a scandal subscription. Here it is, uh, uh, not initialized subscription. So not, not even, uh, started to subscribe. Never was subscribed. So different states, uh, we can have a look at subscription Index. Yeah, so if the user is subscribed, then we see their current subscription. Uh, otherwise there is their pricing table and the features are shown to everybody to see the value that you have if you're subscribed or that you can have, if you will, uh, subscribe. Now, uh, here is the index. Now check out, uh, again, uh, we find the price by the ID from the bottom here. You can see on the button we have PERS price id. So we find that Stripe Price and Initialized a checkout session with this Stripe price. And there are all these additional settings like, uh, enable Automatic Text, allow promotional codes or not. You can actually disable all of these. Uh, nothing will change. You just have to keep success. URL cancel, URL, the line items and the mode subscription. So it initializes checkout session and directs to it. And this has to be, uh, data turbo false, uh, for it to work. Let's, uh, try without Turbo False. Let's go to pricing. Uh, here has the subscribe button. So, um, got started and yeah, actually it worked on the phone, so it doesn't always have to be data top of Falls. Okay, great. Um, going next, uh, back to the subscriptions controller. So here has the checkout, then we have the billing portal. This one is super easy. Uh, we just initialized the billing code portal and direct to our Stripe, uh, subscription management page, this one. And also there's a bunch of logic here all around to ensure that only organization admins have access to subscriptions logic that, uh, says that the subscriptions should be, uh, Syed and billing should be enabled. Uh, meaning if you don't have any Stripe credentials, then uh, these, uh, billing pages will not be visible at all in the, the application. So you can use it, uh, you can use Money Gun as a ancy application without the subscriptions model. If you don't have a stripe, uh, key present. Let's try moving the Stripe key. Um, Okay, let's edit our credentials. I will comment out the Stripe private key. Now save, leave. I will, uh, restart the server. So see if there is no Stripe public, oh, private key present. Then the billing logic benefits from the application. Now I will add it back in. Okay, so the subscription logic has been added back. Now, there are actually three different, uh, states of payments, uh, not, uh, subscribed subscription, uh, not renew and active subscription. So let's create another account of it and active subscription. I will create the I know, bus route. I'll add the logo. I will, uh, go and subscribe. Okay, subscribe. In this organization, pay is doing its magic with, uh, standing the web hooks, updating the pay customers pay subscriptions, so we don't have to manage about all this in our application. And here we have an organization with an active subscription. So let's have a look at all organizations. Once again, you see three organizations in different, uh, states. Let's open all of them and navigate to the billing pages. And see, we have three different states of billing. So, uh, not subscribed, actively subscribed and renew and, uh, actively subscribed, but, uh, not renewing as subscription. So these are like the three most basic states. That's, uh, about it, about the, uh, payments and software as a service implementation. So yes, you can now have, uh, uh, billing on organization level, and you can have multiple organizations. I think it's wonderful. And another tiny thing I did is, uh, I updated the layout. So now, uh, it is more responsive and, uh, it works, uh, fine on the small screens and big screens here has a small screen version. You see, we have this, uh, sidebar looking outside will close the sidebar. And also it is responsive. So if you have like a lot of links, a lot of organizations, it's going to work fine. And another thing, so if you, you can switch the layout. So, uh, let me demonstrate. There are two different sidebar layouts. Uh, this one that looks a bit like Slack. And, uh, this one, that is just one column. So you have two layouts to choose from, or you can build your own. Well, that's about it. I hope you enjoyed it. And, uh, yeah, try building, uh, uh, to be sauce with mangan. I think now it is, uh, possible.
