PluginClassLoader.java 4.02 KB
Newer Older
1 2 3 4 5
/**
 * $RCSfile$
 * $Revision: 2993 $
 * $Date: 2005-10-24 18:11:33 -0300 (Mon, 24 Oct 2005) $
 *
6
 * Copyright (C) 2004-2008 Jive Software. All rights reserved.
7 8
 *
 * This software is published under the terms of the GNU Public License (GPL),
9 10
 * a copy of which is included in this distribution, or a commercial license
 * agreement with Jive.
11 12
 */

13
package org.jivesoftware.openfire.container;
14

15
import org.jivesoftware.openfire.XMPPServer;
16
import org.jivesoftware.util.Log;
17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34

import java.io.File;
import java.io.FilenameFilter;
import java.net.MalformedURLException;
import java.net.URL;
import java.net.URLClassLoader;

/**
 * ClassLoader for plugins. It searches the plugin directory for classes
 * and JAR files, then constructs a class loader for the resources found.
 * Resources are loaded as follows:<ul>
 * <p/>
 * <li>Any JAR files in the <tt>lib</tt> will be added to the classpath.
 * <li>Any files in the classes directory will be added to the classpath.
 * </ul>
 *
 * @author Derek DeMoro
 */
35
public class PluginClassLoader extends URLClassLoader {
36

37 38
    public PluginClassLoader() {
        super(new URL[] {}, findParentClassLoader());
39 40 41
    }

    /**
42
     * Adds a directory to the class loader.
43 44
     *
     * @param directory the directory.
45 46
     * @param developmentMode true if the plugin is running in development mode. This
     *      resolves classloader conflicts between the deployed plugin
47
     * and development classes.
48
     */
49
    public void addDirectory(File directory, boolean developmentMode) {
50
        try {
51
            // Add classes directory to classpath.
52 53
            File classesDir = new File(directory, "classes");
            if (classesDir.exists()) {
54
                addURL(classesDir.toURL());
55
            }
56

57 58 59
            // Add i18n directory to classpath.
            File databaseDir = new File(directory, "database");
            if(databaseDir.exists()){
60
                addURL(databaseDir.toURL());
61 62
            }

63 64 65
            // Add i18n directory to classpath.
            File i18nDir = new File(directory, "i18n");
            if(i18nDir.exists()){
66
                addURL(i18nDir.toURL());
67 68
            }

69 70 71
            // Add web directory to classpath.
            File webDir = new File(directory, "web");
            if(webDir.exists()){
72
                addURL(webDir.toURL());
73 74
            }

75
            // Add lib directory to classpath.
76 77 78 79 80 81 82 83 84
            File libDir = new File(directory, "lib");
            File[] jars = libDir.listFiles(new FilenameFilter() {
                public boolean accept(File dir, String name) {
                    return name.endsWith(".jar") || name.endsWith(".zip");
                }
            });
            if (jars != null) {
                for (int i = 0; i < jars.length; i++) {
                    if (jars[i] != null && jars[i].isFile()) {
85 86 87
                        if (developmentMode) {
                            // Do not add plugin-pluginName.jar to classpath.
                            if (!jars[i].getName().equals("plugin-" + directory.getName() + ".jar")) {
88
                                addURL(jars[i].toURL());
89 90 91
                            }
                        }
                        else {
92
                            addURL(jars[i].toURL());
93
                        }
94 95 96 97 98 99 100 101 102
                    }
                }
            }
        }
        catch (MalformedURLException mue) {
            Log.error(mue);
        }
    }

103 104
    public void addURLFile(URL file) {
        addURL(file);
105 106 107 108 109 110 111
    }

    /**
     * Locates the best parent class loader based on context.
     *
     * @return the best parent classloader to use.
     */
112
    private static ClassLoader findParentClassLoader() {
113
        ClassLoader parent = XMPPServer.class.getClassLoader();
114
        if (parent == null) {
115
            parent = PluginClassLoader.class.getClassLoader();
116 117 118 119 120 121 122
        }
        if (parent == null) {
            parent = ClassLoader.getSystemClassLoader();
        }
        return parent;
    }
}