PreviewDrop for Express

Deploy previews for Express & Node.js apps

Push a branch, get a live preview URL. PreviewDrop installs your dependencies, runs your Node server as a real process, and posts the link to the pull request in under 60 seconds.

TL;DR
Add a Dockerfile, connect your repo, push. PreviewDrop runs npm ci and boots node server.js behind a TLS-terminated subdomain. Because it’s an always-on process, your websockets, SSE streams, in-memory caches and persistent DB pools all behave exactly as they do locally.

Dockerfile

Drop this at the root of your repo. PreviewDrop picks it up on the next push and builds it into a container behind a TLS-terminated subdomain.

Dockerfile
FROM node:22-slim WORKDIR /app COPY package*.json ./ RUN npm ci --omit=dev COPY . . # If you have a build step (TypeScript / bundler), run it here: # RUN npm run build -> then CMD ["node", "dist/server.js"] EXPOSE 3000 CMD ["node", "server.js"]

Environment variables

Set these in the Variables tab of your PreviewDrop project. They're encrypted at rest and injected into every preview container at start.

VariableExample valueNote
PORT3000PreviewDrop injects this. Read it with process.env.PORT and listen on it.
NODE_ENVproductionEnables Express production optimisations and disables verbose error pages.
DATABASE_URLpostgres://user:pass@host:5432/dbPoint at a shared dev DB, or omit for stateless previews.

Common gotchas

Listen on 0.0.0.0 and read process.env.PORT

Use app.listen(process.env.PORT || 3000, '0.0.0.0'). Omitting the host can bind to localhost inside the container, which the proxy can’t reach — the preview will 502.

Commit your lockfile

npm ci requires a committed package-lock.json and fails without one. If you don’t keep a lockfile, switch the build line to npm install --omit=dev. (pnpm / yarn work too — use their install + lockfile.)

Let the image build node_modules

Add a .dockerignore with node_modules so your host’s modules aren’t copied in. Native modules (bcrypt, sharp, better-sqlite3) compile per-platform — a macOS/Windows node_modules will crash inside the Linux container.

Run your build step in the image

If you ship TypeScript or a bundler, add RUN npm run build and point the CMD at the compiled output (node dist/server.js). Don’t rely on ts-node in previews — it’s slower and pulls dev deps you excluded with --omit=dev.

Why not Vercel or Netlify?

Vercel runs Express by wrapping the whole app in a serverless function: every request cold-boots the app, websockets and long-lived SSE connections break, and you can’t hold an in-memory cache or a persistent database pool between requests. PreviewDrop runs node server.js as a genuine always-on process — the same way it runs in production.

Preview your Express app in 5 minutes

Connect a repo, push a branch, get a URL. No credit card, no trial clock.

Start free