EasyStarter

To-Do List API

DatabasesAPI DesignAuth

Problem Statement

TaskBee wants to build a simple to-do application backend that mobile and web apps consume via REST API. Features:

- User accounts - sign up with email/password, login with JWT tokens.Lists & tasks - users create task lists (e.g., "Groceries", "Work"). Each list contains tasks with a title, description, due date, priority, and completion status.Sharing - users can share a list with other users (viewer or editor role).Reminders - send a push notification or email when a task's due date is approaching (24 hours before).Subtasks - tasks can have subtasks (one level deep).

The app targets individual users with a modest user base - 10,000 registered users, 2,000 DAU.

What You'll Learn

Design a RESTful to-do list API with user accounts, lists, tasks, and due-date reminders. Build this architecture under realistic production constraints, then validate tradeoffs in the design lab simulation.

DatabasesAPI DesignAuth

Constraints

Registered users~10,000
Daily active users~2,000
Tasks per user~100 avg
API response time< 200 ms
Reminder deliveryWithin 5 minutes of trigger
Availability target99.5%
ApproachClick to expand

Interview-Ready Approach

1) Clarify Scope and SLOs

  • Problem statement: Design a RESTful to-do list API with user accounts, lists, tasks, and due-date reminders.
  • Design for a peak load target around 100 RPS (including burst headroom).
  • Registered users: ~10,000
  • Daily active users: ~2,000
  • Tasks per user: ~100 avg
  • API response time: < 200 ms
  • Reminder delivery: Within 5 minutes of trigger

2) Capacity Planning Method

  • Convert traffic and growth constraints into request rate, storage growth, and concurrency budgets.
  • Keep at least 2-3x safety margin per tier (ingress, compute, storage, async workers).
  • Reserve explicit latency budgets per hop so p95 can be defended in review.

3) Architecture Decisions

  • Databases: Define a clear system-of-record and design read/write paths separately before adding optimizations.
  • API Design: Standardize API boundaries, idempotency keys, pagination, and error contracts first.
  • Auth: Centralize identity verification and keep authorization checks close to domain resources.

4) Reliability and Failure Strategy

  • Use strong write constraints (transactions or conditional writes) and explicit backup/restore strategy.
  • Apply strict input validation and backward-compatible versioning.
  • Use short-lived tokens and secure key rotation workflows.

5) Validation Plan

  • Run one peak-load test, one dependency-degradation test, and one failover test.
  • Verify idempotency for all retried writes and async consumers.
  • Track user-facing SLOs first: p95 latency, error rate, and successful throughput.

6) Trade-offs to Call Out in Interviews

  • Databases: SQL gives stronger transactional guarantees; NoSQL often gives better write scaling and flexibility.
  • API Design: Rich APIs improve developer speed but can create long-term compatibility burden.
  • Auth: Central auth simplifies policy, but makes auth service availability/security critical.

Practical Notes

  • A single PostgreSQL database with proper indexes covers all read/write needs at this scale.
  • JWT tokens for stateless auth - store a refresh token in the database for token rotation.
  • A cron job or scheduled worker can scan for upcoming due dates and enqueue reminder notifications.

Learn the Concept

Practice Next

Reference SolutionClick to reveal

Why This Solution Works

Request path: The solution keeps ingress, service logic, and stateful dependencies separated so each layer can scale independently.

Reference flow: Web Clients -> API Gateway -> API Service -> Auth Service -> Primary SQL DB

Design strengths

  • Security controls are enforced at ingress to protect downstream capacity.

Interview defense

  • This design makes bottlenecks explicit (ingress, core compute, persistence, async workers).
  • It supports progressive scaling without re-architecting the core request path.
  • It keeps correctness-sensitive state changes in durable systems while offloading background work asynchronously.