From 902e43ea19a16539937cc4a5a60a5343daf22283 Mon Sep 17 00:00:00 2001 From: Levi Neuwirth Date: Wed, 10 Jun 2026 09:25:50 -0400 Subject: [PATCH] Add /poetry/ and /fiction/ indexes; widen tag-collision guard MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Nav, the home portal grid, and the library have linked both URLs since the portals were added, but no rule generated either index — confirmed 404s in production (AUDIT §2.1). Both rules mirror the essays index; fiction renders an empty list until content exists. sectionOwnedTopLevelTags now lists every namespace owning a /index.html route, not just photography — Hakyll silently overwrites on duplicate routes, so an essay tagged e.g. "music" would have clobbered a real section landing (AUDIT §2.2). Co-Authored-By: Claude Fable 5 --- build/Site.hs | 40 ++++++++++++++++++++++++++++++++++++++++ build/Tags.hs | 24 ++++++++++++------------ 2 files changed, 52 insertions(+), 12 deletions(-) diff --git a/build/Site.hs b/build/Site.hs index 8c0c2f0..8316a0d 100644 --- a/build/Site.hs +++ b/build/Site.hs @@ -566,6 +566,46 @@ rules = do >>= loadAndApplyTemplate "templates/default.html" ctx >>= relativizeUrls + -- --------------------------------------------------------------------------- + -- Poetry index + -- --------------------------------------------------------------------------- + -- Nav, the home portal grid, and the library all link /poetry/; this + -- rule is what keeps those links from 404ing. Lists flat poems and + -- collection poems alike; collection index pages are excluded by + -- 'P.poetryPattern' itself. + create ["poetry/index.html"] $ do + route idRoute + compile $ do + poems <- recentFirst =<< loadAll (P.poetryPattern .&&. hasNoVersion) + let ctx = + listField "essays" poetryCtx (return poems) + <> constField "title" "Poetry" + <> constField "portal" "true" + <> siteCtx + makeItem "" + >>= loadAndApplyTemplate "templates/essay-index.html" ctx + >>= loadAndApplyTemplate "templates/default.html" ctx + >>= relativizeUrls + + -- --------------------------------------------------------------------------- + -- Fiction index + -- --------------------------------------------------------------------------- + -- Same rationale as the poetry index. content/fiction/ has no entries + -- yet; an empty match list renders an empty index rather than a 404. + create ["fiction/index.html"] $ do + route idRoute + compile $ do + stories <- recentFirst =<< loadAll (P.fictionPattern .&&. hasNoVersion) + let ctx = + listField "essays" fictionCtx (return stories) + <> constField "title" "Fiction" + <> constField "portal" "true" + <> siteCtx + makeItem "" + >>= loadAndApplyTemplate "templates/essay-index.html" ctx + >>= loadAndApplyTemplate "templates/default.html" ctx + >>= relativizeUrls + -- --------------------------------------------------------------------------- -- New page — all content sorted by creation date, newest first -- --------------------------------------------------------------------------- diff --git a/build/Tags.hs b/build/Tags.hs index 951e740..7d97baa 100644 --- a/build/Tags.hs +++ b/build/Tags.hs @@ -80,23 +80,23 @@ expandTag t = -- | Top-level tags that own a section URL outside the tag system, and -- therefore must NOT be created as tag pages — doing so would --- collide with a section landing route. The literal @"photography"@ --- is the only one currently affected: every photo's @tags:@ list --- begins with the bare @"photography"@ portal tag (per the section's --- convention), and 'tagIdentifier' would route that to --- @"photography/index.html"@ — already owned by --- @photographyLandingRules@. +-- collide with a section landing route. Hakyll does not error on +-- duplicate routes (one item silently overwrites the other), so an +-- essay tagged e.g. @music@ would otherwise clobber +-- @music/index.html@. The set therefore lists every namespace that +-- owns a @/index.html@ route, not just the tags currently in +-- use: @photography@ (every photo's @tags:@ list begins with it, per +-- the section convention) plus the other section landings and +-- generated index namespaces. -- -- Sub-tags (@photography/landscape@, @photography/film@, …) are -- unaffected; they keep their tag pages because no section landing -- claims those URLs. --- --- Other portal tags (@music@, @poetry@, @fiction@, …) don't appear --- here because their content types don't currently feed --- 'tagIndexable', so the top-level tag never enters the tag system. --- Add to this set if that ever changes. sectionOwnedTopLevelTags :: [String] -sectionOwnedTopLevelTags = ["photography"] +sectionOwnedTopLevelTags = + [ "photography", "poetry", "fiction", "music", "essays", "blog" + , "cv", "archive", "authors", "bibliography" + ] -- | All expanded tags for an item (reads the "tags" metadata field). -- Filters out any 'sectionOwnedTopLevelTags' to prevent route