Meet the the very first Experts Zone podcast! Experts Zone is the place where our professionals will share the precious experience in design, development, project management and other fields. Concrete and useful information for you from your Frontend House experts.
The host of the first Experts Zone episode is the tech lead at Frontend House Tomasz Krajewski. The topic is Micro Frontends - foundations.
Why the topic is useful: it gives a different approach to how to deal with the modularisation in our apps, so it's worth to know how to deal with it in different ways.
In today's Experts Zone #1 episode you will find:
- 00:00 - Intro
- 00:54 - Contents
- 01:30 - Software architecture
- 01:47 - Monolith architecture
- 03:17 - Distributed architecture
- 06:04 - Micro Frontends
- 09:25 - Why might we use that?
- 11:23 - The Vanilla Example
Hello, my name is Thomasz Krajewski, and I'm tech lead at Frontend House. Probably you know me from the Frontend News podcast, but today I'm here at Experts Zone to share with you a really hot and awesome topic, which is Micro Frontends. Why is it going to be interesting? Well, it gives a different approach with how to deal with the modularization in our apps, so it's worth knowing how to deal with it in different ways. Are you interested? Check it out and leave your comments. Thank you.
OK, guys, as I promised, we are going to speak about micro frontman's foundations. Let me share the agenda first so we will speak about software architecture, monolith architecture, distributed architecture. Then we are going to speak about micro frontents, discuss if it is really worth to use in our projects? And I would like to share the Vanilla.js example to show you how to deal with the micro frontend set up. At the end I would like to summarize everything and I hope you will enjoy the whole show.
So at first, let's speak about software architecture. In the short term, the software architecture is about organizing the whole system. What we need to define the components, relations between the components, environment, rules and design patterns. Monolith architecture is the example of the architecture that is using a single application to encapsulate the whole business logic and other problems that are related to creating our app. It means that the front end layer, business logic layer and database layer are closed in terms of the single app, for example, Ruby on Rails apps. The pros and cons of using monolith architecture are: as I've mentioned before, we encapsulate all problems and solutions under the single application. On complexity growth, unfortunately, it's hard to scale such applications. Security of data storing and communication is easy to achieve or easier than on the distributed architecture. But I will explain that later. We have reduced palette of technologies used to resolve certain problems. Unfortunately, using the monolith architecture has a lack of modularity and it's really hard to take a single piece from our app and inject it somewhere else.
But what is good, monolith architecture is good for startups and for the very first part of the company app because it's really easy to start a development. You do not have to take care of configuration of the complex ecosystem and define the relations between each of the parts.
Another example of architecture is distributed architecture. In the previous example, we were closing all of the logic under the single application. Distributed architecture has different assumptions, so it's mostly focused on the back end site. But I will try to prove later that it also reflects the front end. But yeah, first thing first. So the distributed architecture assumes that we split our business logic into single apps that resolve a certain part of the business functionalities. So for example, instead of having the monolith Ruby on Rails app, we can define three micro services that will deal with the specific problems.
For example, patients micro service that will contain the patient API and patient database, hospital micro service that will be responsible for resolving the hospital related logic and micro service that will be responsible for authorizing our users. What is worth to mention is that in distributed architecture we have also included something that is called Gateway API Gateway, to be more precise. API Gateway is being responsible to take care of the communication between all of these micro services and expose the single API to the rest of the world.
I hope it makes sense. And pros and cons of this approach. So micro services and distributed architecture at all have a really high performance under the huge traffic. This solution is really easy to scale. Higher complexity at the beginning of implementation makes it really hard to start our project. And, you know, we need to think about a lot of the problems at the beginning of the whole development process. What is good? We have a wide palette of technologies that we are able to use in our project or in our micro services projects because each of the micro service is a separate app.
The bad side of using that approach is that we need to think about how to provide a good security between each of the micro services and how to secure the data and the communication. OK, the last cons, is that we have increased response time, and that depends on the number of notes that we need to use to process the request.
OK, guys, now it's time to deal with the microgrants topic. So what exactly is it?
Micro frontends are for the front end. The same as micro services are for the backend. It means that we are accommodating the distributed architecture and adjust it to be used in our front end application. As I explained, in the monolith approach we have the single app that closes all of the business logic into the single app. The micro frontends assumes that we split our client up into smaller chunks, into smaller app to be able to manage all this closed business features under the single app that can be done by the separate project team.
What is important and it looks similar like in micro services, we have something that is a gateway, but let's call it a shell app.
The responsibility for the shell app is to make sure that all of our micro contents, our micro apps are well-communicated and they react properly on the location change or on the global stage change. What I like the most about using micro frontends is that each of the apps, each of the micro frontends can be realized in a separate technology. This gives a really big boost for how we deal with the problems. Why? The answer is quite simple. For example, it's not like Angular will resolve all of our problems we will be struggling during the app development. And for some cases, React looks better to resolve problems with building the small, fast and efficient module, let's say schedule. And yeah, thanks to the micro frontends, we can pick the best technology that will precisely resolve our issue instead of adjusting the one technology to be able to solve all of our problems.
And what you can see on the presentation right now is the distributed architecture for the front end and for the back end perspective and how it looks like being combined together. So each of our micro front end apps is able to speak with the certain microservices through the API gateway, and that works pretty fast if we don't have to process the data in a lot of different Nodes.
Why might we use that?
The question is good and there are good answers too.
First of all, if our back end architecture assumes that we will create a lot of micro services that will have certain responsibilities, we should think about how to create our front end layer in a best maniere. It means that we should figure out how to communicate our client app with all of our micro services. And if we want to go full on with a distributed architecture, we can think about creating the specific modules that will be responsible to communicate with the single micro service and combine those micro apps all together under the shell app and expose it to the world.
But, you know, micro services are not the only answer when it's worth using the micro frontends.
The second thing - which in my opinion is a really great usage example of micro frontends - is when we would like to migrate from one technology to another. Instead of making the revolution in our client up, we can slowly, step by step, migrate, for example, from Angular into React and what we get thanks to that approach, we can test our concept. We can test if the migration will be successful before we rewrite the whole application, for example, we can check the single module and proof that our concept is OK and it's safe to be implemented for the rest of the app. As I said, micro frontends give us the possibility to choose technology with surgical precision. Thanks to granularization, we are able to use white palette of technologies. In consequence, the tools that are picked to resolve the business problem can be chosen precisely and give the best performance solution.
The Vanilla Example
And now it's time for some Vanilla.js examples, which will introduce you to the world of the micro frontends. As I promised, I want to share with you the simple example of the micro frontend set up. I have defined three apps: game app, scores app and shell app. Each of this apps has a totally separate environment and we can use whatever we want to resolve the particular problems.
The Shell app responsibility is to run our smaller modules, our micro frontends within the single app and expose it to the user. Inside the source directory, we have our index and the really small block of the code. And what actually is going on here is when we load our documents, we want to register our micro frontends. I have created the register game and register scores methods inside the game and scores up and attach them to the micro frontend namespace. So this is our first argument of the register method, right? The second argument is the id of the div where we want to render our micro frontend app. This is pretty simple. Let's check the index.html, just to quickly jump in. As we can see, those ideas are here. And the third argument, this is the storage, and what's inside the storage is a single instance of the storage class, which defines two methods.
And what it's worth to mention is the data object that contains this course. This will be like our, let's say, shared memory between our apps.
But obviously you want to react somehow to the value change. And we've got two methods.
Increment scores modify our scores value. And this part of the event to inform our apps that “hey course has been changed”.
The subscribed method allows us to subscribe and listen for the previously emitted event and react on the change by triggering the callback function.
It's pretty simple, right?
So let's check the course app. Scores app contains the register score methods. It's obvious, and it has been attached to the micro front end namespace and what's going on in here is actually creating the HTML counter element and subscribe to the scores change.
Thanks to sharing our stories instance, it's pretty simple to use it, we can just trigger the subscribe methods on the storage class instance and pass the callback function. And after we receive the update the scores, we can update our HTML counter.
We download block.
This is something that allow us to test our micro frontend app without need of running the shell app so we can work on this module separately, in a separate team.
OK, so the game app is also pretty simple.
We are creating the HTML bottom and attach the action for this button. So each time we click it, we are incrementing our scores value inside the storage. This is the separate app, so it's not a scores app, it's a game app. Yes. And we have defined the register game method to be able to render it in our shell app. And in the same example we have the window.onload, which allows us to test the game app without running the shell app.
One thing worth mentioning is that we have to overwrite our increment scores because the storage is not being created inside the game.app. It's being passed from the shell.app, so we need to somehow mock up this API and this construction is pretty simple. OK, we have three apps: the shell app that renders the game and scores app, the scores app that displays the scores and game app that allows us to increment the score. Let's check how it looks in real life. And yes, I know the minimalism is really here to huge in here.
So each time we click the bottom, the scores value should be incremented by one in this case.
Let's check it out. Yes, it works and how does it communicate? As I mentioned, we are sending events each time we increment score and we have this event listener we are using inside this scores app. Does it make sense?
I hope you understand the very basics of the micro frontends configuration.
And believe me, this is the really simple, simple row example. But imagine what you can do with the micro frontend approach. Distributed architecture opens a lot of possibilities for us. Thank you for your attention.
I hope you enjoy this small example at the last slide. I would like to show you that micro frontends is not an experimental architecture, but it is the tool, the approach, that is widely used all around the world, for example, by Zalando, Ikea, Microsoft, Leroy Merlin or Starbucks. Thank you for your attention and I hope to see you in the next chapters.
Tommy K, bye bye.