
CI/CD pipelines for web applications: a practical guide
How to set up a CI/CD pipeline for a web application: build, tests, preview environments, deployment and rollback. With tool choices and common pitfalls.
In short: A CI/CD pipeline checks every code change automatically and ships it to production with one click or fully automatically. A typical web application needs only a few stages: install dependencies, lint and type-check, run tests, build, deploy to a preview environment and then to production. With GitHub Actions or GitLab CI such a pipeline can be set up in a day. The real work is keeping it fast and reliable.
What CI and CD actually mean
Continuous integration (CI) means every change is merged into the main branch early and built and tested automatically along the way. Bugs show up while they are still small. Continuous delivery means every passing build can be released at any time. Continuous deployment goes one step further and releases it without manual approval.
For most teams, continuous delivery with a deliberate click for production is a sensible middle ground. Teams with good test coverage and monitoring can move to fully automatic deployment later.
The stages of a practical pipeline
Checks: linting, types, formatting
The first stage is the fastest and catches most trivial mistakes. ESLint, Prettier and, for TypeScript projects, tsc --noEmit run in seconds to a few minutes. They should run on every pull request and block the merge when they fail.
Tests
Unit tests check individual functions, integration tests check how code works with the database and API, and end-to-end tests with Playwright or Cypress walk through the user interface. E2E tests are slow and more fragile, so a small set covering critical flows like login and checkout is usually enough. Our post on testing strategies for React applications covers how to balance them.
Build and artifact
Build once, then promote the same artifact unchanged through every environment, for example as a Docker image with a unique tag. If you build separately for staging and production, you are not strictly testing what goes live. Environment-specific values belong in environment variables, not in the build.
Preview environments
A short-lived environment with its own URL for every pull request makes reviews much easier for developers and business stakeholders alike. Platforms like Vercel or Netlify offer this out of the box. On your own infrastructure you can rebuild it with containers and some automation.
Deployment and rollback
Production deployments should be reproducible and reversible. Blue-green or rolling deployments avoid downtime, and rolling back to the previous image must take a single command. Database migrations are the tricky part. Our article on zero-downtime database migrations explains how to handle them.
Which tools to use
If your code lives on GitHub, GitHub Actions is usually the obvious choice. GitLab CI is just as capable and can be fully self-hosted, which matters to companies with strict data protection requirements. The infrastructure you deploy to is best managed as code too, for example with Terraform. Our post on infrastructure as code with Terraform shows what that looks like.
In monorepos with several packages, tools like Turborepo or Nx help you rebuild and retest only what actually changed.
Common pitfalls
Slow pipelines are the main reason teams start working around them. Cache dependencies and build outputs, run independent jobs in parallel and keep feedback on a pull request as short as you can.
Flaky tests that pass one run and fail the next destroy trust in the pipeline. Fix or remove them instead of hitting re-run. Credentials belong in the CI system's secret store, never in the repository, and each job should get only the permissions it needs.
Finally, the work does not end at deployment. Without monitoring and alerts, you find out about a broken release when customers call.
Frequently asked questions (FAQ)
Is CI/CD worth it for small projects?
Yes. Even a simple pipeline with linting, tests and automatic deployment prevents many of the mistakes that happen with manual uploads. The setup effort for a small project is low and pays back quickly.
GitHub Actions or GitLab CI?
That mostly depends on where your code lives. Both cover what a typical web application needs. GitLab can be run entirely on your own servers, which can matter if you have strict requirements about data location.
How long should a pipeline take?
As short as possible. If developers wait a long time for feedback on every pull request, they switch to other work and lose context. Caching, parallel jobs and a lean set of E2E tests help most.
Should every change go live automatically?
Not necessarily. Many teams do well with automatic deployment to staging and a deliberate approval for production. Fully automatic deployment requires good test coverage, monitoring and a fast rollback.
Conclusion
A good CI/CD pipeline is a handful of small, dependable stages that every change has to pass. What matters most is that the team trusts it: it has to be fast, give consistent results and make rollback easy when something goes wrong. If you want to build that kind of foundation for your web application, we can help as part of our web development services.
Related posts
- Building a SaaS Product: Architecture Decisions You Can't Undo
Multi-tenancy, data model, authentication and hosting: the SaaS architecture choices that are hard to reverse, and how to make them well from the start.
- Microservices vs. monolith: what's right for your SaaS
Microservices or monolith for your SaaS product? Why a modular monolith is usually the better start, and the signals that tell you it is time to split.
- Serverless Architecture: When It Makes Sense and When It Doesn't
When serverless with AWS Lambda and similar saves cost and effort, where cold starts, time limits and lock-in cause trouble, and what the alternatives are.
- Database selection: PostgreSQL, MongoDB or something else?
PostgreSQL, MongoDB, MySQL, Redis or SQLite: which database fits your web application? A practical comparison with clear criteria for the decision.