From ad6db747010774ec55592b4304ad45c169a7209f Mon Sep 17 00:00:00 2001 From: Martyn Taylor Date: Fri, 10 Aug 2018 12:25:14 +0100 Subject: [PATCH] ARTEMIS-2024 Enable SharedClientID on ConnectionFactory --- .../api/core/client/ActiveMQClient.java | 2 ++ .../jms/client/ActiveMQConnection.java | 11 +++++++++- .../jms/client/ActiveMQConnectionFactory.java | 14 +++++++++++- .../ConnectionFactoryConfiguration.java | 4 ++++ .../ConnectionFactoryConfigurationImpl.java | 22 ++++++++++++++++++- .../jms/server/impl/JMSServerManagerImpl.java | 1 + .../artemis/ra/ActiveMQResourceAdapter.java | 2 ++ .../ra/ConnectionFactoryProperties.java | 17 ++++++++++++++ .../artemis/ra/inflow/ActiveMQActivation.java | 2 ++ .../activemq/ActiveMQConnectionFactory.java | 1 + .../jms/ActiveMQConnectionFactoryTest.java | 3 ++- .../jms/client/ConnectionTest.java | 21 ++++++++++++++++++ .../ra/ConnectionFactoryPropertiesTest.java | 1 + 13 files changed, 97 insertions(+), 4 deletions(-) diff --git a/artemis-core-client/src/main/java/org/apache/activemq/artemis/api/core/client/ActiveMQClient.java b/artemis-core-client/src/main/java/org/apache/activemq/artemis/api/core/client/ActiveMQClient.java index d24efff84f..ab647a3170 100644 --- a/artemis-core-client/src/main/java/org/apache/activemq/artemis/api/core/client/ActiveMQClient.java +++ b/artemis-core-client/src/main/java/org/apache/activemq/artemis/api/core/client/ActiveMQClient.java @@ -95,6 +95,8 @@ public final class ActiveMQClient { public static final boolean DEFAULT_PRE_ACKNOWLEDGE = false; + public static final boolean DEFAULT_ENABLED_SHARED_CLIENT_ID = false; + public static final long DEFAULT_DISCOVERY_INITIAL_WAIT_TIMEOUT = 10000; public static final long DEFAULT_DISCOVERY_REFRESH_TIMEOUT = 10000; diff --git a/artemis-jms-client/src/main/java/org/apache/activemq/artemis/jms/client/ActiveMQConnection.java b/artemis-jms-client/src/main/java/org/apache/activemq/artemis/jms/client/ActiveMQConnection.java index ec67cc33d9..0f04889697 100644 --- a/artemis-jms-client/src/main/java/org/apache/activemq/artemis/jms/client/ActiveMQConnection.java +++ b/artemis-jms-client/src/main/java/org/apache/activemq/artemis/jms/client/ActiveMQConnection.java @@ -679,11 +679,19 @@ public class ActiveMQConnection extends ActiveMQConnectionForContextImpl impleme } public void authorize() throws JMSException { + authorize(true); + } + + public void authorize(boolean validateClientId) throws JMSException { try { initialSession = sessionFactory.createSession(username, password, false, false, false, false, 0); if (clientID != null) { - validateClientID(initialSession, clientID); + if (validateClientId) { + validateClientID(initialSession, clientID); + } else { + initialSession.addMetaData(ClientSession.JMS_SESSION_CLIENT_ID_PROPERTY, clientID); + } } addSessionMetaData(initialSession); @@ -718,6 +726,7 @@ public class ActiveMQConnection extends ActiveMQConnectionForContextImpl impleme return this.factoryReference.getDeserializationWhiteList(); } + // Inner classes -------------------------------------------------------------------------------- private static class JMSFailureListener implements SessionFailureListener { diff --git a/artemis-jms-client/src/main/java/org/apache/activemq/artemis/jms/client/ActiveMQConnectionFactory.java b/artemis-jms-client/src/main/java/org/apache/activemq/artemis/jms/client/ActiveMQConnectionFactory.java index db1fc78269..17ee6fe302 100644 --- a/artemis-jms-client/src/main/java/org/apache/activemq/artemis/jms/client/ActiveMQConnectionFactory.java +++ b/artemis-jms-client/src/main/java/org/apache/activemq/artemis/jms/client/ActiveMQConnectionFactory.java @@ -70,6 +70,8 @@ public class ActiveMQConnectionFactory extends JNDIStorable implements Connectio private String clientID; + private boolean enableSharedClientID = ActiveMQClient.DEFAULT_ENABLED_SHARED_CLIENT_ID; + private int dupsOKBatchSize = ActiveMQClient.DEFAULT_ACK_BATCH_SIZE; private int transactionBatchSize = ActiveMQClient.DEFAULT_ACK_BATCH_SIZE; @@ -452,6 +454,14 @@ public class ActiveMQConnectionFactory extends JNDIStorable implements Connectio this.clientID = clientID; } + public boolean isEnableSharedClientID() { + return enableSharedClientID; + } + + public void setEnableSharedClientID(boolean enableSharedClientID) { + this.enableSharedClientID = enableSharedClientID; + } + public synchronized int getDupsOKBatchSize() { return dupsOKBatchSize; } @@ -857,7 +867,7 @@ public class ActiveMQConnectionFactory extends JNDIStorable implements Connectio connection.setReference(this); try { - connection.authorize(); + connection.authorize(!isEnableSharedClientID()); } catch (JMSException e) { try { connection.close(); @@ -882,6 +892,8 @@ public class ActiveMQConnectionFactory extends JNDIStorable implements Connectio transactionBatchSize + ", readOnly=" + readOnly + + "EnableSharedClientID=" + + enableSharedClientID + "]"; } diff --git a/artemis-jms-server/src/main/java/org/apache/activemq/artemis/jms/server/config/ConnectionFactoryConfiguration.java b/artemis-jms-server/src/main/java/org/apache/activemq/artemis/jms/server/config/ConnectionFactoryConfiguration.java index 43b9904b21..eee7431431 100644 --- a/artemis-jms-server/src/main/java/org/apache/activemq/artemis/jms/server/config/ConnectionFactoryConfiguration.java +++ b/artemis-jms-server/src/main/java/org/apache/activemq/artemis/jms/server/config/ConnectionFactoryConfiguration.java @@ -193,4 +193,8 @@ public interface ConnectionFactoryConfiguration extends EncodingSupport { boolean isEnable1xPrefixes(); ConnectionFactoryConfiguration setEnable1xPrefixes(boolean enable1xPrefixes); + + boolean isEnableSharedClientID(); + + ConnectionFactoryConfiguration setEnableSharedClientID(boolean enabled); } diff --git a/artemis-jms-server/src/main/java/org/apache/activemq/artemis/jms/server/config/impl/ConnectionFactoryConfigurationImpl.java b/artemis-jms-server/src/main/java/org/apache/activemq/artemis/jms/server/config/impl/ConnectionFactoryConfigurationImpl.java index 2f546ec163..ae71ecaa8d 100644 --- a/artemis-jms-server/src/main/java/org/apache/activemq/artemis/jms/server/config/impl/ConnectionFactoryConfigurationImpl.java +++ b/artemis-jms-server/src/main/java/org/apache/activemq/artemis/jms/server/config/impl/ConnectionFactoryConfigurationImpl.java @@ -126,6 +126,9 @@ public class ConnectionFactoryConfigurationImpl implements ConnectionFactoryConf private boolean enable1xPrefixes = ActiveMQClient.DEFAULT_ENABLE_1X_PREFIXES; + private boolean enableSharedClientID = ActiveMQClient.DEFAULT_ENABLED_SHARED_CLIENT_ID; + + // Static -------------------------------------------------------- // Constructors -------------------------------------------------- @@ -638,6 +641,9 @@ public class ConnectionFactoryConfigurationImpl implements ConnectionFactoryConf deserializationWhiteList = BufferHelper.readNullableSimpleStringAsString(buffer); enable1xPrefixes = buffer.readableBytes() > 0 ? buffer.readBoolean() : null; + + enableSharedClientID = buffer.readableBytes() > 0 ? buffer.readBoolean() : ActiveMQClient.DEFAULT_ENABLED_SHARED_CLIENT_ID; + } @Override @@ -729,6 +735,8 @@ public class ConnectionFactoryConfigurationImpl implements ConnectionFactoryConf BufferHelper.writeAsNullableSimpleString(buffer, deserializationWhiteList); buffer.writeBoolean(enable1xPrefixes); + + BufferHelper.writeNullableBoolean(buffer, enableSharedClientID); } @Override @@ -844,9 +852,11 @@ public class ConnectionFactoryConfigurationImpl implements ConnectionFactoryConf BufferHelper.sizeOfNullableSimpleString(deserializationWhiteList) + - DataConstants.SIZE_BOOLEAN; + DataConstants.SIZE_BOOLEAN + // enable1xPrefixes; + BufferHelper.sizeOfNullableBoolean(enableSharedClientID); + return size; } @@ -914,6 +924,16 @@ public class ConnectionFactoryConfigurationImpl implements ConnectionFactoryConf return this; } + @Override + public ConnectionFactoryConfiguration setEnableSharedClientID(boolean enabled) { + this.enableSharedClientID = enabled; + return this; + } + + @Override + public boolean isEnableSharedClientID() { + return enableSharedClientID; + } // Public -------------------------------------------------------- diff --git a/artemis-jms-server/src/main/java/org/apache/activemq/artemis/jms/server/impl/JMSServerManagerImpl.java b/artemis-jms-server/src/main/java/org/apache/activemq/artemis/jms/server/impl/JMSServerManagerImpl.java index 58acbbceda..27abbbe8af 100644 --- a/artemis-jms-server/src/main/java/org/apache/activemq/artemis/jms/server/impl/JMSServerManagerImpl.java +++ b/artemis-jms-server/src/main/java/org/apache/activemq/artemis/jms/server/impl/JMSServerManagerImpl.java @@ -1221,6 +1221,7 @@ public class JMSServerManagerImpl implements JMSServerManager, ActivateCallback cf.setDeserializationWhiteList(cfConfig.getDeserializationWhiteList()); cf.setInitialMessagePacketSize(cfConfig.getInitialMessagePacketSize()); cf.setEnable1xPrefixes(cfConfig.isEnable1xPrefixes()); + cf.setEnableSharedClientID(cfConfig.isEnableSharedClientID()); return cf; } diff --git a/artemis-ra/src/main/java/org/apache/activemq/artemis/ra/ActiveMQResourceAdapter.java b/artemis-ra/src/main/java/org/apache/activemq/artemis/ra/ActiveMQResourceAdapter.java index 8c31c2abb5..f3e4614683 100644 --- a/artemis-ra/src/main/java/org/apache/activemq/artemis/ra/ActiveMQResourceAdapter.java +++ b/artemis-ra/src/main/java/org/apache/activemq/artemis/ra/ActiveMQResourceAdapter.java @@ -1792,6 +1792,7 @@ public class ActiveMQResourceAdapter implements ResourceAdapter, Serializable { throw new IllegalArgumentException("must provide either TransportType or DiscoveryGroupAddress and DiscoveryGroupPort for ResourceAdapter Connection Factory"); } + cf.setEnableSharedClientID(true); setParams(cf, overrideProperties); return cf; } @@ -1858,6 +1859,7 @@ public class ActiveMQResourceAdapter implements ResourceAdapter, Serializable { cf.setReconnectAttempts(0); cf.setInitialConnectAttempts(0); + cf.setEnableSharedClientID(true); return cf; } diff --git a/artemis-ra/src/main/java/org/apache/activemq/artemis/ra/ConnectionFactoryProperties.java b/artemis-ra/src/main/java/org/apache/activemq/artemis/ra/ConnectionFactoryProperties.java index cda5afcec9..c0a7702eda 100644 --- a/artemis-ra/src/main/java/org/apache/activemq/artemis/ra/ConnectionFactoryProperties.java +++ b/artemis-ra/src/main/java/org/apache/activemq/artemis/ra/ConnectionFactoryProperties.java @@ -130,6 +130,8 @@ public class ConnectionFactoryProperties implements ConnectionFactoryOptions { private String deserializationWhiteList; + private Boolean enableSharedClientID; + /** * @return the transportType */ @@ -755,6 +757,14 @@ public class ConnectionFactoryProperties implements ConnectionFactoryOptions { return hasBeenUpdated; } + public void setEnableSharedClientID(boolean enable) { + this.enableSharedClientID = enable; + } + + public boolean isEnableSharedClientID() { + return enableSharedClientID; + } + @Override public boolean equals(Object obj) { if (this == obj) @@ -999,6 +1009,12 @@ public class ConnectionFactoryProperties implements ConnectionFactoryOptions { } else if (!this.enable1xPrefixes.equals(other.enable1xPrefixes)) return false; + if (enableSharedClientID == null) { + if (other.enableSharedClientID != null) + return false; + } else if (!enableSharedClientID == other.enableSharedClientID) + return false; + return true; } @@ -1052,6 +1068,7 @@ public class ConnectionFactoryProperties implements ConnectionFactoryOptions { result = prime * result + ((deserializationBlackList == null) ? 0 : deserializationBlackList.hashCode()); result = prime * result + ((deserializationWhiteList == null) ? 0 : deserializationWhiteList.hashCode()); result = prime * result + ((enable1xPrefixes == null) ? 0 : enable1xPrefixes.hashCode()); + result = prime * result + ((enableSharedClientID == null) ? 0 : enableSharedClientID.hashCode()); return result; } } diff --git a/artemis-ra/src/main/java/org/apache/activemq/artemis/ra/inflow/ActiveMQActivation.java b/artemis-ra/src/main/java/org/apache/activemq/artemis/ra/inflow/ActiveMQActivation.java index 3a893696bd..204d5d0aac 100644 --- a/artemis-ra/src/main/java/org/apache/activemq/artemis/ra/inflow/ActiveMQActivation.java +++ b/artemis-ra/src/main/java/org/apache/activemq/artemis/ra/inflow/ActiveMQActivation.java @@ -454,12 +454,14 @@ public class ActiveMQActivation { // This will clone the connection factory // to make sure we won't close anyone's connection factory when we stop the MDB factory = ActiveMQJMSClient.createConnectionFactory(((ActiveMQConnectionFactory) fac).toURI().toString(), "internalConnection"); + factory.setEnableSharedClientID(true); } else { factory = ra.newConnectionFactory(spec); } } else { factory = ra.newConnectionFactory(spec); } + } /** diff --git a/tests/activemq5-unit-tests/src/main/java/org/apache/activemq/ActiveMQConnectionFactory.java b/tests/activemq5-unit-tests/src/main/java/org/apache/activemq/ActiveMQConnectionFactory.java index 0b1453a8fc..823c76149a 100644 --- a/tests/activemq5-unit-tests/src/main/java/org/apache/activemq/ActiveMQConnectionFactory.java +++ b/tests/activemq5-unit-tests/src/main/java/org/apache/activemq/ActiveMQConnectionFactory.java @@ -217,6 +217,7 @@ public class ActiveMQConnectionFactory extends JNDIBaseStorable implements Conne } public ActiveMQConnectionFactory(URI brokerURL) { + setBrokerURL(brokerURL.toString()); } diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/jms/ActiveMQConnectionFactoryTest.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/jms/ActiveMQConnectionFactoryTest.java index f44e317091..c235c5c6c8 100644 --- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/jms/ActiveMQConnectionFactoryTest.java +++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/jms/ActiveMQConnectionFactoryTest.java @@ -35,6 +35,7 @@ import java.util.Map; import org.apache.activemq.artemis.api.core.BroadcastGroupConfiguration; import org.apache.activemq.artemis.api.core.DiscoveryGroupConfiguration; +import org.apache.activemq.artemis.api.core.RoutingType; import org.apache.activemq.artemis.api.core.SimpleString; import org.apache.activemq.artemis.api.core.TransportConfiguration; import org.apache.activemq.artemis.api.core.UDPBroadcastEndpointFactory; @@ -45,7 +46,6 @@ import org.apache.activemq.artemis.core.config.Configuration; import org.apache.activemq.artemis.core.config.ha.SharedStoreMasterPolicyConfiguration; import org.apache.activemq.artemis.core.server.ActiveMQServer; import org.apache.activemq.artemis.core.server.ActiveMQServers; -import org.apache.activemq.artemis.api.core.RoutingType; import org.apache.activemq.artemis.jms.client.ActiveMQConnectionFactory; import org.apache.activemq.artemis.tests.integration.IntegrationTestLogger; import org.apache.activemq.artemis.tests.integration.jms.serializables.TestClass1; @@ -444,6 +444,7 @@ public class ActiveMQConnectionFactoryTest extends ActiveMQTestBase { long retryInterval = RandomUtil.randomPositiveLong(); double retryIntervalMultiplier = RandomUtil.randomDouble(); int reconnectAttempts = RandomUtil.randomPositiveInt(); + boolean enableSharedClientID = true; try { cf.setClientID(clientID); diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/jms/client/ConnectionTest.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/jms/client/ConnectionTest.java index 8ea65dbc7f..f53de93746 100644 --- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/jms/client/ConnectionTest.java +++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/jms/client/ConnectionTest.java @@ -131,6 +131,27 @@ public class ConnectionTest extends JMSTestBase { session2.close(); } + @Test + public void testTwoConnectionsSameIDThroughCFWithShareClientIDEnabeld() throws Exception { + ActiveMQConnectionFactory connectionFactory = new ActiveMQConnectionFactory("tcp://localhost:61616?clientID=myid;enableSharedClientID=true"); + + conn = connectionFactory.createConnection(); + try { + conn2 = connectionFactory.createConnection(); + } catch (InvalidClientIDException expected) { + Assert.fail("Should allow sharing of client IDs among the same CF"); + } + + Session session1 = conn.createSession(); + Session session2 = conn.createSession(); + Session session3 = conn2.createSession(); + Session session4 = conn2.createSession(); + + session1.close(); + session2.close(); + session3.close(); + session4.close(); + } @Test public void testGetSetConnectionFactory() throws Exception { diff --git a/tests/unit-tests/src/test/java/org/apache/activemq/artemis/tests/unit/ra/ConnectionFactoryPropertiesTest.java b/tests/unit-tests/src/test/java/org/apache/activemq/artemis/tests/unit/ra/ConnectionFactoryPropertiesTest.java index 3901e1b43f..b463e30383 100644 --- a/tests/unit-tests/src/test/java/org/apache/activemq/artemis/tests/unit/ra/ConnectionFactoryPropertiesTest.java +++ b/tests/unit-tests/src/test/java/org/apache/activemq/artemis/tests/unit/ra/ConnectionFactoryPropertiesTest.java @@ -46,6 +46,7 @@ public class ConnectionFactoryPropertiesTest extends ActiveMQTestBase { UNSUPPORTED_CF_PROPERTIES.add("user"); UNSUPPORTED_CF_PROPERTIES.add("userName"); UNSUPPORTED_CF_PROPERTIES.add("password"); + UNSUPPORTED_CF_PROPERTIES.add("enableSharedClientID"); UNSUPPORTED_RA_PROPERTIES = new TreeSet<>(); UNSUPPORTED_RA_PROPERTIES.add("HA");