Architecture of large frontend applications

Architecture of large frontend applications

Von am 02.10.2025

Creating web applications with the size of a prototype is easy. Things get spicy when a frontend application has been under active development by multiple teams and for many years. Ideally, the right measures were taken at an early stage of a project, which allows it to grow in an ordered way. Anyway, it is never too late. With this article, I would like to present my learning on this topic, which resulted from working on such a large frontend application.

Modularization

When you start a new Next or Nuxt application, you are tempted to throw all pages into the folder “pages” and all components into a folder “components,” etc. This will become a horrible mess once the application grows. My first and most important recommendation is to modularize the application ideally from the start. Each module holds its relevant code (pages, components, etc.).

It can be tricky to decide how to draw your modules. You can read the book “The Art of Micro Frontends” by Florian Rappl, which covers this topic in a chapter. The approach which has worked for me and my team was to first identify the domains of your application and make them modules. Later, you can split the code of the domains into further sub-modules representing individual features. With this clear structure, you will be able to navigate your code base easily and to see and enforce dependencies/relationships between the modules of your project.

You might want to convert some modules into micro-frontends, which are loaded at runtime. But be aware of the extra complexity which comes with micro-frontends. Again, I recommend reading the book “The Art of Micro Frontends” by Florian Rappl, which is a comprehensive guide in this regard.

SOLID

When designing software, keeping the SOLID principles in mind is essential. Yet, it seems that there is only little awareness of this among web developers. For creating the architecture of your project, I want to especially highlight two principles.

Open/Closed Principle -> software entities should be open for extension but closed for modifications.
Dependency Inversion Principle -> depend upon abstractions, not concretes.

They will lead to a special approach when designing your code. Let me give you an example. In an e-commerce application, you might have a module holding the code for displaying a product and another module which holds an add-to-cart button. Now, according to the principles, you would create your product view to contain and expose a slot which receives the product data. The module containing the add-to-cart button registers the button inside the product view’s slot. The result is that the module with the product view is extended without having to have knowledge of the add-to-cart button.

Feature flags

You modularized your application, and the code which belongs to the individual domains and features is in the respective location. You might have noticed that this structure encourages using feature flags to enable/disable modules. Feature flags might be necessary because your application is supposed to be distributed in different configurations. But feature flags have another interesting and powerful use: releasing features by activating a feature flag instead of by deploying your application. The idea is, when you are ready to release a feature, you deploy the application without the feature being activated. For more detailed information on the benefits and additional use cases of feature flags, please read the article “Feature Toggles (aka Feature Flags)“ by Pete Hodgson (https://martinfowler.com/articles/feature-toggles.html).

What’s next

I hope this article gave you good ideas on how to design your application. I am looking forward to comments and discussion as this is a very relevant topic to me. This article might require follow-ups which are dedicated to specific technical implementations of the described principles.

Beitrag kommentieren

(*) Pflichtfeld