2017-10-10 74 views
0

我有一個代碼生成器工具,我部分擁有,現在csproj文件可以列出它們中的多個目標框架並構建它們全部,我想弄清楚如何使MSBuild目標只做代碼生成每運行一次構建,無論列出了多少個目標框架,並且每個目標框架的編譯都要等到代碼生成完成。如何製作僅在TargetFrameworks標記中的每個框架運行一次的目標之前運行一次而不是運行一次的MSBuild目標?

我目前擁有TargetFramework特定值的條件。例如,Condition="'netstandard2.0' == '$(TargetFramework)'"

這可避免同時爲每個目標框架啓動代碼生成工具,然後在進程嘗試創建/更新相同文件時獲取訪問被拒絕錯誤。

但是,其他目標框架正確地嘗試編譯而不等待代碼生成完成,並且在沒有該代碼存在的情況下失敗。

我希望每次構建項目時都只發生一次代碼生成,並且每個目標框架的編譯僅在完成後纔開始。

每次構建運行時都需要運行,以防輸入發生變化並生成不同的代碼。

注意:目前我忽略了使用#if FrameworkSpecificDefine將不同的輸入代碼添加到代碼生成器的情況,這樣不同的目標框架會導致代碼生成器的不同輸出。目前,我正在考慮代碼生成器的輸出在所有目標框架中都是相同和有效的。

更新:尋找出現這種情況的MSBuild分成TargetFramework特定之前版本,我可以再勾之前建立一個目標之後,我在VS看到這個詳細的生成輸出:

1>Target _SetBuildInnerTarget: 
1>Target _ComputeTargetFrameworkItems: 
1>Target DispatchToInnerBuilds: 
1> Using "MSBuild" task from assembly "Microsoft.Build.Tasks.Core, Version=15.1.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a". 
1> Task "MSBuild" 
1> Additional Properties for project "ProjectA.csproj": 
1>  TargetFramework=netstandard2.0 
1> Additional Properties for project "ProjectA.csproj": 
1>  TargetFramework=net47 

我然後將我的目標設置爲BeforeTargets="DispatchToInnerBuilds",它在專門設置TargetFramework的單個構建之前運行,似乎完全符合我的需求。

(添加到BuildDependsOn屬性似乎不再工作:Add a msbuild task that runs after building a .NET Core project in Visual Studio 2017 RC;我懷疑Microsoft.Common.targets稍後以新的csproj格式進行評估,並且任何附加到您在項目文件中執行的屬性被Microsoft.Common.targets覆蓋。)

+0

這是否會每次構建一次或一次? –

+0

你可以用CoreBuildDependsOn或類似的方式注入你的目標嗎? –

回答

0

雖然有些目標只能在內部構建中運行,例如當您使用BeforeTargets="BeforeBuild"時,外部版本還定義了IsCrossTargetingBuild變量,以指示當前正在運行的構建是分派到內部構建的外部構建,並且是調整目標的首選方式。

因此,您可以像Condition="'$(IsCrossTargetingBuild)' == 'true'"那樣調整目標以確保目標僅針對外部構建運行。