← All work

GVRAT

2020 – now

Homepage of gvrat.racing, October 2026: the GVRAT 2026 route map from Rainbow Bridge, Missouri to Pueblo, Colorado

The 2026 race dashboard

Live at dashboard.gvrat.racing. It runs entirely on free tiers, so hosting costs nothing.

It replaced a manual workflow in Google Sheets and WordPress Ninja Tables with a fully automated pipeline for about 500 runners over a 153-day race.

Engineering highlights

  • A fair daily cutoff: the day closes at 12:00 UTC, when the last time zone on Earth finishes its day, so every runner worldwide has had the same number of complete days to log miles.
  • Two simulated characters: the Gingerbread Man always stays one mile ahead of the leader, and the Buzzard moves at exactly the pace needed to finish on the last day.
  • Privacy by design: personal data is removed before anything is published as public JSON.

Front end

  • Next.js 16 (App Router), built as a fully static site, so there is no server at runtime.
  • React 19 and TypeScript.
  • Tailwind CSS v4, with a documented design system of tokens and component patterns.
  • Leaflet and React-Leaflet for an interactive map of the 679-mile course, with a pin for every runner; Leaflet.markercluster groups the 490+ pins.
  • TanStack Table v8 for a leaderboard you can sort and filter by name, bib, gender and country.
  • pdf-lib and fontkit to generate finisher certificates as PDFs in the browser.
  • A static page for every runner, each with its own progress view, built with generateStaticParams.

Data pipeline

  • Python 3.12 pulls in the data and does the calculations.
  • Pydantic v2 defines and checks the shape of the data.
  • Requests calls the RunSignup REST API.
  • gpxpy reads the GPS course file and finds where each runner is along the route.
  • Pluggable data sources (the RunSignup API or CSV) sit behind one shared interface.
  • pytest for tests, and uv to manage dependencies.

Automation

  • GitHub Actions runs the pipeline every day on a schedule, then commits the updated data back to the repository.
  • Cloudflare Pages rebuilds and redeploys the site on each commit.
  • JSON files in git act as the database, and daily snapshots keep a full history of the race.

How it started

We planned for 2,000. 19,600 showed up. During lockdown in India, I built a virtual-race system in under a week. Runners logged more than 12 million miles in the first four months. The work grew into years of running virtual events.

The decision

When demand exceeded the original plan, I made the case to keep entries open.

The build

Activity logging and processing, runner maps, certificates, and email communications. RunSignup handled registration and payments.

The people using it

I also answered participant questions about logging miles, correcting entries and finding their way around the platform. Clear written instructions helped people with different levels of technical confidence take the next step.

Beyond launch

We added challenges as runners finished early. The Circumpolar Race Around the World (CRAW) followed: a team relay along a 30,167-mile route, with nearly 55,000 registrations over four years. Read the CRAW case study.

Working on something similar? Let’s talk.