AZ-400: Designing and Implementing Microsoft DevOps Solutions

Design and Implement a Package Management Strategy

Versioning Strategies Semantic Versioning Date Based Versioning

In this article, we explore two essential versioning strategies—semantic versioning and date-based versioning—using a .NET console application as our example. Versioning is crucial for managing software releases, helping you communicate the significance of changes such as bug fixes, new features, or breaking updates.

Setting Up the .NET Console Application

Begin by creating a new .NET console application. In this example, we manually set a version number based on the chosen versioning strategy. Initially, the version is set to 0.0.0:

// See https://aka.ms/new-console-template for more information
Console.WriteLine("Hello, World!");

Later, update the application code to include a version string:

using System;

namespace VersioningDemo
{
    // The version number will be manually set based on the versioning strategy
    static string version = "v0.0.0";

    static void Main(string[] args)
    {
        Console.WriteLine("Hello, Azure DevOps!");
        Console.WriteLine($"Version: {version}");
    }
}

Understanding Semantic Versioning

Semantic versioning follows the MAJOR.MINOR.PATCH format (e.g., 1.2.3). Each segment indicates a specific type of change:

  • Major: Indicates breaking changes or significant software updates. Increment the major version only when making changes that are not backward compatible.
  • Minor: Represents new features or additions that maintain backward compatibility. Existing functionality remains unaffected even if new features are added.
  • Patch: Used for bug fixes or minor updates that do not introduce any breaking changes.

For example, updating the version from 0.0.0 to 1.2.3 could produce the following output:

C:\Users\jeremy\Projects\VersioningDemo>dotnet run
Hello, Azure DevOps!
Version: v1.2.3

After a bug fix, the version might update to 1.2.4. Conversely, non-breaking enhancements—such as updates to a menu system or API improvements—would prompt the version to change to 1.3.0:

using System;

namespace VersioningDemo
{
    // The version number is updated to reflect new features while remaining backward compatible.
    static string version = "v1.3.0";

    static void Main(string[] args)
    {
        Console.WriteLine("Hello, Azure DevOps!");
        Console.WriteLine($"Version: {version}");
    }
}

When major changes occur, such as a complete system overhaul or an upgrade to .NET Standard that is not backward compatible, increase the major version to 2.0.0:

using System;

namespace VersioningDemo
{
    class Program
    {
        // The version is updated to indicate a backward incompatible release.
        static string version = "v2.0.0";

        static void Main(string[] args)
        {
            Console.WriteLine("Hello, Azure DevOps!");
            Console.WriteLine($"Version: {version}");
        }
    }
}

Any application or API integration that depends on your software can quickly assess the impact of changes by comparing version numbers. A change in the major version clearly signals that breaking changes have occurred.

Note

Using semantic versioning helps consumers of your API or software understand the scale of changes with a simple glance at the version number.

Introducing Date-Based Versioning

Date-based versioning incorporates the release date directly into the version number. This method is particularly effective in environments with frequent releases, such as continuous integration and deployment scenarios. Instead of the semantic format, the version number includes the year, month, day, and a build number—for example, "2024.10.03.01".

Below is an example demonstrating date-based versioning in the .NET console application:

using System;

namespace VersioningDemo
{
    class Program
    {
        // The version number is based on the release date with an appended build number.
        static string version = "2024.10.03.01";

        static void Main(string[] args)
        {
            Console.WriteLine("Hello, Azure DevOps!");
            Console.WriteLine($"Version: {version}");
        }
    }
}

In this format:

  • "2024.10.03" represents the release date (year, month, day).
  • "01" is the build number, which increments with subsequent builds on the same day (for instance, "2024.10.03.02" for the second build).

Date-based versioning shifts the focus from the type of changes to the timeline of releases, providing precise information on when each build was produced.

When to Use Each Versioning Strategy

Versioning StrategyUse CaseExample Version
Semantic VersioningTraditional software projects with clear distinctions for breaking changes, new features, and fixes.v1.2.3, v2.0.0
Date-Based VersioningProjects with frequent deployments or continuous delivery processes where release dates are more informative.2024.10.03.01
  • Semantic Versioning: Choose this strategy for well-defined, milestone-based releases. It clearly indicates whether changes are major, minor, or patches.
  • Date-Based Versioning: Best for agile environments and continuous deployment pipelines where tracking the exact release date and build number is critical.

Tip

Selecting the right versioning strategy can enhance collaboration between your development teams and external integrators by providing clear insight into the release changes. Consider the nature of your software releases when deciding between semantic and date-based versioning.

By understanding and correctly implementing these versioning strategies, you improve software maintenance and create clear communication channels with your users and integration partners.

Enjoy building and versioning your software!

Watch Video

Watch video content

Previous
Implementing package feeds