Starting over from scratch is always a bitter sweet experience, and it seems I’ve probably done this too much with my personal website over the years. This new site is probably the 5th iteration depending on how you count it. It usually starts by forgetting about all the problems you encountered in the previous iteration, and a strongly held belief that it should be simple and elegant, and that all of the current problems are solvable if only you started over with some shiny new strategy.
In the earlier iterations I was using metalsmith. The core metalsmith project is pretty simple, and until very recently didn’t require any updates in functionality for a number of years, simply because it had very few built in features and relied on an ecosystem of community authored plugins. The problem with this approach is that the community authored plugins were pretty poor quality. There’s a well established cycle where new users or developers would discover metalsmith, write a plugin to solve their specific problem, and then move on to newer shinier things and leave their plugin to languish. As a consequence plugins rarely evolved and matured into something versatile and robust, and inevitably when the next person encountered the same problem they would end up writing their own plugin to resolve the same problem.
In the end my metalsmith stack was all custom (unpublished) plugins in an effort to avoid inevitably running into a problem that an existing plugin can’t solve. The main reason I abandoned metalsmith was an inherent limitation in dealing with media, specifically video files. The metalsmith core basically reads all content to memory, runs a stack of plugins, and then writes the resulting files to disk. However, if you have video files in your content then this approach is a terrible idea because you have to read the entire site including all video to memory every time.
In conclusion, I would say metalsmith is great for static sites with only text-based content but not ideal for anything else.
The most recent iteration was nuxt static. nuxt is a boehemoth vue app generator, but it does have a static site mode. However, while I didn’t realise this at the outset, nuxt creates an "app" from your static site, so visitors essentially download the entire site (excluding images and video) to view a single page. It was still possible to get snappy download times with some async magic, but if you feel uncomfortable about a bloated web then this is a terrible approach. If you have 100 pages on your blog then of all the actual content you push to a visitor only 1% is useful.
In conclusion, nuxt-static would be great to render the front pages for an app or something, but it’s definitely not the way to render your blog.
This time round I went with a more or less metalsmith approach but I wrote the core logic myself. Metalsmith is more or less a task runner, so it was pretty easy to write something similar that was more suitable to my needs. The result is pretty great I think. Really snappy load times and pretty good management of content during the build. I don’t have any intention of publishing the task runner itself because it would probably take a lot of work to make it robust enough for all use cases.