Breaking Free from Bootstrap Bloat

Steve Widom
Ordergroove Engineering
4 min readSep 10, 2021

Twitter’s Bootstrap framework has been a godsend for web developers for ten years now. For those unfamiliar with the nuance and fragility of CSS, Bootstrap provides a way to create clean, modern websites with a modicum of additional markup. Even for seasoned front-end developers, Bootstrap can streamline one’s workflow and reduce the time spent getting a website up and running. However, with increasing browser support for new native HTML elements like <dialog>, <details>, and <template>, is the additional KB of the Bootstrap library necessary?

Benefits of Bootstrap

I am not anti-Bootstrap by any means. It provides a ton of useful tools and an industry-standard grid system. Perhaps its biggest appeal is the inclusion of custom components. Take a peek at the official website and you’ll see a plethora of pristine examples you can use on your project easily; things like: carousels, accordions, toasts, and navbars. Bootstrap even includes a library of icons. Using Bootstrap’s grid system, it is effortless to create an appealing and responsive layout. Why then am I poo-pooing the inclusion of Bootstrap on our new subscription management interface?

Why Bootstrap is Bad

OK, bad is a strong word, but if you haven’t noticed by now, I love my alliteration. We decided as a team not to use Bootstrap for the latest version of our interface for one simple reason: size. Minified and gzipped, including Bootstrap adds over 40KB! Keep in mind, if you’re using a version prior to Bootstrap 5, jQuery is also included/required and can add a few hundred more KB to your project.

40KB in 2021 isn’t awful, right? Considering the rest of the code for our SMI compiles down to about 40KB, it kind of is. But the biggest reason we decided to shy away from Bootstrap this time around is simply its lack of usefulness for our current needs.

Prior to Bootstrap’s arrival, if you wanted a dialog, for example, you had to build that bad boy from scratch (or include a separate library/plugin just for dialogs). You’d be responsible for creating all of the markup, JavaScript to control the interaction, and testing it across all major browsers. Bootstrap served a very real need for many (in webdev) years. Nowadays however, native support for elements like <dialog> is near ubiquitous.

Boss Browser Support

Dialogs no longer require a separate library or dependency (for Chrome anyway, more about that later). Instead, all you need to do is create a <dialog> element, with some content in it, which will be hidden by default. If the dialog and the button to display it are in the same parent container, then a simple single line of JavaScript can control the opening:

document.querySelector('#open-dialog-button').parentNode.querySelector('dialog').showModal()

Simply switch the showModal() event with close() to hide the dialog, and you're good to go!

The other element we recreated without the use of Bootstrap is the accordion. Instead we used the summary and details elements:

<details> <summary>Click me to expand!</summary> This content is hidden by default </details>

The above code will display the text within the summary element, and reveal the rest of the details content once the summary is clicked. Easy peas!

Drawbacks and Dangers

My high school yearbook photos will show you I’m nothing if not contrarian (and painfully uncool), so let’s talk about why eschewing Bootstrap may be a bad idea. Firstly, browser support for the native elements I’ve described above is decent, but not perfect. <details> is supported in the latest versions of all modern browsers (Chrome, Edge, Firefox) and even Safari! No such luck for IE though. <dialog>, on the other hand, is not supported in the latest (as of this writing) Firefox or Safari. So what to do? Polyfills to the rescue!

Wait a minute, if we include a polyfill, essentially a plugin/library, aren’t we back to the old way of doing things, pre-Bootstrap? Not really, because polyfills can be included conditionally. This way we don’t serve unnecessary JavaScript or CSS to Chrome users, for example. In the case of <dialog>, Firefox requires a JavaScript polyfill, whereas Safari requires both a JavaScript and CSS polyfill. It's simple enough to set up:

npm install dialog-polyfill

Or you can just use a CDN like we did. All we have to do then, is check if the dialog element exists, and include a script tag if it doesn’t, and register the actual polyfill:

if (!document.createElement('dialog').showModal) { const script = document.createElement('script'); script.src = 'https://cdnjs.cloudflare.com/ajax/libs/dialog-polyfill/0.5.6/dialog-polyfill.min.js'; script.onload = () => { const dialogPolyfill = window.dialogPolyfill; smiElement.querySelectorAll('dialog').forEach(dialogPolyfill.registerDialog); } }

To conditionally include the CSS for Safari, we simply sniff the userAgent and include a <link> as needed:

const ua = navigator.userAgent.toLowerCase(); if (ua.includes('safari') && !(ua.includes('chrome') || ua.includes('chromium')) { const link = document.createElement('link'); link.type = 'text/css'; link.rel = 'stylesheet'; link.href = 'https://cdnjs.cloudflare.com/ajax/libs/dialog-polyfill/0.5.6/dialog-polyfill.min.css'; document.head.appendChild(link); }

And we’re done!

What about Bootstrap’s acclaimed grid system? Surely we didn’t recreate that from scratch, right? We didn’t have to. Not because we were using a separate library or framework, but because our design didn’t call for it. It’s a simple layout that needn’t be squeezed into a 16-column design. A hundred lines of CSS or so and we were able to align everything properly using flexbox. As for mobile responsiveness? Same story, the simple layout didn’t call for the need to include an external framework. We simply added a few media queries and an “og-desktop” and “og-mobile” class for specific conditional rendering.

Conclusion

If you’re developing a full-fledged website with multiple pages, sections, and experiences, by all means use the best tool available for the job, which may or may not include Bootstrap. On the other hand, if you’re developing a simple layout and have some CSS chops, why not look into native browser support for many of Bootstrap’s custom components, and save the end-user a few hundred KB of bandwidth.

--

--