Scout — Full Product Context → feature documentation

Nearby patch alerts

A once-a-day banner when you arrive somewhere new and a patch you don't have is within about 5 miles: "Your next patch is 2 mi away".

Summary

When you arrive somewhere new (you travelled at least 2 km, then stayed in one spot for a couple of minutes — not a red light, not driving past) and a patch you don't have yet is within about 5 miles, Scout shows one banner: "Your next patch is 2 mi away", the patch's name underneath, and its art on the right (iOS). A tap opens that patch, or Near me when several are close. At most once a day, never at night, and never about the same patch twice.

It is a local notification decided on the phone, like the unlock banner: nothing is pushed from a server. Built 2026-11-04 to give people a reason to open Scout while they are out (the analytics read that day: 88% of installs finish onboarding, only 48% come back on a later day).

Status

User-facing surfaces

How it works

  1. Every background fix. The background location task (mobile/src/services/location/tracker.ts:143) hands every fix of each batch, with its timestamp, to runNearbyPass.
  2. The arrival detector (arrivalStep, nearbyAlert.ts:62), its memory kept between wakes in MMKV (scout-nearby-alerts):
    • the anchor is the last place you settled (the first fix ever, then each arrival);
    • a fix worse than 100 m (a cell-tower jump) or with no usable time is ignored;
    • a fix at driving speed (over 3 m/s) ends any stay — stop-and-go traffic never settles;
    • a stay starts at a fix and lasts while later fixes stay within 250 m;
    • a stay of 2 minutes or more over at least 3 fixes, at least 2 km (ARRIVAL_TRAVEL_KM) from the anchor, is settling somewhere: the new anchor. (A stopped car gives one fix at the stop and the next as it pulls away, so even a long red light never reaches 3);
    • it is an arrival only if it is new: not within 2 km of one of the last 20 places you settled, so home and work stop counting after the first time.
  3. The guards (runNearbyPass): the switch is on; the app is not open (AppState active — Near me already shows it); no Just drive trip is live (its own "patch ahead" alert covers the road, services/nearbyAlerts.ts:94); not 21:00–08:00 local and not already today (mayAlertAt, nearbyAlert.ts:125); the OS already allows notifications (osAllowsLocalNotifications, mobile/src/services/localNotify.ts — it never prompts); the account's patches have loaded (a cold background wake before they have would not know which you hold, so it holds).
  4. The pick (pickNearby, nearbyAlert.ts:98): from the tracker's uncollected list, minus any patch you hold (the list keeps a live trip's stops even when collected, so they are dropped again, nearbyAlerts.ts:98), minus cities, states, regions and airports (isSuggestable: you are inside a city when you arrive, and it unlocks), minus every patch already alerted about: the closest within 5 miles straight line (NEARBY_RADIUS_MI).
  5. The banner (trigger: null, data { type: 'nearby_patch', patchId, others }), then the day and the patch are remembered (the newest 500 patches) and nearby_alert_sent is logged (distance to 0.1 mi, the count close by, whether the art attached — never where).

Data model

None on the server. On the phone: MMKV scout-nearby-alerts (the detector's anchor, current stay, recent places, the last alert's day, the alerted patch ids) and the store switch nearbyAlertsEnabled (persisted, default true, mobile/src/domain/store.ts:1639).

The MMKV memory belongs to whoever is signed in: signing out, or signing in to a different existing account, clears it (resetNearbyState, mobile/src/providers/AuthProvider.tsx), so the next person on the phone neither inherits the day's alert nor the list of patches already named.

API surface

None.

Key files

Configuration and flags

No flag. The device switch nearbyAlertsEnabled (default on). The constants (5 mi, 2 km, 250 m, 2 min, once a day, 21:00–08:00) are in nearbyAlert.ts.

Edge cases and known limits

What this feature does NOT do

Tests that cover it

Open questions