Skip to main content

Microservices

Microservices architecture best practices

17
Best Practices
7
Stacks
4
FAQs

Best Practices

CNCF Cloud-Native Definition & Principles

The CNCF’s formal definition of cloud-native computing and core principles for micro-services, containers, and dynamic orchestration.

by Cloud Native Computing Foundation

Production-Ready Micro-services Checklist

A checklist covering operability, reliability, deployability, and observability of micro-services.

by Susan Fowler

Contract-Driven Development with Pact

Consumer-driven contract testing methodology to ensure micro-service compatibility.

by Pact Foundation

Distributed Tracing Best Practices

Techniques for instrumenting and propagating trace context across services so requests can be followed end-to-end, with sampling and span design that aid debugging.

by OpenTelemetry (CNCF)

CQRS (Command Query Responsibility Segregation)

An architecture pattern that separates the model that writes data (commands) from the model that reads it (queries), allowing each side to scale and evolve independently.

by Martin Fowler

Event Sourcing

An architecture pattern that stores every change to application state as an immutable sequence of events, making the event log the source of truth instead of current state.

by Martin Fowler

Saga Pattern

A pattern for managing data consistency across microservices using a sequence of local transactions coordinated by events or a central orchestrator, with compensating actions on failure.

by Microsoft

Circuit Breaker Pattern

A resilience pattern that stops calls to a failing dependency once errors cross a threshold, preventing cascading failures and giving the dependency time to recover.

by Martin Fowler

Bulkhead Pattern

A resilience pattern that isolates resources into separate pools so a failure or overload in one part of a system cannot consume the resources others depend on.

by Microsoft

Backends for Frontends (BFF)

An architecture pattern that gives each frontend client its own tailored backend service, instead of forcing web, mobile, and other clients to share one general-purpose API.

by Sam Newman

API Gateway Pattern

An architecture pattern that places a single entry point in front of backend services to handle routing, authentication, rate limiting, and other cross-cutting concerns.

by Microsoft

Service Mesh Best Practices

Guidance for using a service mesh to manage service-to-service traffic, security, and observability through sidecar proxies, keeping that logic out of application code.

by Cloud Native Computing Foundation

Sidecar Pattern

A design pattern that deploys a helper component alongside the main application in the same unit, adding capabilities like proxying, logging, or config without changing the app.

by Microsoft

Domain-Driven Design (DDD)

A software design approach that models complex business domains in code, using a shared language and bounded contexts to align software structure with the business it serves.

by Eric Evans

Modular Monolith

An architecture that keeps a single deployable application but enforces strong internal module boundaries, capturing many microservices benefits without distributed-system complexity.

by ThoughtWorks

gRPC Best Practices

Guidance for building high-performance gRPC services with Protocol Buffers: service design, streaming, deadlines, error codes, and backward-compatible schema evolution.

by Cloud Native Computing Foundation

Micro-Frontends

An architecture that splits a web app into independently developed and deployed frontend pieces owned by separate teams, then composes them into one experience.

by Cam Jackson / Thoughtworks

Patterns

API Gateway

A single entry point that routes, aggregates, and secures client requests across many backend microservices.

Service Registry

A database of available service instances and their network locations, kept current as instances start, stop, and fail.

Service Discovery

A mechanism for clients to find the current network location of a service without hard-coding addresses.

API Composition

Implements a query that spans multiple services by invoking each owner service and joining the results in memory.

CQRS (Command Query Responsibility Segregation)

Separates the model that writes data (commands) from the model that reads it (queries) so each can be optimized independently.

Aggregator

A component that invokes multiple services and combines their responses into a single consolidated result for the caller.

Choreography

Coordinates a distributed workflow through services reacting to each other's events, with no central controller.

Orchestration

Coordinates a distributed workflow through a central orchestrator that explicitly invokes each service in sequence.

Message Router

Consumes a message and redirects it to a different channel based on conditions, decoupling producers from the decision of where messages should go.

Content-Based Router

Routes each message to a destination channel chosen by inspecting the message's content, so the payload itself determines where it is delivered.

Routing Slip

Attaches a sequence of processing steps to a message so it routes itself through a series of components determined per message at runtime.

Process Manager

A central component that maintains the state of a multi-step message flow and decides the next step, coordinating complex or branching workflows.

Retry with Backoff

Automatically re-attempts a failed operation after progressively longer waits, smoothing over transient faults without overwhelming a struggling dependency.

Exponential Backoff with Jitter

Adds randomness to exponentially growing retry delays so that many clients do not retry in lockstep and overwhelm a recovering service.

Timeout

Bounds how long a caller waits for an operation, freeing resources and surfacing failures fast instead of blocking indefinitely on a slow or hung dependency.

Bulkhead

Isolates resources into independent pools so a failure or overload in one part of a system cannot consume capacity needed by the rest.

Fallback

Provides an alternative response or behavior when a primary operation fails, keeping the system useful instead of returning an error to the user.

Fail Fast

Detects invalid state or unavailable dependencies as early as possible and reports the error immediately, rather than continuing into deeper, costlier failure.

Backpressure

Lets a slow consumer signal upstream producers to slow down, preventing unbounded queues and memory exhaustion when demand exceeds processing capacity.

Tutorials

How to install Istio and enable mTLS for service-to-service traffic

Deploy Istio, enable automatic sidecar injection, and turn on strict mutual TLS between services.

How to add a lightweight service mesh with Linkerd

Install Linkerd, mesh a workload, and gain automatic mTLS plus golden-metrics observability with low overhead.

Checklists

Monolith Decomposition Readiness Checklist

Verify a monolithic application is understood, instrumented, and bounded well enough to begin safe decomposition into services.

Microservice Production-Readiness Checklist

Confirm a new or extracted microservice meets operational, security, and resilience bars before it serves production traffic.

Service Extraction Cutover Checklist

Cutover checks for routing live traffic from a monolith to a newly extracted service without downtime or data loss.

Event-Driven Architecture Readiness Checklist

Confirm readiness to adopt event-driven communication between services, covering schemas, delivery semantics, and observability.

Database-Per-Service Decoupling Checklist

Separate a shared database into per-service ownership so microservices can deploy and scale independently without hidden coupling.

gRPC Rollout Checklist

Pre-flight items for rolling out gRPC services across a system, covering contracts, compatibility, security, and observability.

Microservices API Contract Testing Checklist

Verification items for establishing consumer-driven contract testing across microservices to prevent integration breakage.

Technology Stacks

Go + gRPC Stack

Compiled Go backend stack using gRPC and Protocol Buffers with PostgreSQL for fast, strongly-typed inter-service communication.

Micronaut JVM Microservices Stack

JVM microservices stack using Micronaut with ahead-of-time compilation and PostgreSQL for low-memory, fast-starting services and serverless functions.

Event-Driven Microservices Stack

Asynchronous microservices architecture using Kafka as an event backbone with independently deployable services for loose coupling and scalability.

gRPC Service Mesh Stack

Microservices stack combining gRPC inter-service communication with a service mesh on Kubernetes for typed, observable, secure service-to-service traffic.

Dapr Distributed Application Stack

Polyglot microservices stack using Dapr building blocks for service invocation, state, pub/sub, and bindings, abstracted from underlying infrastructure.

Vert.x Reactive Stack

A polyglot, event-driven toolkit on the JVM built around a non-blocking event loop and the reactor pattern for high-concurrency, low-latency services.

Spring WebFlux Reactive

Spring's reactive, non-blocking web stack built on Project Reactor and Netty, for high-concurrency services that need backpressure and efficient resource use.

FAQs

What is a service mesh?

A service mesh is an infrastructure layer that manages communication between microservices, handling traffic routing, load balancing, retries, encryption, and observability without changing application code. It typically works by injecting a lightweight proxy (a sidecar) alongside each service that intercepts all network traffic. Popular implementations include Istio, Linkerd, and Consul. A service mesh is most valuable in large microservice deployments where consistent security, reliability, and telemetry are needed across many services.

What is a sidecar container?

A sidecar is a secondary container that runs alongside the main application container in the same pod to extend or support it without changing the application itself. Common uses include log shipping, metrics collection, configuration syncing, and acting as a service-mesh proxy. Because containers in a pod share the network and can share storage, the sidecar can transparently intercept traffic or read and write the same files. The sidecar pattern keeps cross-cutting concerns separate from business logic and reusable across services.

What is a microservice?

A microservice is a small, independently deployable service that owns a single business capability and communicates with other services over the network, typically via HTTP/REST, gRPC, or messaging. Each microservice has its own codebase and usually its own data store, allowing teams to develop, deploy, and scale it without coordinating with the rest of the system. The trade-off for this independence is added operational complexity: distributed transactions, network failures, and observability across many services all become harder.

What is event-driven architecture?

Event-driven architecture is a style where components communicate by producing and reacting to events—records that something happened—rather than calling each other directly. Producers publish events to a broker or stream such as Kafka or a message queue, and consumers subscribe and act independently and asynchronously. This decouples services, improves scalability, and lets new consumers be added without changing producers. The trade-offs are eventual consistency, harder debugging, and the need to handle duplicate or out-of-order events.

Vibgrate CLI

See a real scan run

A replay of the actual CLI running against our test repositories — live progress, real findings, a genuine DriftScore. Nothing executes in your browser.

Replay
demo@vibgrate — bash
npx @vibgrate/cli scan
 
╭──────────────────────────────────────────╮
Vibgrate Drift Report
╰──────────────────────────────────────────╯
 
── node-turborepo (node) .
Runtime: >=18.0.0 (6 majors behind)
Frameworks:
Turbo: 1.13.4 → 2.10.8 (1 behind)
TypeScript: 5.9.3 → 7.0.2 (2 behind)
Dependencies:
1 current 1 1-behind 3 2+ behind 1 unknown
 
── @repo/admin (node) apps/admin
Frameworks:
TanStack Query: 5.101.4 → 5.101.4 (current)
React: 18.3.1 → 19.2.8 (1 behind)
React DOM: 18.3.1 → 19.2.8 (1 behind)
TypeScript: 5.9.3 → 7.0.2 (2 behind)
Vite: 5.4.21 → 8.2.1 (3 behind)
Dependencies:
3 current 9 1-behind 3 2+ behind 4 unknown
 
── @repo/api (node) apps/api
Frameworks:
Express: 4.22.2 → 5.2.1 (1 behind)
TypeScript: 5.9.3 → 7.0.2 (2 behind)
Vitest: 1.6.1 → 4.1.10 (3 behind)
Dependencies:
7 current 5 1-behind 3 2+ behind 4 unknown
 
── @repo/web (node) apps/web
Frameworks:
Next.js: 14.2.35 → 16.3.0 (2 behind)
React: 18.3.1 → 19.2.8 (1 behind)
React DOM: 18.3.1 → 19.2.8 (1 behind)
TypeScript: 5.9.3 → 7.0.2 (2 behind)
Dependencies:
2 current 6 1-behind 3 2+ behind 5 unknown
 
── @repo/config (node) packages/config
Frameworks:
TypeScript: 5.9.3 → 7.0.2 (2 behind)
Dependencies:
2 current 2 1-behind 5 2+ behind 0 unknown
 
── @repo/database (node) packages/database
Frameworks:
Prisma: 5.22.0 → 7.9.1 (2 behind)
TypeScript: 5.9.3 → 7.0.2 (2 behind)
Dependencies:
1 current 0 1-behind 3 2+ behind 1 unknown
 
── @repo/types (node) packages/types
Frameworks:
TypeScript: 5.9.3 → 7.0.2 (2 behind)
Dependencies:
0 current 0 1-behind 1 2+ behind 1 unknown
 
── @repo/ui (node) packages/ui
Frameworks:
React: 18.3.1 → 19.2.8 (1 behind)
TypeScript: 5.9.3 → 7.0.2 (2 behind)
React: 18.3.1 → 19.2.8 (1 behind)
Dependencies:
1 current 4 1-behind 1 2+ behind 1 unknown
 
── @repo/utils (node) packages/utils
Frameworks:
TypeScript: 5.9.3 → 7.0.2 (2 behind)
Vitest: 1.6.1 → 4.1.10 (3 behind)
Dependencies:
0 current 1 1-behind 2 2+ behind 1 unknown
 
Tech Stack
Frontend: React, React DOM
Meta-frameworks: Next.js
Bundlers: tsx, Turbo, Vite
CSS / UI: Autoprefixer, PostCSS, Tailwind CSS
Backend: Express
ORM / Database: Prisma, Prisma Client
Testing: Vitest
Lint & Format: ESLint, ESLint Prettier, ESLint React, Prettier, typescript-eslint
 
Services & Integrations
Auth: JWT 9.0.3
Databases: Prisma 5.22.0
 
TypeScript
v5.3.3 · strict ✔ · MIXED · target: ES2022
 
Build & Deploy
Package Managers: pnpm
Monorepo: npm-workspaces, pnpm-workspaces, turbo
 
Product Purpose Signals
Frameworks: react, nextjs
Evidence: 177
Top Signals:
- [heading] Dashboard (apps/admin/src/pages/Dashboard.tsx)
- [title] Revenue Overview (apps/admin/src/pages/Dashboard.tsx)
- [copy] workspace:* (packages/ui/package.json)
- [copy] ./dist (packages/ui/tsconfig.json)
- [copy] ./src/index.ts (packages/ui/package.json)
- [copy] @repo/config/tsconfig-base.json (packages/ui/tsconfig.json)
- [copy] @repo/ui (packages/ui/package.json)
- [copy] #3b82f6 (apps/admin/src/pages/Dashboard.tsx)
Unknowns:
- No pricing or billing evidence found.
- No integrations/connectors evidence found.
- No route structure evidence found.
 
Security Posture
Lockfile ✖ · .env ✔ · node_modules ✔
 
Platform
Native modules: turbo
 
Code Quality
Files: 36 · Functions: 183 · Avg complexity: 2.62 · Avg length: 21.13 lines
Max nesting: 2 · Circular deps: 0 · Dead code: 0%
God files: apps/admin/src/pages/Products (448 lines)
 
Database Schema
postgresql · 8 models · 1 enum
Models: Address, CartItem, Category, Order, OrderItem (+3 more)
 
Findings (16 errors, 11 warnings)
Node.js runtime ">=18.0.0" reached end-of-life on 2025-04-30 (latest: 24.0.0).
vibgrate/runtime-eol in .
TypeScript is 2 major versions behind (current: 5.9.3, latest: 7.0.2).
vibgrate/framework-major-lag in .
60% of dependencies are 2+ major versions behind in node-turborepo.
vibgrate/dependency-rot in .
@types/node is 6 major versions behind (spec: ^20.11.0, latest: 26.1.2).
vibgrate/dependency-major-lag in .
TypeScript is 2 major versions behind (current: 5.9.3, latest: 7.0.2).
vibgrate/framework-major-lag in apps/admin
Vite is 3 major versions behind (current: 5.4.21, latest: 8.2.1).
vibgrate/framework-major-lag in apps/admin
vite is 3 major versions behind (spec: ^5.0.12, latest: 8.2.1).
vibgrate/dependency-major-lag in apps/admin
TypeScript is 2 major versions behind (current: 5.9.3, latest: 7.0.2).
vibgrate/framework-major-lag in apps/api
Vitest is 3 major versions behind (current: 1.6.1, latest: 4.1.10).
vibgrate/framework-major-lag in apps/api
@types/node is 6 major versions behind (spec: ^20.11.0, latest: 26.1.2).
vibgrate/dependency-major-lag in apps/api
vitest is 3 major versions behind (spec: ^1.2.1, latest: 4.1.10).
vibgrate/dependency-major-lag in apps/api
Next.js is 2 major versions behind (current: 14.2.35, latest: 16.3.0).
vibgrate/framework-major-lag in apps/web
TypeScript is 2 major versions behind (current: 5.9.3, latest: 7.0.2).
vibgrate/framework-major-lag in apps/web
@types/node is 6 major versions behind (spec: ^20.11.0, latest: 26.1.2).
vibgrate/dependency-major-lag in apps/web
TypeScript is 2 major versions behind (current: 5.9.3, latest: 7.0.2).
vibgrate/framework-major-lag in packages/config
56% of dependencies are 2+ major versions behind in @repo/config.
vibgrate/dependency-rot in packages/config
eslint-plugin-react-hooks is 3 major versions behind (spec: ^4.6.0, latest: 7.1.1).
vibgrate/dependency-major-lag in packages/config
Prisma is 2 major versions behind (current: 5.22.0, latest: 7.9.1).
vibgrate/framework-major-lag in packages/database
TypeScript is 2 major versions behind (current: 5.9.3, latest: 7.0.2).
vibgrate/framework-major-lag in packages/database
75% of dependencies are 2+ major versions behind in @repo/database.
vibgrate/dependency-rot in packages/database
TypeScript is 2 major versions behind (current: 5.9.3, latest: 7.0.2).
vibgrate/framework-major-lag in packages/types
100% of dependencies are 2+ major versions behind in @repo/types.
vibgrate/dependency-rot in packages/types
TypeScript is 2 major versions behind (current: 5.9.3, latest: 7.0.2).
vibgrate/framework-major-lag in packages/ui
TypeScript is 2 major versions behind (current: 5.9.3, latest: 7.0.2).
vibgrate/framework-major-lag in packages/utils
Vitest is 3 major versions behind (current: 1.6.1, latest: 4.1.10).
vibgrate/framework-major-lag in packages/utils
67% of dependencies are 2+ major versions behind in @repo/utils.
vibgrate/dependency-rot in packages/utils
vitest is 3 major versions behind (spec: ^1.2.1, latest: 4.1.10).
vibgrate/dependency-major-lag in packages/utils
 
╭──────────────────────────────────────────╮
Top Priority Actions
╰──────────────────────────────────────────╯
 
1. Upgrade EOL runtime in node-turborepo
End-of-life runtimes no longer receive security patches and block ecosystem upgrades.
./.
>=18.0.0 → 24.0.0 (6 majors behind)
Impact: −10 drift points (runtime & EOL)
 
2. Fix security posture: no lockfile found
Without a lockfile, installs are non-deterministic. Run the install command to generate one and commit it.
./
Missing: package-lock.json, pnpm-lock.yaml, or yarn.lock
 
3. Upgrade Vite 5.4.21 → 8.2.1 in @repo/admin (+2 more)
3 major versions behind. Major framework drift increases breaking change risk and blocks access to security fixes and performance improvements.
./apps/admin
Vite: 5.4.21 → 8.2.1 (3 majors behind)
./apps/api
Vitest: 1.6.1 → 4.1.10 (3 majors behind)
./packages/utils
Vitest: 1.6.1 → 4.1.10 (3 majors behind)
Impact: −5–15 drift points
 
4. Reduce dependency rot in @repo/types (100% severely outdated)
1 of 1 dependencies are 2+ majors behind. Run `npm outdated` and prioritise packages with known CVEs or breaking API changes.
./packages/types
typescript: 5.9.3 → 7.0.2 (2 majors behind)
Impact: −5–10 drift points
 
5. Reduce dependency rot in @repo/database (75% severely outdated)
3 of 4 dependencies are 2+ majors behind. Run `npm outdated` and prioritise packages with known CVEs or breaking API changes.
./packages/database
@prisma/client: 5.22.0 → 7.9.1 (2 majors behind)
prisma: 5.22.0 → 7.9.1 (2 majors behind)
typescript: 5.9.3 → 7.0.2 (2 majors behind)
Impact: −5–10 drift points
 
╭──────────────────────────────────────────╮
Architecture Layers
╰──────────────────────────────────────────╯
 
Archetype: monorepo (80% confidence)
Files classified: 29 (6 unclassified)
 
presentation 9 files drift ████████████████████ 100 risk high
routing 4 files drift ████████████████████ 100 risk high
middleware 2 files drift ███████▍░░░░░░░░░░░░ 37 risk moderate
domain 4 files drift ████████████████████ 100 risk high
data-access 2 files drift ████████████████████ 100 risk high
infrastructure 0 files drift ░░░░░░░░░░░░░░░░░░░░ 0 risk none
config 3 files drift ░░░░░░░░░░░░░░░░░░░░ 0 risk none
shared 5 files drift ████████████████████ 100 risk high
testing 0 files drift ████████████████████ 100 risk high
 
╭──────────────────────────────────────────╮
DriftScore Summary
╰──────────────────────────────────────────╯
 
DriftScore: 66/100
Risk Level: HIGH
Projects: 9
Classified: 8 nano · 1 micro · 0 small · 0 standard
Billable: 0.42 · 9 detected → 0.42 billable projects (micro-project pricing)
0.1 micro · 0.32 nano
These fractions add up across repositories, then round down to whole billable projects.
 
Score Breakdown
Runtime: ████████████████████ 100
Frameworks: █████████▏░░░░░░░░░░ 46
Dependencies: ██████░░░░░░░░░░░░░░ 30
EOL Risk: ████████████████████ 100
 
Scanned at 2026-08-07T06:14:10.284Z · 25.2s · 286 files scanned · 56 workspace files · 27 dirs
Press Run to start.