I have a content file to inlcude in the build output, but I would like to change its output name during the build process. For example, I have a file "LICENSE" for my Foo repository in GitHub. When I build the project, I should like to rename it to Foo.License.txt, so as to avoid colliding with other LICENSE files when the end user installs/copies the binary to a common directory (such as ~/bin).
I tried looking at the attributes of the and elenents as supplied by intellisense, but nothing seemed to jump out at me. I did some searching on the MSDN website, and there wasn't anything obvious there either.
My first answer wasn't as reliable as I'd like. "Ren" could error out in a few build scenarios which are not terribly unlikely. So the following is a bullet-proof fix.
<?xml version="1.0" encoding="utf-8"?>
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<AssemblyName>Foo</AssemblyName>
</PropertyGroup>
<ItemGroup>
<Content Include="LICENSE" CopyToOutputDirectory="Always" />
</ItemGroup>
<Target Name="RmLicense" AfterTargets="Clean" Condition=" '$(OutDir)' != '' ">
<Delete ContinueOnError="false"
Files="$(OutDir)\$(AssemblyName).License.txt"
/>
</Target>
<Target Name="MvLicense" AfterTargets="Build" Condition=" '$(OutDir)' != '' ">
<Move ContinueOnError="false"
SourceFiles="$(OutDir)\LICENSE"
DestinationFiles="$(OutDir)\$(AssemblyName).License.txt"
/>
</Target>
</Project>
There are two build tasks, one which executes after a Clean operation, and the other after a Build operation. During the clean operation the renamed output file (if present) is deleted. It is during the build operation that we rename the output file. Note there is a condition. I don't fully understand why, but during the build process there is a time when the $(OutDir) is empty, and no such file will be found. Now we can't just blindly ignore errors (ContinueOnError="true") because during normal operation we want to know if there is a problem here; a missing file or inability to rename the file is an exceptional condition which should correctly break the build. So we skip the operation in the event the $(OutDir) is empty but otherwise perform our work.
I've tried this in multiple projects and it works just fine, so I'm very happy with this. Many thanks to @JonathanDodds for pointing me in the correct direction.