My stack requires no maintenance, has perfect Lighthouse scores, will never have any security vulnerability, is based on open standards, is portable, has an instant dev loop, has no build step and… will outlive any other stack.
It’s not LAMP, Wordpress, Rails, MEAN, Jamstack... I don’t do CSR (Client-side rendering), SSR (Server Side Rendering), SSG (Static Site Generation)...
My stack is HTML+CSS.
And because my sources are in git, pushed to GitHub, GitHub Pages is my host.
Of course, I’m being a bit provocative here. I should rather say that, for some specific use cases, I concluded that to get top performances and to guatantee long term support, HTML+CSS was the best choice, instead on relying on technologies currently more popular. Because I’m done rewriting my site every couple of years.
It all started with a blog, that I was hosting on Wordpress.com (which is "Wordpress-as-a-Service", because the last thing I want to do is administer a Wordpress installation on my own server). I paid Wordpress.com to do one job: host my blog. And one day I looked at its sources and Lighthouse scores:
What have we done?
Sure, these are the problems of one specific blogging platform. I’m pretty sure others are better, at least in terms of performance. But isn’t there something fundamentally wrong if displaying a short text with images takes seconds, loads countless render-blocking scripts, and has unreadable sources?
My requirements were:
- long long term support
It was time to say goodbye to Wordpress. I didn’t need 99% of its features anyway. Other blogging platforms didn’t meet expectations either (I seriously have no idea why so many people publish on Medium… behind a login wall). I looked at static site generators like Jekyll, Hugo, 11ty, but all of these require tooling installed, have a build step and will ultimately need some updates or be abandonned by their maintainer. What if we also get rid of these?
The best tool is no tool, the best build step is no build step, the best update is no update. HTML gives us all that, and more.
What is the HTML+CSS stack good for?
Let’s first differentiate between what I call a web page and a web app: The goal of a web page is to serve content, on the other hand, the goal of a web app is to enable the user to perform interactive tasks. Of course, there are in-betweens, often in the form of content that might need customization depending on the logged in user and content that might allow some interactions.
HTML+CSS fits the web page use case. Wow, what a revelation! It might seem obvious, but it seems we’ve all forgotten this these days. HTML+CSS does not fit the web app use case, or any in between.
We said a web page serves content, but let’s dive into more concrete use cases:
- Product / Company / Business landing page and marketing sites
- Personal portfolio / bio
How to develop for HTML+CSS?
Authoring a pure HTML+CSS site can be done in any text editor, in any environment (any desktop OS, any smartphone, or even directly using GitHub’s single file editor) and previewed by simply opening the file in any browser.
Keep the HTML of every page minimal and semantic. First, because there is no need for countless of <div>, but then because it makes sources more readable and easier to edit. See for example the HTML sources of this page: a total of 150 lines, 100 lines are for the content, the rest is metadata and page structure, nothing extra.
For consistency, all pages that need to share the same style can point to the same CSS file. This avoids duplication when it comes to styling (but note that loading this file creates an extra HTTP request, which could be avoided if style was inlined).
When not cluttered with unnecessary scripts, divs or classes, I have no issue writing HTML directly. Yes, the paragraph tags are a bit annoying and distracting, but proper indentation and syntax highlighting mitigate this.
Sometimes, for drafting long blog articles, I’m working in Google Docs, and when I’m happy, export the content to clean HTML using an add-on. Google Docs is awesome for collaboration, with powerful suggestions and commenting system. That’s ideal for the “draft” phase.
Because all content is in git, final review and approval can be done via GitHub pull requests.
When I publish a new page, I need to link to it manually from the index page. I’m OK with that. It’s done in one line. It also allows me to have more control over when I want the page to be “published”.
I don't need to pay for custom themes, I have complete freedom in the style and layout of my site. I can embed anything I want without being restricted by the choice of the hosting platform: SVG images, 3D models, interactive JS experiences.
Creating a new page requires to clone an existing one. So... if I don’t use any templating system, how do I update my header, footer or nav? Well, simply by using the ”Replace in files” feature of any good text editor. They don’t need frequent updates anyway. The benefits of using a templating system is not worth the cost of introducing the tooling it requires.
You don’t need Wordpress, or Hugo to put a blog online, or Angular, React or Next.js to put a web page online. Raw HTML and CSS do the job.
That being said, you’ll need to pick up some tooling or framework if you want to build a web app or add more interactivity or customization to your web pages. And for that, I’m very glad to see that frameworks now seem to be prioritizing performance, notably by prioritizing serving the content first and leveraging caching whenever possible. The era of “download 5MB of JS first and then download content from a REST API” seems to be over for content web pages. (I personally think it’s still OK to do so for web apps, as the user’s intent and expectations are different).
Is the “HTML+CSS only” approach a bit extreme? A bit, it’s basically saying “all software is terrible, how can I minimize my dependencies on software”. Web standards are a model of backward compatibility. I’m pretty confident that my web pages written in raw HTML+CSS will have no issue being accessed and authored 10 years from now, without me having to do anything.