From d5e40fba12adab2294df482a60adc9fb5a05cb45 Mon Sep 17 00:00:00 2001 From: Leo Vasanko Date: Sun, 16 Aug 2026 16:13:12 +0000 Subject: [PATCH] Serve built assets under /_/assets, admin at /_/admin Reorganize the URL space so all machinery lives under /_/: the Vite build (now with assetsDir: '', two ES-module entries and hashed shared assets: style.css, pygments.css, banner.svg, fonts moved from pagerite/static to frontend/src/assets) is served at /_/assets via frontend.route(app, "/_/assets") with cached="/", and the admin shell moves to /_/admin, leaving only "_" as a reserved top-level slug. A /favicon.ico route serves the file Vite copies from frontend/public. In dev, Vite proxies content pages and /_/admin to the backend. Editor changes: drop the noisy status line for a save-error indicator, reconnect the WebSocket with exponential backoff, and re-establish the connection from send() when it has dropped. The socket connects when an editor is opened (they mount on pen click), not before. --- AGENTS.md | 36 +++++---- docs/design-principles.md | 24 +++--- frontend/src/PageEditor.vue | 52 ++++++------ frontend/src/SiteEditor.vue | 68 +++++++++------- .../static => frontend/src/assets}/banner.svg | 0 .../src/assets}/fonts/firacode.woff2 | Bin frontend/src/assets/fonts/fonts.css | 3 + .../src/assets}/fonts/fraunces.woff2 | Bin .../src/assets}/fonts/literata.woff2 | Bin .../src/assets}/pygments.css | 0 .../static => frontend/src/assets}/style.css | 6 +- frontend/src/main.js | 6 +- {pagerite/static => frontend/src}/pagerite.js | 7 +- frontend/vite.config.js | 26 +++++- pagerite/app.py | 34 ++++---- pagerite/markdown.py | 2 +- pagerite/static/fonts/fonts.css | 3 - pagerite/views.py | 75 +++++++++++------- 18 files changed, 205 insertions(+), 137 deletions(-) rename {pagerite/static => frontend/src/assets}/banner.svg (100%) rename {pagerite/static => frontend/src/assets}/fonts/firacode.woff2 (100%) create mode 100644 frontend/src/assets/fonts/fonts.css rename {pagerite/static => frontend/src/assets}/fonts/fraunces.woff2 (100%) rename {pagerite/static => frontend/src/assets}/fonts/literata.woff2 (100%) rename {pagerite/static => frontend/src/assets}/pygments.css (100%) rename {pagerite/static => frontend/src/assets}/style.css (99%) rename {pagerite/static => frontend/src}/pagerite.js (98%) delete mode 100644 pagerite/static/fonts/fonts.css diff --git a/AGENTS.md b/AGENTS.md index 38fb8b6..f1303f2 100644 --- a/AGENTS.md +++ b/AGENTS.md @@ -21,15 +21,15 @@ not for the public pages. See `docs/design-principles.md` for the design. - `app.py` — the FastAPI app. FastAPI's built-in API docs are disabled (`docs_url`/`redoc_url`/`openapi_url=None`) because `/docs` belongs to our content. Our own routes (content pages, `/_/api/...`, `/_/f/...`, - `/static/...`) are registered BEFORE `frontend.route(app, "/")` is + `/_/assets/...`, `/_/admin`) are registered BEFORE `frontend.route(app, "/_/assets")` is called: fastapi-vue inserts its file routes at the position where `route()` was called (during `load()` in the lifespan), so anything defined earlier wins. The one exception is the content catch-all `/{path:path}`, registered AFTER `frontend.route()` so that built frontend assets still take priority over content slugs. The `Frontend` is constructed with `spa=False` explicitly: it only serves the built - asset files at root without a catch-all; an `index.html` in the build - would become a `/` route, so leave it out of the build to keep `/` ours. + asset files under `/_/assets/` without a catch-all; an `index.html` in the build + would become a `/_/assets/` route, so leave it out of the build to keep `/` ours. - `data.py` — msgspec Structs for the kanta database. The site structure is a tree: `Data.menu` maps top-level slugs to `Node`s, each with `children` keyed by slug — the URL path is the slug chain. The front @@ -72,12 +72,17 @@ not for the public pages. See `docs/design-principles.md` for the design. (`#page-banner`, `#nav`, `#sidebar`, `#main`) for fetch-navigation swaps. - `seed.py` — demo content written on startup for paths missing from the database (never overwrites existing pages). - - `static/` — our own assets served at `/static/`: `style.css` (shared - with Vue later), `pagerite.js` (fetch-navigation with rotating-cube - `startViewTransition`, scroll-reveal), `banner.svg` - (full-width header art) and `fonts/` (self-hosted Fraunces/Literata/ - Fira Code variable woff2). The `::view-transition*` block at the end of - `style.css` (from termotohtori.fi) is fragile — do not tweak. + - `frontend/src/` — the Vue editor and public-page entries. + - `main.js` — Vue editor app entry, mounts PageEditor/SiteEditor. + - `pagerite.js` — public page entry; imports the shared style and runs + fetch-navigation, scroll-reveal and code copy buttons. + - `assets/` — shared styles and data files built by Vite and served hashed + under `/_/assets/`: `style.css`, `pygments.css`, `banner.svg` and + `fonts/` (self-hosted Fraunces/Literata/Fira Code variable woff2). The + `::view-transition*` block at the end of `style.css` (from + termotohtori.fi) is fragile — do not tweak. + - Vite builds ES-module `.js` outputs; the backend renders `