【问题标题】:Build order in CruiseControl.NET with project dependenciesCruiseControl.NET 中的构建顺序与项目依赖项
【发布时间】:2009-06-12 19:21:29
【问题描述】:

在我们的 .NET 软件开发商店中,我们设置了 CruiseControl.NET 来构建 28 个项目,其中一些是相互依赖的。每个项目大致代表一个与单元测试配对的 Visual Studio 项目或 Flex 库。令我恼火的是,我还没有找到一种好的方法来确保项目按照表示依赖项的顺序构建。

这是我正在做的事情:

  1. 一切都在同一个构建队列中。我这样做是为了按顺序完成构建,这样我就可以避免需要多个工作目录。
  2. 我为项目设置了队列优先级,我认为这会影响它们的构建顺序。但仔细阅读文档后,我发现它只是在队列中有多个构建请求时控制优先级。
  3. 除了使用间隔触发器启动构建之外,我还使用项目触发器,以便在成功构建依赖项时,它们的依赖项也会构建。

在某种程度上,这种设置是有效的。主要问题是,如果有人对项目 A 和项目 B 中的代码进行了更改,其中项目 B 依赖于项目 A。有时,项目 B 会在项目 A 之前构建。因为项目 A 尚未构建,所以这可以有时会导致项目 B 中断。这是暂时的,因为间隔触发器会导致项目 A 稍后构建,并且其成功构建会触发项目 B 重新构建并得到修复。我要避免的是在项目 A 之前构建项目 B,这样就不会发生中间损坏。

您使用哪些实践来正确管理 CruiseControl.NET 服务器上的相互依赖关系?在这一点上,我不愿意换成像 TeamCity 这样的非免费持续集成包。

【问题讨论】:

    标签: .net continuous-integration cruisecontrol.net


    【解决方案1】:

    不要将依赖项放在 CC.NET 项目设置中。您需要通过 NAnt 脚本控制项目构建顺序。您不必在解决方案级别上构建,您可以在单个项目级别上构建。

    <target name="Project1" depends="Projects2" description="Builds project 1">
         <msbuild>
            <executable>C:\WINDOWS\Microsoft.NET\Framework\v2.0.50727\MSBuild.exe</executable>
            <workingDirectory>C:\dev\ccnet</workingDirectory>
            <projectFile>CCNet.sln</projectFile>
            <buildArgs>/noconsolelogger /p:Configuration=Debug /v:diag</buildArgs>
            <targets>Build;Test</targets>
            <timeout>900</timeout>
            <logger>C:\Program Files\CruiseControl.NET\server\ThoughtWorks.CruiseControl.MsBuild.dll</logger>
         </msbuild>
    </target>
    
    <target name="Project2" depends="Projects3" description="Builds project 2">
         <msbuild>
            <executable>C:\WINDOWS\Microsoft.NET\Framework\v2.0.50727\MSBuild.exe</executable>
            <workingDirectory>C:\dev\ccnet</workingDirectory>
            <projectFile>CCNet.sln</projectFile>
            <buildArgs>/noconsolelogger /p:Configuration=Debug /v:diag</buildArgs>
            <targets>Build;Test</targets>
            <timeout>900</timeout>
            <logger>C:\Program Files\CruiseControl.NET\server\ThoughtWorks.CruiseControl.MsBuild.dll</logger>
         </msbuild>
    </target>
    
    <target name="Project3" description="Builds Project 3">
         <msbuild>
                <executable>C:\WINDOWS\Microsoft.NET\Framework\v2.0.50727\MSBuild.exe</executable>
                <workingDirectory>C:\dev\ccnet</workingDirectory>
                <projectFile>CCNet.sln</projectFile>
                <buildArgs>/noconsolelogger /p:Configuration=Debug /v:diag</buildArgs>
                <targets>Build;Test</targets>
                <timeout>900</timeout>
                <logger>C:\Program Files\CruiseControl.NET\server\ThoughtWorks.CruiseControl.MsBuild.dll</logger>
         </msbuild>
    </target>
    

    您可以在单个项目级别上运行单元测试,因此您不需要在多个项目上重复运行。

    【讨论】:

    • 这样做意味着我必须将每个依赖项目的构建指令复制到每个依赖项目中。但我想如果事实证明我无法控制 CC.NET 中的构建顺序,我将不得不变得多余。至少我可以使用 CC.NET 对 XML Entities 的支持来封装项目的构建步骤。
    • 不一定。使用单个 Cruise.build 文件来存储 NAnt 脚本。在项目之间共享这个单一的 Cruise.build 文件,这样它们都遵循依赖层次结构,而您不会复制脚本。
    • 虽然构建框仍然需要进行重复构建很糟糕,但看起来没有什么好办法。这个答案看起来是最好的。
    • 不幸的是,可能是这样。尽管您可以使用 msbuild 和已编译的存储位置来跳过构建已编译的 DLL,从而避免一些开销。
    【解决方案2】:

    我建议您不要将 CruiseControl 项目的概念与 Visual Studio 项目混为一谈!我通常会建立一个包含大量工作的 CC 项目。对我来说,这意味着 CC 项目将运行一个 NAnt 脚本。 NAnt 脚本对我做什么和什么时候做有非常细粒度的控制。这意味着我可以构建我的解决方案(它知道首先构建哪个项目!),运行我的单元测试,重置数据库,部署一些代码,发送一些电子邮件,进行一些代码分析(NDepend 和 NCover 很棒!),等等。这意味着我有一个项目出现在 CCTray 中,这让事情更加真实。然后我可以在 CC 中创建一个新项目来控制我何时从 DEV 推送到 STAGING 以及从 STAGING 推送到 PROD,以便我们可以“按下按钮”这个任务。但这仅产生了 3 个巡航控制项目,并且对用户更加友好。

    【讨论】:

    • 同意。 VS 解决方案文件的概念更类似于我们的 CC 构建。我们的 CC 项目每个都代表一个“产品”,每个产品都有很多很多 .csproj 文件。
    • 我不这样做的主要原因是因为我有“属于”每个 VS 项目的单元测试,并且我不想为共享的每个解决方案运行相同的单元测试项目。
    【解决方案3】:

    虽然您已经接受了答案,但我建议您提出其他建议:您不应该在两个项目之间建立直接依赖关系。 “直接”是指每次项目 A 中的二进制文件发生变化时,这并不意味着您会自动使用它们来构建项目 B。

    更新这些引用的过程应该(由你自己)控制,否则你将不可避免地为项目 B 生成大量损坏的构建。

    我倾向于将 lib 目录(和子目录)下的所有外部二进制文件置于源代码控制之下,并仅在我决定这样做时更新它们。 “外部”是指第 3 方库和我公司其他项目的库(例如:http://code.google.com/p/projectpilot/source/browse/#svn/trunk/lib

    【讨论】:

      猜你喜欢
      • 2014-03-19
      • 2017-02-11
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-01-30
      • 1970-01-01
      • 2015-11-22
      • 2011-08-15
      相关资源
      最近更新 更多