docs+openspec: prior-art research (Organic Maps, Endurain, wanderer) and 15 proposals

Add docs/inspirations.md as the durable record of the 2026-07-05/06
prior-art research — per-project learnings with source paths, canonical
credit lines, and the changes each spawned — and extend the
acknowledgment lists in philosophy.md/architecture.md (Organic Maps,
Endurain, wanderer).

New OpenSpec changes (proposal/design/specs/tasks each):
- Organic Maps: elevation-profile-hardening, gpx-parser-robustness,
  hiking-time-estimate, poi-index, hiking-foot-profile
- Endurain: account-export, activity-duplicate-review,
  fit-parsing-hardening, activity-locations, self-hosting-guide,
  activity-privacy-controls
- wanderer: federation-hardening, link-share-tokens
- credits-page (user-visible acknowledgments)

Updated in-flight changes with wanderer prior-art sections:
route-federation, route-discovery.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
Ullrich Schäfer 2026-07-06 07:23:00 +02:00
parent be4f7e4ae8
commit 5dd4968626
80 changed files with 2600 additions and 2 deletions

View file

@ -0,0 +1,2 @@
schema: spec-driven
created: 2026-07-06

View file

@ -0,0 +1,42 @@
## Context
Static informational pages already follow a pattern: journal routes (`legal.terms.tsx`, `legal.privacy.tsx`, `privacy.tsx`) registered in `routes.ts`, linked from the shared `Footer.tsx`; the planner's footer links to absolute Journal URLs because the planner is stateless (spec `legal-disclaimers`, "Footer legal links"). The acknowledgment list lives in `docs/philosophy.md` (Open Source section, updated 2026-07-06 with Organic Maps and Endurain). Map attribution renders in the Leaflet attribution control; data-level attribution (GeoNames CC-BY from `activity-locations`, extended OSM usage from `poi-index`) has no page-level home yet — both changes reference "journal credits" as a pending surface.
## Goals / Non-Goals
**Goals:**
- One user-visible page that carries inspirations, data attributions, and key components — reachable from both apps' footers.
- Curated and short: every entry says *why* it's there in one line.
- Stays consistent with `docs/philosophy.md` without a build-time sync mechanism.
**Non-Goals:**
- Generated dependency/license inventory, sponsor/donor lists, per-page dynamic attribution logic (the Leaflet control keeps doing on-map attribution).
## Decisions
### 1. Route: `/about/credits` on the Journal, static component
A plain route module like the legal pages — no loader, content as JSX with `useTranslation`. Chosen over `/legal/credits` because credits aren't a legal disclosure and shouldn't imply one; `/about/` leaves room for future informational pages. Planner links to `${JOURNAL_URL}/about/credits`, mirroring the legal-links pattern exactly.
### 2. Content structure: three typed lists, strings in i18n
The entries (name, URL, description-key) live as a small typed array in the route module; descriptions and headings resolve through i18n so de/en stay complete. Entry list: Inspirations (BRouter, bikerouter.de, brouter-web, Organic Maps, Endurain, wanderer), Data (OSM/ODbL with the required "© OpenStreetMap contributors" wording, BRouter segment data, tile providers, GeoNames slot commented until `activity-locations` lands), Built with (BRouter, Leaflet, Yjs, Fedify, PostGIS).
*Alternative:* markdown file rendered at build time — rejected; i18n for prose is already the established mechanism and a JSX page matches the legal-page precedent.
### 3. Sync with the docs by convention, not tooling
`docs/inspirations.md` is the canonical record: each project entry carries a **credit line** that is the exact acknowledgment text for both the philosophy list and this page's entries (translated for de). A comment atop the entries array points there; a generator would be over-engineering for a six-item list (simplicity principle).
## Risks / Trade-offs
- [Lists drift between docs and page] → cross-reference comments; both files touched in the same PR whenever an inspiration is added (as this change itself demonstrates).
- [Attribution wording obligations (ODbL, CC-BY)] → use each project's canonical attribution string; verify against their attribution guidelines in tasks.
## Migration Plan
Additive UI + route registration; no data or API changes. Rollback = revert.
## Open Questions
- None blocking.

View file

@ -0,0 +1,30 @@
## Why
trails.cool owes its shape to other open projects — BRouter, bikerouter.de, brouter-web, wanderer, and (as of the 2026-07 research) Organic Maps and Endurain — and builds on data that carries attribution obligations (OpenStreetMap; GeoNames once `activity-locations` lands). Today that acknowledgment lives only in `docs/philosophy.md`, invisible to users. A user-visible credits page makes the acknowledgment real, gives data attributions a durable home beyond the map corner, and matches how the projects we admire credit their own inputs (Organic Maps' `copyright.html`, its required-credit NOTICE).
## What Changes
- New **`/about/credits`** page on the Journal with three curated sections:
1. **Inspirations** — the projects from the philosophy doc's acknowledgment list, each with a link and a one-line "what we learned from them".
2. **Data** — OpenStreetMap (© OpenStreetMap contributors, ODbL), BRouter routing segments, tile providers, and a slot for GeoNames (CC-BY) when `activity-locations` ships.
3. **Built with** — a short curated list of load-bearing open-source components (BRouter, Leaflet, Yjs, Fedify, PostGIS), not a generated dependency dump.
- **Footer link** "Credits" in both apps (planner links to the Journal page, same pattern as the legal links).
- The page and `docs/philosophy.md`'s acknowledgment list are cross-referenced so they stay in sync (comment in both pointing at the other).
- Localized (en/de) like every user-facing surface.
- Not in scope: an auto-generated full dependency-license inventory (can be a later `licenses` page if ever needed), donation/sponsor listings.
## Capabilities
### New Capabilities
- `credits-page`: The user-visible credits & inspirations page — content sections, localization, and its footer entry point.
### Modified Capabilities
- `legal-disclaimers`: the "Footer legal links" requirement gains the Credits link in both apps.
## Impact
- `apps/journal`: new route `about.credits.tsx` (+ registration in `routes.ts`), Footer link.
- `apps/planner`: footer variant gains the absolute link to the Journal page.
- `packages/i18n`: footer label + page strings (en/de).
- `docs/philosophy.md`: cross-reference comment.
- `activity-locations` and `poi-index` tasks that mention "journal credits" now have their concrete target surface.

View file

@ -0,0 +1,16 @@
## ADDED Requirements
### Requirement: Credits page
The Journal SHALL serve a credits page at `/about/credits` with three sections — inspirations (linked projects with a one-line acknowledgment each, matching the list in `docs/philosophy.md`), data attributions (including "© OpenStreetMap contributors" per ODbL guidelines and, once shipped, GeoNames CC-BY), and key open-source components. All strings SHALL be localized.
#### Scenario: Page renders with inspirations
- **WHEN** a user (authenticated or not) opens `/about/credits`
- **THEN** the page lists BRouter, bikerouter.de, brouter-web, Organic Maps, Endurain, and wanderer with links and acknowledgment lines
#### Scenario: Localized content
- **WHEN** the UI locale is German
- **THEN** headings and acknowledgment lines render in German
#### Scenario: OSM attribution wording
- **WHEN** the data section renders
- **THEN** it contains the canonical "© OpenStreetMap contributors" attribution with a link to the OSM copyright page

View file

@ -0,0 +1,12 @@
## MODIFIED Requirements
### Requirement: Footer legal links
Both the Journal and Planner SHALL render a footer with links to Impressum, Datenschutzerklärung, Terms of Service, Credits, and the source repository.
#### Scenario: Footer on Journal
- **WHEN** a user views any Journal page
- **THEN** the footer contains links labeled "Impressum", "Privacy", and "Terms" pointing to the respective `/legal/*` pages, a "Credits" link pointing to `/about/credits`, plus a link to the source repository
#### Scenario: Footer on Planner
- **WHEN** a user views any Planner page
- **THEN** the footer contains the same legal and credits links, pointing at absolute URLs on the Journal instance (since the Planner is stateless and these pages live on the Journal), plus a link to the source repository

View file

@ -0,0 +1,20 @@
## 1. Page
- [ ] 1.1 Create `apps/journal/app/routes/about.credits.tsx` with the three sections (typed entries array + i18n strings); register in `apps/journal/app/routes.ts`
- [ ] 1.2 Add en/de strings to `packages/i18n` (headings, per-entry acknowledgment lines, attribution wording)
- [ ] 1.3 Verify OSM attribution wording against the ODbL attribution guidelines; leave a commented GeoNames entry slot referencing `activity-locations`
## 2. Footer links
- [ ] 2.1 Add the Credits link to the journal `Footer.tsx`
- [ ] 2.2 Add the absolute-URL Credits link to the planner footer (same pattern as legal links)
## 3. Cross-references
- [ ] 3.1 Source acknowledgment lines from the credit lines in `docs/inspirations.md`; add mutual "update together" comments to the entries array, `docs/philosophy.md`, and `docs/inspirations.md`
- [ ] 3.2 Note the credits page as the target surface in the still-open `poi-index` and `activity-locations` attribution tasks
## 4. Verification
- [ ] 4.1 E2E: `/about/credits` renders unauthenticated with all six inspirations; footer link present on a journal page and a planner page
- [ ] 4.2 Run `pnpm typecheck && pnpm lint && pnpm test && pnpm test:e2e`