Last week in my current project we received a requirement of creating a module and we had to write it in 3 different frameworks as we have to use that module in all 3 projects which are written in AngularJS, Angular 12, and React. Basically, we had to write the same module in all 3 frameworks.
We had a discussion within the team and we got into an idea of creating a Web Component so that we could write the module once and use it in all 3 frameworks. But we had some pessimistic opinions about Web Components. Whether it is a good choice or not, what framework/library or tool we should use, browser support, and integrations with frameworks.
After some long meetings about the Good and Bad parts of the web component, we came to a decision that we should create a POC on the web component and get all the questions/doubts answered.
First let's check what is web component?
Web Components is a suite of different technologies allowing you to create reusable custom elements — with their functionality encapsulated away from the rest of your code — and utilize them in your web apps.As developers, we all know that reusing code as much as possible is a good idea. This has traditionally not been so easy for custom markup structures — think of the complex HTML (and associated style and script) you've sometimes had to write to render custom UI controls, and how using them multiple times can turn your page into a mess if you are not careful.
Web Components aims to solve such problems — it consists of three main technologies, which can be used together to create versatile custom elements with encapsulated functionality that can be reused wherever you like without fear of code collisions.
- Custom elements: A set of JavaScript APIs that allow you to define custom elements and their behavior, which can then be used as desired in your user interface.
- Shadow DOM: A set of JavaScript APIs for attaching an encapsulated "shadow" DOM tree to an element — which is rendered separately from the main document DOM — and controlling associated functionality. In this way, you can keep an element's features private, so they can be scripted and styled without the fear of collision with other parts of the document.
- HTML templates: The <template> and <slot> elements enable you to write markup templates that are not displayed in the rendered page. These can then be reused multiple times as the basis of a custom element's structure.
The Initiative and Research
I took the initiative to create a POC on Web Components as I strongly believed that web components will be a good solution (write once use anywhere) for our requirements and without creating something we cannot judge a framework/library or concept, that is it a good choice or not.I started doing research and the first keyboard I typed on Google was “How to create Web Component”. I got a lot of results and went through most of them from the 1st page of Google Search Result, but was not convinced or I can say I did not get what I was looking for.
I recalled that I had heard about Polymer when I was discussing web components with someone a few years ago. I went to Polymer 3 documentation but it stated that it is under development currently and we should check Lit and link to Lit documentation was provided.
I went to Lit documentation, saw some code and I was overwhelmed and my first impression about Lit was “Wow, this is awesome”.
I was impressed with Lit from the opening paragraph from its documentations overview page which says:
“A Lit component is a reusable piece of UI. You can think of a Lit component as a container that has some state and that displays a UI based on its state. It can also react to user input, fire events—anything you'd expect a UI component to do. And a Lit component is an HTML element, so it has all of the standard element APIs.”
I went through the documentation and created a small app with Lit. I used ViteJs to scaffold my Lit app which, creating the app was very fast as the documentation was good enough for a beginner to get along, but it does not have good documentation about publishing the web component or maybe I couldn’t get the documentation correctly.
I searched a lot but could not get an answer to my question as Lit’s community I felt was not very strong and had limited answers on the internet. I tried reaching out to some friends and I got a suggestion. I told them what I want to achieve and whether I am looking to create a web component is right or not. I got a very positive response on creating a web component . The problem statement I’m looking for is a perfect scenario for a web component and one of them suggested StencilJS.
I went through StencilJS documentation and this time again I had the same impression that this library is great and the documentation is also very nice to use and easy to learn. But this time i did my research on the issue where I got stuck with Lit, and whether I could results for my search with StencilJS or not, and the best part was StencilJS has a good amount of search results and I got what I was looking for.
Time for real action
Now it is time to create a component with StencilJS and check if this suits our needs and can we go ahead and use it in our project. I again went through the documentation and started the project with it. Stencil has its own CLI which scaffolds the project and also can be used to generate components in apps like angular-cli.
What is StencilJS?
Stencil is a compiler that generates Web Components (more specifically, Custom Elements) and builds high-performance web apps. Stencil combines the best concepts of the most popular frameworks into a simple build-time tool.
Stencil takes features such as
- Virtual DOM
- Async rendering (inspired by React Fiber)
- Reactive data-binding
- TypeScript
- JSX
- Static Site Generation (SSG)
- Vanilla JS
- AngularJS
- Angular 14
- React
With StencilJS we can delegate custom events which could be used to send data to the host app and also we can assign methods which can be used from the host app to communicate to the web component.
I was shocked with the results I achieved in such little time though it is a very small app which I have created but as an extremely beginner to the framework it was very nice to achieve results in such less time.
Conclusion
So at the end I came to a decision that we should definitely go ahead with StencilJS and create Web Component rather than writing it on all frameworks which is obviously not a good solution. As an engineer it is our responsibility to provide the best possible solution to any problem or requirement to the project/client.
Link for Code & Demo
You can check the code and demo at the below links:
Component Github Repo: gkhan205/stencil-wc
Published Web Component: npm: cwg-stencil-wc
Vanilla JS Demo: wc-demo-js - CodeSandbox
React Demo: wc-react-demo - CodeSandbox
Angular Demo: wc-angular-2-demo - CodeSandbox
AngularJS Demo: WC-Demo-AngularJS