Two ideas, JAMStack and static website generators, are getting attention as a way to simplify website and web application development, while simultaneously being vague unclear marketing terms. Both talk about static assets for website, but what does that really mean? To help decode the vague marketing words, let's examine the technologies, see how they differ, and try to figure out if there's anything important to learn.
In the beginning (of the web) websites were HTML files (and images) you uploaded to a web server using FTP. That's it. My first websites, in 1994-1995, were coded that way, and of course I used FTP. A big advance was finding a programmers editor, that handled HTML syntax coloring, and which could directly edit files in remote directory structures. That meant not having to upload using FTP, and the syntax coloring made it a little easier to edit the HTML. Another advance was a feature called Server Side Includes, letting one have sidebar or header or footer "widgets" loaded as HTML snippets from a shared directory. That simplified having a consistent look across the website. Then came the variety of pseudo-WYSIWYG HTML editors where we could edit web pages visually, rather than guessing what the page looked like while editing raw HTML. These editors didn't support server side includes, but there was a similar feature in Dreamweaver allowing one to have shared HTML snippets.
The point is that a website built with simple HTML files is not a new concept. We've been doing that since the beginning of the Web.
For me, both are a reaction to complicated dynamic CMS's, or complex custom micro-services deployed to cloud hosting. Over the years of learning the intricacies of Drupal 6 and Wordpress, learning how to customize Blogger templates, and learning Docker and Docker Swarm, I came away with a distaste of the burden it is to host a complex content management system which dynamically generates pages. At one time I was maintaining 10 or so Drupal instances for different websites, managing multiple VPS's, facing a never ending grind of updating modules on each site, and worrying how I would pay the hosting bill.
As a result of those experiences I developed my own static website generator, AkashaCMS. With it the hosting bill is minuscule, and the page load time for users of the websites is excellent.
The JAMStack and static website generator proponents are preaching a similar vision - modern HTML+CSS+JS - static assets for speed - simplified deployment - eliminating complexity - so let's start with this question...
What is JAMStack?
The JAMStack concept is defined as "Fast and secure sites and apps delivered by pre-rendering files and serving them directly from a CDN, removing the requirement to manage or run web servers." To drive the point home the acronym, JAM, means:
- (STACK) Because, well, every software product is described as a Stack, right?
That's simple enough, static assets and fast page load times. But the JAMStack definition says "sites or apps" and requires deployment to a CDN. Why do they explicitly call out those points? Is there a real difference between JAMStack and a static website generator?
In a system like AkashaCMS, the user edits Markdown or AsciiDoc files, then runs a tool to render those files to HTML+CSS+JS, and uses rsync to deploy to a web server. This is the JAMStack and statically generated website model, uploading static HTML+CSS+JS assets to a hosting system. A couple observations:
- A statically generated website does not require backend API's or DOM manipulation, but can include JS that calls backend API's and performs DOM manipulation, if needed
- We can use modern HTML+CSS+JS in a statically generated website
- The statically generated website can be hosted on cheap shared web hosting that uses Apache or NGINX web-servers
- Such websites can be hosted to a CDN to aid delivery to readers around the world
- Why is there an insistence on deployment to a CDN?
With both, we skip a bunch of complexity and cost arising from using dynamically executed services to dynamically generate websites (e.g. Drupal or Wordpress).
But, why do JAMStack proponents insist on using a CDN? What is a CDN? A CDN, a.k.a. Content Delivery Network, is a cloud based service for distributing assets to remote servers around the world. The promise is high performance, in part to automatically distribute content to CDN endpoints around the world.
Why insist on a CDN?
In the JAMStack literature the task of "managing a webserver" is described as a huge burden. The CDN is described as being "serverless", which is described as a huge advantage. Of course serverless is rather silly because of course CDN's are built from zillions of servers. What that really means is that the person deploying the code isn't involved with the overhead of provisioning and managing servers. The customer doesn't have to configure the servers. We just deploy our code, and the serverless service takes care of the rest. With a CDN, you upload the files, and the CDN takes care of both the servers and distributing your HTML+CSS+JS assets around the world.
CDN's primary stated advantage is that the CDN guarantees similar performance anywhere in the world. With traditional hosting from a single web server -- my sites are hosted on shared hosting rented from Dreamhost whose servers are in southern California -- the distance from that server affects speed of accessing the website.
According to Google Analytics the page load speed for my websites (all hosted on simple shared Apache web hosting) is under 20 milliseconds. Seems to me that 20 milliseconds is pretty close to blazingly fast. I haven't tried hosting a site on a CDN and don't know if CDN's deliver content even more blazingly fast. A reader of my sites in Uganda might see slower page loading times than a reader in Huntington Beach California. Hosting on a CDN is supposed to equalize the two.
Additionally, CDN providers truly offer unlimited bandwidth (at a fee). The traditional shared hosting providers, like Dreamhost, offer unlimited bandwidth, but there is often an unstated usage level beyond which the hosting provider will start sending emails demanding your site move somewhere else. CDNs have performance guarantees that cannot be made by the traditional Apache-based web hosting provider.
Where did JAMStack come from?
Front-end engineering is oriented to visual and interactive effects, whereas back-end coding is about server deployments, service scaling, and the like. It stands to reason a front-end engineer would balk at doing server deployments.
The folks talking about JAMStack focus on the ease of deploying applications. The folks using static website generators, like me, are looking for a slightly different thing. We have websites (blogs etc) to deploy, don't see the point of dynamically generating the content on every page view, and want a lower hosting cost.
Avoiding complexity may be the biggest gain
This image demonstrates the advantage of both JAMStack and the websites rendered using a Static Website Generator. The far simpler system is lower cost and lower resource impact and lower overhead to maintain and faster.
On the left (blue arrows and text) we have the model of deploying static assets. They can be deployed to a CDN, as the JAMStack proponents insist, or to a simple Apache or NGINX server. In both cases the user's web browser makes a request to a web server, and the web server simply sends back the file, and that's that.
On the right (with green text and arrows) we have a complex system deployed on cloud hosting infrastructure. A cloud hosting platform like AWS has close to a zillion features, giving technologists lots of things to get excited about. Global scale custom services of the type driving all kinds of websites are possible by configuring and using cloud hosting platforms. It's a compelling model, because anyone can rent service that can scale from a small deployment to a globe spanning service at the click of a few buttons. But trust me when I say that it is complex to learn, complex to understand, complex to grok how to minimize the costs, complex to manage, etc.
Serverless is the real method for eliminating complexity
The JAMStack proponents praise CDN deployment, but what they should be praising is the serverless concept.
There are a lot of hugely complex systems available in today's computing world. Some kinds of websites require that complexity, because of the intense number of services to manage.
To build and maintain a system that works across multiple availability zones, automatically handles service failure, that handles automatic localization and internationalization, and much more, requires multiple teams of highly skilled engineers. Not everyone can afford the cost of hiring such a deep talent base.
The serverless approach offers a different route. The service provider hires the engineering talent required to deploy a cloud based service, and we simply rent their service. Whether it's a database service, a content distribution service, a cloud functions service, or any other service, we simply use the service providers website to rent the service. The service provider's engineering team takes care of scaling to meet traffic, multi-zone availability, backups, reliability, and more. Our task is simple - we configure the application stack with service access particulars, and get on with the business of writing application code.
It's so simple that an individual (or small team) can:
- Deploy any custom back-end services to functions-as-a-service system
- Utilize database-as-a-service
- Utilize other 3rd party cloud services
All with no complexity, and the ability to quickly develop/deploy a website or web application. All the complexity is handled by serverless service providers.
However, not all serverless services are equally simplified. AWS Fargate is billed as a serverless version of AWS ECS or AWS EKS. ECS is an AWS cloud service for hosting Docker containers, and EKS is the AWS service for running Kubernetes. Fargate is serverless in that you do not provision the servers involved in hosting the Docker containers, which does slightly simplify the task of hosting a Docker service. But Fargate is still extremely complex.
In the next section let's talk more concretely about JAMStack implementation.
That's nice theory, but what are JAMStack or static websites for real?
All of that was rather abstract, so let's look at some concrete examples of JAMStack.
Commenting systems on static HTML or JAMStack websites
There were advantages to those dynamic CMS's. For instance Wordpress and Drupal both integrate a native commenting system, and allow users to register with the website in order to leave comments. It is possible to build a community via a website by allowing your readers to leave comments. Why should we leave that and other features behind?
The first step is to render the content of the website using a static website generator. There are many such systems each with different behaviors. In most cases content is written in Markdown and rendered through templates to create the static HTML site.
The Disqus UI integrates a number of back-end services. For example users can sign up as a Disqus user without leaving the web page, and it can also authenticate people using 3rd party services like Facebook or Twitter. Once a reader is authenticated, they can leave comments and the comments area is dynamically updated as others leave comments.
Custom back-end services in static HTML or JAMStack websites
Many websites have custom services as well. Not every need fits into what a 3rd party service can provide, after all.
To take an example, one of my websites is a proper static HTML site, where one section has a service implemented in old school PHP. The original version of that service was implemented in TCL in 1997, and sometime in the 00's I rewrote it to simplistic old-CGI-style PHP. Today, the PHP scripts are rendered from templates by AkashaCMS and deployed with the HTML+CSS+JS of that website, but it's still the old-school PHP.
That website is therefore not pure static HTML, nor is it a JAMStack site. According to JAMStack proponents, this has complexity and is something to avoid. In this case the PHP implementation requires extra security measures.
There are close to a zillion reasons any given site might have custom dynamic services. Not every need is satisfied by a prebaked third party service. Since the JAMStack approach is not just about performance, but simplicity and security, that leads us to a question: What's the simplest, highest performance, and most secure way to use a custom dynamic service on a JAMStack site?
My mind turns immediately to a function-as-a-service platform like AWS Lambda, and the promises of scalability, performance, and baked-in security.
The JAMStack proponents would probably say to implement a custom service as:
- A back-end offering a JSON/REST API
<div id="app"></div> <script src="/dist/build.js"></script>
The JS code at the URL, in this case
/dist/build.js, must be written to target the
div#app element where it will initialize the application.
Over on the JAMStack website is a corresponding issue. Namely, the list of factors that are NOT JAMStack websites includes:
A single page app that uses isomorphic rendering to build views on the server at runtime.
On that Wikipedia page, there is a discussion of the problem of search engines indexing sites that have client side rendering. Rather, since that page presents Isomorphic Rendering as a good thing, it gives this as one of the benefits:
Hence, I am justified in my concern about whether this would impact search engine visibility of my site. FWIW Vue.js claims to be indexable by search engines, so I might be overstating the issue.
Websites as applications
Unlike the sites I normally create, some folks use a website as the location for an application. Some examples are Slack, Discord, Google Mail, Canva, all of which are websites with a small amount of public content, and an area where you access an application. Instead of the primary purpose being presenting written content like this, it is the application.
For back-end services, the UI would likely use a variety of 3rd party and custom services. For the custom services you again are recommended to host on a serverless platform in order to keep it simple.
Following those recommendations would make this a JAMStack site.
Such a site probably does not desire search engines to index the application. Would a search engine find any indexable anything in a wordprocessor application UI like what we get on Google Docs?
What we've learned is that a JAMStack site is similar to a static HTML website, but with a couple specific requirements. Since the goal is simple system management, JAMStack sites are best hosted on serverless platforms.
But there's this issue about insisting JAMStack sites/applications must be on a CDN. I fully understand the goal of "Jamstack projects don’t rely on server-side code" since that eliminates a bottleneck to delivering blistering performance. Clearly the JAMStack website insists on CDN deployment, but is that the only rational choice?
In my experience, for the traffic level I deal with, Apache on a simple shared web hosting provider is sufficient for excellent page load times. One thing the JAMStack site says is:
The thing that they all have in common is that they don’t depend on a web server.
Instead we're supposed to depend on serverless services, which of course are built from servers. What serverless means is other peoples servers, and the advantage to that is a simplified management experience. That's what JAMStack means by not depending on a web server.
I guarantee that with Dreamhost I'm not involved with server management either. I have a half dozen static HTML sites on a simple shared Apache account on Dreamhost, and have zero involvement with managing the server. I simply use rsync to upload the HTML+CSS+JS to the server and everything is hunky dory. I wish the JAMStack site weren't so stuck on this anti-server stance.