doctor is green and something is still wrong, the symptoms below are the ones that come up most.
DATABASE_URL is not set
The Store Runtime boots without a database, and then every endpoint that needs data fails. That combination makes the symptom look unrelated to the cause. Set both in.env:
.env
DATABASE_URL is the pooled string and DATABASE_URL_UNPOOLED is the direct one. Under Docker Compose, both point at postgres:5432.
Database is not reachable
The TCP check in86d dev and 86d init failed. Either the database is down or the host in DATABASE_URL is wrong.
- Local Postgres:
pg_isready -h localhost -p 5432 - Docker Compose:
docker compose ps postgresshould say healthy - Neon or Railway: check the project is awake and the connection string has not rotated
A Module component renders as text
<ProductGrid /> shows up as literal text, or the page errors with “component not found”.
Regenerate and restart:
config.json. A "*" wildcard, or a missing modules field, discovers Modules without admitting Experimental ones, and every first-party Module is Experimental. You also need advanced.version: 1 with allowExperimentalModules: true.
Module is enabled in Template but not found
86d doctor says this when config.json names a Module with no folder under modules/. Either install it:
config.json and run 86d generate.
Code generation fails
86d generate almost always fails for one of three reasons:
- a Module whose
src/index.tshas no default factory export - a Module whose
package.jsonnamedoes not match its directory. First-party Modules must be@86d-store/<dir> - a circular
requiresbetween two Modules
Stripe webhooks return 401
Stripe rejects with401 when the signing secret is wrong, when the signed body changed in transit, or when the timestamp is outside the replay window. In that order of likelihood:
STRIPE_WEBHOOK_SECREThas to be the secret for the endpoint that is receiving the event, on the deployment that is receiving it. Test and live secrets differ, and so do secrets per endpoint.- Check that no reverse proxy is rewriting the body. The handler reads the raw bytes before any JSON parsing, and reformatting the JSON invalidates the signature.
- Events older than 5 minutes are rejected as replays. Resend from the Stripe CLI to get a current signature.
Could not find active Template config.json
The CLI works out which Template is active from thetemplate/* path alias in apps/store/tsconfig.json. Hand-edit that alias into something other than ../../templates/<name>/ and the CLI stops being able to find anything.
Fix it by re-activating:
Production rejects BETTER_AUTH_SECRET
Production refuses to start when the secret is missing, under 32 characters, a known default, or too predictable to pass the entropy check. Generate a real one:.env and restart. 86d init does this for you on first run.
86d.app sign-in callbacks fail
Single sign-on only turns on when both OAuth client values are set. Then, in order:BETTER_AUTH_URLhas to be the Store’s public URL.86D_API_URLhas to reach a Control Plane serving valid OpenID discovery metadata.86D_ADMIN_OAUTH_CLIENT_IDand86D_ADMIN_OAUTH_CLIENT_SECREThave to belong to the same OAuth client.- The returned profile needs the
adminrole or thestore:adminscope. 86D_WORKLOAD_CREDENTIALis not a substitute. It authenticates a machine, and no machine credential can authenticate a person.- Do not debug the Google, X, Slack, Shopify, Apple, or Facebook variables. The auth package does not read them, so nothing you set there has any effect.
Uploads fail in production
localstorage on a serverless host does not persist. Files written to disk are gone on the next request. SwitchSTORAGE_CLIENTtovercelwith a Blob store attached, or tos3.- With MinIO inside Docker, set
STORAGE_PUBLIC_URL_MODE=proxy. Otherwise upload URLs point at a container hostname a browser cannot resolve.
TypeScript errors after an upgrade
Clean install first:Still stuck
- Run
86d doctorand copy the whole output. - Copy the error verbatim, the command that produced it, and the page or endpoint involved.
- Open an issue at github.com/86d-store/86d/issues.