MSbuild Copy whole folder

╄→尐↘猪︶ㄣ 提交于 2019-12-20 10:18:10

问题


trying to copy a whole folder, but when i do this:

<Copy SourceFiles="$(TargetDir)\*.*" DestinationFolder="$(BuildOutput)\SomeDir" />

the copy attempts to do this: copy c:\source\*.* c:\destination\SomeDir\*.* and fails with "illegal characters"


回答1:


Specify your ItemGroup for SourceFiles explicitly.

<ItemGroup>
    <_CopyItems Include="$(TargetDir)\*.*" />
</ItemGroup>
<Copy
    SourceFiles="@(_CopyItems)"
    DestinationFolder="$(BuildOutput)\SomeDir"
    />

Note that _CopyItems is an item type, so it's referenced using '@' symbol rather than '$'.




回答2:


Copying files can be done with the following code snippet which handles antivirus programs and subdirectories

  <ItemGroup>
        <SomeAppStuff Include="$(SolutionDir)\ProjectXXX\bins\**\*.*" />
  </ItemGroup>
  <Copy 
      SourceFiles="@(SomeAppStaff)" 
      DestinationFolder="$(OutputPath)\%(RecursiveDir)" 
      SkipUnchangedFiles="true"
      OverwriteReadOnlyFiles="true" 
      Retries="3"
      RetryDelayMilliseconds="300"/>

Specifying $(OutputPath)\%(RecursiveDir) will ask Copy task to respect subfolders, so it will place subfolders of source directory to subfolders of target directories.

SkipUnchangedFiles will increase build speed on computers with enough memory, because Windows optimizes IO for frequently used files when there's enough RAM.

Retries and RetryDelayMilliseconds handles issues related a) Compressed NTFS file system, when builds fails in seldom cases b) Antivirus Software with SSD drives.




回答3:


Looking at the MSDN documentation, I believe the SourceFiles parameter requires an ITaskItem[] value. See MSDN MSBuild Copy Task

The last example on the above link is to do a recursive copy from one directory to another, maintaining the folder structure.




回答4:


If you put the folder in the root of your c# project then you can simple put this in your csproj.

<ItemGroup>
    <None Update="FolderToCopy\**\*.*">
      <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
    </None>
</ItemGroup>

I have only tested in the 2017 version of csproj, but I assume it's backwards compatible. Could be wrong on that though




回答5:


Succeeded to accomplish this task like this

<Target Name="AfterBuild">
  <ItemGroup>
    <SomeDir Include="$(SolutionDir)\SomeOtherProject\SomeDir\**\*" />
  </ItemGroup>
  <Copy 
    SourceFiles="@(SomeDir)" 
    DestinationFiles="@(SomeDir->'$(OutDir)\SomeDir\%(RecursiveDir)%(Filename)%(Extension)')" 
    SkipUnchangedFiles="true" 
    OverwriteReadOnlyFiles="true" 
    Retries="3" 
    RetryDelayMilliseconds="300" />




回答6:


For me what worked was this: - kept folder structure - copied all files within the folder - works for any folder, doesn't have to be in the project or the same project folder

<ItemGroup>
    <_CopyItems Include="<path relative to project>\**\*.*" />
</ItemGroup>

<Target Name="AfterBuild">
  <Copy SourceFiles="@(_CopyItems)" DestinationFiles="@(_CopyItems->'$(OutDir)\<output folder>\%(RecursiveDir)%(Filename)%(Extension)')"/>
</Target>

legend:

  • <path relative to project>: this could be any path, using ..\ for going above the proj folder works
  • <output folder>: folder you want the whole file structure to be dropped into, excluding the source folder.
  • $(OutDir) will be bin\Debug or whatever build mode you have, if you want something else, change that.


来源:https://stackoverflow.com/questions/5123655/msbuild-copy-whole-folder

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!