At this year’s NG-Conf, John Papa gave a talk about ngrx-data, as well as the JAMstack. This talk highlighted a lot of cool things about building apps with a JAMstack, and why it greatly improves development for engineers. So now I’m sure you’re asking yourself, what is a JAM stack? Well, it’s really a name for an architectural pattern that has become very popular. In this post, I’m going to define what a JAM stack is and walk you through how I used it to build a learning app recently. I’m going to showcase a few key areas where the JAMstack greatly improves the development experience, and takes a lot of the work out of maintaining applications.
Here’s John Papa’s talk (please take a second to watch if you can):
Before I proceed, I also wanted to highlight a great medium post — The JAMstack: It’s Pretty Sweet by Astasia Myers. I’m going to reference it in my discussion, and it covers the JAMstack really well. When you finish reading my post, please check it out if you have time.
From LAMP to JAM
Let’s walk through how the JAMstack came about from previous popular architectures.
Everybody remembers the LAMP stack:
- L: Linux
- A: Apache
- M: MySQL
- P: PHP
This architecture was super common years ago, and was setup by hosting a server and installing instances of all four of these technologies. The challenge was that once you had these setup, you still had to maintain them with patches and OS upgrades. You also usually setup some kind of logging or alert system that potentially lead to a maintenance headache.
Next, came the MEAN stack:
- M: MongoDB
- E: Express.js
- A: Angular
- N: Node.js
Now, this brings us to the JAMstack (directly quoting from Astasia’s post):
- Markup (M): Templated markup should be prebuilt at deploy time, usually using a site generator for content sites, or a build tool for web apps (e.g. Gatsby.js, Webpack).
After hearing John Papa’s talk and reading Astasia’s article, I realized that I had already been coding JAM stack apps for the last year with Firebase.
Firebase lets you develop apps without the need to worry about a backend and a frontend, etc. Of course, you could build out a traditional architecture with what Firebase offers you. However, providing APIs for authentication, a database, file storage, and hosting all make your life much easier when building applications.
I’ve actually written quite a bit about firebase and recommend checking out the following two articles from Angular-In-Depth:
- How the AngularFire Library makes Firebase feel like Magic
- The Angular DevOps Series: Deploying to Firebase with CircleCI
The Overwatch-Challenge, a JAM Stack Example
So now that I’ve introduced the JAM Stack, let‘s talk about an example.
Recently, I built an Angular application I’ve called The Overwatch-Challenge. It’s open source, and you can look at the code on GitHub here. The name actually comes from the internal name for a dev team I work on, and I liked the sound of it for this application.
The application provides a platform for learning. I wanted to orchestrate collaboration and sharing of some work my team (and several of my dev friends) were doing….so I wrote an app!
- It scores users based on learning activity that they record each week.
- The idea is that once a week the winners are recognized, and then there’s an impromptu meeting to highlight some of what was learned.
- The app includes Slack integration along with Zoom for the meetings.
- When users record learning activity, a hyperlink is included so that the activities can be reviewed later
So how is this a JAM stack? Well let’s look at how it works.
- First, the entire application is hosted with Firebase Hosting. This makes the entire process very simple because Firebase has a nice CLI that bundles and deploys your code easily. Checkout my article on Firebase Hosting for more details .
- The deployment is done with CircleCI. I connected my GitHub repo so that any pushes to Master trigger a build in CircleCI. CircleCI then will notify me of the build status. CircleCI has a great console that allows for debugging and logging as your builds occur. Checkout my article on CircleCI for more details.
- To integrate with Slack, I’m also using Firebase Cloud Functions. These are really just Google Cloud Functions for Firebase, but they provide a great way to have serverless functions work for my application. Firebase Cloud Functions are really powerful, I’ve built mine around triggers when values are written to the Firestore database. You can extend these functions to be full API’s with Node Express as well.
- I’m also making use of Firebase Authentication to control authentication to the application, and Cloud Firestore database for a NoSQL database
- I’m interacting with the Authentication and Firestore using the AngularFire library to inject dependencies in my Angular Components. I should mention that you can call the Firebase APIs directly, but I’m a big fan of AngularFire so I used it in my application.
The coolest part with all of this is that I only have one project. The majority of code I wrote for this was focused on building out the Angular Frontend, and orchestrating calls to the APIs. I don’t have the traditional backend and frontend apps, that are usually the architecture of choice.
My application’s JAM stack comes down to the following:
- APIs (A) = AngularFire library injected dependencies in the Angular Application and Firebase Cloud Functions that trigger on database events
- Markup (M) = Webpack used to compile Angular Application bundle and Node Express build for Firebase Cloud Functions
Also, as a side note, I am also using MkDocs as a static site generator for the Overwatch-Challenge user guide. This is done separately from my CICD pipeline I built with CircleCI, and not really part of the JAMstack discussion. I wanted to mention it here just as an example of a site generator. MkDocs is a really awesome open source site generator I highly recommend.
What advantages did I get out of this architecture?
- Development time for my application was greatly accelerated (took about 20 hours probably total)
- Very low external dependencies as everything was handled by the Firebase services
- Able to focus on building a good UI and experience for the application (not having to build out running servers)
- Pushing the maintenance of the application onto the Firebase Console rather than having to build my own set of servers
So I hope my explanation and showcase of a JAM stack has shown you the benefits of this architecture. I’ve been building applications using Firebase for some time now, and just realized why the JAM stack enables them to be fun to build and easy to maintain. I’d recommend reviewing the Firebase Documentation and building out a hello world app if you have some time. Please also look at the linked articles I provided for more in-depth explanations of the concepts discussed.