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 2015/09/23 11:35:39 UTC

[03/16] camel git commit: CAMEL-8545: camel-swagger-java to run outside servlet - work in progress

CAMEL-8545: camel-swagger-java to run outside servlet - work in progress


Project: http://git-wip-us.apache.org/repos/asf/camel/repo
Commit: http://git-wip-us.apache.org/repos/asf/camel/commit/b88093cb
Tree: http://git-wip-us.apache.org/repos/asf/camel/tree/b88093cb
Diff: http://git-wip-us.apache.org/repos/asf/camel/diff/b88093cb

Branch: refs/heads/master
Commit: b88093cb668097c3e3cf7814e6286fd7ac5cf878
Parents: 3818efe
Author: Claus Ibsen <da...@apache.org>
Authored: Tue Sep 22 16:25:19 2015 +0200
Committer: Claus Ibsen <da...@apache.org>
Committed: Wed Sep 23 07:51:03 2015 +0200

----------------------------------------------------------------------
 .../camel/component/rest/RestApiComponent.java  |  46 +++++
 .../camel/component/rest/RestApiEndpoint.java   | 204 +++++++++++++++++++
 .../camel/component/rest/RestApiProducer.java   |  50 +++++
 .../model/rest/RestConfigurationDefinition.java |  33 +++
 .../apache/camel/model/rest/RestDefinition.java |  41 +++-
 .../camel/spi/RestApiConsumerFactory.java       |  43 ++++
 .../camel/spi/RestApiProcessorFactory.java      |  40 ++++
 .../camel/spi/RestApiResponseAdapter.java       |  33 +++
 .../org/apache/camel/spi/RestConfiguration.java |  17 ++
 .../org/apache/camel/component/rest-api         |  18 ++
 .../rest/DummyRestConsumerFactory.java          |  14 +-
 .../rest/DummyRestProcessorFactory.java         |  38 ++++
 .../camel/component/rest/FromRestApiTest.java   |  62 ++++++
 .../camel/swagger/RestSwaggerProcessor.java     |  81 ++++++++
 .../camel/swagger/RestSwaggerSupport.java       |  66 +++---
 .../swagger/SwaggerRestApiProcessorFactory.java |  32 +++
 .../swagger/servlet/RestSwaggerServlet.java     |  21 +-
 .../servlet/ServletRestApiResponseAdapter.java  |  48 +++++
 .../servlet/ServletSwaggerApiProvider.java      |  55 -----
 .../camel/swagger/spi/SwaggerApiProvider.java   |  32 ---
 20 files changed, 848 insertions(+), 126 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/camel/blob/b88093cb/camel-core/src/main/java/org/apache/camel/component/rest/RestApiComponent.java
----------------------------------------------------------------------
diff --git a/camel-core/src/main/java/org/apache/camel/component/rest/RestApiComponent.java b/camel-core/src/main/java/org/apache/camel/component/rest/RestApiComponent.java
new file mode 100644
index 0000000..9abaaac
--- /dev/null
+++ b/camel-core/src/main/java/org/apache/camel/component/rest/RestApiComponent.java
@@ -0,0 +1,46 @@
+/**
+ * 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.rest;
+
+import java.util.Map;
+
+import org.apache.camel.Endpoint;
+import org.apache.camel.impl.UriEndpointComponent;
+
+public class RestApiComponent extends UriEndpointComponent {
+
+    public RestApiComponent() {
+        super(RestApiEndpoint.class);
+    }
+
+    @Override
+    protected Endpoint createEndpoint(String uri, String remaining, Map<String, Object> parameters) throws Exception {
+        RestApiEndpoint answer = new RestApiEndpoint(uri, this);
+        answer.setPath(remaining);
+
+        setProperties(answer, parameters);
+        answer.setParameters(parameters);
+
+        // if no explicit component name was given, then fallback and use default configured component name
+        if (answer.getComponentName() == null && getCamelContext().getRestConfiguration() != null) {
+            answer.setComponentName(getCamelContext().getRestConfiguration().getComponent());
+        }
+
+        return answer;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/b88093cb/camel-core/src/main/java/org/apache/camel/component/rest/RestApiEndpoint.java
----------------------------------------------------------------------
diff --git a/camel-core/src/main/java/org/apache/camel/component/rest/RestApiEndpoint.java b/camel-core/src/main/java/org/apache/camel/component/rest/RestApiEndpoint.java
new file mode 100644
index 0000000..a4ff9f5
--- /dev/null
+++ b/camel-core/src/main/java/org/apache/camel/component/rest/RestApiEndpoint.java
@@ -0,0 +1,204 @@
+/**
+ * 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.rest;
+
+import java.util.Map;
+import java.util.Set;
+
+import org.apache.camel.Component;
+import org.apache.camel.Consumer;
+import org.apache.camel.NoSuchBeanException;
+import org.apache.camel.Processor;
+import org.apache.camel.Producer;
+import org.apache.camel.impl.DefaultEndpoint;
+import org.apache.camel.spi.Metadata;
+import org.apache.camel.spi.RestApiConsumerFactory;
+import org.apache.camel.spi.RestApiProcessorFactory;
+import org.apache.camel.spi.RestConfiguration;
+import org.apache.camel.spi.UriEndpoint;
+import org.apache.camel.spi.UriParam;
+import org.apache.camel.spi.UriPath;
+
+@UriEndpoint(scheme = "rest-api", title = "REST API", syntax = "rest-api:path", consumerOnly = true, label = "core,rest")
+public class RestApiEndpoint extends DefaultEndpoint {
+
+    @UriPath @Metadata(required = "true")
+    private String path;
+    @UriParam
+    private String componentName;
+
+    private Map<String, Object> parameters;
+
+    public RestApiEndpoint(String endpointUri, RestApiComponent component) {
+        super(endpointUri, component);
+    }
+
+    @Override
+    public RestApiComponent getComponent() {
+        return (RestApiComponent) super.getComponent();
+    }
+
+    public String getPath() {
+        return path;
+    }
+
+    /**
+     * The base path
+     */
+    public void setPath(String path) {
+        this.path = path;
+    }
+
+    public String getComponentName() {
+        return componentName;
+    }
+
+    /**
+     * The Camel Rest component to use for the REST transport, such as restlet, spark-rest.
+     * If no component has been explicit configured, then Camel will lookup if there is a Camel component
+     * that integrates with the Rest DSL, or if a org.apache.camel.spi.RestConsumerFactory is registered in the registry.
+     * If either one is found, then that is being used.
+     */
+    public void setComponentName(String componentName) {
+        this.componentName = componentName;
+    }
+
+    public Map<String, Object> getParameters() {
+        return parameters;
+    }
+
+    /**
+     * Additional parameters to configure the consumer of the REST transport for this REST service
+     */
+    public void setParameters(Map<String, Object> parameters) {
+        this.parameters = parameters;
+    }
+
+    @Override
+    public Producer createProducer() throws Exception {
+        RestApiProcessorFactory factory = null;
+
+        // lookup in registry
+        Set<RestApiProcessorFactory> factories = getCamelContext().getRegistry().findByType(RestApiProcessorFactory.class);
+        if (factories != null && factories.size() == 1) {
+            factory = factories.iterator().next();
+        }
+
+        if (factory != null) {
+
+            // calculate the url to the rest API service
+            String path = getPath();
+            if (path != null && !path.startsWith("/")) {
+                path = "/" + path;
+            }
+
+
+            Processor processor = factory.createApiProcessor(getCamelContext(), path, getParameters());
+            return new RestApiProducer(this, processor);
+        } else {
+            throw new IllegalStateException("Cannot find RestApiProcessorFactory in Registry");
+        }
+    }
+
+    @Override
+    public Consumer createConsumer(Processor processor) throws Exception {
+        RestApiConsumerFactory factory = null;
+        String cname = null;
+        if (getComponentName() != null) {
+            Object comp = getCamelContext().getRegistry().lookupByName(getComponentName());
+            if (comp != null && comp instanceof RestApiConsumerFactory) {
+                factory = (RestApiConsumerFactory) comp;
+            } else {
+                comp = getCamelContext().getComponent(getComponentName());
+                if (comp != null && comp instanceof RestApiConsumerFactory) {
+                    factory = (RestApiConsumerFactory) comp;
+                }
+            }
+
+            if (factory == null) {
+                if (comp != null) {
+                    throw new IllegalArgumentException("Component " + getComponentName() + " is not a RestApiConsumerFactory");
+                } else {
+                    throw new NoSuchBeanException(getComponentName(), RestApiConsumerFactory.class.getName());
+                }
+            }
+            cname = getComponentName();
+        }
+
+        // try all components
+        if (factory == null) {
+            for (String name : getCamelContext().getComponentNames()) {
+                Component comp = getCamelContext().getComponent(name);
+                if (comp != null && comp instanceof RestApiConsumerFactory) {
+                    factory = (RestApiConsumerFactory) comp;
+                    cname = name;
+                    break;
+                }
+            }
+        }
+
+        // lookup in registry
+        if (factory == null) {
+            Set<RestApiConsumerFactory> factories = getCamelContext().getRegistry().findByType(RestApiConsumerFactory.class);
+            if (factories != null && factories.size() == 1) {
+                factory = factories.iterator().next();
+            }
+        }
+
+        if (factory != null) {
+
+            RestConfiguration config = getCamelContext().getRestConfiguration(cname, true);
+
+            // calculate the url to the rest API service
+            String path = getPath();
+            if (path != null && !path.startsWith("/")) {
+                path = "/" + path;
+            }
+
+            // TODO: is this needed?
+            // there may be an optional context path configured to help Camel calculate the correct urls for the REST services
+            // this may be needed when using camel-serlvet where we cannot get the actual context-path or port number of the servlet engine
+            // during init of the servlet
+/*            String contextPath = config.getApiContextPath();
+            if (contextPath != null) {
+                if (!contextPath.startsWith("/")) {
+                    path = "/" + contextPath + path;
+                } else {
+                    path = contextPath + path;
+                }
+            }
+*/
+
+            Consumer consumer = factory.createApiConsumer(getCamelContext(), processor, path, getParameters());
+            configureConsumer(consumer);
+
+            return consumer;
+        } else {
+            throw new IllegalStateException("Cannot find RestApiConsumerFactory in Registry or as a Component to use");
+        }
+    }
+
+    @Override
+    public boolean isSingleton() {
+        return true;
+    }
+
+    @Override
+    public boolean isLenientProperties() {
+        return true;
+    }
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/b88093cb/camel-core/src/main/java/org/apache/camel/component/rest/RestApiProducer.java
----------------------------------------------------------------------
diff --git a/camel-core/src/main/java/org/apache/camel/component/rest/RestApiProducer.java b/camel-core/src/main/java/org/apache/camel/component/rest/RestApiProducer.java
new file mode 100644
index 0000000..77c994d
--- /dev/null
+++ b/camel-core/src/main/java/org/apache/camel/component/rest/RestApiProducer.java
@@ -0,0 +1,50 @@
+/**
+ * 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.rest;
+
+import org.apache.camel.Endpoint;
+import org.apache.camel.Exchange;
+import org.apache.camel.Processor;
+import org.apache.camel.impl.DefaultProducer;
+import org.apache.camel.util.ServiceHelper;
+
+public class RestApiProducer extends DefaultProducer {
+
+    private final Processor processor;
+
+    public RestApiProducer(Endpoint endpoint, Processor processor) {
+        super(endpoint);
+        this.processor = processor;
+    }
+
+    @Override
+    public void process(Exchange exchange) throws Exception {
+        processor.process(exchange);
+    }
+
+    @Override
+    protected void doStart() throws Exception {
+        super.doStart();
+        ServiceHelper.startService(processor);
+    }
+
+    @Override
+    protected void doStop() throws Exception {
+        super.doStop();
+        ServiceHelper.stopService(processor);
+    }
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/b88093cb/camel-core/src/main/java/org/apache/camel/model/rest/RestConfigurationDefinition.java
----------------------------------------------------------------------
diff --git a/camel-core/src/main/java/org/apache/camel/model/rest/RestConfigurationDefinition.java b/camel-core/src/main/java/org/apache/camel/model/rest/RestConfigurationDefinition.java
index f44f5ba..1ed3239 100644
--- a/camel-core/src/main/java/org/apache/camel/model/rest/RestConfigurationDefinition.java
+++ b/camel-core/src/main/java/org/apache/camel/model/rest/RestConfigurationDefinition.java
@@ -55,6 +55,9 @@ public class RestConfigurationDefinition {
     private String contextPath;
 
     @XmlAttribute
+    private String apiContextPath;
+
+    @XmlAttribute
     private RestHostNameResolver hostNameResolver;
 
     @XmlAttribute @Metadata(defaultValue = "auto")
@@ -154,6 +157,22 @@ public class RestConfigurationDefinition {
         this.contextPath = contextPath;
     }
 
+    public String getApiContextPath() {
+        return apiContextPath;
+    }
+
+    /**
+     * Sets a leading API context-path the REST API services will be using.
+     * <p/>
+     * This can be used when using components such as <tt>camel-servlet</tt> where the deployed web application
+     * is deployed using a context-path.
+     *
+     * @param contextPath the API context path
+     */
+    public void setApiContextPath(String contextPath) {
+        this.apiContextPath = contextPath;
+    }
+
     public RestHostNameResolver getHostNameResolver() {
         return hostNameResolver;
     }
@@ -339,6 +358,17 @@ public class RestConfigurationDefinition {
     }
 
     /**
+     * Sets a leading API context-path the REST API services will be using.
+     * <p/>
+     * This can be used when using components such as <tt>camel-servlet</tt> where the deployed web application
+     * is deployed using a context-path.
+     */
+    public RestConfigurationDefinition apiContextPath(String contextPath) {
+        setApiContextPath(contextPath);
+        return this;
+    }
+
+    /**
      * Sets a leading context-path the REST services will be using.
      * <p/>
      * This can be used when using components such as <tt>camel-servlet</tt> where the deployed web application
@@ -484,6 +514,9 @@ public class RestConfigurationDefinition {
         if (port != null) {
             answer.setPort(CamelContextHelper.parseInteger(context, port));
         }
+        if (apiContextPath != null) {
+            answer.setApiContextPath(CamelContextHelper.parseText(context, apiContextPath));
+        }
         if (contextPath != null) {
             answer.setContextPath(CamelContextHelper.parseText(context, contextPath));
         }

http://git-wip-us.apache.org/repos/asf/camel/blob/b88093cb/camel-core/src/main/java/org/apache/camel/model/rest/RestDefinition.java
----------------------------------------------------------------------
diff --git a/camel-core/src/main/java/org/apache/camel/model/rest/RestDefinition.java b/camel-core/src/main/java/org/apache/camel/model/rest/RestDefinition.java
index 9e1a34d..7f93637 100644
--- a/camel-core/src/main/java/org/apache/camel/model/rest/RestDefinition.java
+++ b/camel-core/src/main/java/org/apache/camel/model/rest/RestDefinition.java
@@ -21,7 +21,6 @@ import java.util.ArrayList;
 import java.util.HashMap;
 import java.util.List;
 import java.util.Map;
-
 import javax.xml.bind.annotation.XmlAccessType;
 import javax.xml.bind.annotation.XmlAccessorType;
 import javax.xml.bind.annotation.XmlAttribute;
@@ -534,10 +533,48 @@ public class RestDefinition extends OptionalIdentifiedDefinition<RestDefinition>
         }
         for (RestConfiguration config : camelContext.getRestConfigurations()) {
             addRouteDefinition(camelContext, answer, config.getComponent());
+            if (config.getApiContextPath() != null) {
+                addApiRouteDefinition(camelContext, answer, config);
+            }
         }
         return answer;
     }
-    
+
+    private void addApiRouteDefinition(CamelContext camelContext, List<RouteDefinition> answer, RestConfiguration configuration) {
+        RouteDefinition route = new RouteDefinition();
+
+        // create the from endpoint uri which is using the rest-api component
+        String from = "rest-api:" + configuration.getApiContextPath();
+
+        // append options
+        Map<String, Object> options = new HashMap<String, Object>();
+
+        String routeId = "rest-api-" + route.idOrCreate(camelContext.getNodeIdFactory());
+        options.put("routeId", routeId);
+        if (configuration.getComponent() != null && !configuration.getComponent().isEmpty()) {
+            options.put("componentName", configuration.getComponent());
+        }
+
+        if (!options.isEmpty()) {
+            String query;
+            try {
+                query = URISupport.createQueryString(options);
+            } catch (URISyntaxException e) {
+                throw ObjectHelper.wrapRuntimeCamelException(e);
+            }
+            from = from + "?" + query;
+        }
+
+        // we use the same uri as the producer (so we have a little route for the rest api)
+        String to = from;
+
+        // the route should be from this rest endpoint
+        route.fromRest(from);
+        route.to(to);
+        route.setRestDefinition(this);
+        answer.add(route);
+    }
+
     private void addRouteDefinition(CamelContext camelContext, List<RouteDefinition> answer, String component) {
         for (VerbDefinition verb : getVerbs()) {
             // either the verb has a singular to or a embedded route

http://git-wip-us.apache.org/repos/asf/camel/blob/b88093cb/camel-core/src/main/java/org/apache/camel/spi/RestApiConsumerFactory.java
----------------------------------------------------------------------
diff --git a/camel-core/src/main/java/org/apache/camel/spi/RestApiConsumerFactory.java b/camel-core/src/main/java/org/apache/camel/spi/RestApiConsumerFactory.java
new file mode 100644
index 0000000..acad9a8
--- /dev/null
+++ b/camel-core/src/main/java/org/apache/camel/spi/RestApiConsumerFactory.java
@@ -0,0 +1,43 @@
+/**
+ * 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.spi;
+
+import java.util.Map;
+
+import org.apache.camel.CamelContext;
+import org.apache.camel.Consumer;
+import org.apache.camel.Processor;
+
+public interface RestApiConsumerFactory {
+
+    /**
+     * Creates a new REST API <a
+     * href="http://camel.apache.org/event-driven-consumer.html">Event
+     * Driven Consumer</a>, which provides API listing of the REST services
+     *
+     * @param camelContext the camel context
+     * @param processor    the processor
+     * @param contextPath  the context-path
+     * @param parameters   additional parameters
+     *
+     * @return a newly created REST API consumer
+     * @throws Exception can be thrown
+     */
+    Consumer createApiConsumer(CamelContext camelContext, Processor processor, String contextPath, Map<String, Object> parameters) throws Exception;
+
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/b88093cb/camel-core/src/main/java/org/apache/camel/spi/RestApiProcessorFactory.java
----------------------------------------------------------------------
diff --git a/camel-core/src/main/java/org/apache/camel/spi/RestApiProcessorFactory.java b/camel-core/src/main/java/org/apache/camel/spi/RestApiProcessorFactory.java
new file mode 100644
index 0000000..6650213
--- /dev/null
+++ b/camel-core/src/main/java/org/apache/camel/spi/RestApiProcessorFactory.java
@@ -0,0 +1,40 @@
+/**
+ * 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.spi;
+
+import java.util.Map;
+
+import org.apache.camel.CamelContext;
+import org.apache.camel.Processor;
+
+public interface RestApiProcessorFactory {
+
+    /**
+     * Creates a new REST API <a
+     * href="http://camel.apache.org/processor.html">Processor
+     * </a>, which provides API listing of the REST services
+     *
+     * @param camelContext the camel context
+     * @param contextPath  the context-path
+     * @param parameters   additional parameters
+     *
+     * @return a newly created REST API provider
+     * @throws Exception can be thrown
+     */
+    Processor createApiProcessor(CamelContext camelContext, String contextPath, Map<String, Object> parameters) throws Exception;
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/b88093cb/camel-core/src/main/java/org/apache/camel/spi/RestApiResponseAdapter.java
----------------------------------------------------------------------
diff --git a/camel-core/src/main/java/org/apache/camel/spi/RestApiResponseAdapter.java b/camel-core/src/main/java/org/apache/camel/spi/RestApiResponseAdapter.java
new file mode 100644
index 0000000..3575d8d
--- /dev/null
+++ b/camel-core/src/main/java/org/apache/camel/spi/RestApiResponseAdapter.java
@@ -0,0 +1,33 @@
+/**
+ * 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.spi;
+
+import java.io.IOException;
+import java.io.OutputStream;
+
+/**
+ * An adapter to allow Camel rest-api to use Camel components to render the api response.
+ */
+public interface RestApiResponseAdapter {
+
+    void addHeader(String name, String value);
+
+    OutputStream getOutputStream() throws IOException;
+
+    void noContent();
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/b88093cb/camel-core/src/main/java/org/apache/camel/spi/RestConfiguration.java
----------------------------------------------------------------------
diff --git a/camel-core/src/main/java/org/apache/camel/spi/RestConfiguration.java b/camel-core/src/main/java/org/apache/camel/spi/RestConfiguration.java
index 5daecd9..7e5e3fe 100644
--- a/camel-core/src/main/java/org/apache/camel/spi/RestConfiguration.java
+++ b/camel-core/src/main/java/org/apache/camel/spi/RestConfiguration.java
@@ -42,6 +42,7 @@ public class RestConfiguration {
     private String host;
     private int port;
     private String contextPath;
+    private String apiContextPath;
     private RestHostNameResolver restHostNameResolver = RestHostNameResolver.localHostName;
     private RestBindingMode bindingMode = RestBindingMode.off;
     private boolean skipBindingOnErrorCode = true;
@@ -147,6 +148,22 @@ public class RestConfiguration {
         this.contextPath = contextPath;
     }
 
+    public String getApiContextPath() {
+        return apiContextPath;
+    }
+
+    /**
+     * Sets a leading API context-path the REST API services will be using.
+     * <p/>
+     * This can be used when using components such as <tt>camel-servlet</tt> where the deployed web application
+     * is deployed using a context-path.
+     *
+     * @param contextPath the API context path
+     */
+    public void setApiContextPath(String contextPath) {
+        this.apiContextPath = contextPath;
+    }
+
     /**
      * Gets the resolver to use for resolving hostname
      *

http://git-wip-us.apache.org/repos/asf/camel/blob/b88093cb/camel-core/src/main/resources/META-INF/services/org/apache/camel/component/rest-api
----------------------------------------------------------------------
diff --git a/camel-core/src/main/resources/META-INF/services/org/apache/camel/component/rest-api b/camel-core/src/main/resources/META-INF/services/org/apache/camel/component/rest-api
new file mode 100644
index 0000000..385496b
--- /dev/null
+++ b/camel-core/src/main/resources/META-INF/services/org/apache/camel/component/rest-api
@@ -0,0 +1,18 @@
+#
+# 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.
+#
+
+class=org.apache.camel.component.rest.RestApiComponent
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/camel/blob/b88093cb/camel-core/src/test/java/org/apache/camel/component/rest/DummyRestConsumerFactory.java
----------------------------------------------------------------------
diff --git a/camel-core/src/test/java/org/apache/camel/component/rest/DummyRestConsumerFactory.java b/camel-core/src/test/java/org/apache/camel/component/rest/DummyRestConsumerFactory.java
index 84819a4..d51d3d3 100644
--- a/camel-core/src/test/java/org/apache/camel/component/rest/DummyRestConsumerFactory.java
+++ b/camel-core/src/test/java/org/apache/camel/component/rest/DummyRestConsumerFactory.java
@@ -23,9 +23,10 @@ import org.apache.camel.Consumer;
 import org.apache.camel.Processor;
 import org.apache.camel.component.seda.SedaEndpoint;
 import org.apache.camel.impl.ActiveMQUuidGenerator;
+import org.apache.camel.spi.RestApiConsumerFactory;
 import org.apache.camel.spi.RestConsumerFactory;
 
-public class DummyRestConsumerFactory implements RestConsumerFactory {
+public class DummyRestConsumerFactory implements RestConsumerFactory, RestApiConsumerFactory {
 
     @Override
     public Consumer createConsumer(CamelContext camelContext, Processor processor, String verb, String basePath, String uriTemplate,
@@ -45,4 +46,15 @@ public class DummyRestConsumerFactory implements RestConsumerFactory {
         return seda.createConsumer(processor);
     }
 
+    @Override
+    public Consumer createApiConsumer(CamelContext camelContext, Processor processor, String contextPath, Map<String, Object> parameters) throws Exception {
+        // just use a seda endpoint for testing purpose
+        String id = ActiveMQUuidGenerator.generateSanitizedId(contextPath);
+        // remove leading dash as we add that ourselves
+        if (id.startsWith("-")) {
+            id = id.substring(1);
+        }
+        SedaEndpoint seda = camelContext.getEndpoint("seda:api:" + "-" + id, SedaEndpoint.class);
+        return seda.createConsumer(processor);
+    }
 }

http://git-wip-us.apache.org/repos/asf/camel/blob/b88093cb/camel-core/src/test/java/org/apache/camel/component/rest/DummyRestProcessorFactory.java
----------------------------------------------------------------------
diff --git a/camel-core/src/test/java/org/apache/camel/component/rest/DummyRestProcessorFactory.java b/camel-core/src/test/java/org/apache/camel/component/rest/DummyRestProcessorFactory.java
new file mode 100644
index 0000000..ecb8c6c
--- /dev/null
+++ b/camel-core/src/test/java/org/apache/camel/component/rest/DummyRestProcessorFactory.java
@@ -0,0 +1,38 @@
+/**
+ * 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.rest;
+
+import java.util.Map;
+
+import org.apache.camel.CamelContext;
+import org.apache.camel.Exchange;
+import org.apache.camel.Processor;
+import org.apache.camel.spi.RestApiProcessorFactory;
+
+public class DummyRestProcessorFactory implements RestApiProcessorFactory {
+
+    @Override
+    public Processor createApiProcessor(CamelContext camelContext, String contextPath, Map<String, Object> parameters) throws Exception {
+        return new Processor() {
+            @Override
+            public void process(Exchange exchange) throws Exception {
+                // noop;
+            }
+        };
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/b88093cb/camel-core/src/test/java/org/apache/camel/component/rest/FromRestApiTest.java
----------------------------------------------------------------------
diff --git a/camel-core/src/test/java/org/apache/camel/component/rest/FromRestApiTest.java b/camel-core/src/test/java/org/apache/camel/component/rest/FromRestApiTest.java
new file mode 100644
index 0000000..9294381
--- /dev/null
+++ b/camel-core/src/test/java/org/apache/camel/component/rest/FromRestApiTest.java
@@ -0,0 +1,62 @@
+/**
+ * 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.rest;
+
+import org.apache.camel.ContextTestSupport;
+import org.apache.camel.builder.RouteBuilder;
+import org.apache.camel.impl.JndiRegistry;
+import org.apache.camel.model.ToDefinition;
+import org.apache.camel.model.rest.RestDefinition;
+
+public class FromRestApiTest extends ContextTestSupport {
+
+    @Override
+    protected JndiRegistry createRegistry() throws Exception {
+        JndiRegistry jndi = super.createRegistry();
+        jndi.bind("dummy-rest", new DummyRestConsumerFactory());
+        jndi.bind("dummy-rest-api", new DummyRestProcessorFactory());
+        return jndi;
+    }
+
+    public void testFromRestModel() throws Exception {
+
+        assertEquals(1, context.getRestDefinitions().size());
+        RestDefinition rest = context.getRestDefinitions().get(0);
+        assertNotNull(rest);
+        assertEquals("/say/hello", rest.getPath());
+        assertEquals(1, rest.getVerbs().size());
+        ToDefinition to = assertIsInstanceOf(ToDefinition.class, rest.getVerbs().get(0).getTo());
+        assertEquals("log:hello", to.getUri());
+
+        // should be 2 routes
+        assertEquals(2, context.getRoutes().size());
+    }
+
+    @Override
+    protected RouteBuilder createRouteBuilder() throws Exception {
+        return new RouteBuilder() {
+            @Override
+            public void configure() throws Exception {
+                restConfiguration().host("localhost").component("dummy-rest").apiContextPath("/api");
+
+                rest("/say/hello")
+                    .get().to("log:hello");
+
+            }
+        };
+    }
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/b88093cb/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/RestSwaggerProcessor.java
----------------------------------------------------------------------
diff --git a/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/RestSwaggerProcessor.java b/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/RestSwaggerProcessor.java
new file mode 100644
index 0000000..d8b34db
--- /dev/null
+++ b/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/RestSwaggerProcessor.java
@@ -0,0 +1,81 @@
+/**
+ * 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.swagger;
+
+import java.util.Map;
+
+import io.swagger.jaxrs.config.BeanConfig;
+import org.apache.camel.Exchange;
+import org.apache.camel.Processor;
+import org.apache.camel.spi.RestApiResponseAdapter;
+import org.apache.camel.support.ServiceSupport;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+public class RestSwaggerProcessor extends ServiceSupport implements Processor {
+
+    private static final Logger LOG = LoggerFactory.getLogger(RestSwaggerProcessor.class);
+    private final BeanConfig swaggerConfig;
+    private final RestSwaggerSupport support;
+
+    public RestSwaggerProcessor(Map<String, Object> parameters) {
+        support = new RestSwaggerSupport();
+        swaggerConfig = new BeanConfig();
+        support.initSwagger(swaggerConfig, parameters);
+    }
+
+    @Override
+    public void process(Exchange exchange) throws Exception {
+
+        String contextId;
+        String route = exchange.getIn().getHeader(Exchange.HTTP_PATH, String.class);
+
+        RestApiResponseAdapter adapter = null;
+
+        try {
+
+            // render list of camel contexts as root
+            if (route == null || route.equals("") || route.equals("/")) {
+                support.renderCamelContexts(adapter);
+            } else {
+                // first part is the camel context
+                if (route.startsWith("/")) {
+                    route = route.substring(1);
+                }
+                // the remainder is the route part
+                contextId = route.split("/")[0];
+                if (route.startsWith(contextId)) {
+                    route = route.substring(contextId.length());
+                }
+
+                support.renderResourceListing(adapter, swaggerConfig, contextId, route);
+            }
+        } catch (Exception e) {
+            LOG.warn("Error rendering Swagger API due " + e.getMessage(), e);
+        }
+    }
+
+    @Override
+    protected void doStart() throws Exception {
+        // noop
+    }
+
+    @Override
+    protected void doStop() throws Exception {
+        // noop
+    }
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/b88093cb/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/RestSwaggerSupport.java
----------------------------------------------------------------------
diff --git a/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/RestSwaggerSupport.java b/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/RestSwaggerSupport.java
index 6b7f56d..ebff12f 100644
--- a/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/RestSwaggerSupport.java
+++ b/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/RestSwaggerSupport.java
@@ -19,6 +19,7 @@ package org.apache.camel.swagger;
 import java.lang.management.ManagementFactory;
 import java.util.ArrayList;
 import java.util.List;
+import java.util.Map;
 import java.util.Set;
 import javax.management.MBeanServer;
 import javax.management.ObjectName;
@@ -35,36 +36,41 @@ import org.apache.camel.impl.DefaultClassResolver;
 import org.apache.camel.model.ModelHelper;
 import org.apache.camel.model.rest.RestDefinition;
 import org.apache.camel.model.rest.RestsDefinition;
-import org.apache.camel.swagger.spi.SwaggerApiProvider;
+import org.apache.camel.spi.RestApiResponseAdapter;
 import org.apache.camel.util.CamelVersionHelper;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
+/**
+ * A support class for that allows SPI to plugin
+ * and offer Swagger API service listings as part of the Camel component. This allows rest-dsl components
+ * such as servlet/jetty/netty4-http to offer Swagger API listings with minimal effort.
+ */
 public class RestSwaggerSupport {
 
     private static final Logger LOG = LoggerFactory.getLogger(RestSwaggerSupport.class);
     private RestSwaggerReader reader = new RestSwaggerReader();
     private boolean cors;
 
-    public void initSwagger(BeanConfig swaggerConfig, SwaggerApiProvider config) {
+    public void initSwagger(BeanConfig swaggerConfig, Map<String, Object> config) {
         // configure swagger options
-        String s = config.getInitParameter("swagger.version");
+        String s = (String) config.get("swagger.version");
         if (s != null) {
             swaggerConfig.setVersion(s);
         }
-        s = config.getInitParameter("base.path");
+        s = (String) config.get("base.path");
         if (s != null) {
             swaggerConfig.setBasePath(s);
         }
-        s = config.getInitParameter("host");
+        s = (String) config.get("host");
         if (s != null) {
             swaggerConfig.setHost(s);
         }
-        s = config.getInitParameter("cors");
+        s = (String) config.get("cors");
         if (s != null) {
             cors = "true".equalsIgnoreCase(s);
         }
-        s = config.getInitParameter("schemas");
+        s = (String) config.get("schemas");
         if (s != null) {
             String[] schemas = s.split(",");
             swaggerConfig.setSchemes(schemas);
@@ -73,15 +79,15 @@ public class RestSwaggerSupport {
             swaggerConfig.setSchemes(new String[]{"http"});
         }
 
-        String version = config.getInitParameter("api.version");
-        String title = config.getInitParameter("api.title");
-        String description = config.getInitParameter("api.description");
-        String termsOfService = config.getInitParameter("api.termsOfService");
-        String licenseName = config.getInitParameter("api.license.name");
-        String licenseUrl = config.getInitParameter("api.license.url");
-        String contactName = config.getInitParameter("api.contact.name");
-        String contactUrl = config.getInitParameter("api.contact.url");
-        String contactEmail = config.getInitParameter("api.contact.email");
+        String version = (String) config.get("api.version");
+        String title = (String) config.get("api.title");
+        String description = (String) config.get("api.description");
+        String termsOfService = (String) config.get("api.termsOfService");
+        String licenseName = (String) config.get("api.license.name");
+        String licenseUrl = (String) config.get("api.license.url");
+        String contactName = (String) config.get("api.contact.name");
+        String contactUrl = (String) config.get("api.contact.url");
+        String contactEmail = (String) config.get("api.contact.email");
 
         Info info = new Info();
         info.setVersion(version);
@@ -159,13 +165,13 @@ public class RestSwaggerSupport {
         return answer;
     }
 
-    public void renderResourceListing(SwaggerApiProvider provider, BeanConfig swaggerConfig, String contextId, String route) throws Exception {
+    public void renderResourceListing(RestApiResponseAdapter response, BeanConfig swaggerConfig, String contextId, String route) throws Exception {
         LOG.trace("renderResourceListing");
 
         if (cors) {
-            provider.addHeader("Access-Control-Allow-Headers", "Origin, Accept, X-Requested-With, Content-Type, Access-Control-Request-Method, Access-Control-Request-Headers");
-            provider.addHeader("Access-Control-Allow-Methods", "GET, HEAD, POST, PUT, DELETE, TRACE, OPTIONS, CONNECT, PATCH");
-            provider.addHeader("Access-Control-Allow-Origin", "*");
+            response.addHeader("Access-Control-Allow-Headers", "Origin, Accept, X-Requested-With, Content-Type, Access-Control-Request-Method, Access-Control-Request-Headers");
+            response.addHeader("Access-Control-Allow-Methods", "GET, HEAD, POST, PUT, DELETE, TRACE, OPTIONS, CONNECT, PATCH");
+            response.addHeader("Access-Control-Allow-Origin", "*");
         }
 
         List<RestDefinition> rests = getRestDefinitions(contextId);
@@ -176,34 +182,34 @@ public class RestSwaggerSupport {
             ObjectMapper mapper = new ObjectMapper();
             mapper.enable(SerializationFeature.INDENT_OUTPUT);
             mapper.setSerializationInclusion(JsonInclude.Include.NON_NULL);
-            mapper.writeValue(provider.getOutputStream(), swagger);
+            mapper.writeValue(response.getOutputStream(), swagger);
         } else {
-            provider.noContent();
+            response.noContent();
         }
     }
 
     /**
      * Renders a list of available CamelContexts in the JVM
      */
-    public void renderCamelContexts(SwaggerApiProvider provider) throws Exception {
+    public void renderCamelContexts(RestApiResponseAdapter response) throws Exception {
         LOG.trace("renderCamelContexts");
 
         if (cors) {
-            provider.addHeader("Access-Control-Allow-Headers", "Origin, Accept, X-Requested-With, Content-Type, Access-Control-Request-Method, Access-Control-Request-Headers");
-            provider.addHeader("Access-Control-Allow-Methods", "GET, HEAD, POST, PUT, DELETE, TRACE, OPTIONS, CONNECT, PATCH");
-            provider.addHeader("Access-Control-Allow-Origin", "*");
+            response.addHeader("Access-Control-Allow-Headers", "Origin, Accept, X-Requested-With, Content-Type, Access-Control-Request-Method, Access-Control-Request-Headers");
+            response.addHeader("Access-Control-Allow-Methods", "GET, HEAD, POST, PUT, DELETE, TRACE, OPTIONS, CONNECT, PATCH");
+            response.addHeader("Access-Control-Allow-Origin", "*");
         }
 
         List<String> contexts = findCamelContexts();
-        provider.getOutputStream().write("[\n".getBytes());
+        response.getOutputStream().write("[\n".getBytes());
         for (int i = 0; i < contexts.size(); i++) {
             String name = contexts.get(i);
-            provider.getOutputStream().write(("{\"name\": \"" + name + "\"}").getBytes());
+            response.getOutputStream().write(("{\"name\": \"" + name + "\"}").getBytes());
             if (i < contexts.size() - 1) {
-                provider.getOutputStream().write(",\n".getBytes());
+                response.getOutputStream().write(",\n".getBytes());
             }
         }
-        provider.getOutputStream().write("\n]".getBytes());
+        response.getOutputStream().write("\n]".getBytes());
     }
 
 }

http://git-wip-us.apache.org/repos/asf/camel/blob/b88093cb/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/SwaggerRestApiProcessorFactory.java
----------------------------------------------------------------------
diff --git a/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/SwaggerRestApiProcessorFactory.java b/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/SwaggerRestApiProcessorFactory.java
new file mode 100644
index 0000000..436ae45
--- /dev/null
+++ b/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/SwaggerRestApiProcessorFactory.java
@@ -0,0 +1,32 @@
+/**
+ * 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.swagger;
+
+import java.util.Map;
+
+import org.apache.camel.CamelContext;
+import org.apache.camel.Processor;
+import org.apache.camel.spi.RestApiProcessorFactory;
+
+public class SwaggerRestApiProcessorFactory implements RestApiProcessorFactory {
+
+    @Override
+    public Processor createApiProcessor(CamelContext camelContext, String contextPath, Map<String, Object> parameters) throws Exception {
+        RestSwaggerProcessor processor = new RestSwaggerProcessor(parameters);
+        return null;
+    }
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/b88093cb/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/servlet/RestSwaggerServlet.java
----------------------------------------------------------------------
diff --git a/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/servlet/RestSwaggerServlet.java b/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/servlet/RestSwaggerServlet.java
index 75d0290..3159776 100644
--- a/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/servlet/RestSwaggerServlet.java
+++ b/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/servlet/RestSwaggerServlet.java
@@ -19,6 +19,9 @@ package org.apache.camel.swagger.servlet;
 import java.io.IOException;
 import java.net.MalformedURLException;
 import java.net.URL;
+import java.util.Enumeration;
+import java.util.HashMap;
+import java.util.Map;
 import javax.servlet.ServletConfig;
 import javax.servlet.ServletException;
 import javax.servlet.http.HttpServlet;
@@ -26,8 +29,8 @@ import javax.servlet.http.HttpServletRequest;
 import javax.servlet.http.HttpServletResponse;
 
 import io.swagger.jaxrs.config.BeanConfig;
+import org.apache.camel.spi.RestApiResponseAdapter;
 import org.apache.camel.swagger.RestSwaggerSupport;
-import org.apache.camel.swagger.spi.SwaggerApiProvider;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
@@ -48,8 +51,14 @@ public class RestSwaggerServlet extends HttpServlet {
     @Override
     public void init(final ServletConfig config) throws ServletException {
         super.init(config);
-
-        swagger.initSwagger(swaggerConfig, new ServletSwaggerApiProvider(config, null));
+        Map<String, Object> parameters = new HashMap<String, Object>();
+        Enumeration en = config.getInitParameterNames();
+        while (en.hasMoreElements()) {
+            String name = (String) en.nextElement();
+            Object value = config.getInitParameter(name);
+            parameters.put(name, value);
+        }
+        swagger.initSwagger(swaggerConfig, parameters);
     }
 
     @Override
@@ -59,7 +68,7 @@ public class RestSwaggerServlet extends HttpServlet {
             initBaseAndApiPaths(request);
         }
 
-        SwaggerApiProvider resp = new ServletSwaggerApiProvider(null, response);
+        RestApiResponseAdapter adapter = new ServletRestApiResponseAdapter(response);
 
         String contextId;
         String route = request.getPathInfo();
@@ -68,7 +77,7 @@ public class RestSwaggerServlet extends HttpServlet {
 
             // render list of camel contexts as root
             if (route == null || route.equals("") || route.equals("/")) {
-                swagger.renderCamelContexts(resp);
+                swagger.renderCamelContexts(adapter);
             } else {
                 // first part is the camel context
                 if (route.startsWith("/")) {
@@ -80,7 +89,7 @@ public class RestSwaggerServlet extends HttpServlet {
                     route = route.substring(contextId.length());
                 }
 
-                swagger.renderResourceListing(resp, swaggerConfig, contextId, route);
+                swagger.renderResourceListing(adapter, swaggerConfig, contextId, route);
             }
         } catch (Exception e) {
             LOG.warn("Error rendering swagger due " + e.getMessage(), e);

http://git-wip-us.apache.org/repos/asf/camel/blob/b88093cb/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/servlet/ServletRestApiResponseAdapter.java
----------------------------------------------------------------------
diff --git a/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/servlet/ServletRestApiResponseAdapter.java b/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/servlet/ServletRestApiResponseAdapter.java
new file mode 100644
index 0000000..499b07d
--- /dev/null
+++ b/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/servlet/ServletRestApiResponseAdapter.java
@@ -0,0 +1,48 @@
+/**
+ * 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.swagger.servlet;
+
+import java.io.IOException;
+import java.io.OutputStream;
+import javax.servlet.http.HttpServletResponse;
+
+import org.apache.camel.spi.RestApiResponseAdapter;
+
+public class ServletRestApiResponseAdapter implements RestApiResponseAdapter {
+
+    private final HttpServletResponse response;
+
+    public ServletRestApiResponseAdapter(HttpServletResponse response) {
+        this.response = response;
+    }
+
+    @Override
+    public void addHeader(String name, String value) {
+        response.addHeader(name, value);
+    }
+
+    @Override
+    public OutputStream getOutputStream() throws IOException {
+        return response.getOutputStream();
+    }
+
+    @Override
+    public void noContent() {
+        response.setStatus(HttpServletResponse.SC_NO_CONTENT);
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/b88093cb/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/servlet/ServletSwaggerApiProvider.java
----------------------------------------------------------------------
diff --git a/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/servlet/ServletSwaggerApiProvider.java b/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/servlet/ServletSwaggerApiProvider.java
deleted file mode 100644
index 3d39825..0000000
--- a/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/servlet/ServletSwaggerApiProvider.java
+++ /dev/null
@@ -1,55 +0,0 @@
-/**
- * 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.swagger.servlet;
-
-import java.io.IOException;
-import java.io.OutputStream;
-import javax.servlet.ServletConfig;
-import javax.servlet.http.HttpServletResponse;
-
-import org.apache.camel.swagger.spi.SwaggerApiProvider;
-
-public class ServletSwaggerApiProvider implements SwaggerApiProvider {
-
-    private final ServletConfig config;
-    private final HttpServletResponse response;
-
-    public ServletSwaggerApiProvider(ServletConfig config, HttpServletResponse response) {
-        this.config = config;
-        this.response = response;
-    }
-
-    @Override
-    public String getInitParameter(String key) {
-        return config.getInitParameter(key);
-    }
-
-    @Override
-    public void addHeader(String name, String value) {
-        response.addHeader(name, value);
-    }
-
-    @Override
-    public OutputStream getOutputStream() throws IOException {
-        return response.getOutputStream();
-    }
-
-    @Override
-    public void noContent() {
-        response.setStatus(HttpServletResponse.SC_NO_CONTENT);
-    }
-}

http://git-wip-us.apache.org/repos/asf/camel/blob/b88093cb/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/spi/SwaggerApiProvider.java
----------------------------------------------------------------------
diff --git a/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/spi/SwaggerApiProvider.java b/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/spi/SwaggerApiProvider.java
deleted file mode 100644
index 42e6a2d..0000000
--- a/components/camel-swagger-java/src/main/java/org/apache/camel/swagger/spi/SwaggerApiProvider.java
+++ /dev/null
@@ -1,32 +0,0 @@
-/**
- * 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.swagger.spi;
-
-import java.io.IOException;
-import java.io.OutputStream;
-
-public interface SwaggerApiProvider {
-
-    String getInitParameter(String key);
-
-    void addHeader(String name, String value);
-
-    OutputStream getOutputStream() throws IOException;
-
-    void noContent();
-
-}