Reputation: 565
I have an unusual problem which is concerned to dynamic loading java .class file at run-time. All I want to do is to load a .class file and basing on it create a Class object.
Input: an absolute path of .class file.
Basing on it i want to load class by ClassLoader, so I need a path of root directory where file is located and full class name e.g com.test.MyClass. Basing on mentioned absolute path I can only get a class name but I can't get a package name which is "hiden" in this file.
Here is code of my "loading class method":
public static void loadClass(String directory){
// Get file root directory
String rootDirectory = new File(directory).getParent();
// Get rid of file extension
String className = getFileNameWithoutExtension(directory);
URL[] urls = null;
ClassLoader cl = null;
try {
// Convert File to a URL and save them
urls = new URL[]{new File(rootDirectory).toURI().toURL()};
// Create a new class loader with the directory
cl = new URLClassLoader(urls);
// Load in the class
dynamicClass = cl.loadClass(className);
}
catch (MalformedURLException e)
{
}
catch (ClassNotFoundException e)
{
}
catch (NoClassDefFoundError e)
{
// Basing on error message get the class package name
String classPackage = getClassPackage(e.getMessage());
try {
// Load the class once more!
dynamicClass = cl.loadClass(classPackage);
}
catch (ClassNotFoundException ex)
{
}
}
}
Second method is used to get package name from exception message:
private static String getClassPackage(String errorMsg){
// Start and end index of cutting
int startIndex = errorMsg.lastIndexOf(" ") + 1;
int endIndex = errorMsg.length() - 1;
// Let's save a substring
String classPackage = errorMsg.substring(startIndex, endIndex);
// Replace char '/' to '.'
classPackage = classPackage.replace('/', '.');
return classPackage;
}
Code of method getFileNameWithoutExtension:
private static String getFileNameWithoutExtension(String path){
int start = path.lastIndexOf(File.separator) + 1;
int end = path.lastIndexOf(DOT);
end = start < end ? end : path.length();
String name = path.substring(start, end);
return name;
}
Where the static final variable is:
private static final String DOT = ".";
And here is my question: is it possible to get package name from .class file without using this kind of trick?
Upvotes: 1
Views: 17628
Reputation: 1844
You can use the Foo.class.getPackage().getName()
method to determine this.
public Package getPackage()
Returns:
the package of the class, or null if no package information is available from the archive or codebase.
Using getName() :
public String getName()
Returns:
The fully-qualified name of this package as defined in section 6.5.3 of The Java™ Language Specification, for example, java.lang
Upvotes: 8
Reputation: 2148
You can do like this-
String packName = new Object(){}.getClass().getPackage().getName();
System.out.println(packName);
Upvotes: 0
Reputation: 10121
Since you already have the required data in className
, just use it again. You don't need the getClassPackage
method.
catch (NoClassDefFoundError e)
{
// Basing on error message get the class package name
//But we already have the class name in className variable!
//String classPackage = getClassPackage(e.getMessage());
try {
// Load the class once more!
dynamicClass = cl.loadClass(className);
}
catch (ClassNotFoundException ex)
{
}
}
And if you want to get the package name only (not sure why), you can just get it from the class name:
String packageName = className.substring(0, className.lastIndexOf('.'));
dynamicClass = cl.loadClass(packageName);
Upvotes: 0