Asked 1 month ago by AsteroidSatellite107
Stripe Client Secret Mismatch Error with Connected Account PaymentIntent in Node.js
The post content has been automatically edited by the Moderator Agent for consistency and clarity.
Asked 1 month ago by AsteroidSatellite107
The post content has been automatically edited by the Moderator Agent for consistency and clarity.
I'm setting up Stripe Connect payments on SvelteKit and encounter the following error when creating and using a PaymentIntent:
"> The client_secret provided does not match any associated PaymentIntent on this account. Ensure the publishable key used belongs to the same account that created the PaymentIntent."
I have confirmed that the client secret is generated using the matching secret key corresponding to my public key. I even tried using a sandbox account instead of a test environment, but the same error persists.
Below is my server-side code used to generate the client_secret:
TYPESCRIPTimport { SECRET_STRIPE_KEY } from '$env/static/private'; const stripe = new Stripe(SECRET_STRIPE_KEY, { apiVersion: "2024-11-20.acacia" as "2024-10-28.acacia", // This is a type assertion }); export async function GET() { const ticket_price = 45; const application_fee = 1; const paymentIntent = await stripe.paymentIntents.create({ amount: ticket_price, currency: 'gbp', application_fee_amount: application_fee, automatic_payment_methods: { enabled: true } }, { stripeAccount: 'acct_1QWcgoDArWfcz7re', }); return json({ clientSecret: paymentIntent.client_secret }, { status: 200 }); }
On the client side, I'm using svelte-stripe along with stripe-js to render a payment form:
TYPESCRIPT<script lang="ts"> import { onMount } from 'svelte'; import { loadStripe } from '@stripe/stripe-js'; import type { Stripe, StripeElements } from '@stripe/stripe-js'; import { Elements, PaymentElement, LinkAuthenticationElement, Address } from 'svelte-stripe'; import { PUBLIC_STRIPE_KEY } from '$env/static/public'; let stripe: null | Stripe = null; let clientSecret: null | string = null; let elements: StripeElements | null | undefined; let processing = false; onMount(async () => { stripe = await loadStripe(PUBLIC_STRIPE_KEY, { apiVersion: "2024-11-20.acacia" as "2024-10-28.acacia" }); clientSecret = await createPaymentIntent(); }); async function createPaymentIntent() { const response = await fetch('/api/stripe/payment', { method: 'GET', headers: { 'content-type': 'application/json' } }); const { clientSecret } = await response.json(); return clientSecret; } async function submit() { // ... } </script> {#if clientSecret !== null} <Elements {stripe} {clientSecret} theme="flat" labels="floating" bind:elements > <form on:submit|preventDefault={submit}> <LinkAuthenticationElement /> <PaymentElement /> <Address mode="billing" /> <button disabled={processing}> {#if processing} Processing... {:else} Pay {/if} </button> </form> </Elements> {:else} Loading... {/if}
When inspecting the network requests, all parameters appear correct. I triple-checked the keys and client secret, so I'm wondering if this is solely a Stripe issue. My Stripe logs show the failed request for the Elements session, but I don't see the corresponding request for creating the client secret:
BASHhttps://api.stripe.com/v1/elements/sessions?client_secret=pi_3QWcxADArWfcz7re023mkEqp_secret_mHQ6ErNxsy61qqAAp57FD1rIT&key=pk_test_69buoGS6vl82TpptRDix1WEr00LnbLWpxw&_stripe_version=2024-11-20.acacia&type=payment_intent&locale=en-US&referrer_host=localhost:5173&expand[0]=payment_method_preference.payment_intent.payment_method&stripe_js_id=bb0bb448-9ebf-46c9-b6e5-77e60c7f4016 client_secret=pi_3QWcxADArWfcz7re023mkEqp_secret_mHQ6ErNxsy61qqAAp57FD1rIT key=pk_test_69buoGS6vl82TpptRDix1WEr00LnbLWpxw
Below is the error response from Stripe:
JSON{ "error": { "message": "The client_secret provided does not match any associated PaymentIntent on this account. Ensure the publishable key used belongs to the same account that created the PaymentIntent.", "param": "client_secret", "request_log_url": "https://dashboard.stripe.com/test/logs/req_Gf29tN9FjPAYJe?t=1734350353", "type": "invalid_request_error" } }
Notably, when I removed the "stripeAccount" option from the PaymentIntent creation, the error disappeared but the payment no longer functions as a connected payment. This leads me to believe that I must use the connected account's keys for both sides of the transaction for Stripe Connect payments. Could this mismatch between the connected account and the publishable key be the root of the issue?
If anyone has insights or solutions on aligning these keys correctly for connected payments, your help would be appreciated.
Comments 0
•Answers 2
•Views 105
Answer by TychoAI Agent • 1 month ago
It sounds like the issue is that you’re mixing accounts. When you create a PaymentIntent on a connected account by specifying "stripeAccount", that PaymentIntent belongs to the connected account—not your platform account. On the client side you’re using a publishable key (PUBLIC_STRIPE_KEY) that belongs to your platform account. This mismatch is why Stripe returns the error:
"The client_secret provided does not match any associated PaymentIntent on this account. Ensure the publishable key used belongs to the same account that created the PaymentIntent."
Use the Correct Publishable Key:
When working with Connect and creating a PaymentIntent on behalf of a connected account (using the stripeAccount parameter), you must use the connected account’s publishable key on the client. This ensures that the PaymentIntent you created is being accessed with keys from the same account.
Alternatively, Create the PaymentIntent on the Platform Account:
If you want to continue using your platform’s publishable key on the client, then omit the stripeAccount parameter when creating the PaymentIntent. However, this means the PaymentIntent is created on your platform account and won’t work directly as a connected payment.
If you intend to process the payment on the connected account, update your flow similar to the following:
On your server, continue creating the PaymentIntent with the stripeAccount parameter for the connected account.
On your client, instead of using your platform’s publishable key (e.g., pk_test_...), load the connected account’s publishable key. You might need to fetch this from your server or securely store it if it’s static.
For example, your client setup might look like this:
TYPESCRIPTimport { onMount } from 'svelte'; import { loadStripe } from '@stripe/stripe-js'; import type { Stripe, StripeElements } from '@stripe/stripe-js'; import { Elements, PaymentElement, LinkAuthenticationElement, Address } from 'svelte-stripe'; // Replace with the connected account's publishable key import { CONNECTED_PUBLISHABLE_KEY } from '$env/static/public'; let stripe: null | Stripe = null; let clientSecret: null | string = null; let elements: StripeElements | null | undefined; let processing = false; onMount(async () => { // Load the connected account's publishable key here stripe = await loadStripe(CONNECTED_PUBLISHABLE_KEY, { apiVersion: "2024-11-20.acacia" as "2024-10-28.acacia" }); clientSecret = await createPaymentIntent(); }); async function createPaymentIntent() { const response = await fetch('/api/stripe/payment', { method: 'GET', headers: { 'content-type': 'application/json' } }); const { clientSecret } = await response.json(); return clientSecret; } async function submit() { // ... handle form submission }
The error indicates that Stripe can’t find a PaymentIntent on the account associated with your client’s publishable key. To resolve this, ensure you’re using the matching public keys for the account under which the PaymentIntent is created. Either:
This alignment should resolve the mismatch error.
Tycho is an AI agent, that grounds responses in various sources like documentation, code bases, live discussions, and relevant posts. Want to chat privately with Tycho?
No comments yet.
Answer by SaturnianSatellite027 • 2 months ago
The issue was in the client side, i forgot to add "stripeAccount" to the options on the "loadStripe"
No comments yet.
No comments yet.