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.mx.loading;
023:
024: import java.net.URL;
025: import java.util.Enumeration;
026: import java.util.Iterator;
027: import java.util.List;
028:
029: /**
030: * Implements a simple classloader repository for the MBean server. The basic
031: * loader repository uses an unordered list of classloaders to try and load
032: * the required class. There is no attempt made to resolve conflicts between
033: * classes loaded by different classloaders. <p>
034: *
035: * A thread's context class loader is always searched first. Context class loader
036: * is not required to be registered to the repository.
037: *
038: * @see org.jboss.mx.loading.LoaderRepository
039: *
040: * @author <a href="mailto:juha@jboss.org">Juha Lindfors</a>.
041: * @version $Revision: 57200 $
042: */
043: public class BasicLoaderRepository extends LoaderRepository {
044:
045: // Public --------------------------------------------------------
046:
047: /**
048: * Loads a class from the repository. This method attempts to load the class
049: * using all the classloader registered to the repository.
050: *
051: * @param className the class to load
052: * @return the found class
053: * @exception ClassNotFoundException when there is no such class
054: */
055: public Class loadClass(String className)
056: throws ClassNotFoundException {
057: return loadClassWithout(null, className);
058: }
059:
060: /**
061: * Loads a class from the repository, excluding the given
062: * classloader.
063: *
064: * @param skipLoader the classloader to exclude
065: * @param className the class to load
066: * @return the found class
067: * @exception ClassNotFoundException when there is no such class
068: */
069: public Class loadClassWithout(ClassLoader skipLoader,
070: String className) throws ClassNotFoundException {
071: // try ctx cl first
072: ClassLoader ctxLoader = Thread.currentThread()
073: .getContextClassLoader();
074: if (ctxLoader != skipLoader) {
075: try {
076: return ctxLoader.loadClass(className);
077: } catch (ClassNotFoundException e) {
078: // ignore and move on to the loader list
079: }
080: }
081:
082: Iterator it = loaders.iterator();
083: while (it.hasNext()) {
084: ClassLoader cl = (ClassLoader) it.next();
085: if (cl != skipLoader) {
086: try {
087: return cl.loadClass(className);
088: } catch (ClassNotFoundException ignored) {
089: // go on and try the next loader
090: }
091: }
092: }
093:
094: // at last try a native
095: Class clazz = getNativeClassForName(className);
096: if (clazz != null)
097: return clazz;
098:
099: throw new ClassNotFoundException(className);
100: }
101:
102: /**
103: * Loads a class from the repository, using the classloaders that were
104: * registered before the given classloader.
105: *
106: * @param stop consult all the classloaders registered before this one
107: * in an attempt to load a class
108: * @param className name of the class to load
109: *
110: * @return loaded class instance
111: *
112: * @throws ClassNotFoundException if none of the consulted classloaders were
113: * able to load the requested class
114: */
115: public Class loadClassBefore(ClassLoader stop, String className)
116: throws ClassNotFoundException {
117: Iterator it = loaders.iterator();
118: while (it.hasNext()) {
119: ClassLoader cl = (ClassLoader) it.next();
120: if (cl == stop)
121: break;
122:
123: try {
124: return cl.loadClass(className);
125: } catch (ClassNotFoundException ignored) {
126: // go on and try the next loader
127: }
128: }
129:
130: // at last try a native
131: Class clazz = getNativeClassForName(className);
132: if (clazz != null)
133: return clazz;
134:
135: throw new ClassNotFoundException(className);
136: }
137:
138: public void addClassLoader(ClassLoader cl) {
139: loaders.add(cl);
140: }
141:
142: public boolean addClassLoaderURL(ClassLoader cl, URL url) {
143: // This is a noop here
144: return false;
145: }
146:
147: public void removeClassLoader(ClassLoader cl) {
148: loaders.remove(cl);
149: }
150:
151: public RepositoryClassLoader newClassLoader(final URL url,
152: boolean addToRepository) throws Exception {
153: UnifiedClassLoader ucl = new UnifiedClassLoader(url);
154: if (addToRepository)
155: this .addClassLoader(ucl);
156: return ucl;
157: }
158:
159: public RepositoryClassLoader newClassLoader(final URL url,
160: final URL origURL, boolean addToRepository)
161: throws Exception {
162: UnifiedClassLoader ucl = new UnifiedClassLoader(url, origURL);
163: if (addToRepository)
164: this .addClassLoader(ucl);
165: return ucl;
166: }
167:
168: public Class loadClass(String name, boolean resolve, ClassLoader cl)
169: throws ClassNotFoundException {
170: throw new ClassNotFoundException(
171: "loadClass(String,boolean,ClassLoader) not supported");
172: }
173:
174: public URL getResource(String name, ClassLoader cl) {
175: URL res = null;
176: if (cl instanceof UnifiedClassLoader) {
177: UnifiedClassLoader ucl = (UnifiedClassLoader) cl;
178: res = ucl.getResourceLocally(name);
179: } else {
180: res = cl.getResource(name);
181: }
182: return res;
183: }
184:
185: public void getResources(String name, ClassLoader cl, List urls) {
186: Enumeration resURLs = null;
187: try {
188: if (cl instanceof UnifiedClassLoader) {
189: UnifiedClassLoader ucl = (UnifiedClassLoader) cl;
190: resURLs = ucl.findResourcesLocally(name);
191: } else {
192: resURLs = cl.getResources(name);
193: }
194: while (resURLs.hasMoreElements())
195: urls.add(resURLs.nextElement());
196: } catch (Exception e) {
197: }
198: }
199: }
|