In JDK 1.4.2_06, a Java Bean with zero properties will cause a NullPointerException when getBeanInfo() is called.
From my inspection of the source code of java/bean/Introspection.java, I believe this is caused because the pdStore Map is not instantiated until addPropertyDescriptor(PropertyDescriptor) is called. If a bean has no properties, this is never called. Then when processPropertyDescriptors() is called, the null pdStore results in immediate return before properties can be assigned to a new HashMap. In getTargetPropertyInfo(), the call to properties.size() on line 591 then results in a NPE.
Below is a simple test case and instructions on its execution.
Instructions to Compile and Execute:
javac -g Bisc.java beans/nb.java
java Bisc beans.nb
Results of Execution with JDK 1.4.2_05 (Correct Behavior)
bash-2.05$ java -version
java version "1.4.2_05"
Java(TM) 2 Runtime Environment, Standard Edition (build 1.4.2_05-b04)
Java HotSpot(TM) Client VM (build 1.4.2_05-b04, mixed mode)
bash-2.05$ java Bisc beans.nb
Class beans.nb
Methods via Bean
bash-2.05$
Results of Execution with JDK 1.4.2_06 (Incorrect Behavior)
bash-2.05$ java -version
java version "1.4.2_06"
Java(TM) 2 Runtime Environment, Standard Edition (build 1.4.2_06-b02)
Java HotSpot(TM) Client VM (build 1.4.2_06-b02, mixed mode)
bash-2.05$ java Bisc beans.nb
java.lang.NullPointerException
at java.beans.Introspector.getTargetPropertyInfo(Introspector.java:591)
at java.beans.Introspector.getBeanInfo(Introspector.java:380)
at java.beans.Introspector.getBeanInfo(Introspector.java:215)
at java.beans.Introspector.getBeanInfo(Introspector.java:201)
at Bisc.main(Bisc.java:15)
bash-2.05$
/////////////////////////
/// File: beans/nb.java
/////////////////////////
package beans;
public class nb
{
}
/// End File: beans/nb.java
/////////////////////////
/// File: Bisc.java
/////////////////////////
import java.beans.*;
import java.lang.reflect.Method;
import java.lang.reflect.Modifier;
public class Bisc
{
public static void main(String[] args)
{
if (args.length != 1)
System.err.println("Usage: java Bisc <JavaBeanClassName>");
try
{
Class cl = Class.forName(args[0]);
BeanInfo bi = Introspector.getBeanInfo(cl, cl.getSuperclass());
PropertyDescriptor[] pds = bi.getPropertyDescriptors();
System.out.println("Class " + args[0]);
System.out.println("\nMethods via Bean");
for (int i = 0; i < pds.length; i++)
{
PropertyDescriptor pd = pds[i];
System.out.println("Prop " + pd.getName());
Method rm = pd.getReadMethod();
Method wm = pd.getWriteMethod();
if (rm != null)
{
System.out.print("Read method: ");
methodInfo(rm);
}
else
System.out.println("Read method is null");
if (wm != null)
{
System.out.print("Write method: ");
methodInfo(wm);
}
else
System.out.println("Write method is null");
}
}
catch (Exception e)
{
e.printStackTrace();
}
}
static void methodInfo(Method m)
{
System.out.println(m.getName());
System.out.println(" modifiers: " +
Modifier.toString(m.getModifiers()));
System.out.println(" declaring class: " + m.getDeclaringClass());
}
}
/// End File: Bisc.java
###@###.### 10/18/04 21:17 GMT