- Implemented `resolveApiAssetUrl` function to normalize asset URLs based on API base. - Updated `MedialibImage` component to utilize new asset URL resolution and added support for alt text and class properties. - Enhanced image loading behavior with improved width measurement and focal point handling. - Added placeholder image handling and improved accessibility with alt text. - Introduced new test script for auditing broken links in skill documentation. - Expanded seeded test content to include medialib entries and updated related tests for pagebuilder previews. - Improved global setup and teardown logging for clarity on seeded content management.
3.1 KiB
SSR and Caching
Server-side rendering via goja (Go JS runtime) with HTML caching.
For the full workflow, prefer the tibi-ssr-caching skill.
Related skills
frontend-architecturewhen SSR changes interact with route loading, i18n, orApp.sveltedata flow.media-seo-publishingwhen SSR output includes image URLs, SEO metadata, or publication timing.tibi-hook-authoringwhen SSR changes depend on neighboring hook behavior such as public filtering or cache invalidation.
Request flow
get_read.jsreceives the request and callslib/ssr-server.js.get_read.jsloadslib/app.server.jsand callsapp.default.render({ url }).frontend/src/ssr.tsstays thin and only initializes locale state before renderingApp.svelte.frontend/src/App.svelteis responsible for actual page data loading for both browser and SSR.- During SSR,
App.sveltecalls the sameloadContent(...)path directly insidetypeof window === "undefined". - Rendered HTML is stored in the
ssrcollection together with dependency tracking strings.
Keep browser and SSR content loading on the same application path whenever possible. Do not fork a second data-loading model for SSR unless the current architecture explicitly requires it.
Build
- SSR bundle is built via
yarn build:serverand outputs tolib/app.server.js. - The project no longer uses Babel for SSR.
- goja-compatible transforms are configured in
esbuild.config.server.jsviasupported. - The server build must remove frontend-only splitting/outdir options inherited from the shared esbuild config.
Cache invalidation
clear_cache.jshook invalidates SSR cache entries based on collection dependencies.- Dependencies are stored as strings like
content:<id>orcontent:*. DELETEinvalidation must be robust even whencontext.data.idis missing.
Route validation
- SSR route validation is active in
config.js. - Public page URLs are language-prefixed (
/de/...,/en/...), whilecontent.pathin the DB is stored without that prefix. ssrValidatePath()must strip the language prefix before querying content and return a canonical language-prefixed URL when needed.- If route validation changes, inspect
api/hooks/config.js,filter_public.js, and the frontend route-loading path together instead of patching only one side.
404 signaling
The SSR hook (get_read.js) checks context.is404 after rendering to determine the HTTP status code. If true, it returns HTTP 404 with the rendered 404 page HTML (and does not cache the result).
NotFound.svelte sets context.is404 = true during SSR. When the component renders (only when the page is not found), its top-level script sets the flag. The goja runtime provides context as a global during SSR, so it's available from the compiled frontend code.
When adding a 404 page or changing the not-found logic, ensure context.is404 is still set during SSR.
Related validation
- After SSR changes, run
yarn build:serverplus the narrowest reachable SSR/public-read check. - If caching or publication behavior changed, also rerun the relevant mutation-side invalidation check instead of relying on HTML diffing alone.