Msbuild 如何在编译之前对文件进行获取排序?

Msbuild 如何在编译之前对文件进行获取排序?,msbuild,wix,tfsbuild,Msbuild,Wix,Tfsbuild,我使用在TFS构建服务器中生成结构。在此之后,我使用WiX项目中的来正确获取_PublishedApplications文件夹的内容。但我的问题是构建过程中的顺序 如果我在中使用,它不包括复制到_PublishedApplications的二进制文件,因为捕获是在发布(文件拷贝)之前执行的 如果在编译之前将目标更改为,编译将不会成功,因为首先没有文件。以下是WiX项目(其相关部分)的代码: 简单工程 {GUID} 真的 真的 二进制文件 安装文件夹 问题 二进制文件复制到_Published

我使用在TFS构建服务器中生成结构。在此之后,我使用WiX项目中的
来正确获取_PublishedApplications文件夹的内容。但我的问题是构建过程中的顺序

如果我在
中使用
,它不包括复制到_PublishedApplications的二进制文件,因为捕获是在发布(文件拷贝)之前执行的

如果在编译之前将目标更改为
,编译将不会成功,因为首先没有文件。以下是WiX项目(其相关部分)的代码:


简单工程
{GUID}
真的
真的
二进制文件
安装文件夹
问题


二进制文件复制到_PublishedApplications后,如何执行捕获?

您需要做的第一件事是将安装程序项目中的项目引用添加到应用程序项目中。这将强制应用程序生成并可用于安装程序项目

如果右键单击VisualStudio下的解决方案并单击“项目生成顺序…”,如果需要更改配置项目依赖项所需的顺序,则可以验证项目的生成顺序。

然后在安装程序项目中执行以下操作:

    <PropertyGroup>
        <RootDir>{PATH TO _PublishedApplications FOLDER}</RootDir>
        <HarvestDirectoryNoLogo>true</HarvestDirectoryNoLogo>
        <HarvestDirectorySuppressAllWarnings>false</HarvestDirectorySuppressAllWarnings>
        <HarvestDirectoryTreatWarningsAsErrors>false</HarvestDirectoryTreatWarningsAsErrors>
        <HarvestDirectoryTreatSpecificWarningsAsErrors>
        </HarvestDirectoryTreatSpecificWarningsAsErrors>
        <HarvestDirectoryVerboseOutput>false</HarvestDirectoryVerboseOutput>
        <HarvestDirectoryAutogenerateGuids>false</HarvestDirectoryAutogenerateGuids>
        <HarvestDirectoryGenerateGuidsNow>true</HarvestDirectoryGenerateGuidsNow>
        <HarvestDirectorySuppressFragments>true</HarvestDirectorySuppressFragments>
        <HarvestDirectorySuppressUniqueIds>false</HarvestDirectorySuppressUniqueIds>
    </PropertyGroup>
    <Import Project="$(WixTargetsPath)" />
    <Target Name="BeforeBuild">
        <ItemGroup>
            <HarvestDirectory Include="$(RootDir)">
                <Transforms>
                </Transforms>
                <ComponentGroupName>MyComponent</ComponentGroupName>
                <DirectoryRefId>WebSiteRoot</DirectoryRefId>
                <PreprocessorVariable>var.RootDir</PreprocessorVariable>
                <SuppressCom>false</SuppressCom>
                <SuppressRegistry>false</SuppressRegistry>
                <SuppressRootDirectory>true</SuppressRootDirectory>
                <KeepEmptyDirectories>true</KeepEmptyDirectories>
            </HarvestDirectory>
        </ItemGroup>
        <HeatDirectory 
            NoLogo="$(HarvestDirectoryNoLogo)" 
            SuppressAllWarnings="$(HarvestDirectorySuppressAllWarnings)" 
            SuppressSpecificWarnings="$(HarvestDirectorySuppressSpecificWarnings)" 
            ToolPath="$(WixToolPath)" 
            TreatWarningsAsErrors="$(HarvestDirectoryTreatWarningsAsErrors)" 
            TreatSpecificWarningsAsErrors="$(HarvestDirectoryTreatSpecificWarningsAsErrors)" 
            VerboseOutput="$(HarvestDirectoryVerboseOutput)" 
            AutogenerateGuids="$(HarvestDirectoryAutogenerateGuids)" 
            GenerateGuidsNow="$(HarvestDirectoryGenerateGuidsNow)" 
            OutputFile="$(IntermediateOutputPath)_%(HarvestDirectory.Filename)_dir.wxs" 
            SuppressFragments="$(HarvestDirectorySuppressFragments)" 
            SuppressUniqueIds="$(HarvestDirectorySuppressUniqueIds)" 
            Transforms="%(HarvestDirectory.Transforms)" 
            Directory="@(HarvestDirectory)" 
            ComponentGroupName="%(HarvestDirectory.ComponentGroupName)" 
            DirectoryRefId="%(HarvestDirectory.DirectoryRefId)" 
            KeepEmptyDirectories="%(HarvestDirectory.KeepEmptyDirectories)" 
            PreprocessorVariable="%(HarvestDirectory.PreprocessorVariable)" 
            SuppressCom="%(HarvestDirectory.SuppressCom)" 
            SuppressRootDirectory="%(HarvestDirectory.SuppressRootDirectory)" 
            SuppressRegistry="%(HarvestDirectory.SuppressRegistry)" />
    </Target>
</Project>

{到_PublishedApplications文件夹的路径}
真的
假的
假的
假的
假的
真的
真的
假的
真菌成分
网站根
根迪尔变种
假的
假的
真的
真的

我根据的文档生成了此代码,并将其用于实际项目中。

我使用以下命令构建解决方案:

msbuild SimpleInstaller.sln /p:OutDir=C:\Temp\Output\ /v:diag > C:\Temp\Log.txt
这将把所有日志输出到文本文件。您可以使用

然后我发现,当您构建一个C#项目时,会调用文件Microsoft.Common.targets中的target
Compile
。此目标有一个属性
DependsOnTarget
,其中包含对编译前目标
的引用

在我自己的C#项目中,我可以在编译之前覆盖这个目标
,只需在它的末尾添加以下代码(file.csproj):

所有这些问题都是因为我在解决方案中的第一个项目是WiX项目,然后我才添加了C#projects。由于这个原因,
BeforeBuild
是在执行其他所有操作之前执行的

解决此问题的另一个解决方案是编辑解决方案文件(.sln),并将解决方案文件开头的WiX项目声明移动到所有项目声明的结尾(而不是解决方案文件的结尾)。然后WiX项目的
BeforeBuild
将在C#项目创建_PublishedApplications文件夹后执行

此手动编辑是必需的,因为如果更改项目生成顺序,实际上是在更改项目引用(至少在解决方案文件中),但在负责调用任何引用的生成的
ResolveProjectReferences
之前,仍会调用目标
BeforeBuild

这是项目声明,应在所有其他声明之后:

Project("GUID") = "SimpleInstaller", "SimpleInstaller\SimpleInstaller.wixproj", "GUID"
EndProject

我的建议仍然是使用
Harvest
target,因为它独立于解决方案文件中的任何更改。

这与我所做的完全相同,并且不起作用,因为复制输出的NuGet\u PublishedApplications包中的任务是在捕获之后执行的。它独立于项目的引用。不应直接编辑解决方案文件。VS中有这样一个选项。请查看我回答中的更新。即使您更改了项目构建顺序,当您执行构建时,第一个目标是文件中的第一个项目。然后,调用第一个项目的BeforeBuild。只有在调用BeforeBuild之后,才会调用ResolveProjectReferences,因此即使您通过添加项目引用来更改生成顺序,它在这种特定情况下也不会起作用。我有一个解决方案文件(VS 2013u5-12.0.40629.0),其中.wixproj是在文件中最后一个(项目引用)定义的,但我仍在观察.wixproj的BeforeBuild目标在依赖项目生成之前被调用的行为。
  ...
  <Target Name="BeforeCompile">
    <!-- custom action. -->
  </Target>
</Project>
<Target Name="Harvest">
  <HeatDirectory OutputFile="Autogenerated.wxs" Directory="$(Sources)"
                 PreprocessorVariable="var.SimpleProject.TargetDir" 
                 AutogenerateGuids="true" SuppressRegistry="true"
                 ToolPath="$(WixToolPath)" DirectoryRefId="INSTALLFOLDER"
                 ComponentGroupName="ComponentGroup_Core" 
                 SuppressRootDirectory="true" />
</Target>
Project("GUID") = "SimpleInstaller", "SimpleInstaller\SimpleInstaller.wixproj", "GUID"
EndProject