Architecture
System context
Container diagram
Key modules
Backend (app/)
| Module | Path | Responsibility |
|---|---|---|
| App factory | app/factory.py | App assembly — routers, static files, startup lifespan |
| Aggregate router | app/api/routes/grass.py | Mounts all sub-routers under /grass |
| Environment registry | app/services/env_registry.py | GRASS environment lifecycle, Redis sync, disk persistence |
| GRASS runtime | app/services/grass_runtime.py | Async subprocess execution, mapset locking |
| Routing client | app/services/routing/client.py | Valhalla HTTP proxy |
| Curvature service | app/services/curvature/ | road_db.py query, pop_density.py grid lookup, kmz_ingest.py pipeline |
| Terrain builder | app/services/terrain_builder.py | Quantized-mesh tile generation via mago-3d-terrainer |
| WFS service | app/wfs_service.py | MapServer WFS integration + vector info cache |
| POI database | app/db/osm_poi.py | PostGIS POI query helpers |
| Route storage | app/db/routes.py | PostGIS route CRUD, GPX/GeoJSON export |
| Schema migration | app/db/migrate.py | ensure_schema() at startup — routes + osm_poi tables |
| Auth | app/auth/ | API key issuance, X-API-Key validation, web session middleware |
Route modules (all mounted at /grass/…)
| File | Prefix | Purpose |
|---|---|---|
environments.py | /grass/env | Create / list / delete GRASS environments |
layers.py | /grass/env/{id}/layers | Layer metadata and WMS/WFS layer management |
profile.py | /grass/env/{id}/profile | r.profile transect execution |
histogram.py | /grass/env/{id}/histogram | r.stats histogram execution |
analysis_artifacts.py | /grass/artifacts | Save / load / delete profile+histogram results |
terrain.py | /grass/env/{id}/terrain | Terrain build + list + delete |
vector_edit.py | /grass/env/{id}/vedit | Vector digitise, move, attribute write |
db_manager.py | /grass/env/{id}/db | SQLite + PostgreSQL table inspection |
routing.py | /grass/routing | Valhalla route, isochrone, matrix, loop, speed cameras, POI |
routes_manager.py | /grass/routing/routes | Save / load / delete / export routes |
location.py | /grass/routing/location | Live group position sharing |
curvature.py | /grass/curvature | Curvy-road DB query and precomputed analysis |
elevation.py | /grass/elevation/sample | GRASS-free elevation sampling along any polyline — best national DEM auto-selected, OpenTopoData fallback |
field_sessions.py | /grass/env/{id}/field-sessions | Mobile field session registry (Redis-backed) |
data_packs.py | /grass/data-packs | Region management + background rebuild jobs |
tiles.py | /grass/tiles | 1°×1° SQLite tile catalog + download |
Frontend (app/static/grass_runner/js/)
| Module | Responsibility |
|---|---|
main.js | Entry point — wires toolbar, panels, tool modules |
state.js | Shared reactive state (connection, env, active module) |
cesium-layers.js | Layer registry, WMS/WFS add/remove, drag-and-drop order |
session-state.js | Collect / restore full app state |
session-ui.js | Named workspace save/load UI |
profile-tool.js | Profile line drawing and r.profile execution |
histogram-tool.js | Bounding-box drawing and r.stats execution |
vector-edit.js | Vector digitise, move, vertex edit, attribute write |
db-manager.js | DB Manager UI (SQLite + PostgreSQL inspection) |
picker.js | r.what / v.what identify tool, cluster interaction |
region.js / region-draw.js | Computational region management |
Mobile app (mobile-app/)
| Path | Responsibility |
|---|---|
app/(tabs)/navigate.tsx | Navigation/map screen — routing, POI, curvy-road discovery, offline packs |
app/(tabs)/capture.tsx | Field capture screen — GPS track, samples, sync |
app/(tabs)/profile.tsx | Elevation profile tab — GRASS r.profile transect tool wired to stores |
app/(tabs)/more.tsx | Settings, connection, environment management, analyses viewer |
src/stores/ | Zustand stores: connection, environment, location, profile, field-capture, tile-packs, settings |
src/modules/navigation/ | Sheets: plan-route, loop-route, curvy-roads (inline elevation charts), offline-packs |
src/modules/profile/ | ProfilePanels, ProfileChart (Skia), profileStore, useElevationProfile hook |
src/modules/field-capture/ | Session management, sync handlers, pull service |
src/modules/map/ | MapLibre layer model, FieldCaptureMap, FieldMapPanel |
src/lib/fastgis-client.ts | HTTP API client — all backend endpoints including elevation sampling |
src/lib/tileGrid.ts | 1°×1° tile math: coordinate → tile ID, bbox, routeToTileIds |
src/lib/curvatureDb.ts | Offline curvature queries — tiled and monolithic SQLite |
src/lib/poiDb.ts | Offline POI queries — tiled SQLite |
src/lib/resetAppData.ts | Wipe all cached offline data (tiles, curvature DB, cached routes) keeping credentials and user data |