> writing an entire app in vanilla web components is kind of crazy talk in my opinion
Why?
I've done many.
My guiding principles:
- Avoid shadow dom unless it's a library. Stick with the light DOM and css system of your choice.
- Use lit-html or similar for rendering
- Use class properties for reactivity (add a render() call to setters, as needed)
- Ignore attributes entirely. Just use properties.
- Don't bother with composable components and slots. You generally don't need them
- Use a nice router like vaadin or ionic or similar to hoist components and support deep linking
- Let components maintain their own state. Structure the dom so that it's easy to grab state from a component with querySelector. If this doesn't work, I have a little state lib called ApplicationState[1] that works great.
- Really think about what needs to be a component vs normal html. Don't overdo it with components.
- Structure the app with high level "scene" components that map to URL deep links, and app components that you use to build the scenes. Scenes are targets of the router.
I've been doing this for years for many apps for many clients. Blazing fast, simple, no framework churn, no compilation, no framework download or overhead...
It's pretty tough to make myself use a framework at this point.
I didn’t suggest for a moment you couldn’t. I said it was a bit of a crazy decision to take.
The entire reason I said that was because there is going to come a time after you have built probably your 5th component where you are going to start moving a whole bunch of shared logic into a base class that extends HTMLElement and that is the point you should probably stop and just bring in Lit at around 5kb total because they already did exactly what you’re doing and they almost certainly have done a better job with a bigger team and access to browser engineers with thousands of existing users and a bigger test suite with better documentation and well.. you get the point.
A lot of your argument seems to be quite focused on the idea that frameworks are some heavy weight thing which is perfectly true in many cases. But other options exist, and with a 5kb-10kb library download budget those arguments don’t carry a lot of weight.
> after you have built probably your 5th component where you are going to start moving a whole bunch of shared logic into a base class that extends HTMLElement
I kind of thought this too at first, and started down that path several times. I actually wrote a whole framework similar to Lit early on, thinking the same thing.
What I've found over time, is 99% of that is YAGNI (You ain't gonna need it).
All my components just extend HTMLElement directly.
I explicitly dislike Lit because you lose control over the component lifecycle. I don't find it easier, I find it harder - especially when you're mixing in pure js libraries like draggable or whatever.
I prefer having to call render() explicitly, and controlling when/how that's done. At the end of the day, it's not actually any more code.
> a better job with a bigger team and access to browser engineers with thousands of existing users and a bigger test suite
Yeah, I don't need all that to show some interactive markup on the screen and organize code well. That's really what WC's are for me - just a convenient unit of encapsulation for vanilla JS/DOM stuff.
Lit is cool, so's stencil. I just don't need it.
lit-html, however, is probably my favorite piece of tech in the last 5 years. I've been using it since it was originally created and was only like 200 lines of code.
All that code I wrote is still working great, and hasn't needed any sort of update. On the other hand, if I'd gone with the Web Components Framework Of The Day, I'd have done Polymer and caused a massive headache for my clients.
Many people were making the exact same arguments you were about Polymer back then.
And then LitElement.
And then Lit.
Lit 2.0.
Now Lit 3.0.
Same story with <fill in your framework here>.
Angular 1.5 anyone?
Framework churn can kill a company.
I code to standards, keep it as vanilla as possible, and prefer libraries over frameworks (though sometimes the lines get blurry there - looking at you Ionic).
“For the *vast majority* of users there should be no required code changes to upgrade from Lit 2 to Lit 3. Most apps and libraries should be able to extend their npm version ranges to include both 2.x and 3.x, like "^2.7.0 || ^3.0.0".“
Why?
I've done many.
My guiding principles:
- Avoid shadow dom unless it's a library. Stick with the light DOM and css system of your choice.
- Use lit-html or similar for rendering
- Use class properties for reactivity (add a render() call to setters, as needed)
- Ignore attributes entirely. Just use properties.
- Don't bother with composable components and slots. You generally don't need them
- Use a nice router like vaadin or ionic or similar to hoist components and support deep linking
- Let components maintain their own state. Structure the dom so that it's easy to grab state from a component with querySelector. If this doesn't work, I have a little state lib called ApplicationState[1] that works great.
- Really think about what needs to be a component vs normal html. Don't overdo it with components.
- Structure the app with high level "scene" components that map to URL deep links, and app components that you use to build the scenes. Scenes are targets of the router.
I've been doing this for years for many apps for many clients. Blazing fast, simple, no framework churn, no compilation, no framework download or overhead...
It's pretty tough to make myself use a framework at this point.
[1] https://claytongulick.github.io/applicationstate/