One idea at a time: definition, necessity, priority, layer, recommendation. Every row is now shipped, scheduled, parked with a trigger, or dropped with a reason — so both tracking files are gone rather than left as a parallel backlog. Roughly a third already shipped. A quarter needed only a theme fragment or CSS, including several the list assumed were features: arbitrary `theme.*` frontmatter attributes already reach templates through Extra (verified), native lazy loading already ships and is deliberately absent on lead figures, and in-page timelines are a theme-defined container. roadmap.md gains an "Order of work" — nine bodies of work in sequence, because the sections this review added had accumulated without one. Item 0 is a decision, not work: core sits at ~2965 of 3000 and logging alone wants the remainder, so discover.go moves out *and* the ceiling rises with an ADR. feed.go and web/extras.go cannot move; they are resolver cases, and three parked items now wait on that same seam decision. Two ADRs came out of it. ADR-0083: the dependency rule described a practice it forbade. "Stdlib first, always" and "usually 40 lines of stdlib" would, read literally, have argued against all five modules here — every one is a format or algorithm somebody else specified, and their allowlist comments say so. Surfaced when this agent proposed hand-rolling Reed–Solomon for QR encoding. The test is now whether you can verify it, not whether you can write it, with compute-versus-hold as the counterweight. conventions.md and allowed-deps.txt contradicted it and were realigned. ADR-0084: the Effect primitive said every Effect is "idempotent and re-runnable from scratch" — true of derivatives, false of anything outbound, since a sent message cannot be recalled. Split into artifact-producing and outbound, the latter idempotent only against a delivery ledger, at-least-once with a dedupe key, and ledgers in a -state directory distinct from the disposable cache. Asked for as forward-looking design so webmentions need no redesign; recorded as a shape rather than built, the way extensions.md records the Extension struct. Also fixed a STATUS claiming Effects were "not buildable yet" when the derivative pass has inhabited them since ADR-0042. Findings that were defects rather than ideas: the Atom feed emits no <author>, which RFC 4287 requires. HTML comments in content are published verbatim — verified — so anything commented out is already public, and a check warning is scheduled rather than the engine deleting authored bytes. `Page` has no Date, so a theme cannot mark up dt-published or show an article's own date. A frontmatter naming rule after this agent proposed `archive` alongside the accepted `archived`: no near-homograph keys, and name the benefit rather than the vendor. reference/microformats-and-indieweb.md is new and is the reference asked for — microformats2 properties and IndieWeb rel values mapped to where a theme puts them, with spec URLs, marked scheduled. rel="me" is the highest-value lowest-cost item in that space and needs no endpoint at all. Four things this agent got wrong and the human caught: asserting "the engine never fetches" from a sentence scoped to the content repo, twice; inventing a data-sovereignty argument for an item he had filed as "a cool geeky thing", when the raw Markdown in his git already is the sovereignty; the archive naming; and claiming microformats could be fully implemented today. 15 files, +556/-385. No code changed. Nothing was scheduled that this agent could not name a consumer for. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
6.7 KiB
microformats2 and IndieWeb markup — a theme author's reference
Established 2026-08-02 from the microformats2 and IndieWeb specifications, checked against what this engine
supplies today. Vocabulary is somebody else's standard, so this file records it rather than deciding it;
what the engine promises a theme is harness/theme-contract.md.
Status: actively scheduled. The markup, the rel values and the config that feeds them are on the
roadmap under "IndieWeb markup and identity" — not parked. Almost all of it is theme work; the engine's share
is Page.Date, .Summary and author identity in site config, each scheduled separately and each wanted by
other features too.
Where the specs live
Canonical spec homes, recorded from knowledge rather than fetched — stable URLs, but confirm against the page if a detail matters.
| Topic | URL |
|---|---|
| microformats2, the umbrella | https://microformats.org/wiki/microformats2 |
| parsing rules (what a consumer actually does) | https://microformats.org/wiki/microformats2-parsing |
h-entry |
https://microformats.org/wiki/h-entry |
h-card |
https://microformats.org/wiki/h-card |
h-feed |
https://microformats.org/wiki/h-feed |
h-cite |
https://microformats.org/wiki/h-cite |
rel="me" |
https://microformats.org/wiki/rel-me and https://indieweb.org/rel-me |
u-syndication, for POSSE back-links |
https://indieweb.org/u-syndication |
| POSSE, the practice | https://indieweb.org/POSSE |
| Webmention (W3C REC) | https://www.w3.org/TR/webmention/ |
| Micropub (W3C REC) | https://www.w3.org/TR/micropub/ |
| IndieAuth | https://indieauth.spec.indieweb.org/ |
| WebSub (W3C REC) | https://www.w3.org/TR/websub/ |
Atom, which requires <author> |
https://www.rfc-editor.org/rfc/rfc4287 |
| the IndieWeb wiki generally | https://indieweb.org/ |
The parsing spec is the one worth reading before arguing about a property: it decides whether a class reads an attribute or text, which is where most mistakes come from.
The four prefixes
| Prefix | Means | Read from |
|---|---|---|
p- |
plain text | the element's text content |
u- |
a URL | href, src, or text |
dt- |
a datetime | datetime attribute preferred, text otherwise |
e- |
an element tree | the element's inner HTML, markup included |
The prefix is the whole trick: p-name and e-content differ only in whether markup survives.
h-entry — one post
Goes on the <article> a bundle page already renders.
| Property | Where it goes | Engine field |
|---|---|---|
p-name |
the <h1> |
.Title |
p-summary |
a summary paragraph | .Summary — scheduled |
e-content |
the wrapper around the body | .HTML |
dt-published |
<time datetime="…"> |
blocked — see below |
dt-updated |
<time datetime="…"> |
blocked — see below |
u-url |
a link to the permalink | .Canonical |
u-uid |
same element as u-url, both classes |
.Canonical |
p-category |
each tag link | .Tags |
p-author |
a nested h-card, or a u-url p-author link to one |
site config — scheduled |
u-featured |
the lead image | the OG-image work, scheduled |
Machine-readable form goes in the attribute and the human form in the text — which is already the theme
contract's standing rule for dates, so dt-published needs no new discipline, only the field.
h-card — a person
Goes on an author page (pages/about is the natural home) and, in miniature, wherever a post names its
author.
| Property | Typical element |
|---|---|
p-name |
the name |
u-url |
a link to the site or the page itself |
u-photo |
an avatar <img> |
u-uid |
the canonical identity URL, usually the site root |
p-note |
a one-line bio |
rel="author" on a post should point at whatever page carries the full h-card.
h-feed — a stream
Goes on a listing: the section index, the root listing, a tag listing.
| Property | Where |
|---|---|
p-name |
the listing's heading |
p-author |
an h-card, usually once per feed rather than per entry |
| children | each entry marked h-entry with at least p-name and u-url |
h-cite — a quoted or replied-to post
Only relevant once responses exist. p-name, u-url, p-author, dt-published describing somebody
else's post, nested inside your h-entry under one of:
u-in-reply-to · u-like-of · u-repost-of · u-bookmark-of
Link relations — the other half, and the half that is not microformats
These are rel values in <head> or in body links. They are what makes an IndieWeb consumer able to do
anything with a page.
| rel | Purpose | State here |
|---|---|---|
canonical |
the permalink | emitted |
alternate (+ type) |
feeds, and language variants via hreflang |
emitted |
me |
identity links — a profile URL that links back verifies you own it. This is what Mastodon's verified-link checkmark reads, and what IndieAuth uses to identify you | scheduled |
author |
points at the page carrying the h-card |
scheduled |
webmention |
your receiving endpoint | endpoint does not exist |
micropub |
your publishing endpoint | endpoint does not exist |
authorization_endpoint, token_endpoint |
IndieAuth | not built |
hub |
WebSub, for push rather than polling | dropped — push instead of polling matters at a scale this site does not have |
rel="me" is the highest-value, lowest-cost item in this table: a list of profile URLs in <head>, and it
is what makes an identity claim checkable rather than asserted.
What this space needs that is not markup
Found while writing this, and each is recorded where it belongs rather than here:
- Author identity in site config.
site.yamldeclaresbaseandtitleand nothing about a person. Anh-card,rel="me",rel="author", the Atom<author>element and a default OpenGraph image all want the same handful of fields. One addition, four consumers. - The Atom feed emits no
<author>. RFC 4287 requiresatom:feedto carry one unless every entry does, so the feed is invalid as it stands and readers show no author. A defect, not a feature. .well-known/is already servable. IndieAuth metadata and anything else the specs put there works today through the passthrough feature (ADR-0081), including.tmplinterpolation of the site's own base — so endpoint discovery documents cost nothing when the endpoints eventually exist.
The one thing a theme cannot express today
dt-published and dt-updated need the bundle's date, and Page has no Date field. It is lifted out
of Extra by the parser, so a bundle template cannot reach it at all; feeds and listings have it, an article
does not. Already on the Unarced list as a defect. Everything else above can be marked up now.