Semantic versioning for end-user applications
Just one approach…
SemVer (semantic versioning, aka “semver”) is a scheme for determining how to assign a new version number to software to based on the difference between the previous version and the new version. Essentially:
Given a version number MAJOR.MINOR.PATCH, increment the:
- MAJOR version when you make incompatible API changes,
- MINOR version when you add functionality in a backwards-compatible manner, and
-PATCH version when you make backwards-compatible bug fixes.
Semver is most useful when applied to software components, which usually have a well-defined “public API” (application programming interface). The notion of a public API is a core requirement to using semver.
For example, if a command line tool called
edi accepts one argument which must be a number, then it’s public API looks like this:
edi <number>. If in the next version of the tool the API changes to
edi <date>, that would be a breaking change to the public API (because a user who passed a number to
edi would receive an error) and hence would require the MAJOR version number to increment (from
2.0.0 for example).
What is the public API of a web, mobile or desktop application?
To help answer this question, let’s use the Twitter app (with the initial version
1.0.0) as an example. If the Twitter design team add a button to their user interface, have they changed their public API?
From an end-user’s perspective, they see a new feature. And they don’t care about semver or version numbers (unless they see them in the marketing e.g.
iPhone 7 or
PS4-slim). So from an end-user’s perspective, “it just doesn’t matter”… unless something goes wrong. Then it will be the support person who cares about the version number of Twitter that the end-user is trying to use, so that they can troubleshoot the problem. (But that support conversation usually ends with, “Please install the latest version…”, anyway).
Consider now an end-user who writes code to automate the UI (user interface) or perform screen-scraping of data inside the Twitter app. The new button *is* potentially significant and may be a breaking change because the UI is their public API. They would expect to see the new version called
Another kind of UI change could occur in web applications — the code behind the UI may change (e.g. a CSS class or HTML element change), but the UI may look the same. To the end-user who writes code, this could also be a breaking change (depending on how their code interacts with the Twitter App).
In practice though, application-writers do not care about the end-users who write code, as they are a tiny portion of their entire audience, and generally cause more trouble than they’re worth :P
Two, random, internet people who have taken the time to blog about the pros and cons of versioning for applications are Dave Hall and Owen Jacobson. They agree that semver is useful for components, but argue that it isn’t useful for end-user applications for the following reasons:
- End-users don’t have a choice as to which version to run (for web & mobile apps; desktop applications do offer more flexibility)
- End-users don’t know or care which version they’re using
But there is another kind of user who would care about the changes to an application that perhaps has not been considered…
The installer-user is the person who has to install the application. To them, the “public API” of the application is the installation-requirements. But who is the installer-user?
For the Twitter mobile app and desktop app, the installer is (usually) the end-user. The installation-requirements would be a minimum required version of the operating system and an internet connection.
For the Twitter web application, the installer is someone from the DevOps (or Operations) team. They care deeply about the installation-requirements as they need to provision the correct infrastrucure based on these requirements.
Given the importance of the installation-requirements of an application to installer-users, I propose that semver be used to version end-user applications using the installation-requirements as the public API with installer-users as the consumers of this API.
In practice, increment the:
- MAJOR version when you make incompatible API changes (e.g. installer-users have to modify their infrastructure (phone/tablet/PC/web-server/firewall config/etc) in some way),
- MINOR version when you add functionality in a backwards-compatible manner (e.g. passing additional data to an already-provisioned API or adding any end-user functionality that does not affect the installation-requirements), and
- PATCH version when you make backwards-compatible bug fixes (e.g. fixing any end-user bug that does not affect the installation requirements).
By treating the installer-users as the consumers of an end-user application, and the installation-requirements as the public API, I believe that semver does make sense and is valuable as a communications mechanism for end-user applications.