我试图建立在这个问题的基础上:
Reading a single value from a file in MSBuild
我的目标是让一个地方放置在多个项目中使用的版本号,并且我还希望其中一个项目的DLL文件名中有一部分版本号。
基于上面的问题,我已经得到了第一部分,但我对第二部分遇到了困难,并希望得到一些指导。
在我的解决方案中,我设置了一个名为Version.txt的纯文本文件,其中仅包含我的完整版本号:
1.1.0.0
在我的两个项目中,我打开了他们的AssemblyInfo.cs文件并删除了AssemblyVersion和AssemblyFileVersion项,然后修改了两个项目以在单独的文件中生成它们,如上面的问题所述。
<ItemGroup>
<VersionFile Include="..\Version.txt" />
</ItemGroup>
<Target Name="BeforeBuild">
<ReadLinesFromFile File="@(VersionFile)">
<Output TaskParameter="Lines" PropertyName="VersionNumber" />
</ReadLinesFromFile>
<Delete Files="Properties\Version.cs" />
<WriteLinesToFile File="Properties\Version.cs" Lines="using System.Reflection%3B

[assembly: AssemblyVersion("$(VersionNumber)")]
[assembly: AssemblyFileVersion("$(VersionNumber)")]" />
</Target>
现在,当我构建时,我为每个项目获取一个生成的Properties \ Version.cs文件,该文件用于构建EXE / DLL并显示为&#34; 1.1.0.0&#34;在他们的文件属性中。这正是我想要的。
对于DLL,我想命名程序集&#34; filename.v1.1.dll&#34;,其中&#34; 1.1&#34;来自上面Version.txt中的前两个组件。只要我能得到完整的&#34; 1.1.0.0&#34;我就可以灵活地使用Version.txt的格式。在EXE / DLL属性和&#34; 1.1&#34;在DLL文件名中。
为了尝试这一点,我修改了DLL的csproj文件:
<RootNamespace>dllfile</RootNamespace>
<AssemblyName>dllfile.v$(VersionNumber)</AssemblyName>
当然,这会在文件名中插入完整版本号,这是我不想要的。
有没有人有关于如何进行的任何提示?
感谢。
编辑:我已经能够通过将以下内容添加到我的.csproj BeforeBuild目标中来提取版本号的主要/次要组件:
<ReadLinesFromFile File="@(VersionFile)">
<Output TaskParameter="Lines" PropertyName="VersionNumber" />
</ReadLinesFromFile>
<PropertyGroup>
<VersionNumberFirstDotIndex>$(VersionNumber.IndexOf('.'))</VersionNumberFirstDotIndex>
<VersionNumberMajorStart>0</VersionNumberMajorStart>
<VersionNumberMajorLen>$(VersionNumberFirstDotIndex)</VersionNumberMajorLen>
<VersionNumberMinorStart>$([MsBuild]::Add(1, $(VersionNumberFirstDotIndex)))</VersionNumberMinorStart>
<VersionNumberSecondDotIndex>$(VersionNumber.IndexOf('.', $(VersionNumberMinorStart)))</VersionNumberSecondDotIndex>
<VersionNumberMinorLen>$([MSBuild]::Subtract($([MSBuild]::Subtract($(VersionNumberSecondDotIndex), $(VersionNumberFirstDotIndex))), 1))</VersionNumberMinorLen>
<VersionNumberMajor>$(VersionNumber.Substring($(VersionNumberMajorStart), $(VersionNumberMajorLen)))</VersionNumberMajor>
<VersionNumberMinor>$(VersionNumber.Substring($(VersionNumberMinorStart), $(VersionNumberMinorLen)))</VersionNumberMinor>
<VersionNumberShort>$(VersionNumberMajor).$(VersionNumberMinor)</VersionNumberShort>
</PropertyGroup>
<Message Text="DEBUG1 VersionNumberFull=$(VersionNumber)" Importance="High" />
<Message Text="DEBUG2 VersionNumberAbbrev=$(VersionNumberShort)" Importance="High" />
<Delete Files="Properties\Version.cs" />
<WriteLinesToFile File="Properties\Version.cs" Lines="using System.Reflection%3B

[assembly: AssemblyVersion("$(VersionNumber)")]
[assembly: AssemblyFileVersion("$(VersionNumber)")]" />
我现在唯一缺少的是如何将此VersionNumberShort转换为DLL文件名。除非有人有更好的想法,否则我可以接受彼得的建议并使用移动任务:
<Target Name="AfterBuild">
<Move SourceFiles="$(OutputPath)$(AssemblyName).pdb" DestinationFiles="$(OutputPath)$(AssemblyName).v$(VersionNumberShort).pdb" />
<Move SourceFiles="$(OutputPath)$(AssemblyName).dll" DestinationFiles="$(OutputPath)$(AssemblyName).v$(VersionNumberShort).dll" />
</Target>
<Target Name="AfterClean" DependsOnTargets="Common">
<Delete Files="$(OutputPath)$(AssemblyName).v$(VersionNumberShort).pdb" ContinueOnError="true" />
<Delete Files="$(OutputPath)$(AssemblyName).v$(VersionNumberShort).dll" ContinueOnError="true" />
</Target>
由于我需要与以前相同的属性定义,因此我将上面的代码段移到了#34; Common&#34;目标并在此处显示的构建和清理任务中引用它。
彼得 - 如果你想将评论作为答案移动,我会接受它。谢谢!
编辑:根据jdlugosz的回答,我尝试在我的任务中设置AssemblyName。不幸的是,根据顶部列出的原始示例,这似乎没有任何效果:
<Target Name="BeforeBuild">
...
<WriteLinesToFile ... />
<PropertyGroup>
<AssemblyName>dllfile.v$(VersionNumber)</AssemblyName>
</PropertyGroup>
</Target>
我尝试使用Visual Studio Developer命令提示符中的MSBuild运行它:
msbuild /target:clean projfile.csproj
msbuild /verbosity:diag projfile.csproj > out.txt
在此之前,我将我的csproj文件顶部重命名为&#34;重新定义&#34;使其易于搜索(例如&#34; dllfileoriginal&#34; vs.&#34; dllfilemodified&#34;)。
查看输出日志,我找不到对修改后文本的任何引用;它在输出中到处都是dllfileoriginal。
在WriteLinesToFile任务之后,看起来构建了以下目标:
这些内容中没有任何DLL名称的引用。
看起来目前仍是我最好的选择。
答案 0 :(得分:0)
目标名称显示在IDE属性页编辑器的“配置属性”选项卡下的“常规”页面上。我没有一个方便自己为你查找名称,但你可以通过将IDE中的空白更改为XXXX并保存来实现。然后在版本控制提交审阅者中查看diff并查看该属性的名称。在这种情况下,请编辑该行以将XXXX更改为$(OutputPath)$(AssemblyName).v$(VersionNumberShort)
哦,看看FormatVersion
任务,这可能会有所帮助。我认为有一些预制任务可以操纵类似于你所展示的版本程序集。
我正在为版本做的是通过#defines传递作为/D
命令行参数的部分。我猜你在C#中没有这个,但IIRC。
答案 1 :(得分:0)
这对我有用,它解决了在构建时将版本信息字符串附加到文件名的看似简单的问题。
首先,构建后事件:
(右键单击项目 - &gt;属性 - &gt;构建事件 - &gt;编辑后构建...)
$(TargetPath) "version" > $(TargetDir)text.txt
set /p version= <$(TargetDir)text.txt
copy $(TargetPath) $(TargetDir)$(TargetName)_%version%.exe
del $(TargetDir)text.txt
现在,诀窍: 重载sub main以返回版本信息,并在刚刚构建的exe上的post-build事件中调用它。
这是F#中的一个例子:
[<EntryPoint>]
let main argv =
let version = argv.Length = 1 && argv.[0] = "version"
if version then
let version = System.Reflection.Assembly.GetExecutingAssembly().GetName().Version.ToString()
do stdout.WriteLine(version)
do stdout.Flush()
else
try
//...
上面的构建后事件
1)使用“version”arg调用新构建的exe,并将输出写入txt文件
2)将文本文件内容读入本地变量
3)通过添加版本信息
3)复制新建的exe,将版本信息添加到名称
4)清理临时文件
*将“move”更改为“copy”,以便Visual Studio仍可以F5项目