Architecture Comparison: Reservation System
4 architectures. 4 phases of growing complexity. Same domain.
The Experiment
This is a practical laboratory exploring how different architectural approaches respond to increasing domain complexity. The same business logic is implemented in four distinct ways, each tackling the same problem with different design philosophies.
How does your architecture behave when the domain becomes complex?
A01 — Monolithic Eloquent
Active Record / Monolithic
Philosophy: Direct ORM usage, logic in models and controllers.
Strength: Fastest to start, minimal boilerplate.
A02 — Repository Pattern
Service + Repository
Philosophy: Separation of concerns with service layer.
Strength: Better testability through dependency injection.
A03 — Strategy Polymorphism
Strategy Pattern + Polymorphism
Philosophy: Encapsulate behaviors through object polymorphism.
Strength: More expressive domain model.
A04 — Decorator Domain
Builder + Decorator Pattern
Philosophy: Compose behaviors dynamically without modification.
Strength: Scales horizontally with new rules.
Domain & Endpoints
Hotel Reservation System with progressive business rule complexity across 4 phases.
Shared Endpoints
| Method | Endpoint | Description |
|---|---|---|
| POST | /api/{arch}/v{phase}/reservation | Create reservation |
| GET | /api/{arch}/v{phase}/reservation/{id} | Get reservation |
URL Prefixes by Architecture
| URL Prefix | Architecture |
|---|---|
| /api/arch_01/ | Monolithic Eloquent |
| /api/arch_02/ | Repository Pattern |
| /api/arch_03/ | Strategy + Polymorphism |
| /api/arch_04/ | Decorator Domain |
Evolution Phases
Domain complexity increases progressively across 4 phases
Phase 01: Base Calculation
Price per night, per_night/per_stay extras
Phase 02: Conditional Rules
Volume discounts (7/14 nights), combined promo, minimum price, spa validation
Phase 03: Polymorphic Behavior
Hotel/event taxes, commissions, 3-night event restriction
Phase 04: Combinable Rules
Early booking (30/60 days), seasonal surcharge (high/low season)
Architecture Trade-off Map
Where does each architecture live in the simplicity vs fragility space? The ideal is bottom-left (simple AND robust), but reality forces trade-offs.
Where does each architecture live in the simplicity vs fragility space? The ideal is bottom-left (simple AND robust), but reality forces trade-offs.
🏆 Final Rankings
| Criterion | 🥇 Gold | 🥈 Silver | 🥉 Bronze | ❌ Worst |
|---|---|---|---|---|
| Simplicity | A01 (6 files) | A02 (10) | A03 (14) | A04 (22) |
| Thin Controller | A02/A03/A04 (30-32) | — | — | A01 (184) |
| Thin Service | A04 (99+152) | A03 (123) | A02 (172) | A01 (184) |
| Testability | A04 (pure domain) | A03 (strategy) | A02 (service) | A01 (needs DB) |
| Extensibility | A04 (new Decorator) | A03 (new Strategy) | A02 (modify service) | A01 (modify controller) |
| Fragility | A04 (low) | A03 (medium) | A02 (medium-high) | A01 (high) |
⚡ When to Use Each
Architecture selection based on your domain characteristics
Stable domain, no changing rules
→ A01 or A02
Product types with different formulas
→ A03
Pricing rules that change frequently
→ A04
💡 Key Conclusions
A01: Simplicity has exponential cost
Controller grew from 83 to 184 lines in a single method handling 13 responsibilities. Early booking discount amount is parsed from the discount_reason string (str_starts_with + explode) — a fragile hack.
A02: God Service problem
Controller stays at 30 lines but all complexity moved to a 172-line 'God Service'. Repository Pattern decouples infrastructure but doesn't reduce algorithmic complexity.
A03: Strategy duplication
Phase04PricingStrategy duplicates all logic from BasicPricingStrategy just to add 3 methods. Good balance but needs refactoring to avoid strategy duplication per phase.
A04: Horizontal scalability
Highest initial cost (22 files, 1139 lines) but scales horizontally: each new rule is a new Decorator file, not modified code. Builder + Decorator means Phase 05 barely touches existing code.