Notes

3 posts, read from disk and rendered once.

An island in prose

A post is prose, and prose is finished when you write it. Once in a while a paragraph wants something that is not: a poll, a calculator, a chart of the thing it is arguing about, a button that counts how many readers agreed.

The old answer was to send the whole framework down the wire so that one paragraph could have its button, and to send it to every reader of every post, including the ones who close the tab after the first line. It is a strange trade when you write it down.

The answer here is to say where the exception is and let the page keep its shape:

be the first

That is a ::: island container. frontage.content renders the Markdown around it and puts an island where it stood, so the widget hydrates when a reader scrolls to it and the rest of the post never asks for anything at all.

Rendered once

There is no Markdown renderer in the page you are reading. There is no Markdown in it either.

The browser was handed HTML and asked to do the one thing it has always been good at.

markdown-it-py ran on a laptop, once, while the site was built, and everything it produced was written into the file the server sends. That is the whole trick, and it is the reason a post costs a kilobyte instead of a quarter of a megabyte.

A directory is a database

A content site's data is not a table. It is a folder of files, one per thing, with a name you chose, and its best feature is that a person can open one in any editor and see what it says.

A collection is that folder, given a type:

Post = record(("title", text(min=1)), ("date", iso_date()), ("summary", text(), None))
posts = collection("posts", Post)

frontage.schema was written for forms and for what a server sends back. Pointing it at a directory costs nothing and buys the thing a folder of files usually lacks: a file whose front matter is wrong does not become a bad page, it stops the build and says which field.