How to get names of classes inside a jar file?
Unfortunately, Java doesn't provide an easy way to list classes in the "native" JRE. That leaves you with a couple of options: (a) for any given JAR file, you can list the entries inside that JAR file, find the .class
files, and then determine which Java class each .class
file represents; or (b) you can use a library that does this for you.
Option (a): Scanning JAR files manually
In this option, we'll fill classNames
with the list of all Java classes contained inside a jar file at /path/to/jar/file.jar
.
List<String> classNames = new ArrayList<String>();
ZipInputStream zip = new ZipInputStream(new FileInputStream("/path/to/jar/file.jar"));
for (ZipEntry entry = zip.getNextEntry(); entry != null; entry = zip.getNextEntry()) {
if (!entry.isDirectory() && entry.getName().endsWith(".class")) {
// This ZipEntry represents a class. Now, what class does it represent?
String className = entry.getName().replace('/', '.'); // including ".class"
classNames.add(className.substring(0, className.length() - ".class".length()));
}
}
Option (b): Using specialized reflections libraries
Guava
Guava has had ClassPath
since at least 14.0, which I have used and liked. One nice thing about ClassPath
is that it doesn't load the classes it finds, which is important when you're scanning for a large number of classes.
ClassPath cp=ClassPath.from(Thread.currentThread().getContextClassLoader());
for(ClassPath.ClassInfo info : cp.getTopLevelClassesRecurusive("my.package.name")) {
// Do stuff with classes here...
}
Reflections
I haven't personally used the Reflections library, but it seems well-liked. Some great examples are provided on the website like this quick way to load all the classes in a package provided by any JAR file, which may also be useful for your application.
Reflections reflections = new Reflections("my.project.prefix");
Set<Class<? extends SomeType>> subTypes = reflections.getSubTypesOf(SomeType.class);
Set<Class<?>> annotated = reflections.getTypesAnnotatedWith(SomeAnnotation.class);
Find a class somewhere inside dozens of JAR files?
Eclipse can do it, just create a (temporary) project and put your libraries on the projects classpath. Then you can easily find the classes.
Another tool, that comes to my mind, is Java Decompiler. It can open a lot of jars at once and helps to find classes as well.
Listing classes in a jar file
Have a look at the classes in the package java.util.jar
. You can find examples of how to list the files inside the JAR on the web, here's an example. (Also note the links at the bottom of that page, there are many more examples that show you how to work with JAR files).
List Classes inside jar dynamically
You can use JarFile#entries
to get an enumeration of the ZIP file entries, than use a URLClassLoader
to get the classes:
private List<Class<?>> loadClasses(String pathToJar){
ArrayList<Class<?>> classes = new ArrayList<Class<?>>();
JarFile jarFile = null;
try {
jarFile = new JarFile(pathToJar);
Enumeration<JarEntry> e = jarFile.entries();
URL[] urls = { new URL("jar:file:" + pathToJar+"!/") };
URLClassLoader cl = URLClassLoader.newInstance(urls);
while (e.hasMoreElements()) {
JarEntry je = e.nextElement();
if(je.isDirectory() || !je.getName().endsWith(".class")){
continue;
}
String className = je.getName().substring(0,je.getName().length()-String.valueOf(".class").length());
className = className.replace('/', '.');
Class<?> clazz = cl.loadClass(className);
classes.add(clazz);
}
} catch (IOException e1) {
e1.printStackTrace();
} catch (ClassNotFoundException e1) {
e1.printStackTrace();
}finally {
try {
jarFile.close();
} catch (IOException e) {
e.printStackTrace();
}
}
return classes.isEmpty() ? null : classes;
}
How to list the files inside a JAR file?
CodeSource src = MyClass.class.getProtectionDomain().getCodeSource();
if (src != null) {
URL jar = src.getLocation();
ZipInputStream zip = new ZipInputStream(jar.openStream());
while(true) {
ZipEntry e = zip.getNextEntry();
if (e == null)
break;
String name = e.getName();
if (name.startsWith("path/to/your/dir/")) {
/* Do something with this entry. */
...
}
}
}
else {
/* Fail... */
}
Note that in Java 7, you can create a FileSystem
from the JAR (zip) file, and then use NIO's directory walking and filtering mechanisms to search through it. This would make it easier to write code that handles JARs and "exploded" directories.
Extract class names from JAR with special formatting
String path = "org/apache/commons/math3/analysis/integration/gauss/BaseRuleFactory.class";
path = path.replaceAll("/", ".")
.replaceAll("\\$(\\d+)\\.class", "\\.$1");
java list all methods and classes in a jar file of specific package using cmd
jar tf
will list the contents for you.
javap
will allow you to see more details of the classes (see the tools guide here).
For instance if you have a class named mypkg.HelloWorld in a jar myjar.jar then run it like
javap -classpath myjar.jar mypkg.HelloWorld
To see method in .class file embedded in jar file | is it possible ?
Extract the class from jar file and then run
unzip Classes.jar
find . -name '*.class' | xargs javap -p > classes.txt
The classes.txt
file will have all information about the classes inside jar. You can search it for a method.
Related Topics
How to Embed Binary Data in Xml
Java Simpledateformat for Time Zone with a Colon Separator
Java: How to Access Methods from Another Class
How to Run a Class in a War from the Command Line
Why Does Arraylist Have "Implements List"
CSV Parsing in Java - Working Example
JSONobject:Why JSONobject Changing the Order of Attributes
Why Doesn't Java Allow Generic Subclasses of Throwable
Spring-Batch Without Persisting Metadata to Database
Eclipse Error: "Failed to Connect to Remote Vm"
Declaring and Initializing Variables Within Java Switches
The Server Time Zone Value 'Aest' Is Unrecognized or Represents More Than One Time Zone
Why Is an Instance Variable of the Superclass Not Overridden by a Subclass