Merge branch 'gerrit/trinity' into 'gerrit/morpheus'
Change-Id: Id74f7a332fcd32351aa3bf6d4ffe91e5e7b73458
diff --git a/asterixdb/asterix-external-data/src/main/java/org/apache/asterix/external/library/ExternalLibraryManager.java b/asterixdb/asterix-external-data/src/main/java/org/apache/asterix/external/library/ExternalLibraryManager.java
index 050d9f0..1743695 100755
--- a/asterixdb/asterix-external-data/src/main/java/org/apache/asterix/external/library/ExternalLibraryManager.java
+++ b/asterixdb/asterix-external-data/src/main/java/org/apache/asterix/external/library/ExternalLibraryManager.java
@@ -48,6 +48,7 @@
import java.util.HashSet;
import java.util.List;
import java.util.Map;
+import java.util.Optional;
import java.util.Set;
import java.util.function.Function;
import java.util.zip.ZipEntry;
@@ -657,11 +658,10 @@
final INetworkSecurityConfig configuration = networkSecurityManager.getConfiguration();
KeyStore trustStore = KeyStore.getInstance(KeyStore.getDefaultType());
try (FileInputStream trustStoreFile = new FileInputStream(configuration.getTrustStoreFile())) {
- String ksPassword = configuration.getKeyStorePassword();
- trustStore.load(trustStoreFile,
- ksPassword == null || ksPassword.isEmpty() ? null : ksPassword.toCharArray());
+ Optional<char[]> ksPassword = configuration.getKeyStorePassword();
+ trustStore.load(trustStoreFile, ksPassword.orElse(null));
}
- SSLContext sslcontext = NetworkSecurityManager.newSSLContext(configuration);
+ SSLContext sslcontext = NetworkSecurityManager.newSSLContext(configuration, false);
SSLConnectionSocketFactory sslsf = new SSLConnectionSocketFactory(sslcontext, new String[] { "TLSv1.2" },
null, SSLConnectionSocketFactory.getDefaultHostnameVerifier());
return HttpClients.custom().setSSLSocketFactory(sslsf).build();
diff --git a/asterixdb/asterix-metadata/src/main/java/org/apache/asterix/metadata/RMIClientFactory.java b/asterixdb/asterix-metadata/src/main/java/org/apache/asterix/metadata/RMIClientFactory.java
index ce459e2..da802a7 100644
--- a/asterixdb/asterix-metadata/src/main/java/org/apache/asterix/metadata/RMIClientFactory.java
+++ b/asterixdb/asterix-metadata/src/main/java/org/apache/asterix/metadata/RMIClientFactory.java
@@ -68,7 +68,7 @@
protected SSLSocketFactory factory;
public RMITrustedClientSSLSocketFactory(INetworkSecurityConfig config) {
- this.factory = NetworkSecurityManager.newSSLContext(config).getSocketFactory();
+ this.factory = NetworkSecurityManager.newSSLContext(config, false).getSocketFactory();
}
public Socket createSocket(InetAddress host, int port) throws IOException {
diff --git a/asterixdb/asterix-metadata/src/main/java/org/apache/asterix/metadata/RMIServerFactory.java b/asterixdb/asterix-metadata/src/main/java/org/apache/asterix/metadata/RMIServerFactory.java
index 6a0edc0..845324a1 100644
--- a/asterixdb/asterix-metadata/src/main/java/org/apache/asterix/metadata/RMIServerFactory.java
+++ b/asterixdb/asterix-metadata/src/main/java/org/apache/asterix/metadata/RMIServerFactory.java
@@ -46,7 +46,7 @@
public ServerSocket createServerSocket(int port) throws IOException {
ServerSocketFactory socketFactory;
if (securityManager.getConfiguration().isSslEnabled()) {
- socketFactory = securityManager.newSSLContext().getServerSocketFactory();
+ socketFactory = securityManager.newSSLContext(false).getServerSocketFactory();
} else {
socketFactory = ServerSocketFactory.getDefault();
}
diff --git a/hyracks-fullstack/hyracks/hyracks-api/pom.xml b/hyracks-fullstack/hyracks/hyracks-api/pom.xml
index 7a4eb58..eee03f3 100644
--- a/hyracks-fullstack/hyracks/hyracks-api/pom.xml
+++ b/hyracks-fullstack/hyracks/hyracks-api/pom.xml
@@ -105,5 +105,9 @@
<groupId>com.google.guava</groupId>
<artifactId>guava</artifactId>
</dependency>
+ <dependency>
+ <groupId>io.netty</groupId>
+ <artifactId>netty-handler</artifactId>
+ </dependency>
</dependencies>
</project>
diff --git a/hyracks-fullstack/hyracks/hyracks-api/src/main/java/org/apache/hyracks/api/network/INetworkSecurityConfig.java b/hyracks-fullstack/hyracks/hyracks-api/src/main/java/org/apache/hyracks/api/network/INetworkSecurityConfig.java
index 7fc0335..e581c5a 100644
--- a/hyracks-fullstack/hyracks/hyracks-api/src/main/java/org/apache/hyracks/api/network/INetworkSecurityConfig.java
+++ b/hyracks-fullstack/hyracks/hyracks-api/src/main/java/org/apache/hyracks/api/network/INetworkSecurityConfig.java
@@ -24,6 +24,8 @@
import java.security.KeyStore;
import java.util.Optional;
+import io.netty.handler.ssl.ClientAuth;
+
public interface INetworkSecurityConfig extends Serializable {
/**
@@ -34,25 +36,51 @@
boolean isSslEnabled();
/**
- * Gets the key store to be used for secured connections
- *
- * @return the key store to be used
+ * Indicates how to handle client authentication when ssl is enabled
*/
- KeyStore getKeyStore();
+ ClientAuth getClientAuth();
/**
- * Gets a key store file to be used if {@link INetworkSecurityConfig#getKeyStore()} returns null.
+ * Gets the key store to be used for secured connections
+ *
+ * @return the key store to be used, if present
+ */
+ Optional<KeyStore> getKeyStore();
+
+ /**
+ * Gets a key store file, password pair to be used if {@link INetworkSecurityConfig#getKeyStore()} returns empty.
*
* @return the key store file
*/
File getKeyStoreFile();
/**
- * Gets the password for the key store file.
+ * Gets a password to be used to unlock or check integrity of the key store.
*
- * @return the password to the key store file
+ * @return the key store password, or {@link Optional#empty()}
*/
- String getKeyStorePassword();
+ Optional<char[]> getKeyStorePassword();
+
+ /**
+ * Gets the client key store to be used for client auth, if applicable.
+ *
+ * @return the client key store to be used for client auth, or {@link Optional#empty()}
+ */
+ Optional<KeyStore> getClientKeyStore();
+
+ /**
+ * Gets a client key store file to be used if {@link INetworkSecurityConfig#getClientKeyStore()} returns empty.
+ *
+ * @return the key store file
+ */
+ File getClientKeyStoreFile();
+
+ /**
+ * Gets a password to be used to unlock or check integrity of the client key store.
+ *
+ * @return the client key store password, or {@link Optional#empty()}
+ */
+ Optional<char[]> getClientKeyStorePassword();
/**
* Gets the trust store to be used for validating certificates of secured connections
diff --git a/hyracks-fullstack/hyracks/hyracks-api/src/main/java/org/apache/hyracks/api/network/INetworkSecurityManager.java b/hyracks-fullstack/hyracks/hyracks-api/src/main/java/org/apache/hyracks/api/network/INetworkSecurityManager.java
index eb52436..8462f91 100644
--- a/hyracks-fullstack/hyracks/hyracks-api/src/main/java/org/apache/hyracks/api/network/INetworkSecurityManager.java
+++ b/hyracks-fullstack/hyracks/hyracks-api/src/main/java/org/apache/hyracks/api/network/INetworkSecurityManager.java
@@ -28,14 +28,14 @@
*
* @return a new ssl context
*/
- SSLContext newSSLContext();
+ SSLContext newSSLContext(boolean clientMode);
/**
* Creates a new ssl engine based on the current configuration of this {@link INetworkSecurityManager}
*
* @return a new ssl engine
*/
- SSLEngine newSSLEngine();
+ SSLEngine newSSLEngine(boolean clientMode);
/**
* Sets the configuration to be used for this {@link INetworkSecurityManager}
diff --git a/hyracks-fullstack/hyracks/hyracks-ipc/pom.xml b/hyracks-fullstack/hyracks/hyracks-ipc/pom.xml
index 939f487..8157554 100644
--- a/hyracks-fullstack/hyracks/hyracks-ipc/pom.xml
+++ b/hyracks-fullstack/hyracks/hyracks-ipc/pom.xml
@@ -67,5 +67,9 @@
<groupId>org.apache.httpcomponents</groupId>
<artifactId>httpclient</artifactId>
</dependency>
+ <dependency>
+ <groupId>io.netty</groupId>
+ <artifactId>netty-handler</artifactId>
+ </dependency>
</dependencies>
</project>
diff --git a/hyracks-fullstack/hyracks/hyracks-ipc/src/main/java/org/apache/hyracks/ipc/security/NetworkSecurityConfig.java b/hyracks-fullstack/hyracks/hyracks-ipc/src/main/java/org/apache/hyracks/ipc/security/NetworkSecurityConfig.java
index bfcd623..a8bd087 100644
--- a/hyracks-fullstack/hyracks/hyracks-ipc/src/main/java/org/apache/hyracks/ipc/security/NetworkSecurityConfig.java
+++ b/hyracks-fullstack/hyracks/hyracks-ipc/src/main/java/org/apache/hyracks/ipc/security/NetworkSecurityConfig.java
@@ -31,6 +31,8 @@
import org.apache.hyracks.api.network.INetworkSecurityConfig;
+import io.netty.handler.ssl.ClientAuth;
+
public class NetworkSecurityConfig implements INetworkSecurityConfig {
private static final long serialVersionUID = 2L;
@@ -68,18 +70,38 @@
}
@Override
+ public ClientAuth getClientAuth() {
+ return ClientAuth.NONE;
+ }
+
+ @Override
public File getKeyStoreFile() {
return keyStoreFile;
}
@Override
- public String getKeyStorePassword() {
- return keyStorePassword;
+ public Optional<char[]> getKeyStorePassword() {
+ return keyStorePassword != null ? Optional.of(keyStorePassword.toCharArray()) : Optional.empty();
}
@Override
- public KeyStore getKeyStore() {
- return keyStore;
+ public Optional<KeyStore> getKeyStore() {
+ return Optional.ofNullable(keyStore);
+ }
+
+ @Override
+ public Optional<KeyStore> getClientKeyStore() {
+ return Optional.empty();
+ }
+
+ @Override
+ public File getClientKeyStoreFile() {
+ return null;
+ }
+
+ @Override
+ public Optional<char[]> getClientKeyStorePassword() {
+ return Optional.empty();
}
@Override
diff --git a/hyracks-fullstack/hyracks/hyracks-ipc/src/main/java/org/apache/hyracks/ipc/security/NetworkSecurityManager.java b/hyracks-fullstack/hyracks/hyracks-ipc/src/main/java/org/apache/hyracks/ipc/security/NetworkSecurityManager.java
index db524ca..d8f5cff 100644
--- a/hyracks-fullstack/hyracks/hyracks-ipc/src/main/java/org/apache/hyracks/ipc/security/NetworkSecurityManager.java
+++ b/hyracks-fullstack/hyracks/hyracks-ipc/src/main/java/org/apache/hyracks/ipc/security/NetworkSecurityManager.java
@@ -18,6 +18,7 @@
*/
package org.apache.hyracks.ipc.security;
+import java.io.File;
import java.io.FileInputStream;
import java.security.KeyStore;
import java.security.SecureRandom;
@@ -37,7 +38,7 @@
private volatile INetworkSecurityConfig config;
protected final ISocketChannelFactory sslSocketFactory;
- public static final String TSL_VERSION = "TLSv1.2";
+ public static final String TLS_VERSION = "TLSv1.2";
public NetworkSecurityManager(INetworkSecurityConfig config) {
this.config = config;
@@ -45,15 +46,16 @@
}
@Override
- public SSLContext newSSLContext() {
- return newSSLContext(config);
+ public SSLContext newSSLContext(boolean clientMode) {
+ return newSSLContext(config, clientMode);
}
@Override
- public SSLEngine newSSLEngine() {
+ public SSLEngine newSSLEngine(boolean clientMode) {
try {
- SSLContext ctx = newSSLContext();
- return ctx.createSSLEngine();
+ SSLEngine sslEngine = newSSLContext(clientMode).createSSLEngine();
+ sslEngine.setUseClientMode(clientMode);
+ return sslEngine;
} catch (Exception ex) {
throw new IllegalStateException("Failed to create SSLEngine", ex);
}
@@ -76,12 +78,22 @@
this.config = config;
}
- public static SSLContext newSSLContext(INetworkSecurityConfig config) {
+ public static SSLContext newSSLContext(INetworkSecurityConfig config, boolean clientMode) {
try {
- final char[] password = getKeyStorePassword(config);
- KeyStore engineKeyStore = config.getKeyStore();
- if (engineKeyStore == null) {
- engineKeyStore = loadKeyStoreFromFile(password, config);
+ KeyStore engineKeyStore;
+ final char[] password;
+ if (clientMode) {
+ password = config.getClientKeyStorePassword().orElse(null);
+ engineKeyStore = config.getClientKeyStore().orElse(null);
+ if (engineKeyStore == null) {
+ engineKeyStore = loadKeyStoreFromFile(password, config.getClientKeyStoreFile());
+ }
+ } else {
+ password = config.getKeyStorePassword().orElse(null);
+ engineKeyStore = config.getKeyStore().orElse(null);
+ if (engineKeyStore == null) {
+ engineKeyStore = loadKeyStoreFromFile(password, config.getKeyStoreFile());
+ }
}
final String defaultAlgorithm = KeyManagerFactory.getDefaultAlgorithm();
KeyManagerFactory keyManagerFactory = KeyManagerFactory.getInstance(defaultAlgorithm);
@@ -89,10 +101,10 @@
keyManagerFactory.init(engineKeyStore, password);
KeyStore trustStore = config.getTrustStore();
if (trustStore == null) {
- trustStore = loadTrustStoreFromFile(password, config);
+ trustStore = loadKeyStoreFromFile(password, config.getTrustStoreFile());
}
trustManagerFactory.init(trustStore);
- SSLContext ctx = SSLContext.getInstance(TSL_VERSION);
+ SSLContext ctx = SSLContext.getInstance(TLS_VERSION);
ctx.init(keyManagerFactory.getKeyManagers(), trustManagerFactory.getTrustManagers(), new SecureRandom());
return ctx;
} catch (Exception ex) {
@@ -100,28 +112,14 @@
}
}
- private static KeyStore loadKeyStoreFromFile(char[] password, INetworkSecurityConfig config) {
+ private static KeyStore loadKeyStoreFromFile(char[] password, File keystoreFile) {
try {
final KeyStore ks = KeyStore.getInstance(KeyStore.getDefaultType());
- ks.load(new FileInputStream(config.getKeyStoreFile()), password);
+ ks.load(new FileInputStream(keystoreFile), password);
return ks;
} catch (Exception e) {
throw new IllegalStateException("failed to load key store", e);
}
}
- private static KeyStore loadTrustStoreFromFile(char[] password, INetworkSecurityConfig config) {
- try {
- final KeyStore ks = KeyStore.getInstance(KeyStore.getDefaultType());
- ks.load(new FileInputStream(config.getTrustStoreFile()), password);
- return ks;
- } catch (Exception e) {
- throw new IllegalStateException("failed to load trust store", e);
- }
- }
-
- private static char[] getKeyStorePassword(INetworkSecurityConfig config) {
- final String pass = config.getKeyStorePassword();
- return pass == null || pass.isEmpty() ? null : pass.toCharArray();
- }
}
diff --git a/hyracks-fullstack/hyracks/hyracks-ipc/src/main/java/org/apache/hyracks/ipc/sockets/SslSocketChannelFactory.java b/hyracks-fullstack/hyracks/hyracks-ipc/src/main/java/org/apache/hyracks/ipc/sockets/SslSocketChannelFactory.java
index 2a2fb62..0e4b9da 100644
--- a/hyracks-fullstack/hyracks/hyracks-ipc/src/main/java/org/apache/hyracks/ipc/sockets/SslSocketChannelFactory.java
+++ b/hyracks-fullstack/hyracks/hyracks-ipc/src/main/java/org/apache/hyracks/ipc/sockets/SslSocketChannelFactory.java
@@ -36,15 +36,13 @@
@Override
public ISocketChannel createServerChannel(SocketChannel socketChannel) {
- final SSLEngine sslEngine = networkSecurityManager.newSSLEngine();
- sslEngine.setUseClientMode(false);
+ final SSLEngine sslEngine = networkSecurityManager.newSSLEngine(false);
return new SslSocketChannel(socketChannel, sslEngine);
}
@Override
public ISocketChannel createClientChannel(SocketChannel socketChannel) {
- final SSLEngine sslEngine = networkSecurityManager.newSSLEngine();
- sslEngine.setUseClientMode(true);
+ final SSLEngine sslEngine = networkSecurityManager.newSSLEngine(true);
return new SslSocketChannel(socketChannel, sslEngine);
}
}