stripe / react-stripe-js

React components for Stripe.js and Stripe Elements
https://stripe.com/docs/stripe-js/react
MIT License
1.75k stars 267 forks source link

[BUG]: Why are secrets exposed in the front end? #507

Closed openSourceBugs closed 3 months ago

openSourceBugs commented 4 months ago

What happened?

I'm not really understanding why "secrets" are handled in this way. Any user can call/playback/sniff/whatever the /create-intent endpoint and get the "secret".

const res = await fetch('/create-intent', { method: 'POST', });

const {client_secret: clientSecret} = await res.json();  
alert("the secret was " + client_secret);  // Is this really so secret if the user can put a breakpoint here and see what it is?

Environment

No response

Reproduction

No response

openSourceBugs commented 4 months ago

This seems like a huge obvious security flaw but I don't know how stripe is supposed to work based on the docs anyhow.

brendanm-stripe commented 3 months ago

Thanks for raising this. Broadly, this is expected behaviour necessary for Stripe.js to function. The client_secret on Payment and Setup Intents are used to allow those intents to be confirmed by the client using a publishable key, but it is scoped to just that one intent and only allows specific actions that are expected to happen client side.

To prevent abuse, we recommend securing your endpoint that creates intents and returns client secrets: https://docs.stripe.com/disputes/prevention/card-testing#implement-controls

If you prefer not to confirm from the client, you can instead generate Confirmation Tokens with just your PK and confirm intents on your server: https://docs.stripe.com/payments/finalize-payments-on-the-server?platform=web&type=payment#create-ct

If you've got a more specific security-related concern, please share those details using security@stripe.com or using our HackerOne bug bounty program and our team will investigate urgently.