Thanks to visit codestin.com
Credit goes to www.scribd.com

0% found this document useful (0 votes)
119 views28 pages

Practical Model C4

This document presents the C4 model for documenting software architectures. The C4 model consists of a hierarchy of four diagrams that represent the architecture at different levels of detail: context diagram, container diagram, component diagram, and code diagram. The C4 model provides a simple way to communicate software architecture to different audiences using different levels of abstraction.
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as DOCX, PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
119 views28 pages

Practical Model C4

This document presents the C4 model for documenting software architectures. The C4 model consists of a hierarchy of four diagrams that represent the architecture at different levels of detail: context diagram, container diagram, component diagram, and code diagram. The C4 model provides a simple way to communicate software architecture to different audiences using different levels of abstraction.
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as DOCX, PDF, TXT or read online on Scribd
You are on page 1/ 28

AUTONOMOUS UNIVERSITY

“GABRIEL RENE MORENO”


FACULTY OF ENGINEERING IN COMPUTER SCIENCES AND TELECOMMUNICATIONS

PRACTICAL

“MODEL C4, COMPONENT DIAGRAM AND DIAGRAM ORGANIZED IN LAYERS”

Santa Cruz, June 30, 2020


THE C4 DOCUMENTATION MODEL FOR SOFTWARE ARCHITECTURE
Main points

 The creation of software diagrams decreased as a result of the shift in the use of agile
methodologies. When diagrams are created, they are often confusing and unclear.

 The C4 model consists of a hierarchical set of software architecture diagrams for context,
containers, components, and code.

 The hierarchy of C4 diagrams provides different levels of abstraction, each of which is relevant to
a different audience.

 Avoid ambiguity in your diagrams by including a sufficient amount of text as well as a key or
legend for the notation used

Software architecture diagrams are a great way to communicate how you plan to build a software
system (initial design) or how an existing software system works (retrospective documentation,
knowledge sharing, and learning).

However, there's a good chance that most software architecture diagrams you've seen are a confusing
mess of boxes and lines. An unfortunate and unintended side effect of the Agile Software
Development Manifesto is that many teams have stopped or reduced their diagramming and
documentation efforts, including the use of UML.

Now, these same teams tend to rely on ad hoc diagrams that they draw on a whiteboard or assemble
using general-purpose diagramming tools, like Microsoft Visio. Ionut Balosin last year wrote “The Art of
Making Architectural Diagrams,” which describes a number of common problems in doing so, related
to incomprehensible and unclear semantic notations.

Ambiguous software architecture diagrams lead to misunderstandings, which can slow down a good
team. In our industry, we should strive to create better software architecture diagrams. After years of
building software and working with teams around the world, I have created something I call the “C4
model.” C4 stands for context, containers, components, and code — a set of hierarchical diagrams that
you can use to describe the architecture of your software at different zoom levels, each useful for
different audiences. Think of it like Google Maps for your code.

To create these maps of your code, you first need a common set of abstractions to create a ubiquitous
language that describes the static structure of a software system. The C4 model considers the static
structures of a software system in terms of containers (applications, data stores, microservices, etc.),
components, and code. It also considers the people who use the software systems we build.
LEVEL 1: THE SYSTEM CONTEXT DIAGRAM
Level 1, a system context diagram, shows the software system you are building and how it fits into the
world in terms of the people who use it and the other software systems it interacts with. Here is an
example of a context diagram that describes an Internet banking system you may be building:

Your banking customers use the Internet banking system to view information about their bank
accounts and make payments. The Internet banking system uses the bank's system on the bank's
existing mainframe to do this and uses the bank's existing email system to send email to customers.
The color code in the diagram indicates the software systems that already exist (the gray boxes) and
those that are to be built (blue).
LEVEL 2: THE CONTAINER DIAGRAM
Level 2, a container diagram, extends the software system and shows the containers (applications,
data storage, microservices, etc.) that make up this software system. Technological decisions are also a
fundamental part of this diagram. The following is an example of a container diagram for the Internet
banking system. This shows that the internet banking system (the dotted box) consists of five
containers: a server-side web application, a client-side single-page application, a mobile application, a
server-side API application, and a data base.

The Web Application is a Java/Spring MVC system that simply displays static content (HTML, CSS and
JavaScript), including the content that constitutes the single page application. The single page
application is an Angular application that runs in the customer's web browser, providing all the
features of Internet banking. Alternatively, customers can use a cross-platform Xamarin-built mobile
app to access a subset of internet banking functionality. The single page app and mobile app use a
JSON/HTTTPS API, which provides another Java/Spring MVC application running on the server side. The
application in the API obtains user information from the database (a relational database schema). The
API application also communicates with the banking system on the existing mainframe, using a
proprietary XML/HTTTPS interface, to obtain bank account information or perform transactions. The
API application also uses the existing email system if you need to send email to customers.
LEVEL 3: THE COMPONENT DIAGRAM
Level 3, a component diagram, expands an individual container to show the components it contains.
These components must be mapped to real abstractions (for example, a code pool) based on their
code. Below is an example of a component diagram for the fictional Internet banking system showing
some (rather than all) of the components of the API application.

Two Spring MVC controllers in Rest provide access points to the JSON/HTTTPS API, and each controller
subsequently uses other components to access data from the database and banking system on the
mainframe.
LEVEL 4: THE CODE
Finally, if you really want or need to, you can zoom into an individual component to show how this
component is implemented. This is an example (and partial) UML class diagram for the fictional
Internet banking system showing the code elements (interfaces and classes) that make up the
MainframeBankingSystemFacade component.

This diagram shows that the component consists of several classes and that the implementation details
directly reflect the indicator. I wouldn't necessarily recommend creating diagrams at this level of detail,
especially when they can be obtained on demand from most IDEs.
A NOTE
The C4 model does not prescribe any specific notation, and what you see in these presented diagrams
is a simple notation that works well on whiteboards, papers, sticky notes, index cards, and a variety of
design tools. You can also use UML as a notation, with the appropriate use of packages, components,
and stereotypes.

Regardless of which notation you use, I recommend that each element include a name, the type of
element (i.e. “Person”, “Software System”, “Container” or “Component”), a technology option (if
applicable) and some descriptive text. It may seem unusual to include so much text in a diagram, but
this additional text eliminates much of the ambiguity typically seen in software architecture diagrams.

Make sure you have a key or legend to describe any annotation you are using, even if it is obvious to
you. This should cover colors, shapes, acronyms, line styles, borders, scaling, etc. Ideally, your
annotation should be consistent at all levels of detail. Below I present the diagram key/legend for the
container diagram shown above.

The C4 model is a simple way to communicate software architecture at different levels of abstraction,
so that different stories can be told to different audiences. It's also a way to introduce (often
reintroduce) some rigor and light modeling to software development teams. Visit c4model.com for
more information about the C4 model, as well as supplemental diagrams (runtime and
implementation), examples, a notation checklist, frequently asked questions, lecture videos, and tool
options.

COMPONENT DIAGRAM
While other UML diagrams describe the functionality of a system, component diagrams are used to
model the components that help make those functionalities, representing the way they are organized
and their dependencies.

In this entry dedicated to component diagrams we will see what a component diagram is, the symbols
of this diagram and how to draw one in a very simple way. At the end of the article you can find a few
diagrams to illustrate the entire theory as an example.

What is a component diagram

Component diagram is one of the main UML diagrams. It is classified as a structure diagram and, as
such, statically represents the information system. It is usually used after having created the class
diagram, as it needs information from this diagram such as the classes themselves.

This diagram provides a high-level view of the components within a system. Components can be a
software component, such as a database or a user interface; or a hardware component such as a
circuit, microchip or device; or a business unit such as a supplier, payroll, or shipping.

Some uses of this type of diagram are the following:

 They are used in component-based development to describe systems with service-oriented


architecture .
 Show the structure of the code itself.
 It can be used to focus on the relationship between components while hiding specification
details.
 Help communicate and explain the functions of the system that is being built to interested
parties or stakeholders .
To build it, you must first consider identifying the components that the information system will use, as
well as the different interfaces. A typical and common way for a first approach in simple systems is to
use a central component to which the other components are attached, and which is used as the
system management component.

First approach to the component diagram

Elements of the component diagram

The component diagram is made up of three elements: Component, Interface and Dependency .

Component

A component is a block of logical system units, a slightly higher abstraction than classes . It is
represented as a rectangle with a smaller rectangle in the upper right corner with tabs or the word
written above the component name to help distinguish it from a class.

A component can represent two types of elements : logical components (such as business or process
components) or physical components (such as .NET, EJB components...). For example, in an
application developed in Java there will, with complete certainty, be several “.java” components,
which are logical components of the system.
It is represented by a rectangle that has, in turn, two rectangles on the left, as shown in the following
image:

Component Notation

Another notation, used in the latest versions of UML consists of a rectangle with a smaller rectangle in
the upper right corner with tabs.

Other component notation

It is also possible to use the package diagram to make a set of several modules. With this, it is possible
to represent the union of these modules for a specific purpose.

Package with various components

Examples of components could be the following: I/O Management, Animal, Person, Incident
Management, Workflow Manager,... As you can see, they are very broad concepts and can be more or
less specific depending on the depth that can be given to the diagram.
Examples of components

Ideally, components should be designed to have high cohesion and low coupling, to encourage reuse.

Interface

The interface is always associated with a component and is used to represent the area of the module
that is used for communication with another component.

It is represented by a line that has an unfilled circle at the end:

Notation of an interface

Other modules can be connected to an interface. This is done when one component requires or uses
the other component through its interface, which are the external operations offered by the
component. It is represented with a line that ends in a semicircle that surrounds the interface of the
other component. The diagram would look like this:

Interface usage
Dependency relationship

Although you can show more details about the relationship between two components by using
interface notation (provided interface and required interface), you can also use a dependency arrow
to show the relationship between two components . It is a more general relationship.

The dependency relationship represents that one component requires another to execute its work. It
is different from the interface, since it identifies that a component offers a series of operations. In any
case, sometimes to simplify the diagram, interfaces are not used but only dependency relationships
are used.

A dependency relationship is represented by a dashed arrow that goes from the component that
requires another component to the required one.

Notation of a dependency relationship

Dependency relationships can join, in addition to components with other components, components
with interfaces.

How to draw a component diagram

You can use a component diagram when you want to represent your system as a collection of
components and interfaces. This will help you get an idea of the future implementation of the system.
The following are the steps that can serve as a guide when drawing a component diagram.

 Step 1: Determine the purpose of the diagram and identify artifacts such as files, documents,
etc. in your system or application that you need to represent in your diagram.
 Step 2: As you discover the relationships between the elements you identified above, create a
mental layout of your component diagram.
 Step 3: When drawing the diagram, add the components first, grouping them within other
components as you see fit.
 Step 4: The next step is to add other elements such as interfaces, classes, objects,
dependencies, etc. to the component diagram and complete it.
 Step 5: You can attach notes to different parts of your component diagram to clarify certain
details for other users.

Component diagrams, examples

These are some examples of the component diagram, each one has been drawn at a different level of
abstraction.
Component diagram of a veterinary clinic.

In this case packages have been used to give a high level view of the system.

Veterinary clinic components diagram


Component diagram of an online store

Online store component diagram

ATM component diagram

ATM Component Diagram


Library Management Component Diagram
DIAGRAM ORGANIZED IN CAPAZ
Software Architecture

A software architecture is a description of the subsystems and components of a software system and the
relationships between them. Subsystems and components are typically specified in different views to show the
relevant functional and non-functional properties of a software system. The software architecture of a system
is an artifact. It is the result of software design activity.

Component

A component is an encapsulated part of a software system. A component has an interface. Components serve
as building blocks for the structure of a system. At the programming language level, components can be
represented in the form of modules, classes, objects or a set of related functions.

View

A view represents a partial aspect of a software architecture that displays specific properties of a software
system.

Maintainability

This is primarily concerned with fixing a problem, "repairing" a software system after errors occur. A software
architecture that is well prepared for maintenance tends to localize changes and minimize their side effects on
other components.

Extensibility

This focuses on extending a software system with new features, as well as replacing components with
improved versions and removing unwanted or unnecessary features and components. To achieve extensibility
a software system requires loosely coupled components.

This is a structure that allows you to exchange components without affecting your customers. Support for the
integration of new components into an existing architecture is also necessary.

What is a Pattern?

A pattern is a three-part rule, which expresses a relationship between a certain context, a problem, and a
solution.

A pattern addresses a recurring design problem that arises in specific design situations, and presents a solution
to it.

Patterns identify and specify abstractions that are above the level of individual classes and instances, or components. Typically, a
pattern describes several components, classes, or objects, and details of their responsibilities and relationships, as well as their
cooperation. Patterns are a way to document software architectures. Patterns provide a skeleton of functional behavior and
therefore help implement the functionality of the application.

An architectural pattern expresses a fundamental structural organization scheme of software systems. Provides
a set of
predefined subsystems, specify their responsibilities, and include rules and guidelines for organizing the
relationships between them.

A design pattern provides an outline for refining the subsystems or components of a software system, or the
relationships between them. It describes a common recurring structure of communicating components that
solves a general design problem in a particular context.

Layered Pattern

The Layers architectural pattern helps structure applications that can be decomposed into groups of subtasks
in which each group of subtasks is at a particular level of abstraction.

Context: A large system that requires decomposition.

Problem: Imagine that you are designing a system whose predominant characteristic is a mix of high- and low-
level issues, where the

High level operations are based on lower levels.

Such systems often also require some horizontal structuring that is orthogonal to their vertical subdivision. This
is the case where multiple operations are at the same level of abstraction, but are largely independent of each
other.

In this case, it is necessary to balance the following forces:

Late changes to the source code should not mess through the system. They should be limited to one
component and not affect the others.

The parts of the system must be interchangeable. Components must be able to be replaced by alternative
implementations without affecting the rest of the system. Design for change, in general, is an important
facilitator of normal system evolution.

Solution: From the high level point of view the solution is very simple. Structure your system into an
appropriate number of layers and place them on top of each other. Start at the lowest level of abstraction, call
it layer 1. This is the basis of your system. Work the abstraction by putting layer J on top of layer J-1 until you
reach the top level of functionality, call it layer N.

The main structural characteristic of the layer pattern is that the services of layer J are only used by layer J+1,
there are no more

direct dependencies between layers. The responsibility of layer J is to provide services used by layer J+1 and
delegate subtasks to layer J-1.
Figure 1: Layers Pattern.

Domain-Oriented N-Layer Pattern

This pattern is an extension to the traditional Layers pattern explained in the previous point. At the highest,
most abstract level, the logical architecture view of a system can be thought of as a set of related services
grouped into various layers, similar to Figure 2.

Figure 2: Domain-oriented N-Layer Architecture.

In “Domain Oriented” Architectures, the clear delimitation and separation of the Domain layer from the rest
of the layers is crucial. It is actually a prerequisite for DDD (Domain Driven Design). “ Everything must revolve
around the Dominion .”

In complex applications, the behavior of business rules (Domain logic) is subject to many changes and it is very
important to be able to modify, build and test these layers of domain logic in an easy and independent way.
Because of this, an important objective is to have minimal coupling between the Domain Model (logic and
business rules) and the rest of the system layers (presentation layers, infrastructure layers, data persistence,
etc.). Thus, the reasons why it is important to use a “Domain Oriented N-Layer Architecture” is especially in
cases where the business behavior to be automated (domain logic) is subject to many changes and evolutions.

Specifically, the layers and sub-layers proposed for “Domain-Oriented N-Layers” applications are:

a. Presentation Layer
This layer is responsible for displaying information to the user and interpreting their actions.

b. Distributed Services Layer

When an application acts as a service provider for other remote applications, or even if the presentation
layer is

also physically located in remote locations, the business logic (internal business layers) is normally
published through a

services. This layer of services (usually Web Services) provides a means of remote access based on
communication channels and data messages.

c. Application Layer
It defines the work that the application as such must perform and redirects to the domain and
infrastructure objects (persistence, etc.) which are the ones that must internally resolve the problems. It
mainly serves to coordinate the flow logic of the use case. It also allows you to implement format
converters or adapters.

d. Domain Layer

This layer is responsible for representing business concepts and implementation of domain rules. This
layer, Domain, is the heart of the software. Thus, these components implement the main functionality of
the system and encapsulate all the relevant business logic (generically called Domain logic according to
DDD nomenclature).

e. Data Persistence Layer

This layer provides the ability to persist data as well as logically access it. It can be the system's own data or
even access data exposed by external systems (external Web Services, etc.). Thus, this data persistence
layer exposes data access to higher layers. This exposure should be done in a decoupled way (this can be
achieved by applying the abstract factory pattern).

Abstract Factory Pattern

In simple terms, an abstract factory is a class that provides an interface to produce a family of objects [3]. The
general layout of the pattern is shown in Figure 3.

Figure 3: Abstract Factory Pattern.

The classes that participate in this pattern are:

 Abstract Factory (from Figure 3: AbstractFactory): Declares an interface for operations that create
abstract product objects.

 Concrete Factory (from figure 3:

ConcreteFactory1, ConcreteFactory2): Implements the operations to create concrete product objects.


 Abstract Product (from Figure 3: AbstractProductA, AbstractProductB): Declares an interface for a product
object type.

 Concrete Product (from figure 3:

ProductA1, ProductA2, ProductB1, ProductB2): defines a product object to be created by the


corresponding factory; implements the abstract product interface.

 Client (from figure 3: Client): only uses interfaces declared by the Abstract Factory and Abstract Product
classes.

Use the pattern mainly when:

 A system must be independent of how its products are created, composed, and represented.

 You want to provide a family of product classes, and you only want to reveal their interfaces, not their
implementations.

DESIGN MODEL

The design model presented in this section allows demonstrating the application of the Domain-Oriented N-
Layers architecture pattern and the application of the Abstract Factory design pattern. The use of the Abstract
Factory design pattern will allow achieving decoupling between the Application Layer and the Data Persistence
Layer.

The design model represents the logical view of the architecture, which allows showing the layers, sublayers
and classes that participate in the realization of a significant or high priority use case.

For the example case, the use case “Generate worker payment” is designed. The purpose of the use case is to
calculate and record payment to a worker who has been hired for a period of time to perform a set of tasks.
Payment will depend on how many tasks you have completed as scheduled and in how many hours. The
scheduled work hour and the extra work hour have a value set in your contract.

The design of the use case is explained below.

Architecture Design

Below is a UML package diagram representing the N-Layer Architecture. Each layer contains sublayers and each
sublayer contains the design classes necessary for the realization of the use case. Figure 4 shows the general
structure of the architecture with layers and sublayers.

Figure 4: Domain-oriented N-Layer Architecture.


Presentation Layer

This layer contains the “forms” sublayer where the FormPagoContrato class is located, which represents the
graphical user interface that allows the actor to interact with the functionality of the system related to the use
case. Figure 5 represents the presentation layer with the sublayer and its class.

Figure 5: Presentation Layer.

Application Layer

This layer contains the “services” sublayer where the PagoContratoServicio class is located, which allows
coordinating the requests that come from the presentation layer and delegating tasks to the domain and
persistence layers. Figure 6 represents the application layer with the sublayer and its class.

Figure 6: Application Layer.

Domain Layer

This layer contains the “entities” sublayer where the classes that represent the domain or business information
and that have the responsibility of managing the business rules or logic are found. It also contains the
“contracts” sublayer where the interfaces that will be implemented by the persistence layer classes are
located. Interfaces define the contracts that must be respected to achieve decoupling with the persistence
layer. Figure 7 represents the domain layer with the sublayers and their classes.
Figure 7: Domain Layer.

Figure 8 shows the class diagram of the “entities” sublayer of the Domain layer. This figure shows only the attributes of the
classes and not the operations for better visualization.

Figure 8: Entities Sublayer Classes.

The entity class that contains the most relevant operations in this model is the Contract class. Figure 9 shows
the Contract class with all its attributes and operations.

Figure 9: Contract Class.

Persistence Layer
This layer contains the “repositories” sublayer where the classes that implement the interfaces of the
“contracts” sublayer of the Domain layer are located. These classes fulfill data access logic, that is, they consult
or update data sources. It also contains the “factory” sublayer where the classes that implement the Abstract
Factory pattern are found. Figure 10 represents the persistence layer with the sublayers and their classes.

On the other hand, Figure 11 shows the class diagram of the “repositories” sublayer of the Persistence layer.
This class diagram shows the implementation relationships between the repository classes and the interfaces.

Likewise, Figure 12 shows the class diagram of the “factory” sublayer of the Persistence layer. This class
diagram shows the inheritance relationship between the classes, where the FabricaRepositorioSQL class
implements the abstract methods of the abstract class FabricaRepositorio. FabricaRepositorioSQL is the class
that creates the repository objects that access an SQL database.

Figure 10: Persistence Layer.


Figure 11: Classes of the Repositories Sublayer.

Figure 12: Factory Sublayer Classes.

ADVANTAGES AND RECOMMENDATIONS

Advantages

Maintaining improvements to a solution will be much easier because the features are localized. Furthermore,
the layers must be loosely coupled to each other and with high internal cohesion, which makes it possible to
easily vary different implementations/combinations of layers.

recommendations

This type of architecture should be implemented in complex enterprise applications where the business logic
changes a lot and the application will undergo subsequent changes and maintenance over at least a relatively
long application life.

On the other hand, this type of architecture should not be implemented in small applications that once
completed, few changes are expected, the life of the application will be relatively short and where speed in the
development of the application takes priority.

You might also like