Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Make JVM use My Own Class Loader

I wrote my own class loader. I need all my classes to be loaded using my class loader. I have passed the VM the following: -Djava.system.class.loader=MyClassLoader

Only the first referenced class in my package is being loaded using my class loader. Other classes in my package are being loaded using AppClassLoader.

Here is what MyClassLoader looks like:

import java.io.IOException;
import java.io.InputStream;
import java.net.URL;
import java.util.Enumeration;

public class MyClassLoader extends ClassLoader {

  public MyClassLoader() {
    super(MyClassLoader.class.getClassLoader());
  }

  public MyClassLoader(ClassLoader parent) {
    super(parent);
  }

  @Override
  public Class<?> loadClass(String name) throws ClassNotFoundException {
    System.out.println("MyClassLoader is loading " + name);
    return super.loadClass(name);
  }//loadClass

  @Override
  public synchronized Class<?> loadClass(String name, boolean resolve) throws ClassNotFoundException {
    System.out.println("MyClassLoader is loading " + name + " with resolve = " + resolve);
    return super.loadClass(name, resolve);
  }

  @Override
  protected Class<?> findClass(String name) throws ClassNotFoundException {
    System.out.println("MyClassLoader findClass " + name);
    return super.findClass(name);
  }

  @Override
  protected URL findResource(String name) {
    System.out.println("MyClassLoader findResource " + name);
    return super.findResource(name);
  }

  @Override
  protected Enumeration<URL> findResources(String name) throws IOException {
    System.out.println("MyClassLoader findResources " + name);
    return super.findResources(name);
  }

  @Override
  protected Package getPackage(String name) {
    System.out.println("MyClassLoader getPackage " + name);
    return super.getPackage(name);
  }

  @Override
  public URL getResource(String name) {
    System.out.println("MyClassLoadergetResource " + name);
    return super.getResource(name);
  }

  @Override
  public InputStream getResourceAsStream(String name) {
    System.out.println("MyClassLoader getResourceAsStream " + name);
    return super.getResourceAsStream(name);
  }

  @Override
  public Enumeration<URL> getResources(String name) throws IOException {
    System.out.println("MyClassLoader getResources " + name);
    return super.getResources(name);
  }
}//MyClassLoader

I have this code in a static block in one of my classes that are being loaded:

  static {
    System.out.println("My class loader = " + MyClass.class.getClassLoader().getClass());
  }

The output of this was:

My class loader = class sun.misc.Launcher$AppClassLoader

Is there a way that I can force using my class loader?

like image 863
user1053792 Avatar asked Nov 18 '11 12:11

user1053792


People also ask

How do I use a custom class loader?

The BootStrap class will dynamically load the target. jar and spring-context jar files by the same classloader which is a URLClassLoader instance. Because of this, the method start in Target instance can access the DateFormatter class that is defined in spring-context . Finally, run the BootStrap main method.

Can we create custom class loader?

To create a custom class loader, we will create a class that will extend ClassLoader. There is a method findClass() that must be overridden. Create a method that will load your given class from the class path. In our case we have created the method loadClassData() that will return byte[].

Can we create our own ClassLoader in Java?

We will create our own ClassLoader by extending the ClassLoader class and overriding the loadClass(String name) method. If the class name will start from com. journaldev then we will load it using our custom class loader or else we will invoke the parent ClassLoader loadClass() method to load the class.

How do I load a class into JVM?

loadClass(String name, boolean resolve): This method is used to load the classes which are referenced by the JVM. It takes the name of the class as a parameter. This is of type loadClass(String, boolean). defineClass(): The defineClass() method is a final method and cannot be overriden.


1 Answers

Based on what I've read, what you have done should work. I suspect that the problem may be in your classloader. Another possibility is that you haven't used the fully qualified classname of your classloader.


For the record, the javadoc for the ClassLoader.getSystemClassLoader() method explains what the java.system.class.loader property actually does. Read it and see if that gives any clues to the cause of your problems.

like image 142
Stephen C Avatar answered Oct 01 '22 20:10

Stephen C