Skip to content

fix(docs): serve the home page at / on the node-server output (UXF-286) - #336

Open
alexgrozav wants to merge 1 commit into
mainfrom
agent/palette/24ac05830cfe
Open

alexgrozav wants to merge 1 commit into
mainfrom
agent/palette/24ac05830cfe

Conversation

@alexgrozav

Copy link
Copy Markdown
Contributor

Description

The apps/docs Node server answered / with a 302 to /llms.txt. The cause is not a route rule — it is server/plugins/llms-redirect.ts in @uxfront/layer-docs@0.4.1, a Nitro request-hook plugin that redirects the site root when the client sends Accept: text/markdown or a curl/* user agent.

Two problems with keeping it on:

  1. It never runs in production. Vercel serves the prerendered index.html from the CDN, so Nitro never sees /. Verified — curl -H 'accept: text/markdown' https://www.styleframe.dev/ returns 200 text/html. The plugin only fires on the node-server preset, so the build output disagreed with the live site on the site root: exactly the route a self-hosted deploy or a local production check hits first.
  2. The curl/* branch is not content negotiation. curl is what humans, health checks, uptime monitors and CI smoke tests speak HTTP with. curl -I http://localhost:3000/ returning a redirect to a text file is how this was reported as a broken home page.

This disables the plugin from apps/docs with nitro.ignore. /llms.txt and /llms-full.txt are still generated and served; agents reach them through the llms.txt convention.

Upstream follow-up: the durable fix is dropping the user-agent branch in @uxfront/layer-docs. The nuxt.config.ts comment says so, and the guard below will keep this honest until then.

The test

test/root-route.build.test.ts boots the compiled .output/server/index.mjs on an OS-assigned port and asserts / returns 200 text/html for a browser UA, for curl/8.7.1, and for Accept: text/markdown — plus that /llms.txt still serves.

It has to boot the real server. The redirect lives in a request hook that runs ahead of Nitro's public-asset handler, so reading .output/public (what the other build guards do) cannot see it, and nuxt dev never exercises the compiled plugin list. It runs in the existing test:build suite, against the artifact the docs build job just produced.

Verification

Against the built Node server, before the change:

built Node server > serves the home page at / to curl
  AssertionError: expected 200, got 302 → /llms.txt
built Node server > serves the home page at / to a markdown-preferring client
  AssertionError: expected 200, got 302 → /llms.txt

After, on a forced rebuild:

curl /                       200 text/html;charset=utf-8
accept: text/markdown /      200 text/html;charset=utf-8
/llms.txt                    200 text/plain; charset=utf-8
/docs                        307 → /docs/getting-started/introduction   (route rule intact)

pnpm test:build 8 passed · pnpm test 4 passed · pnpm typecheck exit 0 · oxlint/oxfmt clean.

Related issue

Relates to UXF-286.

Type of change

  • 🐞 Bug fix (non-breaking change that fixes an issue)
  • ✨ New feature (non-breaking change that adds functionality)
  • 💥 Breaking change (fix or feature that changes existing behavior)
  • 📖 Documentation
  • ♻️ Refactor / internal (no functional change)
  • 🔧 Build / tooling / CI

Checklist

  • My commits follow Conventional Commits with a package scope (e.g. feat(theme): …)
  • I ran pnpm build:nodocs && pnpm lint && pnpm typecheck && pnpm test and everything passes
  • I added a changeset (pnpm changeset) for changes to publishable packages, or this change only touches docs/storybook/app/playground/tests
  • I added or updated tests where relevant
  • I updated documentation where relevant
  • I did not edit generated files (dist/, .styleframe/)
  • My PR targets main and stays focused in scope

Notes / screenshots

@styleframe/docs is in the changesets ignore list, so no changeset applies.

No visual change: browsers were already served the correct home page, which is why this survived to a 0.3.0 baseline unnoticed.

The layer's llms-redirect plugin 302s the site root to /llms.txt for
`Accept: text/markdown` and for `curl/*` user agents. It never fires on
our Vercel deploy, where the CDN serves the prerendered index.html
before Nitro sees the request, so the node-server output disagreed with
the live site on the site root — and `curl -I` on a local production
check reported the home page as broken.

Disable it via nitro.ignore and guard the route with a build test that
boots the compiled server. Reading .output/public cannot catch this:
the redirect lives in a request hook that runs ahead of the public-asset
handler, and prerendering writes a correct index.html either way.

/llms.txt and /llms-full.txt are unchanged.
@changeset-bot

changeset-bot Bot commented Sep 8, 2026

Copy link
Copy Markdown

⚠️ No Changeset found

Latest commit: ea6d857

Merging this PR will not cause a version bump for any packages. If these changes should not result in a new version, you're good to go. If these changes should result in a version bump, you need to add a changeset.

This PR includes no changesets

When changesets are added to this PR, you'll see the packages that this PR includes changesets for and the associated semver types

Click here to learn what changesets are, and how to add one.

Click here if you're a maintainer who wants to add a changeset to this PR

@vercel

vercel Bot commented Sep 8, 2026 •

Copy link
Copy Markdown

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated
styleframe-dev Ready Ready Preview Sep 8, 2026 7:03am UTC
styleframe-dev-storybook Ready Ready Preview Sep 8, 2026 7:03am UTC

Request Review

@codecov

codecov Bot commented Sep 8, 2026

Copy link
Copy Markdown

Codecov Report

✅ All modified and coverable lines are covered by tests.

📢 Thoughts on this report? Let us know!

This branch was successfully deployed

2 active deployments
Preview – styleframe-dev — ea6d8574 Deployed Sep 8, 2026 by vercel[bot]
Preview – styleframe-dev-storybook — ea6d8574 Deployed Sep 8, 2026 by vercel[bot]
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant