System Design Space
Knowledge graphSettings

Updated: April 16, 2026 at 7:09 AM

Clean Architecture (short summary)

medium

“Clean Architecture” is interesting not because of the circles, but because of the question behind them: what should a system actually depend on? The book is about keeping business logic resilient while databases, frameworks, interfaces, and delivery mechanisms keep changing around it.

Inside a service, it gives a very practical frame for module boundaries, dependency direction, SOLID, cohesion, coupling, and plugin-style thinking. That helps teams separate domain logic from infrastructure details instead of letting the codebase collapse into a tangle of controllers, integrations, and use cases.

In interviews and reviews, the chapter adds depth inside the system. It lets you discuss not only the outer design, but the internal structure as well: where responsibilities sit and why dependencies should point in a particular direction.

Practical value of this chapter

Module boundaries

Teaches clear boundaries between domain, application, and infrastructure to reduce coupling.

Dependency direction

Builds dependency discipline so business logic is insulated from framework details.

Evolvable code

Keeps systems easier to test, refactor, and extend as product scope grows.

Interview depth

Enables strong discussion of internal service design beyond high-level architecture sketches.

Source

Review on tellmeabout.tech

Article from the Code of Architecture club - part 1

Перейти на сайт

Clean Architecture: A Craftsman's Guide to Software Structure and Design

Authors: Robert C. Martin
Publisher: Pearson, 2017
Length: 432 pages

Uncle Bob's classic on structural value, programming paradigms, SOLID, component cohesion and coupling, and plugin-style architecture.

Original
Translated

Introduction: Design and Architecture

The opening chapter makes a simple but demanding claim:

"When software is done right, it requires a fraction of the human resources to create and maintain. Changes are simple and rapid. Defects are few and far between."

Architecture = Design?

Martin treats architecture and design as one continuous spectrum of decisions, from large system boundaries down to low-level implementation details.

Main conclusion

“The only way to go fast is to go well” means speed is not the alternative to architecture. It is one of the outcomes of getting the structure right.

Related book

A Philosophy of Software Design

Ousterhout also talks about dealing with complexity and strategic programming

Читать обзор

Two aspects of software value

Every software system creates value in two different ways:

Behavior

This is the functional side of the system: what it does for the business and the user. Teams usually experience this as the urgent part.

Structure

This is the structural side: how easy the system is to change, test, and extend. It is important, but often treated as less urgent.

The author frames this conflict through the Eisenhower matrix. In practice, teams often let urgent feature work crowd out architectural decisions that determine the long-term cost of change.

"It is the responsibility of the software development team to assert the importance of architecture over the urgency of features."

Programming Paradigms

The book makes an important point here: each paradigm matters not because of what it enables, but because of what it forbids. Those constraints shape architecture:

ParadigmLimitationAdvantageFor architecture
Structured Programming
Ban gotoDecomposition into testable functionsFunctional decomposition
Object-Oriented Programming
Safe polymorphismPlugin-style structure and dependency inversionComponent separation
Functional Programming
ImmutabilityFewer race conditions and hidden side effectsSeparation of mutable and immutable state

Structured Programming

Dijkstra showed that programs can be expressed through three basic control structures:sequence,selection, anditeration. For architecture, that matters as the basis for clear decomposition and testable control flow.

"Testing shows the presence, not the absence, of bugs" — Dijkstra

Object-Oriented Programming

OOP combines encapsulation, inheritance, and polymorphism. From an architectural point of view, polymorphism matters most because it enables dependency inversion and lets details evolve more independently.

"OO is the ability to gain absolute control over every source code dependency in the system."

Functional Programming

Its core idea is immutability. Architecturally, that means fewer race conditions and deadlocks, and it naturally connects to patterns such as Event Sourcing.

"Event sourcing is a strategy wherein we store the transactions, but not the state."

Part 2

Review on tellmeabout.tech

SOLID and component principles

Перейти на сайт

Design Principles (SOLID)

The SOLID principles help build mid-level software structures that are:

  • easy to change without a cascade of side effects
  • easy to understand
  • strong foundations for reusable components

SOLID principles

Click on the letter for details

SSingle Responsibility Principle

Not "a function should do one thing", but a module must be responsible to one actor. Symptoms of the violation: accidental duplication and merge conflicts.

OOpen-Closed Principle

An artifact should remain open to extension while protecting stable behavior from constant rewrites. That is one of the forces that drives architecture in the first place.

LLiskov Substitution Principle

Subtypes must remain interchangeable with the base type. Once that promise breaks, code starts accumulating special branches for every implementation.

IInterface Segregation Principle

Clients should not depend on methods they do not use. At the architecture level, that means avoiding dependencies on oversized components and oversized contracts.

DDependency Inversion Principle

The most flexible systems are the ones whose source code dependencies point only to abstractions. Factories help move concrete construction details out of policy code.

Dependency Inversion with a factory

How abstractions and factories reverse dependency direction

Application
High-level policy
depends on
ConcreteImpl
Low-level detail
Step 1 from 4
Problem: direct dependence

Application directly depends on ConcreteImpl, so policy is tied to implementation detail.

Related book

Fundamentals of Software Architecture

Richards and Ford continue the discussion of coupling and coordinated change through Connascence

Читать обзор

Component Principles

Components are units of deployment. One of the book's strongest takeaways is that long-term architecture tends to move toward stable cores surrounded by replaceable details.

Component Cohesion

Three principles govern how to break down classes into components:

REP

Reuse/Release Equivalence
Classes released together should share a clear theme or reason to live together.

CCP

Common Closure
Group together classes that tend to change for the same reason and at the same time.

CRP

Common Reuse
Do not make component users depend on behavior they do not actually need.

Tension Diagram: Component Cohesion

Too many unneeded releases
Hard to reuse
Too many components change
REP
Reuse/Release
CCP
Common Closure
CRP
Common Reuse

Architects balance these principles differently depending on whether the system needs cleaner reuse, fewer coordinated releases, or more localized change.

Component Coupling

The next principles govern the relationships between components rather than their internal makeup:

ADP: Acyclic Dependencies Principle

Avoid cycles in the component dependency graph.
The graph should stay directed and acyclic. When cycles appear, teams usually break them by introducing an abstraction and inverting dependencies.

SDP: Stable Dependencies Principle

Depend in the direction of stability.
Fan-in and Fan-out make that visible: more incoming dependencies and fewer outgoing ones usually mean a more stable component. I = Fan-out / (Fan-in + Fan-out) gives a compact stability signal.

SAP: Stable Abstractions Principle

A component should be as abstract as it is stable.
A = Na / Nc measures how abstract a component is. Together with SDP, this principle brings dependency inversion to the component level.

Main Sequence and risk zones

Zone ofPainZone ofUselessnessMainSequenceI: InstabilityA: Abstractness(0,0)(1,0)(0,1)(1,1)
Main Sequence

Ideal diagonal: a balance between abstractness and stability. Formula: D = |A + I - 1|

Zone of Pain

Concrete and stable components (A≈0, I≈0). Hard to change because many dependencies rely on them.

Zone of Uselessness

Abstract and unstable components (A≈1, I≈1). Abstractions that are weakly connected to real implementations.

Main architectural takeaway

Structure cannot be postponed

If architecture is always deferred, every next change becomes more expensive than it needs to be.

Plugin Architecture

Polymorphism and dependency inversion let stable policy stay in the center while replaceable details evolve around it.

Structure must evolve

Component boundaries are not designed once forever. They need to evolve as the product and its pressures change.

Main Sequence

Healthy components stay close to the main sequence instead of drifting into painful rigidity or useless abstraction.

Sources

Related chapters

Where to find the book

Enable tracking in Settings