I heard a lot about JAM stack in 2018. But, my day job is largely on a huge monolith so I didn’t get to experiment with it much.
We use React at work. And, largely the newer stuff serves up data into the frontend. But, there’s always an extent to which you can bend your older systems.
The thing about working on a Monolith is you largely have the flexibility to do anything. All of your data is just a query away. You can push whatever you want from your Model into your Controller and straight into your view.
Authentication is largely done-for-you with something like Laravel or Django.
You have sessions which let you show flash messages and provide another layer of authentication. Life generally just works.
It’s like a big factory. If you need something, chances are you can just get it from somewhere in the factory without much thought.
So, to challenge myself and keep learning, I started a non-marketable, simple side-project earlier this year.
The goal is simple:
Build a Progressive webapp (either SSR or statically compiled), electron desktop app, and React Native mobile app all which allow a user to control a team of up-to 500 users and see their user’s data all via an API.
I also challenged myself to keep every response time of the API sub-300ms.
When it comes to building a JWT-API that’s used across varioius apps, you must standarize your database models and responses much sooner.
You’re not just registering accounts in one place, you are registering accounts in 3 places. This means if I tweak a property on the users model, it has implications in several places.
At first this was frustrating, but the structure started to give the code more meaning in the end. The video below really helped flesh out my many-to-many-to-many relationships. And I was able to build some incredibly optimized queries for large amounts of data.
If I would have been in a monolith typeof enviroment, it would have been a lot more tempting to have an internal and external endpoints. With my web react app acting as the only interface, I feel like I ended up with a cleaner codebase.
One of my primary goals was making all response times under 300 ms. The biggest struggle with this goal comes when it’s time to do things like email or use external APIs (Billing/Notifications/Analytics).
This stuff just takes too much time when a user is using a fast JS interface.
So, I ended up using a lot of Queue works in the app to keep everything from registering to querying 1000 records around 200-300 ms.
Additionally, when you get into some complex relational data, it became pretty important to eagerly load relations.
This saved some of my longer queries.
In terms of the user interface, the use of skeleton loaders really make the app smooth. Here’s what Slack’s looks like:
These things, while not direcly speeding up your queries, make a world of difference.
As there were several React apps and then a backend api, I settled on a Monorepo. It’s just easier. You can use your IDE’s features for folder/file navigation better. And you only have to manage one git repository.
The biggest pain here came from setting up continous deployment.
Most of the free services you’d used for a non-marketable side thing like this, give you limited continous deployment.
That’s tricky when you’re trying to deploy multiple apps with various build processes out of the same repo.
I was going to try and use Zeit’s Now product that everyone RAVES about. But, I found it very unreliable and rather limited in terms of deployment options.
As a web-first dev, I thought these tools would require more learning. They didn’t. I was very impressed at how far I could get with very little reading about the platforms.
Overall, I think JAMSTACK is largely going to takeover in the next few years. The costs of hosting are much cheaper. The flexibility it gives you in your code is much higher. And generally I think you can build better experiences for users faster. It took a little getting used too. But, after a few weeks, I think, you are generally coding things out faster.