如何有一个自动递增版本号(Visual Studio)?

这个问题在这里已经有了答案:

  • 使用Visual Studio时是否可以自动增加文件构建版本? 23个答案

  • 如果将AssemblyInfo类添加到项目中,并将AssemblyVersion属性修改为以星号结尾,例如:

    [assembly: AssemblyVersion("2.10.*")]
    

    视觉工作室会根据这些规则为你增加最后的数字(感谢galets,我完全错了!)

    要在代码中引用此版本,可以将其显示给用户,请使用反射。 例如,

    Version version = System.Reflection.Assembly.GetExecutingAssembly().GetName().Version;
    DateTime buildDate = new DateTime(2000, 1, 1)
                            .AddDays(version.Build).AddSeconds(version.Revision * 2);
    string displayableVersion = $"{version} ({buildDate})";
    

    你应该知道两个重要的陷阱

    来自@ ashes999:

    值得注意的是,如果AssemblyVersionAssemblyFileVersion都被指定了,那么你的.exe文件中就不会看到这个。

    来自@ BrainSlugs83:

    只将第四个数字设置为*可能很糟糕,因为版本不会始终增加。 第三个数字是自2000年以来的天数,第四个数字是自午夜以来的秒数(除以2)[IT并非随机]。 因此,如果您在一天的某一天晚些时候以及第二天的某天早些时候构建解决方案,那么稍后的版本将具有较早的版本号。 我建议您始终使用XY*代替XYZ*因为您的版本号总是会以这种方式增加。


    您可以使用Visual Studio中的T4模板机制从简单的文本文件生成所需的源代码:

    我想为某些.NET项目配置版本信息生成。 自从我调查可用选项已经很长时间了,所以我搜索了各地希望找到一些简单的方法来做到这一点。 我发现的结果并不令人鼓舞:人们编写Visual Studio加载项和自定义的MsBuild任务只是为了获得一个整数(好的,也许是两个)。 这对于一个小型的个人项目来说感觉过分了。

    灵感来自StackOverflow讨论之一,有人建议T4模板可以完成这项工作。 当然他们可以。 该解决方案需要最小的努力,并且不需要Visual Studio或构建流程定制。 这里应该做什么:

  • 创建一个扩展名为“.tt”的文件,并在那里放置将生成AssemblyVersion和AssemblyFileVersion属性的T4模板:
  • <#@ template language="C#" #>
    // 
    // This code was generated by a tool. Any changes made manually will be lost
    // the next time this code is regenerated.
    // 
    
    using System.Reflection;
    
    [assembly: AssemblyVersion("1.0.1.<#= this.RevisionNumber #>")]
    [assembly: AssemblyFileVersion("1.0.1.<#= this.RevisionNumber #>")]
    <#+
        int RevisionNumber = (int)(DateTime.UtcNow - new DateTime(2010,1,1)).TotalDays;
    #>
    

    你将不得不决定版本号生成算法。 对于我来说,自动生成一个修订版号就足够了,该修订版号设置为自2010年1月1日以来的天数。正如您所看到的,版本生成规则是用纯C#编写的,因此您可以根据需要轻松调整它。

  • 上面的文件应该放在其中一个项目中。 我使用这个单一文件创建了一个新项目,使版本管理技术变得清晰。 当我构建这个项目时(实际上我甚至不需要构建它:保存文件足以触发Visual Studio操作),将生成以下C#代码:
  • // 
    // This code was generated by a tool. Any changes made manually will be lost
    // the next time this code is regenerated.
    // 
    
    using System.Reflection;
    
    [assembly: AssemblyVersion("1.0.1.113")]
    [assembly: AssemblyFileVersion("1.0.1.113")]
    

    是的,今天是2010年1月1日以来的113天。明天版本号会改变。

  • 下一步是从应该共享相同自动生成版本信息的所有项目中的AssemblyInfo.cs文件中删除AssemblyVersion和AssemblyFileVersion属性。 相反,为每个项目选择“添加现有项目”,使用T4模板文件导航到该文件夹​​,选择相应的“.cs”文件并将其添加为链接。 这将做到!
  • 我喜欢这种方法是轻量级的(没有自定义的MsBuild任务),并且自动生成的版本信息不会添加到源代码管理中。 当然,使用C#进行版本生成算法会打开任何复杂的算法。


    这是我对T4建议的实现......每次构建项目时都会增加内部版本号,而不管选择的配置如何(即Debug | Release),并且每次执行Release版本时都会增加版本号。 您可以通过应用程序➤程序集信息...继续更新主版本号和次版本号

    为了更详细地解释,这将读取现有的AssemblyInfo.cs文件,并使用正则表达式来查找AssemblyVersion信息,然后根据TextTransform.exe输入增加修订版本和内部版本号。

  • 删除您现有的AssemblyInfo.cs文件。
  • 在它的位置创建一个AssemblyInfo.tt文件。 在保存T4文件后,Visual Studio应创建AssemblyInfo.cs并将其与T4文件分组。

    <#@ template debug="true" hostspecific="true" language="C#" #>
    <#@ output extension=".cs" #>
    <#@ import namespace="System.IO" #>
    <#@ import namespace="System.Text.RegularExpressions" #>
    <#
        string output = File.ReadAllText(this.Host.ResolvePath("AssemblyInfo.cs"));
        Regex pattern = new Regex("AssemblyVersion("(?<major>d+).(?<minor>d+).(?<revision>d+).(?<build>d+)")");
        MatchCollection matches = pattern.Matches(output);
        if( matches.Count == 1 )
        {
            major = Convert.ToInt32(matches[0].Groups["major"].Value);
            minor = Convert.ToInt32(matches[0].Groups["minor"].Value);
            build = Convert.ToInt32(matches[0].Groups["build"].Value) + 1;
            revision = Convert.ToInt32(matches[0].Groups["revision"].Value);
            if( this.Host.ResolveParameterValue("-","-","BuildConfiguration") == "Release" )
                revision++;
        }
    #>
    
    using System.Reflection;
    using System.Runtime.CompilerServices;
    using System.Runtime.InteropServices;
    using System.Resources;
    
    // General Information
    [assembly: AssemblyTitle("Insert title here")]
    [assembly: AssemblyDescription("Insert description here")]
    [assembly: AssemblyConfiguration("")]
    [assembly: AssemblyCompany("Insert company here")]
    [assembly: AssemblyProduct("Insert product here")]
    [assembly: AssemblyCopyright("Insert copyright here")]
    [assembly: AssemblyTrademark("Insert trademark here")]
    [assembly: AssemblyCulture("")]
    
    // Version informationr(
    [assembly: AssemblyVersion("<#= this.major #>.<#= this.minor #>.<#= this.revision #>.<#= this.build #>")]
    [assembly: AssemblyFileVersion("<#= this.major #>.<#= this.minor #>.<#= this.revision #>.<#= this.build #>")]
    [assembly: NeutralResourcesLanguageAttribute( "en-US" )]
    
    <#+
        int major = 1;
        int minor = 0;
        int revision = 0;
        int build = 0;
    #>
    
  • 将此添加到您的预生成事件中:

    "%CommonProgramFiles(x86)%microsoft sharedTextTemplating$(VisualStudioVersion)TextTransform.exe" -a !!BuildConfiguration!$(Configuration) "$(ProjectDir)PropertiesAssemblyInfo.tt"
    
  • 链接地址: http://www.djcxy.com/p/50667.html

    上一篇: How to have an auto incrementing version number (Visual Studio)?

    下一篇: How can I force clients to refresh JavaScript files?