Keyboard shortcuts

Press ← or → to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

Rendering

Plinth builds the same Dioxus app for browser and native targets. The route source of truth is Route in crates/dioxus-ui/src/lib.rs; the table below documents the default all-bricks build.

Route Modes

RouteModeWhy
/Streaming SSR (StreamingMode::OutOfOrder)The home page is the only route allowed to introduce server futures; the shell can stream while its content resolves.
/aboutCached SSRSite content changes only when an admin publishes the about key; external page-cache invalidation is explicit.
/support, /posts, /posts/:slug, /posts/tag/:tag, /series, /series/:slug, /projects, /projects/:slugCached SSRPublish-cadence content is served through PageCache; writes invalidate affected keys/tags.
/activity, /activity/:idFresh SSRActivity is ranked and refreshed at request time.
/todos, /todos/tag/:tag, /todos/:slugFresh SSRTodo ordering and completion state are mutable.

Custom builds with one or more bricks disabled keep the static site-content routes and omit the disabled brick routes at compile time.

Decision Rule

Use external page caching for publish-cadence content: site pages, blog posts, series, and portfolio entries. Use streaming SSR only for the home aggregate. Use fresh SSR for user-curated, ranked, or externally refreshed data. Dioxus hydration is kept at the app boundary; interactive widgets use ordinary Dioxus signals and event handlers.

Islands Boundary

The SSR/hydrate build renders the same Dioxus route tree on both targets. The mobile menu is a local signal boundary, so read-only content does not need a separate framework island.

Static Regeneration

Admin publish paths send page-cache invalidation events after a successful write:

Admin writeInvalidated static routes
Blog publish, update, delete, or tag change/posts, matching /posts/:slug, matching /posts/tag/:tag, /series, and matching /series/:slug when a series is involved
Portfolio publish/projects and matching /projects/:slug
Site content publishMatching site-content route such as /about or /support

The invalidation signal is narrow: fresh activity/todo routes are never cached.

Build Targets

Build the default SSR/islands target with:

cargo build --package plinth-web --bin plinth-web --features server,brick-blog,brick-portfolio,brick-todo,brick-activity

The Nix package additionally builds the browser target, runs wasm-bindgen, and emits target/site/pkg plus Tailwind CSS. The same route table controls server rendering and the hydration boundary.

Build the client-only CSR target with:

nix build .#plinth-csr

The CSR package emits static files only. It renders routes in the browser and uses public GET /api/* endpoints instead of server-only Dioxus functions. Use it for static previews or static hosting paired with a separate Plinth API server; prefer the default SSR package when the deployment should serve rendered HTML, feeds, admin APIs, and proxied images from one process.

WASM Safety

Server-only dependencies stay behind the Dioxus server feature. The web crate is built with default-features = false, and browser builds must not pull in Axum, Tokio server actors, SQLx, forge refresh code, or other server-only runtime dependencies. Data that the browser needs comes through shared types, hydrated resources, generated fullstack endpoints, or public REST calls in the CSR build.