# Stop Treating OOD and HLD as Separate Interview Skills

<img src="https://bugfree-s3.s3.amazonaws.com/mermaid_diagrams/image_1769710558365.png" alt="System design diagram" style="max-width:800px;height:auto;display:block;margin:0 auto;" />

Why treat high-level design (HLD) and object-oriented design (OOD) like two disconnected interview topics? Interviewers are evaluating your ability to design systems end-to-end: from architecture and data flow down to classes, interfaces, and trade-offs. The strongest answers connect the two — showing how low-level design choices support high-level goals.

Here’s a concise, practical approach to unify HLD and OOD during interviews.

1) Start with requirements and constraints

- Ask clarifying questions: scope, scale, SLAs, data volume, consistency needs, and failure tolerance.
- Distinguish functional vs. non-functional requirements — these drive both architecture and class responsibilities.

2) Sketch the HLD first

- Draw components and boundaries: API layer, services, databases, caches, queues, and external integrations.
- Show data flow and identify stateful vs. stateless parts.
- Highlight scaling points and potential bottlenecks (storage, hot shards, network).
- Discuss operational concerns: monitoring, deployment, and fault tolerance.

3) Drill down into OOD from the HLD

- Map each architectural component to modules or subsystems and then to classes and interfaces.
- For each class, define responsibilities (single responsibility), relationships, and the public interface.
- Use encapsulation to hide implementation, and choose patterns (factory, strategy, repository, adapter) where they reduce coupling or add clarity.
- Prefer composition over inheritance when it increases flexibility.

4) Make coupling low and cohesion high

- Keep interfaces small and focused. High cohesion inside modules makes them easier to test and evolve.
- Reduce coupling with well-defined contracts (interfaces) and dependency injection.

5) Tie OOD choices back to HLD goals

- Maintainability: separate concerns, clear interfaces, and module-level tests make future changes cheaper.
- Performance: choose appropriate data structures, caching locations, and batching strategies in the class design.
- Scalability: design stateless service classes, sharded repositories, and partition-aware logic.
- Reliability: implement idempotent operations, retries, and circuit breakers where the architecture demands resilience.

6) Iterate and justify trade-offs

- When the interviewer challenges a decision, refactor in place: show how you’d change interfaces, add a pattern, or introduce caching. Explain the cost and benefits.
- Talk about complexity (time/space), operational cost, and development velocity for each option.

Quick example (messaging service)

- HLD: API Gateway → Auth Service → Message Service → Message Store (DB) + Queue → Worker(s)
- OOD mapping:
  - MessageService: sendMessage(userId, conversationId, payload)
  - MessageStore interface: save(message), fetch(conversationId, limit, after)
  - Conversation, Message, User domain objects with behavior (e.g., markRead())
  - Worker implements MessageProcessor interface to handle delivery/retries

How this maps to goals:
- Stateless MessageService instances (HLD) lead to a simple OOD: small, testable class with injected MessageStore and Queue clients (low coupling).
- MessageStore implementations can differ (SQL vs. partitioned NoSQL) without changing service interfaces (extensibility).

Interview tips

- Narrate your thought process; don’t stay silent.
- Draw/label diagrams and then point to the area you’re diving into.
- Ask constraints early and state assumptions clearly.
- Be explicit about trade-offs and how your OOD decisions satisfy HLD objectives.

Treat HLD and OOD as a continuum: show how components become modules and modules become classes. The interview is as much about communication and trade-off reasoning as it is about technical correctness.

