Our build process updates the forth digit (buildnumber or revision) of the version number on every build.
I'm using the following code to try and get the version so that it can be displayed on the splash screen and about page.
var version = Assembly.GetEntryAssembly().GetName().Version;
var programName = "Version: " + version;
How come the 4th digit in the version number is always zero, and what can I change to get it to property reflect the build number?
Any assembly has two metadatas: the assembly version and the file version. The assembly version I don't know exactly how to take it. It seems that there is an AssemblyVersionAttribute but when I try to search for it, a null reference is returned.
But the File version you can take using this code:
public static Version GetAssemblyVersion (Assembly asm)
{
var attribute = Attribute.GetCustomAttribute(asm, typeof(AssemblyFileVersionAttribute), true) as AssemblyFileVersionAttribute;
return new Version(attribute.Version);
}
Generally, I use to synchronize so that file version = assembly version every time so I can grab assembly version using this code. Third party libraries, from my experience I can tell that are following this pattern also.
Related
I am working on desktop application. I have create a setup.
Ex. My Application. Version is 1.0.0.
I want to get the current version of my desktop application which is 1.0.0. I have tried by using Application.ProductVersion but it provides the version of my controls. (I am using DevExpress Control15.2.7, so it provides the current version as 15.2.7).
How can I get the current version of the installed application? I want to compare it to the installed version to provide a "New Version Available" functionality for my product.
The info you are looking for is in AssemblyInfo.cs.
To access the info written in there at runtime you can use the System.Reflection.Assembly.
Use System.Reflection.Assembly.GetExecutingAssembly() to get the assembly (that this line of code is in) or use System.Reflection.Assembly.GetEntryAssembly() to get the assembly your project started with (most likely this is your app).
In multi-project solutions this is something to keep in mind!
string version = Assembly.GetExecutingAssembly().GetName().Version.ToString()
// returns 1.0.0.0
Corresponding AssemblyInfo.cs:
Corresponding EXE-properties:
This may be important when working with InstallShield (see comments) !
System.Reflection.Assembly executingAssembly = System.Reflection.Assembly.GetExecutingAssembly();
var fieVersionInfo = FileVersionInfo.GetVersionInfo(executingAssembly .Location);
var version = fieVersionInfo.FileVersion;
Another approach, which is basically the same as the accepted answer, is:
Version appVersion = Assembly.GetExecutingAssembly().GetName().Version;
versionLabel.Text = "v" + appVersion.Major + "." + appVersion.Minor + "." + appVersion.Build + ".";
Get the version of a specific assembly:
private const string AssemblyName = "MyAssembly"; // Name of your assembly
public Version GetVersion()
{
// Get all the assemblies currently loaded in the application domain.
Assembly[] assemblies = Thread.GetDomain().GetAssemblies();
for (int i = 0; i < assemblies.Length; i++)
{
if (string.Compare(assemblies[i].GetName().Name, AssemblyName) == 0)
{
return assemblies[i].GetName().Version;
}
}
return Assembly.GetExecutingAssembly().GetName().Version; // return current version assembly or return null;
}
I have a program that I have written and am trying to create an about box for. I recently updated my program's product version to 1.00.0003, and I want this to be reflected in the about window.
The default setup of the aboutBox shows a value of 1.0.0.0, which is the assembly version, not the product version. I have since been scouring the Internet to find how to get the product version to be shown. I have tried all of these:
{
Assembly assembly = Assembly.GetExecutingAssembly();
FileVersionInfo fileVersionInfo = FileVersionInfo.GetVersionInfo(assembly.Location);
string version = fileVersionInfo.ProductVersion;
Debug.WriteLine(version);
Debug.WriteLine(assembly.GetName().Version);
string v = VersionNumber;
Debug.WriteLine(v);
Debug.WriteLine( fileVersionInfo.FileVersion);
Debug.WriteLine(Application.ProductVersion);
Debug.WriteLine(AssemblyProductVersion);
Assembly assembly2 = Assembly.GetEntryAssembly();
FileVersionInfo fileVersionInfo2 = FileVersionInfo.GetVersionInfo(assembly.Location);
string version2 = fileVersionInfo2.ProductVersion;
Debug.WriteLine(version2);
Debug.WriteLine(assembly2.GetName().Version);
return version;
}
private string _ourVersion = "Version: v";
private string VersionNumber
{
get
{
System.Reflection.Assembly _assemblyInfo =
System.Reflection.Assembly.GetExecutingAssembly();
if (System.Deployment.Application.ApplicationDeployment.IsNetworkDeployed)
_ourVersion += ApplicationDeployment.CurrentDeployment.CurrentVersion.ToString();
else
{
if (_assemblyInfo != null)
_ourVersion += _assemblyInfo.GetName().Version.ToString();
}
return _ourVersion;
}
}
private static string AssemblyProductVersion
{
get
{
object[] attributes = Assembly.GetExecutingAssembly()
.GetCustomAttributes(typeof(AssemblyInformationalVersionAttribute), false);
return attributes.Length == 0 ?
"" :
((AssemblyInformationalVersionAttribute)attributes[0]).InformationalVersion;
}
}
Every single one of these returns 1.0.0.0 (yes, I did look for their output in the console, not what was actually displayed), instead 1.00.0003 like I need. The product version is set in the General Information tab of the InstallShield setup. When it is installed, going to Programs and Features shows a Product Version of 1.00.0003, so I cannot figure out why this is so hard to programmatically retrieve this value. Any ideas?
Your product version should match the assembly version - have a look at How to make Product Version property match executable's version number automatically
The version 1.00.0003 you want to retrieve is the version of the installer of your product. To get this version programmatically you need to inspect the installer (MSI file), not the installed files. I'm not sure that is what you want to do but there is a answer to the question Checking ProductVersion of an MSI programatically that explains how to do that.
If you want your executable files to contain the same version number you need to store the version number in some way either using a .NET attribute like AssemblyFileVersion or a Windows VERSIONINFO resource.
InstallShield allows you to specify the product version on the command line. This allows you to store your product version in a single file and then use that as the source of both the product version embedded in your installer as well as AssemblyFileVersion of your assemblies.
If only the installer knows about this version information, the only place you could retrieve it from would be the registry.
Uninstall Registry Key:
The following installer properties give the values written under the registry key:
VersionMinor Derived from ProductVersion property
VersionMajor Derived from ProductVersion property
Version Derived from ProductVersion property
But I'd go with #devdigital's (implied) suggestion - you ought to have one of the assembly versions actually matching your installer version.
Simple question... is there a way to change the Assembly Version of a compiled .NET assembly?
I'd actually be fine with a way to change the Assembly File Version.
You can use ILMerge:
ILMerge.exe Foo.dll /ver:1.2.3.4 /out:Foo2.dll
A valid reason to do this is to increment the assembly version in a build in you find breaking changes (using NDepend for example). That way if there are no breaking changes the assembly version stays the same, and you can patch released builds easily.
We always increment the file version, and that reflects the build number.
Old topic but here are my 5 dimes...
Disassemble
ildasm my.exe /output:my.il /metadata
Edit my.il to change version information.
There are several places to look into:
major:minor:revision:build - usually one occurrence
major.minor.revision.build - several occurrences. The string is found in the comment section after the actual line. The version is a hexadecimal value in a byte array. Example:
.custom instance void [mscorlib]System.Reflection.AssemblyFileVersionAttribute::.ctor(string) = ( 01 00 07 35 2E 31 2E 33 2E 30 00 00 ) // ...5.1.3.0..
Edit my.res to change version information.
Double click and edit with visual studio. Pretty straight forward procedure.
Assemble
ilasm my.il /res:my.res
Why do you want to do this? If it's so that another application can use it, you might want to look into assembly binding redirection instead.
It sounds like your process is heavy because you have to update multiple AssemblyInfo files. Have you considered sharing the same AssemblyInfo file between projects?
Derik Whittaker gives a good example on how to do this.
Once you have a single file, you could then go the extra distance by having a build process update your single AssemblyInfo version using MSBuild or NAnt.
If you have formal testing and source control, the process becomes fairly straightforward. It starts with an understanding of who can change the diferent number segments of the version, and when. .net assemblies have 4 number segments (i.e. 1.0.0.1).
The first segment contains the Major Version number. This is set by upper management and indicates a major change in the UI or in the platform of the app. This should always be same number between the assembly version and the file version.
The second segment contains the Minor Version number, also known as the Feature Release number. This is set by Project Management and indicates that new features have been added to the app. This should always be same number between the assembly version and the file version.
The third segment contains the Build number. This is set by the testing group and indicates that the app is ready to be deployed. It is changed before bug fixes are released. When releasing a new build, testing resets the fourth segment to 0. This can be the same number between the assembly version and the file version, but is usually left at 0 for the assembly version to simplify patching existing deployments.
The fourth segment contains the Revision number. This set by the development group whenever they check new code into source control. This number would be included in the file version of the compiled DLL, but not in the assembly version.
I have found that this helps deployers, testers and developers keep track of the latest versions without stepping on each others toes. Unfortunatley, I have also worked with companies that used a static versioning system so that nobody really knew what the latest, best assembly was.
VerPatch, as referenced in this answer, is simple and effective.
Its strange folks have missed Resource Hacker. It is specially made for hacking file resources. So it will also help you edit assembly information including File Version.
using System;
using System.Windows.Forms;
using System.Diagnostics;
public class rh
{
public static void Main()
{
Assembly_Changer("file_path.exe");
}
private static string rc()
{
string FileVersion = "6,8,0,1";
return "1 VERSIONINFO"
+ "\n FILEVERSION " + FileVersion
+ "\n PRODUCTVERSION 0,0,0,0"
+ "\n FILEOS 0x4"
+ "\n FILETYPE 0x1"
+ "\n {BLOCK \"StringFileInfo\"{BLOCK \"000004b0\"{}}BLOCK \"VarFileInfo\"{VALUE \"Translation\", 0x0000 0x04B0}}";
}
public static void Assembly_Changer(string exe)
{
System.IO.File.WriteAllText("details.rc", rc());
process("reshacker.exe", "-open details.rc -save resources.res -action compile -log NUL");
process("reshacker.exe", "-open \"" + exe + "\" -resource resources.res -save \"" + exe + "\" -action addoverwrite -mask \"Version info\"");
}
public static bool process(string filename, string args)
{
using (Process process = new Process())
{
process.StartInfo.FileName = filename;
process.StartInfo.Arguments = args;
process.StartInfo.WindowStyle = ProcessWindowStyle.Hidden;
process.Start();
process.WaitForExit();
}
return true;
}
}
Application.ProductVersion is not showing the incremental version. can anybody help me how to perform this, using C# ?
You can have build and revision incremented for you but not major and minor.
Simply substitute
[assembly: AssemblyVersion("1.0.0.0")]
with
[assembly: AssemblyVersion("1.0.*")]
in the AssemblyInfo.cs
Have you tried grabbing the Assembly's version?
System.Reflection.Assembly.GetExecutingAssembly().GetName().Version;
Perhaps this is what you are looking for.
Also check out this other SO post - I think this is what you are looking for.
Automatically update version number
Below is a second link to a .Net add-in that automatically increments the:
Major
Minor
Build
Revision
http://testdox.wordpress.com/versionupdater/
I have found that it works well to simply display the date of the last build using the following wherever a product version is needed:
System.IO.File.GetLastWriteTime(System.Reflection.Assembly.GetExecutingAssembly().Location).ToString("yyyy.MM.dd.HHMM")
Rather than attempting to get the version from something like the following:
System.Reflection.Assembly assembly = System.Reflection.Assembly.GetExecutingAssembly();
object[] attributes = assembly.GetCustomAttributes(typeof(System.Reflection.AssemblyFileVersionAttribute), false);
object attribute = null;
if (attributes.Length > 0)
{
attribute = attributes[0] as System.Reflection.AssemblyFileVersionAttribute;
}
I am trying to get the file version using C#:
string file = #"C:\somefile.dll";
Console.WriteLine(FileVersionInfo.GetVersionInfo(file).FileVersion);
For most files this is fine, however for some i receive results that are different than the ones presented in the Windows file explorer.
See the attached image: the file version presented in windows is "0.0.0.0", however the one i get using FileVersion property is "000.000.000.000".
I've tried using different versions of the .NET (2, 3.5, 4) which give the same results.
Anyone else experienced this issue?
Thanks
Lior
It seems Windows Explorer are stripping leading 0s of the version parts.
Try creating an assembly with FileVersion 001.001.001.001, it will show as 1.1.1.1 in explorer. But your code would return the actual value (001.001.001.001).
EDIT:
Explorer will return 001.001.001.001 as ProductVersion, but only if AssemblyInformationalVersion isn't set, in which case it would return that as ProductVersion.
The reason is, in WIN32 API (and the file metadata), product versions are defined as string but file versions are defined as integer while in .NET, all of them are defined as integer.
If you use reflector and inspect FileVersionInfo class, you can see that they are loaded differently:
this.productVersion = GetFileVersionString(memIntPtr, string.Format(CultureInfo.InvariantCulture, format, new object[] { codepage, "ProductVersion" }))
But:
this.fileMajor = HIWORD(fixedFileInfo.dwFileVersionMS);
this.fileMinor = LOWORD(fixedFileInfo.dwFileVersionMS);
this.fileBuild = HIWORD(fixedFileInfo.dwFileVersionLS);
this.filePrivate = LOWORD(fixedFileInfo.dwFileVersionLS);