Just for fun I set up a little test app. It demonstrates that the bug is definitely in Common Beanutils. Normal Java relfection can call a method derived from a protected nested class without problems. The problem seems to be in o/a/c/b/MethodUtils.java : line 442ish where Beanutils checks the declaring class to see if its public - it should probably check the derived class instead ie clazz = method.getClass()
-----MethodUtils.java - getAccessibleMethod(Method method) ---------
// If the requested method is not public we cannot call it if (!Modifier.isPublic(method.getModifiers())) { return (null); }
// If the declaring class is public, we are done Class clazz = method.getDeclaringClass(); if (Modifier.isPublic(clazz.getModifiers())) { return (method); }
----End------------------------------------------------------------------
As far as your problem goes the simplest fix seems to be write a public getName() method in Area and in its implementation call super.getName().
The alternative is to fix Beanutils (I haven't checked bugzilla so this might even be a recently fixed bug). I'm cross-posting this to commons-dev to confirm that it is a bug since I may look at it a bit furthere and write a patch next week if I have the time.
Paul- Hope this helps Alan - Hope this is of interest
Gareth.
PS. I've also appended a quick test app I wrote
------scratchpad.java ------------------------------
public class scratchpad {
public static void main(String[] args) throws Exception{
publicNestedClass test = new publicNestedClass();
//Works - nested inheritance works ok
//System.out.println(test.getMessage());
//Doesn't work PropertyUtils bug
//System.out.println((String)PropertyUtils.getProperty(test, "message"));
Class c = publicNestedClass.class;
Method m = c.getMethod("getMessage", null);
if(m!=null){
System.out.println("Method " + m.getName() + " of " + m.getDeclaringClass() + " found.");
System.out.println("Method " + (Modifier.isPublic(m.getModifiers()) ? "is" : "isn't") + " public");
System.out.println("Class " + (Modifier.isPublic(m.getClass().getModifiers()) ? "is" : "isn't") + " public");
System.out.println("Declaring Class " + (Modifier.isPublic(m.getDeclaringClass().getModifiers()) ? "is" : "isn't") + " public");
}
System.out.println((String)m.invoke(test, null));
}
protected static class protectedNestedClass {
public String getMessage(){
return "Hello from a protected nested class";
}
}
public static class publicNestedClass extends protectedNestedClass{
}
}
-------------------------------------------------------------------------------------------
Paul Harrison wrote:
thanks for confirming that this should work - one fact that I omitted in my original mailing was that the classes were inner classes
i.e. it was the PostCode.Area class that is in the collection
public class PostCode { protected static class Pbase { protected String name;
public String getName() { return name; }
} public static class Area extends Pbase { } }
I works it I change the access on the Pbase class to public, but do I have to ? I thought that it was legal to have derived classes increase the accessibility - I do not want to expose the Pbase class.... - however this is pushing the limits of my knowledge about what should be happening.....
Alen Ribic wrote:
I'm doing the same thing in my current project successfully. No problems in my specializes class.
e.g.
public abstract class BaseBusinessBean implements java.io.Serializable { protected int id; protected String description;
// getters/setters here }
e.g.
public class Category extends BaseBusinessBean { // Category specific getters/setters }
Now I use Category class with no problem in my options for select box.
You have code <snippet>?
--Alen
----- Original Message ----- From: "Paul Harrison" <[EMAIL PROTECTED]> To: "Struts Users Mailing List" <[EMAIL PROTECTED]> Sent: Wednesday, June 18, 2003 4:55 PM Subject: Problems with an inherited getter in a derived bean
In my struts application, I have a base bean with a set of basic
properties (e.g. name) and then I create various derived beans with
their own extra properties. I have a problem with the <html:options> tag
in that if I try to read a property that is inherited from the base
bean from a collection of the derived beans
i.e. I have a tag like this
<html:options collection="CountyList" property="name" />
- I get an error saying
No getter method available for property name for bean under name
CountyList
and if I implement the getter in the derived bean the error goes away. Is this known behaviour in struts - is seems like a bug to me (or perhaps a bug in commons-beanutils?) Can anyone comment....
-- Paul Harrison
[EMAIL PROTECTED]
--------------------------------------------------------------------- To unsubscribe, e-mail: [EMAIL PROTECTED] For additional commands, e-mail: [EMAIL PROTECTED]
--------------------------------------------------------------------- To unsubscribe, e-mail: [EMAIL PROTECTED] For additional commands, e-mail: [EMAIL PROTECTED]
--------------------------------------------------------------------- To unsubscribe, e-mail: [EMAIL PROTECTED] For additional commands, e-mail: [EMAIL PROTECTED]