Skip to content

Sandbox credentials

In sandbox mode the application never holds the credential it appears to use.

egress:
rules:
- host: api.stripe.com
mode: sandbox
credential: STRIPE_SECRET_KEY

The container gets a placeholder in STRIPE_SECRET_KEY. The proxy substitutes the sandbox key on the way out. The live key is never inside the environment, so nothing that reads the container’s environment, filesystem, or process list can find it: not a crash dump, not a debug endpoint that prints process.env, not a dependency doing something it should not.

There is a conformance test that starts a container and asserts exactly that.

The same chain as every other secret: an exported variable, then .env, then the encrypted local store. The manifest names the variable and never the value.

Terminal window
export STRIPE_SECRET_KEY_SANDBOX=sk_test_...
AF-SEC-003 The value supplied for STRIPE_SECRET_KEY carries a live credential
prefix, and STRIPE_SECRET_KEY is configured for sandbox use.
Next: Point STRIPE_SECRET_KEY at a sandbox credential; the environment must
never hold a live key.

Checked before anything starts, by prefix, so a live key cannot be handed to a sandbox rule by accident. This is the same detector CI runs over the repository and the proxy runs over outbound requests: one definition of what a live credential looks like, in all three places.

AF-NET-005 The sandbox credential for api.stripe.com was rejected: invalid api
key provided.

The substitution worked and the key is wrong. Usually a sandbox key from a different account than the webhook signing secret, or one that was rotated.

Use mock with a fixture pack, or synth where a fixture would have to be invented anyway. block is also an answer: an environment that cannot reach a service is an environment that tells you what your application does when that service is down.

Related: egress, secrets.