Phase 1: Clarify, Scope & Constraints
Interviewer: "Let's design Uber — a ride-hailing service. How do you approach this?"
Candidate: "Let me clarify the core user journeys:
- Rider request journey — Rider requests a trip from point A to B, gets matched with a nearby driver, tracks the driver's approach, and completes the trip
- Driver availability journey — Driver goes online, location is broadcast to the system, they receive trip requests, accept, pick up, and drop off
- Matching journey — The system matches available drivers to nearby riders as fast as possible
- Surge pricing journey — When demand exceeds supply in an area, prices increase dynamically to incentivize drivers
The dominant complexity is the real-time matching problem. Uber has ~36 million trips per day across 15,000+ cities, with on the order of 2 million drivers online concurrently at peak (out of millions active over a day). Finding the best available driver for a rider, in milliseconds, while continuously tracking all drivers' GPS locations at 4-second intervals — that's the core challenge.
WHY: The secondary complexity is ETA accuracy. Riders make decisions (whether to request a ride, whether to accept the price) based on ETA. If the ETA is wrong, the user experience is broken. Computing accurate ETAs for hundreds of thousands of concurrent trips requires sophisticated ML, not just shortest-path routing.
Non-goals for V1:
- Uber Eats / food delivery (separate matching constraints)
- Driver background check and onboarding
- Payment processing (treat as an external service call)
- Surge pricing algorithm ML training (treat surge multipliers…
In the full tutorial
- Phase 2: High-Level Architecture
- Phase 3: Deep Dive & Evolution
- Phase 4: Robustness & Operations