用于可视化软件架构的 C4 模型



C4型号是...

1. 一组分层抽象(软件系统、容器、组件和代码)。
2. 一组层次图(系统上下文、容器、组件和代码)。
3. 独立于符号。
4. 独立于工具。


用途和好处

C4 模型是一种易于学习、开发人员友好的软件架构图绘制方法。 良好的软件架构图有助于软件开发/产品团队内部/外部的沟通、新员工的高效入职、架构审查/评估、风险识别(例如风险风暴)、威胁建模

介绍

请建筑行业的人士以可视化方式传达建筑物的架构,您将获得场地平面图、平面图、立面图、横截面图和详细图纸。 相比之下,如果要求软件开发人员使用图表来传达软件系统的软件架构,您可能会得到一堆混乱的方框和线条……不一致的符号(颜色编码、形状、线条样式等)、模糊的命名、未标记的关系、通用术语、缺少技术选择、混合抽象等。

软件架构草图

软件架构草图

软件架构草图

软件架构草图

作为一个行业,我们确实拥有统一建模语言 (UML)、ArchiMate 和 SysML,但询问这些是否提供了一种有效的方式来传达软件架构通常是无关紧要的,因为许多团队已经抛弃了它们,转而采用更简单的“方块和线”图。 放弃这些建模语言是一回事,但也许在敏捷性的竞赛中,许多软件开发团队已经失去了可视化沟通的能力。



您的代码的映射

C4 模型的创建是为了帮助软件开发团队在前期设计会议期间和回顾性记录现有代码库时描述和交流软件架构。 这是一种以不同细节级别创建代码地图的方法,就像您使用 Google 地图等工具来放大和缩小您感兴趣的区域一样。


谷歌地图
谷歌地图
谷歌地图
谷歌街景

第 1 级: 系统上下文 图提供了一个起点,显示范围内的软件系统如何融入其周围的世界。

第 2 级: 容器 图放大了软件系统的范围,显示了高级技术构建块。

第 3 级: 组件 图放大到单个容器,显示其中的组件。

级别 4: 代码 (例如 UML 类)图可用于放大单个组件,显示该组件是如何实现的。



C4 模型是一种“抽象优先”的软件架构图解方法,它基于反映软件架构师和开发人员如何思考和构建软件的抽象。 一小组抽象和图表类型使 C4 模型易于学习和使用。 请注意,您不需要使用所有 4 个级别的图表; 只有那些能增加价值的——系统上下文和容器图对于许多软件开发团队来说就足够了。


C4型号概述

不同级别的缩放允许您向不同的受众讲述不同的故事。

将鼠标悬停在图表上,找到带有 的元素 ,然后双击进行放大。

抽象

为了创建这些代码映射,我们首先需要一组通用的抽象来创建一种通用语言,我们可以用它来描述软件系统的静态结构。 软件 系统由一个或多个 容器 (应用程序和数据存储)组成 ,每个容器包含一个或多个 组件 ,而组件又由一个或多个 代码元素 (类、接口、对象、函数等)实现。 "人(Person)" 可以使用我们构建的软件系统


抽象



一个人代表软件系统的人类用户之一(例如演员、角色、人物角色等)。

软件系统

软件系统是最高层次的抽象,它描述了为其用户提供价值的东西,无论他们是人类还是非人类。 这包括您正在建模的软件系统,以及您的软件系统所依赖的其他软件系统(反之亦然)。 在许多情况下,软件系统由单个软件开发团队“拥有”。

容器 (应用程序和数据存储)

不是 Docker! 在C4模型中,容器代表 应用程序 数据存储 容器是需要运行才能使整个软件系统正常工作的东西。 实际上,容器类似于:

  • 服务器端 Web 应用程序 :在 Apache Tomcat 上运行的 Java EE Web 应用程序、在 Microsoft IIS 上运行的 ASP.NET MVC 应用程序、在 WEBrick 上运行的 Ruby on Rails 应用程序、Node.js 应用程序等。
  • 客户端 Web 应用程序 :使用 Angular、Backbone.JS、jQuery 等在 Web 浏览器中运行的 JavaScript 应用程序。
  • 客户端桌面应用程序 :使用WPF编写的Windows桌面应用程序、使用Objective-C编写的OS X桌面应用程序、使用JavaFX编写的跨平台桌面应用程序等。
  • 移动应用程序 :Apple iOS 应用程序、Android 应用程序、Microsoft Windows Phone 应用程序等。
  • 服务器端控制台应用程序 :独立(例如“public static void main”)应用程序、批处理过程等。
  • 无服务器函数 :单个无服务器函数(例如 Amazon Lambda、Azure Function 等)。
  • 数据库 :关系数据库管理系统、文档存储、图形数据库等中的模式或数据库,例如 MySQL、Microsoft SQL Server、Oracle Database、MongoDB、Riak、Cassandra、Neo4j 等。
  • Blob 或内容存储 :Blob 存储(例如 Amazon S3、Microsoft Azure Blob 存储等)或内容交付网络(例如 Akamai、Amazon CloudFront 等)。
  • 文件系统 :完整的本地文件系统或较大网络文件系统的一部分(例如SAN、NAS 等)。
  • Shell脚本 :用Bash等编写的单个shell脚本。
  • ETC

容器本质上是一个上下文或边界,在其中执行一些代码或存储一些数据。 每个容器都是一个单独的可部署/可运行的事物或运行时环境,通常(但并非总是)在其自己的进程空间中运行。 因此,容器之间的通信通常采用进程间通信的形式。

组件

“组件”一词在软件开发行业中是一个含义非常广泛的术语,但在这种情况下,组件是封装在定义良好的接口后面的一组相关功能。 如果您使用的是 Java 或 C# 等语言,那么考虑组件的最简单方法是,它是接口背后的实现类的集合。 诸如如何打包这些组件(例如,每个 JAR 文件、DLL、共享库等一个组件与多个组件)等方面是一个单独且正交的问题。

这里需要注意的重要一点是容器内的所有组件通常在同一进程空间中执行。 在 C4 模型中,组件不是可单独部署的单元。

1. 系统上下文图 关联

系统上下文图

图键

系统上下文图是绘制和记录软件系统的良好起点,让您可以退一步查看全局。 绘制一个图表,将您的系统显示为中心的一个盒子,周围是它的用户和与其交互的其他系统。

细节在这里并不重要,因为这是您的缩小视图,显示了系统景观的大图。 重点应该放在人(参与者、角色、角色等)和软件系统上,而不是技术、协议和其他低级细节上。 这是一种可以向非技术人员展示的图表。

范围 :单个软件系统。

主要要素 :范围内的软件系统。
支持元素 :在范围内直接连接到软件系统的人员(例如用户、参与者、角色或角色)和软件系统(外部依赖项)。 通常,这些其他软件系统位于您自己的软件系统的范围或边界之外,并且您对它们没有责任或所有权。

目标受众 :软件开发团队内部和外部的每个人,无论是技术人员还是非技术人员。

推荐给大多数团队 :是的。

2.容器图 关联

容器图

图键

一旦您了解了您的系统如何适应整个 IT 环境,下一步真正有用的就是使用容器图放大系统边界。 “容器”类似于服务器端 Web 应用程序、单页应用程序、桌面应用程序、移动应用程序、数据库模式、文件系统等。本质上,容器是一个单独的可运行/可部署的单元(例如单独的进程空间) )执行代码或存储数据。

容器图显示了软件架构的高级形状以及如何在其中分配职责。 它还显示了主要的技术选择以及容器如何相互通信。 这是一个简单的、以高级技术为中心的图表,对于软件开发人员和支持/操作人员等非常有用。

范围 :单个软件系统。

主要元素 :软件系统范围内的容器。
支持元素 :直接连接到容器的人员和软件系统。

目标受众 :软件开发团队内外的技术人员; 包括软件架构师、开发人员和运营/支持人员。

推荐给大多数团队 :是的。

注意 :该图没有提及集群、负载均衡器、复制、故障转移等,因为它可能会因不同环境(例如生产、登台、开发等)而有所不同。 通过一个或多个部署图 可以更好地捕获这一信息

3. 组件图 关联

组件图

图键

接下来,您可以进一步放大并分解每个容器,以识别主要的结构构建块及其相互作用。

组件图显示了容器如何由许多“组件”组成、每个组件是什么、它们的职责以及技术/实现细节。

范围 :单个容器。

主要元素 :范围内容器内的组件。
支持元素 :容器(在软件系统范围内)加上直接连接到组件的人员和软件系统。

目标受众 :软件架构师和开发人员。

建议大多数团队 :不,仅在您认为组件图增加价值时才创建组件图,并考虑自动创建长期文档。

4. 代码图 关联

UML 类图

最后,您可以放大每个组件以显示它是如何实现为代码的; 使用 UML 类图、实体关系图或类似的图。

这是一个可选的详细级别,通常可以通过 IDE 等工具按需获取。 理想情况下,该图将使用工具(例如 IDE 或 UML 建模工具)自动生成,并且您应该考虑仅显示那些允许您讲述您想要讲述的故事的属性和方法。 除了最重要或最复杂的组件之外,不建议对任何其他组件使用这种详细程度。

范围 :单个组件。

主要元素 :范围内组件内的代码元素(例如类、接口、对象、函数、数据库表等)。

目标受众 :软件架构师和开发人员。

对大多数团队的建议 :不,特别是对于长期存在的文档,因为大多数 IDE 可以根据需要生成这种级别的详细信息。

系统架构图 关联

系统架构图

图键

C4 模型提供了单个软件系统 的静态视图 ,但在现实世界中,软件系统永远不会孤立存在。 因此,特别是如果您负责软件系统的集合/组合,了解所有这些软件系统如何在给定的企业、组织、部门等中组合在一起通常很有用。本质上,这是一张地图所选范围内的软件系统,并对每个感兴趣的软件系统进行 C4 深入分析。

从实践的角度来看,系统景观图实际上只是一个系统上下文图,没有具体关注特定的软件系统。

范围 :企业/组织/部门/等。

主要元素 :与所选范围相关的人员和软件系统。

目标受众 :软件开发团队内部和外部的技术人员和非技术人员。

动态图 关联

动态图

图键

当您想要显示静态模型中的元素如何在运行时协作以实现用户故事、用例、功能等时,动态图可能很有用。该动态图基于 UML 通信图(以前称为“UML )协作图”)。 它类似于 UML 序列图 ,尽管它允许图元素的自由形式排列,并通过编号的交互来指示顺序。

范围 :特定功能、故事、用例等。

主要和支持元素 :您的选择 - 您可以显示在运行时交互的软件系统、容器或组件。

目标受众 :软件开发团队内部和外部的技术人员和非技术人员。

注意 :如果您喜欢 UML 序列图的视觉风格,请随意使用它。

部署图 关联

部署图

图键

AWS 部署图示例

部署图允许您说明静态模型中的软件系统和/或容器的实例如何部署到给定 部署环境 (例如生产、登台、开发等)内的基础设施上。 它基于 UML 部署图

部署节点 代表 软件系统/容器实例运行的位置; 也许是物理基础设施(例如物理服务器或设备)、虚拟化基础设施(例如 IaaS、PaaS、虚拟机)、容器化基础设施(例如 Docker 容器)、执行环境(例如数据库服务器、Java EE Web/应用程序服务器、 Microsoft IIS)等。部署节点可以嵌套。

您可能还希望包括 基础设施节点 ,例如 DNS 服务、负载均衡器、防火墙等。

请随意使用 Amazon Web Services、Azure 等提供的图标来补充您的部署图...只需确保您使用的任何图标都包含在您的图表键/图例中即可。

范围 :单个部署环境(例如生产、登台、开发等)内的一个或多个软件系统。

主要元素 :部署节点、软件系统实例和容器实例。
支持元素 :软件系统部署中使用的基础设施节点。

目标受众 :软件开发团队内外的技术人员; 包括软件架构师、开发人员、基础设施架构师和运营/支持人员。

符号

C4 模型与 符号无关 ,并且不规定任何特定的符号。 不过,作为起点,下面是一个适用于白板、纸张、便利贴、索引卡和各种图表工具的简单符号。

人

软件系统

软件系统

容器

容器

组件

组件

关系

关系

然后,您可以使用颜色和形状来补充图表,以添加附加信息或只是使图表更美观。

C4和UML

尽管上面的示例图是使用“框和线”表示法创建的,但可以使用 UML 并适当使用包、组件和构造型来说明核心图。 然而,生成的 UML 图确实往往缺乏相同程度的描述性文本,因为使用某些 UML 工具添加此类文本是不可能(或容易)的。

以下是系统上下文、容器和组件图的三个示例,以供比较。

系统上下文图
容器图
组件图
系统上下文图
容器图
元件图
系统上下文图
容器图
组件图
系统上下文图
容器图
组件图

C4 和 ArchiMate

有关如何使用 ArchiMate 创建 C4 模型图的详细信息, 请参阅 C4 模型、架构观点和 Archi 4.7 。



图例/图例

使用的任何符号都应尽可能具有自我描述性,但 所有图表都应有一个键/图例 以使符号明确。 这也适用于使用 UML、ArchiMate 和 SysML 等符号创建的图表,因为并不是每个人都知道所使用的符号。

图键



符号、符号、符号

尽管 C4 模型是一种抽象优先的方法并且与符号无关,但您仍然需要确保图表符号有意义,并且图表易于理解。 思考这个问题的一个好方法是问自己每个图表是否可以独立存在,并且(大部分)无需叙述即可被理解。 您可以使用这个简短的 软件架构图审查清单 来提供帮助。 这里有一些与符号相关的建议。

图表

  • 每个图都应该有一个描述图类型和范围的标题(例如“我的软件系统的系统上下文图”)。
  • 每个图表都应该有一个图例/图例来解释所使用的符号(例如形状、颜色、边框样式、线条类型、箭头等)。
  • 首字母缩写词和缩写词(业务/领域或技术)应为所有受众所理解,或在图表键/图例中进行解释。

元素

  • 应明确指定每个元素的类型(例如,人员、软件系统、容器或组件)。
  • 每个元素都应该有一个简短的描述,以提供关键职责的“一目了然”的视图。
  • 每个容器和组件都应该有明确指定的技术。

人际关系

  • 每条线都应该代表单向关系。
  • 每行都应该有标签,标签与关系的方向和意图(例如依赖性或数据流)一致。 标签尽量具体,最好避免使用“用途”等单一单词。
  • 容器之间的关系(通常代表进程间通信)应该有明确标记的技术/协议。


替代可视化

最后,不要觉得您需要始终使用传统的“框和箭头”图。 尽管这通常是默认方法,但还有其他通常是交互式的可视化,可用于以非常不同的方式显示相同的 C4 模型抽象。

传统的“方框和箭头”图是文档和演示的默认方法。

D3.js 力导向图是一种非常简洁的可视化大型软件架构的方法,还提供了一种探索依赖关系的简单方法。

Ilograph 的交互式图表提供了一种选择性放大和缩小的方法,使您能够探索整个软件架构模型。

工具

对于设计会议,您可能会发现白板或活动挂图纸更适合协作和快速迭代。 对于长期存在的文档,有许多工具可以帮助创建基于 C4 模型的软件架构图。


(例如系统上下文、容器和组件图)
(例如协作图或序列图)
(例如显示部署和基础设施问题的图表)
(免费、分叉/定制等)
(为了轻松进行版本控制并集成到构建管道/其他工具中)
(重命名元素时自动保持多个图表同步)
受到推崇的
(使用不同的工具或可视化格式(例如 图表、图表等) 呈现图表)

经常问的问题

C4模型背后的背景是什么?

C4 模型是由 Simon Brown 创建的,他在伦敦担任软件开发人员/架构师期间开始教授人们有关软件架构的知识。 西蒙培训课程的一部分是设计练习,向一组人提出一些要求,要求他们进行一些设计,并绘制一些图表来表达该设计。

尽管这是一项以设计为重点的练习,但各种各样的图表表明,想法的可视化是大多数人非常缺乏的技能。 C4 模型本质上是 Simon 如何可视化软件架构的形式化,它已经发展了多年。

C4模型背后的灵感是什么?

C4模型的灵感来自于 统一建模语言 软件架构的4+1模型 总之,您可以将 C4 模型视为底层概念的简化版本,旨在 (1) 让软件开发人员更容易描述和理解软件系统的工作原理,以及 (2) 最大限度地减少软件之间的差距架构模型/描述和源代码。

C4 模型及其中的各种图表类型的根源可以追溯到 2006 年左右的某个地区,尽管“C4”名称出现得晚得多,大约是 2011 年底。受敏捷运动影响的团队对使用 UML 不太热衷。

C4车型不是倒退了吗? 为什么要重新发明 UML? 为什么不直接使用 UML?

您将 C4 模型视为前进还是倒退取决于您所处的位置。 如果您正在使用 UML(或 SysML、ArchiMate 等)并且它对您有用,请坚持使用它。 不幸的是,UML 的使用似乎正在下降,许多团队已再次恢复使用临时框和线图。 鉴于许多团队不想使用 UML(出于各种原因),C4 模型有助于在软件架构的沟通方式中引入一些结构和规则。 对于很多团队来说,C4 模型就足够了。 对于其他人来说,也许这是迈向 UML 的垫脚石。

有多少人使用C4型号?

诚实的答案是没有人知道。 Simon 亲自向 30 多个国家的 10,000 多人教授 C4 模型; 会议演讲、视频、书籍和文章的影响远不止于此。 其他人也在教授、演讲和撰写有关 C4 模型的文章。 但它肯定在从初创公司到全球家喻户晓的组织中使用。

为什么是“容器”?

“进程”、“应用程序”、“应用程序”、“服务器”、“可部署单元”等术语都有相关的含义,因此选择“容器”这个名称作为描述组件所在事物的通用方式。 从一个角度来看,不幸的是容器化已经变得流行,因为许多软件开发人员现在将“容器”一词与 Docker 联系在一起。 但从另一个角度来看,C4 模型中的容器和基础设施(例如 Docker)容器之间有时存在很好的一致性。

虽然许多团队成功地按原样使用 C4 模型,但如果需要,请随意更改术语。

我们可以改变术语吗?

该术语(上下文、容器、组件和代码)适用于许多组织和多种类型的软件。 然而,有时组织会有人们已经熟悉的现有术语。 或者也许“组件”和“类”不容易映射到正在使用的技术(例如,函数式语言经常使用术语“模块”和“函数”)。

请随意修改用于描述不同抽象级别的软件架构的术语。 只要确保每个人都明确理解它即可。

如何对微服务和无服务器建模?

一般来说,使用 C4 模型时有两种绘制微服务图表的选项,尽管这取决于“微服务”的含义。

方法 1:每个“微服务”均由单独的团队拥有
如果您的软件系统依赖于您无法控制的许多微服务(例如,它们由单独的团队拥有和/或运营),请将这些微服务建模为外部软件系统,您无法看到其内部。

方法二:单个团队拥有多个“微服务”

想象一下,您有一个 API 应用程序(例如 Spring Boot、ASP.NET MVC 等),可以读取/写入关系数据库模式。 无论您认为术语“微服务”仅指 API 应用程序,还是 API 应用程序和数据库模式的组合……如果微服务是您正在构建的软件系统的一部分(即您拥有它们) ),将每个可部署的事物建模为容器。 换句话说,您将显示两个容器:API 应用程序和数据库架构。 请随意在这两个容器周围画一个框以表明它们是相关的/分组的。

对于无服务器函数/lambda 等也是如此; 根据所有权将它们视为软件系统或容器。

如何绘制大型且复杂的软件系统的图表?

即使使用相对较小的软件系统,也很容易尝试将整个故事包含在单个图表中。 例如,如果您有一个 Web 应用程序,那么创建一个显示组成该 Web 应用程序的所有组件的单个组件图似乎是合乎逻辑的。 除非您的软件系统真的那么小,否则您可能会耗尽图表画布上的空间,或者发现很难找到一个不被无数重叠线弄乱的布局。 使用更大的图表画布有时会有所帮助,但大图表通常难以解释和理解,因为认知负荷太高。 如果没有人理解该图,就没有人会看它。

相反,不要害怕将单个复杂图拆分为大量更简单的图,每个图都特定于业务领域、功能区域、功能分组、有界上下文、用例、用户交互、功能集等关键是要确保每个单独的图表在相同的抽象级别上讲述同一整体故事的不同部分。 您还可以使用 替代可视化

图表会很快过时吗?

由于 C4 模型的层次性质,每个图都会以不同的速率变化。

  • 系统上下文图 :在大多数情况下,系统上下文图的变化非常缓慢,因为它描述了软件系统正在运行的环境。
  • 容器图 :除非您正在构建一个大量使用微服务或无服务器 lambda/函数等的软件系统,否则容器图的变化也会相对缓慢。
  • 组件图 :对于任何正在积极开发的软件系统,随着团队添加、删除代码或将代码重组为内聚组件,组件图可能会频繁更改。 使用工具自动生成这种级别的细节会有所帮助。
  • 代码图 :如果代码库正在积极开发中,4 级代码(例如类)图可能很快就会过时。 因此,建议 (1) 根本不创建它们或 (2) 使用 IDE 等工具按需生成它们。

为什么C4模型没有涵盖业务流程、工作流、状态机、领域模型、数据模型等?

C4 模型的重点是构成软件系统的不同抽象级别的静态结构。 如果需要描述其他方面,请随意用UML图、BPML图、ArchiMate图、实体关系图等补充C4图。

C4 模型与 UML、ArchiMate 和 SysML 对比?

尽管 UML、ArchiMate 和 SysML 等现有符号已经存在,但许多软件开发团队似乎并不使用它们。 通常这是因为团队对这些符号不够了解,认为它们太复杂,认为它们与敏捷方法不兼容或没有所需的工具。

如果您已经成功地使用这些符号之一来传达软件架构并且它正在工作,请坚持下去。 如果没有,请尝试 C4 型号。 如果需要,不要害怕用 UML 状态图、时序图等来补充 C4 图。

我们可以将 C4 和 arc42 结合起来吗?

是的,很多团队都这样做,并且 C4 模型与arc42 文档模板 兼容, 如下所示。

  • 上下文和范围 => 系统上下文图
  • 构建块视图(级别 1)=> 容器图
  • 构建块视图(级别 2)=> 组件图
  • 构建块视图(第 3 级)=> 类图

C4 模型是否暗示了设计流程或团队结构?

一个常见的误解是团队的设计过程应该遵循 C4 模型层次结构中的级别,也许团队中的不同人员负责不同级别的图表。 例如,业务分析师创建系统上下文图,架构师创建容器图,而开发人员则负责其余的细节级别。

虽然您当然可以通过这种方式使用 C4 模型,但这不是预期或推荐的使用模式。 C4模型只是从不同抽象层次描述软件系统的一种方式,它与交付软件的过程无关。

使用C4来描述库、框架和SDK?

C4 模型实际上是为了在不同的抽象级别上对软件系统进行建模而设计的。 要记录库、框架或 SDK,您最好使用 UML 之类的东西。 或者,您可以使用 C4 模型来描述您的框架、库或 SDK 的使用示例; 也许使用颜色编码来表示软件系统的哪些部分是定制的,哪些部分是为您提供的。

网络应用程序; 一个容器还是两个容器?

如果您正在构建主要生成静态 HTML 内容的服务器端 Web 应用程序(例如 Spring MVC、ASP.NET、Ruby on Rails、Django 等),那么这就是单个容器。 如果服务器端 Web 应用程序(例如使用 Angular 构建的单页应用程序)交付了大量 JavaScript,那么那就是两个容器。 这是一个例子

尽管在部署时,服务器端 Web 应用程序同时包含服务器端和客户端代码,但将客户端和服务器视为两个单独的容器可以明确表明它们是两个单独的进程空间,通过进程间通信进行通信/远程通信机制(例如JSON/HTTPS)。 它还为单独放大每个容器以显示其中的组件提供了基础。

这些线应该代表依赖关系还是数据流?

这是你的选择。 有时图表可以更好地显示依赖关系(例如使用、读取等),有时数据流(例如客户更新事件)效果更好。 无论您选择哪一个,请确保线条的描述与箭头的方向一致。

还值得记住的是,大多数关系都可以用任何一种方式表达,而且表达得越明确越好。 例如,将关系描述为“将客户更新事件发送至”比简单地“客户更新事件”更具描述性。

Java JAR、C# 程序集、DLL、模块等是容器吗?

通常不会。 容器是一个运行时构造,就像应用程序一样; 而 Java JAR 文件、C# 程序集、DLL、模块等用于组织这些应用程序中的代码。

Java JAR、C# 程序集、DLL、模块、包、命名空间、文件夹等是组件吗?

也许吧,但同样,通常不会。 C4 模型旨在显示运行时单元(容器)以及如何在它们(组件)之间划分功能,而不是显示 Java JAR 文件、C# 程序集、DLL、模块、包、命名空间或文件夹结构等组织单元。

当然,这些构造和组件之间可能存在一对一的映射; 例如,如果您正在构建六边形架构,则可以为每个组件创建一个 Java JAR 文件或 C# 程序集。 另一方面,单个组件可能使用多个 JAR 文件中的代码来实现,这通常是当您开始考虑第三方框架/库以及它们如何嵌入到代码库中时发生的情况。

您是否应该包括消息总线、API 网关、服务网格等?

如果您有两个服务 A 和 B,它们通过消息总线(无论主题、队列、p2p、pub/sub 等)或其他中介(例如 API 网关或服务网格)发送消息来进行通信,那么您有几个选项。 第一个选项是显示服务 A 向中介发送消息,中介随后将该消息转发给服务 B。虽然准确,但该图的“中心辐射”性质往往会掩盖消息之间存在耦合的概念。生产者和消费者。

另一种方法是省略中介,而是使用符号(例如文本描述、颜色编码、线条样式等)来表示服务 A 和 B 之间的交互是通过中介发生的。 这种方法往往会产生能够讲述更清晰故事的图表。

数据存储服务应该表现为软件系统还是容器?

一个常见问题是 Amazon S3、Amazon RDS、Azure SQL 数据库、内容交付网络等服务是否应该显示为软件系统或容器。 毕竟,这些是我们大多数人不拥有或自己运营的外部服务。

如果您正在构建一个使用 Amazon S3 存储数据的软件系统,那么您自己确实不运行 S3,但您确实对所使用的存储桶拥有所有权和责任。 与 Amazon RDS 类似,您可以(或多或少)完全控制您创建的任何数据库架构。 因此,请将它们视为容器,因为它们是软件架构不可或缺的一部分,尽管它们托管在其他地方。

C4模型是否普遍适用?

C4 模型旨在帮助描述、记录和绘制定制的定制软件系统。 从这个角度来看,C4模型可以用来描述各种软件架构(单体或分布式),用各种编程语言构建,部署在各种平台(本地或云端)上。

可能不太适合 C4 模型的解决方案包括嵌入式系统/固件,以及依赖大量定制而不是定制开发的解决方案(例如 SAP 和 Salesforce)。 即使使用这些解决方案,您仍然可能会发现系统上下文和容器图很有用。

更多信息

如果您正在寻找有关可视化软件架构和 C4 模型的更多信息,建议您使用以下资源。

用于可视化软件架构的 C4 模型

这是 Simon Brown 的《 可视化软件架构的 C4 模型》 电子书,可以从 Leanpub 购买 PDF、EPUB 和 MOBI 格式的电子书。 这是使用 C4 模型可视化软件架构的简短指南。

使用 C4 模型可视化软件架构
Agile on the Beach 2019 - 英国法尔茅斯 - 2019 年 7 月

图表代码 2.0
JBCNConf - 西班牙巴塞罗那 - 2022 年 7 月