001: /*
002: * JBoss, Home of Professional Open Source.
003: * Copyright 2006, Red Hat Middleware LLC, and individual contributors
004: * as indicated by the @author tags. See the copyright.txt file in the
005: * distribution for a full listing of individual contributors.
006: *
007: * This is free software; you can redistribute it and/or modify it
008: * under the terms of the GNU Lesser General Public License as
009: * published by the Free Software Foundation; either version 2.1 of
010: * the License, or (at your option) any later version.
011: *
012: * This software is distributed in the hope that it will be useful,
013: * but WITHOUT ANY WARRANTY; without even the implied warranty of
014: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
015: * Lesser General Public License for more details.
016: *
017: * You should have received a copy of the GNU Lesser General Public
018: * License along with this software; if not, write to the Free
019: * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
020: * 02110-1301 USA, or see the FSF site: http://www.fsf.org.
021: */
022: package org.jboss.deployment.scanner;
023:
024: import java.util.Comparator;
025: import java.net.URL;
026: import org.jboss.deployment.DeploymentSorter;
027: import org.jboss.deployment.DefaultDeploymentSorter;
028:
029: /**
030: * <p>This class is a comparator to sort deployment URLs based on the existence
031: * of a numeric prefix. The name portion of the URL is evaluated for any
032: * leading digits. If they exist, then they will define a numerical ordering
033: * for this comparator. If there is no leading digits, then they will
034: * compare as less than any name with leading digits. In the case of a
035: * tie, the DeploymentSorter is consulted (@see org.jboss.deployment.DeploymentSorter).
036: *
037: * <p>Ex.these names are in ascending order:
038: * test.sar, crap.ear, 001test.jar, 5test.rar, 5foo.jar, 120bar.jar
039: */
040: public class PrefixDeploymentSorter implements Comparator,
041: DefaultDeploymentSorter {
042:
043: /** This is used to break ties */
044: private DeploymentSorter sorter = new DeploymentSorter();
045:
046: public String[] getSuffixOrder() {
047: return sorter.getSuffixOrder();
048: }
049:
050: public void setSuffixOrder(String[] suffixOrder) {
051: sorter.setSuffixOrder(suffixOrder);
052: }
053:
054: /**
055: * As described in @see java.util.Comparator. This implements the
056: * comparison technique described above.
057: */
058: public int compare(Object o1, Object o2) {
059: int comp = getPrefixValue((URL) o1) - getPrefixValue((URL) o2);
060:
061: return comp == 0 ? sorter.compare(o1, o2) : comp;
062: }
063:
064: /**
065: * This extracts the prefix value from the name of a URL. If no prefix
066: * value exists, this returns -1
067: */
068: private int getPrefixValue(URL url) {
069: String path = url.getPath();
070: int nameEnd = path.length() - 1;
071: if (nameEnd <= 0) {
072: return 0;
073: }
074:
075: // ignore a trailing '/'
076: if (path.charAt(nameEnd) == '/') {
077: nameEnd--;
078: }
079:
080: // find the previous URL separator: '/'
081: int nameStart = path.lastIndexOf('/', nameEnd) + 1;
082:
083: // calculate where the digit-prefix ends
084: int prefixEnd = nameStart;
085: while (prefixEnd <= nameEnd
086: && Character.isDigit(path.charAt(prefixEnd))) {
087: prefixEnd++;
088: }
089:
090: // If zero length prefix, return -1
091: if (prefixEnd == nameStart) {
092: return -1;
093: }
094:
095: // strip leading zeroes
096: while (nameStart < prefixEnd && path.charAt(nameStart) == '0') {
097: nameStart++;
098: }
099:
100: return (nameStart == prefixEnd) ? 0 : Integer.parseInt(path
101: .substring(nameStart, prefixEnd));
102: }
103: }
|