Skip to main content
The /subscribe route presents the Stripe Elements checkout form where the customer enters their card details to complete the subscription payment. The PaymentIntent client secret is passed in as a query parameter from the /prices redirect.

GET /subscribe

Reads the client_secret query parameter and passes it to the Stripe Elements card form.

Query parameters

client_secret
string
required
The PaymentIntent client secret returned when the subscription was created on POST /prices. Stripe Elements uses this value to identify and confirm the correct PaymentIntent.

Loader source

export const loader = async ({ request }: LoaderFunctionArgs) => {
  const url = new URL(request.url);
  const client_secret = url.searchParams.get("client_secret");
  return { client_secret };
};

Rendered components

The route renders a Stripe Elements provider wrapping the card subscription form:
<Elements stripe={stripePromise}>
  <CardSubscription clientSecret={client_secret} />
</Elements>
stripePromise is initialized with your Stripe publishable key via loadStripe.

Payment confirmation

When the customer submits the card form, CardSubscription calls stripe.confirmCardPayment with the client secret and the entered payment details:
stripe.confirmCardPayment(clientSecret, {
  payment_method: {
    card,
    billing_details: { name },
  },
});

Success

If confirmCardPayment resolves without an error, the user is navigated to /account to view their active subscription.

Error

If confirmCardPayment returns an error, the error message is displayed inline in the card form. The customer can correct their details and resubmit without navigating away.

Test cards

Use the following Stripe test card numbers to verify payment flows in test mode.
Card numberBehavior
4242 4242 4242 4242Payment succeeds immediately.
4000 0025 0000 3155Requires Strong Customer Authentication (SCA) — triggers a 3D Secure challenge.
For both test cards, use any future expiry date, any 3-digit CVC, and any billing postal code.
Test cards only work when Stripe is initialized with a test publishable key (pk_test_...). In live mode, use real card numbers.
If the SCA test card redirects to a Stripe authentication dialog, click Complete authentication to simulate a successful 3D Secure challenge.

Build docs developers (and LLMs) love