Master the 23 Core Software Architecture Principles Every Engineer Should Know
This article presents a concise overview of 23 essential software architecture principles—from Dependency Inversion and Separation of Concerns to Bounded Context and KISS—explaining each concept, its practical impact, and providing code examples to help developers design clean, maintainable systems.
Software architecture is built on a set of fundamental principles that experienced architects apply to create robust, adaptable systems. Below is a rapid tour of the daily principles most architects follow.
1. Dependency Inversion
This principle states that dependencies should point toward abstractions rather than concrete implementations. By inverting the direction of control, high‑level modules are not forced to depend on low‑level details.
2. Separation of Concerns (SoC)
Systems should be divided according to the type of work they perform—such as business logic, infrastructure, or UI—making development, testing, and deployment easier. SoC drives many architectural styles like Domain‑Driven Design, Hexagonal Architecture, and Clean Architecture.
3. Inversion of Control (IoC)
IoC extends the idea of Dependency Inversion to the overall flow of control, often delegated to frameworks (e.g., Spring) that manage object creation and wiring instead of the application code.
4. Dependency Injection
Dependencies are supplied at runtime, typically via constructors. The following example shows an Action interface injected into a Human class to decide which concrete action runs.
package az.alizeynalli.di;
public interface Action {
void do();
}
public class HumanAction implements Action {
@Override
public void do() {
System.out.print("run");
}
}
public class Human {
Action action;
public Human(Action action) {
this.action = action;
}
@Override
public void do() {
action.do();
}
}
public class Main {
public static void main(String[] args) {
Human human = new Human(new HumanAction());
human.do();
}
}5. Single Responsibility
Each building block—whether a plugin, package, class, function, or variable—should have only one reason to change.
6. DRY (Don’t Repeat Yourself)
Avoid redundant code by reusing existing functionality instead of copying identical snippets.
7. Open‑Closed Principle
Software entities should be open for extension but closed for modification, minimizing the need to alter existing code when adding new features.
8. Persistence Ignorance
Business logic should remain independent of any specific database or persistence technology, allowing the underlying storage to change without affecting higher‑level code.
9. YAGNI
You Aren’t Gonna Need It—avoid premature optimization and over‑engineering by only implementing features that are truly required.
10. Boy Scout Rule
Leave the codebase cleaner than you found it; refactor when encountering anti‑patterns to improve long‑term quality.
11. Liskov Substitution
Objects of a subtype must be replaceable for objects of the supertype without altering the desirable properties of the program.
12. Encapsulation
Restrict external access to a component’s internal state, typically by using private members or access modifiers.
13. Loose Coupling
Dependencies between components should be minimal so that changes in one part have little impact on others. Techniques include Dependency Inversion, asynchronous messaging, and event sourcing.
14. Cohesion
Measures how closely related the responsibilities of a single module are; high cohesion supports maintainability and aligns with Single Responsibility.
15. Interface Segregation
Clients should not be forced to depend on interfaces they do not use; this principle is most relevant for statically typed languages.
16. Bounded Context
A central pattern in Domain‑Driven Design that partitions a large system into distinct conceptual modules, each with its own model and data store.
17. Stable Dependencies
Components should depend only on reliable, stable artifacts—an idea especially pertinent to Docker images and external libraries.
18. Polymorphism
One of the four pillars of object‑oriented programming, allowing entities to be used in multiple forms.
19. Modularization
Divides a system into independent modules, extending the Single Responsibility principle to the architectural level.
20. Abstraction
Focuses on essential characteristics while ignoring irrelevant details, akin to generalization.
21. KISS (Keep It Simple, Stupid)
Encourages simple, easy‑to‑understand code to reduce misunderstandings.
22. Incremental/Iterative Approach
Core to agile development; each iteration adds functionality while ensuring the system remains operational.
23. Least Knowledge (Information Hiding)
Components should only know what they need to, limiting the spread of information across the system.
Below is a concrete example of a service interface and its implementations that illustrate the Stable Dependencies and Interface Segregation principles.
package az.alizeynalli.cashflow.core.service;
public interface ConverterService {
Income convertIncome(Income income);
Expense convertExpense(Expense expense);
}
@Component
public class ExpenseConverterServiceImpl implements ConverterService {
@Override
public Income convertIncome(Income income) {
throw new UnsupportedOperationException();
}
@Override
public Expense convertExpense(Expense expense) {
// convert expense here
return expense;
}
}
@Component
public class IncomeConverterServiceImpl implements ConverterService {
@Override
public Income convertIncome(Income income) {
// convert income here
return income;
}
@Override
public Expense convertExpense(Expense expense) {
throw new UnsupportedOperationException();
}
}These principles collectively guide architects toward building clean, maintainable, and adaptable software systems.
Signed-in readers can open the original source through BestHub's protected redirect.
This article has been distilled and summarized from source material, then republished for learning and reference. If you believe it infringes your rights, please contactand we will review it promptly.
21CTO
21CTO (21CTO.com) offers developers community, training, and services, making it your go‑to learning and service platform.
How this landed with the community
Was this worth your time?
0 Comments
Thoughtful readers leave field notes, pushback, and hard-won operational detail here.
