如何始终在MSBuild中执行目标

Jas*_*son 4 msbuild

我有一个MSBuild文件,在编译应用程序之前操作AssemblyInfo文件.在构建结束时,它将还原AssemblyInfo文件.它通过备份文件,操作它,然后在构建时间之后恢复文件来完成此操作.

这种方法非常有效,除非在构建期间发生错误.然后它不会恢复原始文件.有没有办法告诉MSBuild在构建结束时执行目标,无论它成功还是失败?

Say*_*imi 5

根据您对原始问题的最后评论,我会采取另一种方法,并忘记您目前采取的方法.您应该知道您的版本信息不必在AssemblyInfo.cs文件中.它可以在任何代码文件中,只要你只有每个定义一次AssemblyVersion和AssemblyFileVersion属性.有了这样说,我会做的是遵循以下步骤:

  1. 从AssemblyInfo.cs中删除AssemblyVersion和AssemblyFileVersion
  2. 创建一个新文件,在我的情况下将它命名为您想要的名称我将它放在Properties\VersionInfo.cs中.不要将此文件添加到项目中.
  3. 编辑项目文件以将该文件包含在仅在您需要时编译的文件列表中

让我们在#3上稍微扩展一下.构建.NET项目时,项目本身就是一个MSBuild文件.在该文件中,您将找到一个声明为Compile的项目.这是将发送到编译器的文件列表.您可以动态地包含/排除该列表中的文件.在这种情况下,只有在构建服务器(或您定义的任何其他条件)上构建时,才要包含VersionInfo.cs文件.对于此示例,我将条件定义为项目是否在发布模式下构建.因此,对于Release模式,VersionInfo.cs将被发送到编译器,而不是其他版本.以下是VersionInfo.cs的内容

VersionInfo.cs

[assembly: System.Reflection.AssemblyVersion("1.2.3.4")]
[assembly: System.Reflection.AssemblyFileVersion("1.2.3.4")]
Run Code Online (Sandbox Code Playgroud)

为了将其挂钩到构建过程中,您必须编辑项目文件.在该文件中,您将找到一个元素(可能超过1,具体取决于项目类型).您应该添加类似于以下内容的目标.

<Target Name="BeforeCompile">
  <ItemGroup Condition=" '$(Configuration)'=='Release' ">
    <Compile Include="Properties\VersionInfo.cs" />
  </ItemGroup>
</Target>
Run Code Online (Sandbox Code Playgroud)

这里我在这里做的是定义一个目标,BeforeCompile,这是一个众所周知的目标,你可以覆盖.请参阅此MSDN有关其他类似目标的文章.基本上,这是一个在调用编译器之前始终会调用的目标.在此目标中,仅当Configuration属性设置为release时,才将VersionInfo.cs添加到Compile项.您可以将该属性定义为您想要的任何属性.例如,如果你有TFS作为你的构建服务器,那么它可能是,

<Target Name="BeforeCompile">
  <ItemGroup Condition=" '$(TeamFoundationServerUrl)'!='' ">
    <Compile Include="Properties\VersionInfo.cs" />
  </ItemGroup>
</Target>
Run Code Online (Sandbox Code Playgroud)

因为我们知道TeamFoundationServerUrl仅在通过TFS构建时定义.

如果您正在构建命令行,那么就像这样

<Target Name="BeforeCompile">
  <ItemGroup Condition=" '$(IncludeVersionInfo)'=='true' ">
    <Compile Include="Properties\VersionInfo.cs" />
  </ItemGroup>
</Target>
Run Code Online (Sandbox Code Playgroud)

当您构建项目时,只需执行msbuild.exe YourProject.proj/p:IncludeVersion = true.注意:构建解决方案时,这不起作用.


Pet*_*voy 2

改变一下问题怎么样:

  • 将“模板”AssemblyInfo.cs.template 添加到版本控制中,代表您的“理想”AssemblyInfo.cs,其中包含正则表达式挂钩
  • 在构建之前,将模板复制到真实模板并应用正则表达式
  • 为 AssemblyInfo.cs 添加某种颠覆忽略(我不是 svn 专家,但我很确定有一种方法可以告诉它忽略某些文件)
  • 如果您的开发人员需要添加某种通常出现在 AssemblyInfo.cs 中的自定义(例如 InternalsVisibleTo),请让他们将其添加到已签入的其他.cs 文件中。

作为进一步的改进,将 Sayed 的解决方案与我的解决方案结合起来,从实际的 AssemblyInfo.cs 中删除版本信息内容,并签入 VersionInfo.cs.template,从而在 BeforeBuild 中创建 VersionInfo.cs。