You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@camel.apache.org by da...@apache.org on 2016/02/27 16:25:22 UTC
[4/4] camel git commit: CAMEL-9652: camel-spark-rest - Add support
for hosting swagger api
CAMEL-9652: camel-spark-rest - Add support for hosting swagger api
Project: http://git-wip-us.apache.org/repos/asf/camel/repo
Commit: http://git-wip-us.apache.org/repos/asf/camel/commit/f22d4848
Tree: http://git-wip-us.apache.org/repos/asf/camel/tree/f22d4848
Diff: http://git-wip-us.apache.org/repos/asf/camel/diff/f22d4848
Branch: refs/heads/master
Commit: f22d4848573e40f4847b89b38a89efaa15a2eaab
Parents: 558747b
Author: Claus Ibsen <da...@apache.org>
Authored: Sat Feb 27 14:09:15 2016 +0100
Committer: Claus Ibsen <da...@apache.org>
Committed: Sat Feb 27 16:25:10 2016 +0100
----------------------------------------------------------------------
components/camel-spark-rest/pom.xml | 5 ++
.../camel/component/sparkrest/CamelSpark.java | 1 +
.../sparkrest/DefaultSparkBinding.java | 23 +++++-
.../component/sparkrest/SparkComponent.java | 26 +++++--
.../component/sparkrest/SparkConsumer.java | 5 ++
.../component/sparkrest/SparkEndpoint.java | 18 ++++-
.../component/sparkrest/RestApiSparkTest.java | 73 ++++++++++++++++++++
7 files changed, 144 insertions(+), 7 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/camel/blob/f22d4848/components/camel-spark-rest/pom.xml
----------------------------------------------------------------------
diff --git a/components/camel-spark-rest/pom.xml b/components/camel-spark-rest/pom.xml
index 29ee6e7..a57caf3 100644
--- a/components/camel-spark-rest/pom.xml
+++ b/components/camel-spark-rest/pom.xml
@@ -89,6 +89,11 @@
<artifactId>camel-http</artifactId>
<scope>test</scope>
</dependency>
+ <dependency>
+ <groupId>org.apache.camel</groupId>
+ <artifactId>camel-swagger-java</artifactId>
+ <scope>test</scope>
+ </dependency>
<!-- for testing rest-dsl -->
<dependency>
http://git-wip-us.apache.org/repos/asf/camel/blob/f22d4848/components/camel-spark-rest/src/main/java/org/apache/camel/component/sparkrest/CamelSpark.java
----------------------------------------------------------------------
diff --git a/components/camel-spark-rest/src/main/java/org/apache/camel/component/sparkrest/CamelSpark.java b/components/camel-spark-rest/src/main/java/org/apache/camel/component/sparkrest/CamelSpark.java
index c5e317d..df631df 100644
--- a/components/camel-spark-rest/src/main/java/org/apache/camel/component/sparkrest/CamelSpark.java
+++ b/components/camel-spark-rest/src/main/java/org/apache/camel/component/sparkrest/CamelSpark.java
@@ -16,6 +16,7 @@
*/
package org.apache.camel.component.sparkrest;
+import spark.Filter;
import spark.Route;
import spark.Spark;
http://git-wip-us.apache.org/repos/asf/camel/blob/f22d4848/components/camel-spark-rest/src/main/java/org/apache/camel/component/sparkrest/DefaultSparkBinding.java
----------------------------------------------------------------------
diff --git a/components/camel-spark-rest/src/main/java/org/apache/camel/component/sparkrest/DefaultSparkBinding.java b/components/camel-spark-rest/src/main/java/org/apache/camel/component/sparkrest/DefaultSparkBinding.java
index 3efa003..e721baa 100644
--- a/components/camel-spark-rest/src/main/java/org/apache/camel/component/sparkrest/DefaultSparkBinding.java
+++ b/components/camel-spark-rest/src/main/java/org/apache/camel/component/sparkrest/DefaultSparkBinding.java
@@ -23,6 +23,7 @@ import java.io.StringWriter;
import java.io.UnsupportedEncodingException;
import java.net.URLDecoder;
import java.util.Iterator;
+import java.util.Locale;
import java.util.Map;
import org.apache.camel.Exchange;
@@ -33,6 +34,7 @@ import org.apache.camel.util.ExchangeHelper;
import org.apache.camel.util.IOHelper;
import org.apache.camel.util.MessageHelper;
import org.apache.camel.util.ObjectHelper;
+import org.apache.camel.util.URISupport;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import spark.Request;
@@ -69,9 +71,28 @@ public class DefaultSparkBinding implements SparkBinding {
headers.put(Exchange.HTTP_QUERY, request.raw().getQueryString());
headers.put(Exchange.HTTP_URL, request.raw().getRequestURL().toString());
headers.put(Exchange.HTTP_URI, request.raw().getRequestURI());
- headers.put(Exchange.HTTP_PATH, request.raw().getPathInfo());
headers.put(Exchange.CONTENT_TYPE, request.raw().getContentType());
+ String path = request.raw().getPathInfo();
+ SparkEndpoint endpoint = (SparkEndpoint) exchange.getFromEndpoint();
+ if (endpoint.getPath() != null) {
+ // need to match by lower case as we want to ignore case on context-path
+ String endpointPath = endpoint.getPath();
+ String matchPath = path.toLowerCase(Locale.US);
+ String match = endpointPath.toLowerCase(Locale.US);
+
+ if (match.endsWith("/*")) {
+ match = match.substring(0, match.length() - 2);
+ }
+ if (!match.startsWith("/")) {
+ match = "/" + match;
+ }
+ if (matchPath.startsWith(match)) {
+ path = path.substring(match.length());
+ }
+ }
+ headers.put(Exchange.HTTP_PATH, path);
+
for (String key : request.attributes()) {
Object value = request.attribute(key);
Object decoded = shouldUrlDecodeHeader(configuration, key, value, "UTF-8");
http://git-wip-us.apache.org/repos/asf/camel/blob/f22d4848/components/camel-spark-rest/src/main/java/org/apache/camel/component/sparkrest/SparkComponent.java
----------------------------------------------------------------------
diff --git a/components/camel-spark-rest/src/main/java/org/apache/camel/component/sparkrest/SparkComponent.java b/components/camel-spark-rest/src/main/java/org/apache/camel/component/sparkrest/SparkComponent.java
index 51c553f..5484fd7 100644
--- a/components/camel-spark-rest/src/main/java/org/apache/camel/component/sparkrest/SparkComponent.java
+++ b/components/camel-spark-rest/src/main/java/org/apache/camel/component/sparkrest/SparkComponent.java
@@ -26,13 +26,14 @@ import org.apache.camel.Consumer;
import org.apache.camel.Endpoint;
import org.apache.camel.Processor;
import org.apache.camel.impl.UriEndpointComponent;
+import org.apache.camel.spi.RestApiConsumerFactory;
import org.apache.camel.spi.RestConfiguration;
import org.apache.camel.spi.RestConsumerFactory;
import org.apache.camel.util.FileUtil;
import org.apache.camel.util.ObjectHelper;
import org.apache.camel.util.URISupport;
-public class SparkComponent extends UriEndpointComponent implements RestConsumerFactory {
+public class SparkComponent extends UriEndpointComponent implements RestConsumerFactory, RestApiConsumerFactory {
private final Pattern pattern = Pattern.compile("\\{(.*?)\\}");
@@ -237,6 +238,18 @@ public class SparkComponent extends UriEndpointComponent implements RestConsumer
@Override
public Consumer createConsumer(CamelContext camelContext, Processor processor, String verb, String basePath, String uriTemplate,
String consumes, String produces, RestConfiguration configuration, Map<String, Object> parameters) throws Exception {
+ return doCreateConsumer(camelContext, processor, verb, basePath, uriTemplate, consumes, produces, configuration, parameters, false);
+ }
+
+ @Override
+ public Consumer createApiConsumer(CamelContext camelContext, Processor processor, String contextPath,
+ RestConfiguration configuration, Map<String, Object> parameters) throws Exception {
+ // reuse the createConsumer method we already have. The api need to use GET and match on uri prefix
+ return doCreateConsumer(camelContext, processor, "get", contextPath, null, null, null, configuration, parameters, true);
+ }
+
+ Consumer doCreateConsumer(CamelContext camelContext, Processor processor, String verb, String basePath, String uriTemplate,
+ String consumes, String produces, RestConfiguration configuration, Map<String, Object> parameters, boolean api) throws Exception {
String path = basePath;
if (uriTemplate != null) {
@@ -280,11 +293,16 @@ public class SparkComponent extends UriEndpointComponent implements RestConsumer
}
}
- String uri = String.format("spark-rest:%s:%s", verb, path);
+ String url;
+ if (api) {
+ url = "spark-rest:%s:%s?matchOnUriPrefix=true";
+ } else {
+ url = "spark-rest:%s:%s";
+ }
- String query = URISupport.createQueryString(map);
+ url = String.format(url, verb, path);
- String url = uri;
+ String query = URISupport.createQueryString(map);
if (!query.isEmpty()) {
url = url + "?" + query;
}
http://git-wip-us.apache.org/repos/asf/camel/blob/f22d4848/components/camel-spark-rest/src/main/java/org/apache/camel/component/sparkrest/SparkConsumer.java
----------------------------------------------------------------------
diff --git a/components/camel-spark-rest/src/main/java/org/apache/camel/component/sparkrest/SparkConsumer.java b/components/camel-spark-rest/src/main/java/org/apache/camel/component/sparkrest/SparkConsumer.java
index 1786700..d3191f2 100644
--- a/components/camel-spark-rest/src/main/java/org/apache/camel/component/sparkrest/SparkConsumer.java
+++ b/components/camel-spark-rest/src/main/java/org/apache/camel/component/sparkrest/SparkConsumer.java
@@ -41,6 +41,7 @@ public class SparkConsumer extends DefaultConsumer {
String verb = getEndpoint().getVerb();
String path = getEndpoint().getPath();
String accept = getEndpoint().getAccept();
+ boolean matchOnUriPrefix = getEndpoint().isMatchOnUriPrefix();
if (accept != null) {
log.debug("Spark-rest: {}({}) accepting: {}", new Object[]{verb, path, accept});
@@ -48,6 +49,10 @@ public class SparkConsumer extends DefaultConsumer {
log.debug("Spark-rest: {}({})", verb, path);
}
CamelSpark.spark(verb, path, accept, route);
+
+ if (matchOnUriPrefix) {
+ CamelSpark.spark(verb, path + "/*", accept, route);
+ }
}
}
http://git-wip-us.apache.org/repos/asf/camel/blob/f22d4848/components/camel-spark-rest/src/main/java/org/apache/camel/component/sparkrest/SparkEndpoint.java
----------------------------------------------------------------------
diff --git a/components/camel-spark-rest/src/main/java/org/apache/camel/component/sparkrest/SparkEndpoint.java b/components/camel-spark-rest/src/main/java/org/apache/camel/component/sparkrest/SparkEndpoint.java
index af5c9b2..3e8df90 100644
--- a/components/camel-spark-rest/src/main/java/org/apache/camel/component/sparkrest/SparkEndpoint.java
+++ b/components/camel-spark-rest/src/main/java/org/apache/camel/component/sparkrest/SparkEndpoint.java
@@ -43,6 +43,8 @@ public class SparkEndpoint extends DefaultEndpoint {
private SparkConfiguration sparkConfiguration;
@UriParam
private SparkBinding sparkBinding;
+ @UriParam
+ private boolean matchOnUriPrefix;
public SparkEndpoint(String endpointUri, Component component) {
super(endpointUri, component);
@@ -103,6 +105,17 @@ public class SparkEndpoint extends DefaultEndpoint {
this.accept = accept;
}
+ public boolean isMatchOnUriPrefix() {
+ return matchOnUriPrefix;
+ }
+
+ /**
+ * Whether or not the consumer should try to find a target consumer by matching the URI prefix if no exact match is found.
+ */
+ public void setMatchOnUriPrefix(boolean matchOnUriPrefix) {
+ this.matchOnUriPrefix = matchOnUriPrefix;
+ }
+
@Override
public Producer createProducer() throws Exception {
throw new UnsupportedOperationException("Producer not supported");
@@ -128,7 +141,8 @@ public class SparkEndpoint extends DefaultEndpoint {
ObjectHelper.notEmpty(verb, "verb", this);
ObjectHelper.notEmpty(path, "path", this);
- // verb must be supported by Spark
- HttpMethod.valueOf(verb);
+ // verb must be supported by Spark and lets convert to the actual name
+ HttpMethod method = getCamelContext().getTypeConverter().mandatoryConvertTo(HttpMethod.class, verb);
+ verb = method.name();
}
}
http://git-wip-us.apache.org/repos/asf/camel/blob/f22d4848/components/camel-spark-rest/src/test/java/org/apache/camel/component/sparkrest/RestApiSparkTest.java
----------------------------------------------------------------------
diff --git a/components/camel-spark-rest/src/test/java/org/apache/camel/component/sparkrest/RestApiSparkTest.java b/components/camel-spark-rest/src/test/java/org/apache/camel/component/sparkrest/RestApiSparkTest.java
new file mode 100644
index 0000000..8295939
--- /dev/null
+++ b/components/camel-spark-rest/src/test/java/org/apache/camel/component/sparkrest/RestApiSparkTest.java
@@ -0,0 +1,73 @@
+/**
+ * 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.sparkrest;
+
+import org.apache.camel.builder.RouteBuilder;
+import org.apache.camel.model.rest.RestParamType;
+import org.junit.Test;
+
+public class RestApiSparkTest extends BaseSparkTest {
+
+ @Override
+ protected boolean useJmx() {
+ return true;
+ }
+
+ @Test
+ public void testApi() throws Exception {
+ String out = template.requestBody("http://localhost:" + getPort() + "/api-doc", null, String.class);
+ assertNotNull(out);
+ assertTrue(out.contains("\"version\" : \"1.2.3\""));
+ assertTrue(out.contains("\"title\" : \"The hello rest thing\""));
+ assertTrue(out.contains("\"/hello/bye/{name}\""));
+ assertTrue(out.contains("\"/hello/hi/{name}\""));
+ assertTrue(out.contains("\"summary\" : \"To update the greeting message\""));
+
+ // regular REST service should still work
+ out = template.requestBody("http://localhost:" + getPort() + "/hello/hi/world", null, String.class);
+ assertEquals("Hello World", out);
+
+ }
+
+ @Override
+ protected RouteBuilder createRouteBuilder() throws Exception {
+ return new RouteBuilder() {
+ @Override
+ public void configure() throws Exception {
+ restConfiguration().component("spark-rest").host("localhost").port(getPort()).apiContextPath("/api-doc")
+ .apiProperty("cors", "true").apiProperty("api.title", "The hello rest thing").apiProperty("api.version", "1.2.3");
+
+ rest("/hello").consumes("application/json").produces("application/json")
+ .get("/hi/{name}").description("Saying hi")
+ .param().name("name").type(RestParamType.path).dataType("string").description("Who is it").endParam()
+ .to("direct:hello")
+ .get("/bye/{name}").description("Saying bye")
+ .param().name("name").type(RestParamType.path).dataType("string").description("Who is it").endParam()
+ .responseMessage().code(200).message("A reply message").endResponseMessage()
+ .to("log:bye")
+ .post("/bye").description("To update the greeting message").consumes("application/xml").produces("application/xml")
+ .param().name("greeting").type(RestParamType.body).dataType("string").description("Message to use as greeting").endParam()
+ .to("log:bye");
+
+ from("direct:hello")
+ .transform().constant("Hello World");
+
+ }
+ };
+ }
+
+}