/*
* $Id: $
*
* Copyright 2003-2004 The Apache Software Foundation.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.opensymphony.xwork2.util;
import com.opensymphony.xwork2.XWorkException;
import java.io.File;
import java.net.URI;
import java.net.URISyntaxException;
import java.net.URL;
import java.net.URLClassLoader;
import java.util.HashMap;
import java.util.Vector;
/**
* This class is an utility class that will search through the classpath
* for files whose names match the given pattern. The filename is tested
* using the given implementation of {@link com.opensymphony.xwork2.util.PatternMatcher} by default it
* uses {@link com.opensymphony.xwork2.util.WildcardHelper}
*
* @version $Rev: $ $Date: $
*/
public class ClassPathFinder {
/**
* The String pattern to test against.
*/
private String pattern ;
private int[] compiledPattern ;
/**
* The PatternMatcher implementation to use
*/
private PatternMatcher<int[]> patternMatcher = new WildcardHelper();
private Vector<String> compared = new Vector<String>();
/**
* retrieves the pattern in use
*/
public String getPattern() {
return pattern;
}
/**
* sets the String pattern for comparing filenames
* @param pattern
*/
public void setPattern(String pattern) {
this.pattern = pattern;
}
/**
* Builds a {@link java.util.Vector} containing Strings which each name a file
* who's name matches the pattern set by setPattern(String). The classpath is
* searched recursively, so use with caution.
*
* @return Vector<String> containing matching filenames
*/
public Vector<String> findMatches() {
Vector<String> matches = new Vector<String>();
URLClassLoader cl = getURLClassLoader();
if (cl == null ) {
throw new XWorkException("unable to attain an URLClassLoader") ;
}
URL[] parentUrls = cl.getURLs();
compiledPattern = (int[]) patternMatcher.compilePattern(pattern);
for (URL url : parentUrls) {
if (!"file".equals(url.getProtocol())) {
continue ;
}
URI entryURI ;
try {
entryURI = url.toURI();
} catch (URISyntaxException e) {
continue;
}
File entry = new File(entryURI) ;
Vector<String> results = checkEntries(entry.list(), entry, "");
if (results != null ) {
matches.addAll(results);
}
}
return matches;
}
private Vector<String> checkEntries(String[] entries, File parent, String prefix) {
if (entries == null ) {
return null;
}
Vector<String> matches = new Vector<String>();
for (String listEntry : entries) {
File tempFile ;
if (!"".equals(prefix) ) {
tempFile = new File(parent, prefix + "/" + listEntry);
}
else {
tempFile = new File(parent, listEntry);
}
if (tempFile.isDirectory() &&
!(".".equals(listEntry) || "..".equals(listEntry)) ) {
if (!"".equals(prefix) ) {
matches.addAll(checkEntries(tempFile.list(), parent, prefix + "/" + listEntry));
}
else {
matches.addAll(checkEntries(tempFile.list(), parent, listEntry));
}
}
else {
String entryToCheck ;
if ("".equals(prefix)) {
entryToCheck = listEntry ;
}
else {
entryToCheck = prefix + "/" + listEntry ;
}
if (compared.contains(entryToCheck) ) {
continue;
}
else {
compared.add(entryToCheck) ;
}
boolean doesMatch = patternMatcher.match(new HashMap<String,String>(), entryToCheck, compiledPattern);
if (doesMatch) {
matches.add(entryToCheck);
}
}
}
return matches ;
}
/**
* sets the PatternMatcher implementation to use when comparing filenames
* @param patternMatcher
*/
public void setPatternMatcher(PatternMatcher<int[]> patternMatcher) {
this.patternMatcher = patternMatcher;
}
private URLClassLoader getURLClassLoader() {
URLClassLoader ucl = null;
ClassLoader loader = Thread.currentThread().getContextClassLoader();
if(! (loader instanceof URLClassLoader)) {
loader = ClassPathFinder.class.getClassLoader();
if (loader instanceof URLClassLoader) {
ucl = (URLClassLoader) loader ;
}
}
else {
ucl = (URLClassLoader) loader;
}
return ucl ;
}
}
|