简体   繁体   中英

How do I invoke a class from another jar file?

I am currently trying to load a class or run it by using reflection from java to invoke the main class from the jar file.

Whenever I try to run it I will get the following error:

`java.lang.ClassNotFoundException: MyClass
at java.net.URLClassLoader.findClass(URLClassLoader.java:381)
at java.lang.ClassLoader.loadClass(ClassLoader.java:424)
at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:331)
at java.lang.ClassLoader.loadClass(ClassLoader.java:357)
at java.lang.Class.forName0(Native Method)
at java.lang.Class.forName(Class.java:264)
at com.test.Test.main(Test.java:43)`

The program will also find the jar saying Found MyClass an I also initialize the main class to be the class that it found. Problem is that it doesn't find the class at all even though it's technically found and set.

I already tried the method with invoke to load main class inside of the project which worked fine.

`private static JarFile jarFile;

@SuppressWarnings("unused")
public static void main(String[] args) throws IOException
{
    /** Input of jar file */
    jarFile = new JarFile("MyJarFile.jar");
    Enumeration<JarEntry> e = jarFile.entries();
    URL[] urls = { new URL("jar:file:" + "MyJarFile.jar" +"!/") };
    URLClassLoader cl = URLClassLoader.newInstance(urls);

    Class<?> mainClass = null;

    while (e.hasMoreElements()) 
    {
        JarEntry je = e.nextElement();
        if(je.isDirectory() || !je.getName().endsWith(".class")){
            continue;
        }

        String className = je.getName().substring(0, je.getName().length()-6);
        className = className.replace('/', '.');
        try
        {
            Class<?> c = cl.loadClass(className);
            if (className.equals("MyClass"))
            {
                mainClass = c;
                System.out.println("Found MyClass");
                try
                {
                    /** The method I use to invoke the main class */
                    Class<?> cls = Class.forName(className);
                    Method method = cls.getMethod("main", String[].class);
                    String[] params = new String[]{};
                    method .invoke(null, (Object) params);
                    jarFile.close();
                }
                catch (Exception ex)
                {
                    ex.printStackTrace();
                }
            }
            System.out.println("Loaded: " + className);
        }

        catch (Exception ex)
        {
            ex.printStackTrace();
        }
    }

    if (mainClass == null)
    {
        return;
    }
}
`

I basically expect the program to run the main method inside of the jar and start it.

I'm really not sure why you're trying to load the class using Class.forName when you've already loaded it from the correct classloader using ClassLoader.loadClass .

Remove line

Class<?> cls = Class.forName(className);

(which tries to load the class from the classloader in which the line itself runs, which is not the classloader than can load MyClass )

And change the line after it to:

Method method = c.getMethod("main", String[].class);

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM