diff --git a/docs/_partials/billing/add-new-payment-method.mdx b/docs/_partials/billing/add-new-payment-method.mdx
new file mode 100644
index 0000000000..80e5bde2f6
--- /dev/null
+++ b/docs/_partials/billing/add-new-payment-method.mdx
@@ -0,0 +1,82 @@
+The following example demonstrates how to create a billing page where a user can add a new payment method. It is split into two components:
+
+- **``**: Sets up the ``, which specifies that the payment actions within its children are `for` the `user`.
+- **``**: Renders the payment form and handles the submission logic. It uses `usePaymentElement()` to get the `submit` function and `useUser()` to get the `user` object. When the form is submitted, it first creates a payment token and then attaches it to the user.
+
+", ""]}>
+ ```tsx {{ filename: 'app/user/billing/page.tsx' }}
+ import { ClerkLoaded } from '@clerk/nextjs'
+ import { PaymentElementProvider } from '@clerk/nextjs/experimental'
+ import { AddPaymentMethodForm } from './AddPaymentMethodForm'
+
+ export default function Page() {
+ return (
+
+
Billing Settings
+
+
+
+
+
+
+
+ )
+ }
+ ```
+
+ ```tsx {{ filename: 'app/user/billing/AddPaymentMethodForm.tsx' }}
+ 'use client'
+ import { useUser } from '@clerk/nextjs'
+ import { usePaymentElement, PaymentElement } from '@clerk/nextjs/experimental'
+ import { useState } from 'react'
+
+ export function AddPaymentMethodForm() {
+ const { user } = useUser()
+ const { submit, isFormReady } = usePaymentElement()
+ const [isSubmitting, setIsSubmitting] = useState(false)
+ const [error, setError] = useState(null)
+
+ const handleAddPaymentMethod = async (e: React.FormEvent) => {
+ e.preventDefault()
+ if (!isFormReady || !user) {
+ return
+ }
+
+ setError(null)
+ setIsSubmitting(true)
+
+ try {
+ // 1. Submit the form to the payment provider to get a payment token
+ const { data, error } = await submit()
+
+ // Usually a validation error from stripe that you can ignore.
+ if (error) {
+ setIsSubmitting(false)
+ return
+ }
+
+ // 2. Use the token to add the payment source to the user
+ await user.addPaymentSource(data)
+
+ // 3. Handle success (e.g., show a confirmation, clear the form)
+ alert('Payment method added successfully!')
+ } catch (err: any) {
+ setError(err.message || 'An unexpected error occurred.')
+ } finally {
+ setIsSubmitting(false)
+ }
+ }
+
+ return (
+
+ )
+ }
+ ```
+
diff --git a/docs/_partials/billing/api-experimental-guide.mdx b/docs/_partials/billing/api-experimental-guide.mdx
new file mode 100644
index 0000000000..b2c06f1cca
--- /dev/null
+++ b/docs/_partials/billing/api-experimental-guide.mdx
@@ -0,0 +1,3 @@
+> [!WARNING]
+>
+> This guide is using experimental APIs and subject to change while Clerk Billing is under Beta. To mitigate potential disruptions, we recommend [pinning](https://docs.renovatebot.com/dependency-pinning/#what-is-dependency-pinning) your SDK and `clerk-js` package versions.
diff --git a/docs/_partials/billing/use-checkout-options.mdx b/docs/_partials/billing/use-checkout-options.mdx
new file mode 100644
index 0000000000..3c1075f36b
--- /dev/null
+++ b/docs/_partials/billing/use-checkout-options.mdx
@@ -0,0 +1,20 @@
+
+ - `for?`
+ - `'user' | 'organization'`
+
+ Specifies if the checkout is for an organization. If omitted, the checkout defaults to the current user.
+
+ ---
+
+ - `planId`
+ - `string`
+
+ The ID of the subscription plan to check out (e.g. `cplan_xxx`).
+
+ ---
+
+ - `planPeriod`
+ - `'month' | 'annual'`
+
+ The billing period for the plan.
+
diff --git a/docs/billing/b2b-saas.mdx b/docs/billing/b2b-saas.mdx
index 93403483ce..f14ad0bdaf 100644
--- a/docs/billing/b2b-saas.mdx
+++ b/docs/billing/b2b-saas.mdx
@@ -1,7 +1,7 @@
---
title: Clerk billing for B2B SaaS
description: Clerk billing is a feature that allows you to create and manage plans and features for your application.
-sdk: nextjs, react, expo, react-router, astro, tanstack-react-start, remix, nuxt, vue, js-frontend, expressjs, fastify, js-backend
+sdk: nextjs, react, expo, react-router, astro, tanstack-react-start, remix, nuxt, vue, js-frontend, expressjs, fastify, js-backend
---
@@ -42,7 +42,7 @@ You can add a feature to a plan when you are creating a plan. To add it after a
## Create a pricing page
-You can create a pricing page by using the [``](/docs/components/pricing-table) component. This component displays a table of plans and features that customers can subscribe to. **It's recommended to create a dedicated page**, as shown in the following example.
+You can create a pricing page by using the [``](/docs/components/billing/pricing-table) component. This component displays a table of plans and features that customers can subscribe to. **It's recommended to create a dedicated page**, as shown in the following example.
diff --git a/docs/billing/b2c-saas.mdx b/docs/billing/b2c-saas.mdx
index 72ca3acac2..86b56905c4 100644
--- a/docs/billing/b2c-saas.mdx
+++ b/docs/billing/b2c-saas.mdx
@@ -1,7 +1,7 @@
---
title: Clerk billing for B2C SaaS
description: Clerk billing is a feature that allows you to create and manage plans and features for your application.
-sdk: nextjs, react, expo, react-router, astro, tanstack-react-start, remix, nuxt, vue, js-frontend, expressjs, fastify, js-backend
+sdk: nextjs, react, expo, react-router, astro, tanstack-react-start, remix, nuxt, vue, js-frontend, expressjs, fastify, js-backend
---
@@ -42,7 +42,7 @@ You can add a feature to a plan when you are creating a plan. To add it after a
## Create a pricing page
-You can create a pricing page by using the [``](/docs/components/pricing-table) 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.
+You can create a pricing page by using the [``](/docs/components/billing/pricing-table) 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.
diff --git a/docs/billing/overview.mdx b/docs/billing/overview.mdx
index ca63b940bd..b65148de79 100644
--- a/docs/billing/overview.mdx
+++ b/docs/billing/overview.mdx
@@ -15,4 +15,11 @@ Clerk billing allows your customers to purchase recurring subscriptions to your
- [Billing for B2B SaaS](/docs/billing/b2b-saas)
- To charge companies or organizations
+
+ ---
+
+ - [Build a simple checkout page](/docs/custom-flows/checkout-new-payment-method)
+ - To charge users with a new payment method
+
+ ---
diff --git a/docs/components/checkout-button.mdx b/docs/components/billing/checkout-button.mdx
similarity index 93%
rename from docs/components/checkout-button.mdx
rename to docs/components/billing/checkout-button.mdx
index 5f508e52e7..8f90c51f9c 100644
--- a/docs/components/checkout-button.mdx
+++ b/docs/components/billing/checkout-button.mdx
@@ -27,8 +27,8 @@ The `` component renders a button that opens the checkout draw
---
- - `subscriberType?`
- - `'user' | 'org'`
+ - `for?`
+ - `'user' | 'organization'`
Determines whether the subscription is for the current user or organization. Defaults to `'user'`.
@@ -78,14 +78,14 @@ The `` component renders a button that opens the checkout draw
>
```
-`` will throw an error if the `subscriberType` property is set to `'org'` and no [active organization](/docs/organizations/overview#active-organization) is set.
+`` will throw an error if the `for` prop is set to `'organization'` and no [active organization](/docs/organizations/overview#active-organization) is set.
```tsx
<>
// ❌ This will throw an error if no organization is active
-
+
// ✅ Correct usage
- {auth.orgId ? : null}
+ {auth.orgId ? : null}
>
```
diff --git a/docs/components/plan-details-button.mdx b/docs/components/billing/plan-details-button.mdx
similarity index 100%
rename from docs/components/plan-details-button.mdx
rename to docs/components/billing/plan-details-button.mdx
diff --git a/docs/components/pricing-table.mdx b/docs/components/billing/pricing-table.mdx
similarity index 100%
rename from docs/components/pricing-table.mdx
rename to docs/components/billing/pricing-table.mdx
diff --git a/docs/components/subscription-details-button.mdx b/docs/components/billing/subscription-details-button.mdx
similarity index 93%
rename from docs/components/subscription-details-button.mdx
rename to docs/components/billing/subscription-details-button.mdx
index c740f5ac30..1587aa831e 100644
--- a/docs/components/subscription-details-button.mdx
+++ b/docs/components/billing/subscription-details-button.mdx
@@ -16,7 +16,7 @@ All props are optional.
- `for?`
- - `'user' | 'org'`
+ - `'user' | 'organization'`
Determines whether to show subscription details for the current user or organization. Defaults to `'user'`.
@@ -59,14 +59,14 @@ All props are optional.
>
```
-`` will throw an error if the `for` property is set to `'org'` and no [active organization](/docs/organizations/overview#active-organization) is set.
+`` will throw an error if the `for` prop is set to `'organization'` and no [active organization](/docs/organizations/overview#active-organization) is set.
```tsx
<>
// ❌ This will throw an error if no organization is active
-
+
// ✅ Correct usage
- {auth.orgId ? : null}
+ {auth.orgId ? : null}
>
```
diff --git a/docs/custom-flows/add-new-payment-method.mdx b/docs/custom-flows/add-new-payment-method.mdx
new file mode 100644
index 0000000000..cb4cd4747d
--- /dev/null
+++ b/docs/custom-flows/add-new-payment-method.mdx
@@ -0,0 +1,33 @@
+---
+title: Build a custom flow for adding a new payment method
+description: Learn how to use the Clerk API to build a custom flow for adding a new payment method to a user's account.
+---
+
+
+
+
+
+This guide will walk you through how to build a custom user interface that allows users to **add a new payment method to their account**. This is a common feature in a user's billing or account settings page, allowing them to pre-emptively add a payment method for future use.
+
+For the custom flow that allows users to add a new payment method **during checkout**, see the [dedicated guide](/docs/custom-flows/checkout-new-payment-method).
+
+
+ ### Enable billing features
+
+ To use billing features, you first need to ensure they are enabled for your application. Follow the [Billing documentation](/docs/billing/overview) to enable them and set up your plans.
+
+ ### Add payment method flow
+
+ To add a new payment method for a user, you must:
+
+ 1. Set up the [``](/docs/hooks/use-payment-element) to create a context for the user's payment actions.
+ 1. Render the [``](/docs/hooks/use-payment-element) to display the secure payment fields from your provider.
+ 1. Use the [`usePaymentElement()`](/docs/hooks/use-payment-element) hook to submit the form and create a payment token.
+ 1. Use the [`useUser()`](/docs/hooks/use-user) hook to attach the newly created payment method to the user.
+
+
+
+
+
+
+
diff --git a/docs/custom-flows/checkout-existing-payment-method.mdx b/docs/custom-flows/checkout-existing-payment-method.mdx
new file mode 100644
index 0000000000..f8ae9202cb
--- /dev/null
+++ b/docs/custom-flows/checkout-existing-payment-method.mdx
@@ -0,0 +1,174 @@
+---
+title: Build a custom checkout flow with an existing payment method
+description: Learn how to use the Clerk API to build a custom checkout flow that allows users to checkout with an existing payment method.
+---
+
+
+
+
+
+This guide will walk you through how to build a custom user interface for a checkout flow that allows users to checkout **with an existing payment method**. For the custom flow that allows users to **add a new payment method** during checkout, see the [dedicated guide](/docs/custom-flows/checkout-new-payment-method).
+
+
+ ## Enable billing features
+
+ To use billing features, you first need to ensure they are enabled for your application. Follow the [Billing documentation](/docs/billing/overview) to enable them and setup your plans.
+
+ ## Checkout flow
+
+ To create a checkout session with an existing payment method, you must:
+
+ 1. Set up the checkout provider with plan details.
+ 1. Initialize the checkout session when the user is ready.
+ 1. Fetch and display the user's existing payment methods.
+ 1. Confirm the payment with the selected payment method.
+ 1. Complete the checkout process and redirect the user.
+
+
+
+ The following example:
+
+ 1. Uses the [`useCheckout()`](/docs/hooks/use-checkout) hook to initiate and manage the checkout session.
+ 1. Uses the [`usePaymentMethods()`](/docs/hooks/use-payment-methods) hook to fetch the user's existing payment methods.
+ 1. Assumes that you have already have a valid `planId`, which you can acquire in many ways:
+ - [Copy from the Clerk Dashboard](https://dashboard.clerk.com/last-active?path=billing/plans?tab=user).
+ - Use the [Clerk Backend API](/docs/reference/backend-api/tag/commerce/get/commerce/plans#tag/commerce/get/commerce/plans).
+ - Use the new [`usePlans()`](/docs/hooks/use-plans) hook to get the plan details.
+
+ This example is written for Next.js App Router but can be adapted for any React-based framework.
+
+ ```tsx {{ filename: 'app/checkout/page.tsx' }}
+ 'use client'
+ import * as React from 'react'
+ import { SignedIn, ClerkLoaded } from '@clerk/nextjs'
+ import { CheckoutProvider, useCheckout, usePaymentMethods } from '@clerk/nextjs/experimental'
+ import { useMemo, useState } from 'react'
+
+ export default function CheckoutPage() {
+ return (
+
+
+
+
+
+
+
+ )
+ }
+
+ function CustomCheckout() {
+ const { checkout } = useCheckout()
+ const { status } = checkout
+
+ if (status === 'needs_initialization') {
+ return
+ }
+
+ return (
+
+ )
+ }
+ ```
+
+
+
diff --git a/docs/custom-flows/checkout-new-payment-method.mdx b/docs/custom-flows/checkout-new-payment-method.mdx
new file mode 100644
index 0000000000..a80388f298
--- /dev/null
+++ b/docs/custom-flows/checkout-new-payment-method.mdx
@@ -0,0 +1,166 @@
+---
+title: Build a custom checkout flow with a new payment method
+description: Learn how to use the Clerk API to build a custom checkout flow that allows users to add a new payment method during checkout.
+---
+
+
+
+
+
+This guide will walk you through how to build a custom user interface for a checkout flow that allows users to **add a new payment method during checkout**.
+
+For the custom flow that allows users to checkout **with an existing payment** method, see the [dedicated guide](/docs/custom-flows/checkout-existing-payment-method).
+
+For the custom flow that allows users to add a new payment method to their account, **outside of a checkout flow**, see the [dedicated guide](/docs/custom-flows/add-new-payment-method).
+
+
+ ## Enable billing features
+
+ To use billing features, you first need to ensure they are enabled for your application. Follow the [Billing documentation](/docs/billing/overview) to enable them and setup your plans.
+
+ ## Checkout flow
+
+ To create a checkout session with a new payment card, you must:
+
+ 1. Set up the checkout provider with plan details.
+ 1. Initialize the checkout session when the user is ready.
+ 1. Render the payment form for card collection.
+ 1. Confirm the payment with the collected payment method.
+ 1. Complete the checkout process and redirect the user.
+
+
+
+ The following example:
+
+ 1. Uses the [`useCheckout()`](/docs/hooks/use-checkout) hook to get to initiate and manage the checkout session.
+ 1. Uses the [`usePaymentElement()`](/docs/hooks/use-payment-element) hook to control the payment element, which is rendered by ``.
+ 1. Assumes that you have already have a valid `planId`, which you can acquire in many ways.
+ - [Copy from the Clerk Dashboard](https://dashboard.clerk.com/last-active?path=billing/plans?tab=user).
+ - Use the [Clerk Backend API](/docs/reference/backend-api/tag/commerce/get/commerce/plans#tag/commerce/get/commerce/plans).
+ - Use the new [`usePlans()`](/docs/hooks/use-plans) hook to get the plan details.
+
+ This example is written for Next.js App Router but can be adapted for any React-based framework.
+
+ ```tsx {{ filename: 'app/checkout/page.tsx' }}
+ 'use client'
+ import * as React from 'react'
+ import { SignedIn, ClerkLoaded } from '@clerk/nextjs'
+ import {
+ CheckoutProvider,
+ useCheckout,
+ PaymentElementProvider,
+ PaymentElement,
+ usePaymentElement,
+ } from '@clerk/nextjs/experimental'
+
+ export default function CheckoutPage() {
+ return (
+
+
+
+
+
+
+
+ )
+ }
+
+ function CustomCheckout() {
+ const { checkout } = useCheckout()
+ const { status } = checkout
+
+ if (status === 'needs_initialization') {
+ return
+ }
+
+ return (
+
+ )
+ }
+ ```
+
+
+
diff --git a/docs/hooks/use-checkout.mdx b/docs/hooks/use-checkout.mdx
new file mode 100644
index 0000000000..51c11d55e5
--- /dev/null
+++ b/docs/hooks/use-checkout.mdx
@@ -0,0 +1,377 @@
+---
+title: '`useCheckout()`'
+description: Clerk's useCheckout() hook provides state and methods to manage a subscription checkout flow.
+---
+
+
+
+The `useCheckout()` hook is used to create, manage, and confirm a checkout session for a user or an organization's subscription plan. It provides the state of the current checkout process, such as its status and any errors, along with methods to initiate and complete the checkout.
+
+There are two ways to use `useCheckout()`:
+
+1. In conjunction with [``](#checkout-provider) to create a shared checkout context. All child components inside the provider can then use `useCheckout()` to access or update the same checkout state.
+1. On its own by passing configuration options directly to it. This is ideal for self-contained components that handle their own checkout flow without needing a shared context.
+
+## Parameters
+
+`useCheckout()` accepts a single object with the following properties:
+
+
+ - `options?`
+ - [`UseCheckoutOptions`](#use-checkout-options)
+
+ An object containing the configuration for the checkout flow.
+
+ **Required** if the hook is used without a `` wrapping the component tree.
+
+
+### `UseCheckoutOptions`
+
+
+
+## Returns
+
+`useCheckout()` returns a `{ checkout }` object. The `checkout` object contains the following properties. They are `null` until the checkout process is started by calling the `start()` method.
+
+
+ - `id`
+ - `string | null`
+
+ The unique identifier for the checkout session.
+
+ ---
+
+ - `externalClientSecret`
+ - `string | null`
+
+ The client secret from an external payment provider (such as Stripe) used to complete the payment on the client-side.
+
+ ---
+
+ - `externalGatewayId`
+ - `string | null`
+
+ The identifier for the external payment gateway used for the checkout session.
+
+ ---
+
+ - `paymentSource`
+ - [CommercePaymentSourceResource](/docs/references/javascript/types/commerce-payment-source-resource) | null
+
+ The payment source being used for the checkout.
+
+ ---
+
+ - `plan`
+ - [CommercePlanResource](/docs/references/javascript/types/commerce-plan-resource) | null
+
+ The subscription plan details for the checkout.
+
+ ---
+
+ - `planPeriod`
+ - `'month' | 'annual' | null`
+
+ The billing period for the plan.
+
+ ---
+
+ - `planPeriodStart`
+ - `number | undefined`
+
+ The start date of the plan period, represented as a Unix timestamp.
+
+ ---
+
+ - `status`
+ - `'needs_initialization' | 'needs_confirmation' | 'completed'`
+
+ The current status of the checkout session. The following statuses are possible:
+
+ - `needs_initialization`: The checkout hasn't started but the hook is mounted. Call `start()` to continue.
+ - `needs_confirmation`: The checkout has been initialized and is awaiting confirmation. Call `confirm()` to continue.
+ - `completed`: The checkout has been successfully confirmed. Call `finalize()` to complete the checkout.
+
+ ---
+
+ - `totals`
+ - [`CommerceCheckoutTotals`](/docs/references/javascript/types/commerce-checkout-totals)
+
+ The total costs, taxes, and other pricing details.
+
+ ---
+
+ - `isImmediatePlanChange`
+ - `boolean`
+
+ A boolean that indicates if the plan change will take effect immediately.
+
+ ---
+
+ - `isStarting`
+ - `boolean`
+
+ A boolean that indicates if the `start()` method is in progress.
+
+ ---
+
+ - `isConfirming`
+ - `boolean`
+
+ A boolean that indicates if the `confirm()` method is in progress.
+
+ ---
+
+ - `error`
+ - [ClerkAPIResponseError](/docs/references/javascript/types/clerk-api-response-error) | null
+
+ Returns an error object if any part of the checkout process fails.
+
+ ---
+
+ - `fetchStatus`
+ - `'idle' | 'fetching' | 'error'`
+
+ The data fetching status.
+
+ ---
+
+ - `start()`
+ - `() => Promise<{ data: CommerceCheckoutResource; error: null; } | { data: null; error: ClerkAPIResponseError; }>`
+
+ A function that initializes the checkout process by creating a checkout resource on the server.
+
+ ---
+
+ - `confirm()`
+ - `(params: ConfirmCheckoutParams) => Promise<{ data: CommerceCheckoutResource; error: null; } | { data: null; error: ClerkAPIResponseError; }>`
+
+ A function that confirms and finalizes the checkout process, usually after the user has provided and validated payment information.
+
+ ---
+
+ - `finalize()`
+ - `(params?: { redirectUrl: string }) => void`
+
+ A function that finalizes the checkout process. Can optionally accept a `redirectUrl` to navigate the user to upon completion.
+
+ ---
+
+ - `clear()`
+ - `() => void`
+
+ A function that clears the current checkout state from the cache.
+
+
+## ``
+
+The `` component is a wrapper that provides a checkout context to its children, allowing checkout state to be shared across multiple components. Child components can access the checkout context by calling `useCheckout()`.
+
+### Properties
+
+
+
+## Usage
+
+For the best user experience and to prevent potential errors, always wrap components using `useCheckout()` with both `` and `` components. This ensures that the user is properly authenticated and Clerk is fully initialized before accessing checkout functionality.
+
+```tsx
+function CheckoutPage() {
+ return (
+
+
+
+
+
+ )
+}
+```
+
+### Examples
+
+The `useCheckout()` hook can be used with a context provider for managing state across multiple components or as a standalone hook for more isolated use cases.
+
+", "Standalone Hook"]}>
+
+ The following example shows the basic structure for a checkout flow. A parent component, ``, sets up the `` and renders the checkout flow. A child component, ``, uses the `useCheckout()` hook to access the checkout state.
+
+ ", ""]}>
+
+ ```tsx {{ filename: 'src/components/SubscriptionPage.tsx', collapsible: true }}
+ import { CheckoutProvider } from '@clerk/nextjs/experimental'
+ import { ClerkLoaded } from '@clerk/nextjs'
+ import { CheckoutFlow } from './CheckoutFlow'
+
+ export function SubscriptionPage() {
+ // `` sets the context for the checkout flow.
+ // Any child component can now call `useCheckout()` to access this context.
+ return (
+
+
+ )
+ }
+ ```
+
+
+
+
+
+ For simple, self-contained components, you can use `useCheckout()` by passing the configuration options directly to the hook. This avoids the need to wrap the component in a provider.
+
+ The following example shows an `` component that manages its own checkout flow.
+
+ ```tsx {{ filename: 'src/components/UpgradeButton.tsx' }}
+ 'use client'
+
+ import { useCheckout } from '@clerk/nextjs/experimental'
+
+ export function UpgradeButton({
+ planId,
+ planPeriod,
+ }: {
+ planId: string
+ planPeriod: 'month' | 'annual'
+ }) {
+ // Pass options directly to the hook when not using a provider.
+ const { checkout } = useCheckout({
+ planId,
+ planPeriod,
+ for: 'user',
+ })
+
+ const { start, status, isStarting, error } = checkout
+
+ const handleStartCheckout = async () => {
+ try {
+ await start()
+ // In a real app, you would now use the `externalClientSecret`
+ // from the checkout object to render a payment form.
+ console.log('Checkout started! Status:', checkout.status)
+ } catch (e) {
+ console.error('Error starting checkout:', e)
+ }
+ }
+
+ return (
+
+
+ {error &&
Error: {error.errors[0].message}
}
+
+ )
+ }
+ ```
+
+
+
+## Related guides
+
+
+ - [Checkout flow with a new payment method](/docs/custom-flows/checkout-new-payment-method)
+ - Prompt users to add a new payment method during checkout
+
+ ---
+
+ - [Checkout flow for returning users](/docs/custom-flows/checkout-existing-payment-method)
+ - Prompt users to select an existing payment method during checkout
+
diff --git a/docs/hooks/use-payment-element.mdx b/docs/hooks/use-payment-element.mdx
new file mode 100644
index 0000000000..e968c8373a
--- /dev/null
+++ b/docs/hooks/use-payment-element.mdx
@@ -0,0 +1,120 @@
+---
+title: '`usePaymentElement()`'
+description: Clerk's usePaymentElement() hook provides methods and state for interacting with a payment form.
+---
+
+
+
+The `usePaymentElement()` hook is used to control the payment form rendered by the [``](#payment-element) component. It provides the necessary state and methods to submit payment details to a payment provider like Stripe.
+
+This hook must be used within a component that is a descendant of the `` component. It is typically used in a checkout flow that prompts a user to add a new payment method, or for adding a new payment method outside of a checkout.
+
+## Parameters
+
+`usePaymentElement()` doesn't accept any parameters. It derives its state and configuration from the nearest [``](#payment-element-provider).
+
+## Returns
+
+`usePaymentElement()` returns an object with the following properties:
+
+
+ - `submit()`
+ - `() => Promise<{ data: { gateway: 'stripe'; paymentToken: string } | null; error: PaymentElementError | null}>`
+
+ A function that submits the payment form data to the payment provider. It returns a promise that resolves with either a `data` object containing a payment token on success, or an `error` object on failure.
+
+ ---
+
+ - `reset()`
+ - `() => Promise`
+
+ A function that resets the payment form to its initial, empty state.
+
+ ---
+
+ - `isFormReady`
+ - `boolean`
+
+ A boolean that indicates if the payment form UI has been rendered and is ready for user input. This is useful for disabling a submit button until the form is interactive.
+
+ ---
+
+ - `isProviderReady`
+ - `boolean`
+
+ A boolean that indicates if the underlying payment provider (e.g. Stripe) has been fully initialized.
+
+ ---
+
+ - `provider`
+ - `{ name: 'stripe' } | undefined`
+
+ An object containing information about the initialized payment provider. It is `undefined` until `isProviderReady` is `true`.
+
+
+## Payment element components
+
+The `usePaymentElement()` hook works in conjunction with the `` and `` components.
+
+### ``
+
+The `` component sets up the context for the payment element. It fetches all the necessary data from the payment provider (e.g., Stripe) and makes it available to its children.
+
+#### Properties
+
+
+ - `checkout?`
+ - [`CommerceCheckoutResource`](/docs/references/javascript/types/commerce-checkout-resource)
+
+ An optional checkout resource object. When provided, the payment element is scoped to the specific checkout session.
+
+ ---
+
+ - `for?`
+ - `'user' | 'organization'`
+
+ Specifies whether the payment method is being added for a user or an organization. Defaults to `'user'`.
+
+ ---
+
+ - `stripeAppearance?`
+ - `object`
+
+ An optional object to customize the appearance of the Stripe Payment Element. This allows you to match the form's styling to your application's theme.
+
+ ---
+
+ - `paymentDescription?`
+ - `string`
+
+ An optional description to display to the user within the payment element UI.
+
+
+### ``
+
+This component renders the actual payment form from the provider (e.g., the Stripe Payment Element). It should be rendered as a child of ``.
+
+#### Properties
+
+
+ - `fallback?`
+ - `ReactNode`
+
+ Optional fallback content, such as a loading skeleton, to display while the payment form is being initialized.
+
+
+## Examples
+
+
+
+## Related guides
+
+
+ - [Use PaymentElement in a checkout flow](/docs/custom-flows/checkout-new-payment-method)
+ - Add a new payment method during checkout
+
+ ---
+
+ - [Use PaymentElement outside of a checkout flow](/docs/custom-flows/add-new-payment-method)
+ - Add a new payment method outside of a checkout flow
+
diff --git a/docs/hooks/use-payment-methods.mdx b/docs/hooks/use-payment-methods.mdx
new file mode 100644
index 0000000000..9c29f13ecd
--- /dev/null
+++ b/docs/hooks/use-payment-methods.mdx
@@ -0,0 +1,249 @@
+---
+title: '`usePaymentMethods()`'
+description: Access and manage payment methods in your React application with Clerk's usePaymentMethods() hook.
+---
+
+
+
+The `usePaymentMethods()` hook provides access to the payment methods associated with a user or organization. It returns a paginated list of payment methods and includes methods for managing them.
+
+## Parameters
+
+`usePaymentMethods()` accepts a single object with the following properties:
+
+
+ - `for?`
+ - `'user' | 'organization'`
+
+ Specifies whether to fetch payment methods for the current user or organization. Defaults to `'user'`.
+
+ ---
+
+ - `pageSize?`
+ - `number`
+
+ The number of payment methods to fetch per page. Defaults to `10`.
+
+ ---
+
+ - `initialPage?`
+ - `number`
+
+ The page number to start fetching from. Defaults to `1`.
+
+ ---
+
+ - `infinite?`
+ - `boolean`
+
+ When `true`, enables infinite pagination mode where new pages are appended to existing data. When `false`, each page replaces the previous data. Defaults to `false`.
+
+ ---
+
+ - `keepPreviousData?`
+ - `boolean`
+
+ When `true`, the previous data will be kept while loading the next page. This helps prevent layout shifts. Defaults to `false`.
+
+
+## Returns
+
+`usePaymentMethods()` returns an object with the following properties:
+
+
+ - `data`
+ - [CommercePaymentSourceResource](/docs/references/javascript/types/commerce-payment-source-resource)\[] | null
+
+ An array of [payment methods](/docs/references/javascript/types/commerce-payment-source-resource), or `null` if the data hasn't been loaded yet.
+
+ ---
+
+ - `isLoading`
+ - `boolean`
+
+ A boolean that indicates whether the initial data is still being fetched.
+
+ ---
+
+ - `isFetching`
+ - `boolean`
+
+ A boolean that indicates whether any request is still in flight, including background updates.
+
+ ---
+
+ - `hasNextPage`
+ - `boolean`
+
+ A boolean that indicates whether there are more pages available to load.
+
+ ---
+
+ - `hasPreviousPage`
+ - `boolean`
+
+ A boolean that indicates whether there are previous pages available to load.
+
+ ---
+
+ - `fetchNext`
+ - `() => Promise`
+
+ A function to fetch the next page of payment methods.
+
+ ---
+
+ - `fetchPrevious`
+ - `() => Promise`
+
+ A function to fetch the previous page of payment methods.
+
+ ---
+
+ - `pageCount`
+ - `number`
+
+ The total number of available pages.
+
+ ---
+
+ - `count`
+ - `number`
+
+ The total number of payment methods available.
+
+
+## Examples
+
+### Basic usage
+
+The following example demonstrates how to fetch and display a user's payment methods.
+
+```tsx
+import { usePaymentMethods } from '@clerk/nextjs/experimental'
+
+function PaymentMethodsList() {
+ const { data, isLoading } = usePaymentMethods({
+ for: 'user',
+ pageSize: 10,
+ })
+
+ if (isLoading) {
+ return
Loading payment methods...
+ }
+
+ if (!data || data.length === 0) {
+ // Code for how to add a new payment method: https://clerk.com/docs/custom-flows/add-new-payment-method
+ return
No payment methods found. Please add a payment method to your account.
+ )
+}
+```
+
+### Infinite pagination
+
+The following example demonstrates how to implement infinite scrolling with payment methods.
+
+```tsx
+import { usePaymentMethods } from '@clerk/nextjs/experimental'
+
+function InfinitePaymentMethods() {
+ const { data, isLoading, hasNextPage, fetchNext } = usePaymentMethods({
+ for: 'user',
+ infinite: true,
+ pageSize: 20,
+ })
+
+ if (isLoading) {
+ return
Loading...
+ }
+
+ if (!data || data.length === 0) {
+ // Code for how to add a new payment method: https://clerk.com/docs/custom-flows/add-new-payment-method
+ return
No payment methods found. Please add a payment method to your account.
+ )
+}
+```
+
+### With checkout flow
+
+The following example demonstrates how to use `usePaymentMethods()` in a checkout flow to select an existing payment method. For more information on how to build a checkout flow with an existing payment method, see [Build a custom checkout flow](/docs/custom-flows/checkout-new-payment-method).
+
+```tsx
+import { usePaymentMethods, useCheckout } from '@clerk/nextjs/experimental'
+
+function CheckoutPaymentSelection() {
+ const { data, isLoading } = usePaymentMethods({ for: 'user' })
+ const { checkout } = useCheckout()
+ const { confirm, finalize } = checkout
+
+ const handlePaymentSubmit = async (paymentMethodId: string) => {
+ try {
+ // Confirm checkout with selected payment method
+ await confirm({ paymentSourceId: paymentMethodId })
+ // Complete checkout and redirect
+ finalize({ redirectUrl: '/dashboard' })
+ } catch (error) {
+ console.error('Payment failed:', error)
+ }
+ }
+
+ if (isLoading) {
+ return
Loading payment methods...
+ }
+
+ if (!data || data.length === 0) {
+ // Code for how to add a new payment method: https://clerk.com/docs/custom-flows/checkout-new-payment-method
+ return
No payment methods found. Please add a payment method to your account.
+ }
+
+ return (
+
+
Select a payment method
+ {data?.map((method) => (
+
+ ))}
+
+ )
+}
+```
+
+## Related guides
+
+
+ - [Add a new payment method during checkout](/docs/custom-flows/checkout-new-payment-method)
+ - Build a custom checkout flow that allows users to add a new payment method during checkout
+
+ ---
+
+ - [Add a new payment method outside of a checkout flow](/docs/custom-flows/add-new-payment-method)
+ - Build a custom user interface that allows users to add a new payment method to their account
+
diff --git a/docs/hooks/use-plans.mdx b/docs/hooks/use-plans.mdx
new file mode 100644
index 0000000000..c6d17b8bb1
--- /dev/null
+++ b/docs/hooks/use-plans.mdx
@@ -0,0 +1,214 @@
+---
+title: '`usePlans()`'
+description: Access plans in your React application with Clerk's usePlans() hook.
+---
+
+
+
+The `usePlans()` hook provides access to the subscription plans available in your application. It returns a paginated list of plans and includes methods for managing them.
+
+## Parameters
+
+`usePlans()` accepts a single object with the following properties:
+
+
+ - `for?`
+ - `'user' | 'organization'`
+
+ Specifies whether to fetch plans for users or organizations. Defaults to `'user'`.
+
+ ---
+
+ - `pageSize?`
+ - `number`
+
+ The number of plans to fetch per page. Defaults to `10`.
+
+ ---
+
+ - `initialPage?`
+ - `number`
+
+ The page number to start fetching from. Defaults to `1`.
+
+ ---
+
+ - `infinite?`
+ - `boolean`
+
+ When `true`, enables infinite pagination mode where new pages are appended to existing data. When `false`, each page replaces the previous data. Defaults to `false`.
+
+ ---
+
+ - `keepPreviousData?`
+ - `boolean`
+
+ When `true`, the previous data will be kept while loading the next page. This helps prevent layout shifts. Defaults to `false`.
+
+
+## Returns
+
+`usePlans()` returns an object with the following properties:
+
+
+ - `data`
+ - [`CommercePlanResource[]`](/docs/references/javascript/types/commerce-plan-resource) | null
+
+ An array of [plans](/docs/references/javascript/types/commerce-plan-resource), or `null` if the data hasn't been loaded yet.
+
+ ---
+
+ - `isLoading`
+ - `boolean`
+
+ A boolean that indicates whether the initial data is still being fetched.
+
+ ---
+
+ - `isFetching`
+ - `boolean`
+
+ A boolean that indicates whether any request is still in flight, including background updates.
+
+ ---
+
+ - `hasNextPage`
+ - `boolean`
+
+ A boolean that indicates whether there are more pages available to load.
+
+ ---
+
+ - `hasPreviousPage`
+ - `boolean`
+
+ A boolean that indicates whether there are previous pages available to load.
+
+ ---
+
+ - `fetchNext`
+ - `() => Promise`
+
+ A function to fetch the next page of plans.
+
+ ---
+
+ - `fetchPrevious`
+ - `() => Promise`
+
+ A function to fetch the previous page of plans.
+
+ ---
+
+ - `pageCount`
+ - `number`
+
+ The total number of available pages.
+
+ ---
+
+ - `count`
+ - `number`
+
+ The total number of plans available.
+
+
+## Examples
+
+### Basic usage
+
+The following example shows how to fetch and display available plans.
+
+```tsx
+'use client'
+import { usePlans } from '@clerk/nextjs/experimental'
+
+function PlansList() {
+ const { data, isLoading, hasNextPage, fetchNext, hasPreviousPage, fetchPrevious } = usePlans({
+ for: 'user',
+ pageSize: 10,
+ })
+
+ if (isLoading) {
+ return
Loading plans...
+ }
+
+ return (
+
+ {data?.map((plan) => (
+
+
{plan.name}
+
{plan.description}
+
Is free plan: {!plan.hasBaseFee ? 'Yes' : 'No'}
+
+ Price per month: {plan.currency} {plan.amountFormatted}
+
+
+ Price per year: {plan.currency} {plan.annualAmountFormatted} equivalent to{' '}
+ {plan.currency} {plan.annualMonthlyAmountFormatted} per month
+
+ )
+}
+```
+
+### Infinite pagination
+
+The following example demonstrates how to implement infinite scrolling with plans.
+
+```tsx
+'use client'
+import { usePlans } from '@clerk/nextjs/experimental'
+
+function InfinitePlansList() {
+ const { data, isLoading, hasNextPage, fetchNext } = usePlans({
+ for: 'user',
+ infinite: true,
+ pageSize: 2,
+ })
+
+ if (isLoading) {
+ return
Loading plans...
+ }
+
+ return (
+
+
+ {data?.map((plan) => (
+
+
{plan.name}
+
{plan.description}
+
Is free plan: {!plan.hasBaseFee ? 'Yes' : 'No'}
+
+ Price per month: {plan.currency} {plan.amountFormatted}
+
+
+ Price per year: {plan.currency} {plan.annualAmountFormatted} equivalent to{' '}
+ {plan.currency} {plan.annualMonthlyAmountFormatted} per month
+
+
Features:
+
+ {plan.features.map((feature) => (
+
{feature.name}
+ ))}
+
+
+ ))}
+
+
+ {hasNextPage && }
+
+ )
+}
+```
diff --git a/docs/hooks/use-subscription.mdx b/docs/hooks/use-subscription.mdx
new file mode 100644
index 0000000000..31aaa9d86c
--- /dev/null
+++ b/docs/hooks/use-subscription.mdx
@@ -0,0 +1,216 @@
+---
+title: '`useSubscription()`'
+description: Access subscription information in your React application with Clerk's useSubscription() hook.
+---
+
+
+
+The `useSubscription()` hook provides access to subscription information for users or organizations in your application. It returns the current subscription data and includes methods for managing it.
+
+> [!WARNING]
+> The `useSubscription()` hook should only be used for accessing and displaying subscription information. For authorization purposes (i.e., controlling access to features or content), use the [`has()`](/docs/guides/authorization-checks#use-has-for-authorization-checks) helper or the [``](/docs/components/protect) component instead.
+
+## Parameters
+
+`useSubscription()` accepts a single optional object with the following properties:
+
+
+ - `for?`
+ - `'organization' | 'user'`
+
+ Specifies whether to fetch subscription for an organization or user. Defaults to `'user'`.
+
+ ---
+
+ - `keepPreviousData?`
+ - `boolean`
+
+ When `true`, the previous data will be kept in the cache until new data is fetched. This helps prevent layout shifts. Defaults to `false`.
+
+
+## Returns
+
+`useSubscription()` returns an object with the following properties:
+
+
+ - `data`
+ - [`CommerceSubscriptionResource`](/docs/references/javascript/types/commerce-subscription-resource) | null
+
+ The subscription object, or `null` if the data hasn't been loaded yet.
+
+ ---
+
+ - `isLoading`
+ - `boolean`
+
+ A boolean that indicates whether the initial data is still being fetched.
+
+ ---
+
+ - `isFetching`
+ - `boolean`
+
+ A boolean that indicates whether any request is still in flight, including background updates.
+
+ ---
+
+ - `error`
+ - `Error | null`
+
+ Any error that occurred during the data fetch, or `null` if no error occurred.
+
+ ---
+
+ - `revalidate`
+ - `() => Promise`
+
+ Function to manually trigger a refresh of the subscription data.
+
+
+## Examples
+
+### Basic usage
+
+The following example shows how to fetch and display subscription information.
+
+```tsx
+'use client'
+import { useSubscription } from '@clerk/nextjs/experimental'
+
+function SubscriptionInfo() {
+ const { data, isLoading, error } = useSubscription()
+
+ if (isLoading) {
+ return
Loading subscription...
+ }
+
+ if (error) {
+ return
Error loading subscription: {error.message}
+ }
+
+ if (!data) {
+ return
No subscription found
+ }
+
+ return (
+
+
Your Subscription
+ {/* Display subscription details */}
+
+ )
+}
+```
+
+### Organization subscription
+
+The following example shows how to fetch an organization's subscription.
+
+```tsx
+'use client'
+import { useSubscription } from '@clerk/nextjs/experimental'
+
+function OrganizationSubscription() {
+ const { data, isLoading, revalidate } = useSubscription({
+ for: 'organization',
+ keepPreviousData: true,
+ })
+
+ const handleSubscriptionUpdate = async () => {
+ // After making changes to the subscription
+ await revalidate()
+ }
+
+ if (isLoading) {
+ return
+ )
+}
+```
diff --git a/docs/manifest.json b/docs/manifest.json
index 1502e97b12..dec28c0e8b 100644
--- a/docs/manifest.json
+++ b/docs/manifest.json
@@ -889,25 +889,25 @@
{
"title": "``",
"wrap": false,
- "href": "/docs/components/pricing-table"
+ "href": "/docs/components/billing/pricing-table"
},
{
"title": "``",
"tag": "(Beta)",
"wrap": false,
- "href": "/docs/components/checkout-button"
+ "href": "/docs/components/billing/checkout-button"
},
{
"title": "``",
"tag": "(Beta)",
"wrap": false,
- "href": "/docs/components/plan-details-button"
+ "href": "/docs/components/billing/plan-details-button"
},
{
"title": "``",
"tag": "(Beta)",
"wrap": false,
- "href": "/docs/components/subscription-details-button"
+ "href": "/docs/components/billing/subscription-details-button"
}
]
]
@@ -1062,6 +1062,31 @@
"title": "`useReverification()`",
"wrap": false,
"href": "/docs/hooks/use-reverification"
+ },
+ {
+ "title": "`useCheckout()`",
+ "wrap": false,
+ "href": "/docs/hooks/use-checkout"
+ },
+ {
+ "title": "`usePaymentElement()`",
+ "wrap": false,
+ "href": "/docs/hooks/use-payment-element"
+ },
+ {
+ "title": "`usePaymentMethods()`",
+ "wrap": false,
+ "href": "/docs/hooks/use-payment-methods"
+ },
+ {
+ "title": "`usePlans()`",
+ "wrap": false,
+ "href": "/docs/hooks/use-plans"
+ },
+ {
+ "title": "`useSubscription()`",
+ "wrap": false,
+ "href": "/docs/hooks/use-subscription"
}
]
]
@@ -2235,10 +2260,46 @@
"title": "`ClerkAPIError`",
"href": "/docs/references/javascript/types/clerk-api-error"
},
+ {
+ "title": "`ClerkAPIResponseError`",
+ "href": "/docs/references/javascript/types/clerk-api-response-error"
+ },
{
"title": "`ClerkPaginatedResponse`",
"href": "/docs/references/javascript/types/clerk-paginated-response"
},
+ {
+ "title": "`CommerceCheckoutResource`",
+ "href": "/docs/references/javascript/types/commerce-checkout-resource"
+ },
+ {
+ "title": "`CommerceCheckoutTotals`",
+ "href": "/docs/references/javascript/types/commerce-checkout-totals"
+ },
+ {
+ "title": "`CommerceFeatureResource`",
+ "href": "/docs/references/javascript/types/commerce-feature-resource"
+ },
+ {
+ "title": "`CommerceMoney`",
+ "href": "/docs/references/javascript/types/commerce-money"
+ },
+ {
+ "title": "`CommercePaymentSourceResource`",
+ "href": "/docs/references/javascript/types/commerce-payment-source-resource"
+ },
+ {
+ "title": "`CommercePlanResource`",
+ "href": "/docs/references/javascript/types/commerce-plan-resource"
+ },
+ {
+ "title": "`CommerceSubscriptionItemResource`",
+ "href": "/docs/references/javascript/types/commerce-subscription-item-resource"
+ },
+ {
+ "title": "`CommerceSubscriptionResource`",
+ "href": "/docs/references/javascript/types/commerce-subscription-resource"
+ },
{
"title": "`CustomMenuItem`",
"href": "/docs/references/javascript/types/custom-menu-item"
@@ -3731,6 +3792,25 @@
]
]
},
+ {
+ "title": "Billing",
+ "items": [
+ [
+ {
+ "title": "Checkout with a new payment method",
+ "href": "/docs/custom-flows/checkout-new-payment-method"
+ },
+ {
+ "title": "Checkout with an existing payment method",
+ "href": "/docs/custom-flows/checkout-existing-payment-method"
+ },
+ {
+ "title": "Add a new payment method",
+ "href": "/docs/custom-flows/add-new-payment-method"
+ }
+ ]
+ ]
+ },
{
"title": "Account updates",
"items": [
diff --git a/docs/references/javascript/types/clerk-api-error.mdx b/docs/references/javascript/types/clerk-api-error.mdx
index 1e43984dd5..e855c21f11 100644
--- a/docs/references/javascript/types/clerk-api-error.mdx
+++ b/docs/references/javascript/types/clerk-api-error.mdx
@@ -20,33 +20,113 @@ An interface that represents an error returned by the Clerk API.
---
- - `longMessage`
+ - `longMessage?`
- `string`
A more detailed message that describes the error.
---
- - `meta`
+ - `meta?`
- `object`
Additional information about the error.
-
-The `meta` property consists of the following structure:
-
-```ts {{ prettier: false }}
-meta?: {
- paramName?: string
- sessionId?: string
- emailAddresses?: string[]
- identifiers?: string[]
- zxcvbn?: {
- suggestions: {
- code: string
- message: string
- }[]
- }
- permissions?: string[]
-}
-```
+ ---
+
+ - `meta.paramName?`
+ - `string`
+
+ The name of the parameter that caused the error.
+
+ ---
+
+ - `meta.sessionId?`
+ - `string`
+
+ The ID of the session that caused the error.
+
+ ---
+
+ - `meta.emailAddresses?`
+ - `string[]`
+
+ The email addresses that caused the error.
+
+ ---
+
+ - `meta.identifiers?`
+ - `string[]`
+
+ The identifiers that caused the error.
+
+ ---
+
+ - `meta.zxcvbn?`
+ - `object`
+
+ The [zxcvbn](https://github.com/dropbox/zxcvbn) score of the password that caused the error.
+
+ ---
+
+ - `meta.zxcvbn.suggestions?`
+ - `{ code: string; message: string; }[]`
+
+ Suggestions to improve the password.
+
+ ---
+
+ - `meta.permissions?`
+ - `string[]`
+
+ The permissions that caused the error.
+
+ ---
+
+ - `meta.plan?`
+ - `object`
+
+ The plan that caused the error.
+
+ ---
+
+ - `meta.plan.id?`
+ - `string`
+
+ The ID of the plan that caused the error.
+
+ ---
+
+ - `meta.plan.name?`
+ - `string`
+
+ The name of the plan.
+
+ ---
+
+ - `meta.plan.amount_formatted?`
+ - `string`
+
+ The formatted amount of the plan.
+
+ ---
+
+ - `meta.plan.annual_monthly_amount_formatted?`
+ - `string`
+
+ The formatted annual or monthly amount of the plan.
+
+ ---
+
+ - `meta.plan.currency_symbol?`
+ - `string`
+
+ The currency symbol of the plan.
+
+ ---
+
+ - `meta.isPlanUpgradePossible?`
+ - `boolean`
+
+ Whether the plan upgrade is possible.
+
diff --git a/docs/references/javascript/types/clerk-api-response-error.mdx b/docs/references/javascript/types/clerk-api-response-error.mdx
new file mode 100644
index 0000000000..dff85ae6d4
--- /dev/null
+++ b/docs/references/javascript/types/clerk-api-response-error.mdx
@@ -0,0 +1,50 @@
+---
+title: '`ClerkAPIResponseError`'
+description: An interface that represents an error returned by the Clerk API.
+---
+
+An interface that represents an error returned by the Clerk API.
+
+## Properties
+
+
+ - `clerkError`
+ - `true`
+
+ Always true, marks this as a Clerk API error.
+
+ ---
+
+ - `status`
+ - `number`
+
+ The HTTP status code returned by the API.
+
+ ---
+
+ - `message`
+ - `string`
+
+ The main error message.
+
+ ---
+
+ - `clerkTraceId?`
+ - `string`
+
+ Optional. A trace ID from Clerk for debugging or support.
+
+ ---
+
+ - `retryAfter?`
+ - `number`
+
+ Optional. If set, tells you how many seconds to wait before retrying (from `Retry-After` header).
+
+ ---
+
+ - `errors`
+ - [ClerkAPIError](/docs/references/javascript/types/clerk-api-error)\[]
+
+ An array of error objects with more details about what went wrong.
+
diff --git a/docs/references/javascript/types/commerce-checkout-resource.mdx b/docs/references/javascript/types/commerce-checkout-resource.mdx
new file mode 100644
index 0000000000..dde354dfa7
--- /dev/null
+++ b/docs/references/javascript/types/commerce-checkout-resource.mdx
@@ -0,0 +1,134 @@
+---
+title: '`CommerceCheckoutResource`'
+description: 'The CommerceCheckoutResource type represents information about a checkout session.'
+---
+
+The `CommerceCheckoutResource` type represents information about a checkout session.
+
+## Properties
+
+
+ - `id`
+ - `string`
+
+ The unique identifier for the checkout session.
+
+ ---
+
+ - `externalClientSecret`
+ - `string`
+
+ A client secret from an external payment provider (such as Stripe) used to complete the payment on the client-side.
+
+ ---
+
+ - `externalGatewayId`
+ - `string`
+
+ The identifier for the external payment gateway used for this checkout session.
+
+ ---
+
+ - `paymentSource`
+ - `CommercePaymentSourceResource | undefined`
+
+ The payment source being used for the checkout, such as a credit card or bank account.
+
+ ---
+
+ - `plan`
+ - `CommercePlanResource`
+
+ The subscription plan details for the checkout.
+
+ ---
+
+ - `planPeriod`
+ - `'month' | 'annual'`
+
+ The billing period for the plan.
+
+ ---
+
+ - `planPeriodStart`
+ - `number | undefined`
+
+ The start date of the plan period, represented as a Unix timestamp.
+
+ ---
+
+ - `status`
+ - `'needs_initialization' | 'needs_confirmation' | 'completed'`
+
+ The current status of the checkout session.
+
+ ---
+
+ - `totals`
+ - [`CommerceCheckoutTotals`](/docs/references/javascript/types/commerce-checkout-totals)
+
+ The total costs, taxes, and other pricing details.
+
+ ---
+
+ - `isImmediatePlanChange`
+ - `boolean`
+
+ A boolean that indicates if the plan change will take effect immediately after checkout.
+
+ ---
+
+ - [`confirm()`](#confirm)
+ - `(params: ConfirmCheckoutParams) => Promise`
+
+ A method to confirm and finalize the checkout process, usually after payment information has been provided and validated. [Learn more.](#confirm)
+
+
+### `confirm()`
+
+The `confirm()` function is used to confirm and finalize the checkout process, usually after payment information has been provided and validated.
+
+#### Parameters
+
+**Only one of `paymentSourceId`, `paymentToken`, or `useTestCard` should be provided.**
+
+
+ - `orgId?`
+ - `string | undefined`
+
+ The organization ID to perform the checkout for.
+
+ ---
+
+ - `paymentSourceId?`
+ - `string | undefined`
+
+ The ID of a saved payment source to use for this checkout.
+
+ ---
+
+ - `paymentToken?`
+ - `string | undefined`
+
+ A token representing payment details, usually from a payment form.
+
+ **Requires** `gateway` to be provided.
+
+ ---
+
+ - `useTestCard?`
+ - `boolean | undefined`
+
+ If true, uses a test card for the checkout.
+
+ **Requires** `gateway` to be provided.
+
+ ---
+
+ - `gateway?`
+ - `PaymentGateway | undefined`
+
+ The payment gateway to use. For example, `'stripe'` or `'paypal'`.
+
+ **Required** if `paymentToken` or `useTestCard` is provided.
+
diff --git a/docs/references/javascript/types/commerce-checkout-totals.mdx b/docs/references/javascript/types/commerce-checkout-totals.mdx
new file mode 100644
index 0000000000..bc0cb88072
--- /dev/null
+++ b/docs/references/javascript/types/commerce-checkout-totals.mdx
@@ -0,0 +1,50 @@
+---
+title: '`CommerceCheckoutTotals`'
+description: 'The CommerceCheckoutTotals type represents the total costs, taxes, and other pricing details for a checkout session.'
+---
+
+The `CommerceCheckoutTotals` type represents the total costs, taxes, and other pricing details for a checkout session.
+
+## Properties
+
+
+ - `subtotal`
+ - [`CommerceMoney`](/docs/references/javascript/types/commerce-money)
+
+ The price of the items or plan before taxes, credits, or discounts are applied.
+
+ ---
+
+ - `grandTotal`
+ - [`CommerceMoney`](/docs/references/javascript/types/commerce-money)
+
+ The total amount for the checkout, including taxes and after credits/discounts are applied. This is the final amount due.
+
+ ---
+
+ - `taxTotal`
+ - [`CommerceMoney`](/docs/references/javascript/types/commerce-money)
+
+ The amount of tax included in the checkout.
+
+ ---
+
+ - `totalDueNow`
+ - [`CommerceMoney`](/docs/references/javascript/types/commerce-money)
+
+ The amount that needs to be immediately paid to complete the checkout.
+
+ ---
+
+ - `credit`
+ - [`CommerceMoney`](/docs/references/javascript/types/commerce-money)
+
+ Any credits (like account balance or promo credits) that are being applied to the checkout.
+
+ ---
+
+ - `pastDue`
+ - [`CommerceMoney`](/docs/references/javascript/types/commerce-money)
+
+ Any outstanding amount from previous unpaid invoices that is being collected as part of the checkout.
+
diff --git a/docs/references/javascript/types/commerce-feature-resource.mdx b/docs/references/javascript/types/commerce-feature-resource.mdx
new file mode 100644
index 0000000000..faa9e3e89d
--- /dev/null
+++ b/docs/references/javascript/types/commerce-feature-resource.mdx
@@ -0,0 +1,43 @@
+---
+title: '`CommerceFeatureResource`'
+description: 'The CommerceFeatureResource type represents a feature of a subscription plan.'
+---
+
+The `CommerceFeatureResource` type represents a feature of a subscription plan.
+
+## Properties
+
+
+ - `id`
+ - `string`
+
+ The unique identifier for the feature.
+
+ ---
+
+ - `name`
+ - `string`
+
+ The display name of the feature.
+
+ ---
+
+ - `description`
+ - `string`
+
+ A short description of what the feature provides.
+
+ ---
+
+ - `slug`
+ - `string`
+
+ A unique, URL-friendly identifier for the feature.
+
+ ---
+
+ - `avatarUrl`
+ - `string`
+
+ The URL of the feature's avatar image.
+
diff --git a/docs/references/javascript/types/commerce-money.mdx b/docs/references/javascript/types/commerce-money.mdx
new file mode 100644
index 0000000000..757e86541f
--- /dev/null
+++ b/docs/references/javascript/types/commerce-money.mdx
@@ -0,0 +1,36 @@
+---
+title: '`CommerceMoney`'
+description: 'The CommerceMoney type represents a monetary value with currency information.'
+---
+
+The `CommerceMoney` type represents a monetary value with currency information.
+
+## Properties
+
+
+ - `amount`
+ - `number`
+
+ The raw amount as a number, usually in the smallest unit of the currency (like cents for USD). For example, `1000` for $10.00.
+
+ ---
+
+ - `amountFormatted`
+ - `string`
+
+ The amount as a formatted string. For example, `10` for $10.00.
+
+ ---
+
+ - `currency`
+ - `string`
+
+ The ISO currency code for this amount. For example, `USD` or `EUR`.
+
+ ---
+
+ - `currencySymbol`
+ - `string`
+
+ The symbol for the currency. For example, `$`, `€`, or `£`.
+
diff --git a/docs/references/javascript/types/commerce-payment-source-resource.mdx b/docs/references/javascript/types/commerce-payment-source-resource.mdx
new file mode 100644
index 0000000000..2046a9fb12
--- /dev/null
+++ b/docs/references/javascript/types/commerce-payment-source-resource.mdx
@@ -0,0 +1,82 @@
+---
+title: '`CommercePaymentSourceResource`'
+description: 'The CommercePaymentSourceResource type represents a payment source for a checkout session.'
+---
+
+The `CommercePaymentSourceResource` type represents a payment source for a checkout session.
+
+## Properties
+
+
+ - `id`
+ - `string`
+
+ The unique identifier for the payment method.
+
+ ---
+
+ - `last4`
+ - `string`
+
+ The last four digits of the payment method.
+
+ ---
+
+ - `paymentMethod`
+ - `string`
+
+ The type of payment method. For example, `'card'` or `'bank_account'`.
+
+ ---
+
+ - `cardType`
+ - `string`
+
+ The brand or type of card. For example, `'visa'` or `'mastercard'`.
+
+ ---
+
+ - `isDefault`
+ - `boolean`
+
+ A boolean that indicates if this payment method is set as the default for the account.
+
+ ---
+
+ - `isRemovable`
+ - `boolean`
+
+ A boolean that indicates if the payment method can be removed by the user.
+
+ ---
+
+ - `status`
+ - `'active' | 'expired' | 'disconnected'`
+
+ The current status of the payment method.
+
+ ---
+
+ - `walletType`
+ - `string | undefined`
+
+ The type of digital wallet, if applicable. For example, `'apple_pay'`, or `'google_pay'`.
+
+ ---
+
+ - `remove()`
+ - `(params?: RemovePaymentSourceParams) => Promise`
+
+ A function that removes this payment source from the account. Accepts the following parameters:
+
+ - `orgId?` (`string`): The ID of the organization to remove the payment source from.
+
+ ---
+
+ - `makeDefault()`
+ - `(params?: MakeDefaultPaymentSourceParams) => Promise`
+
+ A function that sets this payment source as the default for the account. Accepts the following parameters:
+
+ - `orgId?` (`string`): The ID of the organization to set as the default.
+
diff --git a/docs/references/javascript/types/commerce-plan-resource.mdx b/docs/references/javascript/types/commerce-plan-resource.mdx
new file mode 100644
index 0000000000..04dac7bb76
--- /dev/null
+++ b/docs/references/javascript/types/commerce-plan-resource.mdx
@@ -0,0 +1,141 @@
+---
+title: '`CommercePlanResource`'
+description: 'The CommercePlanResource type represents a subscription plan with its details.'
+---
+
+The `CommercePlanResource` type represents a subscription plan with its details.
+
+## Properties
+
+
+ - `id`
+ - `string`
+
+ The unique identifier for the plan.
+
+ ---
+
+ - `name`
+ - `string`
+
+ The display name of the plan.
+
+ ---
+
+ - `amount`
+ - `number`
+
+ The price of the plan for a single billing period (usually monthly). For example, `1000` for $10.00.
+
+ ---
+
+ - `amountFormatted`
+ - `string`
+
+ The formatted price for a single billing period. For example, `10` for $10.00.
+
+ ---
+
+ - `annualAmount`
+ - `number`
+
+ The total price for a full year of the plan, in the smallest unit of the currency. For example, `10000` for $100.00.
+
+ ---
+
+ - `annualAmountFormatted`
+ - `string`
+
+ The formatted price for a full year of the plan. For example, `100` for $100.00.
+
+ ---
+
+ - `annualMonthlyAmount`
+ - `number`
+
+ The effective monthly price when billed annually, in the smallest unit of the currency. For example, `833` for $8.33.
+
+ ---
+
+ - `annualMonthlyAmountFormatted`
+ - `string`
+
+ The formatted effective monthly price when billed annually. For example, `8.33` for $8.33.
+
+ ---
+
+ - `currencySymbol`
+ - `string`
+
+ The symbol for the plan's currency. For example, `$` or `€`.
+
+ ---
+
+ - `currency`
+ - `string`
+
+ The ISO currency code for the plan. For example, `USD` or `EUR`.
+
+ ---
+
+ - `description`
+ - `string`
+
+ A short description of what the plan offers.
+
+ ---
+
+ - `isDefault`
+ - `boolean`
+
+ A boolean that indicates if this plan is the default plan.
+
+ ---
+
+ - `isRecurring`
+ - `boolean`
+
+ A boolean that indicates if the plan is billed on a recurring basis.
+
+ ---
+
+ - `hasBaseFee`
+ - `boolean`
+
+ A boolean that indicates if the plan has a base fee.
+
+ ---
+
+ - `forPayerType`
+ - `'org' | 'user'`
+
+ The type of payer this plan is for.
+
+ ---
+
+ - `publiclyVisible`
+ - `boolean`
+
+ A boolean that indicates if the plan is visible to the public.
+
+ ---
+
+ - `slug`
+ - `string`
+
+ A unique, URL-friendly identifier for the plan.
+
+ ---
+
+ - `avatarUrl`
+ - `string`
+
+ The URL of the plan's avatar image.
+
+ ---
+
+ - `features`
+ - [CommerceFeatureResource](/docs/references/javascript/types/commerce-feature-resource)\[]
+
+ The list of features included in this plan.
+
diff --git a/docs/references/javascript/types/commerce-subscription-item-resource.mdx b/docs/references/javascript/types/commerce-subscription-item-resource.mdx
new file mode 100644
index 0000000000..3156ffc181
--- /dev/null
+++ b/docs/references/javascript/types/commerce-subscription-item-resource.mdx
@@ -0,0 +1,122 @@
+---
+title: '`CommerceSubscriptionItemResource`'
+description: 'The CommerceSubscriptionItemResource type represents an item in a subscription.'
+---
+
+The `CommerceSubscriptionItemResource` type represents an item in a subscription.
+
+## Properties
+
+
+ - `id`
+ - `string`
+
+ The unique identifier for the subscription item.
+
+ ---
+
+ - `paymentSourceId`
+ - `string`
+
+ The identifier of the payment source used for the subscription item.
+
+ ---
+
+ - `plan`
+ - [`CommercePlanResource`](/docs/references/javascript/types/commerce-plan-resource)
+
+ The plan associated with the subscription item.
+
+ ---
+
+ - `planPeriod`
+ - `'month' | 'annual'`
+
+ The billing period of the subscription item.
+
+ ---
+
+ - `status`
+ - `'active' | 'ended' | 'upcoming' | 'past_due'`
+
+ The current status of the subscription item.
+
+ ---
+
+ - `createdAt`
+ - `Date`
+
+ The date when the subscription item was created.
+
+ ---
+
+ - `pastDueAt`
+ - `Date | null`
+
+ The date when the subscription item became past due, or `null` if it's not past due.
+
+ ---
+
+ - `periodStartDate`
+ - `Date`
+
+ The start date of the current billing period.
+
+ ---
+
+ - `periodEndDate`
+ - `Date | null`
+
+ The end date of the current billing period, or `null` if not set.
+
+ ---
+
+ - `canceledAtDate`
+ - `Date | null`
+
+ The date when the subscription item was canceled, or `null` if it's not canceled.
+
+ ---
+
+ - `periodStart`
+ - `number`
+
+ **Deprecated. Use `periodStartDate` instead.** The Unix timestamp for the start of the current billing period.
+
+ ---
+
+ - `periodEnd`
+ - `number`
+
+ **Deprecated. Use `periodEndDate` instead.** The Unix timestamp for the end of the current billing period.
+
+ ---
+
+ - `canceledAt`
+ - `number | null`
+
+ **Deprecated. Use `canceledAtDate` instead.** The Unix timestamp for when the item was canceled, or `null`.
+
+ ---
+
+ - `amount`
+ - [CommerceMoney](/docs/references/javascript/types/commerce-money) | undefined
+
+ The amount charged for the subscription item.
+
+ ---
+
+ - `credit`
+ - `{ amount: CommerceMoney } | undefined`
+
+ Credit info for the subscription item, if any.
+
+ ---
+
+ - `cancel`
+ - `(params: CancelSubscriptionParams) => Promise`
+
+ A function to cancel the subscription item. Accepts the following parameters:
+
+ - `orgId?` (`string`): The ID of the organization to cancel the subscription item for.
+
diff --git a/docs/references/javascript/types/commerce-subscription-resource.mdx b/docs/references/javascript/types/commerce-subscription-resource.mdx
new file mode 100644
index 0000000000..c79f1e0de4
--- /dev/null
+++ b/docs/references/javascript/types/commerce-subscription-resource.mdx
@@ -0,0 +1,64 @@
+---
+title: '`CommerceSubscriptionResource`'
+description: 'The CommerceSubscriptionResource type represents a subscription to a plan.'
+---
+
+The `CommerceSubscriptionResource` type represents a subscription to a plan.
+
+## Properties
+
+
+ - `id`
+ - `string`
+
+ The unique identifier for the subscription.
+
+ ---
+
+ - `activeAt`
+ - `Date`
+
+ The date when the subscription became active.
+
+ ---
+
+ - `createdAt`
+ - `Date`
+
+ The date when the subscription was created.
+
+ ---
+
+ - `nextPayment`
+ - `{ amount: CommerceMoney; date: Date } | null`
+
+ Information about the next payment, including the amount and the date it's due. Returns `null` if there is no upcoming payment.
+
+ ---
+
+ - `pastDueAt`
+ - `Date | null`
+
+ The date when the subscription became past due, or `null` if it's not past due.
+
+ ---
+
+ - `status`
+ - `'active' | 'past_due'`
+
+ The current status of the subscription.
+
+ ---
+
+ - `subscriptionItems`
+ - [CommerceSubscriptionItemResource](/docs/references/javascript/types/commerce-subscription-item-resource)\[]
+
+ The list of items (plans/features) included in this subscription.
+
+ ---
+
+ - `updatedAt`
+ - `Date | null`
+
+ The date when the subscription was last updated, or `null` if it hasn't been updated.
+
diff --git a/redirects/static/docs.json b/redirects/static/docs.json
index 0fb833aa54..ae606f5364 100644
--- a/redirects/static/docs.json
+++ b/redirects/static/docs.json
@@ -2469,6 +2469,26 @@
"destination": "/docs/references/overview#build-with-community-maintained-sdks",
"permanent": true
},
+ {
+ "source": "/docs/components/checkout-button",
+ "destination": "/docs/components/billing/checkout-button",
+ "permanent": true
+ },
+ {
+ "source": "/docs/components/plan-details-button",
+ "destination": "/docs/components/billing/plan-details-button",
+ "permanent": true
+ },
+ {
+ "source": "/docs/components/pricing-table",
+ "destination": "/docs/components/billing/pricing-table",
+ "permanent": true
+ },
+ {
+ "source": "/docs/components/subscription-details-button",
+ "destination": "/docs/components/billing/subscription-details-button",
+ "permanent": true
+ },
{
"source": "/docs/references/nextjs/build-mcp-server",
"destination": "/docs/mcp/build-mcp-server",