Starting a new project
Once in a blue moon you will not maintain a project - bumping versions in package.json and testing every corner of the app - but build something brand new. Here's some pointers to get you going.
Starting fresh
Starting fresh gives you many options on how to chose your stack, but the amount of options can be overwhelming. Here's some pointers and advice navigating the landscape. Going modern, within reason, is the general rule of thumb.
Structure: Monorepo
It is rarely a mistake to put multiple tightly coupled apps into a monorepo, instead of spreading it across multiple repos. We have a dedicated guide on Monorepos.
Engine: bun
Bun is a modern JavaScript runtime that replaces several legacy Node.js tools at once. It’s fast, compact, and ships with a built‑in test runner, bundler, and package manager. Node compatibility is extremely strong.
Build Tool: Vite
Vite offers a fast, modern development environment with instant HMR and simple configuration. It has become the default choice for React, Vue, and other frameworks thanks to its speed and developer experience.
Linting & Formatting
Biome on its own - or the pairing of Oxlint and Oxfmt - these Rust‑based tools provide a faster, simpler alternative to the traditional ESLint + Prettier setup. They reduce configuration overhead and dramatically speed up linting and formatting. Not to mention they're a built for modern web development, not for how it was ages ago.
Data Fetching / Server State
TanStack Query is the go‑to solution for managing server state. It handles caching, background updates, retries, and synchronization automatically, letting you remove a lot of boilerplate and avoid misusing global state for API data.
Client State
Zustand keeps UI‑only state lightweight and predictable. It avoids the complexity of large global stores and pairs naturally with TanStack Query, which handles all server‑derived data.
Project Structure
Bulletproof React is a set of rules on how to structure an app. This architecture gives you a scalable, feature‑oriented folder structure. It encourages clear boundaries, reusable patterns, and maintainable conventions as the codebase grows.
Guiding Principles
Keep the architecture grounded in proven engineering ideas:
-
KISS — avoid unnecessary abstractions
-
YAGNI — don’t build what you don’t need yet
-
DRY — reduce duplication without over‑engineering
-
Single Responsibility — keep modules focused
-
Type Safety — lean on TypeScript
-
Pragmatic Performance — optimize only when it matters
Last but not least
And do follow our 27 principles for building great web apps. Good luck!