Estimate the scale of the system you are going to design...
DAU : ~ 100M Users
Each User post 1 tweet per day
Each tweet takes about 5KB
5KB * 100M * 365 * 10 is the storage expectation for the service (in 10 years)
Define what APIs are expected from the system...
/api/postTweet
ReqBody:
{
UserID
PostObject (Video, picture)
Post Description
}
ResBody:
{
status
}
/api/getTweet
ReqBody:
{
TweetID
}
ResBody:
{
Raw Data
}
/api/viewFeed/UserID
ResBody:
{
List of Tweets from followee
}
/api/follow
ReqBody:
{
FollowerID,
FolloweeID
}
ResBody:
{
Status
}
Defining the system data model early on will clarify how data will flow among different components of the system. Also you could draw an ER diagram using the diagramming tool to enhance your design...
Tweet Table (Metadata){
TweetID : String PK
UserID : String FK
Created_By : Date
Data URL : String
Desc : String
}
Follow Table {
Follow ID : String PK
Follower ID : String FK
Followee ID : String FK
}
User Table {
User ID : String PK
User Name : String
User Profile Picture URL : String
}
Drawn in HLD Diagram
For Cache hit, it will use LRU cache since the least recent tweet will lose views.
GraphDB will make adjancy list for user based on followees
CDN will cache the small set of data of static contents like video or picture
Instead of using NoSQL, the reason why I use RDBMS is that the table have complicated relations. We can use NoSQL which has strong capacity on horizontal scaling
Try to discuss as many failure scenarios/bottlenecks as possible.
LB should be single point of failure (it can be covered by trying adding some passive LB)
Cache can be also single point of failure (it will leads high latency to view feed)
Without Rate Limiting, danger from DDOS
Add Rate Limiting and Passive LB for improvement on availability
Partitioning DB Based on User ID (Shard) -> improve process on viewFeed
Make available on multiple pictures or videos to store
Authentication and Authorization system
Notification system when followw post new tweet