Software version numbers are all over the map. At present, my system reports the following versions of various installed software:
Mayan Apocalypse (96)
7.0 (Build 201104080000)
As you can see, there is no concrete pattern here. The most common theme seems to be:
Not all software is created equal:
We have a wide variety of software from libraries and frameworks, to complex server software to simple mobile applications. Some software is characterized by a high build rate (e.g. few times a day) whereas on the other end of the spectrum, it’s easy to find cases where a release every few months or even years is common practice. Some software is released to the public, other stays in-house. It is hard to define a single universal scheme that works for all kinds of software. So let us divide software into the following three broad categories:
- Libraries and Frameworks
- Public Software
- In-house or Hosted Software
Libraries and Frameworks
For library components and frameworks, which define their own API, Semantic Versioning (SemVer) looks promising. It requires that the software must define a public API to be able to use it. From their webpage:
“A normal version number MUST take the form X.Y.Z where X, Y, and Z are non-negative integers. X is the major version, Y is the minor version, and Z is the patch version. Each element MUST increase numerically by increments of one. For instance: 1.9.0 -> 1.10.0 -> 1.11.0.”
Web based frameworks like Express (for Node.js), Ruby On Rails, can benefit from it.
When it comes to public software, things get complicated. Let’s take a moment to ask yourself why your users would ever use the version information? The only answer that comes to my mind is that’s how they decide if there’s a newer version available for purchase or not. Back in the day when I was using Windows 95 and heard about this fancy new thing called Windows 98, I knew it was time to upgrade.
Here’s the deal: your users don’t really care about cryptic version numbers. The only time detailed version information such as 4.1.2222A would come handy is when the user is experiencing issues and is on the phone, the support guy would want to know exactly what version of the software they are using right down to the build number.
Therefore, it is a good idea for public software to have a dual versioning scheme: The first version is a user-friendly name that is easy to remember and use in casual discussions, e.g. Lion. The second is the detailed version to be used in times of crisis, e.g. 10.7.5 (11G63), such as when browsing the Internet for known vulnerabilities or calling Apple for support.
Microsoft seemed to have invented or at least popularized the dual versioning system with Windows 95. Windows 95, the immensely popular successor of Windows 3.1x, was actually called Windows 4.0. Windows 98 was 4.1. Apple picked this idea up starting from OS X 10.0 and started naming major releases after cats (Cheetah, Jaguar, Panther, to the latest Mountain Lion). You can apply your creative juices when coming up with a user-friendly versioning scheme and even involve the marketing group in the process.
For detailed versioning scheme, I personally prefer <major>.<minor>.<revision>.<build>. You could use <major>.<minor>.<revision>.<date>. For example:
1.0.3 (December 21, 2012)
Embedding the date in the release is actually a very good idea. It conveys time the build was generated. Others prefer appending build Ids generated by build management systems such as SVN, Git or Mercurial. At my work, I use the following rules:
- Major: This is usually done at the end of full release cycle; the resulting product is a major upgrade. All stakeholders (Managers, VPs, Marketing Directors) are informed of the major increment and is usually followed by press releases and marketing.
- Minor: When additional functionality or new features are introduced. Software Development managers or Senior Developers typically approve such increments.
- Revision: Bug fixes, ad-hoc patches, any minor change. Developers increment this number each time they make a minor change or fix a bug.
- Build: This is the only component of the version that is automatically generated. There is a python script that generates this using the Git commit SHA every time the software is built.
This post from Alex Collins explain the rules are incrementing each component:
“You zero digits to the right of any you increment, so if you fix a bug and introduce a new feature after version 5.3.6 then the new version is 5.4.0. Unstated digits are assumed to be zero, so 5.4.0 is the same as 184.108.40.206 and 220.127.116.11.0.0.0.0.0…”
In-house or Hosted Software
For high rate builds using automated systems like Jenkins, it is a good idea to have versions automatically time stamped. Something like <year>.<month>.<day>.<time> is good for providing detailed information to support desk staff and for referencing build information to developers. E.g. 2012.12.29.0059 is the version of build generated on December 29, 2012 at 12:59 a.m.
Whatever you do, please be consistent and stick to the system you pick. Sun Microsystems (acquired by Oracle), confused developers everywhere by changing their versioning scheme along the way.