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

dengzh pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/hive.git


The following commit(s) were added to refs/heads/master by this push:
     new 7e2af57fccc HIVE-26425: Skip SSL cert verification for downloading 
JWKS in HS2 (#3473)
7e2af57fccc is described below

commit 7e2af57fccc0e22e03103119df19715e04d4e18b
Author: Yu-Wen <[email protected]>
AuthorDate: Tue Aug 2 08:41:09 2022 +0800

    HIVE-26425: Skip SSL cert verification for downloading JWKS in HS2 (#3473)
---
 .../java/org/apache/hadoop/hive/conf/HiveConf.java |  3 ++
 .../apache/hive/service/auth/jwt/JWTValidator.java |  3 +-
 .../service/auth/jwt/URLBasedJWKSProvider.java     | 49 +++++++++++++++++++---
 3 files changed, 49 insertions(+), 6 deletions(-)

diff --git a/common/src/java/org/apache/hadoop/hive/conf/HiveConf.java 
b/common/src/java/org/apache/hadoop/hive/conf/HiveConf.java
index 0d1a4b586e4..de4c0b54db0 100644
--- a/common/src/java/org/apache/hadoop/hive/conf/HiveConf.java
+++ b/common/src/java/org/apache/hadoop/hive/conf/HiveConf.java
@@ -4250,6 +4250,9 @@ public class HiveConf extends Configuration {
     
HIVE_SERVER2_AUTHENTICATION_JWT_JWKS_URL("hive.server2.authentication.jwt.jwks.url",
 "",
         "URL of the file from where URLBasedJWKSProvider will try to load JWKS 
if JWT is enabled for the\n" +
         "authentication mode."),
+    
HIVE_SERVER2_AUTHENTICATION_JWT_JWKS_SKIP_SSL_CERT("hive.server2.authentication.jwt.jwks.skip.ssl.cert",
 false,
+        "When this is enabled, the SSL certificate verification will be 
skipped.\n" +
+        "This is meant to be used in a testing environment only. Do not use in 
production."),
 
     // HS2 SAML2.0 configuration
     HIVE_SERVER2_SAML_KEYSTORE_PATH("hive.server2.saml2.keystore.path", "",
diff --git 
a/service/src/java/org/apache/hive/service/auth/jwt/JWTValidator.java 
b/service/src/java/org/apache/hive/service/auth/jwt/JWTValidator.java
index a1b934fea41..80e981c7726 100644
--- a/service/src/java/org/apache/hive/service/auth/jwt/JWTValidator.java
+++ b/service/src/java/org/apache/hive/service/auth/jwt/JWTValidator.java
@@ -34,6 +34,7 @@ import org.slf4j.LoggerFactory;
 
 import javax.security.sasl.AuthenticationException;
 import java.io.IOException;
+import java.security.GeneralSecurityException;
 import java.security.Key;
 import java.text.ParseException;
 import java.util.Date;
@@ -51,7 +52,7 @@ public class JWTValidator {
 
   private final URLBasedJWKSProvider jwksProvider;
 
-  public JWTValidator(HiveConf conf) throws IOException, ParseException {
+  public JWTValidator(HiveConf conf) throws IOException, ParseException, 
GeneralSecurityException {
     this.jwksProvider = new URLBasedJWKSProvider(conf);
   }
 
diff --git 
a/service/src/java/org/apache/hive/service/auth/jwt/URLBasedJWKSProvider.java 
b/service/src/java/org/apache/hive/service/auth/jwt/URLBasedJWKSProvider.java
index ebf99e3b889..c8dcf6b667b 100644
--- 
a/service/src/java/org/apache/hive/service/auth/jwt/URLBasedJWKSProvider.java
+++ 
b/service/src/java/org/apache/hive/service/auth/jwt/URLBasedJWKSProvider.java
@@ -24,12 +24,22 @@ import com.nimbusds.jose.jwk.JWKMatcher;
 import com.nimbusds.jose.jwk.JWKSelector;
 import com.nimbusds.jose.jwk.JWKSet;
 import org.apache.hadoop.hive.conf.HiveConf;
+import org.apache.http.HttpEntity;
+import org.apache.http.client.methods.CloseableHttpResponse;
+import org.apache.http.client.methods.HttpGet;
+import org.apache.http.impl.client.CloseableHttpClient;
+import org.apache.http.impl.client.HttpClients;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
+import javax.net.ssl.SSLContext;
+import javax.net.ssl.X509TrustManager;
 import javax.security.sasl.AuthenticationException;
 import java.io.IOException;
-import java.net.URL;
+import java.security.GeneralSecurityException;
+import java.security.SecureRandom;
+import java.security.cert.CertificateException;
+import java.security.cert.X509Certificate;
 import java.text.ParseException;
 import java.util.ArrayList;
 import java.util.List;
@@ -43,7 +53,7 @@ public class URLBasedJWKSProvider {
   private final HiveConf conf;
   private List<JWKSet> jwkSets = new ArrayList<>();
 
-  public URLBasedJWKSProvider(HiveConf conf) throws IOException, 
ParseException {
+  public URLBasedJWKSProvider(HiveConf conf) throws IOException, 
ParseException, GeneralSecurityException {
     this.conf = conf;
     loadJWKSets();
   }
@@ -52,12 +62,41 @@ public class URLBasedJWKSProvider {
    * Fetches the JWKS and stores into memory. The JWKS are expected to be in 
the standard form as defined here -
    * https://datatracker.ietf.org/doc/html/rfc7517#appendix-A.
    */
-  private void loadJWKSets() throws IOException, ParseException {
+  private void loadJWKSets() throws IOException, ParseException, 
GeneralSecurityException {
     String jwksURL = HiveConf.getVar(conf, 
HiveConf.ConfVars.HIVE_SERVER2_AUTHENTICATION_JWT_JWKS_URL);
+    if (jwksURL == null || jwksURL.isEmpty()) {
+      throw new IOException("Invalid value of property: " + 
+          HiveConf.ConfVars.HIVE_SERVER2_AUTHENTICATION_JWT_JWKS_URL.varname);
+    }
     String[] jwksURLs = jwksURL.split(",");
     for (String urlString : jwksURLs) {
-      URL url = new URL(urlString);
-      jwkSets.add(JWKSet.load(url));
+      SSLContext context = null;
+      if (HiveConf.getBoolVar(conf, 
HiveConf.ConfVars.HIVE_SERVER2_AUTHENTICATION_JWT_JWKS_SKIP_SSL_CERT, false)) {
+        context = SSLContext.getInstance("TLS");
+        X509TrustManager trustAllManager = new X509TrustManager() {
+          @Override
+          public void checkClientTrusted(X509Certificate[] chain, String 
authType)
+              throws CertificateException {
+          }
+          @Override
+          public void checkServerTrusted(X509Certificate[] chain, String 
authType)
+              throws CertificateException {
+          }
+          @Override
+          public X509Certificate[] getAcceptedIssuers() {
+            return new X509Certificate[0];
+          }
+        };
+        context.init(null, new X509TrustManager[]{trustAllManager}, new 
SecureRandom());
+      }
+      HttpGet get = new HttpGet(urlString);
+      try (CloseableHttpClient httpClient = 
HttpClients.custom().setSSLContext(context).build();
+          CloseableHttpResponse response = httpClient.execute(get)) {
+        HttpEntity entity = response.getEntity();
+        if (entity != null) {
+          jwkSets.add(JWKSet.load(entity.getContent()));
+        }
+      }
       LOG.info("Loaded JWKS from " + urlString);
     }
   }

Reply via email to