Case study | TrailKit — Trail Running Ecuador
Building a trustworthy geospatial publishing system for trail running.
TrailKit is a local-first content production and publishing platform that transforms GPX tracks, route metadata, race records, activity history, and field media into reviewed, privacy-safe public experiences for Trail Running Ecuador. The central challenge was never rendering a map — it was building a publishing workflow you can trust around uncertain, sensitive, and constantly changing geographic information.
The problem
A CMS makes publishing pages easy — and the important questions impossible.
Trail-running information exists in fragments: GPX files from different people and devices, hand-written route notes, race spreadsheets, social-media observations, photos with embedded GPS metadata, personal activity history, and partial or outdated access and safety information. Multiple recordings often describe what is effectively the same trail.
A traditional CMS would happily publish all of it. What it can't answer:
TrailKit answers these through explicit data contracts, review states, generated artifacts, admin tools, and publication gates.
The system
From raw GPX to public site, with review gates in between.
Route & geospatial processing
The Python trailkit_core pipeline turns GPX and metadata into canonical route packages: GeoJSON, elevation profiles, climb and segment detection, phases and critical sections, map and elevation SVGs, social graphics, content drafts, offline exports, media manifests, QA reports, and checksummed artifact manifests. Generated files are never the durable source of truth — source material persists, dist/ rebuilds.
Canonical trail networks
Individual GPX packages proved too narrow: multiple recordings describe options and variations within one real trail area. The public model evolved into an atlas of trail clusters, canonical network identities, route options per network, and source tracks retained as evidence. Public identities describe the trail experience — never internal filenames or importer history.
Trail Running Ecuador site
A static Astro site: trail atlas, network and route-option pages, race calendar and detail pages, organizer and province views, media galleries, resources, and vocabulary — with public maps, elevation profiles, source-confidence indicators, and safety notices. It consumes only generated public-safe artifacts.
Authoring & review suite
Six standalone admin services — Media, Routes, Races, Publication, Training, and Transit — built on FastAPI with React/Vite map-first workbenches. They handle trace reconciliation, network geometry editing, media review and association, publication readiness, and rollback state, deliberately separated from the public site.
Data & privacy model
"Generated" does not mean "public."
As data accumulated, the project introduced a strict four-tier boundary. It's what lets the system retain rich internal information without ever leaking filesystem paths, raw GPX filenames, review notes, exact GPS metadata, object-storage keys, private activity history, or unpublished geometry.
GPX files, notes, spreadsheets, original media — durable evidence, preserved as-is.
Diagnostics, warnings, review packets, contact sheets, source observations.
Validated, redacted artifacts containing only what the public needs.
Rebuilt deterministically from projections — never edited by hand.
Documented snapshots from the architecture records, not permanent KPIs — the underlying data is actively refreshed.
How it evolved
Five phases, each earned by hitting the limits of the last.
Local-first route generation
Raw GPX became consistent route packages, graphics, drafts, and QA reports. Key insight: a trail website needs a production pipeline before it needs a CMS.
Public editorial experience
Generated artifacts became a public Astro site — bringing responsive layouts, i18n, map and elevation displays, and public-safe empty and error states.
Publication boundaries
More data made it clear that "generated" isn't "public." Explicit tiers separated source data, internal review artifacts, public-safe projections, and site output.
Database-backed authoring
File-based generation stayed for deterministic builds; PostgreSQL/PostGIS arrived where data needed relationships, history, multiple editors, geometry operations, rollback, and audit. A hybrid, not a rewrite.
Operational hardening
Artifact manifests, deterministic rebuilds, atomic SQLite generation, backup and recovery checks, OpenAPI contracts, static public-boundary scans, and CI isolation per admin app. Operating the system safely became the product.
Key design decisions
Decisions I'd defend in a design review.
No simple published flag. Access, safety, attribution, editorial completeness, technical validity, media permissions, and geometry visibility are separate decisions with explicit review gates. Normal builds serve internal work; strict QA mode is the release gate.
Climb detection, phases, and diagnostics are editorial aids, not automatic safety decisions. The system preserves manual overrides, review notes, source confidence, explicit uncertainty, and correction history. A useful guess is not a verified fact.
Source files and recordings are evidence, not identity. The network/option model lets multiple recordings converge on a stable public concept instead of exposing importer history.
Route and media editing are spatial and contextual. Editors get map-first workbenches with inspectors, route traces, elevation profiles, media associations, and command contracts — not generic forms.
Editable source material, generated internal artifacts, public projections, and static output are distinct. Nothing gets silently overwritten; every rebuild is reproducible from a clean checkout.
For safety-relevant, location-sensitive publishing, "the code works" isn't enough. Exact commands, manifests, test results, boundary scans, screenshots, and human acceptance are first-class deliverables, maintained in a repo-owned ticket and evidence system.
What I learned
The map was never the hard part.
The UI is the final expression of a larger system. The difficult work was modeling identities, relationships, provenance, review state, publication policy, and uncertainty. Once those contracts were clear, both the public experience and internal tools became far easier to evolve.
A local-first pipeline was fast to iterate, reproducible, testable with fixtures, and transparent. Moving mutable review workflows into PostGIS recognized that authoring state needs relational and audit capabilities — while files remain durable source evidence.
Public photo projections contain only what the public needs: public IDs, safe URLs, captions, credits, licenses, approved associations. Everything else — EXIF, GPS, processing details — stays behind the boundary.
Unit and contract tests, public-boundary scans, build verification, database integration, visual smoke testing, and human review each catch different failures. Treating them as one "test suite" hides which guarantee you actually have.
Public projections sometimes need rebuilding when original photos are unavailable. The answer: reuse only existing safe derivatives and fail explicitly when required durable assets are missing — never guess.
Current status
Substantially implemented, deliberately described as evolving.
The core pipeline, public Astro site, public projections, admin services, route/network tooling, media workflows, race catalog, and CI contracts are all substantially implemented. The system is designed to keep improving as more field data and editorial decisions arrive — calling it "finished" would misrepresent what it is.