Details
Description
In Java reflection, just because you got a Class object does not necessarily imply that you can access all methods and fields safely. In fact, what happens is that if one of the types used in the method/field signatures are not found, methods like getMethod could fail with NoClassDefFoundError, leaving a stack trace like this:
java.lang.NoClassDefFoundError: javax/servlet/ServletContext
at java.lang.Class.getDeclaredMethods0(Native Method)
at java.lang.Class.privateGetDeclaredMethods(Class.java:2365)
at java.lang.Class.privateGetPublicMethods(Class.java:2488)
at java.lang.Class.getMethods(Class.java:1406)
at com.thoughtworks.qdox.JavaDocBuilder.createBinaryClass(JavaDocBuilder.java:189)
at com.thoughtworks.qdox.JavaDocBuilder.getClassByName(JavaDocBuilder.java:119)
at com.thoughtworks.qdox.model.ClassLibrary.getClassByName(ClassLibrary.java:37)
at com.thoughtworks.qdox.model.Type.getJavaClass(Type.java:98)
at com.thoughtworks.qdox.model.JavaClass.getImplementedInterfaces(JavaClass.java:91)
A few suggestions based on this.
1. improve createBinaryClass method to be prepared for this kind of error, and revert gracefully.
2. this kind of problem happens because of the classloader set up in the caller. This is made worse because JavaDocBuilder
automatically picks up what it calls the "default loader", which is the context classloader and the classloader that loads qdox.
It's not usually desirable for qdox to be able to "see" the classes of the currently executing program (be it maven, ant, etc), and
in fact if anything it's usually harmful. (For example if you think about javac, your program will never be able to see the classes
that implements javac itself — you take "classpath" separately.)
so this design of automatically adding default loaders should be reconsidered, at least so that if the caller wishes to set up
ClassLibrary correctly, it should be able to do so.
Activity
Field | Original Value | New Value |
---|---|---|
Resolution | Fixed [ 1 ] | |
Fix Version/s | 1.8 [ 14826 ] | |
Status | Open [ 1 ] | Closed [ 6 ] |
Kohsuke - I think getMethods() has been replaced for getDeclaredMethods(). At least that's the way it is in head.
Are you thinking that a addClassLoader(ClassLoader cl) is needed for JavaDocBuilder class ? JavaDocBuilder has-a ClassLibrary and ClassLibrary.java has a method addClassLoader(..)
Could it be that this is what you want ?