Conversation
Privacy/Terms links from #1051 render same-origin paths with next/link's <Link>, which prefetches the route's RSC payload. On the hosted deployment /privacy and /terms are not Next routes — Caddy serves static pages at those paths — so every landing-page load logged a 404 for the prefetch request. Legal URLs are operator-supplied and may resolve outside this Next app by design, so they must never be prefetched or client-routed. Render them with a plain <a> always: same-origin paths open in the same tab, absolute cross-origin URLs keep target="_blank" rel="noopener noreferrer". Touches the three call sites from #1051 (SignInConsent's LegalAnchor, LegalFooterLinks, and the landing page footer's FOOTER_LINKS) plus a new `plain` field on the link type legalFooterLinks() returns, so the footer map can render those entries as bare anchors without touching any other footer link. Existing hosted tests are updated to assert a plain anchor via a next/link mock marker, each made to fail before this fix. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Observed on prod after v1.12.1: the Privacy/Terms links added in #1051 render same-origin paths with next/link's
<Link>, which prefetches the route's RSC payload. On the hosted deployment/privacyis not a Next route — Caddy serves a static page at that path — so every landing-page load logged a 404 for/privacy/__next._tree.txt?_rsc=….Legal URLs are by definition operator-supplied paths that may live outside the Next app (the hosted deployment's legal pages come from the private ops repo via a Caddy route), so they must never be prefetched or client-routed by Next.
Rule going forward: legal links always render with a plain
<a>— same-origin paths open in the same tab (notarget), absolute cross-origin URLs keeptarget="_blank" rel="noopener noreferrer". Nevernext/link's<Link>, even when the href looks same-origin.Changes
Touches exactly the three call sites from #1051:
web/src/app/components/SignInConsent.tsx(LegalAnchor) — always renders<a>instead of choosing<Link>for same-origin paths.web/src/app/components/LegalFooterLinks.tsx— always renders<a>, since every entry it receives comes fromlegalFooterLinks()and isplainby definition.web/src/app/page.tsx— added aplain?: booleanfield to theFOOTER_LINKStype; entries from...legalFooterLinks()render as a bare<a>, every other footer entry (GitHub, SDKs, blog, etc.) is untouched and still uses<Link>/<a>exactly as before.web/src/lib/site.ts—LegalLinknow carriesplain: true, with an updated comment onlegalFooterLinks()explaining why (operator-supplied paths that may resolve outside this Next app's own routing).Tests
Updated the four existing hosted-build tests (
page.legal-links.hosted.test.tsx,SignInConsent.test.tsx,LegalFooterLinks.test.tsx,(app)/layout.legal-consent.hosted.test.tsx) pluslib/site.test.ts. Each file'snext/linkmock now tags anything that renders through<Link>with adata-next-linkmarker attribute, and a new/extended assertion checks the marker is absent on the Privacy/Terms links. Verified each of the four hosted tests fails against the pre-fix source and passes after.Test plan
npm cinpm run lintnpx tsc --noEmitnpm test— 1055/1055 passingnpm run build🤖 Generated with Claude Code