CI/CD with GitHub Actions for Next.js and NestJS
A practical pipeline: lint, test, build, preview, and controlled deploy without hour-long queues or leaked secrets.
Ali Mortazavi
Founder, Paradise Code
CI should deliver fast signal, not complex theater
Every minute of PR feedback delay creates human shortcuts. Layer the pipeline: cheap checks first (format/lint/typecheck), then unit tests, then build, and smoke E2E in a separate or conditional path. If everything is serial and heavy, the team mutes Actions.
In a monorepo, build/test only changed packages. Path filters and dependency caching cut real cost.
Caching and determinism
Restore package-manager caches with lockfile keys. Lighten Next builds with framework-appropriate build caches, but never depend on a dirty cache—you need a clean rebuild path.
Pin Node in `.nvmrc`/Volta so “works on my machine” does not recur. Use the same version in Actions and production.
Secrets, environments, and permissions
Keep secrets in GitHub Environments with approval for production. Grant workflows least privilege (`contents: read`, `id-token` only when OIDC is required). Avoid printing env values in logs.
For Nest and Next, split variables by environment: preview must never point at the production database—even read-only.
Previews and progressive delivery
Frontend preview deploys make product review real. For APIs, a staging environment with controlled migrations beats deploying straight from main. Design migrations in the pipeline with locking and a rollback mindset—not as an afterthought.
Tie production deploys to a tag or approval. Practice rollback; an unrunbooked document does not exist.
Merge-gate quality
Branch protection: green checks, code review, and preview status when needed. Limit and audit emergency exceptions. “Skip CI” must not become habit.
For Next apps, bundle budgets or Lighthouse CI on key routes can sit in the same gate—if they stay stable.
Observability of the pipeline itself
Monitor job durations and attack bottlenecks monthly. Failure notifications should hit the team channel with artifact links. A rotting pipeline kills trust like rotting tests do.
End goal: from push to releasable confidence in minutes, with a safe path to production—not raw speed without brakes.
Frequently asked questions
Should we run a browser matrix on every PR?
Usually no. One browser for PR smoke is enough; put the matrix on nightly or pre-release runs.
Run DB migrations in CI or in the app boot?
In a controlled deploy step with backups and locking—not on random multi-instance startup.
Do we need self-hosted runners?
When cost, private network, or special hardware requires it. Otherwise managed runners are simpler and safer to start.
Insights
Need these ideas implemented in your product?
Paradise Code supports you from consult to full delivery.