Skip to main content
Docs

Clerk Billing for B2C SaaS

Clerk Billing for B2C SaaS allows you to create Plans and manage Subscriptions for Users in your application.

Enable Billing

To enable Billing for your application, navigate to the Billing Settings page in the Clerk Dashboard. This page will guide you through enabling Billing for your application.

Create a Plan

Subscription Plans are what your Users subscribe to. There is no limit to the number of Plans you can create.

To create a Plan, navigate to the Plans page in the Clerk Dashboard. Here, you can create, edit, and delete Plans. To setup B2C billing, select the Plans for Users tab and click Add Plan. When creating a Plan, you can also create Features for the Plan; see the next section for more information.

Tip

What is the Publicly available option?

Add Features to a Plan

Features make it easy to give entitlements to your Plans. You can add any number of Features to a Plan.

You can add a Feature to a Plan when you are creating a Plan. To add it after a Plan is created:

  1. Navigate to the Plans page in the Clerk Dashboard.
  2. Select the Plan you'd like to add a Feature to.
  3. In the Features section, select Add Feature.

Tip

What is the Publicly available option?

Create a pricing page

You can create a pricing page by using the <PricingTable /> component. This component displays a table of Plans and Features that users can subscribe to. It's recommended to create a dedicated page, as shown in the following example.

app/pricing/page.tsx
import { PricingTable } from '@clerk/nextjs'

export default function Page() {
  return (
    <div style={{ maxWidth: '800px', margin: '0 auto', padding: '0 1rem' }}>
      <PricingTable />
    </div>
  )
}

Control access with Features and Plans

You can use Clerk's Features and Plans to gate access to the content. There are a few ways to do this, but the recommended and simplest way is either using the has() method or the <Protect> component.

The has() method is available for any JavaScript framework, while <Protect> is only available for React-based frameworks.

Example: Using has()

Use the has() method to test if the user has access to a Plan:

const { has } = await auth()
const hasPremiumAccess = has({ plan: 'gold' })

Or a Feature:

const { has } = await auth()
const hasPremiumAccess = has({ feature: 'widgets' })

The has() method checks if the User has been granted a specific type of access control (Role, Permission, Feature, or Plan) and returns a boolean value. It is available on the auth object on the server. Depending on the framework you are using, you will access the auth object differently.

The following example accesses the auth object and the has() method using the Next.js-specific auth() helper.

The following example demonstrates how to use has() to check if a user has a Plan.

app/page.tsx
import { auth } from '@clerk/nextjs/server'

export default async function Page() {
  // Use `auth()` helper to access the `has()` method
  const { has } = await auth()

  // Use `has()` method to check if user has a Plan
  const hasBronzePlan = has({ plan: 'bronze' })

  if (!hasBronzePlan) return <h1>Only subscribers to the Bronze plan can access this content.</h1>

  return <h1>For Bronze subscribers only</h1>
}

The following example demonstrates how to use has() to check if a user has a Feature.

app/page.tsx
import { auth } from '@clerk/nextjs/server'

export default async function Page() {
  // Use `auth()` helper to access the `has()` method
  const { has } = await auth()

  // Use `has()` method to check if user has a Feature
  const hasPremiumAccess = has({ feature: 'premium_access' })

  if (!hasPremiumAccess)
    return <h1>Only subscribers with the Premium Access feature can access this content.</h1>

  return <h1>Our Exclusive Content</h1>
}

Example: Using <Protect>

The <Protect> component protects content or even entire routes by checking if the User has been granted a specific type of access control (Role, Permission, Feature, or Plan). You can pass a fallback prop to <Protect> that will be rendered if the user does not have the access control.

The following example demonstrates how to use <Protect> to protect a page by checking if the user has a Plan.

export default function ProtectPage() {
  return (
    <Protect
      plan="bronze"
      fallback={<p>Only subscribers to the Bronze plan can access this content.</p>}
    >
      {children}
    </Protect>
  )
}

The following example demonstrates how to use <Protect> to protect a page by checking if the user has a Feature.

export default function ProtectPage() {
  return (
    <Protect
      feature="premium_access"
      fallback={<p>Only subscribers with the Premium Access feature can access this content.</p>}
    >
      {children}
    </Protect>
  )
}

Feedback

What did you think of this content?

Last updated on