Security Notes
System Design

Design Tinder (Dating App / Recommendation)

3 min read 6 sections

DifficultyMedium | HelloInterview: problem breakdown


Problem Statement

Design a dating app where users see a deck of profiles, swipe left (reject) or right (like), and are notified when there's a mutual match.

๐Ÿ“–

Real-world: Two things make Tinder a sharp design. First, the match problem is deceptively about write efficiency โ€” a "match" is just detecting that two one-way likes point at each other, so you store likes and check for the reciprocal on each swipe (you don't scan; you look up "does B already like A?"). Second, the deck is precomputed โ€” you don't run an expensive geo + preference query on every swipe; you build a candidate pool ahead of time using a geospatial index (geohash) plus filters. The security/privacy lessons here are real and well-documented: Tinder shipped for years transmitting photos over plain HTTP and leaking exact distances so precise that researchers trilaterated users' locations to within meters ("Tinder Online" / trilateration attacks). The takeaway for this audience: location data is sensitive PII โ€” fuzz/round distances server-side, never expose precise coordinates to the client, and encrypt everything in transit. Dating apps are a recurring case study in privacy-by-design failures.


Requirements

Functional

  • User profile with photos and bio
  • Swipe left/right on suggested profiles
  • Match when both users like each other
  • In-app messaging after match
  • Recommendation engine (who to show)

Non-Functional

  • 75M DAU, 1.6B swipes/day โ†’ 18,500 swipes/s
  • Deck load latency: < 200ms
  • Match notification: real-time (< 1s after mutual like)
  • Location-based: users see people nearby

Core Design

Profile Deck Generation

The "deck" is a pre-computed list of candidate profiles for each user.

Deck generation factors:
  - Location: within X km (geohash query)
  - Age range
  - Gender preference
  - Not already seen (swiped on)
  - Scored by recommendation model (photos, activity, compatibility)

Pre-computationgenerating a deck in real-time is expensive. Pre-compute each user's deck hourly and cache in Redis.

Redis: deck:{user_id} โ†’ list of profile_ids (sorted by score)
TTL: 1h (refresh hourly or on explicit refresh)

Swipe Recording

swipes(
  user_id      UUID,
  target_id    UUID,
  direction    ENUM('like', 'pass'),
  created_at   TIMESTAMP
)
INDEX (user_id, target_id)  -- for "did user A already swipe on user B?"

18,500 swipes/s โ†’ Cassandra for write throughput. Partition by user_id.

Match Detection

On "like":
  1. Write like to swipes table
  2. Check: did target_id already like user_id?
     โ†’ SELECT FROM swipes WHERE user_id=target_id AND target_id=user_id AND direction='like'
  3. If yes: create match record, notify both users

Optimization: use Redis bloom filter or in-memory set to check if the reverse like exists before hitting the DB.

Match notification: WebSocket push to both users.


Architecture

API โ†’ Swipe Service โ†’ Cassandra (swipes)
                         โ†“
                    Match Checker โ†’ Redis (already liked?) โ†’ Match DB
                                                                   โ†“
                                                       Notification Service (WebSocket)

Recommendation:
  Location Index (Redis/Elasticsearch geo) โ†’ filter candidates
  โ†’ ML scoring model โ†’ pre-computed deck (Redis)
  โ†’ Deck refresher (background job, hourly per user)

Media: Photos โ†’ S3 + CDN (face-detected thumbnail generation)

Security Considerations

ThreatMitigation
Profile spoofing / catfishingPhoto verification (selfie match); phone number verification
Harassment / blockBlock/report flow; moderation queue; ML classifier
Location precision leakageShow distance (e.g., "3 km") not precise location; fuzzing
Profile scrapingRate limit swipe API; anomaly detection on systematic viewing
CSAMAge verification at signup; photo hash scanning

Interview Tips

Pre-computation is the key

don't generate the deck on every request. Show the deck cache + background refresher pattern.

Match detection

is the most interesting algorithmic problem โ€” the Redis bloom filter for fast reverse-like lookup shows real engineering instinct.

Location geo-index

same as Uber/Yelp (geohash).