This is an automated email from the ASF dual-hosted git repository.
oscerd pushed a commit to branch camel-4.14.x
in repository https://gitbox.apache.org/repos/asf/camel.git
The following commit(s) were added to refs/heads/camel-4.14.x by this push:
new a3d35e923122 [backport camel-4.14.x] CAMEL-23592: camel-shiro - align
Exchange header constant names with Camel naming convention (#23559)
a3d35e923122 is described below
commit a3d35e9231225149f3dd45fb6c10313d85bdf518
Author: Andrea Cosentino <[email protected]>
AuthorDate: Thu May 28 16:42:42 2026 +0200
[backport camel-4.14.x] CAMEL-23592: camel-shiro - align Exchange header
constant names with Camel naming convention (#23559)
* CAMEL-23592: camel-shiro - align Exchange header constant names with
Camel naming convention (#23506)
Renames the three Exchange header string values in ShiroSecurityConstants
that drive Shiro authentication (SHIRO_SECURITY_TOKEN,
SHIRO_SECURITY_USERNAME, SHIRO_SECURITY_PASSWORD) to
CamelShiroSecurity<Name>,
following the convention used across the rest of the Camel component catalog
and matching the pattern established in CAMEL-23526 (camel-cxf), CAMEL-23522
(camel-mail), CAMEL-23461 (camel-aws-bedrock), CAMEL-23532
(camel-vertx-websocket / camel-atmosphere-websocket / camel-iggy), and
CAMEL-23576 (camel-jira).
- SHIRO_SECURITY_TOKEN: "SHIRO_SECURITY_TOKEN" -> "CamelShiroSecurityToken"
- SHIRO_SECURITY_USERNAME: "SHIRO_SECURITY_USERNAME" ->
"CamelShiroSecurityUsername"
- SHIRO_SECURITY_PASSWORD: "SHIRO_SECURITY_PASSWORD" ->
"CamelShiroSecurityPassword"
These headers carry credentials and a serialized authentication token, so
filtering them at transport boundaries by default is particularly important.
The Java field names are unchanged so routes referencing the constants
symbolically continue to work; routes using the literal string values must
be
updated (documented in the 4.21 upgrade guide). No tests reference the
literal values, and the shiro adoc documentation references the constants
symbolically.
Tracker: CAMEL-23577
Reported by Claude Code on behalf of Andrea Cosentino
Signed-off-by: Andrea Cosentino <[email protected]>
* CAMEL-23592: camel-itest - update ShiroOverJmsTest for renamed Shiro
security headers
After CAMEL-23592 the three Shiro security header values move into the
Camel* namespace (CamelShiroSecurityToken etc.). The default
JmsHeaderFilterStrategy filters every Camel* header at the transport
boundary, which is the intended behavior for untrusted producers but
strips the serialized authentication token from trusted Shiro-over-JMS
routes that previously relied on the old non-Camel-prefixed value
surviving the JMS round-trip.
ShiroOverJmsTest is exactly such a trusted Shiro-over-JMS route and
was failing on this backport branch's CI:
mock://ShiroOverJmsTestError Received message count.
Expected: <0> but was: <1>
(the consumer-side ShiroSecurityPolicy could no longer read the token
and the message ended up at the dead-letter mock). The same regression
exists latently on main; the matching fix is in PR #23592, and PR #23552
applies it to the 4.18.x backport.
- ShiroOverJmsTest: configure a small subclass of JmsHeaderFilterStrategy
on the JMS component that opts the three Shiro security headers back in
(returns false from applyFilterToCamelHeaders /
applyFilterToExternalHeaders for those headers, delegates to super for
everything else). This is the pattern end-users will need.
- 4.14 upgrade guide: extend the camel-shiro entry to document the new
required HeaderFilterStrategy opt-in for trusted Shiro-over-transport
routes, with a worked code example mirroring the one used in the test.
Co-Authored-By: Claude Opus 4.7 (1M context) <[email protected]>
Signed-off-by: Andrea Cosentino <[email protected]>
---------
Signed-off-by: Andrea Cosentino <[email protected]>
Co-authored-by: Claude Opus 4.7 (1M context) <[email protected]>
---
.../shiro/security/ShiroSecurityConstants.java | 6 +-
.../ROOT/pages/camel-4x-upgrade-guide-4_14.adoc | 64 ++++++++++++++++++++++
.../apache/camel/itest/shiro/ShiroOverJmsTest.java | 35 ++++++++++++
3 files changed, 102 insertions(+), 3 deletions(-)
diff --git
a/components/camel-shiro/src/main/java/org/apache/camel/component/shiro/security/ShiroSecurityConstants.java
b/components/camel-shiro/src/main/java/org/apache/camel/component/shiro/security/ShiroSecurityConstants.java
index b3b30e800efa..4f8e7d21e5ad 100644
---
a/components/camel-shiro/src/main/java/org/apache/camel/component/shiro/security/ShiroSecurityConstants.java
+++
b/components/camel-shiro/src/main/java/org/apache/camel/component/shiro/security/ShiroSecurityConstants.java
@@ -21,9 +21,9 @@ package org.apache.camel.component.shiro.security;
*/
public final class ShiroSecurityConstants {
- public static final String SHIRO_SECURITY_TOKEN = "SHIRO_SECURITY_TOKEN";
- public static final String SHIRO_SECURITY_USERNAME =
"SHIRO_SECURITY_USERNAME";
- public static final String SHIRO_SECURITY_PASSWORD =
"SHIRO_SECURITY_PASSWORD";
+ public static final String SHIRO_SECURITY_TOKEN =
"CamelShiroSecurityToken";
+ public static final String SHIRO_SECURITY_USERNAME =
"CamelShiroSecurityUsername";
+ public static final String SHIRO_SECURITY_PASSWORD =
"CamelShiroSecurityPassword";
private ShiroSecurityConstants() {
}
diff --git
a/docs/user-manual/modules/ROOT/pages/camel-4x-upgrade-guide-4_14.adoc
b/docs/user-manual/modules/ROOT/pages/camel-4x-upgrade-guide-4_14.adoc
index 7e2113be5a7a..b3e3c195b2b3 100644
--- a/docs/user-manual/modules/ROOT/pages/camel-4x-upgrade-guide-4_14.adoc
+++ b/docs/user-manual/modules/ROOT/pages/camel-4x-upgrade-guide-4_14.adoc
@@ -242,6 +242,70 @@ As a consequence, the generated Endpoint DSL header
accessors on
`resultClassType()` -> `arangoDbResultClassType()`.
+=== camel-shiro - potential breaking change
+
+The three Exchange header constants in `ShiroSecurityConstants` that drive
+Shiro authentication used header values outside the `Camel` namespace
+(`SHIRO_SECURITY_TOKEN`, `SHIRO_SECURITY_USERNAME`, `SHIRO_SECURITY_PASSWORD`)
+and were therefore not filtered by the default `HeaderFilterStrategy`. They
+have been renamed to follow the Camel naming convention. The Java field names
+are unchanged; only the header string values have changed:
+
+[options="header"]
+|===
+| Constant | Previous value | New value
+| `ShiroSecurityConstants.SHIRO_SECURITY_TOKEN` | `SHIRO_SECURITY_TOKEN` |
`CamelShiroSecurityToken`
+| `ShiroSecurityConstants.SHIRO_SECURITY_USERNAME` | `SHIRO_SECURITY_USERNAME`
| `CamelShiroSecurityUsername`
+| `ShiroSecurityConstants.SHIRO_SECURITY_PASSWORD` | `SHIRO_SECURITY_PASSWORD`
| `CamelShiroSecurityPassword`
+|===
+
+These headers carry credentials and a serialized authentication token, so
+filtering them at transport boundaries by default is particularly important.
+
+Routes that reference the constants symbolically (for example
+`setHeader(ShiroSecurityConstants.SHIRO_SECURITY_USERNAME, ...)`) continue to
+work without changes. Routes that set the header by its literal string value
+(for example `setHeader("SHIRO_SECURITY_USERNAME", ...)`) must be updated to
+use the new value (`setHeader("CamelShiroSecurityUsername", ...)`).
+
+Because the three header values are now in the `Camel*` namespace, transports
+that filter Camel-internal headers by default (JMS, CXF, HTTP, etc.) will
+strip the serialized Shiro authentication token before publishing. This is
+the intended behavior for untrusted producers. Trusted Shiro-over-transport
+routes that previously relied on the token surviving the boundary must opt
+those three headers back in via a custom `HeaderFilterStrategy`, for example:
+
+[source,java]
+----
+public class ShiroFriendlyJmsHeaderFilterStrategy extends
JmsHeaderFilterStrategy {
+ @Override
+ public boolean applyFilterToCamelHeaders(String name, Object value,
Exchange ex) {
+ if (isShiroSecurityHeader(name)) {
+ return false;
+ }
+ return super.applyFilterToCamelHeaders(name, value, ex);
+ }
+
+ @Override
+ public boolean applyFilterToExternalHeaders(String name, Object value,
Exchange ex) {
+ if (isShiroSecurityHeader(name)) {
+ return false;
+ }
+ return super.applyFilterToExternalHeaders(name, value, ex);
+ }
+
+ private static boolean isShiroSecurityHeader(String name) {
+ return
ShiroSecurityConstants.SHIRO_SECURITY_TOKEN.equalsIgnoreCase(name)
+ ||
ShiroSecurityConstants.SHIRO_SECURITY_USERNAME.equalsIgnoreCase(name)
+ ||
ShiroSecurityConstants.SHIRO_SECURITY_PASSWORD.equalsIgnoreCase(name);
+ }
+}
+
+jmsComponent.setHeaderFilterStrategy(new
ShiroFriendlyJmsHeaderFilterStrategy());
+----
+
+A worked example is in `ShiroOverJmsTest` in the `camel-itest` module.
+
== Upgrading from 4.14.5 to 4.14.6
=== camel-platform-http-main
diff --git
a/tests/camel-itest/src/test/java/org/apache/camel/itest/shiro/ShiroOverJmsTest.java
b/tests/camel-itest/src/test/java/org/apache/camel/itest/shiro/ShiroOverJmsTest.java
index ccd5e8b2661f..5a702f8e9da8 100644
---
a/tests/camel-itest/src/test/java/org/apache/camel/itest/shiro/ShiroOverJmsTest.java
+++
b/tests/camel-itest/src/test/java/org/apache/camel/itest/shiro/ShiroOverJmsTest.java
@@ -19,8 +19,10 @@ package org.apache.camel.itest.shiro;
import java.util.HashMap;
import java.util.Map;
+import org.apache.camel.Exchange;
import org.apache.camel.builder.RouteBuilder;
import org.apache.camel.component.jms.JmsComponent;
+import org.apache.camel.component.jms.JmsHeaderFilterStrategy;
import org.apache.camel.component.mock.MockEndpoint;
import org.apache.camel.component.shiro.security.ShiroSecurityConstants;
import org.apache.camel.component.shiro.security.ShiroSecurityPolicy;
@@ -61,9 +63,42 @@ public class ShiroOverJmsTest extends CamelTestSupport {
amq.setCamelContext(context);
+ // After CAMEL-23592 the Shiro security headers live in the
CamelShiroSecurity* namespace,
+ // which the default JmsHeaderFilterStrategy filters at the transport
boundary. For a
+ // trusted Shiro-over-JMS route, the operator must opt those three
headers back in.
+ amq.setHeaderFilterStrategy(new
ShiroFriendlyJmsHeaderFilterStrategy());
+
registry.bind("jms", amq);
}
+ /**
+ * Allows the three Shiro security headers (token, username, password) to
cross the JMS transport boundary while
+ * still filtering every other Camel-internal header.
+ */
+ private static final class ShiroFriendlyJmsHeaderFilterStrategy extends
JmsHeaderFilterStrategy {
+ @Override
+ public boolean applyFilterToCamelHeaders(String headerName, Object
headerValue, Exchange exchange) {
+ if (isShiroSecurityHeader(headerName)) {
+ return false;
+ }
+ return super.applyFilterToCamelHeaders(headerName, headerValue,
exchange);
+ }
+
+ @Override
+ public boolean applyFilterToExternalHeaders(String headerName, Object
headerValue, Exchange exchange) {
+ if (isShiroSecurityHeader(headerName)) {
+ return false;
+ }
+ return super.applyFilterToExternalHeaders(headerName, headerValue,
exchange);
+ }
+
+ private static boolean isShiroSecurityHeader(String headerName) {
+ return
ShiroSecurityConstants.SHIRO_SECURITY_TOKEN.equalsIgnoreCase(headerName)
+ ||
ShiroSecurityConstants.SHIRO_SECURITY_USERNAME.equalsIgnoreCase(headerName)
+ ||
ShiroSecurityConstants.SHIRO_SECURITY_PASSWORD.equalsIgnoreCase(headerName);
+ }
+ }
+
@Override
protected RouteBuilder createRouteBuilder() {
return new RouteBuilder() {