Components/Location Mismatch
Location Mismatch
Geo-anomaly card for impossible-travel detection. Shows the two locations side-by-side and computes the required travel speed automatically. Flags the event as "Impossible travel" when sustained speed exceeds 1000 km/h — the threshold used by Microsoft, AWS GuardDuty, and Cloudflare Zero Trust.
Expected
São Paulo
Brazil
-23.55, -46.63
Detected
Tokyo
Japan
35.68, 139.69
- Distance
- 18,550 km
- Elapsed
- 45min
- Required speed
- 24,733 km/h
Installation
npx ajaxui add location-mismatchPlausible travel
When the required speed is plausible (e.g. by car, train, or short-haul flight), the card switches to a warning tone instead of critical.
Expected
São Paulo
Brazil
Detected
Rio de Janeiro
Brazil
- Distance
- 430 km
- Elapsed
- 3h
- Required speed
- 143 km/h
Manual flag
Force the impossible-travel state via isImpossibleTravel when your risk engine has additional signals the automatic threshold doesn't see.
Expected
Lisbon
Portugal
Detected
Buenos Aires
Argentina
- Distance
- 9,870 km
- Elapsed
- 12h
- Required speed
- 823 km/h
Geo point shape
interface GeoPoint {
city: string
country: string
coordinates?: [number, number] // [lat, lon] — optional; for future map integrations
}Props
| Prop | Type | Default | Description |
|---|---|---|---|
| expected | GeoPoint | — | Where we expected the user to be. |
| detected | GeoPoint | — | Where the new event came from. |
| distanceKm | number | — | Great-circle distance in km. |
| elapsedSeconds | number | — | Time between expected and detected events. |
| detectedAt | Date | — | Timestamp of the detected event. |
| isImpossibleTravel | boolean | auto | Override the automatic >1000 km/h threshold. |
| locale | string | "en-US" | Locale for distance + date formatting. |
| onAccept | () => void | — | User says "it was me". |
| onReject | () => void | — | User says "not me" — escalates. |
| acceptLabel | string | "It was me" | Override accept button label. |
| rejectLabel | string | "Not me" | Override reject button label. |