This is an automated email from the ASF dual-hosted git repository.

lukaszlenart pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/struts-site.git


The following commit(s) were added to refs/heads/main by this push:
     new ab95721b00 Document AliasInterceptor's @StrutsParameter authorization 
(#347)
ab95721b00 is described below

commit ab95721b00f31b480bf7b1bbfdc75fcce872edc4
Author: ⳕⲛτⲉⲅⲥⲉⳏτⲟⲅ 🕵🏻 <[email protected]>
AuthorDate: Fri Oct 9 10:13:25 2026 +0530

    Document AliasInterceptor's @StrutsParameter authorization (#347)
    
    * Document AliasInterceptor's @StrutsParameter authorization
    
    WW-5758 (apache/struts#1991) adds @StrutsParameter authorization to 
AliasInterceptor: its
    raw-request-parameter fallback follows struts.parameters.requireAnnotations 
like the Parameters
    Interceptor, and copying a value already resolved on the stack follows the 
opt-in
    struts.chaining.requireAnnotations like the Chaining Interceptor.
    
    Adds a Parameter Authorization section to the Alias Interceptor page, 
mirroring the Chaining
    Interceptor page's existing section of the same name, including the 
transitionMode note the
    review asked for (an alias target is always non-nested, so the same 
exemption applies). Adds an
    entry for the Alias Interceptor to the @StrutsParameter page's Where 
authorization applies list.
    
    Version cited as 7.5.0 to match the pattern of the two prior related fixes 
(WW-5752, WW-5753)
    and the current pom.xml SNAPSHOT; WW-5758's Fix Version is not yet set, so 
this may need updating
    once it is.
    
    * Fix factual error, contradictory wording, and review-link typo
    
    Addresses lukaszlenart's review on struts-site#347:
    
    - An alias target CAN be a nested path (an alias map value like 'bean.bar' 
is valid - nothing in
      AliasInterceptor restricts it, confirmed against the merged code). The 
page previously claimed
      'always non-nested', which is wrong; transitionMode only exempts the 
non-nested case, so a
      nested target still needs the annotation regardless of transitionMode.
    - Fixed 'always requires... governed by 
struts.parameters.requireAnnotations' - contradictory
      wording, since with the setting off nothing is required.
    - Dropped 'separately-authorized' describing a stack-resolved source value 
- it can be any state
      an earlier action holds, not necessarily something bound through an 
annotated setter.
    - Added an 'Upgrading an existing application' note: an app using the 
documented foo/bar example
      needs bar annotated once struts.parameters.requireAnnotations is enabled, 
or the alias is
      silently skipped.
    
    * Fix ModelDriven exemption claim and opt-in wording
    
    Addresses lukaszlenart's second review on struts-site#347:
    
    1. The ModelDriven exemption sentence claimed it applies unconditionally, 
which isn't true in
       defaultStack (alias runs before modelDriven there, so the model isn't on 
the stack yet - the
       check and the write both land on the action). Reworded to his exact 
suggested text: the
       exemption only applies in a custom stack that places alias after 
modelDriven.
    2. 'once struts.parameters.requireAnnotations is enabled' read as opt-in; 
it's on by default since
       7.0.0. 'silently skipped (logged at WARN)' was self-contradictory. 
Reworded to his suggested
       text.
---
 source/core-developers/alias-interceptor.md        | 42 ++++++++++++++++++++++
 .../core-developers/struts-parameter-annotation.md |  4 +++
 2 files changed, 46 insertions(+)

diff --git a/source/core-developers/alias-interceptor.md 
b/source/core-developers/alias-interceptor.md
index 1be9c17c45..6e6b38acdf 100644
--- a/source/core-developers/alias-interceptor.md
+++ b/source/core-developers/alias-interceptor.md
@@ -49,6 +49,48 @@ before `conversionError` so that a conversion failure while 
binding the aliased
 
 There is no `overwrite` flag on this interceptor; the ordering above is the 
supported way to get that behavior.
 
+## Parameter Authorization
+
+The value this interceptor copies onto the alias target can come from two 
different places, and
+each is authorized differently:
+
+- **The source name does not resolve anywhere on the value stack**, so the 
interceptor falls back
+  to the raw HTTP request parameter of that name — the behavior the 
`foo`/`bar` example above
+  relies on. This path requires 
[`@StrutsParameter`](struts-parameter-annotation.html) on the
+  target when `struts.parameters.requireAnnotations` is enabled (the default 
since Struts 7.0.0),
+  the same as the [Parameters Interceptor](parameters-interceptor.html).
+- **The source name resolves on the value stack** — typically a property an 
earlier action in a
+  chain already holds. Copying this is the same category of operation as the
+  [Chaining Interceptor](chaining-interceptor.html), so it follows the same 
opt-in constant:
+
+  ```xml
+  <constant name="struts.chaining.requireAnnotations" value="true"/>
+  ```
+
+  With this off (the default), a stack-resolved value is copied regardless of 
annotation, matching
+  this interceptor's traditional behavior. With it on, an unannotated target 
is rejected here too,
+  not just on the request-parameter fallback.
+
+In both cases a rejected target is skipped and logged at `WARN`, and 
authorization uses the same
+`ParameterAuthorizer` service the Parameters and Chaining interceptors use. 
While an application is
+migrating,
+[`struts.parameters.requireAnnotations.transitionMode=true`](../../security/#defining-and-annotating-your-action-parameters)
+exempts non-nested alias targets, the same way it exempts any other non-nested 
setter, on both paths
+above. Nested targets — an alias map value such as `'bean.bar'` is valid — 
still need the
+annotation. In a custom stack that places `alias` after `modelDriven`, a 
target on the model gets the
+same [`ModelDriven`](struts-parameter-annotation.html#modeldriven-actions) 
exemption as the Parameters
+Interceptor.
+
+See also [Where authorization 
applies](struts-parameter-annotation.html#where-authorization-applies)
+for an overview of the channels that can populate an action.
+
+### Upgrading an existing application
+
+If an application already uses this interceptor's documented pattern — the 
`foo`/`bar` example
+above — `bar` now needs [`@StrutsParameter`](struts-parameter-annotation.html) 
for the alias to
+keep working with `struts.parameters.requireAnnotations` enabled (the 
default). Without it, the
+alias is skipped and logged at `WARN` instead of setting `bar`.
+
 ## Extending the Interceptor
 
 This interceptor does not have any known extension points.
diff --git a/source/core-developers/struts-parameter-annotation.md 
b/source/core-developers/struts-parameter-annotation.md
index 8617fba2f7..58f34120f1 100644
--- a/source/core-developers/struts-parameter-annotation.md
+++ b/source/core-developers/struts-parameter-annotation.md
@@ -25,6 +25,10 @@ channel that can populate an action from request data:
   (default, governed by `struts.parameters.requireAnnotations`).
 - [Chaining Interceptor](chaining-interceptor.html) — value-stack copying 
during
   action chaining (opt-in via `struts.chaining.requireAnnotations`).
+- [Alias Interceptor](alias-interceptor.html) — its raw-request-parameter 
fallback follows
+  `struts.parameters.requireAnnotations` like the Parameters Interceptor; 
copying a value already
+  resolved on the stack follows `struts.chaining.requireAnnotations` like the 
Chaining Interceptor
+  (since Struts 7.5.0 — see [Parameter 
Authorization](alias-interceptor.html#parameter-authorization)).
 - [Cookie Interceptor](cookie-interceptor.html) — cookie values.
 - [JSON](../../plugins/json) and [REST](../../plugins/rest) plugins — 
per-property
   authorization performed during deserialization, so an unauthorized property 
is not set on

Reply via email to