应该是搭建脚手架自动测试吧,编程珠玑第二版第五章有讲过这个东西。
脚手架(scaffolding)就是这个样子的,
当然我知道你说的是programming中的脚手架。
这里是stackoverflow上的一个回答:
Scaffolding is a meta-programming method of building database-backed software applications. It is a technique supported by some model-view-controller frameworks, in which the programmer may write a specification that describes how the application database may be used. The compiler uses this specification to generate code that the application can use to create, read, update and delete database entries, effectively treating the template as a "scaffold" on which to build a more powerful application.
翻译过来就是:
“脚手架”是一种元编程的方法,用于构建基于数据库的应用。许多MVC框架都有运用这种思想。
程序员编写一份specification(规格说明书),来描述怎样去使用数据库;而由(脚手架的)编译器来根据这份specification生成相应的代码,进行增、删、改、查数据库的操作。我们把这种模式称为"脚手架",在脚手架上面去更高效的建造出强大的应用!
——————————————————————————————————
是不是很令人振奋,由“程序员手写代码”跨越到了“程序员指挥机器自动生成代码”的时代~~ 并且利用脚手架,我们可以爬到更高的地方、建更高的楼房~
stackoverflow链接:
frameworks - What is scaffolding? Is it a term for a particular platform?就是你有个空架子把环境配置乱七八糟的依赖项都搭建好,要创建新的项目时拿过来直接往里面添加新项目需要的东西。
脚手架在不同场景有不同的含义,需要自己体会理解:
最近在读《人月神话》和《编程珠玑》,对书中脚手架的含义也感到很困惑,直到看了 @太岁头上动土拨鼠 的解答和 StackOverflow 的最后一个答案。
这里摘录一部分脚手架相关的描述:
我们团队一直在持续推进业务系统的体系化治理工作,在这个过程中我们沉淀了自己的 DDD 脚手架项目。脚手架项目是体系化治理过程中比较重要的一环,它的作用有两点:
(1)可以对新建的项目进行统一的规范;
(2)对于指导老项目进行 DDD 的改造提供指导。
本文主要是梳理和总结了 DDD 脚手架使用中的编码规范以及遇到的问题。
DDD 相关的应用架构有很多种,比如四层架构,洋葱架构,六边形架构,整洁架构等。这些应用架构都有各自的特点和不同。但是他们的总体思想都是相似的,主要是通过分层来实现功能和关注点的隔离。达到的目标是领域层不依赖任何其他外部实现,这样就能保证核心业务逻辑的干净和稳定。
左图是整洁架构的示意图,左图为分层,右图表示各个分层的变化频率和抽象层级。整洁架构主要分为 4 层:
(1)Frameworks&Drivers 层:这一层表示系统依赖的外部系统,比如数据库、缓存、前端页面等。这一层是变化频率最高的,也是需要和我们的核心业务逻辑做隔离的。
(2)Interface Adapters 层:这一层是一个适配层,主要负责外部系统和内部业务系统的适配,这一层的主要作用就是外部系统和内部系统的适配和协议转换。
(3)Application Business Rules: 应用业务规则层,可以理解为用例层,这一层表示整个应用可以提供哪些用例级别的功能和服务。这一层也是对第 4 层中的核心业务规则的编排层。
(4)Enterprise Business Rules: 这一层就是最为核心的业务逻辑层,这一层不包含任何和技术相关的内容,只包含业务逻辑。
使用命令如下:
mvn archetype:generate
-DarchetypeGroupId=com.jd.jr.cf
-DarchetypeArtifactId=ddd-archetype
-DarchetypeCatalog=local
-DarchetypeVersion=0.0.1-SNAPSHOT
-DinteractiveMode=false
-DgroupId=com.jd.demo.test //从这一行开始需要根据项目名称修改
-DartifactId=demo-test
-Dversion=1.0.0
-Dpackage=com.jd.demo.test
-DappName=demo-test -s D:/git/settings.xml // 本地 git配置文件
生成完的项目结构如下:
|--- adapter -- 适配器层 应用与外部应用交互适配
| |--- controller -- 控制器层,API中的接口的实现
| | |--- assembler -- 装配器,DTO和领域模型的转换
| | |--- impl -- 协议层中接口的实现
| |--- repository -- 仓储层
| | |--- assembler -- 装配器,PO和领域模型的转换
| | |--- impl -- 领域层中仓储接口的实现
| |--- rpc -- RPC层,Domain层中port中依赖的外部的接口实现,调用远程RPC接口
| |--- task -- 任务,主要是调度任务的适配器
|--- api -- 应用协议层 应用对外暴露的api接口
|--- boot -- 启动层 应用框架、驱动等
| |--- aop -- 切面
| |--- config -- 配置
| |--- Application -- 启动类
|--- app -- 应用层
| |--- cases -- 应用服务
|--- domain -- 领域层
| |--- model -- 领域对象
| | |--- aggregate -- 聚合
| | |--- entities -- 实休
| | |--- vo -- 值对象
| |--- service -- 域服务
| |--- factory -- 工厂,针对一些复杂的Object可以通过工厂来构建
| |--- port -- 端口,即接口
| |--- event -- 领域事件
| |--- exception -- 异常封装
| |--- ability -- 领域能力
| |--- extension -- 扩展点
| | |--- impl -- 扩展点实现
|--- query -- 查询层,封装读服务
| |--- model -- 查询模型
| |--- service -- 查询服务
1、Api 模块编码规范:
2、Adapter/Controller 模块编码规范:
3、App 模块编码规范:
4、Domain 层编码规范:
5、Adapter/Repository 和 Rpc 模块编码规范:
Q1、Api 模块对外提供的 jar 包中是否要引用其他应用的 jar 包?
A1: 有一些场景,A 应用的 Api 接口的入参需要引用其他应用的包中的类。比如 A 应用发出了一个事件,B 应用提供了一个接口来处理这个事件,那 B 应用是否要引用 A 应用的包中的事件定义类呢? 理想情况,最好是 B 应用定义一个自己的类,这样 B 应用就不会依赖 A 应用的包。
Q2、Api 包中是否能包含枚举类的定义?
A2:最好不要在 Api 包中对外暴露内部的枚举值定义。因为枚举值是需要在 Domain 模块中定义和使用的,不适合通过 jar 包的形式暴露给外部。 如果确实有需求要暴露给外部应用 (比如为了让接口调用方方便的知道入参中的值有哪些),可以将枚举类的定义放在同一的 common 包中。这样 Domain 模块和对外提供的 jar 包都可以引用 common 包。
Q3、数据存储是否要使用统一版本号?
A3: 对于新应用,最好是使用统一的版本号,这样在更新数据库的时候就可以统一使用版本号当做乐观锁。但是对于遗留系统而言,启用版本号的成本比较高,因为需要梳理所有对实体进行变更的点,要求所有的点都统一使用版本号。所以要根据情况来确定是否使用。
Q4、对于一些偏流程性的业务,频繁的调用外部 rpc 接口。如果每个 rpc 接口都添加一个防腐层对象的话,会降低开发效率。是否可以不定义防腐层对象?
A4:最好是定义防腐层对象,短期可能降低一些开发效率,但是从长期和代码标准话的角度看,还是值得的。
作者:京东科技 史纪军
来源:京东云开发者社区 转载请注明来源