Thursday, September 9, 2021

A Simple Framework For Mobile System Design Interviews | 20 minutes study

Sept. 9, 2021

Here is the article. 

Alex Lementuev

Disclaimer

Disclaimer


Server-side components:

  • Backend
    Represents the whole server-sider infrastructure. Most likely, your interviewer won’t be interested in discussing it.
  • Push Provider
    Represents the Mobile Push Provider infrastructure. Receives push payloads from the Backend and delivers them to clients.
  • CDN (Content Delivery Network)
    Responsible for delivering static content to clients.

Client-side components:

  • API Service
    Abstracts client-server communications from the rest of the system.
  • Persistence
    A single source of truth. The data your system receives gets persisted on the disk first and then propagated to other components.
  • Repository
    A mediator component between API Service and Persistence.
  • Tweet Feed Flow
    Represents a set of components responsible for displaying an infinite scrollable list of tweets.
  • Tweet Details Flow
    Represents a set of components responsible for displaying a single tweet’s details.
  • DI Graph
    Dependency injection graph.
  • Image Loader
    Responsible for loading and caching static images. Usually represented by a 3rd-party library.
  • Coordinator
    Organizes flow logic between Tweet Feed and Tweet Details components. Helps decoupling components of the system from each other.
  • App Module
    An executable part of the system which “glues” components together.

Providing the “signal”

  • The candidate can present the “big picture” without overloading it with unnecessary implementation details.
  • The candidate can identify the major building blocks of the system and how they communicate with each other.
  • The candidate has app modularity in mind and is capable of thinking in the scope of the entire team and not limiting themselves as a single contributor (this might be more important for senior candidates).

Deep Dive: Tweet Feed Flow

  • Architecture patterns
    MVP, MVVM, MVI, etc. MVC is considered a poor choice these days. It’s better to select a well-known pattern since it makes it easier to onboard new hires (compared to some less known home-grown approaches).
  • Pagination
    Essential for infinite scroll functionality. For more details see Pagination.
  • Dependency injection
    Helps to build an isolated and testable module.
  • Image Loading
    Low-res vs full-res image loading, scrolling performance, etc.

Add diagram here

Components

  • Feed API Service — abstracts Twitter Feed API client: provides the functionality for requesting paginated data from the backend. Injected via DI-graph.
  • Feed Persistence — abstract cached paginated data storage. Injected via DI-graph.
  • Remote Mediator — triggers fetching the next/prev page of data. Redirects the newly fetched paged response into a persistence layer.
  • Feed Repository — consolidates remote and cached responses into a Pager object through Remote Mediator.
  • Pager — trigger data fetching from the Remote Mediator and exposes an observable stream of paged data to UI.
  • “Tweet Like” and “Tweet Details” use cases — provide delegated implementation for “Like” and “Show Details” operations. Injected via DI-graph.
  • Image Loader — abstracts image loading from the image loading library. Injected via DI-graph.

Providing the “signal”

  • The candidate is familiar with the most common MVx patterns.
  • The candidate achieves a clear separation between business logic and UI.
  • The candidate is familiar with dependency injection methods.
  • The candidate is capable of designing self-contained isolated modules.

API Design

Real-time notifications

Push Notifications

  • easier to implement compared to a dedicated service.
  • can wake the app in the background.
  • not 100% reliable.
  • may take up to a minute to arrive.
  • relies on a 3rd-party service.

HTTP-polling

Short HTTP-polling

  • simple and not as expensive (if the time between requests is long).
  • no need to keep a persistent connection.
  • the notification can be delayed for as long as the polling time interval.
  • additional overhead due to TLS Handshake and HTTP-headers

Long HTTP-polling

  • instant notification (no additional delay).
  • more complex and requires more server-side resources.
  • keeps a persistent connection until the server replies.

Server-Sent Events

  • real-time traffic using a single connection.
  • keeps a persistent connection.

Web-Sockets

  • can transmit both binary and text data.
  • more complex to set up compared to Polling/SSE.
  • keeps a persistent connection.

Protocols

REST

  • easy to learn, understand, and implement.
  • easy to cache using a built-in HTTP caching mechanism.
  • loose coupling between client and server.
  • less efficient on mobile platforms since every request requires a separate physical connection.
  • schemaless — it’s hard to check data validity on the client.
  • stateless — needs extra functionality to maintain a session.
  • additional overhead — every request contains contextual metadata and headers.

GraphQL

  • schema-based typed queries — clients can verify data integrity and format.
  • highly customizable — clients can request specific data and reduce the amount of HTTP traffic.
  • bi-directional communication with GraphQL Subscriptions (WebSocket based).
  • more complex backend implementation.
  • “leaky-abstraction” — clients become tightly coupled to the backend.
  • the performance of a query is bound to the performance of the slowest service on the backend (in case the response data is federated between multiple services).

WebSocket

  • real-time bi-directional communication.
  • provides both text-based and binary traffic.
  • requires maintaining an active connection — might have poor performance on unstable cellular networks.
  • schemaless — it’s hard to check data validity on the client.
  • the number of active connections on a single server is limited to 65k.

gRPC

  • lightweight binary messages (much smaller compared to text-based protocols).
  • schema-based — built-in code generation with Protobuf.
  • provides support of event-driven architecture: server-side streaming, client-side streaming, and bi-directional streaming
  • multiple parallel requests.
  • limited browser support.
  • non-human-readable format.
  • steeper learning curve.

Pagination

Offset Pagination

  • easiest to implement — the request parameters can be passed directly to a SQL query.
  • stateless on the server.
  • bad performance on large offset values (the database needs to skip offset rows before returning the paginated result).
  • inconsistent when adding new rows into the database (Page Drift).

Keyset Pagination

  • translates easily into a SQL query.
  • good performance with large datasets.
  • stateless on the server.
  • “leaky abstraction” — the pagination mechanism becomes aware of the underlying database storage.
  • only works on fields with a natural ordering (timestamps, etc).

Cursor/Seek Pagination

  • decouples pagination from SQL database.
  • consistent ordering when new items are inserted.
  • more complex backend implementation.
  • does not work well if items get deleted (ids might become invalid).
GET /v1/feed?after_id=p1234xzy&limit=20
Authorization: Bearer <token>
{
"data": {
"items": [
{
"id": "t123",
"author_id": "a123",
"title": "Title",
"description": "Description",
"likes": 12345,
"comments": 10,
"attachments": {
"media": [
{
"image_url": "https://static.cdn.com/image1234.webp",
"thumb_url": "https://static.cdn.com/thumb1234.webp"
},
...
]
},
"created_at": "2021-05-25T17:59:59.000Z"
},
...
]
},
"cursor": {
"count": 20,
"next_id": "p1235xzy",
"prev_id": null
}
}

Authentication

Providing the “signal”

  • The candidate is aware of the challenges related to poor network conditions and expensive traffic.
  • The candidate is familiar with the most common protocols for unidirectional and bi-directional communication.
  • The candidate is familiar with REST-full API design.
  • The candidate is familiar with authentication and security best practices.
  • The candidate is familiar with network error handling and rate-limiting.

Conclusion

Things you can control

  • Your attitude — always be friendly no matter how the interview goes. Don’t be pushy and don’t argue with the interviewer — this might provide a bad “signal”.
  • Your preparation — the better your preparation is, the bigger the chance of a positive outcome. Practice mock design interviews with your peers (you can find people on Teamblind).
  • Your knowledge — the more knowledge you have, the better your chances are.
  • Gain more experience.
  • Study popular open-source projects: iOSAndroid
  • Read development blogs from tech companies
  • Your resume — make sure to list all your accomplishments with measurable impact.

Things you cannot control

  • Your interviewer’s attitude — they might have a bad day or simply dislike you.
  • Your competition — sometimes there’s simply a better candidate.
  • The hiring committee — would make a decision based on the interviewers’ reports and your resume.

Judging the outcome


No comments:

Post a Comment