버전 매기기

버전은 다음과 같이 구성되어 있다.

major.minor.micro.qualifier

major.minor.micro는 숫자고, qualifier는 알파벳이나 숫자를 사용한다. major 이 외에는 전부 생략이 가능하다. 예를 들어, 1 은 1.0 이고 이건 다시 1.0.0 이랑 같다. 다음으로 중요한 건 높낮이. 1.0 보다 2.0 이 높은 버전이라는 것에는 이견이 없을 것이며 실제로도 그렇다. 그러나 qualifier 쪽으로 가면 그렇게 쉽진 않다.

A. 1.0.0.whiteship1
B. 1.0.0.whiteship2
C. 1.0.0.whiteship10

이 셋 중에서 가장 높은 버전은 몇 일까? C라고 예상하신 분들도 있겠지만, 정답은 B다. Java의 String 클래스의 compareTo()로 비교해서 높은 값이 높은 버전이 된다. String의 compareTo()는 한 글자씩 왼쪽에서 부터 비교한다. 따라서 B < C < A 순으로 높은 버전이 된다.

버전 범위 설정하기

버전 범위는 Import-Package 또는 Required-Bundle 헤더에서 사용한다. 명시하지 않으면 기본 값은 다음과 같다.

"[0.0.0, *]"

0.0.0 부터 모든 버전을 나타낸다. Export-Package 또는 Bundle-Version에 버전을 명시하지 않은 경우 기본값으로 0.0.0이 설정되기 때문에 양쪽에서 모두 기본값을 사용하는 경우 문제없이 참조할 수 있다. 하지만 역시 버전은 명시적으로 관리해주는 것이 좋겠다.

[] 와 ()의 차이만 알면 되겠다. []는 이상 이하. ()는 초과 미만의 개념이다. [1.0.0, 2.0.0) 이렇게 설정되어 있다면 1.0.0 버전이 있으면 그걸 참조하고 2.0.0 만 있다면 그건 참조하지 않는다. 1.9.9와 1.0.0 두 가지 버전이 존재할 땐 높은 버전의 번들을 선택한다.

그렇다고 매번 "[1.0.0, 1.3.0]" 이런식으로 표기해야 하는 것은 아니다. Spring 2.5 이상 어떤 버전이든 관계가 없을 때는 그냥 "2.5." 라고 설정하면 OSGi 프레임워크는 "[2.5.0, *]" 이렇게 인식할 것이다. 따라서 상위 호환이 보장되는 라이브러리를 참조하고 있다면 버전을 저런식으로 명시해도 된다.

이와 반대로 특정 버전 하나 만 참조하는 라이브러리가 있을 수도 있다. 전~혀 상위나 하위 호환이 되지 않아서 딱 그 버전만 써야 한다면, 그때는 "[2.5.5, 2.5.5]" 이렇게 범위를 딱 해당 버전으로만 좁혀줘야 한다.