Published on

UberAspire : A distributed system for Ride Sharing App

Authors
  • avatar
    Name
    Siddharth Singh
    Twitter

Why this project?

TLDR; This is for learning. On multiple fronts.Let me share the key motivations behind this.

Scope

I have been working on distributed systems for quite some time but worked mostly on few components and services. And that's by design. Systems at Big Tech companies are mammoth. They span across multiple teams and orgs with each team owning few of the services.

Sometimes, the feature which you are working spans across team or org boundaries and that's when you get the chance to work on the bigger picture. But most of the time, you are occupied with your team's services, configurations, on calls, reporting, infra.

In fact, leave aside a few fouding engineers whose names are present on 10 year old commits, most of the folks are not even not aware of services owned by other teams and learn only about them when there is an incident from that service.

So, one of the goals for this project is to learn to write an end-2-end system from scratch and develop the product based thinking apart from technical stuff. Think of below questions. How do you look at a big complex system as a whole and analyse the trade-offs while making a small change? How do you optimize you whole system for cost, efficiency, Latency ?

A Distributed system playground

Another reason is to have a distributed system playground of my own. I read so many optimizations techniques for Web infra on scale, memory optimizations, new instructions, APIs etc. These things are mostly forgotten. It's good to have a playground where I can test these optimizations.

Looking Beyond CRUD App projects

Nothing wrong with CRUD Apps but a complex system with CRUD apis, polyglot persistance, caching, queueing , autoscaling, geospatial stuff, multi service communication, observability, performance optimizations offers better learning and implementation of concepts.

Once you do that, you would be careful while drawing boxes in a system design interview.

Learning new stuff

This will give me opportunities to learn .NET Aspire, new Apis availalbe in .net apart from all the classic distributed system concepts, patterns and algorithms. I hope to share them all with the community.

Design Source

I will use the design shared at Hello Interview. It is a popular site for system design interviews as well. The design for Uber is practical for an interview and covers all the aspects.

Design Digram

Note: Downloaded from Hello Inteview site for educational purpose.

uber system design - hellow inteview

Implementation principles

Though a personal project is our own little world where we can experiment and learn with no obligations, external guidelines or commitments, I have thought of few guiding principles to keep things coherent and presentable from the start.

  1. I will try to implement the design as it is mentioned in the source design doc. If it uses 5 services, then we will use five.
  2. Will use the same or similar components. Eg. Postgress can be interchanged with SQL Server.
  3. In general, the code will be written in C# as it is my primary language. If needed, we can go for another language.
  4. Will use containers for local development and testing.
  5. While this should not be production ready but I will try to push the limits for what one person can do.
  6. Functionality should work end to end. I plan to record a demo and share where I used the Rider and Driver apps to navigate.

Here are the requirements of the ride sharing system. Please go through it in detail here.

Blog Index

#Link
1Ride Sharing App- current blog
2Ride Service
3Location Service
4RideMatching Service
5Notification Service
6Rider App
7Driver App
8Ride Matching Queue
9Observability
10Scaling and Sharding
11Deployment
12Testing
13Demos and future enhancements

Functional Requirements

  1. Riders should be able to input a start location and a destination and get a fare estimate.
  2. Riders should be able to request a ride based on the estimated fare.
  3. Upon request, riders should be matched with a driver who is nearby and available.
  4. Drivers should be able to accept/decline a request and navigate to pickup/drop-off.

Non-Functional Requirements

  1. The system should prioritize low latency matching (< 1 minutes to match or failure)
  2. The system should ensure strong consistency in ride matching to prevent any driver from being assigned multiple rides simultaneously
  3. The system should be able to handle high throughput, especially during peak hours or special events (100k requests from same location)

Components

As per the design, below are the components which we need to build. There will be few addditions to services and components during implementation. For example, we may need a configuration App for setting\changing the runtime configs. Similarly, We can have sharding layer, API gateway, datastores for logging and monitoring, background workers for Migration, Payment service, UserProfile, Invoice. I also plan to add authentication in the end.

I will be updating this doc as and when new components are added or removed. For now, Let's go with our source design doc.

Micro Services

  1. Ride
  2. RideMatching
  3. Location
  4. Notification Service

Databases

  1. Rides Database (Can be PostGress or Dynamo)
  2. Location DB (Redis)

Client Side

  1. Rider App
  2. Driver App

Other Infra components

  1. API Gateway
  2. Redis for Distributed Lock
  3. Kafka\RabbitMQ Queue for Ridematching

Repo

The code is hosted at github - UberAspire

Deployment

Dotnet Aspire supports Kubernetes and Azure Container Apps. There are tools to convert the aspire app host to a matching yaml file for kubernetes.

Here is my local aspire dashboard after I created the project and added the services. aspire dashboard

Thanks for reading! I will put an index for the all the posts in this series later.