Architectural Design Patterns
High-level structural patterns: MVC, MVVM, Microservices, Event-Driven, Layered, Hexagonal (Ports & Adapters), CQRS, Serverless, Service Mesh.
High-level structural patterns: MVC, MVVM, Microservices, Event-Driven, Layered, Hexagonal (Ports & Adapters), CQRS, Serverless, Service Mesh.
| Name | Category | Description | Key principles | Benefits | Tradeoffs | Typical components | When to use | Tech examples |
|---|---|---|---|---|---|---|---|---|
| MVC (Model-View-Controller) | Component-Based | Separates application into three components: Model (data/business logic), View (UI presentation), Controller (input handling/orchestration). Promotes separation of concerns. |
| Modular code structure, testability (test model/controller without UI), parallel development (frontend/backend), reusable models and views. | Controller can become God object (too much logic), tight coupling between Controller and View in some implementations, complexity for simple UIs, many files for small features. |
| Applications with rich UI requiring separation, web frameworks (Rails, Django, Spring MVC), desktop apps, team-based development where roles are split. |
|
| MVVM (Model-View-ViewModel) | Component-Based | Evolution of MVC for data-binding UIs. View observes ViewModel via data binding; ViewModel exposes data/commands for View, no direct View reference. Model unchanged. |
| Excellent testability (ViewModel unit tests), designer-developer collaboration (designers work on XAML, devs on ViewModel), clean separation, reactive programming friendly. | Data binding can be opaque (hard to debug), memory leaks from event handlers, overkill for simple UIs, learning curve for binding syntax. |
| Applications with rich data binding (WPF, UWP, Xamarin, SwiftUI, Jetpack Compose), reactive UIs, teams with designer/developer split. |
|
| Microservices Architecture | Distributed Systems | Application as collection of small, independent services. Each service owns its data, runs in its own process, communicates via HTTP/gRPC/messaging. Independently deployable. |
| Independent scaling per service, team autonomy, tech stack flexibility, fault isolation (one service failure doesn't crash all), easier to understand codebase per service. | Complex distributed system (network latency, partial failures), debugging/tracing harder, data consistency challenges (eventual consistency), operational overhead (monitoring, logging, deployment), testing integration complex. |
| Large applications with multiple teams, need independent scaling, varied domains, long-lived complex systems, high availability requirements. |
|
| Event-Driven Architecture | Distributed Systems | Components communicate via events (state changes). Producers publish events; Consumers subscribe and react. Loose coupling, asynchronous, highly scalable. |
| Loose coupling, scalability (can add consumers), resilience (message queues buffer failures), extensibility (new consumers without changing producers), real-time reaction. | Complexity of messaging infrastructure, debugging/observability harder (distributed traces), eventual consistency, event ordering challenges, message duplication. |
| Real-time systems, data pipelines, IoT, distributed systems with loose coupling needed, systems needing audit trail (event sourcing), decoupling services. |
|
| Layered Architecture (N-Tier) | Structural | Organizes system into horizontal layers (presentation, business logic, data access). Each layer depends only on layer directly below it. Classic enterprise architecture. |
| Simple to understand, separation of concerns clear, testable layers, technology swapping per layer possible, widely understood. | Can become monolithic blob (all code in one deployable), single layer failure affects all, network overhead if tiers distributed, layer boundaries may blur over time. |
| Traditional enterprise applications, CRUD-heavy apps, simple monoliths that may later split, teams familiar with layered approach. |
|
| Hexagonal Architecture (Ports & Adapters) | Structural | Application core (business logic) is isolated from external concerns (UI, DB, external APIs) via ports (interfaces) and adapters (implementations). Also called Clean Architecture or Onion Architecture. |
| Testable core without infrastructure, technology-agnostic business logic, easy to swap adapters (e.g., MySQL → PostgreSQL), framework independence, clear boundaries. | More boilerplate/interfaces, may feel over-engineered for simple CRUD apps, learning curve, many small files. |
| Long-lived business applications, complex domain logic, need test isolation from infrastructure, framework-agnostic core desired. |
|
| CQRS (Command Query Responsibility Segregation) | Structural | Separate read (query) and write (command) operations. Commands modify state (write model); Queries read state (read model). May use separate databases/schemas. |
| Optimized models for each purpose (writes enforce rules, reads optimized for queries), scalability (read replicas), audit trail from commands, clear separation of concerns. | Complexity (two models to maintain), eventual consistency (not immediately consistent), increased infrastructure, may not be necessary for simple CRUD. |
| High-read vs write asymmetry, complex domain with business rules, need audit log of all changes, scalability demands separate read/write scaling. |
|
| Serverless Architecture | Cloud-Native | Applications built using managed services and Functions-as-a-Service (FaaS). No server management; cloud provider handles scaling, availability, infrastructure. |
| No server management, automatic scaling, cost-effective for spiky workloads, faster time-to-market, built-in high availability. | Vendor lock-in (proprietary services), cold start latency, debugging/monitoring harder, execution time limits (max duration), local testing difficult, distributed transactions complex. |
| Spiky/irregular workloads, APIs and webhooks, event processing (file upload, DB changes), IoT backends, rapid prototypes, microservices on FaaS. |
|
| Service Mesh | Infrastructure | Dedicated infrastructure layer for service-to-service communication. Handles load balancing, retries, circuit breaking, observability, security (mTLS) transparently via sidecar proxies. |
| Consistent cross-cutting concerns (no code per service), security (mTLS auto), observability (unified telemetry), traffic management (A/B testing, canary), resilience (retries, circuit breakers). | Added complexity (deployment, ops), resource overhead (sidecars), learning curve, may be overkill for small deployments, latency added by proxy. |
| Large microservices deployments (50+ services), need uniform security/observability, complex traffic routing, service-level policies enforced consistently. |
|
The static files are identical to what the API returns, but with no rate limit and no server round trip. Use the API when you want a query and a content type; use the files when you want to cache one document.
curl "https://yjtoon.com/api/dataset/architectural-design-patterns?format=toon"
const res = await fetch( "https://yjtoon.com/static-data/dataset/architectural-design-patterns.toon" ); const toon = await res.text();
Rate limit: 120 requests per minute per IP, no key and no signup. API reference →