<editorial BS>
Version ranges are pure evil if you want to have repeatable builds and want some idea about what you are testing and deploying.
They seem to be used as an alternative to thinking.
<End of editorial BS>

I do have some ideas that I hope will help.

On 13/05/2011 11:42 AM, Paul French wrote:
I've added the below to the discussion at...

http://jira.codehaus.org/browse/MNG-3092

...but include here in case anyone else has some ideas.


If you consider semantic versioning http://semver.org/ where by using carefully chosen version numbers (enforced by an api analysis tool) and version ranges to specify your dependencies between your components then version ranges need to support some basic ideas.

I have component A [1.0.0] and component B [1.1.0] and component A depends on component B with version range [1.0.0,1.2.0)

A [1.0.0] depends on B [1.0.0,1.2.0)

We start additional development on B so it will initially be B [1.1.1-SNAPSHOT] So A will pull this in as it's current dependency i.e. B [1.1.1-SNAPSHOT] as a dependency (the current behaviour of maven 3.0.3)

Work continues on B and someone adds a method to an interface which is used by A, component B's version is increased to [1.2.0-SNAPSHOT] to signal the possible incompatible change since version B [1.1.0]

If you think about it, this snapshot of B could be incompatible to A so we need to exclude it in our version range i.e. we modify component A's dependency version range on B to exclude the 1.2.0-SNAPSHOT

Adding a method to B will not affect A, A can depend on [1.2.0-SNAPSHOT] since the methods that it will call are still there.
OTOH, there is no need to change A since it will be perfectly happy with B[1.1.0] and any subsequent version of B that is upwards compatible.
You can compile with [1.1.0] and execute with any later version of B.
Is B's scope in A "provided" or "compile"? Compile will include B[1.1.0] in A's jar and that may be perfectly alright. Provided will have A using whatever version of B that you provide.

A [1.0.0] depends on B [1.0.0,1.2.0-SNAPSHOT)

So already I'm not liking this since I have to specify I don't want the 1.2 SNAPSHOT but I can live with it.

So don't. Stick with A's original designed dependency B[1.1.0]. When you revisit A and start to use the new method, it will then depend on the current production release of B or some SNAPSHOT if you want to use A to test B.

However the dependency pulled in for A will now always be B [1.1.1-SNAPSHOT], there will never be a release of B[1.1.1] made by us, our baseline is B[1.1.0] and we have not made a new baseline release yet for component B but it will at best be [1.2.0] or a later version.

Never release anything with a SNAPSHOT dependency if you want to be able to maintain it since you have no idea what code is in a SNAPSHOT.
Could be ready to release or in the middle of development.
That is why it is not a Release.
SNAPSHOTS are unstable and do not come with a warranty of usability or any fixed specification.
RELEASES are stable and come with a warranty and a known specification. That is what you want to run in production.

I've concluded but I could be wrong that you need to be able to say whether you want to include or exclude SNAPSHOT in your version ranges. We develop OSGi bundles. Using the PDE analysis API tooling we compare on going development of bundles with a baseline release and update the POM/Bundle-Manifest version as appropriate depending on code changes. So we require to use version ranges with snapshots included when doing continuous integration but do not include SNAPSHOT when doing releases.

I actually would prefer A [1.0.0] depends on B [1.0.0,1.2.0) to actually mean...

"A depends on B from 1.0.0 up to but NOT including 1.2.0 or 1.2.0-SNAPSHOT"

Just pick 1 version and make sure that you do not break upwards compatibility without going back and fixing A.

From our point of view, if you do not want 1.2.0 since it will be incompatible then you do not want 1.2.0-SNAPSHOT either since it will also be incompatible.

To be clear B [1.1.1-SNAPHOT] is valid in the range above by default.

However when building a release we would like to set a property or something equivalent (not in the POM, you do not want to have to go through all the POMS) and exclude SNAPSHOT in version ranges.

I suspect other people may require other scenarios so I see some form of pluggable version range strategy being the answer. You plugin the functionality you require. The default behaviour will be what I have outlined


I hope that no one else is even thinking about this kind of development chaos.

Go back to the drawing board and think about what a dependency actually means - at compile time, at execution time.

Pay particular attention to how you are going to know what code is actually going to be run when the application is in production.

Think about what upwards compatibility actually means.

You are taking advantage of upwards compatibilty all the time with third party software. You do not go through all your code and change the dependencies on the Java Servlet Engine or log4j everytime your system admin upgrades Tomcat. You pray (the system admin probably more than you) that the new version of Tomcat will still run your application even though the versions have all gone up by big amounts.

You are making a lot of extra work for a negative return.

Free advice.
Do as you wish with it.

Ron

My 10 pence


--
Paul French
Kirona Solutions Ltd
Tel: 07803 122 058
E-Mail: paul.fre...@kirona.com
Web: www.kirona.com

This email and any attachments are confidential and should only be read by those to whom they are addressed. If you are not the intended recipient, please contact us on 01625 585511, delete the email (including any attachment) from your computer and destroy any copies. Any distribution or copying without our prior permission is prohibited. Internet communications are not always secure and may be subject to delays, non-delivery and unauthorised alterations. Therefore, information expressed in this message is not given or endorsed by Kirona Solutions Limited ("Kirona") unless otherwise notified by our duly authorised representative independent of this message. No warranty is given that this email (including any attachment) is virus free. Any views or opinions presented are solely those of the author and do not necessarily represent those of Kirona.

Registered addresses: Kirona Solutions Limited, Barrington House, Heyes Lane, Alderley Edge, Cheshire. SK9 7LA Registered in England and Wales No: 04678711


Reply via email to