DEV Community

Cover image for Web Components did not fail!
Danny Engelman
Danny Engelman

Posted on

Web Components did not fail!

My comment to yesterdays Dev.to post: Web components failed. We can fix them became a full post:

TL;DR:

Web Components never failed. Browser vendors have used component-based architecture for decades. Yet developers keep building apps, inventing frameworks, and adding dependencies instead of embracing the platform.

Build apps with frameworks. Build components with Web Components.

The technology isn't the problem. Our mindset is.


Web Components Never Failed

Web Component history

The Web Component story didn't start with today's Custom Elements.

Almost 28 years ago, in 1998, Microsoft proposed HTML Components (HTC):

https://www.w3.org/TR/NOTE-HTMLComponents

In 2006, Mozilla took its own stab at componentizing the Web with XBL, first developed for Mozilla and later proposed as a specification:

https://www-archive.mozilla.org/projects/xbl/

Different technologies, different APIs — but the same underlying desire:

Make pieces of the Web reusable, encapsulated, and programmable.


Your Web Browser serves you Web Components...
on every Web page!

Browser vendors have been using Web Component machinery for many moons longer than we mortal developers have had today's standardized Web Components APIs.

To Us, Modern Web Components became broadly available roughly around:

Chrome 2016 · Safari 2017 · Firefox 2018 · Edge 2020

But browsers themselves have always had that same problem to solve:

  • The WHATWG specifies what an HTML element should do.

  • Browser vendors still have to decide how to build it.

Take a complex native element such as:

<input>
Enter fullscreen mode Exit fullscreen mode
<textarea>
Enter fullscreen mode Exit fullscreen mode
<video>
Enter fullscreen mode Exit fullscreen mode

From the developer's perspective, that's one element.

Underneath, there may be an entire internal UI: buttons, sliders, labels, tracks, controls and state.

That should sound familiar.

It is the same Web Component architecture us mortal developers can now use!

With the appropriate DevTools settings, browsers can expose these internal shadowDOM trees for inspection.

<video> with sahdowDOM in Chromium

Chromium video Shadow DOM

<video> with shadowDOM in Firefox

Firefox video Shadow DOM

They're not your DOM to manipulate.

They're implementation details.

And that's precisely the point.


Web Components did NOT fail

So saying:

"Web Components failed."

has always sounded a little strange to me.

We interact with componentized browser <input> UI every single day.

The browser platform itself demonstrates why encapsulated components are useful.

The question isn't whether components work.

The interesting question is:

Why don't we build more of our own software that way?



Mortal developers and Web Components

I think part of the problem is that we keep thinking in Apps.

Frameworks encourage that.

They scaffold applications.

They give us routing, state management, rendering systems, build pipelines, dependency graphs and application architecture.

And that's perfectly fine when you're building an application.

But:

Frameworks scaffold Apps.
Components are components.

A component doesn't necessarily need to know anything about your application.

A <date-picker> doesn't care whether the surrounding application uses React, Vue, PHP, Django or plain HTML. Or the car is painted red.

A <relative-time> shouldn't need to know either.

Neither should:

<car-tire>
<steering-wheel>
<playing-card rank="Queen" suit="Hearts"></playing-card>
<mark-down src="playing-card-component-usage.md"></mark-down>
Enter fullscreen mode Exit fullscreen mode

They should just work!



We are still building Apps like it's 1899

There's another problem.

Many developers learned one particular way of building software and then taught those patterns to coworkers, and — directly or indirectly — to AI.

So AI happily reproduces them — and teaches the next generation that this is simply how software is built.

Ask AI to build something and you'll often get an entire application architecture when what you actually needed was:

<something-useful>
Enter fullscreen mode Exit fullscreen mode

The tool isn't necessarily wrong.

We're asking it to build the wrong thing.

That's a mindset change.

Change your perspective from:

Everything is an App

to:

Apps with frameworks. Components with Web Components.

There are Henry Fords out there already working differently.

And I suspect some of them aren't shouting about it.

Why would they?

Once you've trained your tools — and your AI — to produce small, independent components instead of miniature applications, it can become a competitive advantage.


"I can do Web Components better!"

In 2022 there were already around 60 Frameworks, Libraries and BaseClasses listed in:

I-can-do-Web-Components-better (aka All the ways to make a Web Component)

Sixty!

And here's where I think we repeatedly take the wrong turn.

  • You discover Web Components
  • You develop a few helper functions
  • Then: Oh, it needs this feature...
  • Then another feature
  • And another
  • Soon you've created conventions
  • Then abstractions
  • Then dependencies
  • Then documentation

Congratulations!

You're building a framework (or a Design System)
And your ego just publsihed it to NPM

Instead, write the abstractions you need for your components.

  • They don't have to become somebody else's architecture.
  • They don't even have to be shared abstractions in your components.
  • Duplicate your code! Something every "guru" developer told you not to do. A well trained AI is great at managing those.

What about (Google) Lit?

Yes, I consider Lit a framework.

It provides its own abstractions for rendering, reactivity and component state.

That's useful if that's how you want to work.

But it's not the only way to build Web Components.

You don't have to write Lit's HTML template blobs.

The DOM already has an API.

document.createElement("button")
Enter fullscreen mode Exit fullscreen mode

isn't primitive.

It's powerful.

You have the entire browser platform underneath you.

Use it.

Write a one line helper function (sell it to your PM as a mini-Framework)

const createElement = (tag,props={}) => 
                       Object.assign(document.createElement(tag),props);
Enter fullscreen mode Exit fullscreen mode

And you are really using the platform!

Note: That "guru" developer in your team now tells you to make this a library you can import.

Don't! You are creating a dependency!
Use AI to manage your code! It is an AI skill

customElements.define("the-obligatory-counter", class extends HTMLElement {
    constructor() {
        super() // sets and returns this scope
            .attachShadow({ mode: "open" }) // sets and returns this.shadowRoot
            .append(
                createElement("button", {
                    part: "plus button",
                    textContent: "-",
                    onclick: evt => this.count--
                }),
                this._count = createElement("count-value", {
                    part: "count value",
                    textContent: 0
                }),
                createElement("button", {
                    part: "min button",
                    textContent: "+",
                    onclick: evt => this.count++
                })
            )
    }
    set count(val) {
        this._count.textContent = val;
    }
    get count() {
        return ~~this._count.textContent;
    }
})
Enter fullscreen mode Exit fullscreen mode

Developing Web Components

Develop Web Components like you use .reduce():

No developer ever told you that you must use it exactly like they do.

That's the freedom Web Components give us.

There doesn't have to be one architecture.

There doesn't have to be one framework.

There doesn't have to be one correct abstraction.

Build the component.

Give it a useful API.

Let the browser do the rest.


So:

Web Components never failed.

Maybe we just haven't learned how to use them yet.

Browser vendors already showed us how.

Every <input>, <video> and <textarea> is proof that complex functionality can live behind one simple HTML element.

If Browser vendors can do it. Why can't we?



Top comments (3)

Collapse
 
pengeszikra profile image
Peter Vivo •

I’m also interested in web components, so I set out to demonstrate their usefulness.
There is a Markdown editor web component somewhere in my program, too—I think it’s worth checking out.

Collapse
 
dannyengelman profile image
Danny Engelman • • Edited

Yes, I checked out your M A R K E R page
I pasted the contents of this DEV.to post...
Your code needs some work:

<mark-down> is a great example were AI can do most of the work,
because Markdown is an established file format.

My <mark-down> is 2200 LOC because I added more syntax parsing;
which is tottaly fine as long as I do NOT publish it on NPM

I wouldn't be surprised if, 5 years from now, you publish MD on a page,
and a <mark-down> parser is generated ad lib (by the browser)

I learned this lesson from my CDrom adventures in the 90s
Its fine to reduce your 600KB PNG to a 50KB JpegX by hand.
But ALWAYS save & keep your sources, because, one day, the server will do it for you.

Collapse
 
pengeszikra profile image
Peter Vivo •

this program written by hand, so that why so sort ... and unfinished because meanwhile I need to ready the whole program to deadline.