📄 webappclassloader.java
字号:
/*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You 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 org.apache.catalina.loader;
import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.FileOutputStream;
import java.io.FilePermission;
import java.io.IOException;
import java.io.InputStream;
import java.lang.reflect.Field;
import java.lang.reflect.Modifier;
import java.net.MalformedURLException;
import java.net.URL;
import java.net.URLClassLoader;
import java.security.AccessControlException;
import java.security.AccessController;
import java.security.CodeSource;
import java.security.Permission;
import java.security.PermissionCollection;
import java.security.Policy;
import java.security.PrivilegedAction;
import java.sql.Driver;
import java.sql.DriverManager;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.Enumeration;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Vector;
import java.util.jar.Attributes;
import java.util.jar.JarEntry;
import java.util.jar.JarFile;
import java.util.jar.Manifest;
import java.util.jar.Attributes.Name;
import javax.naming.NameClassPair;
import javax.naming.NamingEnumeration;
import javax.naming.NamingException;
import javax.naming.directory.DirContext;
import org.apache.catalina.Lifecycle;
import org.apache.catalina.LifecycleException;
import org.apache.catalina.LifecycleListener;
import org.apache.catalina.util.StringManager;
import org.apache.naming.JndiPermission;
import org.apache.naming.resources.Resource;
import org.apache.naming.resources.ResourceAttributes;
import org.apache.tomcat.util.IntrospectionUtils;
/**
* Specialized web application class loader.
* <p>
* This class loader is a full reimplementation of the
* <code>URLClassLoader</code> from the JDK. It is desinged to be fully
* compatible with a normal <code>URLClassLoader</code>, although its internal
* behavior may be completely different.
* <p>
* <strong>IMPLEMENTATION NOTE</strong> - This class loader faithfully follows
* the delegation model recommended in the specification. The system class
* loader will be queried first, then the local repositories, and only then
* delegation to the parent class loader will occur. This allows the web
* application to override any shared class except the classes from J2SE.
* Special handling is provided from the JAXP XML parser interfaces, the JNDI
* interfaces, and the classes from the servlet API, which are never loaded
* from the webapp repository.
* <p>
* <strong>IMPLEMENTATION NOTE</strong> - Due to limitations in Jasper
* compilation technology, any repository which contains classes from
* the servlet API will be ignored by the class loader.
* <p>
* <strong>IMPLEMENTATION NOTE</strong> - The class loader generates source
* URLs which include the full JAR URL when a class is loaded from a JAR file,
* which allows setting security permission at the class level, even when a
* class is contained inside a JAR.
* <p>
* <strong>IMPLEMENTATION NOTE</strong> - Local repositories are searched in
* the order they are added via the initial constructor and/or any subsequent
* calls to <code>addRepository()</code> or <code>addJar()</code>.
* <p>
* <strong>IMPLEMENTATION NOTE</strong> - No check for sealing violations or
* security is made unless a security manager is present.
*
* @author Remy Maucherat
* @author Craig R. McClanahan
* @version $Revision: 482586 $ $Date: 2006-12-05 11:55:38 +0100 (mar., 05 déc. 2006) $
*/
public class WebappClassLoader
extends URLClassLoader
implements Reloader, Lifecycle
{
protected static org.apache.juli.logging.Log log=
org.apache.juli.logging.LogFactory.getLog( WebappClassLoader.class );
public static final boolean ENABLE_CLEAR_REFERENCES =
Boolean.valueOf(System.getProperty("org.apache.catalina.loader.WebappClassLoader.ENABLE_CLEAR_REFERENCES", "true")).booleanValue();
protected class PrivilegedFindResource
implements PrivilegedAction {
protected File file;
protected String path;
PrivilegedFindResource(File file, String path) {
this.file = file;
this.path = path;
}
public Object run() {
return findResourceInternal(file, path);
}
}
// ------------------------------------------------------- Static Variables
/**
* The set of trigger classes that will cause a proposed repository not
* to be added if this class is visible to the class loader that loaded
* this factory class. Typically, trigger classes will be listed for
* components that have been integrated into the JDK for later versions,
* but where the corresponding JAR files are required to run on
* earlier versions.
*/
protected static final String[] triggers = {
"javax.servlet.Servlet" // Servlet API
};
/**
* Set of package names which are not allowed to be loaded from a webapp
* class loader without delegating first.
*/
protected static final String[] packageTriggers = {
};
/**
* The string manager for this package.
*/
protected static final StringManager sm =
StringManager.getManager(Constants.Package);
/**
* Use anti JAR locking code, which does URL rerouting when accessing
* resources.
*/
boolean antiJARLocking = false;
// ----------------------------------------------------------- Constructors
/**
* Construct a new ClassLoader with no defined repositories and no
* parent ClassLoader.
*/
public WebappClassLoader() {
super(new URL[0]);
this.parent = getParent();
system = getSystemClassLoader();
securityManager = System.getSecurityManager();
if (securityManager != null) {
refreshPolicy();
}
}
/**
* Construct a new ClassLoader with no defined repositories and no
* parent ClassLoader.
*/
public WebappClassLoader(ClassLoader parent) {
super(new URL[0], parent);
this.parent = getParent();
system = getSystemClassLoader();
securityManager = System.getSecurityManager();
if (securityManager != null) {
refreshPolicy();
}
}
// ----------------------------------------------------- Instance Variables
/**
* Associated directory context giving access to the resources in this
* webapp.
*/
protected DirContext resources = null;
/**
* The cache of ResourceEntry for classes and resources we have loaded,
* keyed by resource name.
*/
protected HashMap resourceEntries = new HashMap();
/**
* The list of not found resources.
*/
protected HashMap notFoundResources = new HashMap();
/**
* Should this class loader delegate to the parent class loader
* <strong>before</strong> searching its own repositories (i.e. the
* usual Java2 delegation model)? If set to <code>false</code>,
* this class loader will search its own repositories first, and
* delegate to the parent only if the class or resource is not
* found locally.
*/
protected boolean delegate = false;
/**
* Last time a JAR was accessed.
*/
protected long lastJarAccessed = 0L;
/**
* The list of local repositories, in the order they should be searched
* for locally loaded classes or resources.
*/
protected String[] repositories = new String[0];
/**
* Repositories URLs, used to cache the result of getURLs.
*/
protected URL[] repositoryURLs = null;
/**
* Repositories translated as path in the work directory (for Jasper
* originally), but which is used to generate fake URLs should getURLs be
* called.
*/
protected File[] files = new File[0];
/**
* The list of JARs, in the order they should be searched
* for locally loaded classes or resources.
*/
protected JarFile[] jarFiles = new JarFile[0];
/**
* The list of JARs, in the order they should be searched
* for locally loaded classes or resources.
*/
protected File[] jarRealFiles = new File[0];
/**
* The path which will be monitored for added Jar files.
*/
protected String jarPath = null;
/**
* The list of JARs, in the order they should be searched
* for locally loaded classes or resources.
*/
protected String[] jarNames = new String[0];
/**
* The list of JARs last modified dates, in the order they should be
* searched for locally loaded classes or resources.
*/
protected long[] lastModifiedDates = new long[0];
/**
* The list of resources which should be checked when checking for
* modifications.
*/
protected String[] paths = new String[0];
/**
* A list of read File and Jndi Permission's required if this loader
* is for a web application context.
*/
protected ArrayList permissionList = new ArrayList();
/**
* Path where resources loaded from JARs will be extracted.
*/
protected File loaderDir = null;
/**
* The PermissionCollection for each CodeSource for a web
* application context.
*/
protected HashMap loaderPC = new HashMap();
/**
* Instance of the SecurityManager installed.
*/
protected SecurityManager securityManager = null;
/**
* The parent class loader.
*/
protected ClassLoader parent = null;
/**
* The system class loader.
*/
protected ClassLoader system = null;
/**
* Has this component been started?
*/
protected boolean started = false;
/**
* Has external repositories.
*/
protected boolean hasExternalRepositories = false;
/**
* need conversion for properties files
*/
protected boolean needConvert = false;
/**
* All permission.
*/
protected Permission allPermission = new java.security.AllPermission();
// ------------------------------------------------------------- Properties
/**
* Get associated resources.
*/
public DirContext getResources() {
return this.resources;
}
/**
* Set associated resources.
*/
public void setResources(DirContext resources) {
this.resources = resources;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -