[ 
https://issues.apache.org/jira/browse/WW-5771?page=com.atlassian.jira.plugin.system.issuetabpanels:all-tabpanel
 ]

Lukasz Lenart updated WW-5771:
------------------------------
    Fix Version/s: 7.5.0

> StrutsParameterAuthorizer only matches naively capitalized setters, rejecting 
> annotated JavaBeans-compliant setters like seteMail
> ---------------------------------------------------------------------------------------------------------------------------------
>
>                 Key: WW-5771
>                 URL: https://issues.apache.org/jira/browse/WW-5771
>             Project: Struts 2
>          Issue Type: Bug
>          Components: Core Interceptors
>    Affects Versions: 7.4.0
>            Reporter: Niklas Neesen
>            Priority: Major
>             Fix For: 7.5.0
>
>
> Since 7.4.0, {{StrutsParameterAuthorizer.findBindableAccessor}} resolves the 
> setter for a depth-0 parameter by building the name itself:
> {code:java}
> String setterName = "set" + Character.toUpperCase(property.charAt(0)) + 
> property.substring(1);
> {code}
> For a property whose name starts with a lowercase letter followed by an 
> uppercase letter (e.g. {{eMail}}), this only finds the naively capitalized 
> {{setEMail}}. Per the JavaBeans specification (the inverse of 
> {{Introspector.decapitalize}}), the accessor for property {{eMail}} is 
> {{seteMail}} — which is what 7.3.0 found via 
> {{PropertyDescriptor#getWriteMethod}} and what developers annotated with 
> {{@StrutsParameter}}.
> The result: an action with a correctly annotated, spec-compliant setter
> {code:java}
> private String eMail;
> @StrutsParameter
> public void seteMail(String eMail) { this.eMail = eMail; }
> {code}
> passes authorization on 7.3.0 but is rejected on 7.4.0 — the parameter is 
> silently dropped (in production mode nothing is logged above debug level), 
> the field stays null, and the regression surfaces only as downstream 
> application errors.
> The Javadoc on {{findBindableAccessor}} says the setter is "matched the way 
> OGNL matches it". That was true for OGNL 3.4.0-3.4.13, which had exactly this 
> naive-capitalization bug — but it was fixed in OGNL 3.4.14 
> ([https://github.com/orphan-oss/ognl/issues/643], 
> [https://github.com/orphan-oss/ognl/pull/644]): OGNL now resolves both base 
> names, spec-compliant first. So on current Struts 7.4.0 + OGNL 3.4.14+, the 
> authorizer and the binder it guards disagree in both directions:
> * The authorizer inspects {{setEMail}} (and requires the annotation there), 
> while OGNL binds through {{seteMail}}.
> * An annotation on the spec-compliant setter — the method OGNL actually 
> invokes — is invisible to the authorizer.
> h3. Standalone reproducer
> Only struts2-core and ognl on the classpath:
> {code:java}
> public class Repro {
>     public static class SpecCompliantAction {
>         private String eMail;
>         @StrutsParameter
>         public void seteMail(String v) { this.eMail = v; }
>     }
>     public static void main(String[] args) {
>         StrutsParameterAuthorizer auth = new StrutsParameterAuthorizer();
>         auth.setRequireAnnotations("true");
>         auth.setOgnlUtil(/* OgnlUtil with default caches */);
>         auth.setProxyService(/* no-op ProxyService */);
>         SpecCompliantAction a = new SpecCompliantAction();
>         // 7.3.0: true — 7.4.0: false
>         System.out.println(auth.isAuthorized("eMail", a, a));
>     }
> }
> {code}
> Observed matrix:
> || ||annotated {{seteMail}} only||annotated {{seteMail}} + annotated alias 
> {{setEMail}}||
> ||7.3.0|authorized|authorized|
> ||7.4.0|*rejected*|authorized|
> h3. Suggested fix
> Derive the candidate base names the same way OGNL >= 3.4.14 does 
> ({{OgnlRuntime.accessorBaseNames}}): for a lowercase-then-uppercase property 
> name, look up both {{set<property>}} and {{set<Capitalized property>}}, 
> spec-compliant name first, and accept an annotation on whichever method 
> qualifies. The same applies to the getter lookup for nested parameters if it 
> ever moves away from {{PropertyDescriptor}}s.
> Found while upgrading 7.3.0 → 7.4.0: parameters bound to properties of this 
> naming pattern were silently dropped despite annotated, spec-compliant 
> setters, and only annotating a naively capitalized alias setter restores them.



--
This message was sent by Atlassian Jira
(v8.20.10#820010)

Reply via email to