我对如何处理“过时”的 msbuild 输出工件感到有些困惑。
基本上我已经编写了一个在输入文件上创建聚合的目标。
<Target Name="AggregateFoos"
Inputs="@(Foo)"
Outputs="@(Foo->%'AggregationTargetMetadata')">
<WriteLinesToFile File="%(Foo.AggregationTargetMetadata)" Lines="@(Foo)" Overwrite="true" />
</Target>
每当目标聚合文件(及其以前Foo
的目标)发生更改时,这都会得到很好的处理,并得到正确更新。除非文件是聚合的最后一个成员。AggregationTargetMetadata
基本上,输入和X
映射的变化更新都Y
和预期的一样。更改也正确更新-但是永远停留在它的“旧”孤立状态。Z
X -> A , Y -> A, Z -> B
Y -> B
A
B
Z -> A
A
B
我的理解是这是预期的行为,因为B
现在不再是项目任何项目的成员(直接或传递)。
如果聚合只是动态地滑入构建过程,这将是半好的。遗憾的是,它们可能被用作其他事物的设计时间资源,因此通常聚合实际上是项目项本身,并且整个聚合逻辑仅用于更新聚合内容。
现在......我将如何识别“孤立”聚合?
我想我已经想出了一个解决方案,我可以扩展我的聚合以创建指标文件,在聚合之后执行另一个(非增量)目标,然后使用自定义 CodeFragment 任务(甚至是基于预构建的程序集)来检查对于没有源映射的标记...
<Target Name="AggregateFoos"
Inputs="@(Foo)"
Outputs="@(Foo->%'AggregationTargetMetadata');@(Foo->$(IntermediateBuildPath)Foo\%'AggregationTargetMetadata'.foo)">
<WriteLinesToFile File="%(Foo.AggregationTargetMetadata)" Lines="@(Foo)" Overwrite="true" />
<Touch AlwaysCreate="true"
Files="$(IntermediateBuildPath)Foo\%(Foo.AggregationTargetMetadata).foo" />
</Target>
<Target Name="FooOrphanLookup"
AfterTargets="AggregateFoos">
<MagicLookups CurrentFoosAndMapping="@(Foo)"
Markers="$(IntermediateBuildPath)Foo\**.foo" />
<!-- MagicLookups would look through all Markers and give at least
a warning if there is not a Foo with a corresponding AggregationTargetMetadata -->
</Target>
总而言之,这感觉很科学。有没有更简单的方法?