syntaxai/tdd.md · main · goals / build-goals-registry.md

build-goals-registry.md 68 lines · 4610 bytes raw · source

slug: build-goals-registry title: Build /goals registry + site surface (goal #1) date: 2026-05-25 branch: goals-registry-build pr_number: 45 merge_sha: e923da8 status: shipped related_posts: [sama-v2-goal-chain-gap]

Goal: Persist /goal slash commands into git as first-class artifacts, mirroring the /blog and /sama patterns. New top-level directory goals/ holds each goal as a markdown file with YAML frontmatter; the registry lives at src/a31_goals.ts; the site renders /goals (index) and /goals/ (detail) pages; the sitemap automatically picks them up; the workflow change so /goal text always lands as a committed file follows in goal #2. Solves the "we lose /goals" problem at the storage layer first — once /goals/ is the source of truth, future authoring just writes to it.

Done when:

  • New top-level goals/ directory exists; first migrated goal lives at goals/git-url-drop-owner.md (a placeholder file with the /goal text from PR #42 is fine — goal #2 will do the proper migration).
  • Frontmatter format defined and parsed:

    slug: title: date: branch: pr_number: <int|null> merge_sha: <short sha|null> status: pending|shipped|abandoned related_posts: [, ...]

  • Layer 0 registry at src/a31_goals.ts: export interface GoalEntry { slug, title, date, branch, prNumber, mergeSha, status, relatedPosts } export const ALL_GOALS: GoalEntry[] = [...] Same shape as ALL_POSTS — drives /goals, /goals/:slug, and the sitemap.
  • Layer 1 helper src/b32_goals_meta.ts: pure functions parseGoalFrontmatter(body: string) → { meta, body } (no I/O) findGoalByMergeSha(sha: string, all: ReadonlyArray) → GoalEntry | null Sibling test src/b32_goals_meta.test.ts covers: full frontmatter, missing optional fields, malformed frontmatter (returns null), SHA lookup hit/miss, short-vs-full SHA prefix matching (so /GIT/tdd.md/commit/968890f finds a goal whose merge_sha is 968890f8a3bc...).
  • Layer 3 handlers in src/d21_handlers_goals.ts: goalsLandingHandler → /goals index (table: date · title · status · PR · commit) goalSlugHandler → /goals/:slug detail (rendered markdown, frontmatter badges, links to PR + commit + related posts)
  • /goals routes registered in src/d21_app.ts.
  • /goals link added to the main nav in src/b51_render_layout.ts:47 (between /sama and /blog).
  • Sitemap automatically lists every ALL_GOALS entry via the existing b32_sitemap helper — extend src/d21_app.ts "/sitemap.xml" handler to map ALL_GOALS → /goals/; add "/goals" to STATIC_PATHS in src/b32_sitemap.ts.
  • /goals/ pages reference their merge commit via the new /GIT/tdd.md/commit/ link AND back-reference any related blog posts in related_posts[].
  • All 388+ tests still pass; new helper test adds 5-7 cases.
  • /sama/v2/verify still reports 7/7 ✓ (anti-fudge).
  • Deployed; live-verify:

Constraints (anti-fudge):

  • One markdown file per goal — no JSON, no multi-goal files, no goal-text embedded inside another file.
  • Filename is the slug (e.g. git-url-drop-owner.md), NOT the merge SHA. SHA lookup works via the frontmatter field. Rationale: readable URLs, no chicken-and-egg, /goals/ is the canonical permalink. Documented in the file header of a31_goals.ts.
  • ALL_GOALS is the single source of truth — no second list of goals in handlers or rendered HTML.
  • Site language English-only.
  • GitHub flow via flatpak-spawn.
  • Do NOT change any §4 verifier logic.
  • Frontmatter parser stays in Layer 1 (pure string-in, struct-out) — no fs.readFile, no path joining.

Load-bearing files to read FIRST:

  • src/a31_blog.ts (the registry pattern that ALL_GOALS should mirror)
  • src/a31_sama.ts (same — second example of the pattern)
  • src/d21_handlers_sama.ts (samaLandingHandler + samaSlugHandler — the index + detail pattern)
  • src/d21_app.ts (route table — where /goals routes get registered)
  • src/b32_sitemap.ts (extend STATIC_PATHS + add goals URLs to the handler's url list in d21_app.ts)
  • src/b51_render_layout.ts:47 (nav strip — where /goals link goes)
  • content/blog/sama-v2-sitemap-implementation-plan.md (the sitemap impl plan post is the closest existing pattern for this kind of registry-driven feature)