Modern systems rely on architectural components like Load Balancers, API Gateways, Backend-For-Frontends (BFFs), and GraphQL.
While each serves a distinct role, they work in complementary ways to ensure efficient, secure, and tailored data delivery.
Let’s look at how these components fit into the request-response lifecycle.
1 - Load Balancers: The First Line of Defense
A Load Balancer sits between the client and your servers and plays a critical role in distributing incoming requests across multiple backend instances.
Why it’s needed:
In a production system, you don’t rely on a single server to handle all user traffic. You have multiple servers (or containers) behind the scenes. A Load Balancer ensures no single server becomes a bottleneck or single point of failure.
How it works:
When a user sends a request (e.g., opening your website), the Load Balancer evaluates which backend instance is least busy or most available.
It forwards the request to that instance and waits for the response.
If one server crashes, the Load Balancer routes traffic to healthy servers, improving availability and fault tolerance.
Advanced capabilities:
Health Checks: Regularly ping servers to ensure they’re alive.
Sticky Sessions: Maintain user sessions with the same server.
SSL Termination: Offload HTTPS decryption for better performance.
Common Tools: NGINX, HAProxy, AWS ELB, Traefik, Envoy
2 - API Gateway: The Smart Coordinator
While the Load Balancer distributes requests across backend servers, an API Gateway helps coordinate requests between clients and microservices.
Why it’s needed:
Imagine a client app that needs to call multiple services to render one screen—authentication, product listings, user preferences, etc. Instead of calling each service individually, the client can send a single request to the API Gateway, which then delegates tasks internally.
What the API Gateway does:
Routes requests to appropriate microservices.
Handles authentication and authorization using tokens (e.g., JWT).
Applies rate limiting to prevent abuse.
Caches responses to improve performance.
Logs requests and responses for monitoring and debugging.
Benefits:
Simplifies client logic: Clients deal with one endpoint instead of many.
Improves maintainability: Cross-cutting concerns like security and logging are centralized.
Supports versioning: Helps manage multiple versions of APIs.
Common Tools: Kong, AWS API Gateway, Apigee, NGINX with Lua, Express Gateway
3 - Backend-For-Frontends (BFF): Tailoring APIs to Clients
Even with an API Gateway in place, frontend applications often have very specific needs. Mobile apps may require different data formats or less data than web apps. That’s where the Backend-For-Frontend (BFF) pattern comes in.
What is BFF?
A BFF is a dedicated backend layer for each frontend—web, mobile, smart TV, etc. It acts as a customized interface between the frontend and the internal APIs.
Why BFFs are useful:
Frontend-specific needs can be handled without bloating the core APIs.
Reduces over-fetching or under-fetching of data.
Enables faster iteration on frontend features without impacting the entire system.
Simplifies aggregation of data from multiple services for a specific interface.
Example:
A mobile app might need a lighter payload with fewer images and less metadata compared to a desktop app. A BFF can filter and shape the response before sending it to the client.
When to use BFFs:
When you support multiple clients (web, mobile, IoT).
When each client needs different logic or response formats.
When you want to offload complex frontend orchestration to a backend layer.
4 - GraphQL: Flexible Data Fetching for the Frontend
GraphQL is a query language and runtime for APIs that allows clients to request exactly the data they need—no more, no less.
How GraphQL Works:
The client sends a query describing the desired data.
The GraphQL server resolves the query by calling appropriate services or databases.
The server returns a JSON response that matches the structure of the query.
Why GraphQL is powerful:
Prevents over-fetching (getting too much data) and under-fetching (not getting enough data).
Great for frontends with dynamic or evolving data requirements.
Supports real-time updates through subscriptions.
Ideal for mobile apps, where reducing payload size is crucial.
Integrating GraphQL with BFF/API Gateway:
You can use GraphQL as part of a BFF layer or behind an API Gateway. It’s especially useful when clients need aggregated data from multiple microservices, and you want to give them control over the structure of the response.
Popular Tools: Apollo Server, GraphQL Yoga, Hasura, Relay
Bringing It All Together
Here’s how these components often fit together in modern architecture. There can be other arrangements as well.
Load Balancer ensures high availability and distributes traffic.
API Gateway simplifies external access and adds cross-cutting features.
BFFs tailor responses to specific frontends.
GraphQL empowers frontends to define their own data needs.
👉 So - have you used any of them in your applications?
Here are some interesting articles I’ve read recently:
How (not to) fail a system design interview by
How To Get Experience as a Software Engineer? by
6 Testing Mistakes You Should Avoid by
That’s it for today! ☀️
Enjoyed this issue of the newsletter?
Share with your friends and colleagues.