This website is generated with blog-engine-md from Markdown content.
The repo is expected to live next to blog-engine-md:
../blog-engine-md/blog-engine serve
# or
just serveOpen the local URL printed by the engine.
just buildThis generates static files in dist/.
To publish locally into the same immutable-release layout used in production:
just publishPublished releases are stored under releases/, and the active site is the
current symlink. Generated output is intentionally ignored by Git.
Pushes to main deploy through .github/workflows/deploy.yml. The workflow expects a GitHub Actions self-hosted runner on the production server, builds the target commit in a temporary Git worktree, publishes it under /www/website/releases, flips /www/website/current atomically, updates /www/website, reloads nginx, and verifies https://gratheon.com/.
The production runner must be able to write /www/website, execute /www/blog-engine-md/bin/blog-engine, and reload nginx. Nginx should use the checked-in config/nginx.conf, which serves /www/website/current.
Production keeps the two newest immutable releases under /www/website/releases. New releases reuse unchanged files from the previous active release via hardlinks when rsync is available, keeping rollback support without duplicating static assets on every deploy.
If the runner user is not root, give it passwordless sudo for nginx reloads
(replace www if the runner uses another account):
www ALL=(root) NOPASSWD: /usr/sbin/nginx -t, /usr/bin/systemctl reload nginx, /usr/sbin/nginx -s reload
Manual production deploy:
ssh root@gratheon.com
cd /www/website
runuser -u www -- git -C /www/website fetch origin main
runuser -u www -- git -C /www/website reset --hard origin/main
./restart.shcontent/is the source used byblog-engine-md.- Most pages are Markdown copied from the previous Docusaurus content roots.
- Two pages use custom templates:
content/index.md→templates/front.htmlcontent/pricing.md→templates/pricing.html
Legacy Docusaurus files have been removed; content/ is the source of truth.