如何在Visual Studio中关闭生成定义的缓存

24

在项目文件中,我导入了自己的目标文件。

<Import Project="Build\CopyDependencies.target" />

后来我从那个目标文件中调用了目标。

<CallTarget Targets="CopyDependencies" UseResultsCache="false" />

如果我编辑CopyDependencies.target文件,则必须重新加载整个解决方案,只有这样更改才会生效。我认为这是Visual Studio中某种构建定义缓存的问题?如果是这样,也许可以将其关闭?

5个回答

15

感谢 @KazR

以下是一种更简洁的解决方案,可以将其插入到您的 .csproj 文件中。

<Target Name="AfterBuild">
  <PropertyGroup>
    <TempProjectFile>Build.$([System.Guid]::NewGuid()).proj</TempProjectFile>
  </PropertyGroup>
  <Copy SourceFiles="Build.proj" DestinationFiles="$(TempProjectFile)" />
  <MSBuild Projects="$(TempProjectFile)" />
  <ItemGroup>
    <TempProjectFiles Include="Build.????????-????-????-????-????????????.proj"/>
  </ItemGroup>
  <Delete Files="@(TempProjectFiles)" />
</Target>

问题已解决


2
似乎是一个合理的解决方法。对于 MSBuild 4,您可以在目标内部使用 PropertyGroup 而不是 CreateProperty。 - Sayed Ibrahim Hashimi
谢谢你的建议,我已经改了……看起来好多了。 - Martin
如果您正在导入项目而不是构建项目,那么如何应用这种解决方案呢?这个方法行不通:http://pastie.org/4695504(在目标内部导入无效) - user479911
arex1337,我不知道。你可能需要从单独的构建项目中调用该项目来完成此操作,因为VS会非常积极地缓存这些内容。 - Martin
2
+1。我投票支持 Build.????????-????-????-????-????????????.proj 作为今天的代码片段!它和KISS一样有趣 :D - quetzalcoatl

9
我不知道如何禁用VS缓存,但是我有一个解决方法,可以让您在不重新加载解决方案的情况下编辑构建目标。您可以在proj文件中使用MSBuild任务来调用包装器目标,将CopyDependencies.target文件复制到CopyDependencies.[RandomNumber].target,然后在新创建的文件中调用CopyDependencies目标,最后删除它。这将强制VS在每次调用时重新加载目标,因为文件名不同。以下是一个示例:myProject.proj,请将其添加到AfterBuild目标中:
<MSBuild Projects="Wrapper.target" Targets="MyWrappedTarget" UnloadProjectsOnCompletion="true"/>

Wrapper.target

这里的“target”是在构建时将复制真实目标文件并在其中调用所需构建目标的目标(我使用了内联c#任务,它只在MSBuild 4.0中可用):

    <UsingTask TaskName="RandomNumber" TaskFactory="CodeTaskFactory" AssemblyFile="$(MSBuildToolsPath)\Microsoft.Build.Tasks.v4.0.dll">
    <ParameterGroup>
        <Number ParameterType="System.Int32" Output="true"/>
    </ParameterGroup>
    <Task>
        <Code Type="Fragment" Language="cs">
        <!-- CDATA -->
        Random rndGenerator = new Random();
        Number = rndGenerator.Next(Int32.MaxValue);
        <!-- CDATA -->
        </Code>
    </Task>
</UsingTask>

<Target Name="MyWrappedTarget">
    <Message Text="MyWrappedTarget target called"/>


    <RandomNumber>
        <Output TaskParameter="Number" PropertyName="FileNumber"/>
    </RandomNumber>

    <PropertyGroup>
        <CopiedTarget>inner.test.$(FileNumber).target</CopiedTarget>
    </PropertyGroup>

    <Copy SourceFiles="inner.test.target" DestinationFiles="$(CopiedTarget)"/>

    <MSBuild Projects="$(CopiedTarget)" Targets="_innerTestTarget"/>

    <Delete Files="$(CopiedTarget)"/>
</Target>

inner.test.target

这个参数包含了你想要执行的真正构建目标,在这个例子中它是一个简单的文件复制。

    <Target Name="_innerTestTarget">

    <Message Text="This is a inner test text message"/>
    <Copy SourceFiles="x.txt" DestinationFiles="x1.txt"/>
</Target>

虽然这还不是完全可用的产品,但希望能够说明我的观点。

通过这个(稍微有些复杂的)过程,您可以更改 inner.test.target 文件而无需在 VS 中重新加载解决方案。


4
这里有一个解决方案,不需要任何 MSBuild 脚本。我注意到,卸载和重新加载项目并不能解决缓存问题,但是关闭并重新打开解决方案可以。此外,如果 Visual Studio 注意到 .sln 文件已更改,它会提示您重新加载解决方案。最后,this superuser question 解释了如何在 Windows 中触摸文件。
将它们放在一起,我添加了一个 Visual Studio 外部工具来触摸当前解决方案文件。方法如下:
  1. 选择 TOOLS > External Tools ...
  2. 点击添加按钮以添加新工具。
  3. 设置属性如下:
    • 标题:重新加载解决方案
    • 命令:cmd.exe
    • 参数:/c copy "$(SolutionFileName)"+>nul
    • 初始目录:$(SolutionDir)
    • 并打开使用输出窗口
  4. 单击“确定”关闭“External Tools”窗口
现在,如果您对 MSBuild 文件进行了更改,只需选择 TOOLS > Reload Solution,所有构建文件都将被重新加载。

我正在使用Windows 7 64位和Visual Studio 2012 Express for Windows Desktop。


3

我有一个不涉及临时文件的不同解决方案:

Include.targets 文件:

<Project xmlns="http://schemas.microsoft.com/developer/msbuild/2003">

   <Target Name="Foobar">
      <Copy SourceFiles="test.source" DestinationFiles="testFoobar.dest" />
   </Target>

</Project>

项目文件:

....
<Target Name="BeforeBuild">
    <Exec Command="$(MSBuildToolsPath)\MSBuild.exe Include.targets /t:Foobar" ContinueOnError="false" />
</Target>
....

在这种情况下,VS无法识别MSBuild命令,并且不会缓存该文件。
愉快的编码!

2
我也需要引号: <Exec Command="&quot;$(MSBuildToolsPath)\MSBuild.exe&quot; $(TargetsFilePath)" ContinueOnError="false" /> - Cel

0

在运行MSBuild之前,我会运行以下命令来清除下载缓存:

call "%VS120COMNTOOLS%vsvars32.bat"
echo Clear download cache
gacutil -cdl

据我所知,GAC和下载缓存存储程序集,但不存储MSBuild文件。 - weir

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接