---
# site/blog/tags/[tag].md
title: 'Posts tagged {tag}'
description: 'Everything I wrote about {tag}.'
generate:
from: tags
---
<% /* In site/blog/tags/layout.eta */ %>
<h1><%= stati.page.title %></h1>
<ul>
<% for (const post of stati.generated.items) { %>
<li><a href="<%= post.url %>"><%= post.frontMatter.title %></a></li>
<% } %>
</ul>
The links to them, from a post:
<% for (const tag of stati.page.tags ?? []) { %>
<a href="<%= `/blog/tags/${stati.slugify(tag)}` %>">#<%= tag %></a>
<% } %>
- The template never becomes a page itself. It becomes
/blog/tags/css,/blog/tags/node-jsand so on, one for each tag of the posts in/blog. - The keys go through Stati's slugify:
CSSiscss,Node.jsisnode-js.{tag}in the front matter is the tag as written (CSS), andstati.generatedhas both, askeyandlabel. generate: { from: tags, paginate: 10 }splits the long ones into pages, read fromstati.pagination.items.- A tag's page disappears with the last post that has the tag. Tags a
beforeAllhook adds get no page, because the pages are made before the hook runs.
For a page of all the tags, take one outside the blog folder, such as site/tags.md with collection: /blog in its front matter, and count them from pagesByTag:
<% const byTag = stati.collection?.pagesByTag ?? {}; %>
<% for (const tag of Object.keys(byTag).sort()) { %>
<a href="<%= `/blog/tags/${stati.slugify(tag)}` %>"><%= tag %> (<%= byTag[tag].length %>)</a>
<% } %>
An index.md in blog/tags/ would turn up among the posts in the blog's own listing.
In the Stati docs: Generated pages, Placeholders and Linking to generated pages.