Security and CSP
If your page sends a Content-Security-Policy, it has to allow the few things the checkout loads, or the
checkout will not run and the browser will tell you so only in the console. This page is that list.
Where the keys may go #
The publishable key is safe in a web page: it grants no permission at all, and every route that takes it also checks the page's origin. The secret key belongs on your server and nowhere else.
The full version of that, including what to do first if a key gets out, is on Keys.
The policy the checkout needs #
The table names the production hosts. On dev the checkout loads from https://js-dev.ripper.dev and calls
https://api-dev.ripper.dev.
| directive | allow | for |
|---|---|---|
script-src |
https://js.ripper.dev |
The loader, and the one runtime script it inserts. There is no integrity attribute and no version in the URL: the origin is the trust anchor, because the runtime rolls continuously. |
connect-src |
https://js.ripper.dev and https://api.ripper.dev |
The loader's manifest request, and the runtime's API calls. The manifest is fetched with credentials omitted and no caching, because it is the rollout switch. |
font-src |
https://js.ripper.dev |
The checkout's self-hosted faces. Registered through the FontFace API rather than an @font-face rule, so fonts need no style-src of their own. If this is not allowed, the checkout paints in system fonts and the payment still completes. |
img-src |
not yet published | The merchant logo in the checkout header, when the integration's brand sets one. Only needed when a logo is configured, and the URL must be https or it is ignored. NOT published as a fact: no test loads a merchant logo under a policy, so unlike the other rows this one has been reasoned from the code rather than observed in a browser. |
style-src |
'self' |
The checkout's own stylesheet, and any custom CSS set on the integration. No inline styles needed: the runtime adopts a constructable stylesheet, and creates no style element at all. A browser without that support falls back to a style element, which would need inline styles allowed; Safari before 16.4 is that case. |
Every row above is verified for test mode. A strict policy is not yet verified for live payments: live card entry and bank checks load further card-security sources that are not published yet.
What "verified" means here #
A row is published as a fact only where it has been observed in a browser under a real policy, not where it has been reasoned from the code. That is why one row reads "not yet published": nothing yet loads a merchant logo under a policy, so the img-src row is reasoned like the others but has not been watched. A policy built from the published rows will work; a row we have not tested is left out rather than guessed at.
The rows above were confirmed in Chromium, WebKit, Firefox and mobile Safari, under a policy of
default-src 'none' with only the listed sources added, asserting that nothing was refused, the checkout
painted, and a payment completed. Live mode is not verified for any row: live card entry loads further
card-security sources, and this page will say so rather than imply otherwise.
If a directive is missing #
A blocked script or connection stops the checkout: the page shows nothing where the checkout should be, and the browser console names the directive. A blocked font costs only the font — the checkout paints in your fallback stack and the payment still completes, which is deliberate.