Facade Pattern

Updated Nov 23, 2025

Facade Pattern

Intent:

Provides a simplified interface to a complex subsystem. It defines a higher-level interface that makes the subsystem easier to use.

When to Use:

When you have a complex system with many classes and interfaces, and you want to provide a simple interface for common operations. The facade hides the complexity and provides a single entry point.

Key Characteristics:

  • Provides a simple interface to a complex system
  • Hides subsystem complexity
  • Single entry point for common operations
  • Makes the system easier to use

Think of it like a restaurant - you don't need to know how the kitchen works, how orders are managed, or how payments are processed. You just place your order, and the restaurant (facade) handles everything behind the scenes.


🛒 Example: E-Commerce Checkout System

Let's say we're building an e-commerce checkout system. The checkout process involves multiple complex steps: inventory checking, payment processing, shipping calculation, order confirmation, and email notifications. We'll create a facade to simplify this for the user.

Step 1: Inventory Management Subsystem

# inventory_service.py class InventoryService: def check_availability(self, product_id, quantity): print(f"[Inventory] Checking availability for product {product_id}...") # Complex inventory checking logic print(f"[Inventory] {quantity} units available") return True def reserve_items(self, product_id, quantity): print(f"[Inventory] Reserving {quantity} units of product {product_id}") return True

Step 2: Payment Processing Subsystem

# payment_service.py class PaymentService: def validate_payment(self, card_number, amount): print(f"[Payment] Validating payment card...") # Complex payment validation print(f"[Payment] Card validated successfully") return True def process_payment(self, card_number, amount): print(f"[Payment] Processing payment of ₹{amount}...") # Complex payment processing print(f"[Payment] Payment processed successfully") return True

Step 3: Shipping Service Subsystem

# shipping_service.py class ShippingService: def calculate_shipping(self, address, items): print(f"[Shipping] Calculating shipping cost for {address}...") # Complex shipping calculation shipping_cost = 50 print(f"[Shipping] Shipping cost: ₹{shipping_cost}") return shipping_cost def schedule_delivery(self, address, items): print(f"[Shipping] Scheduling delivery to {address}...") # Complex delivery scheduling print(f"[Shipping] Delivery scheduled for tomorrow") return True

Step 4: Order Service Subsystem

# order_service.py class OrderService: def create_order(self, items, total_amount): print(f"[Order] Creating order...") # Complex order creation order_id = "ORD12345" print(f"[Order] Order created: {order_id}") return order_id def confirm_order(self, order_id): print(f"[Order] Confirming order {order_id}...") # Complex order confirmation print(f"[Order] Order confirmed") return True

Step 5: Notification Service Subsystem

# notification_service.py class NotificationService: def send_email(self, email, subject, message): print(f"[Notification] Sending email to {email}...") # Complex email sending print(f"[Notification] Email sent: {subject}") return True def send_sms(self, phone, message): print(f"[Notification] Sending SMS to {phone}...") # Complex SMS sending print(f"[Notification] SMS sent") return True

Step 6: Create Checkout Facade

# checkout_facade.py from inventory_service import InventoryService from payment_service import PaymentService from shipping_service import ShippingService from order_service import OrderService from notification_service import NotificationService class CheckoutFacade: def __init__(self): # Initialize all subsystem services self.inventory = InventoryService() self.payment = PaymentService() self.shipping = ShippingService() self.order = OrderService() self.notification = NotificationService() def checkout(self, items, card_number, address, email, phone): """Simple checkout method - handles all complex operations""" print("\n=== Starting Checkout Process ===\n") # Step 1: Check inventory for item in items: self.inventory.check_availability(item['id'], item['quantity']) self.inventory.reserve_items(item['id'], item['quantity']) # Step 2: Calculate total total = sum(item['price'] * item['quantity'] for item in items) shipping_cost = self.shipping.calculate_shipping(address, items) total_amount = total + shipping_cost print(f"\nTotal: ₹{total}") print(f"Shipping: ₹{shipping_cost}") print(f"Grand Total: ₹{total_amount}\n") # Step 3: Process payment self.payment.validate_payment(card_number, total_amount) self.payment.process_payment(card_number, total_amount) # Step 4: Create order order_id = self.order.create_order(items, total_amount) self.order.confirm_order(order_id) # Step 5: Schedule shipping self.shipping.schedule_delivery(address, items) # Step 6: Send notifications self.notification.send_email( email, "Order Confirmation", f"Your order {order_id} has been confirmed!" ) self.notification.send_sms( phone, f"Order {order_id} confirmed! Total: ₹{total_amount}" ) print("\n=== Checkout Complete ===\n") return order_id

Step 7: Use the Facade (Client Code)

# main.py from checkout_facade import CheckoutFacade # Create facade checkout = CheckoutFacade() # Customer checkout - simple one method call! items = [ {'id': 'PROD001', 'name': 'Laptop', 'quantity': 1, 'price': 50000}, {'id': 'PROD002', 'name': 'Mouse', 'quantity': 2, 'price': 500} ] order_id = checkout.checkout( items=items, card_number="1234-5678-9012-3456", address="123 Main Street, Mumbai", email="customer@example.com", phone="+91-9876543210" ) print(f"Order ID: {order_id}") print("Customer can now track their order!")

Output:

=== Starting Checkout Process ===

[Inventory] Checking availability for product PROD001...
[Inventory] 1 units available
[Inventory] Reserving 1 units of product PROD001
[Inventory] Checking availability for product PROD002...
[Inventory] 2 units available
[Inventory] Reserving 2 units of product PROD002
[Shipping] Calculating shipping cost for 123 Main Street, Mumbai...
[Shipping] Shipping cost: ₹50

Total: ₹51000
Shipping: ₹50
Grand Total: ₹51050

[Payment] Validating payment card...
[Payment] Card validated successfully
[Payment] Processing payment of ₹51050...
[Payment] Payment processed successfully
[Order] Creating order...
[Order] Order created: ORD12345
[Order] Confirming order ORD12345...
[Order] Order confirmed
[Shipping] Scheduling delivery to 123 Main Street, Mumbai...
[Shipping] Delivery scheduled for tomorrow
[Notification] Sending email to customer@example.com...
[Notification] Email sent: Order Confirmation
[Notification] Sending SMS to +91-9876543210...
[Notification] SMS sent

=== Checkout Complete ===

Order ID: ORD12345
Customer can now track their order!

✅ Benefits

1. Simplicity:

  • Provides a simple interface to complex system
  • Client code doesn't need to know about all subsystems

2. Loose Coupling:

  • Client code depends only on facade, not subsystems
  • Changes to subsystems don't affect client code

3. Easy to Use:

  • One method call instead of multiple complex operations
  • Reduces learning curve for developers

4. Centralized Control:

  • All complex operations in one place
  • Easy to modify checkout process

🎯 Key Points

  • Facade provides a simple interface to a complex subsystem
  • Hides complexity from client code
  • Single entry point for common operations
  • Client code doesn't need to know about subsystems
  • Makes the system easier to use and maintain

🌟 Quick Summary

  • Problem: Complex system with many classes makes it hard to use
  • Solution: Create a facade that provides a simple interface
  • Benefit: Easy to use complex system through simple interface
  • Example: E-commerce checkout - one method handles inventory, payment, shipping, orders, and notifications

🎉 End

The Facade Pattern helps you simplify complex systems. It's perfect when you want to provide an easy-to-use interface for a complicated subsystem!