You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@activemq.apache.org by jb...@apache.org on 2018/01/04 19:00:02 UTC
[1/2] activemq-artemis git commit: ARTEMIS-1548 Support CRL
Repository: activemq-artemis
Updated Branches:
refs/heads/master 7232302f0 -> fee083a62
ARTEMIS-1548 Support CRL
Add support for CRL in client authentication
Project: http://git-wip-us.apache.org/repos/asf/activemq-artemis/repo
Commit: http://git-wip-us.apache.org/repos/asf/activemq-artemis/commit/8c0e1e96
Tree: http://git-wip-us.apache.org/repos/asf/activemq-artemis/tree/8c0e1e96
Diff: http://git-wip-us.apache.org/repos/asf/activemq-artemis/diff/8c0e1e96
Branch: refs/heads/master
Commit: 8c0e1e96edd31689018fcba42fac74bea76e3b6f
Parents: 7232302
Author: raul.valdoleiros <ra...@ceiia.com>
Authored: Tue Dec 5 15:57:13 2017 +0000
Committer: Justin Bertram <jb...@apache.org>
Committed: Thu Jan 4 12:56:25 2018 -0600
----------------------------------------------------------------------
.../remoting/impl/netty/NettyConnector.java | 7 +-
.../remoting/impl/netty/TransportConstants.java | 6 +
.../core/remoting/impl/ssl/SSLSupport.java | 77 +++++-
.../core/remoting/impl/netty/NettyAcceptor.java | 7 +-
examples/features/standard/pom.xml | 2 +
.../standard/ssl-enabled-crl-mqtt/pom.xml | 115 +++++++++
.../standard/ssl-enabled-crl-mqtt/readme.md | 98 ++++++++
.../jms/example/MqttCrlEnabledExample.java | 83 +++++++
.../main/resources/activemq/server0/broker.xml | 36 +++
.../resources/activemq/server0/keystore1.jks | Bin 0 -> 2396 bytes
.../resources/activemq/server0/root.crl.pem | 12 +
.../resources/activemq/server0/truststore.jks | Bin 0 -> 1003 bytes
.../src/main/resources/client_not_revoked.jks | Bin 0 -> 2414 bytes
.../src/main/resources/client_revoked.jks | Bin 0 -> 2415 bytes
.../src/main/resources/truststore.jks | Bin 0 -> 1003 bytes
tests/integration-tests/pom.xml | 9 +
.../mqtt/imported/MQTTSecurityCRLTest.java | 247 +++++++++++++++++++
.../src/test/resources/client_not_revoked.jks | Bin 0 -> 2414 bytes
.../src/test/resources/client_revoked.jks | Bin 0 -> 2415 bytes
.../src/test/resources/keystore1.jks | Bin 0 -> 2396 bytes
.../resources/mqttCrl/client0/truststore.jks | Bin 0 -> 1003 bytes
.../resources/mqttCrl/client1/truststore.jks | Bin 0 -> 1003 bytes
.../src/test/resources/root.crl.pem | 12 +
.../src/test/resources/truststore.jks | Bin 0 -> 1003 bytes
24 files changed, 702 insertions(+), 9 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/8c0e1e96/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/remoting/impl/netty/NettyConnector.java
----------------------------------------------------------------------
diff --git a/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/remoting/impl/netty/NettyConnector.java b/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/remoting/impl/netty/NettyConnector.java
index 8faa22d..5d3b82d 100644
--- a/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/remoting/impl/netty/NettyConnector.java
+++ b/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/remoting/impl/netty/NettyConnector.java
@@ -206,6 +206,8 @@ public class NettyConnector extends AbstractConnector {
private String trustStorePassword;
+ private String crlPath;
+
private String enabledCipherSuites;
private String enabledProtocols;
@@ -338,6 +340,8 @@ public class NettyConnector extends AbstractConnector {
trustStorePassword = ConfigurationHelper.getPasswordProperty(TransportConstants.TRUSTSTORE_PASSWORD_PROP_NAME, TransportConstants.DEFAULT_TRUSTSTORE_PASSWORD, configuration, ActiveMQDefaultConfiguration.getPropMaskPassword(), ActiveMQDefaultConfiguration.getPropPasswordCodec());
+ crlPath = ConfigurationHelper.getStringProperty(TransportConstants.CRL_PATH_PROP_NAME, TransportConstants.DEFAULT_CRL_PATH, configuration);
+
enabledCipherSuites = ConfigurationHelper.getStringProperty(TransportConstants.ENABLED_CIPHER_SUITES_PROP_NAME, TransportConstants.DEFAULT_ENABLED_CIPHER_SUITES, configuration);
enabledProtocols = ConfigurationHelper.getStringProperty(TransportConstants.ENABLED_PROTOCOLS_PROP_NAME, TransportConstants.DEFAULT_ENABLED_PROTOCOLS, configuration);
@@ -358,6 +362,7 @@ public class NettyConnector extends AbstractConnector {
trustStoreProvider = TransportConstants.DEFAULT_TRUSTSTORE_PROVIDER;
trustStorePath = TransportConstants.DEFAULT_TRUSTSTORE_PATH;
trustStorePassword = TransportConstants.DEFAULT_TRUSTSTORE_PASSWORD;
+ crlPath = TransportConstants.DEFAULT_CRL_PATH;
enabledCipherSuites = TransportConstants.DEFAULT_ENABLED_CIPHER_SUITES;
enabledProtocols = TransportConstants.DEFAULT_ENABLED_PROTOCOLS;
verifyHost = TransportConstants.DEFAULT_VERIFY_HOST;
@@ -519,7 +524,7 @@ public class NettyConnector extends AbstractConnector {
if (System.getProperty(ACTIVEMQ_TRUSTSTORE_PASSWORD_PROP_NAME) != null) {
realTrustStorePassword = System.getProperty(ACTIVEMQ_TRUSTSTORE_PASSWORD_PROP_NAME);
}
- context = SSLSupport.createContext(realKeyStoreProvider, realKeyStorePath, realKeyStorePassword, realTrustStoreProvider, realTrustStorePath, realTrustStorePassword, trustAll);
+ context = SSLSupport.createContext(realKeyStoreProvider, realKeyStorePath, realKeyStorePassword, realTrustStoreProvider, realTrustStorePath, realTrustStorePassword, trustAll, crlPath);
}
} catch (Exception e) {
close();
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/8c0e1e96/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/remoting/impl/netty/TransportConstants.java
----------------------------------------------------------------------
diff --git a/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/remoting/impl/netty/TransportConstants.java b/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/remoting/impl/netty/TransportConstants.java
index 890b508..efc5eb0 100644
--- a/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/remoting/impl/netty/TransportConstants.java
+++ b/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/remoting/impl/netty/TransportConstants.java
@@ -95,6 +95,8 @@ public class TransportConstants {
public static final String TRUSTSTORE_PASSWORD_PROP_NAME = "trustStorePassword";
+ public static final String CRL_PATH_PROP_NAME = "crlPath";
+
public static final String ENABLED_CIPHER_SUITES_PROP_NAME = "enabledCipherSuites";
public static final String ENABLED_PROTOCOLS_PROP_NAME = "enabledProtocols";
@@ -189,6 +191,8 @@ public class TransportConstants {
public static final String DEFAULT_TRUSTSTORE_PASSWORD = null;
+ public static final String DEFAULT_CRL_PATH = null;
+
public static final String DEFAULT_ENABLED_CIPHER_SUITES = null;
public static final String DEFAULT_ENABLED_PROTOCOLS = null;
@@ -310,6 +314,7 @@ public class TransportConstants {
allowableAcceptorKeys.add(ActiveMQDefaultConfiguration.getPropMaskPassword());
allowableAcceptorKeys.add(ActiveMQDefaultConfiguration.getPropPasswordCodec());
allowableAcceptorKeys.add(TransportConstants.BACKLOG_PROP_NAME);
+ allowableAcceptorKeys.add(TransportConstants.CRL_PATH_PROP_NAME);
ALLOWABLE_ACCEPTOR_KEYS = Collections.unmodifiableSet(allowableAcceptorKeys);
@@ -356,6 +361,7 @@ public class TransportConstants {
allowableConnectorKeys.add(TransportConstants.NETTY_CONNECT_TIMEOUT);
allowableConnectorKeys.add(TransportConstants.USE_DEFAULT_SSL_CONTEXT_PROP_NAME);
allowableConnectorKeys.add(TransportConstants.HANDSHAKE_TIMEOUT);
+ allowableConnectorKeys.add(TransportConstants.CRL_PATH_PROP_NAME);
ALLOWABLE_CONNECTOR_KEYS = Collections.unmodifiableSet(allowableConnectorKeys);
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/8c0e1e96/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/remoting/impl/ssl/SSLSupport.java
----------------------------------------------------------------------
diff --git a/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/remoting/impl/ssl/SSLSupport.java b/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/remoting/impl/ssl/SSLSupport.java
index b4d9dbf..03b6e08 100644
--- a/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/remoting/impl/ssl/SSLSupport.java
+++ b/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/remoting/impl/ssl/SSLSupport.java
@@ -16,6 +16,15 @@
*/
package org.apache.activemq.artemis.core.remoting.impl.ssl;
+import java.security.Security;
+import java.security.cert.CRL;
+import java.security.cert.CertStore;
+import java.security.cert.CertificateFactory;
+import java.security.cert.CollectionCertStoreParameters;
+import java.security.cert.PKIXBuilderParameters;
+import java.security.cert.X509CertSelector;
+import java.util.Collection;
+import javax.net.ssl.CertPathTrustManagerParameters;
import javax.net.ssl.KeyManager;
import javax.net.ssl.KeyManagerFactory;
import javax.net.ssl.SSLContext;
@@ -30,11 +39,11 @@ import java.security.AccessController;
import java.security.KeyStore;
import java.security.PrivilegedAction;
import java.security.SecureRandom;
-
import org.apache.activemq.artemis.utils.ClassloadingUtil;
import io.netty.handler.ssl.util.InsecureTrustManagerFactory;
+
/**
* Please note, this class supports PKCS#11 keystores, but there are no specific tests in the ActiveMQ Artemis test-suite to
* validate/verify this works because this requires a functioning PKCS#11 provider which is not available by default
@@ -51,7 +60,18 @@ public class SSLSupport {
final String trustStorePath,
final String trustStorePassword) throws Exception {
- return SSLSupport.createContext(keystoreProvider, keystorePath, keystorePassword, trustStoreProvider, trustStorePath, trustStorePassword, false);
+ return SSLSupport.createContext(keystoreProvider, keystorePath, keystorePassword, trustStoreProvider, trustStorePath, trustStorePassword, false, null);
+ }
+
+ public static SSLContext createContext(final String keystoreProvider,
+ final String keystorePath,
+ final String keystorePassword,
+ final String trustStoreProvider,
+ final String trustStorePath,
+ final String trustStorePassword,
+ final String crlPath) throws Exception {
+
+ return SSLSupport.createContext(keystoreProvider, keystorePath, keystorePassword, trustStoreProvider, trustStorePath, trustStorePassword, false, crlPath);
}
public static SSLContext createContext(final String keystoreProvider,
@@ -61,9 +81,20 @@ public class SSLSupport {
final String trustStorePath,
final String trustStorePassword,
final boolean trustAll) throws Exception {
+ return SSLSupport.createContext(keystoreProvider, keystorePath, keystorePassword, trustStoreProvider, trustStorePath, trustStorePassword, trustAll, null);
+ }
+
+ public static SSLContext createContext(final String keystoreProvider,
+ final String keystorePath,
+ final String keystorePassword,
+ final String trustStoreProvider,
+ final String trustStorePath,
+ final String trustStorePassword,
+ final boolean trustAll,
+ final String crlPath) throws Exception {
SSLContext context = SSLContext.getInstance("TLS");
KeyManager[] keyManagers = SSLSupport.loadKeyManagers(keystoreProvider, keystorePath, keystorePassword);
- TrustManager[] trustManagers = SSLSupport.loadTrustManager(trustStoreProvider, trustStorePath, trustStorePassword, trustAll);
+ TrustManager[] trustManagers = SSLSupport.loadTrustManager(trustStoreProvider, trustStorePath, trustStorePassword, trustAll, crlPath);
context.init(keyManagers, trustManagers, new SecureRandom());
return context;
}
@@ -93,18 +124,50 @@ public class SSLSupport {
private static TrustManager[] loadTrustManager(final String trustStoreProvider,
final String trustStorePath,
final String trustStorePassword,
- final boolean trustAll) throws Exception {
+ final boolean trustAll,
+ final String crlPath) throws Exception {
if (trustAll) {
//This is useful for testing but not should be used outside of that purpose
return InsecureTrustManagerFactory.INSTANCE.getTrustManagers();
} else if (trustStorePath == null && (trustStoreProvider == null || !"PKCS11".equals(trustStoreProvider.toUpperCase()))) {
return null;
} else {
- TrustManagerFactory trustMgrFactory;
+ TrustManagerFactory trustMgrFactory = TrustManagerFactory.getInstance(TrustManagerFactory.getDefaultAlgorithm());
KeyStore trustStore = SSLSupport.loadKeystore(trustStoreProvider, trustStorePath, trustStorePassword);
- trustMgrFactory = TrustManagerFactory.getInstance(TrustManagerFactory.getDefaultAlgorithm());
- trustMgrFactory.init(trustStore);
+ boolean ocsp = Boolean.valueOf(Security.getProperty("ocsp.enable"));
+
+ boolean initialized = false;
+ if ((ocsp || crlPath != null) && TrustManagerFactory.getDefaultAlgorithm().equalsIgnoreCase("PKIX")) {
+ PKIXBuilderParameters pkixParams = new PKIXBuilderParameters(trustStore, new X509CertSelector());
+ if (crlPath != null) {
+ pkixParams.setRevocationEnabled(true);
+ Collection<? extends CRL> crlList = loadCRL(crlPath);
+ if (crlList != null) {
+ pkixParams.addCertStore(CertStore.getInstance("Collection", new CollectionCertStoreParameters(crlList)));
+ }
+ }
+ trustMgrFactory.init(new CertPathTrustManagerParameters(pkixParams));
+ initialized = true;
+ }
+
+ if (!initialized) {
+ trustMgrFactory.init(trustStore);
+ }
+
return trustMgrFactory.getTrustManagers();
+
+ }
+ }
+
+ private static Collection<? extends CRL> loadCRL(String crlPath) throws Exception {
+ if (crlPath == null) {
+ return null;
+ }
+
+ URL resource = SSLSupport.validateStoreURL(crlPath);
+
+ try (InputStream is = resource.openStream()) {
+ return CertificateFactory.getInstance("X.509").generateCRLs(is);
}
}
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/8c0e1e96/artemis-server/src/main/java/org/apache/activemq/artemis/core/remoting/impl/netty/NettyAcceptor.java
----------------------------------------------------------------------
diff --git a/artemis-server/src/main/java/org/apache/activemq/artemis/core/remoting/impl/netty/NettyAcceptor.java b/artemis-server/src/main/java/org/apache/activemq/artemis/core/remoting/impl/netty/NettyAcceptor.java
index 6141d6c..52c5b7e 100644
--- a/artemis-server/src/main/java/org/apache/activemq/artemis/core/remoting/impl/netty/NettyAcceptor.java
+++ b/artemis-server/src/main/java/org/apache/activemq/artemis/core/remoting/impl/netty/NettyAcceptor.java
@@ -156,6 +156,8 @@ public class NettyAcceptor extends AbstractAcceptor {
private final String trustStorePassword;
+ private final String crlPath;
+
private final String enabledCipherSuites;
private final String enabledProtocols;
@@ -259,6 +261,8 @@ public class NettyAcceptor extends AbstractAcceptor {
trustStorePassword = ConfigurationHelper.getPasswordProperty(TransportConstants.TRUSTSTORE_PASSWORD_PROP_NAME, TransportConstants.DEFAULT_TRUSTSTORE_PASSWORD, configuration, ActiveMQDefaultConfiguration.getPropMaskPassword(), ActiveMQDefaultConfiguration.getPropPasswordCodec());
+ crlPath = ConfigurationHelper.getStringProperty(TransportConstants.CRL_PATH_PROP_NAME, TransportConstants.DEFAULT_CRL_PATH, configuration);
+
enabledCipherSuites = ConfigurationHelper.getStringProperty(TransportConstants.ENABLED_CIPHER_SUITES_PROP_NAME, TransportConstants.DEFAULT_ENABLED_CIPHER_SUITES, configuration);
enabledProtocols = ConfigurationHelper.getStringProperty(TransportConstants.ENABLED_PROTOCOLS_PROP_NAME, TransportConstants.DEFAULT_ENABLED_PROTOCOLS, configuration);
@@ -273,6 +277,7 @@ public class NettyAcceptor extends AbstractAcceptor {
trustStoreProvider = TransportConstants.DEFAULT_TRUSTSTORE_PROVIDER;
trustStorePath = TransportConstants.DEFAULT_TRUSTSTORE_PATH;
trustStorePassword = TransportConstants.DEFAULT_TRUSTSTORE_PASSWORD;
+ crlPath = TransportConstants.DEFAULT_CRL_PATH;
enabledCipherSuites = TransportConstants.DEFAULT_ENABLED_CIPHER_SUITES;
enabledProtocols = TransportConstants.DEFAULT_ENABLED_PROTOCOLS;
needClientAuth = TransportConstants.DEFAULT_NEED_CLIENT_AUTH;
@@ -453,7 +458,7 @@ public class NettyAcceptor extends AbstractAcceptor {
throw new IllegalArgumentException("If \"" + TransportConstants.SSL_ENABLED_PROP_NAME +
"\" is true then \"" + TransportConstants.KEYSTORE_PATH_PROP_NAME + "\" must be non-null " +
"unless an alternative \"" + TransportConstants.KEYSTORE_PROVIDER_PROP_NAME + "\" has been specified.");
- context = SSLSupport.createContext(keyStoreProvider, keyStorePath, keyStorePassword, trustStoreProvider, trustStorePath, trustStorePassword);
+ context = SSLSupport.createContext(keyStoreProvider, keyStorePath, keyStorePassword, trustStoreProvider, trustStorePath, trustStorePassword, crlPath);
} catch (Exception e) {
IllegalStateException ise = new IllegalStateException("Unable to create NettyAcceptor for " + host + ":" + port);
ise.initCause(e);
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/8c0e1e96/examples/features/standard/pom.xml
----------------------------------------------------------------------
diff --git a/examples/features/standard/pom.xml b/examples/features/standard/pom.xml
index d254992..0d77a4e 100644
--- a/examples/features/standard/pom.xml
+++ b/examples/features/standard/pom.xml
@@ -102,6 +102,7 @@ under the License.
<module>xa-heuristic</module>
<module>xa-receive</module>
<module>xa-send</module>
+ <module>ssl-enabled-crl-mqtt</module>
</modules>
</profile>
<profile>
@@ -173,6 +174,7 @@ under the License.
<module>xa-heuristic</module>
<module>xa-receive</module>
<module>xa-send</module>
+ <module>ssl-enabled-crl-mqtt</module>
</modules>
</profile>
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/8c0e1e96/examples/features/standard/ssl-enabled-crl-mqtt/pom.xml
----------------------------------------------------------------------
diff --git a/examples/features/standard/ssl-enabled-crl-mqtt/pom.xml b/examples/features/standard/ssl-enabled-crl-mqtt/pom.xml
new file mode 100644
index 0000000..1c26f0d
--- /dev/null
+++ b/examples/features/standard/ssl-enabled-crl-mqtt/pom.xml
@@ -0,0 +1,115 @@
+<?xml version='1.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.
+-->
+
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
+ <modelVersion>4.0.0</modelVersion>
+
+ <parent>
+ <groupId>org.apache.activemq.examples.broker</groupId>
+ <artifactId>jms-examples</artifactId>
+ <version>2.5.0-SNAPSHOT</version>
+ </parent>
+
+ <artifactId>ssl-enabled-crl-mqtt</artifactId>
+ <packaging>jar</packaging>
+ <name>ActiveMQ Artemis Mqtt CRL Example</name>
+
+ <properties>
+ <activemq.basedir>${project.basedir}/../../../..</activemq.basedir>
+ </properties>
+
+ <dependencies>
+ <dependency>
+ <groupId>org.apache.activemq</groupId>
+ <artifactId>artemis-jms-client-all</artifactId>
+ <version>${project.version}</version>
+ </dependency>
+ <dependency>
+ <groupId>org.fusesource.mqtt-client</groupId>
+ <artifactId>mqtt-client</artifactId>
+ </dependency>
+ </dependencies>
+
+ <build>
+ <plugins>
+ <plugin>
+ <groupId>org.apache.activemq</groupId>
+ <artifactId>artemis-maven-plugin</artifactId>
+ <executions>
+ <execution>
+ <id>create</id>
+ <goals>
+ <goal>create</goal>
+ </goals>
+ <configuration>
+ <ignore>${noServer}</ignore>
+ </configuration>
+ </execution>
+ <execution>
+ <id>start</id>
+ <goals>
+ <goal>cli</goal>
+ </goals>
+ <configuration>
+ <ignore>${noServer}</ignore>
+ <spawn>true</spawn>
+ <testURI>tcp://localhost:61616</testURI>
+ <testUser>consumer</testUser>
+ <testPassword>activemq</testPassword>
+ <args>
+ <param>run</param>
+ </args>
+ </configuration>
+ </execution>
+ <execution>
+ <id>runClient</id>
+ <goals>
+ <goal>runClient</goal>
+ </goals>
+ <configuration>
+ <clientClass>org.apache.activemq.artemis.jms.example.MqttCrlEnabledExample</clientClass>
+ </configuration>
+ </execution>
+ <execution>
+ <id>stop</id>
+ <goals>
+ <goal>cli</goal>
+ </goals>
+ <configuration>
+ <ignore>${noServer}</ignore>
+ <args>
+ <param>stop</param>
+ </args>
+ </configuration>
+ </execution>
+ </executions>
+ <dependencies>
+ <dependency>
+ <groupId>org.apache.activemq.examples.broker</groupId>
+ <artifactId>ssl-enabled-crl-mqtt</artifactId>
+ <version>${project.version}</version>
+ </dependency>
+ </dependencies>
+ </plugin>
+ </plugins>
+ </build>
+
+</project>
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/8c0e1e96/examples/features/standard/ssl-enabled-crl-mqtt/readme.md
----------------------------------------------------------------------
diff --git a/examples/features/standard/ssl-enabled-crl-mqtt/readme.md b/examples/features/standard/ssl-enabled-crl-mqtt/readme.md
new file mode 100644
index 0000000..56be3ce
--- /dev/null
+++ b/examples/features/standard/ssl-enabled-crl-mqtt/readme.md
@@ -0,0 +1,98 @@
+# ActiveMQ Artemis MQTT CRL Example
+
+To run the example, simply type **mvn verify** from this directory, or **mvn -PnoServer verify** if you want to start and create the server manually.
+
+This example shows you how to configure 2-way SSL with CRL along with 2 different connections, one with a valid certificate and another with a revoked certificate.
+
+To configure 2-way SSL with CRL you need to configure the acceptor as follows:
+
+```
+<acceptor name="mqtt">tcp://0.0.0.0:1883?tcpSendBufferSize=1048576;tcpReceiveBufferSize=1048576;protocols=MQTT;useEpoll=true;sslEnabled=true;keyStorePath=${data.dir}/../etc/keystore1.jks;keyStorePassword=changeit;trustStorePath=${data.dir}/../etc/truststore.jks;keyStorePassword=changeit;crlPath=${data.dir}/../etc/root.crl.pem;needClientAuth=true</acceptor>`
+```
+
+In the server-side URL, the `keystore1.jks` is the key store file holding the server's key certificate. The `truststore.jks` is the file holding the certificates which the server trusts. The `root.crl.pem` is the file holding the revoked certificates. Notice also the `sslEnabled` and `needClientAuth` parameters which enable SSL and require clients to present their own certificate respectively.
+
+The various keystore files are generated using the following commands. Keep in mind that each common name should be different and the passwords should be `changeit`.
+
+```
+openssl genrsa -out ca.key 2048
+openssl req -new -x509 -days 1826 -key ca.key -out ca.crt
+touch certindex
+echo 01 > certserial
+echo 01 > crlnumber
+```
+
+## Create the ca.conf file:
+
+```
+[ ca ]
+default_ca = myca
+
+[ crl_ext ]
+# issuerAltName=issuer:copy #this would copy the issuer name to altname
+authorityKeyIdentifier=keyid:always
+
+[ myca ]
+dir = ./
+new_certs_dir = $dir
+unique_subject = no
+certificate = $dir/ca.crt
+database = $dir/certindex
+private_key = $dir/ca.key
+serial = $dir/certserial
+default_days = 730
+default_md = sha1
+policy = myca_policy
+x509_extensions = myca_extensions
+crlnumber = $dir/crlnumber
+default_crl_days = 730
+
+[ myca_policy ]
+commonName = supplied
+stateOrProvinceName = supplied
+countryName = optional
+emailAddress = optional
+organizationName = supplied
+organizationalUnitName = optional
+
+[ myca_extensions ]
+basicConstraints = CA:false
+subjectKeyIdentifier = hash
+authorityKeyIdentifier = keyid:always
+keyUsage = digitalSignature,keyEncipherment
+extendedKeyUsage = serverAuth, clientAuth
+crlDistributionPoints = URI:http://example.com/root.crl
+subjectAltName = @alt_names
+
+[alt_names]
+DNS.1 = example.com
+DNS.2 = *.example.com`
+```
+
+## Continue with the following commands:
+
+```
+openssl genrsa -out keystore1.key 2048
+openssl req -new -key keystore1.key -out keystore1.csr
+openssl ca -batch -config ca.conf -notext -in keystore1.csr -out keystore1.crt
+openssl genrsa -out client_revoked.key 2048
+openssl req -new -key client_revoked.key -out client_revoked.csr
+openssl ca -batch -config ca.conf -notext -in client_revoked.csr -out client_revoked.crt
+openssl genrsa -out client_not_revoked.key 2048
+openssl req -new -key client_not_revoked.key -out client_not_revoked.csr
+openssl ca -batch -config ca.conf -notext -in client_not_revoked.csr -out client_not_revoked.crt
+openssl ca -config ca.conf -gencrl -keyfile ca.key -cert ca.crt -out root.crl.pem
+openssl ca -config ca.conf -revoke client_revoked.crt -keyfile ca.key -cert ca.crt
+openssl ca -config ca.conf -gencrl -keyfile ca.key -cert ca.crt -out root.crl.pem
+
+openssl pkcs12 -export -name client_revoked -in client_revoked.crt -inkey client_revoked.key -out client_revoked.p12
+keytool -importkeystore -destkeystore client_revoked.jks -srckeystore client_revoked.p12 -srcstoretype pkcs12 -alias client_revoked
+
+openssl pkcs12 -export -name client_not_revoked -in client_not_revoked.crt -inkey client_not_revoked.key -out client_not_revoked.p12
+keytool -importkeystore -destkeystore client_not_revoked.jks -srckeystore client_not_revoked.p12 -srcstoretype pkcs12 -alias client_not_revoked
+
+openssl pkcs12 -export -name keystore1 -in keystore1.crt -inkey keystore1.key -out keystore1.p12
+keytool -importkeystore -destkeystore keystore1.jks -srckeystore keystore1.p12 -srcstoretype pkcs12 -alias keystore1
+
+keytool -import -trustcacerts -alias trust_key -file ca.crt -keystore truststore.jks
+```
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/8c0e1e96/examples/features/standard/ssl-enabled-crl-mqtt/src/main/java/org/apache/activemq/artemis/jms/example/MqttCrlEnabledExample.java
----------------------------------------------------------------------
diff --git a/examples/features/standard/ssl-enabled-crl-mqtt/src/main/java/org/apache/activemq/artemis/jms/example/MqttCrlEnabledExample.java b/examples/features/standard/ssl-enabled-crl-mqtt/src/main/java/org/apache/activemq/artemis/jms/example/MqttCrlEnabledExample.java
new file mode 100644
index 0000000..a4ddf6a
--- /dev/null
+++ b/examples/features/standard/ssl-enabled-crl-mqtt/src/main/java/org/apache/activemq/artemis/jms/example/MqttCrlEnabledExample.java
@@ -0,0 +1,83 @@
+/*
+ * 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.activemq.artemis.jms.example;
+
+import javax.net.ssl.SSLException;
+import java.util.concurrent.TimeUnit;
+
+import org.apache.activemq.artemis.core.remoting.impl.ssl.SSLSupport;
+import org.fusesource.mqtt.client.BlockingConnection;
+import org.fusesource.mqtt.client.MQTT;
+import org.fusesource.mqtt.client.Message;
+import org.fusesource.mqtt.client.QoS;
+import org.fusesource.mqtt.client.Topic;
+
+public class MqttCrlEnabledExample {
+
+ public static void main(final String[] args) throws Exception {
+ boolean exception = false;
+ try {
+ callBroker("truststore.jks", "changeit", "client_revoked.jks", "changeit");
+ } catch (SSLException e) {
+ exception = true;
+ }
+ if (!exception) {
+ throw new RuntimeException("The connection should be revoked");
+ }
+ callBroker("truststore.jks", "changeit", "client_not_revoked.jks", "changeit");
+ }
+
+ private static void callBroker(String truststorePath, String truststorePass, String keystorePath, String keystorePass) throws Exception {
+ BlockingConnection connection = null;
+
+ try {
+ connection = retrieveMQTTConnection("ssl://localhost:1883", truststorePath, truststorePass, keystorePath, keystorePass);
+ // Subscribe to topics
+ Topic[] topics = {new Topic("test/+/some/#", QoS.AT_MOST_ONCE)};
+ connection.subscribe(topics);
+
+ // Publish Messages
+ String payload = "This is message 1";
+
+ connection.publish("test/1/some/la", payload.getBytes(), QoS.AT_LEAST_ONCE, false);
+
+ Message message = connection.receive(5, TimeUnit.SECONDS);
+ System.out.println("Message received: " + new String(message.getPayload()));
+
+ } catch (Exception e) {
+ throw e;
+ } finally {
+ if (connection != null) {
+ connection.disconnect();
+ }
+ }
+ }
+
+ private static BlockingConnection retrieveMQTTConnection(String host, String truststorePath, String truststorePass, String keystorePath, String keystorePass) throws Exception {
+ MQTT mqtt = new MQTT();
+ mqtt.setConnectAttemptsMax(0);
+ mqtt.setReconnectAttemptsMax(0);
+ mqtt.setHost(host);
+ mqtt.setSslContext(SSLSupport.createContext("JKS", keystorePath, keystorePass, "JKS", truststorePath, truststorePass));
+ mqtt.setCleanSession(true);
+
+ BlockingConnection connection = mqtt.blockingConnection();
+ connection.connect();
+ return connection;
+ }
+
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/8c0e1e96/examples/features/standard/ssl-enabled-crl-mqtt/src/main/resources/activemq/server0/broker.xml
----------------------------------------------------------------------
diff --git a/examples/features/standard/ssl-enabled-crl-mqtt/src/main/resources/activemq/server0/broker.xml b/examples/features/standard/ssl-enabled-crl-mqtt/src/main/resources/activemq/server0/broker.xml
new file mode 100644
index 0000000..9877bd5
--- /dev/null
+++ b/examples/features/standard/ssl-enabled-crl-mqtt/src/main/resources/activemq/server0/broker.xml
@@ -0,0 +1,36 @@
+<?xml version="1.0" encoding="UTF-8" standalone="no"?>
+<!--
+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.
+-->
+<configuration xmlns="urn:activemq" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="urn:activemq /schema/artemis-server.xsd">
+ <core xmlns="urn:activemq:core">
+
+ <security-enabled>false</security-enabled>
+
+ <acceptors>
+ <acceptor name="netty-acceptor">tcp://localhost:61616</acceptor>
+ <acceptor name="mqtt">tcp://0.0.0.0:1883?protocols=MQTT;sslEnabled=true;keyStorePath=keystore1.jks;keyStorePassword=changeit;trustStorePath=truststore.jks;keyStorePassword=changeit;crlPath=root.crl.pem;needClientAuth=true</acceptor>
+ </acceptors>
+
+ <wildcard-addresses>
+ <routing-enabled>true</routing-enabled>
+ <delimiter>/</delimiter>
+ <any-words>#</any-words>
+ <single-word>+</single-word>
+ </wildcard-addresses>
+
+ </core>
+</configuration>
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/8c0e1e96/examples/features/standard/ssl-enabled-crl-mqtt/src/main/resources/activemq/server0/keystore1.jks
----------------------------------------------------------------------
diff --git a/examples/features/standard/ssl-enabled-crl-mqtt/src/main/resources/activemq/server0/keystore1.jks b/examples/features/standard/ssl-enabled-crl-mqtt/src/main/resources/activemq/server0/keystore1.jks
new file mode 100644
index 0000000..f1d8857
Binary files /dev/null and b/examples/features/standard/ssl-enabled-crl-mqtt/src/main/resources/activemq/server0/keystore1.jks differ
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/8c0e1e96/examples/features/standard/ssl-enabled-crl-mqtt/src/main/resources/activemq/server0/root.crl.pem
----------------------------------------------------------------------
diff --git a/examples/features/standard/ssl-enabled-crl-mqtt/src/main/resources/activemq/server0/root.crl.pem b/examples/features/standard/ssl-enabled-crl-mqtt/src/main/resources/activemq/server0/root.crl.pem
new file mode 100644
index 0000000..8938392
--- /dev/null
+++ b/examples/features/standard/ssl-enabled-crl-mqtt/src/main/resources/activemq/server0/root.crl.pem
@@ -0,0 +1,12 @@
+-----BEGIN X509 CRL-----
+MIIB2DCBwQIBATANBgkqhkiG9w0BAQUFADBpMQswCQYDVQQGEwJBVTETMBEGA1UE
+CAwKU29tZS1TdGF0ZTEhMB8GA1UECgwYSW50ZXJuZXQgV2lkZ2l0cyBQdHkgTHRk
+MRAwDgYDVQQDDAdhc2ZnZGZnMRAwDgYJKoZIhvcNAQkBFgFhFw0xNzEyMTQxODAw
+NDVaFw0xOTEyMTQxODAwNDVaMBQwEgIBAhcNMTcxMjE0MTgwMDM2WqAOMAwwCgYD
+VR0UBAMCAQIwDQYJKoZIhvcNAQEFBQADggEBACNiLQvZayn+ULeeSTnxcOOPaIku
+1E5AGG3M6uUBalECEpstzmXQELdiZvQb2BMRb1hpm1pNJ8uITjrjeT6bf1+KGgeN
+6lRMg36AwyQm8LGiE6ry9jF1OCHqERuImQUrRKWRUbL4hT79Fmji1xm9T9CA3RmE
+hjN5oHXM5avF+pm6aU2L2bZ03DhU4Ur0rOd1DCXcGWiZc7VJEQicSrG2R8dagFO/
+w0OUFiTahbdxSguNNU5kIuSltm4kfMM7GcFMb9/kMTTz/U+nUarm7ZzZozn7p/Sb
+9FjJ39JzFwq0jTT2bK+3WEWagQs9eNWAPjb5F3ofBSUleZ1f3rdhWWCSS+A=
+-----END X509 CRL-----
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/8c0e1e96/examples/features/standard/ssl-enabled-crl-mqtt/src/main/resources/activemq/server0/truststore.jks
----------------------------------------------------------------------
diff --git a/examples/features/standard/ssl-enabled-crl-mqtt/src/main/resources/activemq/server0/truststore.jks b/examples/features/standard/ssl-enabled-crl-mqtt/src/main/resources/activemq/server0/truststore.jks
new file mode 100644
index 0000000..5a8d79f
Binary files /dev/null and b/examples/features/standard/ssl-enabled-crl-mqtt/src/main/resources/activemq/server0/truststore.jks differ
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/8c0e1e96/examples/features/standard/ssl-enabled-crl-mqtt/src/main/resources/client_not_revoked.jks
----------------------------------------------------------------------
diff --git a/examples/features/standard/ssl-enabled-crl-mqtt/src/main/resources/client_not_revoked.jks b/examples/features/standard/ssl-enabled-crl-mqtt/src/main/resources/client_not_revoked.jks
new file mode 100644
index 0000000..7e47443
Binary files /dev/null and b/examples/features/standard/ssl-enabled-crl-mqtt/src/main/resources/client_not_revoked.jks differ
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/8c0e1e96/examples/features/standard/ssl-enabled-crl-mqtt/src/main/resources/client_revoked.jks
----------------------------------------------------------------------
diff --git a/examples/features/standard/ssl-enabled-crl-mqtt/src/main/resources/client_revoked.jks b/examples/features/standard/ssl-enabled-crl-mqtt/src/main/resources/client_revoked.jks
new file mode 100644
index 0000000..8d6f480
Binary files /dev/null and b/examples/features/standard/ssl-enabled-crl-mqtt/src/main/resources/client_revoked.jks differ
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/8c0e1e96/examples/features/standard/ssl-enabled-crl-mqtt/src/main/resources/truststore.jks
----------------------------------------------------------------------
diff --git a/examples/features/standard/ssl-enabled-crl-mqtt/src/main/resources/truststore.jks b/examples/features/standard/ssl-enabled-crl-mqtt/src/main/resources/truststore.jks
new file mode 100644
index 0000000..5a8d79f
Binary files /dev/null and b/examples/features/standard/ssl-enabled-crl-mqtt/src/main/resources/truststore.jks differ
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/8c0e1e96/tests/integration-tests/pom.xml
----------------------------------------------------------------------
diff --git a/tests/integration-tests/pom.xml b/tests/integration-tests/pom.xml
index 1394bae..0249033 100644
--- a/tests/integration-tests/pom.xml
+++ b/tests/integration-tests/pom.xml
@@ -481,6 +481,15 @@
</execution>
</executions>
</plugin>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-resources-plugin</artifactId>
+ <configuration>
+ <nonFilteredFileExtensions>
+ <nonFilteredFileExtension>jks</nonFilteredFileExtension>
+ </nonFilteredFileExtensions>
+ </configuration>
+ </plugin>
</plugins>
</build>
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/8c0e1e96/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/mqtt/imported/MQTTSecurityCRLTest.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/mqtt/imported/MQTTSecurityCRLTest.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/mqtt/imported/MQTTSecurityCRLTest.java
new file mode 100644
index 0000000..4f88661
--- /dev/null
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/mqtt/imported/MQTTSecurityCRLTest.java
@@ -0,0 +1,247 @@
+/**
+ * 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
+ * <p>
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * <p>
+ * 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.activemq.artemis.tests.integration.mqtt.imported;
+
+import javax.net.ssl.SSLContext;
+import javax.net.ssl.SSLException;
+import java.io.IOException;
+import java.util.concurrent.TimeUnit;
+
+import org.apache.activemq.artemis.api.core.TransportConfiguration;
+import org.apache.activemq.artemis.core.config.Configuration;
+import org.apache.activemq.artemis.core.config.WildcardConfiguration;
+import org.apache.activemq.artemis.core.remoting.impl.netty.NettyAcceptorFactory;
+import org.apache.activemq.artemis.core.remoting.impl.netty.TransportConstants;
+import org.apache.activemq.artemis.core.remoting.impl.ssl.SSLSupport;
+import org.apache.activemq.artemis.core.server.ActiveMQServer;
+import org.apache.activemq.artemis.tests.util.ActiveMQTestBase;
+import org.fusesource.mqtt.client.BlockingConnection;
+import org.fusesource.mqtt.client.MQTT;
+import org.fusesource.mqtt.client.Message;
+import org.fusesource.mqtt.client.QoS;
+import org.fusesource.mqtt.client.Topic;
+import org.junit.Test;
+
+public class MQTTSecurityCRLTest extends ActiveMQTestBase {
+ /**
+ * These artifacts are required for testing mqtt with CRL
+ * <p>
+ * openssl genrsa -out ca.key 2048
+ * openssl req -new -x509 -days 1826 -key ca.key -out ca.crt
+ * touch certindex
+ * echo 01 > certserial
+ * echo 01 > crlnumber
+ * <p>
+ * Create ca.conf file with
+ * <p>
+ * [ ca ]
+ * default_ca = myca
+ * <p>
+ * [ crl_ext ]
+ * # issuerAltName=issuer:copy #this would copy the issuer name to altname
+ * authorityKeyIdentifier=keyid:always
+ * <p>
+ * [ myca ]
+ * dir = ./
+ * new_certs_dir = $dir
+ * unique_subject = no
+ * certificate = $dir/ca.crt
+ * database = $dir/certindex
+ * private_key = $dir/ca.key
+ * serial = $dir/certserial
+ * default_days = 730
+ * default_md = sha1
+ * policy = myca_policy
+ * x509_extensions = myca_extensions
+ * crlnumber = $dir/crlnumber
+ * default_crl_days = 730
+ * <p>
+ * [ myca_policy ]
+ * commonName = supplied
+ * stateOrProvinceName = supplied
+ * countryName = optional
+ * emailAddress = optional
+ * organizationName = supplied
+ * organizationalUnitName = optional
+ * <p>
+ * [ myca_extensions ]
+ * basicConstraints = CA:false
+ * subjectKeyIdentifier = hash
+ * authorityKeyIdentifier = keyid:always
+ * keyUsage = digitalSignature,keyEncipherment
+ * extendedKeyUsage = serverAuth, clientAuth
+ * crlDistributionPoints = URI:http://example.com/root.crl
+ * subjectAltName = @alt_names
+ * <p>
+ * [alt_names]
+ * DNS.1 = example.com
+ * DNS.2 = *.example.com
+ * <p>
+ * Continue executing the commands:
+ * <p>
+ * openssl genrsa -out keystore1.key 2048
+ * openssl req -new -key keystore1.key -out keystore1.csr
+ * openssl ca -batch -config ca.conf -notext -in keystore1.csr -out keystore1.crt
+ * openssl genrsa -out client_revoked.key 2048
+ * openssl req -new -key client_revoked.key -out client_revoked.csr
+ * openssl ca -batch -config ca.conf -notext -in client_revoked.csr -out client_revoked.crt
+ * openssl genrsa -out client_not_revoked.key 2048
+ * openssl req -new -key client_not_revoked.key -out client_not_revoked.csr
+ * openssl ca -batch -config ca.conf -notext -in client_not_revoked.csr -out client_not_revoked.crt
+ * openssl ca -config ca.conf -gencrl -keyfile ca.key -cert ca.crt -out root.crl.pem
+ * openssl ca -config ca.conf -revoke client_revoked.crt -keyfile ca.key -cert ca.crt
+ * openssl ca -config ca.conf -gencrl -keyfile ca.key -cert ca.crt -out root.crl.pem
+ * <p>
+ * openssl pkcs12 -export -name client_revoked -in client_revoked.crt -inkey client_revoked.key -out client_revoked.p12
+ * keytool -importkeystore -destkeystore client_revoked.jks -srckeystore client_revoked.p12 -srcstoretype pkcs12 -alias client_revoked
+ * <p>
+ * openssl pkcs12 -export -name client_not_revoked -in client_not_revoked.crt -inkey client_not_revoked.key -out client_not_revoked.p12
+ * keytool -importkeystore -destkeystore client_not_revoked.jks -srckeystore client_not_revoked.p12 -srcstoretype pkcs12 -alias client_not_revoked
+ * <p>
+ * openssl pkcs12 -export -name keystore1 -in keystore1.crt -inkey keystore1.key -out keystore1.p12
+ * keytool -importkeystore -destkeystore keystore1.jks -srckeystore keystore1.p12 -srcstoretype pkcs12 -alias keystore1
+ * <p>
+ * keytool -import -trustcacerts -alias trust_key -file ca.crt -keystore truststore.jks
+ */
+
+ @Test(expected = SSLException.class)
+ public void crlRevokedTest() throws Exception {
+
+ ActiveMQServer server1 = initServer();
+ BlockingConnection connection1 = null;
+ try {
+ server1.start();
+
+ while (!server1.isStarted()) {
+ Thread.sleep(50);
+ }
+
+ connection1 = retrieveMQTTConnection("ssl://localhost:1883", "truststore.jks", "changeit", "client_revoked.jks", "changeit");
+
+ // Subscribe to topics
+ Topic[] topics = {new Topic("test/+/some/#", QoS.AT_MOST_ONCE)};
+ connection1.subscribe(topics);
+
+ // Publish Messages
+ String payload1 = "This is message 1";
+
+ connection1.publish("test/1/some/la", payload1.getBytes(), QoS.AT_LEAST_ONCE, false);
+
+ Message message1 = connection1.receive(5, TimeUnit.SECONDS);
+
+ assertEquals(payload1, new String(message1.getPayload()));
+
+ } finally {
+ if (connection1 != null) {
+ connection1.disconnect();
+ }
+ if (server1.isStarted()) {
+ server1.stop();
+ }
+ }
+ }
+
+ @Test
+ public void crlNotRevokedTest() throws Exception {
+
+ ActiveMQServer server1 = initServer();
+ BlockingConnection connection1 = null;
+ try {
+ server1.start();
+
+ while (!server1.isStarted()) {
+ Thread.sleep(50);
+ }
+
+ connection1 = retrieveMQTTConnection("ssl://localhost:1883", "truststore.jks", "changeit", "client_not_revoked.jks", "changeit");
+
+ // Subscribe to topics
+ Topic[] topics = {new Topic("test/+/some/#", QoS.AT_MOST_ONCE)};
+ connection1.subscribe(topics);
+
+ // Publish Messages
+ String payload1 = "This is message 1";
+
+ connection1.publish("test/1/some/la", payload1.getBytes(), QoS.AT_LEAST_ONCE, false);
+
+ Message message1 = connection1.receive(5, TimeUnit.SECONDS);
+
+ assertEquals(payload1, new String(message1.getPayload()));
+
+ } finally {
+ if (connection1 != null) {
+ connection1.disconnect();
+ }
+ if (server1.isStarted()) {
+ server1.stop();
+ }
+ }
+ }
+
+
+ private ActiveMQServer initServer() throws Exception {
+ Configuration configuration = createDefaultNettyConfig().setSecurityEnabled(false);
+
+ addMqttTransportConfiguration(configuration);
+ addWildCardConfiguration(configuration);
+
+ ActiveMQServer server = createServer(true, configuration);
+ return server;
+ }
+
+ private void addWildCardConfiguration(Configuration configuration) {
+ WildcardConfiguration wildcardConfiguration = new WildcardConfiguration();
+ wildcardConfiguration.setAnyWords('#');
+ wildcardConfiguration.setDelimiter('/');
+ wildcardConfiguration.setRoutingEnabled(true);
+ wildcardConfiguration.setSingleWord('+');
+
+ configuration.setWildCardConfiguration(wildcardConfiguration);
+ }
+
+ private void addMqttTransportConfiguration(Configuration configuration) throws IOException {
+ TransportConfiguration transportConfiguration = new TransportConfiguration(NettyAcceptorFactory.class.getCanonicalName(), null, "mqtt", null);
+
+ transportConfiguration.getParams().put(TransportConstants.SSL_ENABLED_PROP_NAME, true);
+ transportConfiguration.getParams().put(TransportConstants.TRUSTSTORE_PATH_PROP_NAME, "truststore.jks");
+ transportConfiguration.getParams().put(TransportConstants.TRUSTSTORE_PASSWORD_PROP_NAME, "changeit");
+ transportConfiguration.getParams().put(TransportConstants.KEYSTORE_PATH_PROP_NAME, "keystore1.jks");
+ transportConfiguration.getParams().put(TransportConstants.KEYSTORE_PASSWORD_PROP_NAME, "changeit");
+ transportConfiguration.getParams().put(TransportConstants.CRL_PATH_PROP_NAME, "root.crl.pem");
+ transportConfiguration.getParams().put(TransportConstants.NEED_CLIENT_AUTH_PROP_NAME, "true");
+ transportConfiguration.getParams().put(TransportConstants.PORT_PROP_NAME, "1883");
+ transportConfiguration.getParams().put(TransportConstants.HOST_PROP_NAME, "localhost");
+ transportConfiguration.getParams().put(TransportConstants.PROTOCOLS_PROP_NAME, "MQTT");
+
+ configuration.getAcceptorConfigurations().add(transportConfiguration);
+ }
+
+ private BlockingConnection retrieveMQTTConnection(String host, String truststorePath, String truststorePass, String keystorePath, String keystorePass) throws Exception {
+ MQTT mqtt = new MQTT();
+ mqtt.setConnectAttemptsMax(1);
+ mqtt.setReconnectAttemptsMax(0);
+ mqtt.setHost(host);
+ SSLContext sslContext = SSLSupport.createContext(TransportConstants.DEFAULT_KEYSTORE_PROVIDER, keystorePath, keystorePass, TransportConstants.DEFAULT_TRUSTSTORE_PROVIDER, truststorePath, truststorePass);
+ mqtt.setSslContext(sslContext);
+
+ BlockingConnection connection = mqtt.blockingConnection();
+ connection.connect();
+ return connection;
+ }
+
+
+}
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/8c0e1e96/tests/integration-tests/src/test/resources/client_not_revoked.jks
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/resources/client_not_revoked.jks b/tests/integration-tests/src/test/resources/client_not_revoked.jks
new file mode 100644
index 0000000..7e47443
Binary files /dev/null and b/tests/integration-tests/src/test/resources/client_not_revoked.jks differ
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/8c0e1e96/tests/integration-tests/src/test/resources/client_revoked.jks
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/resources/client_revoked.jks b/tests/integration-tests/src/test/resources/client_revoked.jks
new file mode 100644
index 0000000..8d6f480
Binary files /dev/null and b/tests/integration-tests/src/test/resources/client_revoked.jks differ
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/8c0e1e96/tests/integration-tests/src/test/resources/keystore1.jks
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/resources/keystore1.jks b/tests/integration-tests/src/test/resources/keystore1.jks
new file mode 100644
index 0000000..f1d8857
Binary files /dev/null and b/tests/integration-tests/src/test/resources/keystore1.jks differ
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/8c0e1e96/tests/integration-tests/src/test/resources/mqttCrl/client0/truststore.jks
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/resources/mqttCrl/client0/truststore.jks b/tests/integration-tests/src/test/resources/mqttCrl/client0/truststore.jks
new file mode 100644
index 0000000..5a8d79f
Binary files /dev/null and b/tests/integration-tests/src/test/resources/mqttCrl/client0/truststore.jks differ
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/8c0e1e96/tests/integration-tests/src/test/resources/mqttCrl/client1/truststore.jks
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/resources/mqttCrl/client1/truststore.jks b/tests/integration-tests/src/test/resources/mqttCrl/client1/truststore.jks
new file mode 100644
index 0000000..5a8d79f
Binary files /dev/null and b/tests/integration-tests/src/test/resources/mqttCrl/client1/truststore.jks differ
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/8c0e1e96/tests/integration-tests/src/test/resources/root.crl.pem
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/resources/root.crl.pem b/tests/integration-tests/src/test/resources/root.crl.pem
new file mode 100644
index 0000000..8938392
--- /dev/null
+++ b/tests/integration-tests/src/test/resources/root.crl.pem
@@ -0,0 +1,12 @@
+-----BEGIN X509 CRL-----
+MIIB2DCBwQIBATANBgkqhkiG9w0BAQUFADBpMQswCQYDVQQGEwJBVTETMBEGA1UE
+CAwKU29tZS1TdGF0ZTEhMB8GA1UECgwYSW50ZXJuZXQgV2lkZ2l0cyBQdHkgTHRk
+MRAwDgYDVQQDDAdhc2ZnZGZnMRAwDgYJKoZIhvcNAQkBFgFhFw0xNzEyMTQxODAw
+NDVaFw0xOTEyMTQxODAwNDVaMBQwEgIBAhcNMTcxMjE0MTgwMDM2WqAOMAwwCgYD
+VR0UBAMCAQIwDQYJKoZIhvcNAQEFBQADggEBACNiLQvZayn+ULeeSTnxcOOPaIku
+1E5AGG3M6uUBalECEpstzmXQELdiZvQb2BMRb1hpm1pNJ8uITjrjeT6bf1+KGgeN
+6lRMg36AwyQm8LGiE6ry9jF1OCHqERuImQUrRKWRUbL4hT79Fmji1xm9T9CA3RmE
+hjN5oHXM5avF+pm6aU2L2bZ03DhU4Ur0rOd1DCXcGWiZc7VJEQicSrG2R8dagFO/
+w0OUFiTahbdxSguNNU5kIuSltm4kfMM7GcFMb9/kMTTz/U+nUarm7ZzZozn7p/Sb
+9FjJ39JzFwq0jTT2bK+3WEWagQs9eNWAPjb5F3ofBSUleZ1f3rdhWWCSS+A=
+-----END X509 CRL-----
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/8c0e1e96/tests/integration-tests/src/test/resources/truststore.jks
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/resources/truststore.jks b/tests/integration-tests/src/test/resources/truststore.jks
new file mode 100644
index 0000000..5a8d79f
Binary files /dev/null and b/tests/integration-tests/src/test/resources/truststore.jks differ
[2/2] activemq-artemis git commit: This closes #1715
Posted by jb...@apache.org.
This closes #1715
Project: http://git-wip-us.apache.org/repos/asf/activemq-artemis/repo
Commit: http://git-wip-us.apache.org/repos/asf/activemq-artemis/commit/fee083a6
Tree: http://git-wip-us.apache.org/repos/asf/activemq-artemis/tree/fee083a6
Diff: http://git-wip-us.apache.org/repos/asf/activemq-artemis/diff/fee083a6
Branch: refs/heads/master
Commit: fee083a621fefd9ceb31d8bbf2021a717125967d
Parents: 7232302 8c0e1e9
Author: Justin Bertram <jb...@apache.org>
Authored: Thu Jan 4 12:56:49 2018 -0600
Committer: Justin Bertram <jb...@apache.org>
Committed: Thu Jan 4 12:56:49 2018 -0600
----------------------------------------------------------------------
.../remoting/impl/netty/NettyConnector.java | 7 +-
.../remoting/impl/netty/TransportConstants.java | 6 +
.../core/remoting/impl/ssl/SSLSupport.java | 77 +++++-
.../core/remoting/impl/netty/NettyAcceptor.java | 7 +-
examples/features/standard/pom.xml | 2 +
.../standard/ssl-enabled-crl-mqtt/pom.xml | 115 +++++++++
.../standard/ssl-enabled-crl-mqtt/readme.md | 98 ++++++++
.../jms/example/MqttCrlEnabledExample.java | 83 +++++++
.../main/resources/activemq/server0/broker.xml | 36 +++
.../resources/activemq/server0/keystore1.jks | Bin 0 -> 2396 bytes
.../resources/activemq/server0/root.crl.pem | 12 +
.../resources/activemq/server0/truststore.jks | Bin 0 -> 1003 bytes
.../src/main/resources/client_not_revoked.jks | Bin 0 -> 2414 bytes
.../src/main/resources/client_revoked.jks | Bin 0 -> 2415 bytes
.../src/main/resources/truststore.jks | Bin 0 -> 1003 bytes
tests/integration-tests/pom.xml | 9 +
.../mqtt/imported/MQTTSecurityCRLTest.java | 247 +++++++++++++++++++
.../src/test/resources/client_not_revoked.jks | Bin 0 -> 2414 bytes
.../src/test/resources/client_revoked.jks | Bin 0 -> 2415 bytes
.../src/test/resources/keystore1.jks | Bin 0 -> 2396 bytes
.../resources/mqttCrl/client0/truststore.jks | Bin 0 -> 1003 bytes
.../resources/mqttCrl/client1/truststore.jks | Bin 0 -> 1003 bytes
.../src/test/resources/root.crl.pem | 12 +
.../src/test/resources/truststore.jks | Bin 0 -> 1003 bytes
24 files changed, 702 insertions(+), 9 deletions(-)
----------------------------------------------------------------------