Fast abstract ↬

Again in January 2020, Ben Holmes got down to do what nearly each internet developer does every year: rebuild his private website. On this article, he shares his story of how he got down to construct his personal construct pipeline from absolute floor zero and created Slinkity.

I don’t learn about you, however I’ve been overwhelmed by all the net improvement instruments now we have nowadays. Whether or not you want Markdown, plain HTML, React, Vue, Svelte, Pug templates, Handlebars, Vibranium — you may in all probability combine it up with some CMS knowledge and get a pleasant static website cocktail.

I’m not going to inform you which UI improvement instruments to succeed in for as a result of they’re all nice — relying on the wants of your challenge. This submit is about discovering the right static website generator for any event; one thing that lets us use JS-less templates like markdown to start out, and herald “islands” of component-driven interactivity as wanted.

I’m distilling a 12 months’s price of learnings right into a single submit right here. Not solely are we gonna discuss code (aka duct-taping 11ty and Vite collectively), however we’re additionally going to discover why this method is so common to Jamstackian issues. We’ll contact on:

  • Two approaches to static website era, and why we should always bridge the hole;
  • The place templating languages like Pug and Nunjucks nonetheless show helpful;
  • When element frameworks like React or Svelte ought to come into play;
  • How the brand new, hot-reloading world of Vite helps us convey JS interactivity to our HTML with virtually zero configs;
  • How this enhances 11ty’s knowledge cascade, bringing CMS knowledge to any element framework or HTML template you would need.

So with out additional ado, right here’s my story of horrible construct scripts, bundler breakthroughs, and spaghetti-code-duct-tape that (finally) gave me the SSG I all the time needed: an 11ty, Vite and Jam sandwich referred to as Slinkity!

A Nice Divide In Static Website Era

Earlier than diving in, I need to talk about what I’ll name two “camps” in static website era.

Within the first camp, now we have the “easy” static website generator. These instruments don’t convey JavaScript bundles, single-page apps, and another buzzwords we’ve come to count on. They only nail the Jamstack fundamentals: pull in knowledge from whichever JSON blob of CMS you favor, and slide that knowledge into plain HTML templates + CSS. Instruments like Jekyll, Hugo, and 11ty dominate this camp, letting you flip a listing of markdown and liquid information right into a fully-functional web site. Key advantages:

  • Shallow studying curve
    If you realize HTML, you’re good to go!
  • Quick construct occasions
    We’re not processing something complicated, so every route builds in a snap.
  • Prompt time to interactive
    There’s no (or little or no) JavaScript to parse on the consumer.

Now within the second camp, now we have the “dynamic” static website generator. These introduce element frameworks like React, Vue, and Svelte to convey interactivity to your Jamstack. These fulfill the identical core promise of mixing CMS knowledge together with your website’s routes at construct time. Key advantages:

  • Constructed for interactivity
    Want an animated picture carousel? Multi-step type? Simply add a componentized nugget of HTML, CSS, and JS.
  • State administration
    One thing like React Context of Svelte shops permit seamless knowledge sharing between routes. For example, the cart in your e-commerce website.

There are distinct execs to both method. However what should you select an SSG from the primary camp like Jekyll, solely to appreciate six months into your challenge that you just want some component-y interactivity? Otherwise you select one thing like NextJS for these highly effective elements, solely to wrestle with the training curve of React, or unnecessary KB of JavaScript on a static weblog submit?

Few initiatives squarely match into one camp or the opposite in my view. They exist on a spectrum, continually favoring new function units as a challenge’s want evolve. So how can we discover a resolution that lets us begin with the straightforward instruments of the primary camp, and steadily add options from the second once we want them?

Nicely, let’s stroll by way of my studying journey for a bit.

Be aware: If you happen to’re already offered on static templating with 11ty to construct your static websites, be at liberty to hop all the way down to the juicy code walkthrough. 😉

Extra after leap! Proceed studying beneath ↓

Going From Parts To Templates And Net APIs

Again in January 2020, I got down to do what nearly each internet developer does every year: rebuild my private website. However this time was gonna be totally different. I challenged myself to construct a website with my palms tied behind my again, no frameworks or construct pipelines allowed!

This was no easy job as a React devotee. However with my head held excessive, I got down to construct my very own construct pipeline from absolute floor zero. There’s a whole lot of poorly-written code I may share from v1 of my private website… however I’ll allow you to click on this README should you’re so courageous. 😉 As an alternative, I need to deal with the higher-level takeaways I discovered ravenous myself of my JS responsible pleasures.

Templates Go A Lot Additional Than You May Assume

I got here at this challenge a recovering JavaScript junky. There are just a few static-site-related wants I cherished utilizing component-based frameworks to fill:

  1. We need to break down my website into reusable UI elements that may settle for JS objects as parameters (aka “props”).
  2. We have to fetch some data at construct time to slap right into a manufacturing website.
  3. We have to generate a bunch of URL routes from both a listing of information or a fats JSON object of content material.

Record taken from this submit on my private weblog.

However you’ll have observed… none of those actually want clientside JavaScript. Element frameworks like React are primarily constructed to deal with state administration issues, just like the Fb internet app inspiring React within the first place. If you happen to’re simply breaking down your website into bite-sized elements or design system parts, templates like Pug work fairly properly too!

Take this navigation bar for example. In Pug, we will outline a “mixin” that receives knowledge as props:

// nav-mixins.pug
mixin NavBar(hyperlinks)
    // pug's model of a for loop
    every hyperlink in hyperlinks
        a(href=hyperlink.href) hyperlink.textual content

Then, we will apply that mixin wherever on our website.

// index.pug
// kinda like an ESM "import"
embrace nav-mixins.pug
html
  physique
    +NavBar(navLinksPassedByJS)
    important
      h1 Welcome to my pug playground 🐶

If we “render” this file with some knowledge, we’ll get a lovely index.html to serve as much as our customers.

const html = pug.render('/index.pug', { navLinksPassedByJS: [
    { href: "https://smashingmagazine.com/", text: 'Home' },
    { href: '/adopt', text: 'Adopt a Pug' }
] })
// use the NodeJS filesystem helpers to jot down a file to our construct
await writeFile('construct/index.html', html)

Positive, this doesn’t give niceties like scoped CSS on your mixins, or stateful JavaScript the place you need it. But it surely has some very highly effective advantages over one thing like React:

  1. We don’t want fancy bundlers we don’t perceive.
    We simply wrote that pug.render name by hand, and we have already got the primary route of a website ready-to-deploy.
  2. We don’t ship any JavaScript to the end-user.
    Utilizing React usually means sending a giant ole runtime for folks’s browsers to run. By calling a operate like pug.render at construct time, we hold all of the JS on our facet whereas sending a clear .html file on the finish.

Because of this I believe templates are an incredible “base” for static websites. Nonetheless, with the ability to attain for element frameworks the place we actually profit from them could be good. Extra on that later. 🙃

Beneficial Studying: How To Create Higher Angular Templates With Pug by Zara Cooper

You Don’t Want A Framework To Construct Single Web page Apps

Whereas I used to be at it, I additionally needed some attractive web page transitions on my website. However how can we pull off one thing like this with out a framework?

Crossfade with vertical wipe transition
Crossfade with vertical wipe transition. (Massive preview)

Nicely, we will’t do that if each web page is its personal .html file. The entire browser refreshes once we leap from one HTML file to the opposite, so we will’t have that good cross-fade impact (since we’d briefly present each pages on prime of one another).

We’d like a approach to “fetch” the HTML and CSS for wherever we’re navigating to, and animate it into view utilizing JavaScript. This appears like a job for single-page apps!
I used a easy browser API medley for this:

  1. Intercept all of your hyperlink clicks utilizing an occasion listener.
  2. fetch API: Fetch all of the assets for no matter web page you need to go to, and seize the bit I need to animate into view: the content material outdoors the navbar (which I need to stay stationary through the animation).
  3. internet animations API: Animate the brand new content material into view as a keyframe.
  4. historical past API: Change the route displaying in your browser’s URL bar utilizing window.historical past.pushState({}, 'new-route'). In any other case, it seems to be such as you by no means left the earlier web page!

For readability, right here’s a visible illustration of that single web page app idea utilizing a easy find-and-replace (supply article):

Step-by-step clientside routing process: 1. Medium rare hamburger is returned, 2. We request a well done burger using the fetch API, 3. We massage the response, 4. We pluck out the 'patty' element and apply it to our current page.
Step-by-step clientside routing course of: 1. Medium uncommon hamburger is returned, 2. We request a properly carried out burger utilizing the fetch API, 3. We therapeutic massage the response, 4. We pluck out the ‘patty’ component and apply it to our present web page. (Massive preview)

Be aware: You can even go to the supply code from my private website.

Positive, some pairing of React et al and your animation library of selection can do that. However for a use case so simple as a fade transition… internet APIs are fairly dang highly effective on their very own. And if you would like extra sturdy web page transitions on static templates like Pug or plain HTML, libraries like Swup will serve you properly.

What 11ty Introduced To The Desk

I used to be feeling fairly good about my little SSG at this level. Positive it couldn’t fetch any CMS knowledge at build-time, and didn’t assist totally different layouts by web page or by listing, and didn’t optimize my photographs, and didn’t have incremental builds.

Okay, I would want some assist.

Given all my learnings from v1, I believed I earned my proper to drop the “no third-party construct pipelines” rule and attain for present instruments. Seems, 11ty has a treasure trove of options I want!

If you happen to’ve tried out bare-bones SSGs like Jekyll or Hugo, you must have a fairly good concept of how 11ty works. Solely distinction? 11ty makes use of JavaScript through-and-through.

11ty helps mainly each template library on the market, so it was joyful to render all my Pug pages to .html routes. It’s format chaining possibility helped with my foe-single-page-app setup too. I simply wanted a single script for all my routes, and a “world” format to import that script:

// _includes/base-layout.html
<html>
<physique>
  <!--load each web page's content material between some physique tags-->
  {{ content material }}
  <!--and apply the script tag slightly below this-->
  <script src="https://smashingmagazine.com/2021/10/building-ssg-11ty-vite-jam-sandwich/important.js"></script>
</physique>
</html>

// random-blog-post.pug
---
format: base-layout
---

article
  h2 Welcome to my weblog
  p Have you ever heard the story of Darth Plagueis the Smart?

So long as that important.js does all that hyperlink intercepting we explored, now we have web page transitions!

Oh, And The Knowledge Cascade

So 11ty helped clear up all my spaghetti code from v1. But it surely introduced one other vital piece: a clear API to load knowledge into my layouts. That is the bread and butter of the Jamstack method. As an alternative of fetching knowledge within the browser with JavaScript + DOM manipulation, you may:

  1. Fetch knowledge at build-time utilizing Node.
    This could possibly be a name to some exterior API, a neighborhood JSON or YAML import, and even the content material of different routes in your website (think about updating a table-of-contents at any time when new routes are added 🙃).
  2. Slot that knowledge into your routes. Recall that .render operate we wrote earlier:
const html = pug.render('/index.pug', { navLinksPassedByJS: [
    { href: "https://smashingmagazine.com/", text: 'Home' },
    { href: '/adopt', text: 'Adopt a Pug' }
] })

…however as an alternative of calling pug.render with our knowledge each time, we let 11ty do that behind-the-scenes.

Positive, I didn’t have a whole lot of knowledge for my private website. But it surely felt nice to whip up a .yaml file for all my private initiatives:

# _data/works.yaml
- title: Bits of Good Homepage
  hash: bog-homepage
  hyperlinks:
    - href: https://bitsofgood.org
      textual content: Discover the dwell website
    - href: https://github.com/GTBitsOfGood/bog-web
      textual content: Scour the Svelt-ified codebase
  timeframe: Might 2019 - current
  tags:
    - JAMstack
    - SvelteJS
- title: Dolphin Audio Visualizer
...

And entry that knowledge throughout any template:

// residence.pug
.project-carousel
  every work in works
    h3 #{title}
    p #{timeframe}
    every tag in tags
    ...

Coming from the world of “clientside rendering” with create-react-app, this was a reasonably large revelation. No extra sending API keys or large JSON blobs to the browser. 😁

I additionally added some goodies for JavaScript fetching and animation enhancements over model 1 of my website. If you happen to’re curious, right here’s the place my README stood at this level.

I Was Completely satisfied At This Level However One thing Was Lacking

I went surprisingly far by abandoning JS-based elements and embracing templates (with animated web page transitions as well). However I do know this gained’t fulfill my wants endlessly. Keep in mind that nice divide I kicked us off with? Nicely, there’s clearly nonetheless that ravine between my construct setup (firmly in camp #1) and the haven of JS-ified interactivity (the Subsequent, SvelteKit, and extra of camp #2). Say I need to add:

  • a pop-up modal with an open/shut toggle,
  • a component-based design system like Materials UI, full with scoped styling,
  • a fancy multi-step type, perhaps pushed by a state machine.

If you happen to’re a plain-JS-purist, you in all probability have framework-less solutions to all these use instances. 😉 However there’s a purpose JQuery isn’t the norm anymore! There’s one thing interesting about creating discrete, easy-to-read elements of HTML, scoped kinds, and items of JavaScript “state” variables. React, Vue, Svelte, and many others. provide so many niceties for debugging and testing that straight DOM manipulation can’t fairly match.

So right here’s my million greenback query:

Can we use straight HTML templates to start out, and steadily add React/Vue/Svelte elements the place we wish them?

The reply is sure. Let’s attempt it.

11ty + Vite: A Match Made In Heaven ❤️

Right here’s the dream that I’m imagining right here. Wherever I need to insert one thing interactive, I need to go away somewhat flag in my template to “put X React element right here.” This could possibly be the shortcode syntax that 11ty helps:

# Tremendous attention-grabbing programming tutorial

Writing paragraphs has been enjoyable, however that is no approach to study. Time for an interactive code instance!

{% react './elements/FancyLiveDemo.jsx' %}

However bear in mind, the one-piece 11ty (purposely) avoids: a approach to bundle all of your JavaScript. Coming from the OG guild of bundling, your mind in all probability jumps to constructing Webpack, Rollup, or Babel processes right here. Construct a giant ole entry level file, and output some stunning optimized code proper?

Nicely sure, however this may get fairly concerned. If we’re utilizing React elements, for example, we’ll in all probability want some loaders for JSX, a elaborate Babel course of to remodel every thing, an interpreter for SASS and CSS module imports, one thing to assist with dwell reloading, and so forth.

If solely there have been a instrument that would simply see our .jsx information and know precisely what to do with them.

Enter: Vite

Vite’s been the discuss of the city as of late. It’s meant to be the all-in-one instrument for constructing absolutely anything in JavaScript. Right here’s an instance so that you can attempt at residence. Let’s make an empty listing someplace on our machine and set up some dependencies:

npm init -y # Make a brand new package deal.json with defaults set
npm i vite react react-dom # Seize Vite + some dependencies to make use of React

Now, we will make an index.html file to function our app’s “entry level.” We’ll hold it fairly easy:

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <meta http-equiv="X-UA-Appropriate" content material="IE=edge">
  <meta title="viewport" content material="width=device-width, initial-scale=1.0">
  <title>Doc</title>
</head>
<physique>
  <h1>Hi there Vite! (wait is it pronounced "veet" or "vight"...)</h1>
  <div id="root"></div>
</physique>
</html>

The one attention-grabbing bit is that div id="root" within the center. This would be the root of our React element in a second!

If you’d like, you may hearth up the Vite server to see our plain HTML file in your browser. Simply run vite (or npx vite if the command didn’t get configured in your terminal), and also you’ll see this useful output:

vite vX.X.X dev server operating at:

> Native: http://localhost:3000/
> Community: use `--host` to reveal

prepared in Xms.

Very similar to Browsersync or different standard dev servers, the title of every .html file corresponds to a route on our server. So if we renamed index.html to about.html, we’d go to http://localhost:3000/about/ (sure, you’ll want a trailing slash!)

Now let’s do one thing attention-grabbing. Alongside that index.html file, add a primary React element of some type. We’ll use React’s useState right here to show interactivity:

// TimesWeMispronouncedVite.jsx
import React from 'react'

export default operate TimesWeMispronouncedVite() {
  const [count, setCount] = React.useState(0)
  return (
    <div>
      <p>I've mentioned Vite incorrect {depend} occasions in the present day</p>
      <button onClick={() => setCount(depend + 1)}>Add one</button>
    </div>
  )
}

Now, let’s load that element onto our web page. That is all now we have so as to add to our index.html:

<!DOCTYPE html>
...
<physique>
  <h1>Hi there Vite! (wait is it pronounced "veet" or "vight"...)</h1>
  <div id="root"></div>
  <!--Do not forget sort="module"! This lets us use ES import syntax within the browser-->
  <script sort="module">
    // path to our element. Be aware we nonetheless use .jsx right here!
    import Element from './TimesWeMispronouncedVite.jsx';
    import React from 'react';
    import ReactDOM from 'react-dom';
    const componentRoot = doc.getElementById('root');
    ReactDOM.render(React.createElement(Element), componentRoot);
  </script>
</physique>
</html>

Yep, that’s it. No want to remodel our .jsx file to a browser-ready .js file ourselves! Wherever Vite sees a .jsx import, it’ll auto-convert that file to one thing browsers can perceive. There isn’t even a dist or construct folder when working in improvement; Vite processes every thing on the fly — full with scorching module reloading each time we save our modifications. 🤯

Okay, so now we have an extremely succesful construct instrument. How can we convey this to our 11ty templates?

Working Vite Alongside 11ty

Earlier than we leap into the good things, let’s talk about operating 11ty and Vite side-by-side. Go forward and set up 11ty as a dev dependency into the identical challenge listing from final part:

npm i -D @11ty/eleventy # sure, it truly is 11ty twice

Now let’s do some pre-flight verify to see if 11ty’s working. To keep away from any confusion, I’d recommend you:

  1. Delete that index.html file from earlier;
  2. Transfer that TimesWeMispronouncedVite.jsx inside a brand new listing. Say, elements/;
  3. Create a src folder for our web site to dwell in;
  4. Add a template to that src listing for 11ty to course of.

For instance, a blog-post.md file with the next contents:

# Hi there world! It’s markdown right here

Your challenge construction ought to look one thing like this:

src/
  blog-post.md
elements/
  TimesWeMispronouncedVite.jsx

Now, run 11ty out of your terminal like so:

npx eleventy --input=src

If all goes properly, you must see an construct output like this:

_site/
  blog-post/
    index.html

The place _site is our default output listing, and blog-post/index.html is our markdown file fantastically transformed for shopping.

Usually, we’d run npx eleventy --serve to spin up a dev server and go to that /blog-post web page. However we’re utilizing Vite for our dev server now! The objective right here is to:

  1. Have eleventy construct our markdown, Pug, nunjucks, and extra to the _site listing.
  2. Level Vite at that very same _site listing so it may well course of the React elements, fancy model imports, and different issues that 11ty didn’t choose up.

So a two-step construct course of, with 11ty handing off the Vite. Right here’s the CLI command you’ll want to start out 11ty and Vite in “watch” mode concurrently:

(npx eleventy --input=src --watch) & npx vite _site

You can even run these instructions in two separate terminals for simpler debugging. 😄

Hopefully, you must have the ability to go to http://localhost:3000/blog-post/ (once more, don’t overlook the trailing slash!) to see that processed Markdown file.

Partial Hydration With Shortcodes

Let’s do a short rundown on shortcodes. Time to revisit that syntax from earlier:

{% react '/elements/TimesWeMispronouncedVite.jsx' %}

For these unfamiliar with shortcodes: they’re about the identical as a operate name, the place the operate returns a string of HTML to slip into your web page. The “anatomy” of our shortcode is:

  • {% … %}
    Wrapper denoting the beginning and finish of the shortcode.
  • react
    The title of our shortcode operate we’ll configure in a second.
  • '/elements/TimesWeMispronouncedVite.jsx'
    The primary (and solely) argument to our shortcode operate. You may have as many arguments as you’d like.

Let’s wire up our first shortcode! Add a .eleventy.js file to the bottom of your challenge, and add this config entry for our react shortcode:

// .eleventy.js, on the base of the challenge
module.exports = operate(eleventyConfig) {
  eleventyConfig.addShortcode('react', operate(componentPath) {
   // return any legitimate HTML to insert
   return `<div id="root">That is the place we'll import ${componentPath}</div>`
  })

  return {
    dir: {
      // so we do not have to jot down `--input=src` in our terminal each time!
      enter: 'src',
    }
  }
}

Now, let’s boost our blog-post.md with our new shortcode. Paste this content material into our markdown file:

# Tremendous attention-grabbing programming tutorial

Writing paragraphs has been enjoyable, however that is no approach to study. Time for an interactive code instance!

{% react '/elements/TimesWeMispronouncedVite.jsx' %}

And should you run a fast npx eleventy, you must see this output in your _site listing underneath /blog-post/index.html:

<h1>Tremendous attention-grabbing programming tutorial</h1>

<p>Writing paragraphs has been enjoyable, however that is no approach to study. Time for an interactive code instance!</p>

<div id="root">That is the place we'll import /elements/TimesWeMispronouncedVite.jsx</div>

Writing Our Element Shortcode

Now let’s do one thing helpful with that shortcode. Keep in mind that script tag we wrote whereas attempting out Vite? Nicely, we will do the identical factor in our shortcode! This time we’ll use the componentPath argument to generate the import, however hold the remainder just about the identical:

// .eleventy.js
module.exports = operate(eleventyConfig) {
  let idCounter = 0;
  // copy all our /elements to the output listing
  // so Vite can discover them. Essential step!
  eleventyConfig.addPassthroughCopy('elements')

  eleventyConfig.addShortcode('react', operate (componentPath) {
      // we'll use idCounter to generate distinctive IDs for every "root" div
      // this lets us use a number of elements / shortcodes on the identical web page 👍
      idCounter += 1;
      const componentRootId = `component-root-${idCounter}`
      return `
  <div id="${componentRootId}"></div>
  <script sort="module">
    // use JSON.stringify to
    // 1) wrap our componentPath in quotes
    // 2) strip any invalid characters. In all probability a non-issue, however good to be cautious!
    import Element from ${JSON.stringify(componentPath)};
    import React from 'react';
    import ReactDOM from 'react-dom';
    const componentRoot = doc.getElementById('${componentRootId}');
    ReactDOM.render(React.createElement(Element), componentRoot);
  </script>
      `
    })
  
  eleventyConfig.on('beforeBuild', operate () {
    // reset the counter for every new construct
    // in any other case, it will depend up greater and better on each dwell reload
    idCounter = 0;
  })

  return {
    dir: {
      enter: 'src',
    }
  }
}

Now, a name to our shortcode (ex. {% react '/elements/TimesWeMispronouncedVite.jsx' %}) ought to output one thing like this:

<div id="component-root-1"></div>
<script sort="module">
    import Element from './elements/FancyLiveDemo.jsx';
    import React from 'react';
    import ReactDOM from 'react-dom';
    const componentRoot = doc.getElementById('component-root-1');
    ReactDOM.render(React.createElement(Element), componentRoot);
</script>

Visiting our dev server utilizing (npx eleventy --watch) & vite _site, we should always discover a fantastically clickable counter component. ✨

Buzzword Alert — Partial Hydration And Islands Structure

We simply demonstrated “islands structure” in its easiest type. That is the concept that our interactive element bushes don’t need to devour the whole web site. As an alternative, we will spin up mini-trees, or “islands,” all through our app relying on the place we really need that interactivity. Have a primary touchdown web page of hyperlinks with none state to handle? Nice! No want for interactive elements. However do you might have a multi-step type that would profit from X React library? No downside. Use strategies like that react shortcode to spin up a Kind.jsx island.

This goes hand-in-hand with the thought of “partial hydration.” You’ve seemingly heard the time period “hydration” should you work with component-y SSGs like NextJS or Gatsby. In brief, it’s a approach to:

  1. Render your elements to static HTML first.
    This provides the consumer one thing to view after they initially go to your web site.
  2. “Hydrate” this HTML with interactivity.
    That is the place we hook up our state hooks and renderers to, properly, make button clicks really set off one thing.

This 1-2 punch makes JS-driven frameworks viable for static websites. So long as the consumer has one thing to view earlier than your JavaScript is finished parsing, you’ll get a good rating on these lighthouse metrics.

Nicely, till you don’t. 😢 It may be costly to “hydrate” a complete web site because you’ll want a JavaScript bundle able to course of each final DOM component. However our scrappy shortcode approach doesn’t cowl the whole web page! As an alternative, we “partially” hydrate the content material that’s there, inserting elements solely the place crucial.

Don’t Fear, There’s A Plugin For All This: Slinkity

Let’s recap what we found right here:

  1. Vite is an extremely succesful bundler that may course of most file varieties (jsx, vue, and svelte to call just a few) with out additional config.
  2. Shortcodes are a straightforward approach to insert chunks of HTML into our templates, component-style.
  3. We are able to use shortcodes to render dynamic, interactive JS bundles wherever we wish utilizing partial hydration.

So what about optimized manufacturing builds? Correctly loading scoped kinds? Heck, utilizing .jsx to create complete pages? Nicely, I’ve bundled all of this (and an entire lot extra!) right into a challenge referred to as Slinkity. I’m excited to see the warm community reception to the challenge, and I’d love for you, expensive reader, to provide it a spin your self!

🚀 Strive the fast begin information

Astro’s Fairly Nice Too

Readers with their eyes on cutting-edge tech in all probability considered Astro at the very least as soon as by now. 😉 And I can’t blame you! It’s constructed with a fairly related objective in thoughts: begin with plain HTML, and insert stateful elements wherever you want them. Heck, they’ll even allow you to begin writing React elements inside Vue or Svelte elements inside HTML template information! It’s like MDX Xtreme version. 🤯

There’s one fairly main price to their method although: you’ll want to rewrite your app from scratch. This implies a brand new template format based mostly on JSX (which you won’t be snug with), an entire new knowledge pipeline that’s lacking a few niceties proper now, and basic bugginess as they work out the kinks.

However spinning up an 11ty + Vite cocktail with a instrument like Slinkity? Nicely, if you have already got an 11ty website, Vite ought to bolt into place with none rewrites, and shortcodes ought to cowl lots of the similar use instances as .astro information. I’ll admit it’s far from good proper now. However hey, it’s been helpful to date, and I believe it’s a fairly robust various if you wish to keep away from site-wide rewrites!

Wrapping Up

This Slinkity experiment has served my wants fairly properly to date (and a few of y’all’s too!). Be at liberty to make use of no matter stack works on your JAM. I’m simply excited to share the outcomes of my 12 months of construct instrument debauchery, and I’m so pumped to see how we will bridge the good Jamstack divide.

Additional Studying

Need to dive deeper into partial hydration, or ESM, or SSGs typically? Verify these out:

  • Islands Structure
    This weblog submit from Jason Format actually kicked off a dialogue of “islands” and “partial hydration” in internet improvement. It’s chock-full of helpful diagrams and the philosophy behind the thought.
  • Simplify your static with a custom-made static website generator
    One other SmashingMag article that walks you thru crafting Node-based web site builders from scratch. It was an enormous inspiration to me!
  • How ES Modules have redefined internet improvement
    A private submit on how ES Modules have modified the net improvement recreation. This dives somewhat additional into the “then and now” of import syntax on the internet.
  • An introduction to internet elements
    A superb walkthrough on what internet elements are, how the shadow DOM works, and the place internet elements show helpful. Used this information to use {custom} elements to my very own framework!
Smashing Editorial
(vf, yk, il)

#11ty #Vite #JAM #Sandwich #Smashing #Journal

Leave a Reply

Your email address will not be published. Required fields are marked *