Clarification Parameter.getName(?)
Alex Buckley
alex.buckley at oracle.com
Fri Jun 7 16:52:14 PDT 2013
On 6/7/2013 2:09 AM, Oliver Gierke wrote:
>> While the MethodParameters attribute can express a parameter with
>> literally no name, the Core Reflection API follows the precedent of
>> the Language Model API in SE 6 whereby every parameter is deemed to
>> have a name.
>
> Does that mean that with Java 6 you'll find parameter names no matter
> if the code was compile with debug flag or not? What about abstract
> methods - which according to the JLS - don't carry name information
> by definition?
I meant that public signatures in java.lang.reflect don't use types from
java.util. This is a longstanding policy.
I don't understand the question about abstract methods. Their parameter
names are no different than parameter names of non-abstract methods.
What section of the JLS are you referring to?
> In Spring Framework we currently use an ASM based approach to lookup
> parameter names from methods. This approach indicates the absence of
> the name information by returning null. E.g. the Spring MVC framework
> allows you to define a method like this:
>
> public String myMethod(@RequestParam Long id) { … }
>
> With our current approach, we can now discover the request parameter
> name to be id if the code was compiled with debug flag. But we can
> fail fast and ask the user to qualify his method signature to:
>
> public String myMethod(@RequestParam("id") Long id) { … }
>
> We would now like to use the new capabilities of Java 8 if the user
> is on Java 8. Unfortunately we cannot reliably find out about the
> case of missing parameter name as we'd simply get arg0 and cannot
> distinguish between missing name information and a user deliberately
> wants to do the following:
>
> public String myMethod(@RequestParam Long arg0) { … }
>
> The only heuristics we can apply is consider everything that matches
> the arg… pattern indicating a missing parameter name. This feels a
> bit like a hack. To me it feels like a good use case of
> Optional<String> (as soon as the lambda branch is in the main builds
> of course).
You need Parameter.isNamePresent() which would return false if a
parameter's name_index item in MethodParameters is zero (or if there is
no MethodParameters attribute at all). I accept that the info is there
in the class file - specifically for compilers of non-Java languages -
and that it makes sense to expose it. Let me know what you think of that.
Parameter.getName() should still generate a name when
Parameter.isNamePresent() returns false. Consistent availability of
names is helpful for some apps, and there is the precedent of the
Language Model API generating names for VariableElement#getSimpleName
since 2006. Names will get more "truthy" over time as more class files
have a MethodParameters attribute.
>>> Will parameter names be available for interface methods as well?
>>> Currently they cannot be resolved.
>>
>> Are you saying that interface methods do not have a
>> MethodParameters attribute generated when -parameters is used at
>> compile time?
>
> No, I verified the names being present with a current build already.
> I just asked explicitly as our former ASM-based approach to discover
> names for interface methods failed due to the fact the names were
> just not present even if compiled with debug flag (as required by the
> JLS).
The JLS doesn't know about debug flags. If you are talking about the
LocalVariableTable attribute in the JVMS, then the fact that it resides
in the Code attribute is a design flaw for abstract methods since their
method_info structures cannot have Code attributes. That's why the
MethodParameters attribute lives in method_info, not in the Code attribute.
(Also note that the MethodParameters attribute can reify facts about a
parameter other than its name, such as whether it's final.)
Alex
More information about the jdk8-dev
mailing list