Deployments - Prod / Stage / Storybook
Frontend monorepo with focus on best practices and painless developer experience:
- Monorepo setup that can be easily extended 🔧
- Spin it up with single command 🌀
- TypeScript 100% codebase
- Blazing fast builds, lints, tests with Turborepo remote caching ⚡
Easily set up a local development environment
npm install
npm run build
npm run dev
- Start all apps 🚀
Visit one of the monorepo apps localhost:3100
- Turborepo v1 remote cache build system, with blazingly fast execution of commands (build, lint, test etc.) on your local machine and CI
- TypeScript v5 codebase with typescript-eslint
strict-type-checked
andstylistic-type-checked
configurations enabled. - Next.js v13 apps
- Monorepo implements 3 styling solutions with shared theme across all apps (pick your use case and remove others).
Easily import UI components package into apps:- Vanilla CSS package
- Tailwind components library built with Tailwind v3
- Material UI components library built with MUI v5
- Unit and integration tests with Jest and React Testing Library. Run a single test in any monorepo app/package instantly.
- Linting with ESLint
- Prettier code formatter
- Git hooks with Husky and lint-staged
- Commit messages must meet conventional commits format.
After staging changes just runnpm run commit
and get instant feedback on your commit message formatting and be prompted for required fields by Commitizen
Bellow commands will be executed on monorepo level - on all apps and packages where npm script exists.
Command | Description |
---|---|
prepare | Setup git hooks with Husky (executes on npm install) |
build | Build all apps and packages (output build-next-static , dist ) |
dev | Start all apps |
lint | Lint all apps and packages |
lint-staged-husky | Run prettier and lint on staged files |
tsc | Run TypeScript compiler |
test | Run tests on all apps and packages |
storybook | Start storybooks on all apps and packages |
storybook-build | Build all storybooks (output build-storybook-static ) |
format-lint | Lint formatting with Prettier |
format-fix | Fix formatting with Prettier |
clean | Remove installed, generated and cached folders |
remove-turbo-cache | Removes Turborepo local cache |
update-dependencies | Update dependencies to their latest versions |
Convention over configuration should be followed as much as possible as described in TypeScript Style Guide.
TLDR:
- Code is organized and grouped by feature. Collocate code as close as possible to where it's relevant. ⭣
- Strive for data immutability. ⭣
- Strive for functions to be pure, stateless and have single responsibility. ⭣
- Strive for functions to implement majority of arguments/props as required (use optional sparingly). ⭣
- Embrace const assertions. ⭣
- Strong emphasis to keep naming conventions consistent and readable. ⭣
- Use of server-state library is encouraged (react-query, apollo client...). ⭣
- Use of client-state library for global state is discouraged. ⭣
- Use named exports. ⭣
- Prop drilling should not become an issue. ⭣
- Test business logic, not implementation details. ⭣
Monorepo features and conventions:
- Monorepo is opinionated in order to achieve best developer experience. It's meant to be used as frontend only monorepo, 100% TypeScript, consistent codebase across whole monorepo with automated tooling in place as ESLint, Prettier, TypeScript, conventional commits etc.
- Workspaces:
- It comes with two workspaces
apps
andpackages
. - All configurations (eslint, jest, tailwind etc.) in
packages
are always prefixed with "config-" and imported into other workspaces directly from source without building (never transpiled). - All other
packages
beside configurations are always being built/transpiled todist/
folder.
- It comes with two workspaces
- Merging to
main
branch deploys tostage
environment, creating new GitHub release deploys toproduction
. - For consistency all applications in monorepo are built with Next.js, but can be easily replaced with any other React framework/tooling (Vite, Remix etc.)
- Monorepo doesn't implement any high-level architectures (islands, micro-frontends), but is prepared with that in mind, so it can be easily extended (page composition, adding shared state etc.)