How food delivery apps track riders in real time, estimate arrival times accurately, and keep live location updates buttery-smooth — all while going easy on battery and network.
Every time you order food and watch a little scooter icon glide across the map towards you, a surprisingly deep piece of engineering is running quietly underneath.
In plain terms: the app has to always know where the rider is, turn that into a smooth-looking dot on your screen instead of a jumpy one, and keep re-guessing when your food will actually arrive — all without murdering the rider's phone battery over an 8-hour shift.
Think of it like this: the rider's phone is a runner in a relay race, constantly passing a baton (their location) to the next teammate, until it lands perfectly in your hand as a moving dot on your screen — usually in under two seconds.
Rider tracking has to satisfy several competing constraints simultaneously:
Customers expect the rider's position to feel "live," updating every few seconds.
Hundreds of thousands of riders can be actively delivering at once, all streaming updates.
Raw GPS is noisy; a stationary rider can appear to "jump" between nearby streets.
Riders are on the road for hours — tracking can't drain their battery or data plan.
A location change has to reach exactly the right customer's app within a second or two.
The system is a pipeline: location is captured on the rider's device, streamed through an ingestion layer, processed and stored centrally, and pushed back out to exactly the customers who need it.
Captures GPS/network location, batches pings, and adapts sampling rate based on movement, battery, and connectivity.
In shortThe rider's phone quietly checks "where am I?" every few seconds and gets ready to report it.
Lightweight WebSocket/MQTT edge servers accept high-frequency location pings from millions of riders concurrently.
In shortA front door that listens for location updates from every rider on the road, all at the same time.
Buffers and fans out location events to downstream consumers — storage, ETA engine, and live tracking service.
In shortA conveyor belt that carries each location update to everyone who needs to see it, in order.
Redis Geo / H3 keeps the latest rider location indexed for fast proximity queries and instant retrieval by order ID.
In shortA live whiteboard holding everyone's current position, so any order can be looked up instantly.
Combines current location, route graph, historical speed data, and live traffic to recompute arrival estimates.
In shortThe calculator that keeps re-guessing "how long until they arrive?" as things change.
Pushes location + ETA updates to the exact customer app instance tracking that specific order, via WebSocket/SSE.
In shortThe delivery boy for updates — it hands the new position straight to your phone screen.
The rider's app reads GPS coordinates and, where GPS is weak (indoors, tunnels, urban canyons), fuses in network-based and sensor-based location for a more reliable fix.
In shortLike checking a compass — but with backups for when the signal gets foggy.
Instead of streaming every point instantly, the app batches a few points together and sends them every 3–5 seconds while moving — cutting radio wake-ups dramatically.
In shortInstead of texting every second, it groups a few updates and sends them together.
The gateway authenticates the session, validates coordinates (rejecting GPS jumps), and stamps each ping with a server-side timestamp.
In shortA bouncer checks the update is real and not some glitchy, impossible jump.
Kafka topics partitioned by rider/order ID let the geospatial store, ETA engine, and analytics pipeline process the same event in parallel.
In shortOne update, many readers — everyone who needs it gets a copy at once.
The ETA service snaps the rider to the road network, calculates remaining distance, and blends in live traffic for a fresh estimate.
In shortThe "how long left?" number gets quietly recalculated in the background.
The update is published to a pub/sub channel keyed by order ID — the customer's app renders it within a second or two.
In shortThe moving dot on your screen updates — usually before you even notice the lag.
This is where rider-tracking design diverges most from a generic real-time app. Riders keep the app open for entire shifts, so every unnecessary GPS read or network call adds up fast.
Interval scales with speed and movement — frequent while riding, rare when stopped — cutting battery drain and network chatter.
In shortTalks often while moving, goes quiet while parked — like a person, not a machine.
OS-level significant-location-change APIs wake the app only when the rider actually moves a meaningful distance.
In shortThe phone naps until you actually move somewhere, instead of staying wide awake.
Multiple points bundle into one compact binary payload rather than one message per point.
In shortSends one small parcel instead of many tiny letters — cheaper postage, same info.
A single long-lived socket avoids repeated, expensive TLS/TCP handshakes per update.
In shortKeeps one phone line open for the whole trip instead of redialing every time.
Raw points snap onto the road graph and interpolate between updates, so fewer points still look smooth on screen.
In shortThe server fills in the gaps so the dot glides instead of jumping.
Clients receive only what changed — new coordinate + ETA delta — not a full state payload every time.
In shortOnly sends what's new, not the whole story every single time.
The simplest way to guess an ETA is: distance left ÷ how fast you're going. That's what a basic maps app might do — and it falls apart the instant there's a red light, a crowded street, or a turn to make. Here's how a rough guess compares to what production systems actually do:
With hundreds of thousands of riders active at once, two parts of the system take the most strain: the front door that receives every ping, and the delivery layer that pushes updates back out. Here's how they stay standing under load:
| Layer | Common Choices |
|---|---|
| Mobile SDK | Fused Location Provider (Android), Core Location (iOS) |
| Transport | MQTT or WebSocket over TLS for persistent connections |
| Streaming Backbone | Apache Kafka / Pulsar for durable, partitioned fan-out |
| Geospatial Storage | Redis Geo, Uber's H3 hex index, or PostGIS |
| ETA Engine | Road graph (OSRM/Valhalla style) + ML on historical trips |
| Real-Time Push | Pub/Sub fanning into WebSocket/SSE gateways per session |
Rider tracking looks simple on the surface — a dot moving on a map — but it's really a real-time, geospatially-aware distributed system balancing freshness, accuracy, scale, and device efficiency all at once.
A quick, no-nonsense translation of the technical terms used above — for anyone who isn't an engineer (or just wants a refresher).
One "here's where I am" message sent from the rider's phone.
A phone-line-like connection that stays open, so updates travel instantly without hanging up and redialing.
A high-speed conveyor belt for data — events go in at one end and multiple systems can grab a copy at the other.
A map-shaped filing cabinet — built to answer "what's near this point?" almost instantly.
Estimated Time of Arrival — the app's best current guess at when the rider will show up.
Safe to repeat — doing it twice by accident causes no harm, like pressing an elevator button that's already lit.
"Publish/Subscribe" — one sender broadcasts an update, and everyone who's interested automatically receives it.
Nudging a slightly-off GPS point onto the actual street it's on, so the dot doesn't appear to float through buildings.