1 /**
2 * Copyright 2005-2014 The Kuali Foundation
3 *
4 * Licensed under the Educational Community License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.opensource.org/licenses/ecl2.php
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16 package org.kuali.rice.core.api.util;
17
18
19 import org.apache.commons.lang.StringUtils;
20
21 import java.util.regex.Matcher;
22 import java.util.regex.Pattern;
23
24 /**
25 *
26 * Helper class for comparing version strings
27 *
28 * @author Kuali Rice Team (rice.collab@kuali.org)
29 *
30 */
31 public class VersionHelper {
32
33 // This pattern matches any non-digit string containing a version number of the form A.B.C.D followed by any non-digit string
34 private static final Pattern extractVersion = Pattern.compile("(\\D*)((\\d*\\.?)+)(\\S*)");
35
36 // Pattern used for splitting version number for comparison
37 private static final Pattern splitVersion = Pattern.compile("\\.");
38
39 /**
40 * returns -1 if versionOne is less than versionTwo, 0 if the versions are equal, and 1 if versionOne is more recent than versionTwo
41 *
42 * @param versionOne string representation of a version
43 * @param versionTwo string representation of a version
44 * @return int
45 */
46
47 public static int compareVersion(String versionOne, String versionTwo) {
48 try {
49 return compareVersionInt(versionOne, versionTwo);
50 } catch (IllegalArgumentException iae) {
51 return -1;
52 }
53
54 }
55
56 private static int compareVersionInt(String versionOne, String versionTwo) throws IllegalArgumentException {
57
58
59 if (StringUtils.isBlank(versionOne) || StringUtils.isBlank(versionTwo)) {
60 throw new IllegalArgumentException("Invalid argument");
61 }
62
63 Matcher m1 = extractVersion.matcher(versionOne);
64 Matcher m2 = extractVersion.matcher(versionTwo);
65
66 if (!m1.matches() || !m2.matches()) {
67 throw new IllegalArgumentException("Unable to extract version number from string using regex");
68 }
69
70 //uses the matches generated by the extractVersion pattern to pull the version out of a string
71 // i.e. "2.1.3-SNAPSHOT" after sanitization is "2.1.3"
72
73 String sanitizedVOne = versionOne.substring(m1.start(2), m1.end(2));
74 String sanitizedVTwo = versionTwo.substring(m2.start(2), m2.end(2));
75
76 //uses the splitPattern to break a string into an array of numeric strings
77 // i.e. "2.1.3" becomes {"2", "1", "3"}
78
79 String[] oneDigits = splitVersion.split(sanitizedVOne);
80 String[] twoDigits = splitVersion.split(sanitizedVTwo);
81
82 // if there are unequal arrays, iterate over arrays up to the length of the shorter array
83 // have to be able to deal with the case "2.1" compared to "2.1.3"
84 int length=0;
85 if (oneDigits.length<twoDigits.length) {
86 length=oneDigits.length;
87 } else {
88 length=twoDigits.length;
89 }
90
91 for(int i=0; i<length; i++) {
92 Integer intOne = Integer.valueOf(oneDigits[i]);
93 Integer intTwo = Integer.valueOf(twoDigits[i]);
94 Integer compare = intOne.compareTo(intTwo);
95 if (compare < 0) {
96 return -1;
97 }
98 else if (compare > 0) {
99 return 1;
100 }
101 }
102 if (oneDigits.length<twoDigits.length) {
103 return -1;
104 }
105 if (oneDigits.length==twoDigits.length) {
106 return 0;
107 }
108 return 1;
109
110 }
111
112
113 }
114
115