Globe Satellites
An interactive 3D globe showing the live position of active satellites in Earth orbit, built to run on a Raspberry Pi.
- year
- 2026
- role
- Full-stack design and development
- status
- Live
- front
- Vue 3, Globe.gl
- back
- FastAPI, Python, WebSocket

Context
The project
Several thousand active satellites circle above our heads, and their orbits are public. Celestrak publishes orbital elements in the TLE format (Two-Line Element), which is enough to compute the position of any object at any instant.
Globe Satellites shows that ballet on a 3D globe, refreshed every sixty seconds.
Features
- Filtering by category — starlink, oneweb, communications, navigation, stations, weather, Earth observation, science, other — clickable in the HUD, with "Show all" / "Hide all" buttons
- Hover tooltip — name, altitude and category for each satellite
- Logarithmic radial scale — visibly separates low, medium and geostationary orbits instead of stacking them on top of each other
- Automatic WebSocket reconnection (exponential backoff), with a watchdog that catches a frozen connection with no clean TCP close
Computing on the server
The structural choice is to compute server-side. SGP4 orbital propagation
for several thousand objects, once a minute, is not work for the browser — all
the more so since every connected client shares exactly the same result. The
server computes once (SatrecArray + NumPy, a single vectorised call rather
than a Python loop — roughly 24x faster), broadcasts to everyone over WebSocket
in parallel, and the client only renders.
Network resilience
TLEs lose accuracy as the days pass — propagating from week-old elements drifts
noticeably — hence an automatic refresh every two hours. Loading follows a
three-tier chain: the full Celestrak group first, a fallback to 37 groups
downloaded in parallel if that fails or returns a 403, then a backup proxy if
both fail — a sign of a network block rather than an isolated incident. It
returns to the direct route on its own, with no manual action. Data freshness is
exposed through a /health endpoint, which pushes best-effort
Vigie monitoring for the refresh cycle.
The hardware constraint
The project is built for a Raspberry Pi 4 on ARM64. That constraint drove
several decisions: a multi-architecture Docker image, vectorised NumPy
computation rather than a Python loop, a single Three.js InstancedMesh rather
than one object per satellite, and broadcasting one shared state rather than
computing per connected client.
Architecture
01 · Sources
TLEs refreshed every 2h from Celestrak, with automatic failover to a backup proxy when the network blocks them.
02 · Compute
Vectorised SGP4 propagation (SatrecArray + NumPy) with Skyfield — every satellite recomputed in a single call every 60 seconds.
03 · Delivery
One shared computation broadcast over WebSocket to every connected client, in parallel.
04 · Rendering
3D globe (Globe.gl / Three.js), a single InstancedMesh for all satellites, ARM64 Docker image on a Raspberry Pi 4.
Next project
Catan