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

davsclaus pushed a commit to branch camel-4.22.x
in repository https://gitbox.apache.org/repos/asf/camel.git


The following commit(s) were added to refs/heads/camel-4.22.x by this push:
     new 88066606db1a [backport camel-4.22.x] CAMEL-26485: camel-netty-http - 
endpoint options are no longer sent to the server as query parameters (#29768)
88066606db1a is described below

commit 88066606db1ab5038dc4f6e3ff2029e7334c6d78
Author: Claus Ibsen <[email protected]>
AuthorDate: Fri Nov 13 08:01:15 2026 +0100

    [backport camel-4.22.x] CAMEL-26485: camel-netty-http - endpoint options 
are no longer sent to the server as query parameters (#29768)
    
    Backport of #29731 onto camel-4.22.x. Endpoint options of netty-http are no
    longer sent to the server as query parameters. Adapted: on this branch the
    endpoint is created with the full URI, and once the options are bound its
    endpoint URI is set to the address through a new package-private
    NettyHttpEndpoint.setAddressUri. The upgrade-guide note is on main (#29765).
    
    Co-Authored-By: Claude Opus 5.5 <[email protected]>
---
 .../component/netty/http/NettyHttpComponent.java   |  15 +--
 .../component/netty/http/NettyHttpEndpoint.java    |   8 ++
 .../NettyHttpEndpointOptionsNotInQueryTest.java    | 110 +++++++++++++++++++++
 3 files changed, 126 insertions(+), 7 deletions(-)

diff --git 
a/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/NettyHttpComponent.java
 
b/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/NettyHttpComponent.java
index 0e284bfddded..d067e95efb05 100644
--- 
a/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/NettyHttpComponent.java
+++ 
b/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/NettyHttpComponent.java
@@ -175,18 +175,19 @@ public class NettyHttpComponent extends NettyComponent
         // validate config
         config.validateConfiguration();
 
-        // create the address uri which includes the remainder parameters 
(which
-        // is not configuration parameters for this component)
-        URI u = new URI(UnsafeUriCharactersEncoder.encodeHttpURI(remaining));
-
-        String addressUri = URISupport.createRemainingURI(u, 
parameters).toString();
-
-        NettyHttpEndpoint answer = new NettyHttpEndpoint(addressUri, this, 
config);
+        // the endpoint uri is the http address to call: it is set below, once 
the endpoint options are bound
+        NettyHttpEndpoint answer = new NettyHttpEndpoint(uri, this, config);
         // endpoints that differ only in their options must not be equal, so 
the full uri is the identity
         answer.setIdentityUri(uri);
         answer.getConfiguration().setMuteException(muteException);
         setProperties(answer, parameters);
 
+        // create the address uri with the remainder parameters, after the 
endpoint options are bound
+        // (and removed), so only the query parameters that are not endpoint 
options are sent to the server
+        URI u = new URI(UnsafeUriCharactersEncoder.encodeHttpURI(remaining));
+        String addressUri = URISupport.createRemainingURI(u, 
parameters).toString();
+        answer.setAddressUri(addressUri);
+
         // must use a copy of the binding on the endpoint to avoid sharing same
         // instance that can cause side-effects
         if (answer.getNettyHttpBinding() == null) {
diff --git 
a/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/NettyHttpEndpoint.java
 
b/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/NettyHttpEndpoint.java
index b007ac75727b..27a65b6dd59b 100644
--- 
a/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/NettyHttpEndpoint.java
+++ 
b/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/NettyHttpEndpoint.java
@@ -322,6 +322,14 @@ public class NettyHttpEndpoint extends NettyEndpoint 
implements HeaderFilterStra
         this.identityUri = identityUri;
     }
 
+    /**
+     * The http address to call, which is the endpoint uri: the uri without 
the endpoint options, which are bound when
+     * the endpoint is created (CAMEL-26485).
+     */
+    void setAddressUri(String addressUri) {
+        setEndpointUri(addressUri);
+    }
+
     private String getIdentityUri() {
         return identityUri != null ? identityUri : getEndpointUri();
     }
diff --git 
a/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/NettyHttpEndpointOptionsNotInQueryTest.java
 
b/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/NettyHttpEndpointOptionsNotInQueryTest.java
new file mode 100644
index 000000000000..048f2a8cf483
--- /dev/null
+++ 
b/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/NettyHttpEndpointOptionsNotInQueryTest.java
@@ -0,0 +1,110 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.camel.component.netty.http;
+
+import java.util.List;
+import java.util.Set;
+import java.util.stream.Collectors;
+
+import org.apache.camel.BindToRegistry;
+import org.apache.camel.Exchange;
+import org.apache.camel.builder.RouteBuilder;
+import org.apache.camel.http.base.cookie.InstanceCookieHandler;
+import org.apache.camel.support.DefaultExchange;
+import org.junit.jupiter.api.Test;
+
+import static org.junit.jupiter.api.Assertions.assertEquals;
+import static org.junit.jupiter.api.Assertions.assertNotEquals;
+import static org.junit.jupiter.api.Assertions.assertSame;
+
+public class NettyHttpEndpointOptionsNotInQueryTest extends 
BaseNettyTestSupport {
+
+    @BindToRegistry("myCookieHandler")
+    private final InstanceCookieHandler cookieHandler = new 
InstanceCookieHandler();
+
+    @Test
+    public void testEndpointOptionsAreNotSentAsQueryParameters() {
+        String uri = 
"netty-http:http://localhost:{{port}}/echo?bar=1&cookieHandler=#myCookieHandler";
+                     + 
"&httpMethodRestrict=GET&traceEnabled=false&exchangePattern=InOut&lazyStartProducer=true"
+                     + "&throwExceptionOnFailure=true";
+
+        NettyHttpEndpoint endpoint = context.getEndpoint(uri, 
NettyHttpEndpoint.class);
+        // the options are bound to the endpoint
+        assertSame(cookieHandler, endpoint.getCookieHandler());
+        assertEquals("GET", endpoint.getHttpMethodRestrict());
+
+        // and only the query parameter that is not an endpoint option is in 
the address
+        assertEquals("http://localhost:"; + getPort() + "/echo?bar=1",
+                NettyHttpHelper.createURL(new DefaultExchange(context), 
endpoint));
+
+        String query = template.requestBody(uri, null, String.class);
+        assertEquals("bar=1", query);
+    }
+
+    @Test
+    public void testOnlyEndpointOptions() {
+        String query = template.requestBody(
+                
"netty-http:http://localhost:{{port}}/echo?cookieHandler=#myCookieHandler&httpMethodRestrict=GET";,
 null,
+                String.class);
+        // no query parameters at all
+        assertEquals("none", query);
+    }
+
+    @Test
+    public void testConsumersDifferingOnlyInHttpMethodRestrict() {
+        List<NettyHttpEndpoint> endpoints = context.getEndpoints().stream()
+                .filter(NettyHttpEndpoint.class::isInstance)
+                .map(NettyHttpEndpoint.class::cast)
+                .filter(e -> e.getConfiguration().getPath().equals("/orders"))
+                .toList();
+        // the rest consumers for GET and POST on the same path differ only in 
httpMethodRestrict
+        assertEquals(2, endpoints.size());
+        assertNotEquals(endpoints.get(0), endpoints.get(1));
+        assertEquals(Set.of("GET", "POST"),
+                
endpoints.stream().map(NettyHttpEndpoint::getHttpMethodRestrict).collect(Collectors.toSet()));
+
+        String out = 
template.requestBodyAndHeader("netty-http:http://localhost:{{port}}/orders";, 
null,
+                Exchange.HTTP_METHOD, "GET", String.class);
+        assertEquals("get", out);
+        out = 
template.requestBodyAndHeader("netty-http:http://localhost:{{port}}/orders";, 
"Hello",
+                Exchange.HTTP_METHOD, "POST", String.class);
+        assertEquals("post", out);
+    }
+
+    @Override
+    protected RouteBuilder createRouteBuilder() {
+        return new RouteBuilder() {
+            @Override
+            public void configure() {
+                from("netty-http:http://localhost:{{port}}/echo";)
+                        .process(e -> {
+                            String query = 
e.getIn().getHeader(Exchange.HTTP_QUERY, String.class);
+                            e.getMessage().setBody(query != null ? query : 
"none");
+                        });
+
+                
restConfiguration().component("netty-http").host("localhost").port(getPort());
+
+                rest("/orders")
+                        .get().to("direct:get")
+                        .post().to("direct:post");
+
+                from("direct:get").transform().constant("get");
+                from("direct:post").transform().constant("post");
+            }
+        };
+    }
+}

Reply via email to