Software Architecture

What is Software Architecture? A Guide for Developers

What is Software Architecture? A Guide for Developers

Every software system has a structure, whether or not anyone planned it. That structure is what people call software architecture. It covers the components of a system and the relationships between them, along with the principles that govern how those parts get designed and changed.

Teams judge a structure by the quality attributes it delivers, things like performance and security. Maintainability gets measured the same way.

The code doesn’t spell the architecture out anywhere, and as an application evolves the real structure slides away from the intended one (Ducasse and Pollet, IEEE Transactions on Software Engineering, 2009). Teams write it down separately for that reason.

What is software architecture?

YouTube player

People use the term in two ways. Sometimes it means the structure itself, and sometimes it means the work of deciding on that structure.

Bass, Clements and Kazman of the Software Engineering Institute describe it as the structures of a system, made up of software elements and the relations among them, plus the properties of those elements that other elements can observe.

The version I find more useful on a real project counts only the decisions that cost a lot to reverse once code depends on them. Martin Fowler argued this in IEEE Software (2003), building on remarks by Ralph Johnson.

ISO/IEC/IEEE 42010 only standardizes how an architecture gets described. It says nothing about what makes one good. The second edition came out in November 2022, replaces the 2011 one, and applies to software, systems and enterprises (ISO, 2022).

The scope is a whole software system. A single class, function or script is not an architecture.

It also isn’t a server layout on its own, and it isn’t a single framework or library. A pattern name doesn’t count either. A pattern describes a recurring shape, but many different architectures can implement the same one.

What makes up the structure of a software architecture?

YouTube player

The parts are components, things like services, modules and databases. What they use to talk to each other are connectors, such as API calls, message queues and event streams. Between them sit interfaces, which are the contracts, and over all of it sit constraints, the rules every part has to follow.

What drives the global software industry?

Uncover software development statistics: industry growth, methodology trends, developer demographics, and the data behind modern software creation.

Discover Software Insights →

Components and connectors

Components hold behavior or data, while connectors carry requests, messages and events between them.

A web front end, an order service, a payment module and a relational database all count as components. HTTP calls, message queues and event streams are connectors.

A call to a RESTful API is a typical synchronous connector. A message queue is the usual asynchronous one.

Interfaces, boundaries and constraints

A system boundary marks where a component’s responsibility ends, and every crossing goes through an interface.

That makes the interface the part other teams depend on, so it is the hardest piece to change later. The internals behind it can be rewritten freely.

Constraints narrow the options before design starts. Typical ones are an approved technology list and a latency budget for each request. A rule that the user interface never queries the database directly is another common one.

Coupling and cohesion

Coupling is how much one component depends on another, and lower is better. Cohesion goes the other way. It measures how closely the responsibilities inside one component belong together, and you want a lot of it.

Google Cloud’s DORA research lists loosely coupled architecture among the technical capabilities that predict software delivery performance (DORA guidebook, 2021).

Loose coupling has a price, though. Johnson’s point, relayed by Fowler (IEEE Software, 2003), is that making everything easy to change makes the whole system complex.

Which decisions count as architectural?

YouTube player

Ask what it would take to undo the decision later. If the answer is changes across several components, the decision is architectural. Call it the cost-of-change test. It’s not perfect, since cost is partly a judgment call, but it is the quickest way to separate architecture from detail.

Applying the test

Service boundaries pass easily, and so does the question of which service owns which data. The message broker or primary datastore passes too, along with public API contracts that outside consumers rely on. The programming language usually passes once a team has been hired and trained around it.

On the other side sit the internal class structure of one module and the function names and signatures behind an interface. Even the sorting algorithm a single component uses fails the test. Those are design detail.

Renaming a class or splitting a long function is routine code refactoring. It touches one module, so it is design.

Framework choice sits in between. A thin wrapper is easy to swap out, a deep integration is not.

Where the definitions disagree

Wikipedia’s survey of the literature records different views on scope, from macroscopic system structure to whatever is fundamental to understanding a system in its environment.

Bass, Clements and Kazman treat architecture as the elements of a system and the relations among them. Johnson, quoted in Fowler (2003), put it as what the expert developers of a system agree on about its design. Fowler’s own version is shorter: architecture is what is costly to change (Fowler, 2003).

The three don’t contradict each other on facts, they answer different questions. What a system consists of and who holds the picture of it are two of them. Which choices to get right first is the third.

How does software architecture differ from software design and enterprise architecture?

YouTube player

Architecture sits at the level of one system. Design works inside it and decides how each part gets built, while enterprise architecture looks up and out at the business and IT landscape of a whole organization. Scope is the obvious difference, and the level of detail and the cost of change follow from it.

AspectSoftware architectureSoftware designEnterprise architecture
ScopeOne systemOne module or featureWhole organization
Level of detailStructure and interfacesClasses, algorithms, data structuresCapabilities, processes, systems portfolio
Cost of changeHighLowerHigh, spans several systems
Typical ownerSoftware architectDeveloper or tech leadEnterprise architect
Typical artifactComponent diagram, decision recordsClass diagram, codeCapability map, roadmap

The line between the first two blurs in practice. Architecture contains some design decisions, but not all design is architectural, and a late design choice can force an architectural revision.

Patterns show the difference in level. An architectural pattern such as layered architecture organizes the whole system, while a software design pattern such as Adapter (Gamma et al., 1994) refines the relationship between two components. Buschmann et al. (1996) draw the same line between architectural patterns and design patterns.

The enterprise architecture side is a separate discipline with its own framework. The Open Group released the TOGAF Standard, 10th Edition on 25 April 2022, aimed at enterprise, business, IT, data, systems and solution architects.

ISO/IEC/IEEE 42010 applies the same description concepts to software, systems and enterprises. The levels share a vocabulary even though their concerns differ.

Why does software architecture matter, and which quality attributes does it control?

YouTube player

Qualities like performance and security come out of structure, so architecture decides whether a system meets them. Maintainability works the same way. Adding any of them late means reworking the structure, which is the expensive kind of change.

Bass, Clements and Kazman put this first among the reasons architecture matters (Software Architecture in Practice, 4th edition, 2021). The same book gives ten quality attributes a chapter each. They are availability, deployability, energy efficiency, integrability, modifiability, performance, safety, security, testability and usability.

The ISO/IEC 25010 quality model, revised in November 2023, takes a product view instead. It defines nine characteristics, among them functional suitability, reliability and security.

The two lists overlap but do not match. Settle on one vocabulary before arguing about priorities.

Quality attributeStructural decision that drives itTypical trade-off
PerformanceCaching layer, data locality, async callsStale data, more moving parts
ScalabilityStateless services, partitioned dataOperational complexity
AvailabilityRedundant instances, failoverHigher infrastructure cost
SecurityTrust boundaries, central authenticationAdded latency, team friction
MaintainabilityClear module boundaries, low couplingMore indirection, upfront effort

Non-functional requirements set the target, and the architecture decides how the system reaches it. A system can pass every functional test and still miss its non-functional requirements on response time or uptime.

Attributes also pull against each other. Stronger security checks add latency and more redundancy adds cost, which is why architecture work is mostly trade-off decisions.

What are the main architectural styles and patterns?

YouTube player

Layered, monolithic, microservices, event-driven, hexagonal and serverless cover most of what projects actually pick.

Shaw and Garlan call these architectural styles, where Buschmann and colleagues say pattern. Wikipedia separates the two, with a pattern answering a specific problem and a style being a more general way of building.

StyleBest fitMain weakness
Layered (N-tier)Existing enterprise apps with infrequent updatesSlow release cycle, changes ripple across layers
MonolithicSmall teams, domain boundaries still unclearOne fault or one dependency upgrade reaches everything
MicroservicesComplex domains, frequent updates, several teamsHeavy operational load
Event-drivenIoT, streaming, real-time processingEvent ordering, delivery guarantees, eventual consistency
ServerlessSpiky, event-triggered workloadsCost and latency under steady heavy load

The layered, microservices and event-driven rows follow Microsoft’s Azure Architecture Center guidance. The monolithic and serverless rows reflect widely documented trade-offs.

An event-driven architecture swaps a simple request flow for loose coupling. Producers publish events and consumers react in near real time.

Hexagonal and clean architecture

Alistair Cockburn’s hexagonal architecture and Robert C. Martin’s clean architecture both keep business rules free of frameworks and databases. Dependencies point inward, so a web framework or datastore can be replaced without touching the core.

They refine layered design rather than replace it.

Domain-driven design and CQRS

Eric Evans’s domain-driven design cuts boundaries along business domains, which is how many teams decide where one service ends.

CQRS is a different move. It splits the read model from the write model so each scales and changes on its own.

Monolith or microservices

YouTube player

The most argued comparison is one deployable unit against many. A microservices architecture splits the system into independently deployed services, while a monolith ships as one.

A monolith gives you one deployment unit and one test pipeline, and calls stay in-process instead of crossing the network. The cost is that a crash in one module can take the whole service down, and a library upgrade can break several features at once.

Microservices deploy and scale independently per service, and faults stay inside one service. What you pay for that is network calls, distributed data and more infrastructure to deploy, monitor and secure.

How to choose an architectural style

Choose the style from the quality attributes the system cannot miss, then test the shortlist against team size and domain clarity. Fashion is not a criterion, and the simpler style is often the right one.

A selection process that holds up

  1. Rank the quality attributes and keep the top two. Everything below them is negotiable.
  2. List the hard constraints, such as budget, hosting, compliance rules and the skills the team already has.
  3. Map the team structure. Melvin Conway argued in Datamation in 1968 that a system’s design copies the communication structure of the organization that builds it, so the style has to fit the teams.
  4. Shortlist two styles and record the trade-offs of each in a short decision record.
  5. Test the riskiest assumption with a prototype, for example the throughput of one critical path.
  6. Set a measurable trigger for revisiting the choice, like deployment time or on-call load.

Where the fashionable choice failed

Microsoft’s Azure Architecture Center rates microservices as harder to build and run than N-tier or web-queue-worker designs. It says they need mature development and DevOps practices.

Segment ran over 140 services in 2018, and three full-time engineers spent most of their time keeping the system alive. The team consolidated everything into a single service (Noonan, Segment blog, 2018).

Prime Video engineers moved an audio and video monitoring service from distributed components to a monolithic architecture and cut infrastructure cost by over 90% (Prime Video Tech blog, March 2023). It was one service, not the platform.

Shopify weighed microservices against its giant Rails codebase and chose a modular monolith instead, with one codebase and boundaries between components enforced (Shopify Engineering, 2019).

For a small team with unsettled domain boundaries, start with a modular monolith. That’s my default anyway. Splitting a well-bounded monolith later is a planned move, while merging services back together, as Segment did, means migrating queues, tests and dependencies.

How is software architecture documented?

YouTube player

Teams document architecture with views of the structure plus a log of the decisions behind it. 4+1 and C4 organize the views, arc42 gives you a full template, and architecture decision records (ADRs) hold the reasoning.

ISO/IEC/IEEE 42010 specifies requirements for architecture viewpoints and model kinds, which is the idea these approaches put into practice. The aim is software documentation that still makes sense after the original team has moved on.

ApproachStructureBest for
4+1 view model (Kruchten, 1995)Logical, process, development and physical views, tied together by scenariosSystems with distinct audiences: developers, integrators, system engineers, end users
C4 model (Simon Brown)Four zoom levels: context, containers, components, codeDiagrams for mixed technical and business readers
arc42 (Starke and Hruschka, 2005)Twelve sections, from introduction and goals to glossaryA complete documentation set in one structure

Kruchten’s paper states that the 4+1 model is not tied to any notation. UML is optional.

Why C4 uses zoom levels

One diagram that shows everything becomes unreadable, and one that shows a single slice loses the bigger picture. Brown’s answer is a set of related diagrams, each at its own level of detail.

Architecture decision records

Michael Nygard proposed the ADR format on 15 November 2011 (Cognitect blog). A record usually carries these pieces:

  • A title that names the decision in a short noun phrase
  • A status, either proposed, accepted, deprecated or superseded
  • The context, meaning the facts and forces behind the decision
  • The decision itself, in whatever words the team chose
  • The consequences, all of them, negative ones included

Write one record per decision, and supersede an old record instead of rewriting it. Keep the files in the same repository as the code, under source control, so a decision and the change it caused share one history.

How is an architecture evaluated and kept from drifting?

YouTube player

An architecture is evaluated by testing it against quality attribute scenarios, most often with the Architecture Tradeoff Analysis Method (ATAM) from the Software Engineering Institute. It stays honest afterward only if the code is checked against the intended structure.

ATAM

ATAM runs nine steps across two phases (Kazman, Klein and Clements, SEI, 2000), and what comes out is a set of findings that fall into four types.

Risks are decisions that threaten a quality attribute goal, and non-risks are the ones that support business goals. Sensitivity points are elements where a small change moves a quality attribute a lot. A trade-off point is a sensitivity point that affects more than one attribute.

SEI’s own material says the purpose is to discover risks created by architectural decisions, not to produce precise measurements. It is a risk-mitigation method that can run early, while changes are still cheap.

It is also heavy. Small or low-risk systems get more value from a lighter review, and Software Architecture in Practice (4th edition, 2021) devotes a section to lightweight evaluation for that case.

Architectural drift

Architectural drift is the gap between the intended architecture and the one the code implements. Researchers call it architecture erosion.

A mapping study of 73 studies found both technical causes, such as violations, evolution problems and unpaid technical debt, and non-technical ones, such as knowledge vaporization (Li, Liang, Soliman and Avgeriou, Journal of Software: Evolution and Process, 2022). Detection tools exist, but more than half support only one programming language.

Boundary checks in the build help, and Shopify’s Packwerk for Ruby on Rails is one example. Reviewers who know the intended boundaries help during the code review process. And whenever a structural decision changes, write a new decision record.

What does a software architect do?

YouTube player

An architect turns requirements into structure and guides the teams that build it, keeping the decisions written down along the way. The SEI describes the role in terms of duties, skills and knowledge (Bass, Clements, Kazman and Klein, 2008).

Core responsibilities

The architect makes the structural calls, meaning the style, the boundaries and the interfaces. They also keep the decision records current and translate quality attribute goals into terms the business and the developers share.

The last job is drift control, which means reviewing the code against the intended structure.

The role overlaps with other software development roles, but a senior developer answers for a component while the architect answers for the whole structure. In a small team the role is usually shared. A large organization makes it a full-time post.

Staying close to the code

Martin Fowler recommended at the 2015 O’Reilly Software Architecture Conference that architects spend time in the application codebase, for example by examining commits (InfoQ, 2015).

An architect who only draws diagrams loses sight of drift.

Team boundaries shape the system

Microsoft Research tested a question close to Conway’s idea on Windows Vista: whether organizational structure predicts software quality. Organizational metrics were statistically significant predictors of failure-proneness, and they identified failure-prone binaries with higher precision and recall than churn, complexity, coverage, dependencies or pre-release bug counts (Nagappan, Murphy and Basili, ICSE 2008).

That is why a software architect also has a say in how teams are split.

Software Architecture FAQ

Does every software system have an architecture?

Yes. A system has an architecture whether or not anyone designed or recorded it.

The only choice is between a deliberate structure and an accidental one that grew out of unreviewed decisions.

How do application architecture, system architecture and software architecture differ?

Application architecture stays inside one application. System architecture is wider and takes in everything the system contains, hardware and networks included, along with several applications at once.

Software architecture is the software-side structure at either scale.

Is MVC an architecture or a pattern?

It’s an architectural pattern, and Buschmann and colleagues list it among theirs. It splits the user-interface part of an application into model, view and controller.

It says nothing about deployment, data storage or integration, so a complete architecture still needs those decisions.

Does agile mean skipping upfront architecture?

No. Agile changes when architectural decisions are made, not whether they are made.

Teams settle the costly-to-reverse decisions early, defer the rest, and log each one in a short decision record.

Do I need UML or an architecture description language?

Neither is required. Kruchten’s 4+1 model is not tied to any notation, and the C4 model does not mandate one.

An architecture description language is a formal notation for components and connectors, useful when a team wants models that tools can check.

What is a reference architecture?

Teams use one as a proven template for a class of systems, taking the components, relationships and constraints it supplies and adapting them to their own case.

Cloud providers such as Microsoft publish them through resources like the Azure Architecture Center.

How Much Software Architecture Does a Project Need Up Front?

Software architecture work before coding should cover only the decisions that are expensive to reverse. Everything else waits for evidence from running code.

Settle them in dependency order. Quality attribute priorities come first, then the style and component boundaries, then the interfaces to external systems. Each choice constrains the next, and external interfaces are the hardest to change once other teams depend on them.

Deferring the rest trades early certainty for rework in whatever stays open.

The architect calls each review, but the team carrying the on-call load holds a veto. A style whose operating cost grows with every added service needs an owner before the first split. At Segment, the service count grew with every destination the team added, about three a month, until three engineers spent most of their time keeping the system alive (Noonan, Segment blog, 2018).

Decisions that survive review then move into a design document, which turns structure into component-level detail.

Bogdan Sandu

Stay sharp. Ship better code.

Every week: one curated article, one tool worth knowing, one tip you can use tomorrow. No noise, no padding.