【发布时间】:2013-10-11 06:37:07
【问题描述】:
编辑:这是关于使用 Maven 进行持续交付并使用 Jenkins 进行编排。 Maven 绝对不是为此而设计的,这个问题是我们在不使用 Maven 版本的情况下获得高效工作流程的一部分。感谢您的帮助。
我们在主要版本中使用 Maven -SNAPSHOT,以确保客户始终获得该给定版本的最新代码,这很好用。出于技术原因,我们有两个独立的 Maven 作业 - 一个用于将源代码编译为 jar,另一个用于将适当的 jar 组合到给定的部署中。这也很有效。
然后我们让 Jenkins 编排何时调用各个步骤,这有点棘手,因为如果我们在第一步中执行正常的mvn clean install,这意味着所有快照工件都会重新编译,这在turn 使 Jenkins 认为所有快照 已更改(因为它们的指纹 - 也称为 MD5 校验和 - 已更改)即使用于生成工件的源没有更改,从而触发 all下游构建,而不仅仅是那些依赖确实改变的。
到目前为止,我已将这些内容确定为在构建之间有所不同:
- META-INF/maven/.../pom.properties(因为它包含时间戳)
- META-INF/MANIFEST.MF(包含 JDK 和用户)
- jar 文件中的时间戳
我首先找到了解决这两个问题的方法,但后者有点困难。似乎 AbstractZipArchiver(在 zipFile() 和 zipDir() 中完成所有工作)并不是为了允许对存档的生成方式进行任何类型的扩展。
目前我可以想象四种方法(但非常欢迎更多想法):
- 创建当前 maven-jar-plugin 实现的派生,允许
timestamp=<number>属性,然后将其用于插入到 jar 文件中的所有条目。如果未设置,则保留当前行为。 - 修改 Jenkins 指纹识别方案,使其了解 jar 文件并且只查看条目内容,而不查看它们的元数据。
- 将插件附加到
prepare-package阶段,负责touch使用特定时间戳的文件。这要求当时所有文件都存在(意味着不能允许 jar 插件接触 MANIFEST.MF 文件) - 将一个额外的插件附加到“包”阶段,它会重写完成的 jar 文件,将过程中的所有 zip 条目时间戳归零。
同样,我们的目标是让 maven SNAPSHOT 工件完全独立于时间,因此在相同的来源下,您将获得具有相同 MD5 校验和的工件。不过,我也相信这可能对发布版本有益。
我应该如何处理这个问题?
【问题讨论】:
-
您正试图强制快照表现得像发布一样。给你的客户发布版本不是更简单,然后 Maven/Jenkins 等将毫不费力地工作吗?
-
RELEASE 工件在被 Jenkins 重建时的行为方式相同。
-
您能解释一下为什么要重建未更改的快照吗?如果您有一个创建一百万个不同快照的超大型项目,那么单独构建模块或将项目拆分为更小的项目可能是有意义的。在我看来,您试图开发一种解决方法而不是实际解决根本原因。
-
@PeterSchuetze 如果您有很多 maven 项目,每个项目都对应于一个应用程序发送给客户或一个库,这些应用程序中的几个应用程序使用它们,通常将它们组合在一个父项目下。就像现在一样,最简单的方法是将 Jenkins 指向父 pom,然后“mvn clean install”会清理 all 模块并安装 all 模块。 “正确的做法”是为每个模块设置一个 Jenkins 作业,但这非常繁琐——对我们来说可能有一百多个作业。
标签: java maven jar jenkins continuous-delivery