What we can learn from Remix
Backwards compatibility and resilience under bad conditions — such as poor internet connection — have always been a fundamental part of the web’s DNA. So why are we as developers working so hard against it?
At 14islands, we use React a lot. As mentioned in the blog post Our development stack of choice, commiting to a single framework brings a lot of benefits. You end up re-using some quality stuff. For me personally, React served as a common ground when I started writing code in 2016. It helped me get up to speed quickly and enabled me to work alongside more experienced colleagues from the very beginning of my developer journey.
React and web fundamentals — why choose one when you can have both?
As an example, let’s use React. React’s official documentation on handling events immediately starts with explaining how to prevent the default behaviour. If you work with front-end development, it’s likely that your event handlers contain, probably even begin with, an event.preventDefault.
Most of the time, taking control over the full experience is exactly what we want to do. But using the preventDefault method without caution can easily backfire when something goes wrong. We risk missing out on built-in features that are a part of the foundations of the web.
Getting inspired by the latest hot framework
Using React, or any framework, for that matter, does not/should not prevent you from taking advantage of all the built-in features of the web. They can, however, be used with more or less friction depending on the approach you take.
Recently, there has been quite a lot of buzz around one of the latest hyped frameworks: Remix. Remix aims to get “back to the roots” — but in a modern way, trying to make life easier for developers while at the same time making use of standards that have been around for a long time. The fullstack framework relies on web fundamentals for solving problems, using built-in browser APIs to let the browser do what it does best. The idea is simple: work with, not against the platform.
The philosophy behind Remix is stated clearly in their documentation, and I really encourage you to take the time to read it. Regardless of what you feel about the framework itself, it brings up a lot of good questions that are worth circling back to now and then. Questions like:
- How am I treating my users? Do I want to force them to download a bunch of scripts they don’t need, or can I create a website that works straight away, without waiting for that onClick handler to load?
- What do I want to happen if a script fails when a user posts a form?
- Is my site resilient in the face of bad conditions such as poor internet connection?
- Do I need to prevent the default behaviour of the browser when creating event handlers? (My guess is: probably in most cases — but are we also handling potential errors in a responsible way?)
These are questions that front-end developers deal with on a daily basis. However, it’s not uncommon to create components that look something like this:
Nothing too crazy going on here, right? And most of the time, everything goes well. But what happens if that doSomething function is using some fancy new feature that the user’s browser does not support, or if a simple typo causes the whole script to crash?
What if, instead of preventing default behaviour as first action, we did the reverse? First try to execute doSomething. If that, for some reason, fails, prevent default would never be called, and we would fall back to the native behaviour and simply post the form the old fashioned way. Slightly more resilient, without giving up the ability to fully customise the user experience when everything goes our way.
While Remix is not the only React framework that has chosen this approach, they have made some pretty neat design choices that, at least on the surface, looks like a nice developer experience when working with both client and server.