# Process

## Requirements

#### **Key Simplified Workflow**

1. Write 3–5 **Functional Requirements**.
2. Write 3–5 **Non-Functional Requirements** with specific metrics.
3. Skip detailed capacity math unless it's crucial for design decisions.

***

### **Functional Requirements (Core Features)**

* **Goal**: Identify the top 3 features your system must have.
* **Approach**:
  * Think about what **users** or **clients** will do with the system.
  * Use **"Should be able to..."** statements to frame these features.
  * Example:
    * For Twitter: "Users should be able to post tweets."
    * For a Cache: "Clients should be able to read items."

💡 **Tip**: Prioritize only the most critical features. Skip minor details or edge cases.

***

### **Non-Functional Requirements (Qualities)**

* **Goal**: Define key qualities your system should meet (e.g., speed, reliability).
* **Approach**:
  * Use **"The system should..."** statements, with specific metrics when possible.
  * Example:
    * For Twitter: "The system should render feeds in under 200ms."
    * For a Cache: "The system should tolerate one node failure without data loss."

💡 **Checklist for Non-Functional Needs**:

* **CAP Theorem**: Consistency or Availability?
* **Scalability**: Will traffic grow, and how (e.g., bursty traffic)?
* **Latency**: Which operations need to be fast (and how fast)?
* **Durability**: Is data loss acceptable? (Critical for banking; less so for logs.)
* **Fault Tolerance**: How many failures should the system survive?

***

### **Capacity Estimation (Optional)**

* Skip this unless **calculations affect your design**.
* Example:
  * For TopK trending topics: Estimate the number of topics to decide between using a single machine or sharding data.

💡 **Tip**: Explain to the interviewer that you'll do math only if necessary, focusing instead on relevant design trade-offs.

***

## **Core Entities**

**Goal**: Identify the main objects in your system to build your foundation.

* **Approach**:
  * **Who are the actors?** (e.g., users, clients).
  * **What nouns/resources fulfill functional requirements?**
  * Jot down a **bulleted list** of key entities. This is a **first draft**, so avoid overcomplicating with details like relationships or fields.
* **Example (Twitter)**:
  * **User**
  * **Tweet**
  * **Follow**

💡 **Tip**: Use clear, intuitive names for entities to make it easier for everyone to follow.

***

## **API or System Interface**

**Goal**: Define how the system communicates with users or clients (its **contract**).

* **Decision**: Choose a communication protocol:
  * **REST API** (default for simplicity): Uses standard HTTP verbs (GET, POST, etc.).
  * **GraphQL**: Use only if clients need fine-grained control over the data returned.
  * **Wire Protocol**: Define a message format for WebSocket or TCP connections.
* **Steps**:
  * Base your endpoints on **core entities**.
  * Write endpoint definitions that map to **functional requirements**.
* **Example (Twitter REST API)**:
  * **POST /v1/tweet**
    * Body: `{ "text": string }`
    * Authenticated user ID inferred from token.
  * **GET /v1/tweet/:tweetId** → Returns a **Tweet**.
  * **POST /v1/follow/:userId** → Authenticated user follows another user.
  * **GET /v1/feed** → Returns a list of **Tweet\[]**.

💡 **Security Tip**: Avoid putting sensitive data like `userId` in the body or query params when it can be derived securely from headers (e.g., auth tokens).

***

## **High-Level Design**

**Goal**: Build a simple architecture to meet your system’s functional requirements and API design.

* **Focus**:
  * **Components**: Servers, databases, caches, message queues, etc.
  * **Interaction**: Draw arrows to show how components communicate.
  * **Keep It Simple**: Start with basic components and focus on functional requirements.
* **Step-by-Step**:
  1. **Identify core components**: What do you need for your system to work? For example, a web server, a database, etc.
  2. **Flow of data**: Discuss how data flows from one component to another, focusing on state changes during each request.
  3. **Start with API endpoints**: Build your design around these endpoints, adding complexity only when necessary (e.g., caching, queuing).
* **Visual Tips**:
  * You don’t need to document every single detail in your schema. Focus on **important fields** that affect your design.
  * As you draw your architecture, talk through your thought process, explaining how each component interacts.
* **Example (Twitter)**:
  * POST `/v1/tweet` → Send to server → Store in database.
  * GET `/v1/tweet/:tweetId` → Fetch from database → Return to client.
  * POST `/v1/follow/:userId` → Update user’s following list → Store in database.
  * GET `/v1/feed` → Use cached feeds or query database for timeline.

***

## **Deep Dives**

**Goal**: Harden your design by addressing non-functional requirements, edge cases, and bottlenecks.

* **Focus**:
  1. **Non-functional requirements**: Scalability, performance, fault tolerance.
  2. **Edge cases**: Handle unexpected conditions like failed API requests or database downtime.
  3. **Bottlenecks**: Identify and improve performance issues.
  4. **Probes**: Address any interviewer feedback or questions during this section.
* **Proactive Discussion**:
  * **Junior candidates**: Your interviewer will guide you, pointing out places to improve.
  * **Senior candidates**: Lead the discussion by identifying potential problems and discussing solutions.
* **Example (Twitter)**:
  * **Scalability**: Horizontal scaling, caching, and database sharding to handle >100M DAU.
  * **Feed Latency**: Discuss **fanout-on-read** vs **fanout-on-write** strategies and caching to minimize latency when fetching user feeds.
* **Collaboration Tip**: Don’t dominate the conversation. Allow space for the interviewer to probe your design. Their questions may provide valuable insights or signal areas they want to focus on.
