xam.dk is now generated using Quarkus Roq, a static site generator built on Java and Quarkus.
Why it took a while
I had wanted to get off Jekyll for ages. I always felt like a random bet if publishing would work when writing a blog.
I already, with Jason’s help, jbang.dev but had been struggling with getting xam.dk going.
Then I watched Foojay video about Quarkus Roq and the recent quarkus.io migration itself — thousands of pages, versioned docs and all.
So I gave xam.dk another go. This time I leaned on an LLM, feeding it the Roq migration guide and the ready-made prompts on that page. Honestly? It more or less did it. Templates converted, content moved, configuration mapped — I mostly reviewed, nudged, and fixed edge cases.
Cool things I learned along the way
No frontmatter required
You don’t need YAML frontmatter anymore when using AsciiDoc!. This very post is pure AsciiDoc — the document title and :page-*: attributes in the header are picked up as page metadata directly. No --- fences in sight.
Relativize is back — via a template method
My old Jekyll templates used relativize_url almost everywhere so links worked no matter where the site was served. Roq has no direct equivalent, but because it is Qute + Java, I added a tiny template extension:
@TemplateExtension
public class UrlExtensions {
public static String rel(Page page, String target) { ... } // Path.relativize under the hood
}
So templates can now write {=page.rel('/assets/main.css')} and get a proper ../../assets/main.css relative to the current page. Feels awesome I can actually read the code and easily debug it given it is just Java now.
| One gap: this only covers links I control in templates. Relative links inside rendered AsciiDoc/Markdown content aren’t rewritten yet — so in-content image and page references still use absolute paths for now. On TODO list to try handle! |
Old comments and webmentions, preserved
Years ago I had to disable webmentions as the jekyll webmention plugin had issues. Meant old comments were gone from the rendered site - now with LLM, Roq and Qute it was trivial to bring that render back.
New comments are no longer possible (the old staticman/webmention services are gone), but every historical comment and webmention is kept and shown read-only. Likes, reposts and mentions render as a compact avatar facepile with counts; replies and comments show in full. The avatars are cached locally so there is no runtime dependency on a third-party service.
A good spring cleaning
Migrating was also a chance to delete a lot: dead staticman/recaptcha config, an unused contact form, and piles of theme vendor source files that were never served.
Thanks
Thanks to the Roq team — this was genuinely fun and easy to do. If you have a Jekyll site gathering dust, the migration guide plus an LLM is a surprisingly good afternoon.
Fun to also spot that First Post here was 24 years ago - here’s to ~25 year more with xam.dk and Quarkus Roq :)