Skip to content

Perf hardening pass: cache-control audit, tile/index caching, bundle + asset optimization (good first issue, checklist) #408

@Jesssullivan

Description

@Jesssullivan

Welcome! This is a checklist-style first issue — pick one box, open a small PR, repeat. Each item is independent and low-risk, and you'll learn the proxy + service-worker + build layers as you go. darkmap is already in good shape here (we own a ~150-line service worker, the raster proxy coalesces in-flight tiles), so this is hardening, not a rewrite.

What exists today (so you don't re-do it):

  • A hand-rolled service worker with per-bucket runtime caches (src/service-worker.ts): app-shell precache + darkmap-raster-tile / darkmap-atmospheric-tile / darkmap-ephemeris buckets, cache-first for tiles, network-first for navigations.
  • The raster proxy already sets layered cache headers and coalesces concurrent identical tile fetches (src/routes/api/raster/+server.tsinFlightTiles; headers with cdn-cache-control + stale-if-error).
  • A per-process LRU+TTL geocode cache (src/routes/api/geocode/+server.ts) and a 2 h TLE cache (orbit/tle/+server.ts).
  • Vite build is already tuned a bit: reportCompressedSize, chunkSizeWarningLimit: 250, cssCodeSplit (vite.config.ts); adapter-node precompress: true (svelte.config.js). SvelteKit/Vite already minify production output by default.

Sub-tasks (each a standalone PR — check one off):

  • Cache-Control audit across all /api proxies. Make a small table of what each route sets today and flag inconsistencies. Starting points: openaq uses max-age=300 (degraded path max-age=60); point/airquality use max-age=3600; elevation uses max-age=86400, immutable; featureinfo uses max-age=300, s-maxage=3600; raster sets cdn-cache-control/cloudflare-cdn-cache-control but the atmospheric/elevation/openaq routes do not — should they, for CDN absorption? (See also Design shared origin and edge cache for raster tile bursts #163, which found Cloudflare returning DYNAMIC on /api/raster.)
  • A small index/cache for a hot keyless path. elevation/+server.ts says "so we can layer caching later" and currently has no server-side cache — a tiny in-process LRU (mirror geocode's TtlCache, src/lib/server/geocoder/cache.ts) would cut repeat Terrarium fetches on pan.
  • Bundle analysis. Run a production build and inspect chunk sizes (reportCompressedSize is on; chunkSizeWarningLimit is 250 KB). Note any chunk over budget (MapLibre is the likely heavy one) and whether anything obvious can be lazy-loaded. Just report findings first — don't restructure imports speculatively.
  • Minification sanity check. Confirm prod JS/CSS are actually minified and that precompress: true produces .br/.gz in build/. A one-paragraph confirmation closes this box.
  • Static asset optimization. Audit static/ for oversized images. (Pairs nicely with the new branding assets from the logo issue.)

Files to look at:

Acceptance criteria (per checked box):

  • The cache-control audit lands as a short doc/table; any header change is one route at a time with a one-line rationale.
  • Any new server-side cache reuses TtlCache and is bounded (max entries + TTL).
  • Bundle/minification findings are reported before any refactor; size-affecting changes show a before→after number.
  • No behavior regressions: tiles still render, degraded paths still degrade.

How to verify it's safe: just check (includes raster/server.test.ts). For cache-header changes, the safest proof is a before/after curl -I of the affected /api/... route. Keep each PR to one box so review stays trivial.

Metadata

Metadata

Assignees

No one assigned

    Labels

    good first issueGood for newcomersofflineOffline use, PWA, and cachingperfPerformance, caching, and bundle sizestabilityReliability and long-term operational hardening

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions