VueJS Component Library: Why we created our UI component library

Sinisa Grubor
Homeday
Published in
8 min readSep 18, 2019

If you are working in tech industry — specially in frontend engineering or design — you’ve probably heard about design systems and component libraries. You’ve probably also used some of them like Bootstrap, Bulma, Material Design, …. to name a few.

They can be very helpful, when we need to do some work quickly and want our UI to be consistent. Often however, the reality of those libraries can be very different. They rarely fit the branding of your company or desired UX. And when it comes to development, they can be more of a burden than help.

Dealing with CSS specificity issues, overriding default styles, CSS bloat…it can very quickly turn into a nightmare. In that case, it might be better to consider writing your own component library, specifically suited for your branding and use cases. This is what this article is about.

We’re going to look at our path towards building our own frontend component library.

Trying to shape up a generic CSS framework

TL;DR;

We develop multiple products and need to make sure they look and feel consistent. We’ve tackled this issue by defining our design system and building a VueJS (our stack dominant framework) component library — homeday-blocks. If you like to learn more about it, continue reading.

Demo

Source

Many Thanks to…

…the Frontend Team @Homeday:

..and Design Team @Homeday:

Challenge

Frontend engineering team @Homeday started to take its shape and form in early 2017. At that time, our highest priority lied on single new product — our acquisition tool. It needed to be rewritten from jQuery based web widget, to something more maintainable that we can build upon and evolve. VueJS was selected for the task and a few weeks later, we had our new, shiny tools ready.

Next one on the list was our homepage. First version was built with WordPress and it was already screaming for rewrite. So we did just that and used a new CMS framework (Kirby), which offers much better content structure.

With that, we already had 2 products and 2 tech stacks on our hands. Looking a bit further ahead, this was just a start. We’re going to kickoff more new products. The question became clear — how do we minimize the code duplication between all those products?

First try: CSS styleguide

We got our heads together and came up with a plan to abstract the CSS into an independent library.

The idea was simple — let’s start with CSS.

Products might use different tech stacks, so reusing components is not straight forward or it would require a lot of effort (due to different templating engines, server side rendering vs. single page applications, etc.).

Reusing CSS however, was a pretty straight forward improvement. We’ve extracted our base colors, fonts, spacing, buttons,…etc. (mixins) to our own library, gave it a very innovative name — the styleguide ©️ — and started using it cross products.

Life was good — for a while

Single source of truth made our code easier to maintain and it became easier to dispatch visual changes cross products that depended on the library.

Then more products came along. We decided we don’t want to extend our stack with new frameworks if there is no obvious need. We’ve staid in the realm of VueJS and built our Preisatlas with NuxtJS, MeinHomeday with VueJS and other smaller products all using VueJs.

Soon it became clear that there is still a lot of code repetition going on. Styleguide handled shared styles, but a lot of components had similar behaviors, that we had to re-implement cross products. That was a clear call for a second iteration on our styleguide.

Future is not always clear. Keep iterating towards best solution.

Product Engineering Week (PEW)

Every quarter in a year, we dedicate 1 week to something we call Product Engineering Week (PEW). The idea is pretty simple. We cancel all the meetings throughout this week and everyone can dedicate a week to explore new topics and solutions, with learning being the main goal behind it. It starts with kickoff on Monday, where everyone presents their idea to the rest of the team and finishes on Friday with everyone demoing their progress.

In other words, it’s a great time to tackle our second iteration on styleguide.

Second try: Homeday-Blocks

After some discussions, we decided to focus on tackling products that are based on VueJS, as majority — well all expect one — are.
We’ll worry about exceptions later on. First step was to extract all similar components cross products into a single VueJS library, that later became our main component library.

On the following PEW team paired up (thanks Ilyas Amezouar and Oleg Ivaniv for kicking it off) and homeday-blocks were born. It took us a week to try the concept(abstracting similar components to the same library) and in total three product engineering weeks to have library ready for production use. 🚀 In that time, we’ve setup full development environment, CI and integrated storybook to display our components. 👏

The biggest discussion revolved around how do we distribute our component library? And how do other products consume it? At the end, we’ve decided to consume source files directly from the library and the main products will be responsible for build. I will go more in details of tech setup in separate article, for now, I can say, this worked out great! You can see part of the discussion in this PR.

Homeday-blocks components displayed with storybook

Homeday-Blocks: Learning

The good

  • Single source of truth for base building blocks
  • Functioning representation of their design system
  • Consistent UX and UI across line of products
  • Easier UI and UX updates through multiple products
  • Better test coverage
  • Fast kickoff of new products and prototyping

The ”ugly”

  • Communication and collaboration between design and development becomes even more important (this is not really ugly, it’s good, but requires focus)
  • As component library was abstracted after the products have been kicked off, there is some debt to sort out, before you can onboard the components
  • Prioritization of working on component library vs. implementations directly on the products
  • Locking you to single frontend framework

Thoughts

Having an uniformed stack really helped us guiding decisions on how to proceed with building the library. If we would use multiple frontend frameworks, this would have become a different issue.

I also mentioned, our main website is running on PHP. We actually had a lot of discussions what to do with it and how to handle it as server side rendering is crucial — due to SEO benefits. For now, we’ve decided to start using VueJS client side (not as SPA, but as enhancement for dynamic behavior) and are looking into server side rendering with V8JS. This is actually a very cool project and it looks like it makes it possible to use VueJS based component library also in our PHP based CMS system — server side! How awesome is that?! Thanks v8js team for your great work! And I look forward to write an article about that! 🤓

Another thing that needs to be stressed out, is that this can not be purely frontend team effort. There needs to be wider consensus between frontend engineering team, design, product management and stakeholders. It’s critical that everyone is on the same page here and adopt this kind of mindset. For design team that means staying consistent with design system which they created and now became core of the team. It also takes some time to get things right at the beginning, which can cause delays in delivering business value. However, the benefits quickly become clear, especially when we need the same component on 2 places, when we need to kickoff a new product, prototyping or when we just need to update some behavior cross products.
Additionally design team has a functional representation of the design system and we also turned the famous “We have it in the other project, you can just grab it from there, can’t you?” into reality. 😎

Testing was also a special topic for us. We all agreed that testing is important and everyone had an opinion about how to test. After internal discussion (thanks Vinicius Kiatkoski Neves for pushing for tests), we learned that we need more input there. We reached out to Alex Jover Morales from VueDose and he helped us with great workshop about unit testing components in VueJS (thanks Alex Jover Morales for the workshop!).
We still have some work ahead (we’re on ~50% coverage so far), however covering your component library with unit tests is an investment well worth taking. Those tests automatically cover all the products that depend on the library. Talking about time savers…
I would in general recommend unit testing your component library, if you go this route. It makes it just so much easier to catch breaking changes early. Specially when multiple teams are working on it.

Conclusion

Looking back, we can confidently say, that this has proven as a right choice for us. We still have some work ahead— especially in older products, that got outdated, so we can’t directly integrate and replace old components with the new ones. They need to go to through design phase first. I consider this a debt, not just technical, but design debt as well, that we’ll tackle with time. We also need to increase the test coverage, which we are working towards now.

Other than that, we are very happy with the result and the way we use the library now.

The bottom line is — when you have to support multiple products and non of generic design systems work for you, I encourage you to think about this approach and see how you can make it work for your team. And don’t be too harsh on yourself from the start. Give yourself and your team time to get it right. Happy coding!

To make component library work, it requires cross team effort

Contributions

We’ve decided to open source our component library to talk about it and share our learning. If you’re keen to contribute, you can open a PR. We are super happy about test coverage and in return, we will give some constructive feedback about your work. Maybe it sounds like a good deal…let’s see. 😉

Thanks for reading it and we appreciate any feedback or question in the comment section below. If you liked the article, give us a 👏 .

If you want a chance to work on cool projects like these, we’re looking for Frontend Engineers to join our team. Come to Berlin and join us in taking the world! Well, maybe not the whole world, but world of reusable components! :)

--

--

Sinisa Grubor
Homeday
Writer for

Tech leader, advocate of empathic and servant leadership. Passionate about Javascript and software architecture https://www.sinisagrubor.com