This is an automated email from the ASF dual-hosted git repository.
davsclaus pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/camel.git
The following commit(s) were added to refs/heads/main by this push:
new 01d97c3dd31f CAMEL-24910: camel-platform-http-vertx - a path parameter
wins over an incoming header of the same name (#26751)
01d97c3dd31f is described below
commit 01d97c3dd31fa321e55c1b3974f49cf74fc649c3
Author: Claus Ibsen <[email protected]>
AuthorDate: Wed Sep 23 10:28:33 2026 +0200
CAMEL-24910: camel-platform-http-vertx - a path parameter wins over an
incoming header of the same name (#26751)
A path parameter is what the request says it is: it now replaces an
incoming header of the same name instead of appending to it, so /stock/{sku} is
not read as a list when the caller also sent a sku header.
---
.../http/vertx/VertxPlatformHttpSupport.java | 6 ++-
.../http/vertx/VertxPlatformHttpEngineTest.java | 46 ++++++++++++++++++++++
.../ROOT/pages/camel-4x-upgrade-guide-4_23.adoc | 7 ++++
3 files changed, 57 insertions(+), 2 deletions(-)
diff --git
a/components/camel-platform-http-vertx/src/main/java/org/apache/camel/component/platform/http/vertx/VertxPlatformHttpSupport.java
b/components/camel-platform-http-vertx/src/main/java/org/apache/camel/component/platform/http/vertx/VertxPlatformHttpSupport.java
index 43fd2903069b..80226cc58244 100644
---
a/components/camel-platform-http-vertx/src/main/java/org/apache/camel/component/platform/http/vertx/VertxPlatformHttpSupport.java
+++
b/components/camel-platform-http-vertx/src/main/java/org/apache/camel/component/platform/http/vertx/VertxPlatformHttpSupport.java
@@ -274,9 +274,11 @@ public final class VertxPlatformHttpSupport {
applyHeaderFilterStrategy(ctx, headersMap, exchange,
headerFilterStrategy, request);
}
- // Path parameters
+ // Path parameters: the value from the path wins over an incoming
header of that name. A path parameter is
+ // single-valued and part of the route's contract, so appending would
turn ${header.sku} into a list and a
+ // correct value would fail (CAMEL-24910); a query parameter may
repeat and is still appended.
for (Map.Entry<String, String> en : ctx.pathParams().entrySet()) {
- appendEntry(headersMap, en.getKey(), en.getValue());
+ headersMap.put(en.getKey(), en.getValue());
}
SocketAddress localAddress = request.localAddress();
diff --git
a/components/camel-platform-http-vertx/src/test/java/org/apache/camel/component/platform/http/vertx/VertxPlatformHttpEngineTest.java
b/components/camel-platform-http-vertx/src/test/java/org/apache/camel/component/platform/http/vertx/VertxPlatformHttpEngineTest.java
index d81479098864..cb54cbc6bd5e 100644
---
a/components/camel-platform-http-vertx/src/test/java/org/apache/camel/component/platform/http/vertx/VertxPlatformHttpEngineTest.java
+++
b/components/camel-platform-http-vertx/src/test/java/org/apache/camel/component/platform/http/vertx/VertxPlatformHttpEngineTest.java
@@ -503,6 +503,52 @@ public class VertxPlatformHttpEngineTest {
}
}
+ /**
+ * CAMEL-24910: a path parameter is single-valued and part of the route's
contract, so it wins over an incoming
+ * header of the same name; before, the two were merged into a list and
${header.name} answered "[X, Camel]".
+ */
+ @Test
+ public void testPathParameterWinsOverAHeaderOfTheSameName() throws
Exception {
+ final CamelContext context = createCamelContextForTest();
+ try {
+ context.addRoutes(new RouteBuilder() {
+ @Override
+ public void configure() {
+ from("platform-http:/greeting/{name}")
+ .transform().simple("Hello ${header.name}");
+ }
+ });
+
+ context.start();
+
+ given()
+ .when()
+ .get("/greeting/Camel")
+ .then()
+ .statusCode(200)
+ .body(equalTo("Hello Camel"));
+
+ // the same request with a header of that name: the path still
decides
+ given()
+ .header("name", "Rider")
+ .when()
+ .get("/greeting/Camel")
+ .then()
+ .statusCode(200)
+ .body(equalTo("Hello Camel"));
+
+ // and a query parameter may still repeat, which is a list
+ given()
+ .when()
+ .get("/greeting/Camel?other=a&other=b")
+ .then()
+ .statusCode(200)
+ .body(equalTo("Hello Camel"));
+ } finally {
+ context.stop();
+ }
+ }
+
@Test
public void testMatchOnUriPrefix() throws Exception {
final CamelContext context = createCamelContextForTest();
diff --git
a/docs/user-manual/modules/ROOT/pages/camel-4x-upgrade-guide-4_23.adoc
b/docs/user-manual/modules/ROOT/pages/camel-4x-upgrade-guide-4_23.adoc
index be1c20b5d9c4..586085c0b156 100644
--- a/docs/user-manual/modules/ROOT/pages/camel-4x-upgrade-guide-4_23.adoc
+++ b/docs/user-manual/modules/ROOT/pages/camel-4x-upgrade-guide-4_23.adoc
@@ -2330,6 +2330,13 @@ A name without a scheme, `resource:orderTemplate.json`,
is a classpath resource.
value and is not evaluated again. Nothing changes without the option: the
`resource:` prefix on the expression
text itself is resolved as before, and a returned value that happens to start
with `resource:` stays as it is.
+=== camel-platform-http-vertx - a path parameter wins over an incoming header
of the same name
+
+A REST endpoint with a path parameter, `/stock/{sku}`, sets the header `sku`
from the path. When the request also
+carried an HTTP header of that name, the two were merged and `${header.sku}`
was a `List` such as `[X, CAMEL-MUG]`,
+so a route that read it failed even when the path value was correct. The value
from the path is used now; a query
+parameter may still repeat and is still collected into a list.
+
=== camel-core - the required attribute on rest param and route template
parameter is now a String
`ParamDefinition.required` (the rest DSL `param`) and
`RouteTemplateParameterDefinition.required`