LogoTRUONG PHAM
Home
Projects
Blogs
YouTube
Contact

Newsletter

Stay updated with technical artifacts and engineering insights.

LogoTRUONG PHAM

Building scalable software and sharing insights on technology & life.

Sitemap

  • Home
  • Projects
  • Blogs
  • YouTube
  • Contact

Connect

  • GitHub
  • LinkedIn
  • Email
  • YouTube

© 2024 TRUONG PHAM. © All rights reserved.

Privacy PolicyTerms of Service
Back
BFF (Backend for Frontend) - The Savior of UX
Microservice Journey: Lessons & Trade-offs

BFF (Backend for Frontend) - The Savior of UX

A mobile app has to call 5 APIs just to display one page. Why is BFF an indispensable bridge between distributed systems and users?

TP
Truong PhamSoftware Engineer
PublishedMarch 26, 2024
Stack
microservice ·frontend ·ux

Microservices are great for developers, but a nightmare for Clients (Web/Mobile) if not designed correctly. BFF is the "translator" layer that harmonizes these two worlds.


The Problem: The Client is Overwhelmed

Imagine the Home screen of an E-commerce app. To display it, the Mobile App needs to:

  1. Call the User Service for personal info.
  2. Call the Order Service for active deliveries.
  3. Call the Recommendation Service for suggested products.
  4. Call the Promotion Service for promotional banners.

Consequences: 5 simultaneous requests slow down page load, drain phone battery, and make error handling extremely difficult if one of them fails. Our team's Mobile Dev started complaining: "Why is doing microservices so miserable for me?".

1. What is a BFF?

BFF (Backend for Frontend) is an intermediary service, designed specifically for a particular type of Client (e.g., one for Web, one for Mobile). Its job is: Aggregating. Instead of calling 5 services, the Client now calls just 1 API to the BFF. The BFF will "collect" data from those 5 internal services, process it according to the specific format the UI needs, and return a single unified block of data.

2. Real-world Benefits

  • Network Optimization: Minimizes the number of requests from the Client. With unstable 4G/5G networks, this is the difference between "frozen" and "smooth."
  • Data Filtering: Internal microservices often return many redundant data fields. The BFF filters them, only sending back what the UI actually displays, helping to reduce payload size.
  • Hiding Changes: If we split the User Service into Profile Service and Account Service, the Mobile App doesn't need to care. Just update the logic in the BFF.

3. Trade-off: More Code Means More Work

For a 2-person team, maintaining an extra service (BFF) sounds irrational. Our practical formula: Instead of building a bulky Java/Go service as a BFF, we use the Server Side (API Routes) layer of Next.js or a thin Node.js Gateway. It allows Frontend Devs to write the data aggregation logic for themselves.


Lessons Learned

  1. Don't Let the Client Know Too Much: The less the Client knows about the underlying microservice structure, the more flexible it is and the less it's affected by Backend refactors.
  2. BFF Does Not Contain Business Logic: This is the most common mistake. The BFF should only be a "coordination" and "formatting" layer. Don't put financial calculations or heavy business logic here, otherwise, it will become a new Monolith.
  3. Leverage GraphQL? If the team has the resources, GraphQL is a great tool for a BFF because it's born for querying data from multiple different sources. But if not, a simple REST API is enough.

Conclusion

BFF helps us keep the cleanliness of the Microservices underneath while still providing a smooth experience for the users on top. It is the necessary "buffer zone" so that distributed architecture doesn't become a burden for the user experience.

Series • Part 9 of 20

Microservice Journey: Lessons & Trade-offs

NextIdempotency - Why Every API Should Be 'Stubborn'?
Database Separation - A Painful but Necessary 'Divorce'
04REST, gRPC, or NATS? Don't Let Choice Bury Progress05Distributed Transactions - Why 'Immediate Consistency' is a Luxury06Authentication & Authorization - When API Gateway Carries the Team07Docker Compose is Not Enough - The Local Development Story08Database Separation - A Painful but Necessary 'Divorce'09BFF (Backend for Frontend) - The Savior of UXReading10Idempotency - Why Every API Should Be 'Stubborn'?11Infra as Code (IaC) - Automate or Die in a Mountain of Config12The Pain Named Cloud Bill - Cost Optimization for 'Broke Teams'13When the System Goes Silent - Lessons on Post-mortem and Blame-free Culture14Contract Testing - When Integration Testing Becomes a Burden
TP

Written by Truong Pham

Software Engineer passionate about building high-performance systems and meaningful experiences.

Read more articles