Automating Version Updates in Visual Studio with Build Events

How I automated assembly versioning using a batch script triggered by Visual Studio build events

Posted by Hüseyin Sekmenoğlu on February 08, 2019 Tooling & Productivity

🕰️ Versioning by Date in Our Company

In our company, software versions use dates instead of the common semantic versioning format. Instead of versions like 1.2.3, they used date-based versions like "2018.02.28". This was not strictly semantic versioning but still effective.

I decided to improve this date format to something that looked more like a standard version but still kept the date information. So I rearranged the dots and created versions like "1.80.228". If you look closely, this corresponds to the date "18.02.28". This felt more natural and realistic for versioning.


🛠️ The Challenge of Manual Updates

At first, we updated the version number manually for every build. This quickly became tiresome and error-prone.

To solve this, a colleague and I wrote a batch script that would update the version automatically.


🔄 Integrating the Script as a Pre-Build Event

We configured Visual Studio to call the batch script before each build using the pre-build event command line:

makefileCopyEdit

c:\Pre-Build.bat $(SolutionDir)

This means every time Visual Studio builds the solution, the script runs automatically.


📄 How the Script Works

The script searches all AssemblyInfo.cs files in the project folders. For each file:

  • It checks if the current version string exists in the file.

  • If yes, it skips that file to avoid unnecessary changes.

  • If not, it creates a temporary file excluding old version lines.

  • It appends the new version attributes with the updated version number.

  • It replaces the original AssemblyInfo.cs file with the new one.


📅 Generating the Version Number from Date

The script uses Windows Management Instrumentation (WMIC) to get the current local date parts (year, month and day). It formats them into a version string like 1.80.228.

Here is how it processes:

  • Extracts year, month and day parts.

  • Adjusts for leading zeros.

  • Rearranges parts to fit the 1.80.228 pattern.


📝 The Complete Batch Script

@echo off
setlocal enabledelayedexpansion

if [%1] == [] GOTO :USAGE

chdir /d "%1"

for /f %%x in ('wmic path win32_localtime get /format:list ^| findstr "="') do set %%x
set Month=0%Month%
set Day=0%Day%
set Year=%Year:~-3%
set Month=%Month:~-2%
set Day=%Day:~-2%
set today=%Year%%Month%%Day%

set v1=%today:~0,1%
set v2=%today:~1,2%
set v3=%today:~3,3%

set version=%v1%.%v2%.%v3%

for /F "delims=" %%f in ('dir /s /b Assemblyinfo.cs') do (
    echo > %%f

    pushd %%~dpf

    >nul find "%version%" AssemblyInfo.cs && (
        echo "%version%" was found.
    ) || (
        for /F "usebackq delims=" %%g in ("AssemblyInfo.cs") do (
            set ln=%%g
            set skip=0

            if "!ln:AssemblyVersion=!" NEQ "!ln!" set skip=1
            if "!ln:AssemblyFileVersion=!" NEQ "!ln!" set skip=1
            if "!ln:AssemblyInformationalVersion=!" NEQ "!ln!" set skip=1

            if !skip!==0 echo !ln! >> AssemblyInfo.cs.temp
        )

        echo [assembly: AssemblyVersion^("%version%"^)] >> AssemblyInfo.cs.temp
        echo [assembly: AssemblyFileVersion^("%version%"^)] >> AssemblyInfo.cs.temp
        echo [assembly: AssemblyInformationalVersion^("%version%"^)] >> AssemblyInfo.cs.temp

        move /y AssemblyInfo.cs.temp AssemblyInfo.cs

        popd
    )
)
echo Done!

GOTO:EOF

:USAGE
echo Usage:
echo SetVersion.bat ProjectFolderAddress
echo.

✅ Benefits

  • No more manual version updates.

  • Versions reflect build date in a clear and unique format.

  • The build system only changes files when necessary, preventing unnecessary recompilation.

  • Easy to extend or modify for more complex versioning schemes.