Your concept feed

43 ideas

A few small steps. No rush.

Follow the connections in this topic

A familiar idea

Start with what people need to do.

save
read
keep data

A note app must save a note and read it later. Before choosing databases, ask how many people use it and what failures are acceptable.

Swipe when you’re ready
One new wrinkle

Turn “fast” into a measurable promise.

which request?
how often?
how fast?

A latency objective needs an operation, percentile, time limit, and measurement window. Reads and writes may need different promises.

Same idea. One more small step.
Try a tiny example

Separate steady traffic from bursts.

daily average
peak burst

Ten thousand requests per day is an average, not a peak. A short burst can dominate the capacity we actually need.

Same idea. One more small step.
Notice what matters

Choose boxes only after these questions.

requirements
tradeoffs
architecture

List operations, scale assumptions, consistency needs, availability goals, and what is outside scope. Revisit them when a design choice conflicts.

Want to try a tiny question?
No pressure. Just try it.

Does average traffic alone tell us how many workers a peak needs?

You can also keep scrolling
1 / 5
High-level design

One small step at a time.

This idea builds on these smaller ones. Pick any to revisit it here.

How many little jobs?

Hi
Hi
Hi

Visit three places. Say hello once at each. That’s three hellos.

1 / 3
Let’s picture it

A request crosses several boundaries.

DNS
connection + TLS
HTTP

A name resolves to an address. A connection reaches a server. TLS protects the connection. HTTP carries the request and response.

Swipe when you’re ready
One little change

Some setup can be reused.

reused connection
application
storage

Cached DNS and existing connections can avoid repeated setup. The application still performs its own validation, computation, and storage work.

Same idea. One more small step.
Now it has a name

Every boundary can consume time or fail.

request sent
work done?
response missing

A deadline must cover the whole operation. A timeout does not prove the server did nothing; its response might simply be lost.

Want to try a tiny question?
No pressure. Just try it.

Does a timeout prove a write never committed?

You can also keep scrolling
1 / 4
High-level design

One small step at a time.

This idea builds on these smaller ones. Pick any to revisit it here.

Start with what people need to do.

save
read
keep data

A note app must save a note and read it later. Before choosing databases, ask how many people use it and what failures are acceptable.

1 / 4
Let’s picture it

Make one operation’s promise explicit.

request
validated operation
response

Define its resource, input, validation, response, and errors. For writes, also define what a repeated request means.

Swipe when you’re ready
One little change

Pages need a stable ordering key.

timestamp
unique ID

Two notes can have the same timestamp. Add a unique ID as a tie-breaker, then continue after both cursor values.

Same idea. One more small step.
Now it has a name

A cursor is not permission.

page position
authorization separately

A cursor locates the next page. The server must still enforce the caller’s access rights and decide snapshot behavior under concurrent changes.

Want to try a tiny question?
No pressure. Just try it.

Is a timestamp alone always enough for gap-free keyset pagination?

You can also keep scrolling
1 / 4
High-level design

One small step at a time.

This idea builds on these smaller ones. Pick any to revisit it here.

A request crosses several boundaries.

DNS
connection + TLS
HTTP

A name resolves to an address. A connection reaches a server. TLS protects the connection. HTTP carries the request and response.

1 / 3
Let’s picture it

A module does not have to be a separate server.

one deployment
separate responsibilities

Keep notes, accounts, and notifications behind clear code boundaries first. They can begin inside one deployable application.

Swipe when you’re ready
One little change

Split deployment when independence earns its cost.

independent changes
network costs

Separate services can scale and ship independently, but calls now face network latency, partial failure, and independent data ownership.

Same idea. One more small step.
Now it has a name

Choose one owner for each fact.

state owner
published contract

If several services write the same business state without a contract, deployment separation may increase coupling instead of reducing it.

Want to try a tiny question?
No pressure. Just try it.

Does putting every class in its own service automatically reduce coupling?

You can also keep scrolling
1 / 4
High-level design

One small step at a time.

This idea builds on these smaller ones. Pick any to revisit it here.

Make one operation’s promise explicit.

request
validated operation
response

Define its resource, input, validation, response, and errors. For writes, also define what a repeated request means.

1 / 3
Let’s picture it

One worker becomes several.

balancer
worker A
worker B

A load balancer chooses a healthy worker for each request. More workers can share traffic, but they need the state required to serve any user.

Swipe when you’re ready
One little change

Do not hide essential session state in one worker.

request 1 → A
request 2 → B

If only A remembers a user’s session, routing the next request to B breaks the workflow. Use an explicit shared or client-carried session design.

Same idea. One more small step.
Now it has a name

Health and capacity are changing facts.

ready workers
drain safely
observe load

Round-robin is simple, but readiness checks, connection draining, slow workers, and uneven request costs affect real routing.

Want to try a tiny question?
No pressure. Just try it.

Does adding app workers automatically fix a saturated database?

You can also keep scrolling
1 / 4
High-level design

One small step at a time.

This idea builds on these smaller ones. Pick any to revisit it here.

A request crosses several boundaries.

DNS
connection + TLS
HTTP

A name resolves to an address. A connection reaches a server. TLS protects the connection. HTTP carries the request and response.

1 / 3
A familiar idea

Start with the questions storage must answer.

read pattern
write pattern
invariant

Which record do we fetch? Which records do we list together? Which changes must succeed together? Those choices shape keys, indexes, and transactions.

Swipe when you’re ready
One new wrinkle

An index is another maintained structure.

faster reads
extra write work

It makes certain lookups cheaper, but every relevant write must maintain it. Indexes cost memory, disk, and write work.

Same idea. One more small step.
Try a tiny example

Put an invariant inside the write boundary.

check + decrement
one database operation

Claim stock only if enough remains, in one conditional update. Reading first and writing later can race with another claimant.

Same idea. One more small step.
Notice what matters

Choose a data model, not a slogan.

queries
constraints
chosen model

Relational, document, key-value, and wide-column models favor different access patterns. “NoSQL” does not mean every product has the same guarantees.

Want to try a tiny question?
No pressure. Just try it.

Does a separate SELECT followed by an unconditional UPDATE protect stock from concurrent claims?

You can also keep scrolling
1 / 5
High-level design

One small step at a time.

This idea builds on these smaller ones. Pick any to revisit it here.

Make one operation’s promise explicit.

request
validated operation
response

Define its resource, input, validation, response, and errors. For writes, also define what a repeated request means.

1 / 3
A familiar idea

A saved value can have several copies.

leader: new
replica: old

A leader accepts a write and replicas receive it. If copying is asynchronous, a replica may temporarily show the old value.

Swipe when you’re ready
One new wrinkle

An acknowledgment needs a definition.

accepted where?
durable where?

Did the write reach memory, durable storage, or a required set of replicas? Those are different durability and latency promises.

Same idea. One more small step.
Try a tiny example

Overlapping sets are useful, but not a protocol.

set overlap
plus protocol rules

A read quorum and write quorum may intersect. That alone does not define ordering, leadership, version selection, or safe behavior during failures.

Same idea. One more small step.
Notice what matters

Agreement needs explicit coordination.

leader + log
quorum agreement

Consensus protocols such as Raft coordinate a replicated log under stated failure assumptions. Replication is not simply copying a dictionary.

Want to try a tiny question?
No pressure. Just try it.

Does reading from any asynchronous replica always provide read-your-writes?

You can also keep scrolling
1 / 5
High-level design

One small step at a time.

This idea builds on these smaller ones. Pick any to revisit it here.

Start with the questions storage must answer.

read pattern
write pattern
invariant

Which record do we fetch? Which records do we list together? Which changes must succeed together? Those choices shape keys, indexes, and transactions.

1 / 4
A familiar idea

Copies and partitions solve different problems.

replicas: same keys
shards: different keys

Replication copies the same data. Partitioning gives different keys to different owners so storage and work can be spread out.

Swipe when you’re ready
One new wrinkle

Choose a key that spreads the real workload.

many quiet keys
one hot key

Hashing user IDs can spread users, but one extremely busy user may still overload its shard. Equal key counts are not equal traffic.

Same idea. One more small step.
Try a tiny example

A hash ring limits movement during membership changes.

key hash
next token
owner

Consistent hashing assigns a key to the next token on a ring. Virtual nodes spread each server across several ranges.

Same idea. One more small step.
Notice what matters

Movement still needs a data migration plan.

copy
cut over
retire

New routing does not instantly move stored bytes. Define copying, cutover, versioning, and behavior while old and new owners coexist.

Want to try a tiny question?
No pressure. Just try it.

Does consistent hashing automatically solve a single hot key?

You can also keep scrolling
1 / 5
High-level design

One small step at a time.

This idea builds on these smaller ones. Pick any to revisit it here.

A saved value can have several copies.

leader: new
replica: old

A leader accepts a write and replicas receive it. If copying is asynchronous, a replica may temporarily show the old value.

1 / 4
A familiar idea

A nearby copy can save repeated work.

cache hit
or source read

On a cache hit, return the saved value. On a miss, read the source of truth and fill the cache. That is cache-aside.

Swipe when you’re ready
One new wrinkle

The copy can outlive the truth.

database: new
cache: old

If the database changes but the cache does not, a fast answer can be stale. Choose expiry, invalidation, or versioned keys deliberately.

Same idea. One more small step.
Try a tiny example

A miss can become a crowd.

many misses
one overloaded source

If many requests miss together, all may hit the database. Single-flight work, jittered expiry, or controlled stale serving can reduce that stampede.

Same idea. One more small step.
Notice what matters

Cache only where the contract permits.

freshness
ownership
cache key

Private responses need correct identity-aware keys and access controls. A TTL is a freshness choice, not a substitute for authorization.

Want to try a tiny question?
No pressure. Just try it.

Does a long TTL guarantee that cached data is correct until it expires?

You can also keep scrolling
1 / 5
High-level design

One small step at a time.

This idea builds on these smaller ones. Pick any to revisit it here.

Start with the questions storage must answer.

read pattern
write pattern
invariant

Which record do we fetch? Which records do we list together? Which changes must succeed together? Those choices shape keys, indexes, and transactions.

1 / 4
A familiar idea

A queue lets work wait.

producer
queue
worker

The API accepts a job and a worker processes it later. Arrival rate and processing rate no longer need to match at every instant.

Swipe when you’re ready
One new wrinkle

Acknowledgment creates a failure window.

effect done
ack lost
retry

A worker may finish its effect, then lose the acknowledgment. The queue can deliver that job again.

Same idea. One more small step.
Try a tiny example

Use stable job identities.

job ID
effect + dedup record

A duplicate-safe consumer recognizes the same logical job. In a real system, recording completion and applying its effect need a shared durable boundary.

Same idea. One more small step.
Notice what matters

Queues do not make overload disappear.

arrival > service
backlog grows

Backlog grows when arrivals exceed service capacity. Bound retries, monitor age, apply backpressure, and route persistent failures for inspection.

Want to try a tiny question?
No pressure. Just try it.

Does acknowledging only after work automatically prevent duplicate effects?

You can also keep scrolling
1 / 5
High-level design

One small step at a time.

This idea builds on these smaller ones. Pick any to revisit it here.

One worker becomes several.

balancer
worker A
worker B

A load balancer chooses a healthy worker for each request. More workers can share traffic, but they need the state required to serve any user.

1 / 3
Let’s picture it

Large bytes and searchable facts have different jobs.

database: metadata
object store: bytes

Store a video as an object. Keep its owner, status, size, and object key in a database that can answer application queries.

Swipe when you’re ready
One little change

Use stable object identities.

object key
specific bytes

A versioned or content-addressed key avoids confusing an old cached object with a replacement. Metadata points to the intended version.

Same idea. One more small step.
Now it has a name

A CDN can serve a nearby copy.

reader
CDN
object origin

Cache suitable bytes near readers. Private assets still need access checks or bounded signed access; public caching rules must not leak private content.

Want to try a tiny question?
No pressure. Just try it.

Does possession of an object hash automatically grant permission to read it?

You can also keep scrolling
1 / 4
High-level design

One small step at a time.

This idea builds on these smaller ones. Pick any to revisit it here.

Start with the questions storage must answer.

read pattern
write pattern
invariant

Which record do we fetch? Which records do we list together? Which changes must succeed together? Those choices shape keys, indexes, and transactions.

1 / 4
A familiar idea

One slow dependency can occupy every worker.

slow dependency
waiting workers
queue grows

Requests keep waiting, new requests pile up, and the caller becomes unhealthy too. Give downstream work a bounded deadline.

Swipe when you’re ready
One new wrinkle

Retries can multiply the pressure.

failure
many retries
more load

Retry only suitable failures, with a bounded budget and jittered backoff. A timed-out write needs idempotency before blindly trying again.

Same idea. One more small step.
Try a tiny example

A circuit can stop repeated calls temporarily.

closed
open
probe

After enough failures, reject quickly for a cooldown. Then permit a controlled probe before trusting the dependency again.

Same idea. One more small step.
Notice what matters

Isolate resources and plan recovery.

isolate
degrade
recover

Separate pools or limits prevent one dependency from consuming everything. Test failover, backups, restoration, and degraded behavior against explicit recovery goals.

Want to try a tiny question?
No pressure. Just try it.

Should every layer independently retry an operation three times without a shared budget?

You can also keep scrolling
1 / 5
High-level design

One small step at a time.

This idea builds on these smaller ones. Pick any to revisit it here.

A queue lets work wait.

producer
queue
worker

The API accepts a job and a worker processes it later. Arrival rate and processing rate no longer need to match at every instant.

1 / 4
A familiar idea

“The latest value” needs a precise promise.

write: version 7
read: version 6

One user writes a note, then reads an older replica. Eventual convergence and read-your-writes are different guarantees.

Swipe when you’re ready
One new wrinkle

A partition separates communication, not intent.

side A
network split
side B

If two sides cannot communicate, an operation may have to wait or fail to preserve a single up-to-date view. Accepting everywhere can require weaker consistency.

Same idea. One more small step.
Try a tiny example

CAP is about behavior during that split.

during partition
operation-specific choice

It does not mean “pick any two” for every normal request. State which operations favor availability and which must preserve stronger consistency.

Same idea. One more small step.
Notice what matters

A version can expose what the reader needs.

required version
replica version
serve only if ready

A read-your-writes token can require at least the version the client already observed. A lagging replica must wait, reroute, or reject.

Want to try a tiny question?
No pressure. Just try it.

Does eventual consistency alone guarantee that your next read sees your own last write?

You can also keep scrolling
1 / 5
High-level design

One small step at a time.

This idea builds on these smaller ones. Pick any to revisit it here.

A saved value can have several copies.

leader: new
replica: old

A leader accepts a write and replicas receive it. If copying is asynchronous, a replica may temporarily show the old value.

1 / 4
A familiar idea

A database write and an event must agree.

save order
crash gap
publish event

Saving an order then publishing its event leaves a gap: a crash between the two can save the order without notifying anyone.

Swipe when you’re ready
One new wrinkle

Put the event beside the change.

state change
outbox row
one commit

Write business state and an outbox row in one database transaction. Either both commit or neither does.

Same idea. One more small step.
Try a tiny example

Publish the outbox after commit.

relay sends
ack uncertain
may resend

A relay reads pending rows and sends them. It can crash after sending but before marking sent, so duplicates remain possible.

Same idea. One more small step.
Notice what matters

Pair atomic intent with duplicate-safe consumers.

durable intent
idempotent handling

The outbox prevents lost publication intent. It does not make arbitrary downstream effects exactly once.

Want to try a tiny question?
No pressure. Just try it.

Does an outbox remove every possibility of duplicate event delivery?

You can also keep scrolling
1 / 5
High-level design

One small step at a time.

This idea builds on these smaller ones. Pick any to revisit it here.

Start with the questions storage must answer.

read pattern
write pattern
invariant

Which record do we fetch? Which records do we list together? Which changes must succeed together? Those choices shape keys, indexes, and transactions.

1 / 4
Let’s picture it

A workflow crosses several owners.

inventory
payment
shipping

Reserve inventory, authorize payment, then arrange shipping. Each service can commit locally, but there is no single simple rollback across them.

Swipe when you’re ready
One little change

A later failure needs a business response.

failure
compensate earlier steps

If shipping fails, release inventory and void or refund payment according to their contracts. Those are new actions, not erased history.

Same idea. One more small step.
Now it has a name

Compensations can fail too.

durable workflow
retry
reconcile

Store workflow state, retry safely, and make unresolved cases visible. A saga does not make intermediate states invisible to everyone.

Want to try a tiny question?
No pressure. Just try it.

Is compensation identical to rolling back an uncommitted database transaction?

You can also keep scrolling
1 / 4
High-level design

One small step at a time.

This idea builds on these smaller ones. Pick any to revisit it here.

A database write and an event must agree.

save order
crash gap
publish event

Saving an order then publishing its event leaves a gap: a crash between the two can save the order without notifying anyone.

1 / 4
Let’s picture it

Give a caller a refillable budget.

capacity: 3
request: −1
refill over time

A bucket holds at most three tokens. Each request spends one. Tokens refill over time, allowing short bursts but limiting sustained traffic.

Swipe when you’re ready
One little change

Refill only up to capacity.

old tokens + refill
cap at capacity

Unused time should not build unlimited burst credit. Add elapsed-time tokens, then cap the result.

Same idea. One more small step.
Now it has a name

Shared enforcement needs shared state.

server A bucket
server B bucket
global limit?

A separate full bucket on every server multiplies the effective allowance. Decide whether the limit is local, per-user global, or approximate.

Want to try a tiny question?
No pressure. Just try it.

Do three independent capacity-ten buckets enforce one global burst limit of ten?

You can also keep scrolling
1 / 4
High-level design

One small step at a time.

This idea builds on these smaller ones. Pick any to revisit it here.

One slow dependency can occupy every worker.

slow dependency
waiting workers
queue grows

Requests keep waiting, new requests pile up, and the caller becomes unhealthy too. Give downstream work a bounded deadline.

1 / 4
A familiar idea

Measure the promise the user experiences.

traffic
errors
latency
saturation

A successful API call is not enough if it arrives too late. Track request rate, errors, latency distributions, and resource saturation.

Swipe when you’re ready
One new wrinkle

Averages hide the slow tail.

9 fast
1 very slow

Nine requests take 10 milliseconds; one takes 1000. The average does not describe the experience of that slow request.

Same idea. One more small step.
Try a tiny example

Use different signals for different questions.

metrics
logs
traces

Metrics show trends. Logs record selected events. Traces connect spans across a request. Correlate them without leaking secrets or exploding label cardinality.

Same idea. One more small step.
Notice what matters

An error budget makes the target actionable.

10,000 requests
10 failures allowed

For a 99.9% success objective over 10,000 eligible requests, ten failures consume the whole request-based budget.

Want to try a tiny question?
No pressure. Just try it.

Can an average latency show how bad the slowest one percent feels?

You can also keep scrolling
1 / 5
High-level design

One small step at a time.

This idea builds on these smaller ones. Pick any to revisit it here.

Start with what people need to do.

save
read
keep data

A note app must save a note and read it later. Before choosing databases, ask how many people use it and what failures are acceptable.

1 / 4
A familiar idea

Knowing who called is only the first check.

who are you?
may you read this note?

Authentication identifies a principal. Authorization asks whether that principal may perform this operation on this particular object.

Swipe when you’re ready
One new wrinkle

Do not trust ownership supplied by the client.

trusted identity
stored policy
decision

Load the stored object and compare its actual owner or policy with the trusted principal. A request saying owner=me proves nothing.

Same idea. One more small step.
Try a tiny example

Protect the rest of the boundary too.

transport
permissions
data handling

Use TLS, managed secrets, bounded inputs, safe queries, abuse controls, and minimal data exposure. Avoid inventing custom cryptography or logging credentials.

Same idea. One more small step.
Notice what matters

Treat private links as capabilities.

scoped access
limited lifetime

Signed access should be narrowly scoped and expire. Leaking a valid bearer link can let another person use it during its lifetime.

Want to try a tiny question?
No pressure. Just try it.

Does a valid login automatically authorize reading any record ID?

You can also keep scrolling
1 / 5
High-level design

One small step at a time.

This idea builds on these smaller ones. Pick any to revisit it here.

Make one operation’s promise explicit.

request
validated operation
response

Define its resource, input, validation, response, and errors. For writes, also define what a repeated request means.

1 / 3
A familiar idea

A rate and a duration reveal work in flight.

100 / second
× 0.2 seconds
20 in flight

At 100 requests per second and 0.2 seconds average service time, about 20 requests are active in a stable system.

Swipe when you’re ready
One new wrinkle

Leave room for bursts and failures.

steady work
headroom
failure reserve

Sizing every worker at full utilization leaves no room for uneven load or one failed worker. Headroom is an explicit assumption, not free capacity.

Same idea. One more small step.
Try a tiny example

Storage is more than record count.

bytes × retention
replicas + indexes
hot key

Estimate bytes per write, retention, replication, indexes, and overhead. Also estimate read bandwidth and the hottest key, not only total requests.

Same idea. One more small step.
Notice what matters

Check estimates with measurements.

estimate
load-test
revise

Little’s Law describes stable averages. It does not promise tail latency during overload or predict how every implementation scales.

Want to try a tiny question?
No pressure. Just try it.

Does average concurrency alone guarantee a p99 latency target?

You can also keep scrolling
1 / 5
High-level design

One small step at a time.

This idea builds on these smaller ones. Pick any to revisit it here.

One worker becomes several.

balancer
worker A
worker B

A load balancer chooses a healthy worker for each request. More workers can share traffic, but they need the state required to serve any user.

1 / 3
A familiar idea

A short code is a lookup key.

short code
destination URL

Creating a link stores code → destination. Opening it reads that mapping and returns a redirect. Reads may greatly outnumber creates.

Swipe when you’re ready
One new wrinkle

Give creation one durable uniqueness boundary.

allocate ID
encode
unique stored mapping

A unique allocator or collision-checked random code creates the key. Encoding a counter in base 62 makes it shorter, not secret.

Same idea. One more small step.
Try a tiny example

Put a cache on the repeated read path.

reader
cache
mapping store

Redirects can look up popular codes nearby. Updates, expiry, or abuse blocking need an invalidation and freshness policy.

Same idea. One more small step.
Notice what matters

Keep the hard questions visible.

uniqueness
expiry
abuse
analytics

Define custom aliases, expiration, redirect mutability, analytics, and malicious-link handling. Each changes the write and read contracts.

Want to try a tiny question?
No pressure. Just try it.

Does base-62 encoding turn a sequential ID into an unguessable secret?

You can also keep scrolling
1 / 5
High-level design

One small step at a time.

This idea builds on these smaller ones. Pick any to revisit it here.

Start with the questions storage must answer.

read pattern
write pattern
invariant

Which record do we fetch? Which records do we list together? Which changes must succeed together? Those choices shape keys, indexes, and transactions.

1 / 4
A familiar idea

Choose when to assemble the timeline.

push on write
pull on read

When someone posts, push its ID into followers’ inboxes—or wait until a follower reads and merge followed authors’ posts.

Swipe when you’re ready
One new wrinkle

A celebrity makes the difference visible.

10 followers
millions of followers

Pushing one post to ten followers is small. Pushing to millions creates a large fan-out burst. Pulling shifts that work toward readers.

Same idea. One more small step.
Try a tiny example

A hybrid can give different authors different paths.

stored inbox
pulled authors
merged feed

Push ordinary authors’ posts. Pull high-fan-out authors at read time, then merge candidates into one ordered page.

Same idea. One more small step.
Notice what matters

Ordering is not the whole product.

ranking
privacy
freshness

Ranking, privacy, deletions, blocked users, duplicates, and fresh pagination all need contracts. A cached post ID must not bypass current access rules.

Want to try a tiny question?
No pressure. Just try it.

Is fan-out-on-write always the best choice regardless of follower count?

You can also keep scrolling
1 / 5
High-level design

One small step at a time.

This idea builds on these smaller ones. Pick any to revisit it here.

A queue lets work wait.

producer
queue
worker

The API accepts a job and a worker processes it later. Arrival rate and processing rate no longer need to match at every instant.

1 / 4
A familiar idea

A live connection is not message durability.

live delivery
durable history

A WebSocket can carry a message quickly, but the message must be stored and identified if clients should recover it after disconnecting.

Swipe when you’re ready
One new wrinkle

Order messages within a conversation.

conversation
sequence 1, 2, 3

Assign a server-side sequence through one coordinated conversation write boundary. Wall-clock timestamps alone can tie or disagree across clients.

Same idea. One more small step.
Try a tiny example

A retry should reuse the same message identity.

client ID
retry
same committed message

The client sends a stable request ID. A repeated send returns the earlier committed sequence rather than appending a second message.

Same idea. One more small step.
Notice what matters

Reconnect from a known position.

last sequence
fetch gap
resume live

The client asks for messages after its last received sequence. Delivery acknowledgments and read receipts are separate from durable acceptance.

Want to try a tiny question?
No pressure. Just try it.

Does successfully writing to a WebSocket prove the recipient stored or read the message?

You can also keep scrolling
1 / 5
High-level design

One small step at a time.

This idea builds on these smaller ones. Pick any to revisit it here.

A queue lets work wait.

producer
queue
worker

The API accepts a job and a worker processes it later. Arrival rate and processing rate no longer need to match at every instant.

1 / 4
A familiar idea

Let large bytes bypass the application worker.

client
object storage
metadata service

The app creates an authorized upload session. The client sends parts directly to object storage using narrowly scoped access.

Swipe when you’re ready
One new wrinkle

A part can be retried independently.

part 1 ✓
part 2 retry
part 3 ✓

Part numbers and checksums identify progress. Retrying one failed part should not require resending the whole file.

Same idea. One more small step.
Try a tiny example

Completion is a checked transition.

uploading
verify
ready

Verify all required parts and integrity before marking metadata ready. Uploading bytes and publishing a usable file are different states.

Same idea. One more small step.
Notice what matters

Clean up both kinds of leftovers.

expired session
orphaned bytes
access checks

Expired sessions, incomplete parts, and objects without committed metadata need bounded cleanup. Private downloads still require authorization.

Want to try a tiny question?
No pressure. Just try it.

Should a file appear ready merely because an upload session was created?

You can also keep scrolling
1 / 5
High-level design

One small step at a time.

This idea builds on these smaller ones. Pick any to revisit it here.

Large bytes and searchable facts have different jobs.

database: metadata
object store: bytes

Store a video as an object. Keep its owner, status, size, and object key in a database that can answer application queries.

1 / 3
A familiar idea

One event may need several delivery channels.

event
email
push

A saved reminder might become email, push, or both. Preferences and channel capabilities decide which jobs should exist.

Swipe when you’re ready
One new wrinkle

Give each intended delivery its own identity.

event ID
recipient
channel

Use event, recipient, and channel together. Retrying email should not accidentally suppress an independent push notification.

Same idea. One more small step.
Try a tiny example

Providers have limits and uncertain outcomes.

queue
provider
acceptance uncertain

Queue work by channel, pace calls, retry suitable failures, and record provider responses. A timeout may occur after the provider accepted the message.

Same idea. One more small step.
Notice what matters

Recheck preferences at the right boundary.

queued earlier
preference changed
check before send

A user may unsubscribe while a job waits. Define which notifications remain permitted and check before attempting delivery.

Want to try a tiny question?
No pressure. Just try it.

Does one dedup key per event distinguish email from push for two different users?

You can also keep scrolling
1 / 5
High-level design

One small step at a time.

This idea builds on these smaller ones. Pick any to revisit it here.

A queue lets work wait.

producer
queue
worker

The API accepts a job and a worker processes it later. Arrival rate and processing rate no longer need to match at every instant.

1 / 4
A familiar idea

Search needs a different view of the same documents.

token
matching document IDs

A primary store keeps documents. An inverted index maps each token to documents containing it, making token lookup efficient.

Swipe when you’re ready
One new wrinkle

The index is derived data.

source update
index event
new postings

Document changes must update postings and remove old terms. A delayed indexing worker can make search temporarily stale.

Same idea. One more small step.
Try a tiny example

Autocomplete and full search share pieces, not objectives.

prefix suggestions
document ranking

A trie or prefix index suggests beginnings. Full search also needs tokenization, matching, ranking, and result permissions.

Same idea. One more small step.
Notice what matters

Authorization still applies to results.

index candidates
permission check
results

A stale index must not reveal a document the user may no longer read. Filter with a trusted visibility policy at serving time.

Want to try a tiny question?
No pressure. Just try it.

Does updating the source document automatically remove its old search terms?

You can also keep scrolling
1 / 5
High-level design

One small step at a time.

This idea builds on these smaller ones. Pick any to revisit it here.

Car and cat start the same way.

c
a
r / t

Write c, then a, just once. Split where the words become different.

1 / 3
A familiar idea

A crawler has a frontier, not just a loop.

discovered URLs
frontier
fetch when allowed

Discovered URLs wait for permission and scheduling. A seen set prevents repeatedly adding the same canonical URL.

Swipe when you’re ready
One new wrinkle

Be polite per host, not only globally.

host A: wait
host B: ready

Two URLs on one host may need spacing, while another host can be served independently. Keep a next-allowed time per host.

Same idea. One more small step.
Try a tiny example

Permission and safety are separate checks.

policy
network safety
resource bounds

Honor applicable robots rules and access policies. Also prevent fetches into private networks, unsafe redirects, or unexpectedly large responses.

Same idea. One more small step.
Notice what matters

Bound discovery and retries.

scope
depth
bytes
retries

Pages can link forever or generate endless URL variations. Set crawl scope, depth, byte budgets, timeouts, and retry limits.

Want to try a tiny question?
No pressure. Just try it.

Does one global requests-per-second limit guarantee polite spacing for each host?

You can also keep scrolling
1 / 5
High-level design

One small step at a time.

This idea builds on these smaller ones. Pick any to revisit it here.

A queue lets work wait.

producer
queue
worker

The API accepts a job and a worker processes it later. Arrival rate and processing rate no longer need to match at every instant.

1 / 4
A familiar idea

Count events by when they happened.

event time
arrival time

An event created at second 12 may arrive after one created at second 18. Arrival order and event time are different.

Swipe when you’re ready
One new wrinkle

Deduplicate before increasing a count.

same event ID
one contribution

A queue may repeat an event. A stable event ID prevents one logical action from incrementing the same aggregate twice.

Same idea. One more small step.
Try a tiny example

Choose how long late data may revise results.

on-time
allowed late
too late

A watermark is an explicit progress assumption. Events older than the accepted lateness boundary may be dropped or handled through a correction path.

Same idea. One more small step.
Notice what matters

A displayed count may still be provisional.

provisional window
finalized or corrected

Partitioning, delayed events, and recovery affect freshness. Define when a window is final and how corrections reach readers.

Want to try a tiny question?
No pressure. Just try it.

Does processing arrival order automatically preserve the time when events actually occurred?

You can also keep scrolling
1 / 5
High-level design

One small step at a time.

This idea builds on these smaller ones. Pick any to revisit it here.

A queue lets work wait.

producer
queue
worker

The API accepts a job and a worker processes it later. Arrival rate and processing rate no longer need to match at every instant.

1 / 4
A familiar idea

Explain one ordinary write first.

accept
validate
commit
confirm

Who accepts it, who validates it, where does it commit, and what confirms success? A missing answer often reveals an unclear ownership boundary.

Swipe when you’re ready
One new wrinkle

Then follow one read.

source or cache?
fresh enough?
authorized?

Which copy answers, how stale may it be, and who checks permission? Faster reads are useful only if their contract remains correct.

Same idea. One more small step.
Try a tiny example

Now lose one response.

effect maybe done
retry
safe outcome?

Ask what a retry does after the first attempt may already have succeeded. This exposes missing identity and transaction rules.

Same idea. One more small step.
Notice what matters

Name the tradeoff you chose.

requirements
chosen boundary
known limitation

A good design is not the one with the most boxes. It explains why its assumptions, costs, and failure behavior fit this workload.

Want to try a tiny question?
No pressure. Just try it.

Does drawing more services by itself make a design stronger?

You can also keep scrolling
1 / 5
High-level design

One small step at a time.

This idea builds on these smaller ones. Pick any to revisit it here.

A short code is a lookup key.

short code
destination URL

Creating a link stores code → destination. Opening it reads that mapping and returns a redirect. Reads may greatly outnumber creates.

1 / 4
You've reached the end of these ideas.Try them without the labels