I had to wait for 2 hours in a hospital today, so naturally I spend my time writing down long-winded thoughts in Notes.app. We are re-building our company website in Svelte. This seemed to spark some interest on Twitter, so I decided to write about it.
This is a draft for a blog post that will appear on https://mono.company/ . This is the long and wieldy version that needs an edit, but that some might appreciate. It’s about some technical beginnings, it contains some thoughts on routers, and then goes into thoughts about code splitting and ideas about how we could maybe replace WordPress (but probably won’t).
Replacing WordPress with Svelte: why bother?
We’ve recently started experimenting with using Svelte for our website. In this blog post, I’ll talk about some first findings and thoughts.
First of all, why?
- To experiment with new technology
- To make us excited about working on our site again
- To have a codebase we can be proud of
- To not have to fight WordPress’s caching mechanisms anymore
- To not have to fight trying to make a WordPress site fast
- Because we feel we are a bit stuck with our current site when it comes to experimenting with different ways to show our work
It’s an SPA!
First of all, what we are building is is essentially an SPA (Single Page Application).
This method of building a website comes with a different workflow than other methods of building websites, from static site generators to using CMSes like WordPress.
I am used to building sites with CMS’es; for years I experimented with static site generators like Jekyll; but I have never really built a site as an SPA. Up until I have always dismissed the idea, because I felt like there were too many disadvantages to shipping a site through a JS-only bundle. But a-hem -the times are changing – and I feel like I have to get on with the times. Which I might later regret.
The biggest advantage here is speed. An SPA can be very fast. Once the initial bundle is loaded, you can navigate through it without any delays. We can see this in the test version of our site. It is fast. Really fast. And that makes me happy.
Let’s talk about routing first.
When you visit a web page, the page has a URL. The URL lets the browser know which page you are requesting. In an SPA you redirect every URL to
index.html, you then “catch” the URL that was requested (e.g.
/work) and do something with it: typically render a page.
But a good router has more features than just simply displaying a page. For the Mono website, we chose to use Routify.
Routify is a file-based router. By constructing pages and paths you are essentially constructing routes that the router can derive. For me this is a super logical way to work as opposed to manually defining routes in a JS file.
If you’ve heard about Svelte, you might heard about Sapper. It works in similar ways.
A note on the Svelte ecosystem
It has to be said that Routify is quite new as a project. I am actively involved in this project to improve it myself. The authors are doing the hard work at the moment to create the best router for Svelte 3.
I see my role as promoting the router, explaining how to use it, providing good documentation, QA and being the “voice of the user”. The stated goal is that as a tool, Routify is so easy to that a beginner web developer could work with it and get things done.
Now, this is a good example of the state of the Svelte ecosystem. It’s young, there’s many things happening, but not a lot of it is locked down. This means that not every problem is solved yet, and some things might require some digging. That might not be up to your taste.
Earlier I mentioned that once the initial bundle is loaded, you can navigate through an SPA without any delay. This brings us to the topic of bundle size.
If your whole website is contained in a JS file, are you not loading a lot of things upfront that you don’t need? If your website has 30 pages and the visitor only visits 2 of them, aren’t you loading things that the visitor doesn’t need? What if they have a slow connection? Wouldn’t loading the code necessary to load 30 pages lead to a long initial render time?
All of the above are the kind of concerns you could have and that you need to be aware of when building SPAs. If your router supports code splitting (like Sapper does) you can migitate most bundle size problems (extended discussion here).
Code splitting is a technique to split your application into different pieces that are loaded on request. For section A you need bundle 1, for section B you need bundle 2, etc.
(Please note that this is how I understand it now – the whole notion of code splitting is pretty new to me).
Now, what about dynamic content?
If we take the example of blog posts, you could load dynamic content over an API and insert it in the page in a dynamic manner.
Having to request content dynamically comes with speed concerns. How and when do you build the page? Where does the content come from? How do we do this?
There are lots of solutions. To do things properly comes with new challenges. I think I am going to sidestep the “build a dynamic blog” problem for now and focus on rebuilding the website in a great way in Svelte except for the blog.
I’ll explain my rationale below.
The best of both worlds?
Our current site runs on WordPress.
Let’s consider the WordPress editing interface for a moment. I like having access to drafts, the multi user editing, the fact that I can easily add code blocks or callouts if I want to. I like that when I upload an image, WordPress automatically generates responsive images from the source, directly on the server. I can hit the publish button and have a post on my website in an instant, with a shareable URL.
Since we are rebuilding out website, it is now tempting to also rebuild the blog in Svelte. But there are a few technical realities.
First of all, the ecosystem around blogging with Svelte is not mature. There is no good sample Svelte blog project. There are no Svelte CMSes. You would essentially have to do the parts that you need from WordPress, from scratch.
There’s so many parts of WordPress that we actively use. We use categories, there is an RSS feed, there’s pagination; URL fallbacks; and that’s just scratching the surface.
And now I’m just describing the generated output side (i.e. what the CMS outputs). Then we have not even considered the user experience of writing and publishing. I’ve learned to love Gutenberg and for me there is no way back.
What about using WordPress as a data source and then using WordPress’s REST (or even GraphQL) API to pull in data? This technical solution could work, but creates a disconnect between the publishing side and the viewing side. How would you preview a post when you essentially decoupled the CMS from the data loading? How would you show the correct URL in the editing interface when the WordPress editor lives on a different server? (Or can you combine an SPA codebase in a PHP app?)
My current conclusion is that WordPress is just too powerful to replace, but the rest of our website can perfectly run in Svelte. If the WordPress runs on a subdomain, and the portfolio and every other page of the site is managed by a Svelte codebase, where both sites share the same header and footer, we might just have the best of both worlds – or we might just have created a technical monster.
To be continued…