2015-12-11 33 views
0

我正在研究一個MSBuild腳本,它的任務是構建解決方案,然後將兩個項目的構建輸出複製到統一目錄中。夠簡單。關於MSBuild ItemGroup的內容困惑

我正在用複製任務完成此任務。像這樣:

<ItemGroup> 
    <OutputFiles1 Include="Project1\bin\Release\*.*" /> 
    <OutputFiles2 Include="Project2\bin\Release\*.*" /> 
</ItemGroup> 

<Target CopyOutput> 
    <Copy SourceFiles="@(OutputFiles1)" DestinationFolder="DeployOutput" /> 
    <Copy SourceFiles="@(OutputFiles2)" DestinationFolder="DeployOutput" /> 
</Target> 

我遇到的問題是這樣的:兩個的ItemGroup元素包含在目錄中的內容時,構建腳本開始,而不是當溶液建立該目錄的內容完成

因此,例如,如果我將Project1中的引用添加到新程序集中,然後運行構建,則DeployOutput目錄不包含該新程序集,因爲它在構建開始時不存在於項目輸出目錄中。但是如果我再次運行版本該文件在那裏並被複制。

這似乎是這樣的行爲是設計,但我不確定如何完成我的任務,而不會產生到一個批處理文件或類似的副本。

回答

1

古典msbuild evaluation order問題:項目根目錄中的項目和屬性基本上是在分析之前評估的,在任何目標運行之前。將它們放入目標中,然後在目標運行時對它們進行評估。這對你的情況更好,因爲你也可以確保一個目標在另一個目標之後運行,從而使第一個目標看到後者生成的輸出。插圖:

<ItemGroup> 
    <OutputFiles1 Include="Project1\bin\Release\*.*" /> 
</ItemGroup> 

<Target Name="BuildIt"> 
    <Message Text="[email protected](OutputFiles1)" /> 
    <MSBuild Projects="Project1.vcxproj" Targets="Build" /> 
</Target> 

<Target Name="Copy" DependsOnTargets="BuildIt"> 
    <ItemGroup> 
    <ActualOutputFiles1 Include="Project1\bin\Release\*.*" /> 
    </ItemGroup> 
    <Message Text="[email protected](OutputFiles1)" /> 
    <Message Text="[email protected](ActualOutputFiles1)" /> 
</Target> 

當運行復制目標(以及輸出目錄仍是空的),你會得到輸出如下

OutputFiles1= 
.... build output .... 
OutputFiles1= 
ActualOutputFiles1=Project1\bin\Release\a.dll;...... 

OutputFiles1總是空的,因爲在當時被評價的輸出目錄是空的。 ActualOutputFiles1然而在之後被評估爲,因此它包含輸出目錄的內容。

+0

謝謝。我的女朋友現在也感謝你,我不再需要沮喪地禿頂。 –

+0

在這種情況下:向我的女朋友打個招呼,我希望在這裏有更多的無憂無慮的日子:] – stijn