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 2017/10/04 14:56:32 UTC

camel git commit: CAMEL-11695: Add JWT algorithm param and polish documentation

Repository: camel
Updated Branches:
  refs/heads/master 5d8d3d201 -> a558f54ec


CAMEL-11695: Add JWT algorithm param and polish documentation


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

Branch: refs/heads/master
Commit: a558f54ec070e400167af366d3e973f806634760
Parents: 5d8d3d2
Author: Dmitry Volodin <dm...@gmail.com>
Authored: Wed Oct 4 16:39:54 2017 +0300
Committer: Claus Ibsen <da...@apache.org>
Committed: Wed Oct 4 16:55:20 2017 +0200

----------------------------------------------------------------------
 .../src/main/docs/grpc-component.adoc           |  6 +-
 .../camel/component/grpc/GrpcAuthType.java      |  2 +-
 .../camel/component/grpc/GrpcConfiguration.java | 31 +++++--
 .../camel/component/grpc/GrpcConsumer.java      |  5 +-
 .../camel/component/grpc/GrpcProducer.java      |  6 +-
 .../component/grpc/auth/jwt/JwtAlgorithm.java   | 37 ++++++++
 .../grpc/auth/jwt/JwtCallCredentials.java       | 66 ++++++++++++++
 .../component/grpc/auth/jwt/JwtHelper.java      | 56 ++++++++++++
 .../grpc/auth/jwt/JwtServerInterceptor.java     | 88 ++++++++++++++++++
 .../client/auth/jwt/JwtCallCredentials.java     | 66 --------------
 .../grpc/client/auth/jwt/JwtHelper.java         | 43 ---------
 .../server/auth/jwt/JwtServerInterceptor.java   | 96 --------------------
 .../grpc/GrpcConsumerSecurityTest.java          |  9 +-
 .../grpc/GrpcProducerSecurityTest.java          |  5 +-
 14 files changed, 290 insertions(+), 226 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/camel/blob/a558f54e/components/camel-grpc/src/main/docs/grpc-component.adoc
----------------------------------------------------------------------
diff --git a/components/camel-grpc/src/main/docs/grpc-component.adoc b/components/camel-grpc/src/main/docs/grpc-component.adoc
index d1252b1..2d76dd6 100644
--- a/components/camel-grpc/src/main/docs/grpc-component.adoc
+++ b/components/camel-grpc/src/main/docs/grpc-component.adoc
@@ -51,7 +51,7 @@ with the following path and query parameters:
 | *service* | *Required* Fully qualified service name from the protocol buffer descriptor file (package dot service definition name) |  | String
 |===
 
-==== Query Parameters (24 parameters):
+==== Query Parameters (25 parameters):
 
 [width="100%",cols="2,5,^1,2",options="header"]
 |===
@@ -71,6 +71,7 @@ with the following path and query parameters:
 | *userAgent* (producer) | The user agent header passed to the server |  | String
 | *synchronous* (advanced) | Sets whether synchronous processing should be strictly used or Camel is allowed to use asynchronous processing (if supported). | false | boolean
 | *authenticationType* (security) | Authentication method type in advance to the SSL/TLS negotiation | NONE | GrpcAuthType
+| *jwtAlgorithm* (security) | JSON Web Token sign algorithm | HMAC256 | JwtAlgorithm
 | *jwtIssuer* (security) | JSON Web Token issuer |  | String
 | *jwtSecret* (security) | JSON Web Token secret |  | String
 | *jwtSubject* (security) | JSON Web Token subject |  | String
@@ -105,10 +106,13 @@ To enable these features the following component properties combinations must be
 |||serviceAccountResource||Required
 |3|*Custom JSON Web Token implementation authentication*|authenticationType|JWT|Required
 |||negotiationType|NONE or TLS|Optional. The TLS/SSL not checking for this type, but strongly recommended.
+|||jwtAlgorithm|HMAC256(default) or (HMAC384,HMAC512)|Optional
 |||jwtSecret||Required
 |||jwtIssuer||Optional
 |||jwtSubject||Optional
 |=======================================================================
+TLS with OpenSSL is currently the recommended approach for using gRPC over TLS component.
+Using the JDK for ALPN is generally much slower and may not support the necessary ciphers for HTTP2. This function is not implemented in the component.
 
 ### gRPC producer resource type mapping
 

http://git-wip-us.apache.org/repos/asf/camel/blob/a558f54e/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/GrpcAuthType.java
----------------------------------------------------------------------
diff --git a/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/GrpcAuthType.java b/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/GrpcAuthType.java
index f76e5d8..e97735d 100644
--- a/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/GrpcAuthType.java
+++ b/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/GrpcAuthType.java
@@ -32,7 +32,7 @@ public enum GrpcAuthType {
     GOOGLE,
 
     /**
-     * Custom JSON Web Token with HmacSHA256 algorithm implementation
+     * Custom JSON Web Token with HmacSHA algorithms implementation
      */
     JWT
 }

http://git-wip-us.apache.org/repos/asf/camel/blob/a558f54e/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/GrpcConfiguration.java
----------------------------------------------------------------------
diff --git a/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/GrpcConfiguration.java b/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/GrpcConfiguration.java
index 169dd6d..b2bb29a 100644
--- a/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/GrpcConfiguration.java
+++ b/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/GrpcConfiguration.java
@@ -22,6 +22,7 @@ import java.util.Map;
 import io.grpc.internal.GrpcUtil;
 import io.grpc.netty.NegotiationType;
 import io.grpc.netty.NettyChannelBuilder;
+import org.apache.camel.component.grpc.auth.jwt.JwtAlgorithm;
 import org.apache.camel.spi.Metadata;
 import org.apache.camel.spi.UriParam;
 import org.apache.camel.spi.UriParams;
@@ -51,8 +52,8 @@ public class GrpcConfiguration {
     @UriParam(label = "security", defaultValue = "NONE")
     private GrpcAuthType authenticationType = GrpcAuthType.NONE;
     
-    @UriParam(label = "security")
-    private String serviceAccountResource;
+    @UriParam(label = "security", defaultValue = "HMAC256")
+    private JwtAlgorithm jwtAlgorithm = JwtAlgorithm.HMAC256;
     
     @UriParam(label = "security", secret = true)
     private String jwtSecret;
@@ -64,6 +65,9 @@ public class GrpcConfiguration {
     private String jwtSubject;
     
     @UriParam(label = "security")
+    private String serviceAccountResource;
+    
+    @UriParam(label = "security")
     private String keyCertChainResource;
     
     @UriParam(label = "security")
@@ -171,14 +175,14 @@ public class GrpcConfiguration {
     }
     
     /**
-     * Service Account key file in JSON format resource link supported by the Google Cloud SDK
+     * JSON Web Token sign algorithm
      */
-    public String getServiceAccountResource() {
-        return serviceAccountResource;
+    public JwtAlgorithm getJwtAlgorithm() {
+        return jwtAlgorithm;
     }
 
-    public void setServiceAccountResource(String serviceAccountResource) {
-        this.serviceAccountResource = serviceAccountResource;
+    public void setJwtAlgorithm(JwtAlgorithm jwtAlgorithm) {
+        this.jwtAlgorithm = jwtAlgorithm;
     }
     
     /**
@@ -213,6 +217,17 @@ public class GrpcConfiguration {
     public void setJwtSubject(String jwtSubject) {
         this.jwtSubject = jwtSubject;
     }
+    
+    /**
+     * Service Account key file in JSON format resource link supported by the Google Cloud SDK
+     */
+    public String getServiceAccountResource() {
+        return serviceAccountResource;
+    }
+
+    public void setServiceAccountResource(String serviceAccountResource) {
+        this.serviceAccountResource = serviceAccountResource;
+    }
 
     /**
      * The X.509 certificate chain file resource in PEM format link 
@@ -373,5 +388,5 @@ public class GrpcConfiguration {
         }
         
         setService(uri.getPath().substring(1));
-    }
+    }    
 }

http://git-wip-us.apache.org/repos/asf/camel/blob/a558f54e/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/GrpcConsumer.java
----------------------------------------------------------------------
diff --git a/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/GrpcConsumer.java b/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/GrpcConsumer.java
index 750ec21..dfe717f 100644
--- a/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/GrpcConsumer.java
+++ b/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/GrpcConsumer.java
@@ -34,9 +34,9 @@ import javassist.util.proxy.ProxyFactory;
 import org.apache.camel.AsyncCallback;
 import org.apache.camel.Exchange;
 import org.apache.camel.Processor;
+import org.apache.camel.component.grpc.auth.jwt.JwtServerInterceptor;
 import org.apache.camel.component.grpc.server.GrpcHeaderInterceptor;
 import org.apache.camel.component.grpc.server.GrpcMethodHandler;
-import org.apache.camel.component.grpc.server.auth.jwt.JwtServerInterceptor;
 import org.apache.camel.impl.DefaultConsumer;
 import org.apache.camel.spi.ClassResolver;
 import org.apache.camel.util.ObjectHelper;
@@ -129,7 +129,8 @@ public class GrpcConsumer extends DefaultConsumer {
         if (configuration.getAuthenticationType() == GrpcAuthType.JWT) {
             ObjectHelper.notNull(configuration.getJwtSecret(), "jwtSecret");
             
-            serverBuilder = serverBuilder.intercept(new JwtServerInterceptor(configuration.getJwtSecret(), configuration.getJwtIssuer(), configuration.getJwtSubject()));
+            serverBuilder = serverBuilder.intercept(new JwtServerInterceptor(configuration.getJwtAlgorithm(), configuration.getJwtSecret(),
+                                                                             configuration.getJwtIssuer(), configuration.getJwtSubject()));
         }
         
         server = serverBuilder.addService(ServerInterceptors.intercept(bindableService, headerInterceptor))

http://git-wip-us.apache.org/repos/asf/camel/blob/a558f54e/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/GrpcProducer.java
----------------------------------------------------------------------
diff --git a/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/GrpcProducer.java b/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/GrpcProducer.java
index aa7fa37..a411f8e 100644
--- a/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/GrpcProducer.java
+++ b/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/GrpcProducer.java
@@ -30,12 +30,12 @@ import io.netty.handler.ssl.SslProvider;
 import org.apache.camel.AsyncCallback;
 import org.apache.camel.AsyncProcessor;
 import org.apache.camel.Exchange;
+import org.apache.camel.component.grpc.auth.jwt.JwtCallCredentials;
+import org.apache.camel.component.grpc.auth.jwt.JwtHelper;
 import org.apache.camel.component.grpc.client.GrpcExchangeForwarder;
 import org.apache.camel.component.grpc.client.GrpcExchangeForwarderFactory;
 import org.apache.camel.component.grpc.client.GrpcResponseAggregationStreamObserver;
 import org.apache.camel.component.grpc.client.GrpcResponseRouterStreamObserver;
-import org.apache.camel.component.grpc.client.auth.jwt.JwtCallCredentials;
-import org.apache.camel.component.grpc.client.auth.jwt.JwtHelper;
 import org.apache.camel.impl.DefaultProducer;
 import org.apache.camel.spi.ClassResolver;
 import org.apache.camel.util.ObjectHelper;
@@ -105,7 +105,7 @@ public class GrpcProducer extends DefaultProducer implements AsyncProcessor {
             } else if (configuration.getAuthenticationType() == GrpcAuthType.JWT) {
                 ObjectHelper.notNull(configuration.getJwtSecret(), "jwtSecret");
                 
-                String jwtToken = JwtHelper.createJwtToken(configuration.getJwtSecret(), configuration.getJwtIssuer(), configuration.getJwtSubject());
+                String jwtToken = JwtHelper.createJwtToken(configuration.getJwtAlgorithm(), configuration.getJwtSecret(), configuration.getJwtIssuer(), configuration.getJwtSubject());
                 callCreds = new JwtCallCredentials(jwtToken);
             }
             

http://git-wip-us.apache.org/repos/asf/camel/blob/a558f54e/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/auth/jwt/JwtAlgorithm.java
----------------------------------------------------------------------
diff --git a/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/auth/jwt/JwtAlgorithm.java b/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/auth/jwt/JwtAlgorithm.java
new file mode 100644
index 0000000..9a61545
--- /dev/null
+++ b/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/auth/jwt/JwtAlgorithm.java
@@ -0,0 +1,37 @@
+/**
+ * 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.grpc.auth.jwt;
+
+/**
+ * Implemented JSON Web Token secret signing algorithms
+ */
+public enum JwtAlgorithm {
+    /**
+     * HmacSHA256 algorithm
+     */
+    HMAC256,
+
+    /**
+     * HmacSHA384 algorithm
+     */
+    HMAC384,
+
+    /**
+     * HmacSHA512 algorithm
+     */
+    HMAC512
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/a558f54e/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/auth/jwt/JwtCallCredentials.java
----------------------------------------------------------------------
diff --git a/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/auth/jwt/JwtCallCredentials.java b/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/auth/jwt/JwtCallCredentials.java
new file mode 100644
index 0000000..490c237
--- /dev/null
+++ b/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/auth/jwt/JwtCallCredentials.java
@@ -0,0 +1,66 @@
+/**
+ * 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.grpc.auth.jwt;
+
+import java.util.concurrent.Executor;
+
+import io.grpc.Attributes;
+import io.grpc.CallCredentials;
+import io.grpc.Metadata;
+import io.grpc.MethodDescriptor;
+import io.grpc.Status;
+import org.apache.camel.component.grpc.GrpcConstants;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+/**
+ * JSON Web Token client credentials generator and injector 
+ */
+public class JwtCallCredentials implements CallCredentials {
+    private static final Logger LOG = LoggerFactory.getLogger(JwtCallCredentials.class);
+    private final String jwtToken;
+
+    public JwtCallCredentials(String jwtToken) {
+        this.jwtToken = jwtToken;
+    }
+
+    @Override
+    public void applyRequestMetadata(MethodDescriptor<?, ?> method, Attributes attrs, Executor executor, MetadataApplier applier) {
+        String authority = attrs.get(ATTR_AUTHORITY);
+
+        LOG.debug("Using authority {} for credentials", authority);
+        executor.execute(new Runnable() {
+            @Override
+            public void run() {
+                try {
+                    LOG.debug("Start to apply for the JWT token header");
+                    Metadata headers = new Metadata();
+                    Metadata.Key<String> jwtKey = GrpcConstants.GRPC_JWT_METADATA_KEY;
+                    headers.put(jwtKey, jwtToken);
+                    applier.apply(headers);
+                } catch (Throwable e) {
+                    LOG.debug("Unable to set metadata credentials header", e);
+                    applier.fail(Status.UNAUTHENTICATED.withCause(e));
+                }
+            }
+        });
+    }
+
+    @Override
+    public void thisUsesUnstableApi() {
+    }
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/a558f54e/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/auth/jwt/JwtHelper.java
----------------------------------------------------------------------
diff --git a/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/auth/jwt/JwtHelper.java b/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/auth/jwt/JwtHelper.java
new file mode 100644
index 0000000..bf2de48
--- /dev/null
+++ b/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/auth/jwt/JwtHelper.java
@@ -0,0 +1,56 @@
+/**
+ * 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.grpc.auth.jwt;
+
+import java.io.UnsupportedEncodingException;
+
+import com.auth0.jwt.JWT;
+import com.auth0.jwt.algorithms.Algorithm;
+import com.auth0.jwt.exceptions.JWTCreationException;
+
+/**
+ * JSON Web Token credentials generator helper
+ */
+public final class JwtHelper {
+    private JwtHelper() {
+    }
+
+    public static String createJwtToken(JwtAlgorithm algorithmName, String secret, String issuer, String subject) {
+        try {
+            Algorithm algorithm = selectAlgorithm(algorithmName, secret);
+            String token = JWT.create().withIssuer(issuer).withSubject(subject).sign(algorithm);
+            return token;
+        } catch (JWTCreationException e) {
+            throw new IllegalArgumentException("Unable to create JWT token", e);
+        } catch (UnsupportedEncodingException e) {
+            throw new IllegalArgumentException("UTF-8 encoding not supported during JWT token creation", e);
+        }
+    }
+    
+    public static Algorithm selectAlgorithm(JwtAlgorithm algorithmName, String secret) throws IllegalArgumentException, UnsupportedEncodingException {
+        switch (algorithmName) {
+        case HMAC256:
+            return Algorithm.HMAC256(secret);
+        case HMAC384:
+            return Algorithm.HMAC384(secret);
+        case HMAC512:
+            return Algorithm.HMAC512(secret);
+        default:
+            throw new IllegalArgumentException("JWT algorithm " + algorithmName + " not implemented");
+        }
+    }
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/a558f54e/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/auth/jwt/JwtServerInterceptor.java
----------------------------------------------------------------------
diff --git a/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/auth/jwt/JwtServerInterceptor.java b/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/auth/jwt/JwtServerInterceptor.java
new file mode 100644
index 0000000..5186556
--- /dev/null
+++ b/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/auth/jwt/JwtServerInterceptor.java
@@ -0,0 +1,88 @@
+/**
+ * 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.grpc.auth.jwt;
+
+import java.io.UnsupportedEncodingException;
+
+import com.auth0.jwt.JWT;
+import com.auth0.jwt.JWTVerifier;
+import com.auth0.jwt.algorithms.Algorithm;
+import com.auth0.jwt.exceptions.JWTCreationException;
+import com.auth0.jwt.interfaces.DecodedJWT;
+import io.grpc.Context;
+import io.grpc.Contexts;
+import io.grpc.Metadata;
+import io.grpc.ServerCall;
+import io.grpc.ServerCall.Listener;
+import io.grpc.ServerCallHandler;
+import io.grpc.ServerInterceptor;
+import io.grpc.Status;
+import org.apache.camel.component.grpc.GrpcConstants;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+/**
+ * JSON Web Token credentials validator implementation
+ */
+public class JwtServerInterceptor implements ServerInterceptor {
+    private static final Logger LOG = LoggerFactory.getLogger(JwtServerInterceptor.class);
+
+    @SuppressWarnings("rawtypes")
+    private static final ServerCall.Listener NOOP_LISTENER = new ServerCall.Listener() {
+    };
+
+    private final JWTVerifier verifier;
+
+    public JwtServerInterceptor(JwtAlgorithm algorithm, String secret, String issuer, String subject) {
+        verifier = prepareJwtVerifier(algorithm, secret, issuer, subject);
+    }
+
+    @Override
+    @SuppressWarnings("unchecked")
+    public <ReqT, RespT> Listener<ReqT> interceptCall(ServerCall<ReqT, RespT> call, Metadata metadata, ServerCallHandler<ReqT, RespT> serverCallHandler) {
+        String jwtToken = metadata.get(GrpcConstants.GRPC_JWT_METADATA_KEY);
+        if (jwtToken == null) {
+            call.close(Status.UNAUTHENTICATED.withDescription("JWT Token is missing from metadata"), metadata);
+            return NOOP_LISTENER;
+        }
+
+        Context ctx;
+        try {
+            DecodedJWT verified = verifier.verify(jwtToken);
+            ctx = Context.current()
+                         .withValue(GrpcConstants.GRPC_JWT_USER_ID_CTX_KEY, verified.getSubject() == null ? "anonymous" : verified.getSubject())
+                         .withValue(GrpcConstants.GRPC_JWT_CTX_KEY, jwtToken);
+        } catch (Exception e) {
+            LOG.debug("JWT token verification failed - Unauthenticated");
+            call.close(Status.UNAUTHENTICATED.withDescription(e.getMessage()).withCause(e), metadata);
+            return NOOP_LISTENER;
+        }
+
+        return Contexts.interceptCall(ctx, call, metadata, serverCallHandler);
+    }
+    
+    public static JWTVerifier prepareJwtVerifier(JwtAlgorithm algorithmName, String secret, String issuer, String subject) {
+        try {
+            Algorithm algorithm = JwtHelper.selectAlgorithm(algorithmName, secret);
+            return JWT.require(algorithm).withIssuer(issuer).withSubject(subject).build();
+        } catch (JWTCreationException e) {
+            throw new IllegalArgumentException("Unable to create JWT verifier", e);
+        } catch (UnsupportedEncodingException e) {
+            throw new IllegalArgumentException("UTF-8 encoding not supported during JWT verifier creation", e);
+        }
+    }
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/a558f54e/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/client/auth/jwt/JwtCallCredentials.java
----------------------------------------------------------------------
diff --git a/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/client/auth/jwt/JwtCallCredentials.java b/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/client/auth/jwt/JwtCallCredentials.java
deleted file mode 100644
index 676f284..0000000
--- a/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/client/auth/jwt/JwtCallCredentials.java
+++ /dev/null
@@ -1,66 +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.component.grpc.client.auth.jwt;
-
-import java.util.concurrent.Executor;
-
-import io.grpc.Attributes;
-import io.grpc.CallCredentials;
-import io.grpc.Metadata;
-import io.grpc.MethodDescriptor;
-import io.grpc.Status;
-import org.apache.camel.component.grpc.GrpcConstants;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
-/**
- * JSON Web Token client credentials generator and injector 
- */
-public class JwtCallCredentials implements CallCredentials {
-    private static final Logger LOG = LoggerFactory.getLogger(JwtCallCredentials.class);
-    private final String jwtToken;
-
-    public JwtCallCredentials(String jwtToken) {
-        this.jwtToken = jwtToken;
-    }
-
-    @Override
-    public void applyRequestMetadata(MethodDescriptor<?, ?> method, Attributes attrs, Executor executor, MetadataApplier applier) {
-        String authority = attrs.get(ATTR_AUTHORITY);
-
-        LOG.debug("Using authority {} for credentials", authority);
-        executor.execute(new Runnable() {
-            @Override
-            public void run() {
-                try {
-                    LOG.debug("Start to apply for the JWT token header");
-                    Metadata headers = new Metadata();
-                    Metadata.Key<String> jwtKey = GrpcConstants.GRPC_JWT_METADATA_KEY;
-                    headers.put(jwtKey, jwtToken);
-                    applier.apply(headers);
-                } catch (Throwable e) {
-                    LOG.debug("Unable to set metadata credentials header", e);
-                    applier.fail(Status.UNAUTHENTICATED.withCause(e));
-                }
-            }
-        });
-    }
-
-    @Override
-    public void thisUsesUnstableApi() {
-    }
-}

http://git-wip-us.apache.org/repos/asf/camel/blob/a558f54e/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/client/auth/jwt/JwtHelper.java
----------------------------------------------------------------------
diff --git a/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/client/auth/jwt/JwtHelper.java b/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/client/auth/jwt/JwtHelper.java
deleted file mode 100644
index d58f3a2..0000000
--- a/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/client/auth/jwt/JwtHelper.java
+++ /dev/null
@@ -1,43 +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.component.grpc.client.auth.jwt;
-
-import java.io.UnsupportedEncodingException;
-
-import com.auth0.jwt.JWT;
-import com.auth0.jwt.algorithms.Algorithm;
-import com.auth0.jwt.exceptions.JWTCreationException;
-
-/**
- * JSON Web Token credentials generator helper
- */
-public final class JwtHelper {
-    private JwtHelper() {
-    }
-
-    public static String createJwtToken(String secret, String issuer, String subject) {
-        try {
-            Algorithm algorithm = Algorithm.HMAC256(secret);
-            String token = JWT.create().withIssuer(issuer).withSubject(subject).sign(algorithm);
-            return token;
-        } catch (JWTCreationException e) {
-            throw new IllegalArgumentException("Unable to create JWT token", e);
-        } catch (UnsupportedEncodingException e) {
-            throw new IllegalArgumentException("UTF-8 encoding not supported during JWT token creation", e);
-        }
-    }
-}

http://git-wip-us.apache.org/repos/asf/camel/blob/a558f54e/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/server/auth/jwt/JwtServerInterceptor.java
----------------------------------------------------------------------
diff --git a/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/server/auth/jwt/JwtServerInterceptor.java b/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/server/auth/jwt/JwtServerInterceptor.java
deleted file mode 100644
index f332b1e..0000000
--- a/components/camel-grpc/src/main/java/org/apache/camel/component/grpc/server/auth/jwt/JwtServerInterceptor.java
+++ /dev/null
@@ -1,96 +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.component.grpc.server.auth.jwt;
-
-import java.io.UnsupportedEncodingException;
-
-import com.auth0.jwt.JWT;
-import com.auth0.jwt.JWTVerifier;
-import com.auth0.jwt.algorithms.Algorithm;
-import com.auth0.jwt.exceptions.JWTCreationException;
-import com.auth0.jwt.interfaces.DecodedJWT;
-import io.grpc.Context;
-import io.grpc.Contexts;
-import io.grpc.Metadata;
-import io.grpc.ServerCall;
-import io.grpc.ServerCall.Listener;
-import io.grpc.ServerCallHandler;
-import io.grpc.ServerInterceptor;
-import io.grpc.Status;
-import org.apache.camel.component.grpc.GrpcConstants;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
-/**
- * JSON Web Token credentials validator implementation
- */
-public class JwtServerInterceptor implements ServerInterceptor {
-    private static final Logger LOG = LoggerFactory.getLogger(JwtServerInterceptor.class);
-
-    @SuppressWarnings("rawtypes")
-    private static final ServerCall.Listener NOOP_LISTENER = new ServerCall.Listener() {
-    };
-
-    private final JWTVerifier verifier;
-
-    public JwtServerInterceptor(String secret, String issuer, String subject) {
-        verifier = JwtHelper.prepareJwtVerifier(secret, issuer, subject);
-    }
-
-    @Override
-    @SuppressWarnings("unchecked")
-    public <ReqT, RespT> Listener<ReqT> interceptCall(ServerCall<ReqT, RespT> call, Metadata metadata, ServerCallHandler<ReqT, RespT> serverCallHandler) {
-        String jwtToken = metadata.get(GrpcConstants.GRPC_JWT_METADATA_KEY);
-        if (jwtToken == null) {
-            call.close(Status.UNAUTHENTICATED.withDescription("JWT Token is missing from metadata"), metadata);
-            return NOOP_LISTENER;
-        }
-
-        Context ctx;
-        try {
-            DecodedJWT verified = verifier.verify(jwtToken);
-            ctx = Context.current()
-                         .withValue(GrpcConstants.GRPC_JWT_USER_ID_CTX_KEY, verified.getSubject() == null ? "anonymous" : verified.getSubject())
-                         .withValue(GrpcConstants.GRPC_JWT_CTX_KEY, jwtToken);
-        } catch (Exception e) {
-            LOG.debug("JWT token verification failed - Unauthenticated");
-            call.close(Status.UNAUTHENTICATED.withDescription(e.getMessage()).withCause(e), metadata);
-            return NOOP_LISTENER;
-        }
-
-        return Contexts.interceptCall(ctx, call, metadata, serverCallHandler);
-    }
-    
-    /**
-     * JSON Web Token credentials validator helper
-     */
-    public static final class JwtHelper {
-        private JwtHelper() {
-        }
-        
-        public static JWTVerifier prepareJwtVerifier(String secret, String issuer, String subject) {
-            try {
-                Algorithm algorithm = Algorithm.HMAC256(secret);
-                return JWT.require(algorithm).withIssuer(issuer).withSubject(subject).build();
-            } catch (JWTCreationException e) {
-                throw new IllegalArgumentException("Unable to create JWT verifier", e);
-            } catch (UnsupportedEncodingException e) {
-                throw new IllegalArgumentException("UTF-8 encoding not supported during JWT verifier creation", e);
-            }
-        }
-    }
-}

http://git-wip-us.apache.org/repos/asf/camel/blob/a558f54e/components/camel-grpc/src/test/java/org/apache/camel/component/grpc/GrpcConsumerSecurityTest.java
----------------------------------------------------------------------
diff --git a/components/camel-grpc/src/test/java/org/apache/camel/component/grpc/GrpcConsumerSecurityTest.java b/components/camel-grpc/src/test/java/org/apache/camel/component/grpc/GrpcConsumerSecurityTest.java
index 9a89b9d..ee53b5d 100644
--- a/components/camel-grpc/src/test/java/org/apache/camel/component/grpc/GrpcConsumerSecurityTest.java
+++ b/components/camel-grpc/src/test/java/org/apache/camel/component/grpc/GrpcConsumerSecurityTest.java
@@ -28,8 +28,9 @@ import io.grpc.netty.NettyChannelBuilder;
 import io.grpc.stub.StreamObserver;
 import io.netty.handler.ssl.SslProvider;
 import org.apache.camel.builder.RouteBuilder;
-import org.apache.camel.component.grpc.client.auth.jwt.JwtCallCredentials;
-import org.apache.camel.component.grpc.client.auth.jwt.JwtHelper;
+import org.apache.camel.component.grpc.auth.jwt.JwtAlgorithm;
+import org.apache.camel.component.grpc.auth.jwt.JwtCallCredentials;
+import org.apache.camel.component.grpc.auth.jwt.JwtHelper;
 import org.apache.camel.component.mock.MockEndpoint;
 import org.apache.camel.test.AvailablePortFinder;
 import org.apache.camel.test.junit4.CamelTestSupport;
@@ -62,8 +63,8 @@ public class GrpcConsumerSecurityTest extends CamelTestSupport {
 
     @Before
     public void startGrpcChannels() throws SSLException {
-        String correctJwtToken = JwtHelper.createJwtToken(GRPC_JWT_CORRECT_SECRET, null, null);
-        String incorrectJwtToken = JwtHelper.createJwtToken(GRPC_JWT_INCORRECT_SECRET, null, null);
+        String correctJwtToken = JwtHelper.createJwtToken(JwtAlgorithm.HMAC256, GRPC_JWT_CORRECT_SECRET, null, null);
+        String incorrectJwtToken = JwtHelper.createJwtToken(JwtAlgorithm.HMAC256, GRPC_JWT_INCORRECT_SECRET, null, null);
         
         tlsChannel = NettyChannelBuilder.forAddress("localhost", GRPC_TLS_TEST_PORT)
                                         .sslContext(GrpcSslContexts.forClient()

http://git-wip-us.apache.org/repos/asf/camel/blob/a558f54e/components/camel-grpc/src/test/java/org/apache/camel/component/grpc/GrpcProducerSecurityTest.java
----------------------------------------------------------------------
diff --git a/components/camel-grpc/src/test/java/org/apache/camel/component/grpc/GrpcProducerSecurityTest.java b/components/camel-grpc/src/test/java/org/apache/camel/component/grpc/GrpcProducerSecurityTest.java
index 2ba3016..3b2b753 100644
--- a/components/camel-grpc/src/test/java/org/apache/camel/component/grpc/GrpcProducerSecurityTest.java
+++ b/components/camel-grpc/src/test/java/org/apache/camel/component/grpc/GrpcProducerSecurityTest.java
@@ -27,7 +27,8 @@ import io.grpc.stub.StreamObserver;
 import io.netty.handler.ssl.ClientAuth;
 import io.netty.handler.ssl.SslProvider;
 import org.apache.camel.builder.RouteBuilder;
-import org.apache.camel.component.grpc.server.auth.jwt.JwtServerInterceptor;
+import org.apache.camel.component.grpc.auth.jwt.JwtAlgorithm;
+import org.apache.camel.component.grpc.auth.jwt.JwtServerInterceptor;
 import org.apache.camel.test.AvailablePortFinder;
 import org.apache.camel.test.junit4.CamelTestSupport;
 import org.junit.AfterClass;
@@ -66,7 +67,7 @@ public class GrpcProducerSecurityTest extends CamelTestSupport {
         
         grpcServerWithJWT = NettyServerBuilder.forPort(GRPC_JWT_TEST_PORT)
                                               .addService(new PingPongImpl())
-                                              .intercept(new JwtServerInterceptor(GRPC_JWT_CORRECT_SECRET, null, null))
+                                              .intercept(new JwtServerInterceptor(JwtAlgorithm.HMAC256, GRPC_JWT_CORRECT_SECRET, null, null))
                                               .build()
                                               .start();