Tale of Software Architect(ure): Part 17 (Microservice Architecture)
Saiful Islam Rasel
Senior Engineer, SDE @ bKash | Ex: AsthaIT | Sports Programmer | Problem Solver | FinTech | Microservice | Java | Spring-boot | C# | .NET | PostgreSQL | DynamoDB | JavaScript | TypeScript | React.js | Next.js | Angular
Story:
Imagine a small town bakery called "Sweet Slice", famous for its cakes, cookies, and custom pastries. Business is booming, and customers flood the bakery each day with different needs. Some come for cakes, others for fresh bread, and some for a quick coffee. At first, the bakery runs as one large unit, with every employee handling every task like taking orders, baking, handling payments, and packing. But as demand grows, this all-in-one approach causes problems:
Seeing the chaos, the bakery’s owner, Komola, decides to break up the team into smaller, specialized roles. She hires dedicated staff for Order Taking, Baking, Packing, and Payment Handling.
With each person focused on their specific tasks, Sweet Slice runs smoothly. Customers get their orders faster, mistakes are reduced, and Komola can even hire extra hands in busy seasons for any role that’s overwhelmed like adding more bakers on holidays. Plus, if someone is sick, Komola can shift responsibilities or replace just that role without disrupting the whole operation.
Microservice Architecture:
Microservice architecture is a software design approach where a large application is broken down into smaller, loosely coupled services, each responsible for a specific function. Each microservice can be developed, deployed, and maintained independently, often by different teams. This contrasts with a monolithic architecture, where all functions are tightly integrated into one large system.
Key Component / Concepts of Microservices
Practical Example: E-Commerce Platform
Imagine a large e-commerce application broken down into the following microservices:
Each service has its own responsibilities and can be scaled as needed. For instance:
Context
A large application for example an e-commerce platform needs to support millions of users, each engaging with various features such as browsing products, adding items to a cart, placing orders, making payments, and receiving notifications. The system must be highly available, scalable, and resilient to failures. Additionally, it must support rapid development and deployment, allowing for regular feature updates without impacting the entire system.
Problem
In a traditional monolithic architecture, all components like (user management, product catalog, order processing, payments, and notifications) would be tightly coupled into a single application. This setup presents several issues:
Solution
The Microservice Architecture approach addresses these issues by breaking the large application into distinct, loosely coupled services, each responsible for a specific function such as:
How This Solves the Problem:
领英推荐
Sample Pseudocode:
Here’s a pseudocode example demonstrating how an Order Service in a microservice-based e-commerce application might work, coordinating with other microservices. This example uses pseudocode to outline the order workflow, including calls to the User Service, Product Service, Payment Service, and Notification Service.
# Order Service
class OrderService:
def place_order(user_id, cart_items):
# Step 1: Verify User
user_data = UserService.get_user(user_id)
if not user_data:
return "User not found"
# Step 2: Validate Cart Items
available_products = []
for item in cart_items:
product = ProductService.check_availability(item.product_id, item.quantity)
if product is not available:
return f"Product {item.product_id} is out of stock"
available_products.append(product)
# Step 3: Reserve Products
for product in available_products:
ProductService.reserve_product(product.id, product.quantity)
# Step 4: Process Payment
payment_status = PaymentService.process_payment(user_id, calculate_total(cart_items))
if payment_status != "Success":
for product in available_products:
ProductService.release_reservation(product.id)
return "Payment failed"
# Step 5: Create Order
order = create_order(user_id, cart_items)
# Step 6: Notify User
NotificationService.send_notification(
user_id,
f"Order {order.id} placed successfully. Total amount: {calculate_total(cart_items)}"
)
return f"Order {order.id} has been successfully placed"
def calculate_total(cart_items):
total = 0
for item in cart_items:
total += item.price * item.quantity
return total
# User Service (Microservice for managing users)
class UserService:
def get_user(user_id):
# Retrieve user data from the User Service database
return user_database.get(user_id)
# Product Service (Microservice for managing products and inventory)
class ProductService:
def check_availability(product_id, quantity):
# Check if the product is available in the required quantity
product = product_database.get(product_id)
return product if product.stock >= quantity else None
def reserve_product(product_id, quantity):
# Deduct quantity from stock for reservation
product = product_database.get(product_id)
product.stock -= quantity
def release_reservation(product_id):
# Re-add quantity back to stock if payment fails
product = product_database.get(product_id)
product.stock += quantity
# Payment Service (Microservice for handling payments)
class PaymentService:
def process_payment(user_id, amount):
# Mock payment processing logic
payment_success = external_payment_gateway.charge(user_id, amount)
return "Success" if payment_success else "Failure"
# Notification Service (Microservice for sending notifications)
class NotificationService:
def send_notification(user_id, message):
# Send email or SMS to the user
notification_system.send(user_id, message)
# Example Usage
user_id = "user123"
cart_items = [
{"product_id": "prod001", "quantity": 2, "price": 20.0},
{"product_id": "prod002", "quantity": 1, "price": 50.0}
]
# Place an order
order_service = OrderService()
order_status = order_service.place_order(user_id, cart_items)
print(order_status) # Output: Order XYZ has been successfully placed
Summary:
Microservice architecture is a design approach that breaks down a large application into smaller, independent services, each responsible for a specific function. These "microservices" operate independently but work together to fulfill application needs. Each service can be developed, deployed, and scaled separately, often with its own database and team.
Key Benefits:
In essence, microservices increase flexibility and reliability by decentralizing responsibilities within an application.
Previous Parts: