Take the 2-minute tour ×
Programmers Stack Exchange is a question and answer site for professional programmers interested in conceptual questions about software development. It's 100% free, no registration required.

I have a program which is built of 5 major components. I find the standard version numbering too limiting because I would like to see what version each compoment is at.

Has anyone found an easy way to do this other than list each separately?

share|improve this question
1  
Are all components built at the same time? Are they "released" at the same time? –  Anna Lear Aug 28 '11 at 2:11
1  
@Anna Lear: no, the components are built and released at different times. –  John Smith Aug 28 '11 at 3:23
    
If they are released independently I would treat them as separate products, each with their own 'development' version number. If the combination is also sold/released as a single product that can have a 'commercial' version. –  Kwebble Aug 28 '11 at 21:19
    
What is your goal when versioning? What is that version information used for? Bug reporting? checking upgrade compliance? licensing? Answering these questions may answer your root question. –  Alex Feinman Aug 31 '11 at 16:39
add comment

7 Answers

We have this exact same issue with our product, and we decided to do individual version numbers for each component and the product version is only a marketing version which is composed of the various components at a specific revision.

share|improve this answer
    
What would that look like in your version control system? Do you "pin" all sub-projects when you make a major release? –  Robert Harvey Aug 28 '11 at 5:52
    
When we are preparing a major release all components are reviewed and if they have changes then they receive an updated version at that time. The version is tagged in Kiln. –  DaveNay Aug 28 '11 at 14:43
add comment

Versioning is a problem that is separate from component-based application development. Either you want to version each component, or you want to version the whole application.

A good well-known pattern for versioning is from Microsoft:

major version.minor version.build number.revision

For example, you can see the DLL files in .NET platform to have versions like 2.0.3600.1, or something like that.

So, I recommend that you first determine that whether you want to version the whole system or its components. If you want to version the whole system, then after each integration, build the entire project, and increase the build number part. If not, then simply version each component on build.

share|improve this answer
    
I don't agree with your build number strategy. The build number typically changes every time you build the project for a given component, so that isn't going to work. –  Robert Harvey Aug 28 '11 at 5:56
    
@Robert, yeah, the build number becomes a great number soon. That's why some other systems don't include it. You're free to go. But, major version and minor version both exit in almost any versioning system. –  Saeed Neamati Aug 28 '11 at 6:09
add comment

We have a "system release version", which is a standard version number that describes a particular configuration of components, then a separate file lists the individual component versions for that particular system release. Customers say 5.2.1 but we can look up the individual build if necessary. Usually for a major release we sync up all the individual versions so everything gets built out of the same branch number again.

share|improve this answer
add comment

Whole books are written about versioning software.

Here is an approach that I use.

Each part has a version in the form:

major.minor.developmental

Each of these is a number, starting at 0.

For a formal release (ie to customers), the developmental part must always be 0 as a matter of policy.

Major is incremented by marketing decision.

Minor is incremented by feature sets being released - to market.

Example:

  • I start development on a new component, so my version number will 0.0.1. As I release off my desk to my colleages, for example, for internal testing, the development number goes up to 0.0.2, 0.0.3, and so on.

  • I release this new thing to market as 1.0.0, where the only permitted change from the end of development to release was to change the version number (eg 0.0.43 -> 1.0.0).

  • Some new features are to be added. I start work on the 1.0.0 baseline, adding these features, so the versions I release to my colleagues for testing are 1.0.1, 1.0.2, and so on.

  • The next features are released to market as 1.1.0.

  • Marketing decide that the next big thing will be really big, so it will go out as 2.0.0. I start work on 1.1.1, progressing through 1.1.x, and release as 2.0.0.

And so the cycle repeats.

This approach, for each component, gives you traceability of ancestry.

Internal to your source (and object) revision management system, use branches and tags (labels, whatever your terminology of the day is) to manage the development.

Your revision control may then manage each component completely separately, with development branches and labels/tags for each. Or you can bundle them all up together, in which case you may wish to branch by work package - but be sure to label/tag by release of each component (and when you do, label/tag everything, not just the bits for the component. This way you have a snapshot of the state of everything at the time.)

It's likely that your release process will require careful thought. Using this approach does include some manual steps, and this may be undesirable - this all depends on how your build system pokes the version numbers into the final object. For much embedded code where the version numbers are just named numbers (eg #defined in C code), you have little choice but to do this all manually anyhow. Desktop platforms with nice GUIs often make this all much friendlier.

share|improve this answer
    
So are you basically saying that, for versioning individual components you increment the third number, and for versioning the whole system you increment the first or second number for every component? –  Robert Harvey Aug 28 '11 at 15:46
    
Do each component separately as development version numbers. Roll up the major or minor part with the associated full product releases. NOTE that this works reasonably well for embedded firmware - I'd give a lot of thought to this vs something else for PC based s/w where you might ship a bunch of DLLs. This approach also has some wrinkles for things like PC-s/w where you might want to identify and ship a service pack. –  quickly_now Aug 28 '11 at 22:36
add comment

Be careful with versioning, it might kill you :-) Don't try to make things too complicated.

I think the following approach might help you:

Version each component individually with whatever versioning schema you want. From your comments I understand that you have a VCS in place. I also assume that each component has a file where its version is kept (right?). Once per day/week (whichever works better for your team) add a tag to one of the most recent revisions in VCS that marks that revision as the latest official revision (and optionally increment a super-revision number). Now you can query the VCS for the revisions with that tag and then look for the version of the components in that official build.

If you just want locally, write a small script that will aggregate the version of each component from the place where is stored in code.

If you want to make it even fancier, once you do the tagging you can look at the files belonging to each component, considering that you can identifiy the files that belong to a specific component. If any changed, increment the version for that specific component. The alternative is to do this manually. Another alternative is a combination of branching and merging with version tracking.

share|improve this answer
add comment

Most version numbers use a major and minor revision that is driven by marketing, so you can't use those for tracking individual component versions. In short, you need to find some other part of the version that you can use for tracking versions of individual components, and reserve the major and minor version numbers for tracking the whole package.

If you are following something akin to the Microsoft pattern:

major version.minor version.build number.revision

You can use the .revision to track each individual component's version, and use the minor and major revision numbers to track a complete product change, in the usual way.

If you are following a pattern similar to this:

Major Version.Minor Version.Build Number

You will have to use the build number to track the individual component versions.

share|improve this answer
add comment

Summary

For me, the only reliable way to version software is to use the the hash or changeset identifier from your version control system.

An overall build version number can be useful, but it's only really guaranteed to be unique if you have a build server and/or you sign each release. For many of us though, this simply isn't viable.

If your project is split over multiple version control repositories, you will also need to build a mechanism whereby your user interface can query each dependent repository and report it's hash back to the user.

Example from personal experience

In a project at a previous employer, where we had problems with our (internal) customer modifying software and recompiling it, I instituted a process whereby the mercurial hashes were compiled into each application and library. Whenever the software was started, a revisions string was built up by querying all of the software components.

This revision string was displayed when you went to the about page and was written to the log file every time the application was started. It was of the form:

Application name     (6a72e7c61f54)
    Library1         (b672a13a41e1)
        Library2     (9cc35769b23a)
    Library2         (9cc35769b23a)
    Library3         (4e9f56a0186a+)
        Library2     (9cc35769b23a)
    Library4         (2e3b08c4ac76)
        Library1     (b672a13a41e1)
            Library2 (9cc35769b23a)

From this I could easily see that they'd modified Library3 and hadn't committed those changes to the repository, so they are using code that is not controlled. I could also compare the hashes with my current test system, thus I might be able to identify that they have reverted (say) Library1 to an older version.

This meant that whenever they reported a bug, I could always rebuild exactly the code in use at the time the problem occurred, or at the very least know for certain that I could not reproduce the setup.

For more details of the build system I used, how I accomplished this, what problems I had, and what people suggested to avoid them, have a look at my Stack Overflow question.

Note: This system is only really viable if you use a revision control system where a given hash is guaranteed to result in the same set of files in your working directory (e.g. git and mercurial) if a given working directory can contain a mixture of files and directories from several revisions (e.g. svn) then all bets are off regarding the state of the working directory and this method won't work at all.

share|improve this answer
add comment

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.