Repository: camel Updated Branches: refs/heads/camel-2.16.x 5564ac9ed -> 2a66cb220 refs/heads/master 149648b20 -> 72626b572
CAMEL-9382: netty http should be more friendly in the hostname and support default http as protocol. And whether people include double slashes or not. Project: http://git-wip-us.apache.org/repos/asf/camel/repo Commit: http://git-wip-us.apache.org/repos/asf/camel/commit/72626b57 Tree: http://git-wip-us.apache.org/repos/asf/camel/tree/72626b57 Diff: http://git-wip-us.apache.org/repos/asf/camel/diff/72626b57 Branch: refs/heads/master Commit: 72626b57258ed224486fe4af6caa18fbbbb7313f Parents: 149648b Author: Claus Ibsen <davscl...@apache.org> Authored: Thu Dec 10 16:22:49 2015 +0100 Committer: Claus Ibsen <davscl...@apache.org> Committed: Thu Dec 10 16:22:49 2015 +0100 ---------------------------------------------------------------------- .../netty/http/NettyHttpComponent.java | 26 ++++++++-- .../netty/http/NettyDefaultProtocolTest.java | 54 ++++++++++++++++++++ .../http/NettyHttpProtocolNoSlashTest.java | 54 ++++++++++++++++++++ .../netty4/http/NettyHttpComponent.java | 30 ++++++++--- .../netty4/http/NettyDefaultProtocolTest.java | 53 +++++++++++++++++++ .../http/NettyHttpProtocolNoSlashTest.java | 54 ++++++++++++++++++++ 6 files changed, 261 insertions(+), 10 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/camel/blob/72626b57/components/camel-netty-http/src/main/java/org/apache/camel/component/netty/http/NettyHttpComponent.java ---------------------------------------------------------------------- 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 f551b20..8bc0aea 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 @@ -100,15 +100,31 @@ public class NettyHttpComponent extends NettyComponent implements HeaderFilterSt sharedPort = shared.getPort(); } - // configure configuration - config = parseConfiguration(config, remaining, parameters); + // we must include the protocol in the remaining + boolean hasProtocol = remaining.startsWith("http://") || remaining.startsWith("http:") + || remaining.startsWith("https://") || remaining.startsWith("https:"); + if (!hasProtocol) { + // http is the default protocol + remaining = "http://" + remaining; + } + boolean hasSlash = remaining.startsWith("http://") || remaining.startsWith("https://"); + if (!hasSlash) { + // must have double slash after protocol + if (remaining.startsWith("http:")) { + remaining = "http://" + remaining.substring(5); + } else { + remaining = "https://" + remaining.substring(6); + } + } + LOG.debug("Netty http url: {}", remaining); + // set port on configuration which is either shared or using default values if (sharedPort != -1) { config.setPort(sharedPort); } else if (config.getPort() == -1) { - if ("http".equals(config.getProtocol())) { + if (remaining.startsWith("http:")) { config.setPort(80); - } else if ("https".equals(config.getProtocol())) { + } else if (remaining.startsWith("https:")) { config.setPort(443); } } @@ -116,6 +132,8 @@ public class NettyHttpComponent extends NettyComponent implements HeaderFilterSt throw new IllegalArgumentException("Port number must be configured"); } + // configure configuration + config = parseConfiguration(config, remaining, parameters); setProperties(config, parameters); // validate config http://git-wip-us.apache.org/repos/asf/camel/blob/72626b57/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/NettyDefaultProtocolTest.java ---------------------------------------------------------------------- diff --git a/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/NettyDefaultProtocolTest.java b/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/NettyDefaultProtocolTest.java new file mode 100644 index 0000000..4160538 --- /dev/null +++ b/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/NettyDefaultProtocolTest.java @@ -0,0 +1,54 @@ +/** + * 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 org.apache.camel.Exchange; +import org.apache.camel.builder.RouteBuilder; +import org.junit.Test; + +public class NettyDefaultProtocolTest extends BaseNettyTest { + + @Test + public void testDefaultProtocol() throws Exception { + getMockEndpoint("mock:input").expectedBodiesReceived("Hello World"); + getMockEndpoint("mock:input").expectedHeaderReceived("beer", "yes"); + getMockEndpoint("mock:input").expectedHeaderReceived("host", "localhost:" + getPort()); + getMockEndpoint("mock:input").expectedHeaderReceived(Exchange.HTTP_METHOD, "POST"); + getMockEndpoint("mock:input").expectedHeaderReceived(Exchange.HTTP_URL, "http://localhost:" + getPort() + "/foo"); + getMockEndpoint("mock:input").expectedHeaderReceived(Exchange.HTTP_URI, "/foo"); + getMockEndpoint("mock:input").expectedHeaderReceived(Exchange.HTTP_QUERY, "beer=yes"); + getMockEndpoint("mock:input").expectedHeaderReceived(Exchange.HTTP_PATH, ""); + + String out = template.requestBody("netty-http:localhost:{{port}}/foo?beer=yes", "Hello World", String.class); + assertEquals("Bye World", out); + + assertMockEndpointsSatisfied(); + } + + @Override + protected RouteBuilder createRouteBuilder() throws Exception { + return new RouteBuilder() { + @Override + public void configure() throws Exception { + from("netty-http:0.0.0.0:{{port}}/foo") + .to("mock:input") + .transform().constant("Bye World"); + } + }; + } + +} http://git-wip-us.apache.org/repos/asf/camel/blob/72626b57/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/NettyHttpProtocolNoSlashTest.java ---------------------------------------------------------------------- diff --git a/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/NettyHttpProtocolNoSlashTest.java b/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/NettyHttpProtocolNoSlashTest.java new file mode 100644 index 0000000..f498423 --- /dev/null +++ b/components/camel-netty-http/src/test/java/org/apache/camel/component/netty/http/NettyHttpProtocolNoSlashTest.java @@ -0,0 +1,54 @@ +/** + * 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 org.apache.camel.Exchange; +import org.apache.camel.builder.RouteBuilder; +import org.junit.Test; + +public class NettyHttpProtocolNoSlashTest extends BaseNettyTest { + + @Test + public void testHttpProtocolNoSlash() throws Exception { + getMockEndpoint("mock:input").expectedBodiesReceived("Hello World"); + getMockEndpoint("mock:input").expectedHeaderReceived("beer", "yes"); + getMockEndpoint("mock:input").expectedHeaderReceived("host", "localhost:" + getPort()); + getMockEndpoint("mock:input").expectedHeaderReceived(Exchange.HTTP_METHOD, "POST"); + getMockEndpoint("mock:input").expectedHeaderReceived(Exchange.HTTP_URL, "http://localhost:" + getPort() + "/foo"); + getMockEndpoint("mock:input").expectedHeaderReceived(Exchange.HTTP_URI, "/foo"); + getMockEndpoint("mock:input").expectedHeaderReceived(Exchange.HTTP_QUERY, "beer=yes"); + getMockEndpoint("mock:input").expectedHeaderReceived(Exchange.HTTP_PATH, ""); + + String out = template.requestBody("netty-http:http:localhost:{{port}}/foo?beer=yes", "Hello World", String.class); + assertEquals("Bye World", out); + + assertMockEndpointsSatisfied(); + } + + @Override + protected RouteBuilder createRouteBuilder() throws Exception { + return new RouteBuilder() { + @Override + public void configure() throws Exception { + from("netty-http:http:0.0.0.0:{{port}}/foo") + .to("mock:input") + .transform().constant("Bye World"); + } + }; + } + +} http://git-wip-us.apache.org/repos/asf/camel/blob/72626b57/components/camel-netty4-http/src/main/java/org/apache/camel/component/netty4/http/NettyHttpComponent.java ---------------------------------------------------------------------- diff --git a/components/camel-netty4-http/src/main/java/org/apache/camel/component/netty4/http/NettyHttpComponent.java b/components/camel-netty4-http/src/main/java/org/apache/camel/component/netty4/http/NettyHttpComponent.java index 775943b..42e4792 100644 --- a/components/camel-netty4-http/src/main/java/org/apache/camel/component/netty4/http/NettyHttpComponent.java +++ b/components/camel-netty4-http/src/main/java/org/apache/camel/component/netty4/http/NettyHttpComponent.java @@ -91,6 +91,8 @@ public class NettyHttpComponent extends NettyComponent implements HeaderFilterSt NettyHttpSecurityConfiguration securityConfiguration = resolveAndRemoveReferenceParameter(parameters, "securityConfiguration", NettyHttpSecurityConfiguration.class); Map<String, Object> securityOptions = IntrospectionSupport.extractProperties(parameters, "securityConfiguration."); + NettyHttpBinding bindingFromUri = resolveAndRemoveReferenceParameter(parameters, "nettyHttpBinding", NettyHttpBinding.class); + // are we using a shared http server? int sharedPort = -1; NettySharedHttpServer shared = resolveAndRemoveReferenceParameter(parameters, "nettySharedHttpServer", NettySharedHttpServer.class); @@ -100,15 +102,31 @@ public class NettyHttpComponent extends NettyComponent implements HeaderFilterSt sharedPort = shared.getPort(); } - // configure configuration - config = parseConfiguration(config, remaining, parameters); + // we must include the protocol in the remaining + boolean hasProtocol = remaining.startsWith("http://") || remaining.startsWith("http:") + || remaining.startsWith("https://") || remaining.startsWith("https:"); + if (!hasProtocol) { + // http is the default protocol + remaining = "http://" + remaining; + } + boolean hasSlash = remaining.startsWith("http://") || remaining.startsWith("https://"); + if (!hasSlash) { + // must have double slash after protocol + if (remaining.startsWith("http:")) { + remaining = "http://" + remaining.substring(5); + } else { + remaining = "https://" + remaining.substring(6); + } + } + LOG.debug("Netty http url: {}", remaining); + // set port on configuration which is either shared or using default values if (sharedPort != -1) { config.setPort(sharedPort); } else if (config.getPort() == -1) { - if ("http".equals(config.getProtocol())) { + if (remaining.startsWith("http:")) { config.setPort(80); - } else if ("https".equals(config.getProtocol())) { + } else if (remaining.startsWith("https:")) { config.setPort(443); } } @@ -116,13 +134,13 @@ public class NettyHttpComponent extends NettyComponent implements HeaderFilterSt throw new IllegalArgumentException("Port number must be configured"); } + // configure configuration + config = parseConfiguration(config, remaining, parameters); setProperties(config, parameters); // validate config config.validateConfiguration(); - NettyHttpBinding bindingFromUri = resolveAndRemoveReferenceParameter(parameters, "nettyHttpBinding", NettyHttpBinding.class); - // create the address uri which includes the remainder parameters (which // is not configuration parameters for this component) URI u = new URI(UnsafeUriCharactersEncoder.encodeHttpURI(remaining)); http://git-wip-us.apache.org/repos/asf/camel/blob/72626b57/components/camel-netty4-http/src/test/java/org/apache/camel/component/netty4/http/NettyDefaultProtocolTest.java ---------------------------------------------------------------------- diff --git a/components/camel-netty4-http/src/test/java/org/apache/camel/component/netty4/http/NettyDefaultProtocolTest.java b/components/camel-netty4-http/src/test/java/org/apache/camel/component/netty4/http/NettyDefaultProtocolTest.java new file mode 100644 index 0000000..af1aa8a --- /dev/null +++ b/components/camel-netty4-http/src/test/java/org/apache/camel/component/netty4/http/NettyDefaultProtocolTest.java @@ -0,0 +1,53 @@ +/** + * 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.netty4.http; + +import org.apache.camel.Exchange; +import org.apache.camel.builder.RouteBuilder; +import org.junit.Test; + +public class NettyDefaultProtocolTest extends BaseNettyTest { + + @Test + public void testDefaultProtocol() throws Exception { + getMockEndpoint("mock:input").expectedBodiesReceived("Hello World"); + getMockEndpoint("mock:input").expectedHeaderReceived("beer", "yes"); + getMockEndpoint("mock:input").expectedHeaderReceived("host", "localhost:" + getPort()); + getMockEndpoint("mock:input").expectedHeaderReceived(Exchange.HTTP_METHOD, "POST"); + getMockEndpoint("mock:input").expectedHeaderReceived(Exchange.HTTP_URL, "http://localhost:" + getPort() + "/foo"); + getMockEndpoint("mock:input").expectedHeaderReceived(Exchange.HTTP_URI, "/foo"); + getMockEndpoint("mock:input").expectedHeaderReceived(Exchange.HTTP_QUERY, "beer=yes"); + getMockEndpoint("mock:input").expectedHeaderReceived(Exchange.HTTP_PATH, ""); + + String out = template.requestBody("netty4-http:localhost:{{port}}/foo?beer=yes", "Hello World", String.class); + assertEquals("Bye World", out); + + assertMockEndpointsSatisfied(); + } + + @Override + protected RouteBuilder createRouteBuilder() throws Exception { + return new RouteBuilder() { + @Override + public void configure() throws Exception { + from("netty4-http:0.0.0.0:{{port}}/foo") + .to("mock:input") + .transform().constant("Bye World"); + } + }; + } +} \ No newline at end of file http://git-wip-us.apache.org/repos/asf/camel/blob/72626b57/components/camel-netty4-http/src/test/java/org/apache/camel/component/netty4/http/NettyHttpProtocolNoSlashTest.java ---------------------------------------------------------------------- diff --git a/components/camel-netty4-http/src/test/java/org/apache/camel/component/netty4/http/NettyHttpProtocolNoSlashTest.java b/components/camel-netty4-http/src/test/java/org/apache/camel/component/netty4/http/NettyHttpProtocolNoSlashTest.java new file mode 100644 index 0000000..f733ea5 --- /dev/null +++ b/components/camel-netty4-http/src/test/java/org/apache/camel/component/netty4/http/NettyHttpProtocolNoSlashTest.java @@ -0,0 +1,54 @@ +/** + * 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.netty4.http; + +import org.apache.camel.Exchange; +import org.apache.camel.builder.RouteBuilder; +import org.junit.Test; + +public class NettyHttpProtocolNoSlashTest extends BaseNettyTest { + + @Test + public void testHttpProtocolNoSlash() throws Exception { + getMockEndpoint("mock:input").expectedBodiesReceived("Hello World"); + getMockEndpoint("mock:input").expectedHeaderReceived("beer", "yes"); + getMockEndpoint("mock:input").expectedHeaderReceived("host", "localhost:" + getPort()); + getMockEndpoint("mock:input").expectedHeaderReceived(Exchange.HTTP_METHOD, "POST"); + getMockEndpoint("mock:input").expectedHeaderReceived(Exchange.HTTP_URL, "http://localhost:" + getPort() + "/foo"); + getMockEndpoint("mock:input").expectedHeaderReceived(Exchange.HTTP_URI, "/foo"); + getMockEndpoint("mock:input").expectedHeaderReceived(Exchange.HTTP_QUERY, "beer=yes"); + getMockEndpoint("mock:input").expectedHeaderReceived(Exchange.HTTP_PATH, ""); + + String out = template.requestBody("netty4-http:http:localhost:{{port}}/foo?beer=yes", "Hello World", String.class); + assertEquals("Bye World", out); + + assertMockEndpointsSatisfied(); + } + + @Override + protected RouteBuilder createRouteBuilder() throws Exception { + return new RouteBuilder() { + @Override + public void configure() throws Exception { + from("netty4-http:http:0.0.0.0:{{port}}/foo") + .to("mock:input") + .transform().constant("Bye World"); + } + }; + } + +}