Add Build Time to your C# Assembly

Having the Assembly version is great. This give us insights of wich version is running. Have the build time can also useful. Specially when we're troubleshooting our application and we're not sure of which version is running.

For instance besides having only the assembly version we can have the version + time of the build. Such as version 1.1.0 build at 2021-04-21 23:11:00.

Prelude

Often in our Developer, DevOps or infrastructure life we find ourselves wondering:

  • Is this the right assembly?
  • Why my changes are not there? What happened?
  • WHich version is this? Is this the latest version?
  • Oh man, why is this not working? Oh my gosh. I hate this... hahhahaha

This happens especially when we don't have control over the deployment and it's published by a third-party professional.

By default, DotNet doesn't provide us that. Let's get started!
> This works in .Net Core 3.1 and .NET 5.

To make this happen we're going to tell .NET compiler while building the code to also write in the assembly's SourceRevisionId tag the System.DateTime.Now or System.DateTime.UtcNow.

Adding Build Time to Our Assembly

Open your csproj file and add the tag SourceRevisionId with the following content.

<Project Sdk="Microsoft.NET.Sdk">
  <!--existing entries-->
  <PropertyGroup>
    <SourceRevisionId>build$([System.DateTime]::UtcNow.ToString("yyyy-MM-ddTHH:mm:ss:fffZ"))</SourceRevisionId>
  </PropertyGroup>
</Project>
App.csproj

It works for Console App, Windows Forms, WPF, Web App and Xamarin.

💡
What about others? I have no clue. 

To get the written date using C# create the method GetLinkerTime() as described next.

using System;
using System.Globalization;
using System.Reflection;

const string BuildVersionMetadataPrefix = "+build";
const string dateFormat = "yyyy-MM-ddTHH:mm:ss:fffZ";

public static DateTime GetLinkerTime(Assembly assembly)
{
  var attribute = assembly
    .GetCustomAttribute<AssemblyInformationalVersionAttribute>();
  
  if (attribute?.InformationalVersion != null)
  {
    var value = attribute.InformationalVersion;
    var index = value.IndexOf(BuildVersionMetadataPrefix);
    if (index > 0)
    {
      value = value[(index + BuildVersionMetadataPrefix.Length)..];
      
      return DateTime.ParseExact(
      	value, 
        dateFormat, 
        CultureInfo.InvariantCulture);
    }
  }
  return default;
}
Method GetLinkerTime

Full Application - Sample Console Application

using System.Globalization;
using System.Reflection;


Console.WriteLine("Hello World!");

var buildTime = GetLinkerTime(Assembly.GetEntryAssembly());
Console.WriteLine($"Build time at {buildTime}");

Console.WriteLine("Write any key to close");
Console.ReadKey();


public static DateTime GetLinkerTime(Assembly assembly)
{
  const string BuildVersionMetadataPrefix = "+build";
  const string dateFormat = "yyyy-MM-ddTHH:mm:ss:fffZ";

  var attribute = assembly
    .GetCustomAttribute<AssemblyInformationalVersionAttribute>();
  
  if (attribute?.InformationalVersion != null)
  {
    var value = attribute.InformationalVersion;
    var index = value.IndexOf(BuildVersionMetadataPrefix);
    if (index > 0)
    {
      value = value[(index + BuildVersionMetadataPrefix.Length)..];
      
      return DateTime.ParseExact(
      	value, 
        dateFormat, 
        CultureInfo.InvariantCulture);
    }
  }
  return default;
}
Sample Program.cs

Sample output.

sample output

Source Code

ricardodemauro/buildTimeConsoleApp-tutorial
Contribute to ricardodemauro/buildTimeConsoleApp-tutorial development by creating an account on GitHub.

How was the tutorial?

Love Discord?