This is Cheng’s static site, a home for practice projects and everyday tinkering notes. This first post is about the site itself: what goes here, how it is put together, and how it will be deployed.
The obvious win: no server and no database. Every page is already rendered into plain HTML at build time, so hosting is just a folder of files.
That means:
The trade-off is no backend: comments, likes and anything server-side either get dropped or outsourced to a third party. This site currently has comments off.
Writing a post means writing Markdown — one folder per post, one file per language:
src/content/blog/how-this-site-works/├── zh-cn.md└── en.mdA frontmatter block at the top carries the metadata:
---title: How This Site Is BuiltpubDate: 2026-10-03description: One-line summarycategory: SiteslugId: how-this-site-workspinTop: 1---Then a single build step (pnpm build) does four things:
sitemap.xml, rss.xml and robots.txt as build artifacts, so there is nothing to maintain by hand.What is left in dist/ is a folder that any static host can serve.
Navigation gets extra treatment: clicking a link does not reload the whole page — the new page is fetched and only the content area is swapped, with fade transitions and hover prefetching. Images also get a blurred placeholder generated at build time, so a slow image never shows up as a blank box.
Styling is Tailwind plus a set of CSS variables; the light and dark palettes live in one file, so recolouring never means digging through components. The site is bilingual: / is Chinese and /en/ is English.
Three layers:
dist/ automaticallySince the output is purely static, any of those layers can be swapped: move dist/ somewhere else and no code changes.
Two details to handle at launch: point the site URL in the build config at the real domain (otherwise sitemap, RSS and share cards still link to localhost), and if the site ends up under a subpath like username.github.io/repo, configure a path prefix.
Whatever I actually do next — one post at a time, in the order it happens. The archive page groups posts by year automatically, so there is no index to maintain.