History
Feature-Sliced Design has evolved from years of architectural patterns in frontend development. By exploring this history and related approaches, you’ll gain a deeper understanding of why FSD structures code the way it does. This knowledge will help you avoid common pitfalls, make better decisions, and apply FSD more effectively in your projects.
Why frameworks alone aren’t sufficient
Section titled “Why frameworks alone aren’t sufficient”Frameworks and libraries do an excellent job handling technical details like rendering and data fetching, offering reusable and isolated building blocks such as components. However, this foundation isn’t enough to tackle architectural challenges on its own. As projects grow, you need to compose these blocks effectively to manage increasing complexity, facilitate team collaboration, and enable smooth knowledge sharing.
Horizontal slicing
Section titled “Horizontal slicing”One of the earliest methods for organizing frontend code involves dividing it by technical layers, such as components, pages, utils, and stores.
Directorysrc/
Directoryapp/
- …
Directorypages/
- …
Directorycomponents/
- …
Directoryutils/
- …
Directorystores/
- …
This structure remains popular in frameworks like Next.js, Nuxt, and Astro.
A key drawback is that it doesn’t account for the domain: code related to a specific business area gets scattered across multiple top-level folders. Folders like components can expand endlessly without providing isolation between modules.
In FSD terminology, this is known as desegmentation, which is considered a code smell to avoid. While FSD also uses layers, they focus on logical separation rather than purely technical aspects.
Presentational and container components
Section titled “Presentational and container components”Popularized by Dan Abramov in React’s early days, this pattern (also known as smart and dumb components) divides components into two categories: presentational (dumb) components, which handle appearance, and container (smart) components, which manage functionality.
| Presentational | Container |
|---|---|
| Regular DOM and styles | Minimal DOM, no styles |
| No dependency on stores | Interact with stores and pass data/callbacks to presentational components |
| No data fetching or mutation | Act as data sources for presentational components |
This was a helpful starting point for newcomers, but it faced criticism in larger projects:
- Presentational components become tightly coupled to the data shapes and callbacks from containers, so changes in logic ripple through the UI.
- Containers can evolve into “god objects,” shouldering too much responsibility and becoming hard to reuse or test.
- As features grow, nested container hierarchies (e.g., AppContainer > UserContainer > PostContainer) create complex data flows that are tough to trace.
- Logic spread across containers complicates debugging compared to more centralized approaches.
Today, even its creator views this pattern as outdated, thanks to modern framework features like hooks in React, composables in Vue, runes in Svelte, and signals in Angular. These allow domain logic to be handled without relying on class-based container components.
Design principles
Section titled “Design principles”Over the past few decades, numerous design principles have emerged, including SOLID, GRASP, KISS, YAGNI, and DRY. Some, like GRASP, are geared toward object-oriented design, while others, such as KISS and DRY, apply more broadly.
These principles remain valuable and are embraced by developers of all backgrounds.
However, they can be quite abstract and don’t offer concrete structural guidelines. Additionally, they sometimes conflict; for instance, adhering strictly to DRY might violate KISS or YAGNI.
FSD builds on these principles by providing practical guidance: how to structure specific functionality, when to decompose elements, what to prioritize, and more.
DDD, Onion, and Clean Architecture
Section titled “DDD, Onion, and Clean Architecture”
Unlike patterns like MVC, these approaches emphasize modeling the business domain while separating infrastructure and UI code.
However, these approaches come with certain limitations, especially in the fast-paced frontend context:
- Even backend developers often debate the best implementation.
- They primarily address backend concerns and don’t fully handle frontend challenges, where logic and UI are closely intertwined.
- They rely heavily on the inversion of control pattern, particularly IoC containers.
Feature-Sliced Design places a domain-centric focus through its model segment and entities layer, which models business entities and rules independently, similar to DDD’s entities and bounded contexts, while slices provide vertical modularity. FSD layered structure mirrors Onion and Clean Architecture concentric layers, with inner layers like entities and features handling core domain logic and use cases, ensuring dependencies flow inward without relying on heavy IoC containers, making these backend-oriented principles more practical for component-based frontend apps.
- (Article) DDD, Hexagonal, Onion, Clean, CQRS… How I put it all together
- (Talk) Ilya Azin - Feature-Sliced Design (fragment about Clean Architecture, DDD)
- (Article) Alex Bespoyasov - Clean Architecture on frontend
Atomic Design
Section titled “Atomic Design”
Developed by Brad Frost, Atomic Design views the UI as a hierarchy of building blocks, ranging from atoms (basic elements) to molecules (simple components), organisms (complex modules), templates (layouts), and pages.
As web development has leaned toward utility-first CSS and component libraries, this method has become less dominant in general frontend work, though it’s still common in design systems.
However, this approach comes with certain limitations:
- It primarily focuses on design systems and UI/UX, often overlooking business logic.
- Structuring logic within Atomic Design can be challenging.
- The approach may feel too rigid for some dynamic projects.
FSD incorporates Atomic Design concepts in the shared/ui layer for reusable UI primitives, while extending it with additional layers and segments to accommodate business logic effectively.
Feature-driven architecture
Section titled “Feature-driven architecture”Feature-driven architecture serves as a direct predecessor to Feature-Sliced Design, emphasizing the organization of code around domain-specific features. This approach prioritizes grouping related functionality such as UI components, logic, and data handling into self-contained feature modules. By doing so, it aims to improve modularity, scalability, and maintainability in growing applications.
In FDA, features are typically isolated units that encapsulate everything needed for a particular business capability, reducing dependencies and making it easier for teams to work on different parts of the application independently. This can include feature-specific components, services, and state management, all aligned with user stories or business requirements.
While FDA provides a strong foundation for domain-centric organization, it can sometimes lack the granular layering that FSD introduces, such as explicit separation of shared utilities, entities, and UI concerns. FSD builds upon FDA by adding these layers and slices, offering more precise guidelines for decomposition and reuse.
- (Talk) Oleg Isonen - Feature Driven Architecture
- Feature Driven-Short specification (from the point of view of FSD)