我想将SBT用于围绕具有数十个项目的单个Git存储库构建的构建.我希望从构建中获得以下可能性:
现在考虑到这些要求,构建的结构应该是什么?由于要求3,我不能只build.sbt在构建的根目录中使用单个,因为我不想将所有项目设置放在那里,因为它将是大量文本,并且每个更改都在一个项目将反映在顶层.
我也听说*.sbt根项目和子项目的文件使用都容易出错,一般不推荐(在SBT中的多项目构建下使用包为root项目生成工件,或者我如何使用sbt插件作为多项目构建中的依赖项?,子项目中的SBT:plugins.sbt会被忽略吗?等等.我只尝试*.sbt了不同级别的文件的简单多项目构建,它只是起作用.*.sbt考虑到上述要求,如果我要采用多文件方法,我需要记住哪些陷阱?
好的,因为到目前为止没有人发布任何东西,我想我已经发布了到目前为止我从使用 SBT 做单声道存储库中学到的东西。
首先是一些事实:我们的 SBT 构建由 40 多个项目组成,其中包含 10 多个通用项目(其他项目依赖于它们),以及与单个产品相关的 5 组项目(每组 5-7 个项目)。在每个组中,通常有一个组公共项目。
我们有以下构建结构:
build.sbt用于整个构建。build.sbt每个项目一个。project目录中的几个本地 SBT 插件。让我们来谈谈这些项目中的每一个。
build.sbt在这个文件中,定义了一般的构建结构。也就是说,我们在那里保留了跨项目依赖项。我们不使用标准commonSettings方法,例如:
val commonSettings = Seq(scalaVersion := "2.12.3", ...)
...
val proj1 = (project in file("p1")).settings(commonSettings)
val proj2 = (project in file("p2")).settings(commonSettings)
...
Run Code Online (Sandbox Code Playgroud)
这对于一个新项目来说过于冗长且容易出错。相反,我们使用本地 SBT 项目,该项目会自动应用于构建中的每个项目(稍后会详细介绍)。
build.sbt在这些文件中,我们通常定义所有项目设置(非自动插件、库依赖等)。我们没有在这些文件中定义跨项目依赖项,因为这并没有真正按预期工作。SBT*.sbt按特定顺序加载所有文件,并且每个构建中的项目定义都会覆盖先前找到的文件。换句话说,如果您避免在每个项目的*.sbt文件中(重新)定义项目,事情就会顺利进行。所有其他设置都可以保留在那里,以避免 main 中的太多混乱build.sbt。
我们使用一个技巧在<root_dir>/project/目录中定义 SBT 自动插件,并使它们为构建中的所有项目自动加载。我们使用这些插件自动定义所有项目的设置和任务(例如 Scalastyle、scalafmt、Sonar、部署等)。我们还在那里保留了通用设置(scalaVersion 等)。我们保留的另一件事<root_dir>/project/是公共依赖版本(不在插件中,只是纯*.scala文件)。
将 SBT 用于单存储库似乎有效,并且具有某些优点和缺点。
优点:在产品之间重用代码非常容易。Scalastyle、scalafmt 等常见的 SBT 内容也定义一次,所有新项目都可以免费获得。升级所有项目的依赖版本是在一个地方完成的,所以当有人升级版本时,他或她会立即为所有项目执行此操作,以便不同的团队从中受益。这需要团队之间的某些纪律,但到目前为止它对我们有用。
另一个优点是使用通用工具。我们有一个 Gerrit+Jenkins 持续集成,我们有一个单一的工作,例如提交前验证。新项目再次免费获得很多这种机器。
缺点:一方面,构建加载时间。在顶级 13" MacBook Pro 上,它可以轻松地持续 30 秒以上(这是从启动 SBT 到进入 SBT 命令提示符的时间)。不过,如果您可以保持 SBT 持续运行,这还不错。Intellij 刷新构建信息,它可能需要大约 15分钟。我不知道为什么它比在 SBT 中花费的时间长得多,但就是这样。除非绝对必要,否则可以通过避免刷新 Intellij 来减轻这种情况,但这真的很痛苦。
另一个问题是您无法将单个项目或一组项目加载到 Intellij IDEA 中。您被迫加载整个单声道存储库的构建。如果那是可能的,那么,我想,Intellij 的情况可能会更好。
另一个缺点是不能为不同的项目使用不同版本的相同 SBT 插件。当一个项目由于某种原因无法升级到新的插件版本时,整个存储库就不得不等待。有时这很有用,也就是说,它可以加快维护工作,并迫使我们使处于维护模式的项目保持最新状态。但有时对于遗留项目来说,这可能具有挑战性。
总而言之,我们已经在这种模式下工作了大约一年,我们打算在可预见的未来继续这样做。我们担心的是很长的 Intellij IDEA 刷新时间,而且随着我们在此构建中添加更多项目,情况只会变得更糟。我们可能会稍后评估替代构建系统,以避免我们单独加载项目以帮助提高 Intellij 性能,但 SBT 似乎可以胜任这项任务。