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 2016/11/11 19:23:31 UTC

[01/11] activemq-artemis git commit: Stomp refactor + track autocreation for addresses

Repository: activemq-artemis
Updated Branches:
  refs/heads/ARTEMIS-780 d96185281 -> a25a8c481


http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/unit-tests/src/test/java/org/apache/activemq/artemis/tests/unit/core/server/impl/fakes/FakePostOffice.java
----------------------------------------------------------------------
diff --git a/tests/unit-tests/src/test/java/org/apache/activemq/artemis/tests/unit/core/server/impl/fakes/FakePostOffice.java b/tests/unit-tests/src/test/java/org/apache/activemq/artemis/tests/unit/core/server/impl/fakes/FakePostOffice.java
index 512f0f2..35fe5cc 100644
--- a/tests/unit-tests/src/test/java/org/apache/activemq/artemis/tests/unit/core/server/impl/fakes/FakePostOffice.java
+++ b/tests/unit-tests/src/test/java/org/apache/activemq/artemis/tests/unit/core/server/impl/fakes/FakePostOffice.java
@@ -30,7 +30,6 @@ import org.apache.activemq.artemis.core.postoffice.RoutingStatus;
 import org.apache.activemq.artemis.core.postoffice.impl.DuplicateIDCacheImpl;
 import org.apache.activemq.artemis.core.server.MessageReference;
 import org.apache.activemq.artemis.core.server.Queue;
-import org.apache.activemq.artemis.core.server.QueueCreator;
 import org.apache.activemq.artemis.core.server.RoutingContext;
 import org.apache.activemq.artemis.core.server.ServerMessage;
 import org.apache.activemq.artemis.core.server.impl.AddressInfo;
@@ -162,7 +161,6 @@ public class FakePostOffice implements PostOffice {
 
    @Override
    public RoutingStatus route(ServerMessage message,
-                              QueueCreator creator,
                               RoutingContext context,
                               boolean direct) throws Exception {
       return RoutingStatus.OK;
@@ -171,7 +169,6 @@ public class FakePostOffice implements PostOffice {
 
    @Override
    public RoutingStatus route(ServerMessage message,
-                              QueueCreator creator,
                               Transaction tx,
                               boolean direct) throws Exception {
       return RoutingStatus.OK;
@@ -179,7 +176,6 @@ public class FakePostOffice implements PostOffice {
 
    @Override
    public RoutingStatus route(ServerMessage message,
-                              QueueCreator creator,
                               RoutingContext context,
                               boolean direct,
                               boolean rejectDuplicates) throws Exception {
@@ -189,7 +185,6 @@ public class FakePostOffice implements PostOffice {
 
    @Override
    public RoutingStatus route(ServerMessage message,
-                              QueueCreator creator,
                               Transaction tx,
                               boolean direct,
                               boolean rejectDuplicates) throws Exception {
@@ -201,7 +196,7 @@ public class FakePostOffice implements PostOffice {
    }
 
    @Override
-   public RoutingStatus route(ServerMessage message, QueueCreator queueCreator, boolean direct) throws Exception {
+   public RoutingStatus route(ServerMessage message, boolean direct) throws Exception {
       return RoutingStatus.OK;
    }
 }


[03/11] activemq-artemis git commit: Stomp refactor + track autocreation for addresses

Posted by jb...@apache.org.
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v11/StompV11TestBase.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v11/StompV11TestBase.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v11/StompV11TestBase.java
deleted file mode 100644
index 341b583..0000000
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v11/StompV11TestBase.java
+++ /dev/null
@@ -1,167 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements. See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License. You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.activemq.artemis.tests.integration.stomp.v11;
-
-import javax.jms.BytesMessage;
-import javax.jms.Connection;
-import javax.jms.ConnectionFactory;
-import javax.jms.Destination;
-import javax.jms.MessageProducer;
-import javax.jms.Queue;
-import javax.jms.Session;
-import javax.jms.TextMessage;
-import javax.jms.Topic;
-import java.nio.charset.StandardCharsets;
-import java.util.HashMap;
-import java.util.Map;
-
-import org.apache.activemq.artemis.api.core.TransportConfiguration;
-import org.apache.activemq.artemis.core.config.Configuration;
-import org.apache.activemq.artemis.core.protocol.stomp.StompProtocolManagerFactory;
-import org.apache.activemq.artemis.core.registry.JndiBindingRegistry;
-import org.apache.activemq.artemis.core.remoting.impl.invm.InVMAcceptorFactory;
-import org.apache.activemq.artemis.core.remoting.impl.invm.InVMConnectorFactory;
-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.server.ActiveMQServer;
-import org.apache.activemq.artemis.core.server.ActiveMQServers;
-import org.apache.activemq.artemis.jms.client.ActiveMQJMSConnectionFactory;
-import org.apache.activemq.artemis.jms.server.JMSServerManager;
-import org.apache.activemq.artemis.jms.server.config.JMSConfiguration;
-import org.apache.activemq.artemis.jms.server.config.impl.JMSConfigurationImpl;
-import org.apache.activemq.artemis.jms.server.config.impl.JMSQueueConfigurationImpl;
-import org.apache.activemq.artemis.jms.server.config.impl.TopicConfigurationImpl;
-import org.apache.activemq.artemis.jms.server.impl.JMSServerManagerImpl;
-import org.apache.activemq.artemis.tests.unit.util.InVMNamingContext;
-import org.apache.activemq.artemis.tests.util.ActiveMQTestBase;
-import org.junit.Before;
-
-public abstract class StompV11TestBase extends ActiveMQTestBase {
-
-   protected String hostname = "127.0.0.1";
-
-   protected int port = 61613;
-
-   private ConnectionFactory connectionFactory;
-
-   private Connection connection;
-
-   protected Session session;
-
-   protected Queue queue;
-
-   protected Topic topic;
-
-   protected JMSServerManager server;
-
-   protected String defUser = "brianm";
-
-   protected String defPass = "wombats";
-
-   protected boolean persistenceEnabled = false;
-
-   // Implementation methods
-   // -------------------------------------------------------------------------
-   @Override
-   @Before
-   public void setUp() throws Exception {
-      super.setUp();
-
-      server = createServer();
-      server.start();
-      connectionFactory = createConnectionFactory();
-
-      connection = connectionFactory.createConnection();
-      session = connection.createSession(false, Session.AUTO_ACKNOWLEDGE);
-      queue = session.createQueue(getQueueName());
-      topic = session.createTopic(getTopicName());
-      connection.start();
-   }
-
-   /**
-    * @return
-    * @throws Exception
-    */
-   protected JMSServerManager createServer() throws Exception {
-      Map<String, Object> params = new HashMap<>();
-      params.put(TransportConstants.PROTOCOLS_PROP_NAME, StompProtocolManagerFactory.STOMP_PROTOCOL_NAME);
-      params.put(TransportConstants.PORT_PROP_NAME, TransportConstants.DEFAULT_STOMP_PORT);
-      params.put(TransportConstants.STOMP_CONSUMERS_CREDIT, "-1");
-      TransportConfiguration stompTransport = new TransportConfiguration(NettyAcceptorFactory.class.getName(), params);
-
-      Configuration config = createBasicConfig().setPersistenceEnabled(persistenceEnabled).addAcceptorConfiguration(stompTransport).addAcceptorConfiguration(new TransportConfiguration(InVMAcceptorFactory.class.getName())).setConnectionTtlCheckInterval(500);
-
-      ActiveMQServer activeMQServer = addServer(ActiveMQServers.newActiveMQServer(config, defUser, defPass));
-
-      JMSConfiguration jmsConfig = new JMSConfigurationImpl();
-      jmsConfig.getQueueConfigurations().add(new JMSQueueConfigurationImpl().setName(getQueueName()).setBindings(getQueueName()));
-      jmsConfig.getTopicConfigurations().add(new TopicConfigurationImpl().setName(getTopicName()).setBindings(getTopicName()));
-      server = new JMSServerManagerImpl(activeMQServer, jmsConfig);
-      server.setRegistry(new JndiBindingRegistry(new InVMNamingContext()));
-      return server;
-   }
-
-   protected ConnectionFactory createConnectionFactory() {
-      return new ActiveMQJMSConnectionFactory(false, new TransportConfiguration(InVMConnectorFactory.class.getName()));
-   }
-
-   protected String getQueueName() {
-      return "test";
-   }
-
-   protected String getQueuePrefix() {
-      return "";
-   }
-
-   protected String getTopicName() {
-      return "testtopic";
-   }
-
-   protected String getTopicPrefix() {
-      return "";
-   }
-
-   public void sendMessage(String msg) throws Exception {
-      sendMessage(msg, queue);
-   }
-
-   public void sendMessage(String msg, Destination destination) throws Exception {
-      MessageProducer producer = session.createProducer(destination);
-      TextMessage message = session.createTextMessage(msg);
-      producer.send(message);
-   }
-
-   public void sendMessage(byte[] data, Destination destination) throws Exception {
-      sendMessage(data, "foo", "xyz", destination);
-   }
-
-   public void sendMessage(String msg, String propertyName, String propertyValue) throws Exception {
-      sendMessage(msg.getBytes(StandardCharsets.UTF_8), propertyName, propertyValue, queue);
-   }
-
-   public void sendMessage(byte[] data,
-                           String propertyName,
-                           String propertyValue,
-                           Destination destination) throws Exception {
-      MessageProducer producer = session.createProducer(destination);
-      BytesMessage message = session.createBytesMessage();
-      message.setStringProperty(propertyName, propertyValue);
-      message.writeBytes(data);
-      producer.send(message);
-   }
-
-}


[02/11] activemq-artemis git commit: Stomp refactor + track autocreation for addresses

Posted by jb...@apache.org.
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v12/StompV12Test.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v12/StompV12Test.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v12/StompV12Test.java
index b7c0b60..0a52714 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v12/StompV12Test.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v12/StompV12Test.java
@@ -33,14 +33,15 @@ import java.util.concurrent.TimeUnit;
 
 import org.apache.activemq.artemis.api.core.SimpleString;
 import org.apache.activemq.artemis.core.protocol.stomp.Stomp;
+import org.apache.activemq.artemis.core.server.impl.AddressInfo;
 import org.apache.activemq.artemis.core.settings.impl.AddressSettings;
 import org.apache.activemq.artemis.tests.integration.IntegrationTestLogger;
+import org.apache.activemq.artemis.tests.integration.stomp.StompTestBase;
 import org.apache.activemq.artemis.tests.integration.stomp.util.ClientStompFrame;
 import org.apache.activemq.artemis.tests.integration.stomp.util.StompClientConnection;
 import org.apache.activemq.artemis.tests.integration.stomp.util.StompClientConnectionFactory;
 import org.apache.activemq.artemis.tests.integration.stomp.util.StompClientConnectionV11;
 import org.apache.activemq.artemis.tests.integration.stomp.util.StompClientConnectionV12;
-import org.apache.activemq.artemis.tests.integration.stomp.v11.StompV11TestBase;
 import org.junit.After;
 import org.junit.Assert;
 import org.junit.Before;
@@ -49,28 +50,28 @@ import org.junit.Test;
 /**
  * Testing Stomp version 1.2 functionalities
  */
-public class StompV12Test extends StompV11TestBase {
+public class StompV12Test extends StompTestBase {
 
    private static final transient IntegrationTestLogger log = IntegrationTestLogger.LOGGER;
    public static final String CLIENT_ID = "myclientid";
 
-   private StompClientConnectionV12 connV12;
+   private StompClientConnectionV12 conn;
 
    @Override
    @Before
    public void setUp() throws Exception {
       super.setUp();
-      connV12 = (StompClientConnectionV12) StompClientConnectionFactory.createClientConnection("1.2", hostname, port);
+      conn = (StompClientConnectionV12) StompClientConnectionFactory.createClientConnection("1.2", hostname, port);
    }
 
    @Override
    @After
    public void tearDown() throws Exception {
       try {
-         boolean connected = connV12 != null && connV12.isConnected();
+         boolean connected = conn != null && conn.isConnected();
          log.debug("Connection 1.2 : " + connected);
          if (connected) {
-            connV12.disconnect();
+            conn.disconnect();
          }
       } finally {
          super.tearDown();
@@ -119,32 +120,32 @@ public class StompV12Test extends StompV11TestBase {
    public void testConnectionAsInSpec() throws Exception {
       StompClientConnection conn = StompClientConnectionFactory.createClientConnection("1.0", hostname, port);
 
-      ClientStompFrame frame = conn.createFrame("CONNECT");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
-      frame.addHeader("accept-version", "1.2");
-      frame.addHeader("host", "127.0.0.1");
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.CONNECT);
+      frame.addHeader(Stomp.Headers.Connect.LOGIN, this.defUser);
+      frame.addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass);
+      frame.addHeader(Stomp.Headers.ACCEPT_VERSION, "1.2");
+      frame.addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1");
 
       ClientStompFrame reply = conn.sendFrame(frame);
 
-      Assert.assertEquals("CONNECTED", reply.getCommand());
-      Assert.assertEquals("1.2", reply.getHeader("version"));
+      Assert.assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
+      Assert.assertEquals("1.2", reply.getHeader(Stomp.Headers.Error.VERSION));
 
       conn.disconnect();
 
       //need 1.2 client
       conn = StompClientConnectionFactory.createClientConnection("1.2", hostname, port);
 
-      frame = conn.createFrame("STOMP");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
-      frame.addHeader("accept-version", "1.2");
-      frame.addHeader("host", "127.0.0.1");
+      frame = conn.createFrame(Stomp.Commands.STOMP);
+      frame.addHeader(Stomp.Headers.Connect.LOGIN, this.defUser);
+      frame.addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass);
+      frame.addHeader(Stomp.Headers.ACCEPT_VERSION, "1.2");
+      frame.addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1");
 
       reply = conn.sendFrame(frame);
 
-      Assert.assertEquals("CONNECTED", reply.getCommand());
-      Assert.assertEquals("1.2", reply.getHeader("version"));
+      Assert.assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
+      Assert.assertEquals("1.2", reply.getHeader(Stomp.Headers.Error.VERSION));
 
       conn.disconnect();
    }
@@ -153,82 +154,82 @@ public class StompV12Test extends StompV11TestBase {
    public void testNegotiation() throws Exception {
       StompClientConnection conn = StompClientConnectionFactory.createClientConnection("1.0", hostname, port);
       // case 1 accept-version absent. It is a 1.0 connect
-      ClientStompFrame frame = conn.createFrame("CONNECT");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.CONNECT);
+      frame.addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1");
+      frame.addHeader(Stomp.Headers.Connect.LOGIN, this.defUser);
+      frame.addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass);
 
       ClientStompFrame reply = conn.sendFrame(frame);
 
-      Assert.assertEquals("CONNECTED", reply.getCommand());
+      Assert.assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
 
       //reply headers: version, session, server
-      Assert.assertEquals(null, reply.getHeader("version"));
+      Assert.assertEquals(null, reply.getHeader(Stomp.Headers.Error.VERSION));
 
       conn.disconnect();
 
       // case 2 accept-version=1.0, result: 1.0
       conn = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
-      frame = conn.createFrame("CONNECT");
-      frame.addHeader("accept-version", "1.0");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
+      frame = conn.createFrame(Stomp.Commands.CONNECT);
+      frame.addHeader(Stomp.Headers.ACCEPT_VERSION, "1.0");
+      frame.addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1");
+      frame.addHeader(Stomp.Headers.Connect.LOGIN, this.defUser);
+      frame.addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass);
 
       reply = conn.sendFrame(frame);
 
-      Assert.assertEquals("CONNECTED", reply.getCommand());
+      Assert.assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
 
       //reply headers: version, session, server
-      Assert.assertEquals("1.0", reply.getHeader("version"));
+      Assert.assertEquals("1.0", reply.getHeader(Stomp.Headers.Error.VERSION));
 
       conn.disconnect();
 
       // case 3 accept-version=1.1, result: 1.1
       conn = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
-      frame = conn.createFrame("CONNECT");
-      frame.addHeader("accept-version", "1.1");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
+      frame = conn.createFrame(Stomp.Commands.CONNECT);
+      frame.addHeader(Stomp.Headers.ACCEPT_VERSION, "1.1");
+      frame.addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1");
+      frame.addHeader(Stomp.Headers.Connect.LOGIN, this.defUser);
+      frame.addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass);
 
       reply = conn.sendFrame(frame);
 
-      Assert.assertEquals("CONNECTED", reply.getCommand());
+      Assert.assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
 
       //reply headers: version, session, server
-      Assert.assertEquals("1.1", reply.getHeader("version"));
+      Assert.assertEquals("1.1", reply.getHeader(Stomp.Headers.Error.VERSION));
 
       conn.disconnect();
 
       // case 4 accept-version=1.0,1.1,1.3, result 1.2
       conn = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
-      frame = conn.createFrame("CONNECT");
-      frame.addHeader("accept-version", "1.0,1.1,1.3");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
+      frame = conn.createFrame(Stomp.Commands.CONNECT);
+      frame.addHeader(Stomp.Headers.ACCEPT_VERSION, "1.0,1.1,1.3");
+      frame.addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1");
+      frame.addHeader(Stomp.Headers.Connect.LOGIN, this.defUser);
+      frame.addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass);
 
       reply = conn.sendFrame(frame);
 
-      Assert.assertEquals("CONNECTED", reply.getCommand());
+      Assert.assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
 
       //reply headers: version, session, server
-      Assert.assertEquals("1.1", reply.getHeader("version"));
+      Assert.assertEquals("1.1", reply.getHeader(Stomp.Headers.Error.VERSION));
 
       conn.disconnect();
 
       // case 5 accept-version=1.3, result error
       conn = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
-      frame = conn.createFrame("CONNECT");
-      frame.addHeader("accept-version", "1.3");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
+      frame = conn.createFrame(Stomp.Commands.CONNECT);
+      frame.addHeader(Stomp.Headers.ACCEPT_VERSION, "1.3");
+      frame.addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1");
+      frame.addHeader(Stomp.Headers.Connect.LOGIN, this.defUser);
+      frame.addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass);
 
       reply = conn.sendFrame(frame);
 
-      Assert.assertEquals("ERROR", reply.getCommand());
+      Assert.assertEquals(Stomp.Responses.ERROR, reply.getCommand());
 
       System.out.println("Got error frame " + reply);
 
@@ -236,50 +237,31 @@ public class StompV12Test extends StompV11TestBase {
 
    @Test
    public void testSendAndReceive() throws Exception {
-      connV12.connect(defUser, defPass);
-      ClientStompFrame frame = connV12.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-type", "text/plain");
-      frame.setBody("Hello World 1!");
+      conn.connect(defUser, defPass);
 
-      ClientStompFrame response = connV12.sendFrame(frame);
+      ClientStompFrame response = send(conn, getQueuePrefix() + getQueueName(), "text/plain", "Hello World 1!");
 
       Assert.assertNull(response);
 
-      frame.addHeader("receipt", "1234");
-      frame.setBody("Hello World 2!");
-
-      response = connV12.sendFrame(frame);
-
-      Assert.assertNotNull(response);
-
-      Assert.assertEquals("RECEIPT", response.getCommand());
-
-      Assert.assertEquals("1234", response.getHeader("receipt-id"));
+      send(conn, getQueuePrefix() + getQueueName(), "text/plain", "Hello World 2!", true);
 
       //subscribe
       StompClientConnection newConn = StompClientConnectionFactory.createClientConnection("1.2", hostname, port);
       newConn.connect(defUser, defPass);
+      subscribe(newConn, "a-sub");
 
-      ClientStompFrame subFrame = newConn.createFrame("SUBSCRIBE");
-      subFrame.addHeader("id", "a-sub");
-      subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-      subFrame.addHeader("ack", "auto");
-
-      newConn.sendFrame(subFrame);
-
-      frame = newConn.receiveFrame();
+      ClientStompFrame frame = newConn.receiveFrame();
 
       System.out.println("received " + frame);
 
-      Assert.assertEquals("MESSAGE", frame.getCommand());
+      Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
 
-      Assert.assertEquals("a-sub", frame.getHeader("subscription"));
+      Assert.assertEquals("a-sub", frame.getHeader(Stomp.Headers.Message.SUBSCRIPTION));
 
       //'auto' ack mode doesn't require 'ack' header
-      Assert.assertNull(frame.getHeader("ack"));
+      Assert.assertNull(frame.getHeader(Stomp.Headers.Subscribe.ACK_MODE));
 
-      Assert.assertEquals(getQueuePrefix() + getQueueName(), frame.getHeader("destination"));
+      Assert.assertEquals(getQueuePrefix() + getQueueName(), frame.getHeader(Stomp.Headers.Subscribe.DESTINATION));
 
       Assert.assertEquals("Hello World 1!", frame.getBody());
 
@@ -288,90 +270,70 @@ public class StompV12Test extends StompV11TestBase {
       System.out.println("received " + frame);
 
       //unsub
-      ClientStompFrame unsubFrame = newConn.createFrame("UNSUBSCRIBE");
-      unsubFrame.addHeader("id", "a-sub");
-      newConn.sendFrame(unsubFrame);
+      unsubscribe(newConn, "a-sub");
 
       newConn.disconnect();
    }
 
    @Test
    public void testHeaderContentType() throws Exception {
-      connV12.connect(defUser, defPass);
-      ClientStompFrame frame = connV12.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-type", "application/xml");
-      frame.setBody("Hello World 1!");
+      conn.connect(defUser, defPass);
 
-      connV12.sendFrame(frame);
+      send(conn, getQueuePrefix() + getQueueName(), "application/xml", "Hello World 1!");
 
       //subscribe
       StompClientConnection newConn = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
       newConn.connect(defUser, defPass);
+      subscribe(newConn, "a-sub");
 
-      ClientStompFrame subFrame = newConn.createFrame("SUBSCRIBE");
-      subFrame.addHeader("id", "a-sub");
-      subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-      subFrame.addHeader("ack", "auto");
-
-      newConn.sendFrame(subFrame);
-
-      frame = newConn.receiveFrame();
+      ClientStompFrame frame = newConn.receiveFrame();
 
       System.out.println("received " + frame);
 
-      Assert.assertEquals("MESSAGE", frame.getCommand());
+      Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
 
-      Assert.assertEquals("application/xml", frame.getHeader("content-type"));
+      Assert.assertEquals("application/xml", frame.getHeader(Stomp.Headers.CONTENT_TYPE));
 
       //unsub
-      ClientStompFrame unsubFrame = newConn.createFrame("UNSUBSCRIBE");
-      unsubFrame.addHeader("id", "a-sub");
+      unsubscribe(newConn, "a-sub");
 
       newConn.disconnect();
    }
 
    @Test
    public void testHeaderContentLength() throws Exception {
-      connV12.connect(defUser, defPass);
-      ClientStompFrame frame = connV12.createFrame("SEND");
+      conn.connect(defUser, defPass);
 
       String body = "Hello World 1!";
       String cLen = String.valueOf(body.getBytes(StandardCharsets.UTF_8).length);
 
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-type", "application/xml");
-      frame.addHeader("content-length", cLen);
-      frame.setBody(body + "extra");
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SEND)
+                                   .addHeader(Stomp.Headers.Subscribe.DESTINATION, getQueuePrefix() + getQueueName())
+                                   .addHeader(Stomp.Headers.CONTENT_TYPE, "application/xml")
+                                   .addHeader(Stomp.Headers.CONTENT_LENGTH, cLen)
+                                   .setBody(body + "extra");
 
-      connV12.sendFrame(frame);
+      conn.sendFrame(frame);
 
       //subscribe
       StompClientConnection newConn = StompClientConnectionFactory.createClientConnection("1.2", hostname, port);
       newConn.connect(defUser, defPass);
-
-      ClientStompFrame subFrame = newConn.createFrame("SUBSCRIBE");
-      subFrame.addHeader("id", "a-sub");
-      subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-      subFrame.addHeader("ack", "auto");
-
-      newConn.sendFrame(subFrame);
+      subscribe(newConn, "a-sub");
 
       frame = newConn.receiveFrame();
 
-      Assert.assertEquals("MESSAGE", frame.getCommand());
+      Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
       Assert.assertEquals(body, frame.getBody());
 
-      Assert.assertEquals(cLen, frame.getHeader("content-length"));
+      Assert.assertEquals(cLen, frame.getHeader(Stomp.Headers.CONTENT_LENGTH));
 
       //send again without content-length header
-      frame = connV12.createFrame("SEND");
-
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-type", "application/xml");
-      frame.setBody(body + "extra");
+      frame = conn.createFrame(Stomp.Commands.SEND)
+                  .addHeader(Stomp.Headers.Subscribe.DESTINATION, getQueuePrefix() + getQueueName())
+                  .addHeader(Stomp.Headers.CONTENT_TYPE, "application/xml")
+                  .setBody(body + "extra");
 
-      connV12.sendFrame(frame);
+      conn.sendFrame(frame);
 
       //receive again. extra should received.
       frame = newConn.receiveFrame();
@@ -380,11 +342,10 @@ public class StompV12Test extends StompV11TestBase {
 
       //although sender didn't send the content-length header,
       //the server should add it anyway
-      Assert.assertEquals((body + "extra").getBytes(StandardCharsets.UTF_8).length, Integer.valueOf(frame.getHeader("content-length")).intValue());
+      Assert.assertEquals((body + "extra").getBytes(StandardCharsets.UTF_8).length, Integer.valueOf(frame.getHeader(Stomp.Headers.CONTENT_LENGTH)).intValue());
 
       //unsub
-      ClientStompFrame unsubFrame = newConn.createFrame("UNSUBSCRIBE");
-      unsubFrame.addHeader("id", "a-sub");
+      unsubscribe(newConn, "a-sub");
 
       newConn.disconnect();
    }
@@ -396,104 +357,90 @@ public class StompV12Test extends StompV11TestBase {
       addressSettings.setAutoCreateJmsQueues(false);
       server.getActiveMQServer().getAddressSettingsRepository().addMatch("#", addressSettings);
 
-      connV12.connect(defUser, defPass);
-      ClientStompFrame frame = connV12.createFrame("SEND");
+      conn.connect(defUser, defPass);
 
       String body = "Hello World!";
       String cLen = String.valueOf(body.getBytes(StandardCharsets.UTF_8).length);
 
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("destination", "aNonexistentQueue");
-      frame.addHeader("content-type", "application/xml");
-      frame.addHeader("content-length", cLen);
-      frame.addHeader("foo", "value1");
-      frame.addHeader("foo", "value2");
-      frame.addHeader("foo", "value3");
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SEND)
+                                   .addHeader(Stomp.Headers.Subscribe.DESTINATION, getQueuePrefix() + getQueueName())
+                                   .addHeader(Stomp.Headers.Subscribe.DESTINATION, "aNonexistentQueue")
+                                   .addHeader(Stomp.Headers.CONTENT_TYPE, "application/xml")
+                                   .addHeader(Stomp.Headers.CONTENT_LENGTH, cLen)
+                                   .addHeader("foo", "value1")
+                                   .addHeader("foo", "value2")
+                                   .addHeader("foo", "value3");
 
       frame.setBody(body);
 
-      connV12.sendFrame(frame);
+      conn.sendFrame(frame);
 
       //subscribe
       StompClientConnection newConn = StompClientConnectionFactory.createClientConnection("1.2", hostname, port);
       newConn.connect(defUser, defPass);
-
-      ClientStompFrame subFrame = newConn.createFrame("SUBSCRIBE");
-      subFrame.addHeader("id", "a-sub");
-      subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-      subFrame.addHeader("ack", "auto");
-
-      newConn.sendFrame(subFrame);
+      subscribe(newConn, "a-sub");
 
       frame = newConn.receiveFrame();
 
-      Assert.assertEquals("MESSAGE", frame.getCommand());
+      Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
       Assert.assertEquals(body, frame.getBody());
 
       System.out.println("received: " + frame);
       Assert.assertEquals("value1", frame.getHeader("foo"));
 
       //unsub
-      ClientStompFrame unsubFrame = newConn.createFrame("UNSUBSCRIBE");
-      unsubFrame.addHeader("id", "a-sub");
+      unsubscribe(newConn, "a-sub");
 
       newConn.disconnect();
 
       //should get error
-      frame = connV12.createFrame("SEND");
 
       body = "Hello World!";
       cLen = String.valueOf(body.getBytes(StandardCharsets.UTF_8).length);
 
-      frame.addHeader("destination", "aNonexistentQueue");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-type", "application/xml");
-      frame.addHeader("content-length", cLen);
-      frame.addHeader("receipt", "1234");
-
-      frame.setBody(body);
+      frame = conn.createFrame(Stomp.Commands.SEND)
+                  .addHeader(Stomp.Headers.Subscribe.DESTINATION, "aNonexistentQueue")
+                  .addHeader(Stomp.Headers.Subscribe.DESTINATION, getQueuePrefix() + getQueueName())
+                  .addHeader(Stomp.Headers.CONTENT_TYPE, "application/xml")
+                  .addHeader(Stomp.Headers.CONTENT_LENGTH, cLen)
+                  .addHeader(Stomp.Headers.RECEIPT_REQUESTED, "1234")
+                  .setBody(body);
 
-      ClientStompFrame reply = connV12.sendFrame(frame);
-      Assert.assertEquals("ERROR", reply.getCommand());
+      ClientStompFrame reply = conn.sendFrame(frame);
+      // TODO this is broken because queue auto-creation is always on
+      Assert.assertEquals(Stomp.Responses.ERROR, reply.getCommand());
    }
 
    //padding shouldn't be trimmed
    @Test
    public void testHeadersPadding() throws Exception {
-      connV12.connect(defUser, defPass);
-      ClientStompFrame frame = connV12.createFrame("SEND");
+      conn.connect(defUser, defPass);
 
       String body = "<p>Hello World!</p>";
       String cLen = String.valueOf(body.getBytes(StandardCharsets.UTF_8).length);
 
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-type", "application/xml");
-      frame.addHeader("content-length", cLen);
-      frame.addHeader(" header1", "value1 ");
-      frame.addHeader("  header2", "value2   ");
-      frame.addHeader("header3 ", " value3");
-      frame.addHeader(" header4 ", " value4 ");
-      frame.addHeader(" header 5  ", " value 5 ");
-      frame.addHeader("header6", "\t value\t 6 \t");
-
-      frame.setBody(body);
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SEND)
+                                   .addHeader(Stomp.Headers.Subscribe.DESTINATION, getQueuePrefix() + getQueueName())
+                                   .addHeader(Stomp.Headers.CONTENT_TYPE, "application/xml")
+                                   .addHeader(Stomp.Headers.CONTENT_LENGTH, cLen)
+                                   .addHeader(" header1", "value1 ")
+                                   .addHeader("  header2", "value2   ")
+                                   .addHeader("header3 ", " value3")
+                                   .addHeader(" header4 ", " value4 ")
+                                   .addHeader(" header 5  ", " value 5 ")
+                                   .addHeader("header6", "\t value\t 6 \t")
+                                   .setBody(body);
 
-      connV12.sendFrame(frame);
+      conn.sendFrame(frame);
 
       //subscribe
       StompClientConnection newConn = StompClientConnectionFactory.createClientConnection("1.2", hostname, port);
       newConn.connect(defUser, defPass);
-
-      ClientStompFrame subFrame = newConn.createFrame("SUBSCRIBE");
-      subFrame.addHeader("id", "a-sub");
-      subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-      subFrame.addHeader("ack", "auto");
-
-      newConn.sendFrame(subFrame);
+      subscribe(newConn, "a-sub");
 
       frame = newConn.receiveFrame();
 
-      Assert.assertEquals("MESSAGE", frame.getCommand());
+      Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
       Assert.assertEquals(body, frame.getBody());
 
       System.out.println("received: " + frame);
@@ -506,8 +453,7 @@ public class StompV12Test extends StompV11TestBase {
       Assert.assertEquals("\t value\t 6 \t", frame.getHeader("header6"));
 
       //unsub
-      ClientStompFrame unsubFrame = newConn.createFrame("UNSUBSCRIBE");
-      unsubFrame.addHeader("id", "a-sub");
+      unsubscribe(newConn, "a-sub");
 
       newConn.disconnect();
    }
@@ -517,49 +463,41 @@ public class StompV12Test extends StompV11TestBase {
     */
    @Test
    public void testHeaderEncoding() throws Exception {
-      connV12.connect(defUser, defPass);
-      ClientStompFrame frame = connV12.createFrame("SEND");
-
+      conn.connect(defUser, defPass);
       String body = "Hello World 1!";
       String cLen = String.valueOf(body.getBytes(StandardCharsets.UTF_8).length);
-
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-type", "application/xml");
-      frame.addHeader("content-length", cLen);
       String hKey = "\\rspecial-header\\\\\\n\\c\\r\\n";
       String hVal = "\\c\\\\\\ngood\\n\\r";
-      frame.addHeader(hKey, hVal);
 
-      System.out.println("key: |" + hKey + "| val: |" + hVal + "|");
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SEND)
+                                   .addHeader(Stomp.Headers.Subscribe.DESTINATION, getQueuePrefix() + getQueueName())
+                                   .addHeader(Stomp.Headers.CONTENT_TYPE, "application/xml")
+                                   .addHeader(Stomp.Headers.CONTENT_LENGTH, cLen)
+                                   .addHeader(hKey, hVal)
+                                   .setBody(body);
 
-      frame.setBody(body);
+      System.out.println("key: |" + hKey + "| val: |" + hVal + "|");
 
-      connV12.sendFrame(frame);
+      conn.sendFrame(frame);
 
       //subscribe
       StompClientConnection newConn = StompClientConnectionFactory.createClientConnection("1.2", hostname, port);
       newConn.connect(defUser, defPass);
 
-      ClientStompFrame subFrame = newConn.createFrame("SUBSCRIBE");
-      subFrame.addHeader("id", "a-sub");
-      subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-      subFrame.addHeader("ack", "auto");
-
-      newConn.sendFrame(subFrame);
+      subscribe(newConn, "a-sub");
 
       frame = newConn.receiveFrame();
 
       System.out.println("received " + frame);
 
-      Assert.assertEquals("MESSAGE", frame.getCommand());
+      Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
 
       String value = frame.getHeader("\r" + "special-header" + "\\" + "\n" + ":" + "\r\n");
 
       Assert.assertEquals(":" + "\\" + "\n" + "good\n\r", value);
 
       //unsub
-      ClientStompFrame unsubFrame = newConn.createFrame("UNSUBSCRIBE");
-      unsubFrame.addHeader("id", "a-sub");
+      unsubscribe(newConn, "a-sub");
 
       newConn.disconnect();
    }
@@ -568,14 +506,14 @@ public class StompV12Test extends StompV11TestBase {
    public void testHeartBeat() throws Exception {
       StompClientConnection conn = StompClientConnectionFactory.createClientConnection("1.2", hostname, port);
       //no heart beat at all if heat-beat absent
-      ClientStompFrame frame = conn.createFrame("CONNECT");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.CONNECT)
+                                   .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                                   .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                                   .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass);
 
       ClientStompFrame reply = conn.sendFrame(frame);
 
-      Assert.assertEquals("CONNECTED", reply.getCommand());
+      Assert.assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
 
       Thread.sleep(5000);
 
@@ -585,18 +523,18 @@ public class StompV12Test extends StompV11TestBase {
 
       //no heart beat for (0,0)
       conn = StompClientConnectionFactory.createClientConnection("1.2", hostname, port);
-      frame = conn.createFrame("CONNECT");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
-      frame.addHeader("heart-beat", "0,0");
-      frame.addHeader("accept-version", "1.0,1.1,1.2");
+      frame = conn.createFrame(Stomp.Commands.CONNECT)
+                  .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                  .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                  .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass)
+                  .addHeader(Stomp.Headers.Connect.HEART_BEAT, "0,0")
+                  .addHeader(Stomp.Headers.ACCEPT_VERSION, "1.0,1.1,1.2");
 
       reply = conn.sendFrame(frame);
 
-      Assert.assertEquals("CONNECTED", reply.getCommand());
+      Assert.assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
 
-      Assert.assertEquals("0,30000", reply.getHeader("heart-beat"));
+      Assert.assertEquals("0,30000", reply.getHeader(Stomp.Headers.Connect.HEART_BEAT));
 
       Thread.sleep(5000);
 
@@ -606,30 +544,25 @@ public class StompV12Test extends StompV11TestBase {
 
       //heart-beat (1,0), should receive a min client ping accepted by server
       conn = StompClientConnectionFactory.createClientConnection("1.2", hostname, port);
-      frame = conn.createFrame("CONNECT");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
-      frame.addHeader("heart-beat", "1,0");
-      frame.addHeader("accept-version", "1.0,1.2");
+      frame = conn.createFrame(Stomp.Commands.CONNECT)
+                  .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                  .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                  .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass)
+                  .addHeader(Stomp.Headers.Connect.HEART_BEAT, "1,0")
+                  .addHeader(Stomp.Headers.ACCEPT_VERSION, "1.0,1.2");
 
       reply = conn.sendFrame(frame);
 
-      Assert.assertEquals("CONNECTED", reply.getCommand());
+      Assert.assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
 
-      Assert.assertEquals("0,500", reply.getHeader("heart-beat"));
+      Assert.assertEquals("0,500", reply.getHeader(Stomp.Headers.Connect.HEART_BEAT));
 
       Thread.sleep(2000);
 
       //now server side should be disconnected because we didn't send ping for 2 sec
-      frame = conn.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-type", "text/plain");
-      frame.setBody("Hello World");
-
       //send will fail
       try {
-         conn.sendFrame(frame);
+         send(conn, getQueuePrefix() + getQueueName(), "text/plain", "Hello World");
          Assert.fail("connection should have been destroyed by now");
       } catch (IOException e) {
          //ignore
@@ -637,128 +570,106 @@ public class StompV12Test extends StompV11TestBase {
 
       //heart-beat (1,0), start a ping, then send a message, should be ok.
       conn = StompClientConnectionFactory.createClientConnection("1.2", hostname, port);
-      frame = conn.createFrame("CONNECT");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
-      frame.addHeader("heart-beat", "1,0");
-      frame.addHeader("accept-version", "1.0,1.1,1.2");
+      frame = conn.createFrame(Stomp.Commands.CONNECT)
+                  .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                  .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                  .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass)
+                  .addHeader(Stomp.Headers.Connect.HEART_BEAT, "1,0")
+                  .addHeader(Stomp.Headers.ACCEPT_VERSION, "1.0,1.1,1.2");
 
       reply = conn.sendFrame(frame);
 
-      Assert.assertEquals("CONNECTED", reply.getCommand());
+      Assert.assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
 
-      Assert.assertEquals("0,500", reply.getHeader("heart-beat"));
+      Assert.assertEquals("0,500", reply.getHeader(Stomp.Headers.Connect.HEART_BEAT));
 
       conn.startPinger(500);
 
       Thread.sleep(2000);
 
-      frame = conn.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-type", "text/plain");
-      frame.setBody("Hello World");
-
       //send will be ok
-      conn.sendFrame(frame);
+      send(conn, getQueuePrefix() + getQueueName(), "text/plain", "Hello World");
 
       conn.stopPinger();
 
       conn.disconnect();
-
    }
 
    //server ping
    @Test
    public void testHeartBeat2() throws Exception {
       //heart-beat (1,1)
-      ClientStompFrame frame = connV12.createFrame("CONNECT");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
-      frame.addHeader("heart-beat", "1,1");
-      frame.addHeader("accept-version", "1.0,1.1,1.2");
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.CONNECT)
+                                   .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                                   .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                                   .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass)
+                                   .addHeader(Stomp.Headers.Connect.HEART_BEAT, "1,1")
+                                   .addHeader(Stomp.Headers.ACCEPT_VERSION, "1.0,1.1,1.2");
 
-      ClientStompFrame reply = connV12.sendFrame(frame);
+      ClientStompFrame reply = conn.sendFrame(frame);
 
-      Assert.assertEquals("CONNECTED", reply.getCommand());
-      Assert.assertEquals("500,500", reply.getHeader("heart-beat"));
+      Assert.assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
+      Assert.assertEquals("500,500", reply.getHeader(Stomp.Headers.Connect.HEART_BEAT));
 
-      connV12.disconnect();
+      conn.disconnect();
 
       //heart-beat (500,1000)
-      connV12 = (StompClientConnectionV12) StompClientConnectionFactory.createClientConnection("1.2", hostname, port);
-      frame = connV12.createFrame("CONNECT");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
-      frame.addHeader("heart-beat", "500,1000");
-      frame.addHeader("accept-version", "1.0,1.1,1.2");
+      conn = (StompClientConnectionV12) StompClientConnectionFactory.createClientConnection("1.2", hostname, port);
+      frame = conn.createFrame(Stomp.Commands.CONNECT)
+                  .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                  .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                  .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass)
+                  .addHeader(Stomp.Headers.Connect.HEART_BEAT, "500,1000")
+                  .addHeader(Stomp.Headers.ACCEPT_VERSION, "1.0,1.1,1.2");
 
-      reply = connV12.sendFrame(frame);
+      reply = conn.sendFrame(frame);
 
-      Assert.assertEquals("CONNECTED", reply.getCommand());
+      Assert.assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
 
-      Assert.assertEquals("1000,500", reply.getHeader("heart-beat"));
+      Assert.assertEquals("1000,500", reply.getHeader(Stomp.Headers.Connect.HEART_BEAT));
 
-      connV12.startPinger(500);
+      conn.startPinger(500);
 
       Thread.sleep(10000);
 
       //now check the frame size
-      int size = connV12.getServerPingNumber();
+      int size = conn.getServerPingNumber();
 
       System.out.println("ping received: " + size);
 
       Assert.assertTrue("size: " + size, size > 5);
 
       //now server side should be disconnected because we didn't send ping for 2 sec
-      frame = connV12.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-type", "text/plain");
-      frame.setBody("Hello World");
-
       //send will be ok
-      connV12.sendFrame(frame);
+      send(conn, getQueuePrefix() + getQueueName(), "text/plain", "Hello World");
 
-      connV12.disconnect();
+      conn.disconnect();
    }
 
    @Test
    public void testSendWithHeartBeatsAndReceive() throws Exception {
       StompClientConnection newConn = null;
       try {
-         ClientStompFrame frame = connV12.createFrame("CONNECT");
-         frame.addHeader("host", "127.0.0.1");
-         frame.addHeader("login", this.defUser);
-         frame.addHeader("passcode", this.defPass);
-         frame.addHeader("heart-beat", "500,1000");
-         frame.addHeader("accept-version", "1.0,1.1,1.2");
+         ClientStompFrame frame = conn.createFrame(Stomp.Commands.CONNECT);
+         frame.addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+              .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+              .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass)
+              .addHeader(Stomp.Headers.Connect.HEART_BEAT, "500,1000")
+              .addHeader(Stomp.Headers.ACCEPT_VERSION, "1.0,1.1,1.2");
 
-         connV12.sendFrame(frame);
-
-         connV12.startPinger(500);
+         conn.sendFrame(frame);
 
-         frame = connV12.createFrame("SEND");
-         frame.addHeader("destination", getQueuePrefix() + getQueueName());
-         frame.addHeader("content-type", "text/plain");
+         conn.startPinger(500);
 
          for (int i = 0; i < 10; i++) {
-            frame.setBody("Hello World " + i + "!");
-            connV12.sendFrame(frame);
+            send(conn, getQueuePrefix() + getQueueName(), "text/plain", "Hello World " + i + "!");
             Thread.sleep(500);
          }
 
          // subscribe
          newConn = StompClientConnectionFactory.createClientConnection("1.2", hostname, port);
          newConn.connect(defUser, defPass);
-
-         ClientStompFrame subFrame = newConn.createFrame("SUBSCRIBE");
-         subFrame.addHeader("id", "a-sub");
-         subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-         subFrame.addHeader("ack", "auto");
-
-         newConn.sendFrame(subFrame);
+         subscribe(newConn, "a-sub");
 
          int cnt = 0;
 
@@ -773,38 +684,32 @@ public class StompV12Test extends StompV11TestBase {
          Assert.assertEquals(10, cnt);
 
          // unsub
-         ClientStompFrame unsubFrame = newConn.createFrame("UNSUBSCRIBE");
-         unsubFrame.addHeader("id", "a-sub");
-         newConn.sendFrame(unsubFrame);
+         unsubscribe(newConn, "a-sub");
       } finally {
          if (newConn != null)
             newConn.disconnect();
-         connV12.disconnect();
+         conn.disconnect();
       }
    }
 
    @Test
    public void testSendAndReceiveWithHeartBeats() throws Exception {
-      connV12.connect(defUser, defPass);
-      ClientStompFrame frame = connV12.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-type", "text/plain");
+      conn.connect(defUser, defPass);
 
       for (int i = 0; i < 10; i++) {
-         frame.setBody("Hello World " + i + "!");
-         connV12.sendFrame(frame);
+         send(conn, getQueuePrefix() + getQueueName(), "text/plain", "Hello World " + i + "!");
          Thread.sleep(500);
       }
 
       //subscribe
       StompClientConnection newConn = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
       try {
-         frame = newConn.createFrame("CONNECT");
-         frame.addHeader("host", "127.0.0.1");
-         frame.addHeader("login", this.defUser);
-         frame.addHeader("passcode", this.defPass);
-         frame.addHeader("heart-beat", "500,1000");
-         frame.addHeader("accept-version", "1.0,1.1");
+         ClientStompFrame frame = newConn.createFrame(Stomp.Commands.CONNECT)
+                                         .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                                         .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                                         .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass)
+                                         .addHeader(Stomp.Headers.Connect.HEART_BEAT, "500,1000")
+                                         .addHeader(Stomp.Headers.ACCEPT_VERSION, "1.0,1.1");
 
          newConn.sendFrame(frame);
 
@@ -812,12 +717,7 @@ public class StompV12Test extends StompV11TestBase {
 
          Thread.sleep(500);
 
-         ClientStompFrame subFrame = newConn.createFrame("SUBSCRIBE");
-         subFrame.addHeader("id", "a-sub");
-         subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-         subFrame.addHeader("ack", "auto");
-
-         newConn.sendFrame(subFrame);
+         subscribe(newConn, "a-sub");
 
          int cnt = 0;
 
@@ -832,9 +732,7 @@ public class StompV12Test extends StompV11TestBase {
          Assert.assertEquals(10, cnt);
 
          // unsub
-         ClientStompFrame unsubFrame = newConn.createFrame("UNSUBSCRIBE");
-         unsubFrame.addHeader("id", "a-sub");
-         newConn.sendFrame(unsubFrame);
+         unsubscribe(newConn, "a-sub");
       } finally {
          newConn.disconnect();
       }
@@ -844,35 +742,30 @@ public class StompV12Test extends StompV11TestBase {
    public void testSendWithHeartBeatsAndReceiveWithHeartBeats() throws Exception {
       StompClientConnection newConn = null;
       try {
-         ClientStompFrame frame = connV12.createFrame("CONNECT");
-         frame.addHeader("host", "127.0.0.1");
-         frame.addHeader("login", this.defUser);
-         frame.addHeader("passcode", this.defPass);
-         frame.addHeader("heart-beat", "500,1000");
-         frame.addHeader("accept-version", "1.0,1.1,1.2");
-
-         connV12.sendFrame(frame);
+         ClientStompFrame frame = conn.createFrame(Stomp.Commands.CONNECT)
+                                      .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                                      .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                                      .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass)
+                                      .addHeader(Stomp.Headers.Connect.HEART_BEAT, "500,1000")
+                                      .addHeader(Stomp.Headers.ACCEPT_VERSION, "1.0,1.1,1.2");
 
-         connV12.startPinger(500);
+         conn.sendFrame(frame);
 
-         frame = connV12.createFrame("SEND");
-         frame.addHeader("destination", getQueuePrefix() + getQueueName());
-         frame.addHeader("content-type", "text/plain");
+         conn.startPinger(500);
 
          for (int i = 0; i < 10; i++) {
-            frame.setBody("Hello World " + i + "!");
-            connV12.sendFrame(frame);
+            send(conn, getQueuePrefix() + getQueueName(), "text/plain", "Hello World " + i + "!");
             Thread.sleep(500);
          }
 
          // subscribe
          newConn = StompClientConnectionFactory.createClientConnection("1.2", hostname, port);
-         frame = newConn.createFrame("CONNECT");
-         frame.addHeader("host", "127.0.0.1");
-         frame.addHeader("login", this.defUser);
-         frame.addHeader("passcode", this.defPass);
-         frame.addHeader("heart-beat", "500,1000");
-         frame.addHeader("accept-version", "1.0,1.1,1.2");
+         frame = newConn.createFrame(Stomp.Commands.CONNECT)
+                        .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                        .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                        .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass)
+                        .addHeader(Stomp.Headers.Connect.HEART_BEAT, "500,1000")
+                        .addHeader(Stomp.Headers.ACCEPT_VERSION, "1.0,1.1,1.2");
 
          newConn.sendFrame(frame);
 
@@ -880,12 +773,7 @@ public class StompV12Test extends StompV11TestBase {
 
          Thread.sleep(500);
 
-         ClientStompFrame subFrame = newConn.createFrame("SUBSCRIBE");
-         subFrame.addHeader("id", "a-sub");
-         subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-         subFrame.addHeader("ack", "auto");
-
-         newConn.sendFrame(subFrame);
+         subscribe(newConn, "a-sub");
 
          int cnt = 0;
 
@@ -899,33 +787,31 @@ public class StompV12Test extends StompV11TestBase {
          Assert.assertEquals(10, cnt);
 
          // unsub
-         ClientStompFrame unsubFrame = newConn.createFrame("UNSUBSCRIBE");
-         unsubFrame.addHeader("id", "a-sub");
-         newConn.sendFrame(unsubFrame);
+         unsubscribe(newConn, "a-sub");
       } finally {
          if (newConn != null)
             newConn.disconnect();
-         connV12.disconnect();
+         conn.disconnect();
       }
    }
 
    @Test
    public void testNack() throws Exception {
-      connV12.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      subscribe(connV12, "sub1", "client");
+      subscribe(conn, "sub1", "client");
 
-      sendMessage(getName());
+      sendJmsMessage(getName());
 
-      ClientStompFrame frame = connV12.receiveFrame();
+      ClientStompFrame frame = conn.receiveFrame();
 
-      String messageID = frame.getHeader("message-id");
+      String messageID = frame.getHeader(Stomp.Headers.Message.MESSAGE_ID);
 
-      nack(connV12, messageID);
+      nack(conn, messageID);
 
-      unsubscribe(connV12, "sub1");
+      unsubscribe(conn, "sub1");
 
-      connV12.disconnect();
+      conn.disconnect();
 
       //Nack makes the message be dropped.
       MessageConsumer consumer = session.createConsumer(queue);
@@ -935,24 +821,24 @@ public class StompV12Test extends StompV11TestBase {
 
    @Test
    public void testNackWithWrongSubId() throws Exception {
-      connV12.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      subscribe(connV12, "sub1", "client");
+      subscribe(conn, "sub1", "client");
 
-      sendMessage(getName());
+      sendJmsMessage(getName());
 
-      ClientStompFrame frame = connV12.receiveFrame();
+      ClientStompFrame frame = conn.receiveFrame();
 
-      String messageID = frame.getHeader("ack");
+      String messageID = frame.getHeader(Stomp.Headers.Subscribe.ACK_MODE);
 
-      nack(connV12, messageID + "0");
+      nack(conn, messageID + "0");
 
-      ClientStompFrame error = connV12.receiveFrame();
+      ClientStompFrame error = conn.receiveFrame();
 
-      Assert.assertEquals("ERROR", error.getCommand());
+      Assert.assertEquals(Stomp.Responses.ERROR, error.getCommand());
 
-      waitDisconnect(connV12);
-      Assert.assertFalse("Should be disconnected in STOMP 1.2 after ERROR", connV12.isConnected());
+      waitDisconnect(conn);
+      Assert.assertFalse("Should be disconnected in STOMP 1.2 after ERROR", conn.isConnected());
 
       //message should be still there
       MessageConsumer consumer = session.createConsumer(queue);
@@ -962,26 +848,26 @@ public class StompV12Test extends StompV11TestBase {
 
    @Test
    public void testNackWithWrongMessageId() throws Exception {
-      connV12.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      subscribe(connV12, "sub1", "client");
+      subscribe(conn, "sub1", "client");
 
-      sendMessage(getName());
+      sendJmsMessage(getName());
 
-      ClientStompFrame frame = connV12.receiveFrame();
+      ClientStompFrame frame = conn.receiveFrame();
 
       Assert.assertNotNull(frame);
 
-      Assert.assertNotNull(frame.getHeader("ack"));
+      Assert.assertNotNull(frame.getHeader(Stomp.Headers.Subscribe.ACK_MODE));
 
-      nack(connV12, "someother");
+      nack(conn, "someother");
 
-      ClientStompFrame error = connV12.receiveFrame();
+      ClientStompFrame error = conn.receiveFrame();
 
       System.out.println("Receiver error: " + error);
 
-      waitDisconnect(connV12);
-      Assert.assertFalse("Should be disconnected in STOMP 1.2 after ERROR", connV12.isConnected());
+      waitDisconnect(conn);
+      Assert.assertFalse("Should be disconnected in STOMP 1.2 after ERROR", conn.isConnected());
 
       //message should still there
       MessageConsumer consumer = session.createConsumer(queue);
@@ -991,23 +877,23 @@ public class StompV12Test extends StompV11TestBase {
 
    @Test
    public void testAck() throws Exception {
-      connV12.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      subscribe(connV12, "sub1", "client");
+      subscribe(conn, "sub1", "client");
 
-      sendMessage(getName());
+      sendJmsMessage(getName());
 
-      ClientStompFrame frame = connV12.receiveFrame();
+      ClientStompFrame frame = conn.receiveFrame();
 
-      String messageID = frame.getHeader("ack");
+      String messageID = frame.getHeader(Stomp.Headers.Subscribe.ACK_MODE);
 
       Assert.assertNotNull(messageID);
 
-      ack(connV12, messageID, null);
+      ack(conn, messageID);
 
-      unsubscribe(connV12, "sub1");
+      unsubscribe(conn, "sub1");
 
-      connV12.disconnect();
+      conn.disconnect();
 
       //Nack makes the message be dropped.
       MessageConsumer consumer = session.createConsumer(queue);
@@ -1017,28 +903,28 @@ public class StompV12Test extends StompV11TestBase {
 
    @Test
    public void testAckNoIDHeader() throws Exception {
-      connV12.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      subscribe(connV12, "sub1", "client-individual");
+      subscribe(conn, "sub1", "client-individual");
 
-      sendMessage(getName());
+      sendJmsMessage(getName());
 
-      ClientStompFrame frame = connV12.receiveFrame();
+      ClientStompFrame frame = conn.receiveFrame();
 
-      String messageID = frame.getHeader("ack");
+      String messageID = frame.getHeader(Stomp.Headers.Subscribe.ACK_MODE);
 
       Assert.assertNotNull(messageID);
 
-      ClientStompFrame ackFrame = connV12.createFrame("ACK");
+      ClientStompFrame ackFrame = conn.createFrame(Stomp.Commands.ACK);
 
-      connV12.sendFrame(ackFrame);
+      conn.sendFrame(ackFrame);
 
-      frame = connV12.receiveFrame();
+      frame = conn.receiveFrame();
 
-      Assert.assertEquals("ERROR", frame.getCommand());
+      Assert.assertEquals(Stomp.Responses.ERROR, frame.getCommand());
 
-      waitDisconnect(connV12);
-      Assert.assertFalse("Should be disconnected in STOMP 1.2 after ERROR", connV12.isConnected());
+      waitDisconnect(conn);
+      Assert.assertFalse("Should be disconnected in STOMP 1.2 after ERROR", conn.isConnected());
 
       //message still there.
       MessageConsumer consumer = session.createConsumer(queue);
@@ -1048,24 +934,24 @@ public class StompV12Test extends StompV11TestBase {
 
    @Test
    public void testAckWithWrongMessageId() throws Exception {
-      connV12.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      subscribe(connV12, "sub1", "client");
+      subscribe(conn, "sub1", "client");
 
-      sendMessage(getName());
+      sendJmsMessage(getName());
 
-      ClientStompFrame frame = connV12.receiveFrame();
+      ClientStompFrame frame = conn.receiveFrame();
 
       Assert.assertNotNull(frame);
 
-      ack(connV12, "someother", null);
+      ack(conn, "someother");
 
-      ClientStompFrame error = connV12.receiveFrame();
+      ClientStompFrame error = conn.receiveFrame();
 
       System.out.println("Receiver error: " + error);
 
-      waitDisconnect(connV12);
-      Assert.assertFalse("Should be disconnected in STOMP 1.2 after ERROR", connV12.isConnected());
+      waitDisconnect(conn);
+      Assert.assertFalse("Should be disconnected in STOMP 1.2 after ERROR", conn.isConnected());
 
       //message should still there
       MessageConsumer consumer = session.createConsumer(queue);
@@ -1075,32 +961,32 @@ public class StompV12Test extends StompV11TestBase {
 
    @Test
    public void testErrorWithReceipt() throws Exception {
-      connV12.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      subscribe(connV12, "sub1", "client");
+      subscribe(conn, "sub1", "client");
 
-      sendMessage(getName());
+      sendJmsMessage(getName());
 
-      ClientStompFrame frame = connV12.receiveFrame();
+      ClientStompFrame frame = conn.receiveFrame();
 
-      String messageID = frame.getHeader("message-id");
+      String messageID = frame.getHeader(Stomp.Headers.Message.MESSAGE_ID);
 
-      ClientStompFrame ackFrame = connV12.createFrame("ACK");
+      ClientStompFrame ackFrame = conn.createFrame(Stomp.Commands.ACK);
       //give it a wrong sub id
-      ackFrame.addHeader("subscription", "sub2");
-      ackFrame.addHeader("message-id", messageID);
-      ackFrame.addHeader("receipt", "answer-me");
+      ackFrame.addHeader(Stomp.Headers.Message.SUBSCRIPTION, "sub2");
+      ackFrame.addHeader(Stomp.Headers.Message.MESSAGE_ID, messageID);
+      ackFrame.addHeader(Stomp.Headers.RECEIPT_REQUESTED, "answer-me");
 
-      ClientStompFrame error = connV12.sendFrame(ackFrame);
+      ClientStompFrame error = conn.sendFrame(ackFrame);
 
       System.out.println("Receiver error: " + error);
 
-      Assert.assertEquals("ERROR", error.getCommand());
+      Assert.assertEquals(Stomp.Responses.ERROR, error.getCommand());
 
       Assert.assertEquals("answer-me", error.getHeader("receipt-id"));
 
-      waitDisconnect(connV12);
-      Assert.assertFalse("Should be disconnected in STOMP 1.2 after ERROR", connV12.isConnected());
+      waitDisconnect(conn);
+      Assert.assertFalse("Should be disconnected in STOMP 1.2 after ERROR", conn.isConnected());
 
       //message should still there
       MessageConsumer consumer = session.createConsumer(queue);
@@ -1110,32 +996,32 @@ public class StompV12Test extends StompV11TestBase {
 
    @Test
    public void testErrorWithReceipt2() throws Exception {
-      connV12.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      subscribe(connV12, "sub1", "client");
+      subscribe(conn, "sub1", "client");
 
-      sendMessage(getName());
+      sendJmsMessage(getName());
 
-      ClientStompFrame frame = connV12.receiveFrame();
+      ClientStompFrame frame = conn.receiveFrame();
 
-      String messageID = frame.getHeader("message-id");
+      String messageID = frame.getHeader(Stomp.Headers.Message.MESSAGE_ID);
 
-      ClientStompFrame ackFrame = connV12.createFrame("ACK");
+      ClientStompFrame ackFrame = conn.createFrame(Stomp.Commands.ACK);
       //give it a wrong sub id
-      ackFrame.addHeader("subscription", "sub1");
-      ackFrame.addHeader("message-id", String.valueOf(Long.valueOf(messageID) + 1));
-      ackFrame.addHeader("receipt", "answer-me");
+      ackFrame.addHeader(Stomp.Headers.Message.SUBSCRIPTION, "sub1");
+      ackFrame.addHeader(Stomp.Headers.Message.MESSAGE_ID, String.valueOf(Long.valueOf(messageID) + 1));
+      ackFrame.addHeader(Stomp.Headers.RECEIPT_REQUESTED, "answer-me");
 
-      ClientStompFrame error = connV12.sendFrame(ackFrame);
+      ClientStompFrame error = conn.sendFrame(ackFrame);
 
       System.out.println("Receiver error: " + error);
 
-      Assert.assertEquals("ERROR", error.getCommand());
+      Assert.assertEquals(Stomp.Responses.ERROR, error.getCommand());
 
       Assert.assertEquals("answer-me", error.getHeader("receipt-id"));
 
-      waitDisconnect(connV12);
-      Assert.assertFalse("Should be disconnected in STOMP 1.2 after ERROR", connV12.isConnected());
+      waitDisconnect(conn);
+      Assert.assertFalse("Should be disconnected in STOMP 1.2 after ERROR", conn.isConnected());
 
       //message should still there
       MessageConsumer consumer = session.createConsumer(queue);
@@ -1153,29 +1039,29 @@ public class StompV12Test extends StompV11TestBase {
 
    @Test
    public void testAckModeClient() throws Exception {
-      connV12.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      subscribe(connV12, "sub1", "client");
+      subscribe(conn, "sub1", "client");
 
       int num = 50;
       //send a bunch of messages
       for (int i = 0; i < num; i++) {
-         this.sendMessage("client-ack" + i);
+         this.sendJmsMessage("client-ack" + i);
       }
 
       ClientStompFrame frame = null;
 
       for (int i = 0; i < num; i++) {
-         frame = connV12.receiveFrame();
+         frame = conn.receiveFrame();
          Assert.assertNotNull(frame);
       }
 
       //ack the last
-      ack(connV12, frame);
+      ack(conn, frame);
 
-      unsubscribe(connV12, "sub1");
+      unsubscribe(conn, "sub1");
 
-      connV12.disconnect();
+      conn.disconnect();
 
       //no messages can be received.
       MessageConsumer consumer = session.createConsumer(queue);
@@ -1185,31 +1071,31 @@ public class StompV12Test extends StompV11TestBase {
 
    @Test
    public void testAckModeClient2() throws Exception {
-      connV12.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      subscribe(connV12, "sub1", "client");
+      subscribe(conn, "sub1", "client");
 
       int num = 50;
       //send a bunch of messages
       for (int i = 0; i < num; i++) {
-         this.sendMessage("client-ack" + i);
+         this.sendJmsMessage("client-ack" + i);
       }
 
       ClientStompFrame frame = null;
 
       for (int i = 0; i < num; i++) {
-         frame = connV12.receiveFrame();
+         frame = conn.receiveFrame();
          Assert.assertNotNull(frame);
 
          //ack the 49th
          if (i == num - 2) {
-            ack(connV12, frame);
+            ack(conn, frame);
          }
       }
 
-      unsubscribe(connV12, "sub1");
+      unsubscribe(conn, "sub1");
 
-      connV12.disconnect();
+      conn.disconnect();
 
       //one can be received.
       MessageConsumer consumer = session.createConsumer(queue);
@@ -1222,26 +1108,26 @@ public class StompV12Test extends StompV11TestBase {
    //when ack is missing the mode default to auto
    @Test
    public void testAckModeDefault() throws Exception {
-      connV12.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      subscribe(connV12, "sub1", null);
+      subscribe(conn, "sub1", null);
 
       int num = 50;
       //send a bunch of messages
       for (int i = 0; i < num; i++) {
-         this.sendMessage("auto-ack" + i);
+         this.sendJmsMessage("auto-ack" + i);
       }
 
       ClientStompFrame frame = null;
 
       for (int i = 0; i < num; i++) {
-         frame = connV12.receiveFrame();
+         frame = conn.receiveFrame();
          Assert.assertNotNull(frame);
       }
 
-      unsubscribe(connV12, "sub1");
+      unsubscribe(conn, "sub1");
 
-      connV12.disconnect();
+      conn.disconnect();
 
       //no messages can be received.
       MessageConsumer consumer = session.createConsumer(queue);
@@ -1251,26 +1137,26 @@ public class StompV12Test extends StompV11TestBase {
 
    @Test
    public void testAckModeAuto() throws Exception {
-      connV12.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      subscribe(connV12, "sub1", "auto");
+      subscribe(conn, "sub1", Stomp.Headers.Subscribe.AckModeValues.AUTO);
 
       int num = 50;
       //send a bunch of messages
       for (int i = 0; i < num; i++) {
-         this.sendMessage("auto-ack" + i);
+         this.sendJmsMessage("auto-ack" + i);
       }
 
       ClientStompFrame frame = null;
 
       for (int i = 0; i < num; i++) {
-         frame = connV12.receiveFrame();
+         frame = conn.receiveFrame();
          Assert.assertNotNull(frame);
       }
 
-      unsubscribe(connV12, "sub1");
+      unsubscribe(conn, "sub1");
 
-      connV12.disconnect();
+      conn.disconnect();
 
       //no messages can be received.
       MessageConsumer consumer = session.createConsumer(queue);
@@ -1280,32 +1166,32 @@ public class StompV12Test extends StompV11TestBase {
 
    @Test
    public void testAckModeClientIndividual() throws Exception {
-      connV12.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      subscribe(connV12, "sub1", "client-individual");
+      subscribe(conn, "sub1", "client-individual");
 
       int num = 50;
       //send a bunch of messages
       for (int i = 0; i < num; i++) {
-         this.sendMessage("client-individual-ack" + i);
+         this.sendJmsMessage("client-individual-ack" + i);
       }
 
       ClientStompFrame frame = null;
 
       for (int i = 0; i < num; i++) {
-         frame = connV12.receiveFrame();
+         frame = conn.receiveFrame();
          Assert.assertNotNull(frame);
 
          System.out.println(i + " == received: " + frame);
          //ack on even numbers
          if (i % 2 == 0) {
-            ack(connV12, frame);
+            ack(conn, frame);
          }
       }
 
-      unsubscribe(connV12, "sub1");
+      unsubscribe(conn, "sub1");
 
-      connV12.disconnect();
+      conn.disconnect();
 
       //no messages can be received.
       MessageConsumer consumer = session.createConsumer(queue);
@@ -1324,64 +1210,55 @@ public class StompV12Test extends StompV11TestBase {
 
    @Test
    public void testTwoSubscribers() throws Exception {
-      connV12.connect(defUser, defPass, CLIENT_ID);
+      conn.connect(defUser, defPass, CLIENT_ID);
 
-      this.subscribeTopic(connV12, "sub1", "auto", null);
+      this.subscribeTopic(conn, "sub1", Stomp.Headers.Subscribe.AckModeValues.AUTO, null);
 
       StompClientConnection newConn = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
       newConn.connect(defUser, defPass, "myclientid2");
 
-      this.subscribeTopic(newConn, "sub2", "auto", null);
-
-      ClientStompFrame frame = connV12.createFrame("SEND");
-      frame.addHeader("destination", getTopicPrefix() + getTopicName());
+      this.subscribeTopic(newConn, "sub2", Stomp.Headers.Subscribe.AckModeValues.AUTO, null);
 
-      frame.setBody("Hello World");
-
-      connV12.sendFrame(frame);
+      send(conn, getTopicPrefix() + getTopicName(), null, "Hello World");
 
       // receive message from socket
-      frame = connV12.receiveFrame(1000);
+      ClientStompFrame frame = conn.receiveFrame(1000);
 
       System.out.println("received frame : " + frame);
       Assert.assertEquals("Hello World", frame.getBody());
-      Assert.assertEquals("sub1", frame.getHeader("subscription"));
+      Assert.assertEquals("sub1", frame.getHeader(Stomp.Headers.Message.SUBSCRIPTION));
 
       frame = newConn.receiveFrame(1000);
 
       System.out.println("received 2 frame : " + frame);
       Assert.assertEquals("Hello World", frame.getBody());
-      Assert.assertEquals("sub2", frame.getHeader("subscription"));
+      Assert.assertEquals("sub2", frame.getHeader(Stomp.Headers.Message.SUBSCRIPTION));
 
       // remove suscription
-      this.unsubscribe(connV12, "sub1", true);
+      this.unsubscribe(conn, "sub1", true);
       this.unsubscribe(newConn, "sub2", true);
 
-      connV12.disconnect();
+      conn.disconnect();
       newConn.disconnect();
    }
 
    @Test
    public void testSendAndReceiveOnDifferentConnections() throws Exception {
-      connV12.connect(defUser, defPass);
-
-      ClientStompFrame sendFrame = connV12.createFrame("SEND");
-      sendFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-      sendFrame.setBody("Hello World");
+      conn.connect(defUser, defPass);
 
-      connV12.sendFrame(sendFrame);
+      send(conn, getQueuePrefix() + getQueueName(), null, "Hello World");
 
       StompClientConnection connV12_2 = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
       connV12_2.connect(defUser, defPass);
 
-      this.subscribe(connV12_2, "sub1", "auto");
+      this.subscribe(connV12_2, "sub1", Stomp.Headers.Subscribe.AckModeValues.AUTO);
 
       ClientStompFrame frame = connV12_2.receiveFrame(2000);
 
-      Assert.assertEquals("MESSAGE", frame.getCommand());
+      Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
       Assert.assertEquals("Hello World", frame.getBody());
 
-      connV12.disconnect();
+      conn.disconnect();
       connV12_2.disconnect();
    }
 
@@ -1389,80 +1266,80 @@ public class StompV12Test extends StompV11TestBase {
 
    @Test
    public void testBeginSameTransactionTwice() throws Exception {
-      connV12.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      beginTransaction(connV12, "tx1");
+      beginTransaction(conn, "tx1");
 
-      beginTransaction(connV12, "tx1");
+      beginTransaction(conn, "tx1");
 
-      ClientStompFrame f = connV12.receiveFrame();
-      Assert.assertTrue(f.getCommand().equals("ERROR"));
+      ClientStompFrame f = conn.receiveFrame();
+      Assert.assertTrue(f.getCommand().equals(Stomp.Responses.ERROR));
    }
 
    @Test
    public void testBodyWithUTF8() throws Exception {
-      connV12.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      this.subscribe(connV12, getName(), "auto");
+      this.subscribe(conn, getName(), Stomp.Headers.Subscribe.AckModeValues.AUTO);
 
       String text = "A" + "\u00ea" + "\u00f1" + "\u00fc" + "C";
       System.out.println(text);
-      sendMessage(text);
+      sendJmsMessage(text);
 
-      ClientStompFrame frame = connV12.receiveFrame();
+      ClientStompFrame frame = conn.receiveFrame();
       System.out.println(frame);
-      Assert.assertTrue(frame.getCommand().equals("MESSAGE"));
-      Assert.assertNotNull(frame.getHeader("destination"));
+      Assert.assertTrue(frame.getCommand().equals(Stomp.Responses.MESSAGE));
+      Assert.assertNotNull(frame.getHeader(Stomp.Headers.Subscribe.DESTINATION));
       Assert.assertTrue(frame.getBody().equals(text));
 
-      connV12.disconnect();
+      conn.disconnect();
    }
 
    @Test
    public void testClientAckNotPartOfTransaction() throws Exception {
-      connV12.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      this.subscribe(connV12, getName(), "client");
+      this.subscribe(conn, getName(), "client");
 
-      sendMessage(getName());
+      sendJmsMessage(getName());
 
-      ClientStompFrame frame = connV12.receiveFrame();
+      ClientStompFrame frame = conn.receiveFrame();
 
-      Assert.assertTrue(frame.getCommand().equals("MESSAGE"));
-      Assert.assertNotNull(frame.getHeader("destination"));
+      Assert.assertTrue(frame.getCommand().equals(Stomp.Responses.MESSAGE));
+      Assert.assertNotNull(frame.getHeader(Stomp.Headers.Subscribe.DESTINATION));
       Assert.assertTrue(frame.getBody().equals(getName()));
-      Assert.assertNotNull(frame.getHeader("message-id"));
-      Assert.assertNotNull(frame.getHeader("ack"));
+      Assert.assertNotNull(frame.getHeader(Stomp.Headers.Message.MESSAGE_ID));
+      Assert.assertNotNull(frame.getHeader(Stomp.Headers.Subscribe.ACK_MODE));
 
-      String messageID = frame.getHeader("ack");
+      String messageID = frame.getHeader(Stomp.Headers.Subscribe.ACK_MODE);
 
-      beginTransaction(connV12, "tx1");
+      beginTransaction(conn, "tx1");
 
-      ack(connV12, messageID, "tx1");
+      ack(conn, messageID, "tx1");
 
-      abortTransaction(connV12, "tx1");
+      abortTransaction(conn, "tx1");
 
-      frame = connV12.receiveFrame(500);
+      frame = conn.receiveFrame(500);
 
       Assert.assertNull(frame);
 
-      this.unsubscribe(connV12, getName());
+      this.unsubscribe(conn, getName());
 
-      connV12.disconnect();
+      conn.disconnect();
    }
 
    @Test
    public void testDisconnectAndError() throws Exception {
-      connV12.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      this.subscribe(connV12, getName(), "client");
+      this.subscribe(conn, getName(), "client");
 
-      ClientStompFrame frame = connV12.createFrame("DISCONNECT");
-      frame.addHeader("receipt", "1");
+      ClientStompFrame frame = conn.createFrame("DISCONNECT");
+      frame.addHeader(Stomp.Headers.RECEIPT_REQUESTED, "1");
 
-      ClientStompFrame result = connV12.sendFrame(frame);
+      ClientStompFrame result = conn.sendFrame(frame);
 
-      if (result == null || (!"RECEIPT".equals(result.getCommand())) || (!"1".equals(result.getHeader("receipt-id")))) {
+      if (result == null || (!Stomp.Responses.RECEIPT.equals(result.getCommand())) || (!"1".equals(result.getHeader("receipt-id")))) {
          Assert.fail("Disconnect failed! " + result);
       }
 
@@ -1471,12 +1348,9 @@ public class StompV12Test extends StompV11TestBase {
       Thread thr = new Thread() {
          @Override
          public void run() {
-            ClientStompFrame sendFrame = connV12.createFrame("SEND");
-            sendFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-            sendFrame.setBody("Hello World");
             while (latch.getCount() != 0) {
                try {
-                  connV12.sendFrame(sendFrame);
+                  send(conn, getQueuePrefix() + getQueueName(), null, "Hello World");
                   Thread.sleep(500);
                } catch (InterruptedException e) {
                   //retry
@@ -1489,7 +1363,7 @@ public class StompV12Test extends StompV11TestBase {
                   latch.countDown();
                   break;
                } finally {
-                  connV12.destroy();
+                  conn.destroy();
                }
             }
          }
@@ -1509,67 +1383,67 @@ public class StompV12Test extends StompV11TestBase {
 
    @Test
    public void testDurableSubscriber() throws Exception {
-      connV12.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      this.subscribe(connV12, "sub1", "client", getName());
+      this.subscribe(conn, "sub1", "client", getName());
 
-      this.subscribe(connV12, "sub1", "client", getName());
+      this.subscribe(conn, "sub1", "client", getName());
 
-      ClientStompFrame frame = connV12.receiveFrame();
-      Assert.assertTrue(frame.getCommand().equals("ERROR"));
+      ClientStompFrame frame = conn.receiveFrame();
+      Assert.assertTrue(frame.getCommand().equals(Stomp.Responses.ERROR));
 
-      waitDisconnect(connV12);
-      Assert.assertFalse("Should be disconnected in STOMP 1.2 after ERROR", connV12.isConnected());
+      waitDisconnect(conn);
+      Assert.assertFalse("Should be disconnected in STOMP 1.2 after ERROR", conn.isConnected());
    }
 
    @Test
    public void testDurableSubscriberWithReconnection() throws Exception {
-      connV12.connect(defUser, defPass, CLIENT_ID);
+      conn.connect(defUser, defPass, CLIENT_ID);
 
-      this.subscribeTopic(connV12, "sub1", "auto", getName());
+      this.subscribeTopic(conn, "sub1", Stomp.Headers.Subscribe.AckModeValues.AUTO, getName());
 
-      ClientStompFrame frame = connV12.createFrame("DISCONNECT");
-      frame.addHeader("receipt", "1");
+      ClientStompFrame frame = conn.createFrame("DISCONNECT");
+      frame.addHeader(Stomp.Headers.RECEIPT_REQUESTED, "1");
 
-      ClientStompFrame result = connV12.sendFrame(frame);
+      ClientStompFrame result = conn.sendFrame(frame);
 
-      if (result == null || (!"RECEIPT".equals(result.getCommand())) || (!"1".equals(result.getHeader("receipt-id")))) {
+      if (result == null || (!Stomp.Responses.RECEIPT.equals(result.getCommand())) || (!"1".equals(result.getHeader("receipt-id")))) {
          Assert.fail("Disconnect failed! " + result);
       }
 
       // send the message when the durable subscriber is disconnected
-      sendMessage(getName(), topic);
+      sendJmsMessage(getName(), topic);
 
-      connV12.destroy();
-      connV12 = (StompClientConnectionV12) StompClientConnectionFactory.createClientConnection("1.2", hostname, port);
-      connV12.connect(defUser, defPass, CLIENT_ID);
+      conn.destroy();
+      conn = (StompClientConnectionV12) StompClientConnectionFactory.createClientConnection("1.2", hostname, port);
+      conn.connect(defUser, defPass, CLIENT_ID);
 
-      this.subscribeTopic(connV12, "sub1", "auto", getName());
+      this.subscribeTopic(conn, "sub1", Stomp.Headers.Subscribe.AckModeValues.AUTO, getName());
 
       // we must have received the message
-      frame = connV12.receiveFrame();
+      frame = conn.receiveFrame();
 
-      Assert.assertTrue(frame.getCommand().equals("MESSAGE"));
-      Assert.assertNotNull(frame.getHeader("destination"));
+      Assert.assertTrue(frame.getCommand().equals(Stomp.Responses.MESSAGE));
+      Assert.assertNotNull(frame.getHeader(Stomp.Headers.Subscribe.DESTINATION));
       Assert.assertEquals(getName(), frame.getBody());
 
-      this.unsubscribe(connV12, "sub1");
+      this.unsubscribe(conn, "sub1");
 
-      connV12.disconnect();
+      conn.disconnect();
    }
 
    @Test
    public void testDurableUnSubscribe() throws Exception {
-      connV12.connect(defUser, defPass, CLIENT_ID);
+      conn.connect(defUser, defPass, CLIENT_ID);
 
-      this.subscribeTopic(connV12, null, "auto", getName());
+      this.subscribeTopic(conn, null, Stomp.Headers.Subscribe.AckModeValues.AUTO, getName());
 
-      connV12.disconnect();
-      connV12.destroy();
-      connV12 = (StompClientConnectionV12) StompClientConnectionFactory.createClientConnection("1.2", hostname, port);
-      connV12.connect(defUser, defPass, CLIENT_ID);
+      conn.disconnect();
+      conn.destroy();
+      conn = (StompClientConnectionV12) StompClientConnectionFactory.createClientConnection("1.2", hostname, port);
+      conn.connect(defUser, defPass, CLIENT_ID);
 
-      this.unsubscribe(connV12, getName(), false, true);
+      this.unsubscribe(conn, getName(), null, false, true);
 
       long start = System.currentTimeMillis();
       SimpleString queueName = SimpleString.toSimpleString(CLIENT_ID + "." + getName());
@@ -1579,21 +1453,21 @@ public class StompV12Test extends StompV11TestBase {
 
       assertNull(server.getActiveMQServer().locateQueue(queueName));
 
-      connV12.disconnect();
+      conn.disconnect();
    }
 
    @Test
    public void testJMSXGroupIdCanBeSet() throws Exception {
       MessageConsumer consumer = session.createConsumer(queue);
 
-      connV12.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      ClientStompFrame frame = connV12.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SEND);
+      frame.addHeader(Stomp.Headers.Subscribe.DESTINATION, getQueuePrefix() + getQueueName());
       frame.addHeader("JMSXGroupID", "TEST");
       frame.setBody("Hello World");
 
-      connV12.sendFrame(frame);
+      conn.sendFrame(frame);
 
       TextMessage message = (TextMessage) consumer.receive(1000);
       Assert.assertNotNull(message);
@@ -1607,64 +1481,64 @@ public class StompV12Test extends StompV11TestBase {
       int ctr = 10;
       String[] data = new String[ctr];
 
-      connV12.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      this.subscribe(connV12, "sub1", "auto");
+      this.subscribe(conn, "sub1", Stomp.Headers.Subscribe.AckModeValues.AUTO);
 
       for (int i = 0; i < ctr; ++i) {
          data[i] = getName() + i;
-         sendMessage(data[i]);
+         sendJmsMessage(data[i]);
       }
 
       ClientStompFrame frame = null;
 
       for (int i = 0; i < ctr; ++i) {
-         frame = connV12.receiveFrame();
+         frame = conn.receiveFrame();
          Assert.assertTrue("Message not in order", frame.getBody().equals(data[i]));
       }
 
       for (int i = 0; i < ctr; ++i) {
          data[i] = getName() + ":second:" + i;
-         sendMessage(data[i]);
+         sendJmsMessage(data[i]);
       }
 
       for (int i = 0; i < ctr; ++i) {
-         frame = connV12.receiveFrame();
+         frame = conn.receiveFrame();
          Assert.assertTrue("Message not in order", frame.getBody().equals(data[i]));
       }
 
-      connV12.disconnect();
+      conn.disconnect();
    }
 
    @Test
    public void testSubscribeWithAutoAckAndSelector() throws Exception {
-      connV12.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      this.subscribe(connV12, "sub1", "auto", null, "foo = 'zzz'");
+      this.subscribe(conn, "sub1", Stomp.Headers.Subscribe.AckModeValues.AUTO, null, "foo = 'zzz'");
 
-      sendMessage("Ignored message", "foo", "1234");
-      sendMessage("Real message", "foo", "zzz");
+      sendJmsMessage("Ignored message", "foo", "1234");
+      sendJmsMessage("Real message", "foo", "zzz");
 
-      ClientStompFrame frame = connV12.receiveFrame();
+      ClientStompFrame frame = conn.receiveFrame();
 
       Assert.assertTrue("Should have received the real message but got: " + frame, frame.getBody().equals("Real message"));
 
-      connV12.disconnect();
+      conn.disconnect();
    }
 
    @Test
    public void testRedeliveryWithClientAck() throws Exception {
-      connV12.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      this.subscribe(connV12, "subId", "client");
+      this.subscribe(conn, "subId", "client");
 
-      sendMessage(getName());
+      sendJmsMessage(getName());
 
-      ClientStompFrame frame = connV12.receiveFrame();
+      ClientStompFrame frame = conn.receiveFrame();
 
-      Assert.assertTrue(frame.getCommand().equals("MESSAGE"));
+      Assert.assertTrue(frame.getCommand().equals(Stomp.Responses.MESSAGE));
 
-      connV12.disconnect();
+      conn.disconnect();
 
       // message should be received since message was not acknowledged
       MessageConsumer consumer = session.createConsumer(queue);
@@ -1677,7 +1551,7 @@ public class StompV12Test extends StompV11TestBase {
    public void testSendManyMessages() throws Exception {
       MessageConsumer consumer = session.createConsumer(queue);
 
-      connV12.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
       int count = 1000;
       final CountDownLatch latch = new CountDownLatch(count);
@@ -1695,30 +1569,22 @@ public class StompV12Test extends StompV11TestBase {
          }
       });
 
-      ClientStompFrame frame = connV12.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.setBody("Hello World");
-
       for (int i = 1; i <= count; i++) {
-         connV12.sendFrame(frame);
+         send(conn, getQueuePrefix() + getQueueName(), null, "Hello World");
       }
 
       Assert.assertTrue(latch.await(60, TimeUnit.SECONDS));
 
-      connV12.disconnect();
+      conn.disconnect();
    }
 
    @Test
    public void testSendMessage() throws Exception {
       MessageConsumer consumer = session.createConsumer(queue);
 
-      connV12.connect(defUser, defPass);
-
-      ClientStompFrame frame = connV12.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.setBody("Hello World");
+      conn.connect(defUser, defPass);
 
-      connV12.sendFrame(frame);
+      send(conn, getQueuePrefix() + getQueueName(), null, "Hello World");
 
       TextMessage message = (TextMessage) consumer.receive(1000);
       Assert.assertNotNull(message);
@@ -1737,18 +1603,16 @@ public class StompV12Test extends StompV11TestBase {
    public void testSendMessageWithContentLength() throws Exception {
       MessageConsumer consumer = session.createConsumer(queue);
 
-      connV12.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
       byte[] data = new byte[]{1, 0, 0, 4};
 
-      ClientStompFrame frame = connV12.createFrame("SEND");
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SEND)
+                                   .addHeader(Stomp.Headers.Subscribe.DESTINATION, getQueuePrefix() + getQueueName())
+                                   .setBody(new String(data, StandardCharsets.UTF_8))
+                                   .addHeader(Stomp.Headers.CONTENT_LENGTH, String.valueOf(data.length));
 
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.setBody(new String(data, StandardCharsets.UTF_8));
-
-      frame.addHeader("content-length", String.valueOf(data.length));
-
-      connV12.sendFrame(frame);
+      conn.sendFrame(frame);
 
       BytesMessage message = (BytesMessage) consumer.receive(10000);
       Assert.assertNotNull(message);
@@ -1764,16 +1628,15 @@ public class StompV12Test extends StompV11TestBase {
    public void testSendMessageWithCustomHeadersAndSelector() throws Exception {
       MessageConsumer consumer = session.createConsumer(queue, "foo = 'abc'");
 
-      connV12.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      ClientStompFrame frame = connV12.createFrame("SEND");
-      frame.addHeader("foo", "abc");
-      frame.addHeader("bar", "123");
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SEND)
+                                   .addHeader(Stomp.Headers.Subscribe.DESTINATION, getQueuePrefix() + getQueueName())
+                                   .addHeader("foo", "abc")
+                                   .addHeader("bar", "123")
+                                   .setBody("Hello World");
 
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.setBody("Hello World");
-
-      connV12.sendFrame(frame);
+      conn.sendFrame(frame);
 
       TextMessage message = (TextMessage) consumer.receive(1000);
       Assert.assertNotNull(message);
@@ -1786,14 +1649,13 @@ public class StompV12Test extends StompV11TestBase {
    public void testSendMessageWithLeadingNewLine() throws Exception {
       MessageConsumer consumer = session.createConsumer(queue);
 
-      connV12.connect(defUser, defPass);
-
-      ClientStompFrame frame = connV12.createFrame("SEND");
+      conn.connect(defUser, defPass);
 
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.setBody("Hello World");
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SEND)
+                                   .addHeader(Stomp.Headers.Subscribe.DESTINATION, getQueuePrefix() + getQueueName())
+                                   .setBody("Hello World");
 
-      connV12.sendWickedFrame(frame);
+      conn.sendWickedFrame(frame);
 
       TextMessage message = (TextMessage) consumer.receive(1000);
       Assert.assertNotNull(message);
@@ -1807,24 +1669,16 @@ public class StompV12Test extends StompV11TestBase {
 
       Assert.assertNull(consumer.receive(1000));
 
-      connV12.disconnect();
+      conn.disconnect();
    }
 
    @Test
    public void testSendMessageWithReceipt() throws Exception {
       MessageConsumer consumer = session.createConsumer(queue);
 
-      connV12.connect(defUser, defPass);
-
-      ClientStompFrame frame = connV12.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("receipt", "1234");
-      frame.setBody("Hello World");
-
-      frame = connV12.sendFrame(frame);
+      conn.connect(defUser, defPass);
 
-      Assert.assertTrue(frame.getCommand().equals("RECEIPT"));
-      Assert.assertEquals("1234", frame.getHeader("receipt-id"));
+      send(conn, getQueuePrefix() + getQueueName(), null, "Hello World", true);
 
       TextMessage message = (TextMessage) consumer.receive(1000);
       Assert.assertNotNull(message);
@@ -1836,28 +1690,27 @@ public class StompV12Test extends StompV11TestBase {
       long tmsg = message.getJMSTimestamp();
       Assert.assertTrue(Math.abs(tnow - tmsg) < 1000);
 
-      connV12.disconnect();
+      conn.disconnect();
    }
 
    @Test
    public void testSendMessageWithStandardHeaders() throws Exception {
       MessageConsumer consumer = session.createConsumer(queue);
 
-      connV12.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      ClientStompFrame frame = connV12.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("correlation-id", "c123");
-      frame.addHeader("persistent", "true");
-      frame.addHeader("priority", "3");
-      frame.addHeader("type", "t345");
-      frame.addHeader("JMSXGroupID", "abc");
-      frame.addHeader("foo", "abc");
-      frame.addHeader("bar", "123");
-
-      frame.setBody("Hello World");
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SEND)
+                                   .addHeader(Stomp.Headers.Subscribe.DESTINATION, getQueuePrefix() + getQueueName())
+                                   .addHeader("correlation-id", "c123")
+                                   .addHeader("persistent", "true")
+                                   .addHeader("priority", "3")
+                                   .addHeader(Stomp.Headers.Message.TYPE, "t345")
+                                   .addHeader("JMSXGroupID", "abc")
+                                   .addHeader("foo", "abc")
+                                   .addHeader("bar", "123")
+                                   .setBody("Hello World");
 
-      frame = connV12.sendFrame(frame);
+      conn.sendFrame(frame);
 
       TextMessage message = (TextMessage) consumer.receive(1000);
       Assert.assertNotNull(message);
@@ -1871,33 +1724,32 @@ public class StompV12Test extends StompV11TestBase {
 
       Assert.assertEquals("JMSXGroupID", "abc", message.getStringProperty("JMSXGroupID"));
 
-      connV12.disconnect();
+      conn.disconnect();
    }
 
    @Test
    public void testSendMessageWithLongHeaders() throws Exception {
       MessageConsumer consumer = session.createConsumer(queue);
 
-      connV12.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
       StringBuffer buffer = new StringBuffer();
       for (int i = 0; i < 2048; i++) {
          buffer.append("a");
       }
 
-      ClientStompFrame frame = connV12.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("correlation-id", "c123");
-      frame.addHeader("persistent", "true");
-      frame.addHeader("priority", "3");
-      frame.addHeader("type", "t345");
-      frame.addHeader("JMSXGroupID", "abc");
-      frame.addHeader("foo", "abc");
-      frame.addHeader("very-very-long-stomp-message-header", buffer.toString());
-
-      frame.setBody("Hello World");
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SEND)
+                                   .addHeader(Stomp.Headers.Subscribe.DESTINATION, getQueuePrefix() + getQueueName())
+                                   .addHeader("correlation-id", "c123")
+                                   .addHeader("persistent", "true")
+                                   .addHeader("priority", "3")
+                                   .addHeader(Stomp.Headers.Message.TYPE, "t345")
+                                   .addHeader("JMSXGroupID", "abc")
+                                   .addHeader("foo", "abc")
+                                   .addHeader("very-very-long-stomp-message-header", buffer.toString())
+                                   .setBody("Hello World");
 
-      frame = connV12.sendFrame(frame);
+      conn.sendFrame(frame);
 
       TextMessage message = (TextMessage) consumer.receive(1000);
       Assert.assertNotNull(message);
@@ -1911,80 +1763,75 @@ public class StompV12Test extends StompV11TestBase {
 
       Assert.assertEquals("JMSXGroupID", "abc", message.getStringProperty("JMSXGroupID"));
 
-      connV12.disconnect();
+      conn.disconnect();
    }
 
    @Test
    public void testSubscribeToTopic() throws Exception {
-      connV12.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      this.subscribeTopic(connV12, "sub1", null, null, true);
+      this.subscribeTopic(conn, "sub1", null, null, true);
 
-      sendMessage(getName(), topic);
+      sendJmsMessage(getName(), topic);
 
-      ClientStompFrame frame = connV12.receiveFrame();
+      ClientStompFrame frame = conn.receiveFrame();
 
-      Assert.assertTrue(frame.getCommand().equals("MESSAGE"));
-      Assert.assertTrue(frame.getHeader("desti

<TRUNCATED>

[10/11] activemq-artemis git commit: Fix issues after merge

Posted by jb...@apache.org.
Fix issues after merge


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

Branch: refs/heads/ARTEMIS-780
Commit: 037182250ead410c429b2d6d0f3a45cad0ec342e
Parents: 84df373
Author: jbertram <jb...@apache.com>
Authored: Thu Nov 10 19:10:01 2016 -0600
Committer: jbertram <jb...@apache.com>
Committed: Thu Nov 10 20:51:14 2016 -0600

----------------------------------------------------------------------
 .../config/ActiveMQDefaultConfiguration.java    |  3 -
 .../artemis/jms/client/ActiveMQSession.java     |  2 +-
 .../management/impl/AddressControlImpl.java     |  2 +-
 .../core/config/impl/FileConfigurationTest.java | 61 +-------------------
 .../tests/integration/stomp/StompTest.java      | 49 ++--------------
 .../tests/integration/stomp/StompTestBase.java  |  2 +-
 .../stomp/StompTestWithLargeMessages.java       | 22 -------
 .../stomp/StompTestWithMessageID.java           |  1 +
 .../stomp/util/StompFrameFactoryV11.java        |  2 -
 .../stomp/util/StompFrameFactoryV12.java        |  2 -
 .../integration/stomp/v11/ExtraStompTest.java   |  5 +-
 .../jms/tests/message/MessageHeaderTest.java    |  2 +-
 12 files changed, 15 insertions(+), 138 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/03718225/artemis-core-client/src/main/java/org/apache/activemq/artemis/api/config/ActiveMQDefaultConfiguration.java
----------------------------------------------------------------------
diff --git a/artemis-core-client/src/main/java/org/apache/activemq/artemis/api/config/ActiveMQDefaultConfiguration.java b/artemis-core-client/src/main/java/org/apache/activemq/artemis/api/config/ActiveMQDefaultConfiguration.java
index 8227e06..5511ab6 100644
--- a/artemis-core-client/src/main/java/org/apache/activemq/artemis/api/config/ActiveMQDefaultConfiguration.java
+++ b/artemis-core-client/src/main/java/org/apache/activemq/artemis/api/config/ActiveMQDefaultConfiguration.java
@@ -1188,11 +1188,8 @@ public final class ActiveMQDefaultConfiguration {
    public static boolean getDefaultDeleteQueueOnNoConsumers() {
       return DEFAULT_DELETE_QUEUE_ON_NO_CONSUMERS;
    }
-<<<<<<< HEAD
 
    public static String getInternalNamingPrefix() {
       return DEFAULT_INTERNAL_NAMING_PREFIX;
    }
-=======
->>>>>>> af5f1b1... ARTEMIS-782 Added configuration elements for new address model
 }

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/03718225/artemis-jms-client/src/main/java/org/apache/activemq/artemis/jms/client/ActiveMQSession.java
----------------------------------------------------------------------
diff --git a/artemis-jms-client/src/main/java/org/apache/activemq/artemis/jms/client/ActiveMQSession.java b/artemis-jms-client/src/main/java/org/apache/activemq/artemis/jms/client/ActiveMQSession.java
index 35bbfa0..acbb5e9 100644
--- a/artemis-jms-client/src/main/java/org/apache/activemq/artemis/jms/client/ActiveMQSession.java
+++ b/artemis-jms-client/src/main/java/org/apache/activemq/artemis/jms/client/ActiveMQSession.java
@@ -317,7 +317,7 @@ public class ActiveMQSession implements QueueSession, TopicSession {
             } else {
                if (!response.isExists()) {
                   if (response.isAutoCreateJmsTopics()) {
-                     session.createAddress(jbd.getSimpleAddress(), true);
+                     session.createAddress(jbd.getSimpleAddress(), true, true);
                   } else {
                      throw new InvalidDestinationException("Destination " + jbd.getName() + " does not exist");
                   }

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/03718225/artemis-server/src/main/java/org/apache/activemq/artemis/core/management/impl/AddressControlImpl.java
----------------------------------------------------------------------
diff --git a/artemis-server/src/main/java/org/apache/activemq/artemis/core/management/impl/AddressControlImpl.java b/artemis-server/src/main/java/org/apache/activemq/artemis/core/management/impl/AddressControlImpl.java
index 5808bd3..23b8e32 100644
--- a/artemis-server/src/main/java/org/apache/activemq/artemis/core/management/impl/AddressControlImpl.java
+++ b/artemis-server/src/main/java/org/apache/activemq/artemis/core/management/impl/AddressControlImpl.java
@@ -276,7 +276,7 @@ public class AddressControlImpl extends AbstractControl implements AddressContro
          message.getBodyBuffer().writeBytes(Base64.decode(body));
       }
       message.setAddress(addressInfo.getName());
-      postOffice.route(message, null, true);
+      postOffice.route(message, true);
       return "" + message.getMessageID();
    }
 

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/03718225/artemis-server/src/test/java/org/apache/activemq/artemis/core/config/impl/FileConfigurationTest.java
----------------------------------------------------------------------
diff --git a/artemis-server/src/test/java/org/apache/activemq/artemis/core/config/impl/FileConfigurationTest.java b/artemis-server/src/test/java/org/apache/activemq/artemis/core/config/impl/FileConfigurationTest.java
index 59f2cdf..d95ea52 100644
--- a/artemis-server/src/test/java/org/apache/activemq/artemis/core/config/impl/FileConfigurationTest.java
+++ b/artemis-server/src/test/java/org/apache/activemq/artemis/core/config/impl/FileConfigurationTest.java
@@ -46,14 +46,13 @@ import org.apache.activemq.artemis.core.security.Role;
 import org.apache.activemq.artemis.core.server.JournalType;
 import org.apache.activemq.artemis.core.server.SecuritySettingPlugin;
 import org.apache.activemq.artemis.core.server.cluster.impl.MessageLoadBalancingType;
-import org.apache.activemq.artemis.core.server.impl.AddressInfo;
 import org.apache.activemq.artemis.core.server.impl.LegacyLDAPSecuritySettingPlugin;
 import org.apache.activemq.artemis.core.settings.impl.SlowConsumerPolicy;
 import org.junit.Assert;
 import org.junit.Test;
 
-import static org.apache.activemq.artemis.core.config.CoreAddressConfiguration.RoutingType.ANYCAST;
-import static org.apache.activemq.artemis.core.config.CoreAddressConfiguration.RoutingType.MULTICAST;
+import static org.apache.activemq.artemis.core.server.impl.AddressInfo.RoutingType.ANYCAST;
+import static org.apache.activemq.artemis.core.server.impl.AddressInfo.RoutingType.MULTICAST;
 
 public class FileConfigurationTest extends ConfigurationImplTest {
 
@@ -372,62 +371,6 @@ public class FileConfigurationTest extends ConfigurationImplTest {
       // Addr 1
       CoreAddressConfiguration addressConfiguration = conf.getAddressConfigurations().get(0);
       assertEquals("addr1", addressConfiguration.getName());
-      assertEquals(AddressInfo.RoutingType.ANYCAST, addressConfiguration.getRoutingType());
-      assertEquals(2, addressConfiguration.getQueueConfigurations().size());
-
-      // Addr 1 Queue 1
-      CoreQueueConfiguration queueConfiguration = addressConfiguration.getQueueConfigurations().get(0);
-
-      assertEquals("q1", queueConfiguration.getName());
-      assertFalse(queueConfiguration.isDurable());
-      assertEquals("color='blue'", queueConfiguration.getFilterString());
-      assertEquals(addressConfiguration.getDefaultDeleteOnNoConsumers(), queueConfiguration.getDeleteOnNoConsumers());
-      assertEquals("addr1", queueConfiguration.getAddress());
-      assertEquals(addressConfiguration.getDefaultMaxConsumers(), queueConfiguration.getMaxConsumers());
-
-      // Addr 1 Queue 2
-      queueConfiguration = addressConfiguration.getQueueConfigurations().get(1);
-
-      assertEquals("q2", queueConfiguration.getName());
-      assertTrue(queueConfiguration.isDurable());
-      assertEquals("color='green'", queueConfiguration.getFilterString());
-      assertEquals(new Integer(-1), queueConfiguration.getMaxConsumers());
-      assertFalse(queueConfiguration.getDeleteOnNoConsumers());
-      assertEquals("addr1", queueConfiguration.getAddress());
-
-      // Addr 2
-      addressConfiguration = conf.getAddressConfigurations().get(1);
-      assertEquals("addr2", addressConfiguration.getName());
-      assertEquals(AddressInfo.RoutingType.MULTICAST, addressConfiguration.getRoutingType());
-      assertEquals(2, addressConfiguration.getQueueConfigurations().size());
-
-      // Addr 2 Queue 1
-      queueConfiguration = addressConfiguration.getQueueConfigurations().get(0);
-
-      assertEquals("q3", queueConfiguration.getName());
-      assertTrue(queueConfiguration.isDurable());
-      assertEquals("color='red'", queueConfiguration.getFilterString());
-      assertEquals(new Integer(10), queueConfiguration.getMaxConsumers());
-      assertEquals(addressConfiguration.getDefaultDeleteOnNoConsumers(), queueConfiguration.getDeleteOnNoConsumers());
-      assertEquals("addr2", queueConfiguration.getAddress());
-
-      // Addr 2 Queue 2
-      queueConfiguration = addressConfiguration.getQueueConfigurations().get(1);
-
-      assertEquals("q4", queueConfiguration.getName());
-      assertTrue(queueConfiguration.isDurable());
-      assertNull(queueConfiguration.getFilterString());
-      assertEquals(addressConfiguration.getDefaultMaxConsumers(), queueConfiguration.getMaxConsumers());
-      assertTrue(queueConfiguration.getDeleteOnNoConsumers());
-      assertEquals("addr2", queueConfiguration.getAddress());
-   }
-
-   private void verifyAddresses() {
-      assertEquals(2, conf.getAddressConfigurations().size());
-
-      // Addr 1
-      CoreAddressConfiguration addressConfiguration = conf.getAddressConfigurations().get(0);
-      assertEquals("addr1", addressConfiguration.getName());
       assertEquals(ANYCAST, addressConfiguration.getRoutingType());
       assertEquals(2, addressConfiguration.getQueueConfigurations().size());
 

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/03718225/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTest.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTest.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTest.java
index 91ab5d3..8e54b76 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTest.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTest.java
@@ -723,7 +723,7 @@ public class StompTest extends StompTestBase {
       Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
       Assert.assertTrue("Should have received the real message but got: " + frame, frame.getBody().equals("Real message"));
 
-    conn.disconnect();
+      conn.disconnect();
    }
 
    @Test
@@ -737,7 +737,7 @@ public class StompTest extends StompTestBase {
       Assert.assertNotNull(frame.getHeader(Stomp.Headers.Message.MESSAGE_ID));
       ack(conn, null, frame);
 
-    conn.disconnect();
+      conn.disconnect();
 
       // message should not be received since message was acknowledged by the client
       MessageConsumer consumer = session.createConsumer(queue);
@@ -774,34 +774,20 @@ public class StompTest extends StompTestBase {
    }
 
    protected void assertSubscribeWithClientAckThenConsumeWithAutoAck(boolean sendDisconnect) throws Exception {
-
       conn.connect(defUser, defPass);
-
-//            String frame = Stomp.Commands.SUBSCRIBE + "\n" +
-//               Stomp.Headers.Subscribe.SUBSCRIPTION_TYPE + Stomp.Headers.SEPARATOR + AddressInfo.RoutingType.ANYCAST + "\n" +
-//               Stomp.Headers.Send.DESTINATION + Stomp.Headers.SEPARATOR + getQueuePrefix() + getQueueName() + "\n" +
-//               Stomp.Headers.Message.ACK + Stomp.Headers.SEPARATOR + "client\n\n" +
-//               Stomp.NULL;
-//
-//            sendFrame(frame);
       subscribe(conn, null, Stomp.Headers.Subscribe.AckModeValues.CLIENT);
       sendJmsMessage(getName());
 
-//            frame = receiveFrame(10000);
-//            Assert.assertTrue(frame.startsWith(Stomp.Responses.MESSAGE));
       ClientStompFrame frame = conn.receiveFrame(10000);
       Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
 
       log.info("Reconnecting!");
 
       if (sendDisconnect) {
-       conn.disconnect();
-//         reconnect();
+         conn.disconnect();
          conn.destroy();
          conn = StompClientConnectionFactory.createClientConnection("1.0", hostname, port);
       } else {
-//         reconnect(100);
-//               waitForFrameToTakeEffect();
          conn.destroy();
          conn = StompClientConnectionFactory.createClientConnection("1.0", hostname, port);
       }
@@ -809,17 +795,8 @@ public class StompTest extends StompTestBase {
       // message should be received since message was not acknowledged
       conn.connect(defUser, defPass);
 
-//            frame = Stomp.Commands.SUBSCRIBE + "\n" +
-//               Stomp.Headers.Subscribe.SUBSCRIPTION_TYPE + Stomp.Headers.SEPARATOR + AddressInfo.RoutingType.ANYCAST + "\n" +
-//               Stomp.Headers.Subscribe.DESTINATION + Stomp.Headers.SEPARATOR + getQueuePrefix() + getQueueName() + "\n\n" +
-//               Stomp.NULL;
-//
-//            sendFrame(frame);
       subscribe(conn, null);
 
-//            frame = receiveFrame(10000);
-//            log.info(frame);
-//            Assert.assertTrue(frame.startsWith(Stomp.Responses.MESSAGE));
       frame = conn.receiveFrame(10000);
       Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
 
@@ -829,29 +806,13 @@ public class StompTest extends StompTestBase {
       conn = StompClientConnectionFactory.createClientConnection("1.0", hostname, port);
 
       // now let's make sure we don't see the message again
-//      reconnect();
 
       conn.connect(defUser, defPass);
 
-//            frame = Stomp.Commands.SUBSCRIBE + "\n" +
-//               Stomp.Headers.Subscribe.SUBSCRIPTION_TYPE + Stomp.Headers.SEPARATOR + AddressInfo.RoutingType.ANYCAST + "\n" +
-//               Stomp.Headers.Send.DESTINATION + Stomp.Headers.SEPARATOR + getQueuePrefix() + getQueueName() + "\n" +
-//               Stomp.Headers.RECEIPT_REQUESTED + Stomp.Headers.SEPARATOR + " 1234\n\n" +
-//               Stomp.NULL;
-//
-//            sendFrame(frame);
       subscribe(conn, null, Stomp.Headers.Subscribe.AckModeValues.AUTO, null, true);
 
-      // wait for SUBSCRIBE's receipt
-//            frame = receiveFrame(10000);
-//            Assert.assertTrue(frame.startsWith(Stomp.Responses.RECEIPT));
-
       sendJmsMessage("shouldBeNextMessage");
 
-//            frame = receiveFrame(10000);
-//            Assert.assertTrue(frame.startsWith(Stomp.Responses.MESSAGE));
-//            log.info(frame);
-//            Assert.assertTrue(frame.contains("shouldBeNextMessage"));
       frame = conn.receiveFrame(10000);
       Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
       Assert.assertEquals("shouldBeNextMessage", frame.getBody());
@@ -1013,9 +974,9 @@ public class StompTest extends StompTestBase {
 
       assertEquals("Subscription queue should be deleted", 0, server.getActiveMQServer().getActiveMQServerControl().getQueueNames().length - baselineQueueCount);
 
-    conn.disconnect();
+      conn.disconnect();
    }
-      //
+
    @Test
    public void testSubscribeToQueue() throws Exception {
       final int baselineQueueCount = server.getActiveMQServer().getActiveMQServerControl().getQueueNames().length;

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/03718225/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestBase.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestBase.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestBase.java
index a55f471..3ccca7d 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestBase.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestBase.java
@@ -121,7 +121,7 @@ public abstract class StompTestBase extends ActiveMQTestBase {
       super.setUp();
 
       server = createServer();
-       server.start();
+      server.start();
       connectionFactory = createConnectionFactory();
 
       ((ActiveMQConnectionFactory)connectionFactory).setCompressLargeMessage(isCompressLargeMessages());

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/03718225/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestWithLargeMessages.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestWithLargeMessages.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestWithLargeMessages.java
index 929534f..18410be 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestWithLargeMessages.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestWithLargeMessages.java
@@ -16,35 +16,13 @@
  */
 package org.apache.activemq.artemis.tests.integration.stomp;
 
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.Map;
-
 import org.apache.activemq.artemis.api.core.SimpleString;
-import org.apache.activemq.artemis.api.core.TransportConfiguration;
 import org.apache.activemq.artemis.api.core.client.ActiveMQClient;
-import org.apache.activemq.artemis.core.config.Configuration;
-import org.apache.activemq.artemis.core.protocol.stomp.StompProtocolManagerFactory;
-import org.apache.activemq.artemis.core.registry.JndiBindingRegistry;
-import org.apache.activemq.artemis.core.remoting.impl.invm.InVMAcceptorFactory;
-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.security.Role;
-import org.apache.activemq.artemis.core.server.ActiveMQServer;
-import org.apache.activemq.artemis.core.server.ActiveMQServers;
-import org.apache.activemq.artemis.jms.server.JMSServerManager;
-import org.apache.activemq.artemis.jms.server.config.JMSConfiguration;
-import org.apache.activemq.artemis.jms.server.config.impl.JMSConfigurationImpl;
-import org.apache.activemq.artemis.jms.server.config.impl.JMSQueueConfigurationImpl;
-import org.apache.activemq.artemis.jms.server.config.impl.TopicConfigurationImpl;
-import org.apache.activemq.artemis.jms.server.impl.JMSServerManagerImpl;
-import org.apache.activemq.artemis.spi.core.security.ActiveMQJAASSecurityManager;
 import org.apache.activemq.artemis.tests.integration.IntegrationTestLogger;
 import org.apache.activemq.artemis.tests.integration.largemessage.LargeMessageTestBase;
 import org.apache.activemq.artemis.tests.integration.stomp.util.ClientStompFrame;
 import org.apache.activemq.artemis.tests.integration.stomp.util.StompClientConnection;
 import org.apache.activemq.artemis.tests.integration.stomp.util.StompClientConnectionFactory;
-import org.apache.activemq.artemis.tests.unit.util.InVMNamingContext;
 import org.junit.Assert;
 import org.junit.Before;
 import org.junit.Test;

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/03718225/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestWithMessageID.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestWithMessageID.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestWithMessageID.java
index fc44437..69c214b 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestWithMessageID.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestWithMessageID.java
@@ -31,6 +31,7 @@ import org.junit.Test;
 
 public class StompTestWithMessageID extends StompTestBase {
 
+   @Override
    public boolean isEnableStompMessageId() {
       return true;
    }

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/03718225/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactoryV11.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactoryV11.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactoryV11.java
index 807b3f0..dc9622f 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactoryV11.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactoryV11.java
@@ -16,8 +16,6 @@
  */
 package org.apache.activemq.artemis.tests.integration.stomp.util;
 
-import java.util.StringTokenizer;
-
 /**
  * 1.1 frames
  * <br>

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/03718225/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactoryV12.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactoryV12.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactoryV12.java
index dbd32e0..e128094 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactoryV12.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactoryV12.java
@@ -16,8 +16,6 @@
  */
 package org.apache.activemq.artemis.tests.integration.stomp.util;
 
-import java.util.StringTokenizer;
-
 public class StompFrameFactoryV12 extends StompFrameFactoryV11 {
 
    @Override

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/03718225/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v11/ExtraStompTest.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v11/ExtraStompTest.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v11/ExtraStompTest.java
index 5414a9f..4bd9b6f 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v11/ExtraStompTest.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v11/ExtraStompTest.java
@@ -35,6 +35,7 @@ public class ExtraStompTest extends StompTestBase {
    private StompClientConnection connV10;
    private StompClientConnection connV11;
 
+   @Override
    public boolean isPersistenceEnabled() {
       return true;
    }
@@ -119,8 +120,8 @@ public class ExtraStompTest extends StompTestBase {
    @Test
    public void testNoGarbageAfterPersistentMessageV11() throws Exception {
       testNoGarbageAfterPersistentMessage(connV11);
-   }   
-   
+   }
+
    public void testNoGarbageAfterPersistentMessage(StompClientConnection conn) throws Exception {
       subscribe(conn, "a-sub");
 

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/03718225/tests/jms-tests/src/test/java/org/apache/activemq/artemis/jms/tests/message/MessageHeaderTest.java
----------------------------------------------------------------------
diff --git a/tests/jms-tests/src/test/java/org/apache/activemq/artemis/jms/tests/message/MessageHeaderTest.java b/tests/jms-tests/src/test/java/org/apache/activemq/artemis/jms/tests/message/MessageHeaderTest.java
index 994c1a6..f8b7153 100644
--- a/tests/jms-tests/src/test/java/org/apache/activemq/artemis/jms/tests/message/MessageHeaderTest.java
+++ b/tests/jms-tests/src/test/java/org/apache/activemq/artemis/jms/tests/message/MessageHeaderTest.java
@@ -1125,7 +1125,7 @@ public class MessageHeaderTest extends MessageHeaderTestBase {
       }
 
       @Override
-      public void createAddress(SimpleString address, boolean multicast) throws ActiveMQException {
+      public void createAddress(SimpleString address, boolean multicast, final boolean autoCreated) throws ActiveMQException {
 
       }
 


[08/11] activemq-artemis git commit: Stomp refactor + track autocreation for addresses

Posted by jb...@apache.org.
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/client/HangConsumerTest.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/client/HangConsumerTest.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/client/HangConsumerTest.java
index 159a285..8822015 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/client/HangConsumerTest.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/client/HangConsumerTest.java
@@ -513,7 +513,7 @@ public class HangConsumerTest extends ActiveMQTestBase {
       }
 
       /* (non-Javadoc)
-       * @see SessionCallback#sendMessage(org.apache.activemq.artemis.core.server.ServerMessage, long, int)
+       * @see SessionCallback#sendJmsMessage(org.apache.activemq.artemis.core.server.ServerMessage, long, int)
        */
       @Override
       public int sendMessage(MessageReference ref, ServerMessage message, ServerConsumer consumer, int deliveryCount) {
@@ -592,7 +592,7 @@ public class HangConsumerTest extends ActiveMQTestBase {
                                                         SessionCallback callback,
                                                         OperationContext context,
                                                         boolean autoCreateQueue) throws Exception {
-         return new ServerSessionImpl(name, username, password, validatedUser, minLargeMessageSize, autoCommitSends, autoCommitAcks, preAcknowledge, getConfiguration().isPersistDeliveryCountBeforeDelivery(), xa, connection, getStorageManager(), getPostOffice(), getResourceManager(), getSecurityStore(), getManagementService(), this, getConfiguration().getManagementAddress(), defaultAddress == null ? null : new SimpleString(defaultAddress), new MyCallback(callback), context, null, getPagingManager());
+         return new ServerSessionImpl(name, username, password, validatedUser, minLargeMessageSize, autoCommitSends, autoCommitAcks, preAcknowledge, getConfiguration().isPersistDeliveryCountBeforeDelivery(), xa, connection, getStorageManager(), getPostOffice(), getResourceManager(), getSecurityStore(), getManagementService(), this, getConfiguration().getManagementAddress(), defaultAddress == null ? null : new SimpleString(defaultAddress), new MyCallback(callback), context, getPagingManager());
       }
    }
 

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/ConcurrentStompTest.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/ConcurrentStompTest.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/ConcurrentStompTest.java
deleted file mode 100644
index 6917cfb..0000000
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/ConcurrentStompTest.java
+++ /dev/null
@@ -1,136 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements. See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License. You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.activemq.artemis.tests.integration.stomp;
-
-import java.io.ByteArrayOutputStream;
-import java.io.IOException;
-import java.io.InputStream;
-import java.io.OutputStream;
-import java.net.Socket;
-import java.nio.charset.StandardCharsets;
-import java.util.concurrent.CountDownLatch;
-import java.util.concurrent.TimeUnit;
-
-import org.apache.activemq.artemis.core.protocol.stomp.Stomp;
-import org.junit.Assert;
-import org.junit.Test;
-
-public class ConcurrentStompTest extends StompTestBase {
-
-   private Socket stompSocket_2;
-
-   private ByteArrayOutputStream inputBuffer_2;
-
-   /**
-    * Send messages on 1 socket and receives them concurrently on another socket.
-    */
-   @Test
-   public void testSendManyMessages() throws Exception {
-      try {
-         String connect = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-
-         sendFrame(connect);
-         String connected = receiveFrame(10000);
-         Assert.assertTrue(connected.startsWith("CONNECTED"));
-
-         stompSocket_2 = createSocket();
-         inputBuffer_2 = new ByteArrayOutputStream();
-
-         sendFrame(stompSocket_2, connect);
-         connected = receiveFrame(stompSocket_2, inputBuffer_2, 10000);
-         Assert.assertTrue(connected.startsWith("CONNECTED"));
-
-         final int count = 1000;
-         final CountDownLatch latch = new CountDownLatch(count);
-
-         String subscribe = "SUBSCRIBE\n" +
-            "destination:" + getQueuePrefix() + getQueueName() + "\n" +
-            "ack:auto\n\n" +
-            Stomp.NULL;
-         sendFrame(stompSocket_2, subscribe);
-         Thread.sleep(2000);
-
-         new Thread() {
-            @Override
-            public void run() {
-               int i = 0;
-               while (true) {
-                  try {
-                     String frame = receiveFrame(stompSocket_2, inputBuffer_2, 10000);
-                     Assert.assertTrue(frame.startsWith("MESSAGE"));
-                     Assert.assertTrue(frame.indexOf("destination:") > 0);
-                     System.out.println("<<< " + i++);
-                     latch.countDown();
-                  } catch (Exception e) {
-                     break;
-                  }
-               }
-            }
-         }.start();
-
-         String send = "SEND\n" + "destination:" + getQueuePrefix() + getQueueName() + "\n";
-         for (int i = 1; i <= count; i++) {
-            // Thread.sleep(1);
-            System.out.println(">>> " + i);
-            sendFrame(send + "count:" + i + "\n\n" + Stomp.NULL);
-         }
-
-         assertTrue(latch.await(60, TimeUnit.SECONDS));
-
-      } finally {
-         stompSocket_2.close();
-         inputBuffer_2.close();
-      }
-
-   }
-
-   // Implementation methods
-   // -------------------------------------------------------------------------
-   public void sendFrame(Socket socket, String data) throws Exception {
-      byte[] bytes = data.getBytes(StandardCharsets.UTF_8);
-      OutputStream outputStream = socket.getOutputStream();
-      for (byte b : bytes) {
-         outputStream.write(b);
-      }
-      outputStream.flush();
-   }
-
-   public String receiveFrame(Socket socket, ByteArrayOutputStream input, long timeOut) throws Exception {
-      socket.setSoTimeout((int) timeOut);
-      InputStream is = socket.getInputStream();
-      int c = 0;
-      for (;;) {
-         c = is.read();
-         if (c < 0) {
-            throw new IOException("socket closed.");
-         } else if (c == 0) {
-            c = is.read();
-            if (c != '\n') {
-               byte[] ba = input.toByteArray();
-               System.out.println(new String(ba, StandardCharsets.UTF_8));
-            }
-            Assert.assertEquals("Expecting stomp frame to terminate with \0\n", c, '\n');
-            byte[] ba = input.toByteArray();
-            input.reset();
-            return new String(ba, StandardCharsets.UTF_8);
-         } else {
-            input.write(c);
-         }
-      }
-   }
-
-}

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/ExtraStompTest.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/ExtraStompTest.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/ExtraStompTest.java
deleted file mode 100644
index a0dcdbf..0000000
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/ExtraStompTest.java
+++ /dev/null
@@ -1,848 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements. See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License. You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.activemq.artemis.tests.integration.stomp;
-
-import javax.jms.Message;
-import javax.jms.MessageConsumer;
-import javax.jms.QueueBrowser;
-import javax.jms.TextMessage;
-import java.util.ArrayList;
-import java.util.Enumeration;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-
-import org.apache.activemq.artemis.api.core.Interceptor;
-import org.apache.activemq.artemis.api.core.TransportConfiguration;
-import org.apache.activemq.artemis.api.core.client.ActiveMQClient;
-import org.apache.activemq.artemis.core.config.Configuration;
-import org.apache.activemq.artemis.core.protocol.core.Packet;
-import org.apache.activemq.artemis.core.protocol.stomp.Stomp;
-import org.apache.activemq.artemis.core.protocol.stomp.StompFrame;
-import org.apache.activemq.artemis.core.protocol.stomp.StompFrameInterceptor;
-import org.apache.activemq.artemis.core.protocol.stomp.StompProtocolManagerFactory;
-import org.apache.activemq.artemis.core.registry.JndiBindingRegistry;
-import org.apache.activemq.artemis.core.remoting.impl.invm.InVMAcceptorFactory;
-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.server.ActiveMQServer;
-import org.apache.activemq.artemis.core.server.ActiveMQServers;
-import org.apache.activemq.artemis.jms.server.JMSServerManager;
-import org.apache.activemq.artemis.jms.server.config.JMSConfiguration;
-import org.apache.activemq.artemis.jms.server.config.impl.JMSConfigurationImpl;
-import org.apache.activemq.artemis.jms.server.config.impl.JMSQueueConfigurationImpl;
-import org.apache.activemq.artemis.jms.server.config.impl.TopicConfigurationImpl;
-import org.apache.activemq.artemis.jms.server.impl.JMSServerManagerImpl;
-import org.apache.activemq.artemis.spi.core.protocol.RemotingConnection;
-import org.apache.activemq.artemis.tests.integration.largemessage.LargeMessageTestBase;
-import org.apache.activemq.artemis.tests.integration.stomp.util.ClientStompFrame;
-import org.apache.activemq.artemis.tests.integration.stomp.util.StompClientConnection;
-import org.apache.activemq.artemis.tests.integration.stomp.util.StompClientConnectionFactory;
-import org.apache.activemq.artemis.tests.unit.util.InVMNamingContext;
-import org.junit.Assert;
-import org.junit.Before;
-import org.junit.Test;
-
-public class ExtraStompTest extends StompTestBase {
-
-   @Override
-   @Before
-   public void setUp() throws Exception {
-      autoCreateServer = false;
-      super.setUp();
-   }
-
-   @Test
-   public void testConnectionTTL() throws Exception {
-      try {
-         server = createServerWithTTL("2000");
-         server.start();
-
-         setUpAfterServer();
-
-         String connect_frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n" + "request-id: 1\n" + "\n" + Stomp.NULL;
-         sendFrame(connect_frame);
-
-         String f = receiveFrame(10000);
-         Assert.assertTrue(f.startsWith("CONNECTED"));
-         Assert.assertTrue(f.indexOf("response-id:1") >= 0);
-
-         String frame = "SEND\n" + "destination:" + getQueuePrefix() + getQueueName() + "\n\n" + "Hello World 1" + Stomp.NULL;
-         sendFrame(frame);
-
-         assertChannelClosed();
-
-         MessageConsumer consumer = session.createConsumer(queue);
-
-         TextMessage message = (TextMessage) consumer.receiveNoWait();
-         Assert.assertNotNull(message);
-
-         message = (TextMessage) consumer.receiveNoWait();
-         Assert.assertNull(message);
-      } finally {
-         cleanUp();
-         server.stop();
-      }
-   }
-
-   @Test
-   public void testEnableMessageID() throws Exception {
-      enableMessageIDTest(true);
-   }
-
-   @Test
-   public void testDisableMessageID() throws Exception {
-      enableMessageIDTest(false);
-   }
-
-   @Test
-   public void testDefaultEnableMessageID() throws Exception {
-      enableMessageIDTest(null);
-   }
-
-   //stomp sender -> large -> stomp receiver
-   @Test
-   public void testSendReceiveLargePersistentMessages() throws Exception {
-      try {
-         server = createPersistentServerWithStompMinLargeSize(2048);
-         server.start();
-
-         setUpAfterServer();
-
-         String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-         sendFrame(frame);
-         frame = receiveFrame(10000);
-
-         Assert.assertTrue(frame.startsWith("CONNECTED"));
-         int count = 10;
-         int szBody = 1024 * 1024;
-         char[] contents = new char[szBody];
-         for (int i = 0; i < szBody; i++) {
-            contents[i] = 'A';
-         }
-         String body = new String(contents);
-
-         frame = "SEND\n" + "destination:" + getQueuePrefix() + getQueueName() + "\n" + "persistent:true\n" + "\n\n" + body + Stomp.NULL;
-
-         for (int i = 0; i < count; i++) {
-            sendFrame(frame);
-         }
-
-         frame = "SUBSCRIBE\n" + "destination:" + getQueuePrefix() + getQueueName() + "\n" + "ack:auto\n\nfff" + Stomp.NULL;
-         sendFrame(frame);
-
-         for (int i = 0; i < count; i++) {
-            frame = receiveFrame(60000);
-            Assert.assertNotNull(frame);
-            System.out.println("part of frame: " + frame.substring(0, 200));
-            Assert.assertTrue(frame.startsWith("MESSAGE"));
-            Assert.assertTrue(frame.indexOf("destination:") > 0);
-            int index = frame.indexOf("AAAA");
-            assertEquals(szBody, (frame.length() - index));
-         }
-
-         // remove suscription
-         frame = "UNSUBSCRIBE\n" + "destination:" +
-            getQueuePrefix() +
-            getQueueName() +
-            "\n" +
-            "receipt:567\n" +
-            "\n\n" +
-            Stomp.NULL;
-         sendFrame(frame);
-         waitForReceipt();
-
-         frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-         sendFrame(frame);
-      } catch (Exception ex) {
-         ex.printStackTrace();
-         throw ex;
-      } finally {
-         cleanUp();
-         server.stop();
-      }
-   }
-
-   //core sender -> large -> stomp receiver
-   @Test
-   public void testReceiveLargePersistentMessagesFromCore() throws Exception {
-      try {
-         server = createPersistentServerWithStompMinLargeSize(2048);
-         server.start();
-
-         setUpAfterServer();
-
-         int msgSize = 3 * ActiveMQClient.DEFAULT_MIN_LARGE_MESSAGE_SIZE;
-         char[] contents = new char[msgSize];
-         for (int i = 0; i < msgSize; i++) {
-            contents[i] = 'B';
-         }
-         String msg = new String(contents);
-
-         int count = 10;
-         for (int i = 0; i < count; i++) {
-            this.sendMessage(msg);
-         }
-
-         String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-         sendFrame(frame);
-         frame = receiveFrame(10000);
-
-         Assert.assertTrue(frame.startsWith("CONNECTED"));
-
-         frame = "SUBSCRIBE\n" + "destination:" + getQueuePrefix() + getQueueName() + "\n" + "ack:auto\n\nfff" + Stomp.NULL;
-         sendFrame(frame);
-
-         for (int i = 0; i < count; i++) {
-            frame = receiveFrame(60000);
-            Assert.assertNotNull(frame);
-            System.out.println("part of frame: " + frame.substring(0, 250));
-            Assert.assertTrue(frame.startsWith("MESSAGE"));
-            Assert.assertTrue(frame.indexOf("destination:") > 0);
-            int index = frame.indexOf("BBBB");
-            assertEquals(msgSize, (frame.length() - index));
-         }
-
-         // remove suscription
-         frame = "UNSUBSCRIBE\n" + "destination:" +
-            getQueuePrefix() +
-            getQueueName() +
-            "\n" +
-            "receipt:567\n" +
-            "\n\n" +
-            Stomp.NULL;
-         sendFrame(frame);
-         waitForReceipt();
-
-         frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-         sendFrame(frame);
-      } catch (Exception ex) {
-         ex.printStackTrace();
-         throw ex;
-      } finally {
-         cleanUp();
-         server.stop();
-      }
-   }
-
-   //stomp v12 sender -> large -> stomp v12 receiver
-   @Test
-   public void testSendReceiveLargePersistentMessagesV12() throws Exception {
-      try {
-         server = createPersistentServerWithStompMinLargeSize(2048);
-         server.start();
-
-         setUpAfterServer();
-
-         StompClientConnection connV12 = StompClientConnectionFactory.createClientConnection("1.2", "localhost", port);
-         connV12.connect(defUser, defPass);
-
-         int count = 10;
-         int szBody = 1024 * 1024;
-         char[] contents = new char[szBody];
-         for (int i = 0; i < szBody; i++) {
-            contents[i] = 'A';
-         }
-         String body = new String(contents);
-
-         ClientStompFrame frame = connV12.createFrame("SEND");
-         frame.addHeader("destination", getQueuePrefix() + getQueueName());
-         frame.addHeader("persistent", "true");
-         frame.setBody(body);
-
-         for (int i = 0; i < count; i++) {
-            connV12.sendFrame(frame);
-         }
-
-         ClientStompFrame subFrame = connV12.createFrame("SUBSCRIBE");
-         subFrame.addHeader("id", "a-sub");
-         subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-         subFrame.addHeader("ack", "auto");
-
-         connV12.sendFrame(subFrame);
-
-         for (int i = 0; i < count; i++) {
-            ClientStompFrame receiveFrame = connV12.receiveFrame(30000);
-
-            Assert.assertNotNull(receiveFrame);
-            System.out.println("part of frame: " + receiveFrame.getBody().substring(0, 20));
-            Assert.assertTrue(receiveFrame.getCommand().equals("MESSAGE"));
-            Assert.assertEquals(receiveFrame.getHeader("destination"), getQueuePrefix() + getQueueName());
-            assertEquals(szBody, receiveFrame.getBody().length());
-         }
-
-         // remove susbcription
-         ClientStompFrame unsubFrame = connV12.createFrame("UNSUBSCRIBE");
-         unsubFrame.addHeader("id", "a-sub");
-         connV12.sendFrame(unsubFrame);
-
-         connV12.disconnect();
-      } catch (Exception ex) {
-         ex.printStackTrace();
-         throw ex;
-      } finally {
-         cleanUp();
-         server.stop();
-      }
-   }
-
-   //core sender -> large -> stomp v12 receiver
-   @Test
-   public void testReceiveLargePersistentMessagesFromCoreV12() throws Exception {
-      try {
-         server = createPersistentServerWithStompMinLargeSize(2048);
-         server.start();
-
-         setUpAfterServer();
-
-         int msgSize = 3 * ActiveMQClient.DEFAULT_MIN_LARGE_MESSAGE_SIZE;
-         char[] contents = new char[msgSize];
-         for (int i = 0; i < msgSize; i++) {
-            contents[i] = 'B';
-         }
-         String msg = new String(contents);
-
-         int count = 10;
-         for (int i = 0; i < count; i++) {
-            this.sendMessage(msg);
-         }
-
-         StompClientConnection connV12 = StompClientConnectionFactory.createClientConnection("1.2", "localhost", port);
-         connV12.connect(defUser, defPass);
-
-         ClientStompFrame subFrame = connV12.createFrame("SUBSCRIBE");
-         subFrame.addHeader("id", "a-sub");
-         subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-         subFrame.addHeader("ack", "auto");
-
-         connV12.sendFrame(subFrame);
-
-         for (int i = 0; i < count; i++) {
-            ClientStompFrame receiveFrame = connV12.receiveFrame(30000);
-
-            Assert.assertNotNull(receiveFrame);
-            System.out.println("part of frame: " + receiveFrame.getBody().substring(0, 20));
-            Assert.assertTrue(receiveFrame.getCommand().equals("MESSAGE"));
-            Assert.assertEquals(receiveFrame.getHeader("destination"), getQueuePrefix() + getQueueName());
-            assertEquals(msgSize, receiveFrame.getBody().length());
-         }
-
-         // remove susbcription
-         ClientStompFrame unsubFrame = connV12.createFrame("UNSUBSCRIBE");
-         unsubFrame.addHeader("id", "a-sub");
-         connV12.sendFrame(unsubFrame);
-
-         connV12.disconnect();
-      } catch (Exception ex) {
-         ex.printStackTrace();
-         throw ex;
-      } finally {
-         cleanUp();
-         server.stop();
-      }
-   }
-
-   //core sender -> large (compressed regular) -> stomp v10 receiver
-   @Test
-   public void testReceiveLargeCompressedToRegularPersistentMessagesFromCore() throws Exception {
-      try {
-         server = createPersistentServerWithStompMinLargeSize(2048);
-         server.start();
-
-         setUpAfterServer(true);
-
-         LargeMessageTestBase.TestLargeMessageInputStream input = new LargeMessageTestBase.TestLargeMessageInputStream(ActiveMQClient.DEFAULT_MIN_LARGE_MESSAGE_SIZE, true);
-         LargeMessageTestBase.adjustLargeCompression(true, input, ActiveMQClient.DEFAULT_MIN_LARGE_MESSAGE_SIZE);
-
-         char[] contents = input.toArray();
-         String msg = new String(contents);
-
-         String leadingPart = msg.substring(0, 100);
-
-         int count = 10;
-         for (int i = 0; i < count; i++) {
-            this.sendMessage(msg);
-         }
-
-         String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-         sendFrame(frame);
-         frame = receiveFrame(10000);
-
-         Assert.assertTrue(frame.startsWith("CONNECTED"));
-
-         frame = "SUBSCRIBE\n" + "destination:" + getQueuePrefix() + getQueueName() + "\n" + "ack:auto\n\nfff" + Stomp.NULL;
-         sendFrame(frame);
-
-         for (int i = 0; i < count; i++) {
-            frame = receiveFrame(60000);
-            Assert.assertNotNull(frame);
-            System.out.println("part of frame: " + frame.substring(0, 250));
-            Assert.assertTrue(frame.startsWith("MESSAGE"));
-            Assert.assertTrue(frame.indexOf("destination:") > 0);
-            int index = frame.indexOf(leadingPart);
-            assertEquals(msg.length(), (frame.length() - index));
-         }
-
-         // remove suscription
-         frame = "UNSUBSCRIBE\n" + "destination:" +
-            getQueuePrefix() +
-            getQueueName() +
-            "\n" +
-            "receipt:567\n" +
-            "\n\n" +
-            Stomp.NULL;
-         sendFrame(frame);
-         waitForReceipt();
-
-         frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-         sendFrame(frame);
-      } catch (Exception ex) {
-         ex.printStackTrace();
-         throw ex;
-      } finally {
-         cleanUp();
-         server.stop();
-      }
-   }
-
-   //core sender -> large (compressed regular) -> stomp v12 receiver
-   @Test
-   public void testReceiveLargeCompressedToRegularPersistentMessagesFromCoreV12() throws Exception {
-      try {
-         server = createPersistentServerWithStompMinLargeSize(2048);
-         server.start();
-
-         setUpAfterServer(true);
-
-         LargeMessageTestBase.TestLargeMessageInputStream input = new LargeMessageTestBase.TestLargeMessageInputStream(ActiveMQClient.DEFAULT_MIN_LARGE_MESSAGE_SIZE, true);
-         LargeMessageTestBase.adjustLargeCompression(true, input, ActiveMQClient.DEFAULT_MIN_LARGE_MESSAGE_SIZE);
-
-         char[] contents = input.toArray();
-         String msg = new String(contents);
-
-         int count = 10;
-         for (int i = 0; i < count; i++) {
-            this.sendMessage(msg);
-         }
-
-         StompClientConnection connV12 = StompClientConnectionFactory.createClientConnection("1.2", "localhost", port);
-         connV12.connect(defUser, defPass);
-
-         ClientStompFrame subFrame = connV12.createFrame("SUBSCRIBE");
-         subFrame.addHeader("id", "a-sub");
-         subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-         subFrame.addHeader("ack", "auto");
-
-         connV12.sendFrame(subFrame);
-
-         for (int i = 0; i < count; i++) {
-            ClientStompFrame receiveFrame = connV12.receiveFrame(30000);
-
-            Assert.assertNotNull(receiveFrame);
-            System.out.println("part of frame: " + receiveFrame.getBody().substring(0, 20));
-            Assert.assertTrue(receiveFrame.getCommand().equals("MESSAGE"));
-            Assert.assertEquals(receiveFrame.getHeader("destination"), getQueuePrefix() + getQueueName());
-            assertEquals(contents.length, receiveFrame.getBody().length());
-         }
-
-         // remove susbcription
-         ClientStompFrame unsubFrame = connV12.createFrame("UNSUBSCRIBE");
-         unsubFrame.addHeader("id", "a-sub");
-         connV12.sendFrame(unsubFrame);
-
-         connV12.disconnect();
-      } catch (Exception ex) {
-         ex.printStackTrace();
-         throw ex;
-      } finally {
-         cleanUp();
-         server.stop();
-      }
-   }
-
-   //core sender -> large (compressed large) -> stomp v12 receiver
-   @Test
-   public void testReceiveLargeCompressedToLargePersistentMessagesFromCoreV12() throws Exception {
-      try {
-         server = createPersistentServerWithStompMinLargeSize(2048);
-         server.start();
-
-         setUpAfterServer(true);
-
-         LargeMessageTestBase.TestLargeMessageInputStream input = new LargeMessageTestBase.TestLargeMessageInputStream(ActiveMQClient.DEFAULT_MIN_LARGE_MESSAGE_SIZE, true);
-         input.setSize(10 * ActiveMQClient.DEFAULT_MIN_LARGE_MESSAGE_SIZE);
-         LargeMessageTestBase.adjustLargeCompression(false, input, 10 * ActiveMQClient.DEFAULT_MIN_LARGE_MESSAGE_SIZE);
-
-         char[] contents = input.toArray();
-         String msg = new String(contents);
-
-         int count = 10;
-         for (int i = 0; i < count; i++) {
-            this.sendMessage(msg);
-         }
-
-         StompClientConnection connV12 = StompClientConnectionFactory.createClientConnection("1.2", "localhost", port);
-         connV12.connect(defUser, defPass);
-
-         ClientStompFrame subFrame = connV12.createFrame("SUBSCRIBE");
-         subFrame.addHeader("id", "a-sub");
-         subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-         subFrame.addHeader("ack", "auto");
-
-         connV12.sendFrame(subFrame);
-
-         for (int i = 0; i < count; i++) {
-            ClientStompFrame receiveFrame = connV12.receiveFrame(30000);
-
-            Assert.assertNotNull(receiveFrame);
-            System.out.println("part of frame: " + receiveFrame.getBody().substring(0, 20));
-            Assert.assertTrue(receiveFrame.getCommand().equals("MESSAGE"));
-            Assert.assertEquals(receiveFrame.getHeader("destination"), getQueuePrefix() + getQueueName());
-            assertEquals(contents.length, receiveFrame.getBody().length());
-         }
-
-         // remove susbcription
-         ClientStompFrame unsubFrame = connV12.createFrame("UNSUBSCRIBE");
-         unsubFrame.addHeader("id", "a-sub");
-         connV12.sendFrame(unsubFrame);
-
-         connV12.disconnect();
-      } catch (Exception ex) {
-         ex.printStackTrace();
-         throw ex;
-      } finally {
-         cleanUp();
-         server.stop();
-      }
-   }
-
-   //core sender -> large (compressed large) -> stomp v10 receiver
-   @Test
-   public void testReceiveLargeCompressedToLargePersistentMessagesFromCore() throws Exception {
-      try {
-         server = createPersistentServerWithStompMinLargeSize(2048);
-         server.start();
-
-         setUpAfterServer(true);
-
-         LargeMessageTestBase.TestLargeMessageInputStream input = new LargeMessageTestBase.TestLargeMessageInputStream(ActiveMQClient.DEFAULT_MIN_LARGE_MESSAGE_SIZE, true);
-         input.setSize(10 * ActiveMQClient.DEFAULT_MIN_LARGE_MESSAGE_SIZE);
-         LargeMessageTestBase.adjustLargeCompression(false, input, 10 * ActiveMQClient.DEFAULT_MIN_LARGE_MESSAGE_SIZE);
-
-         char[] contents = input.toArray();
-         String msg = new String(contents);
-
-         String leadingPart = msg.substring(0, 100);
-
-         int count = 10;
-         for (int i = 0; i < count; i++) {
-            this.sendMessage(msg);
-         }
-
-         String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-         sendFrame(frame);
-         frame = receiveFrame(10000);
-
-         Assert.assertTrue(frame.startsWith("CONNECTED"));
-
-         frame = "SUBSCRIBE\n" + "destination:" + getQueuePrefix() + getQueueName() + "\n" + "ack:auto\n\nfff" + Stomp.NULL;
-         sendFrame(frame);
-
-         for (int i = 0; i < count; i++) {
-            frame = receiveFrame(60000);
-            Assert.assertNotNull(frame);
-            System.out.println("part of frame: " + frame.substring(0, 250));
-            Assert.assertTrue(frame.startsWith("MESSAGE"));
-            Assert.assertTrue(frame.indexOf("destination:") > 0);
-            int index = frame.indexOf(leadingPart);
-            assertEquals(msg.length(), (frame.length() - index));
-         }
-
-         // remove suscription
-         frame = "UNSUBSCRIBE\n" + "destination:" +
-            getQueuePrefix() +
-            getQueueName() +
-            "\n" +
-            "receipt:567\n" +
-            "\n\n" +
-            Stomp.NULL;
-         sendFrame(frame);
-         waitForReceipt();
-
-         frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-         sendFrame(frame);
-      } catch (Exception ex) {
-         ex.printStackTrace();
-         throw ex;
-      } finally {
-         cleanUp();
-         server.stop();
-      }
-   }
-
-   protected JMSServerManager createPersistentServerWithStompMinLargeSize(int sz) throws Exception {
-      Map<String, Object> params = new HashMap<>();
-      params.put(TransportConstants.PROTOCOLS_PROP_NAME, StompProtocolManagerFactory.STOMP_PROTOCOL_NAME);
-      params.put(TransportConstants.PORT_PROP_NAME, TransportConstants.DEFAULT_STOMP_PORT);
-      params.put(TransportConstants.STOMP_CONSUMERS_CREDIT, "-1");
-      params.put(TransportConstants.STOMP_MIN_LARGE_MESSAGE_SIZE, sz);
-      TransportConfiguration stompTransport = new TransportConfiguration(NettyAcceptorFactory.class.getName(), params);
-
-      Configuration config = createBasicConfig().setPersistenceEnabled(true).addAcceptorConfiguration(stompTransport).addAcceptorConfiguration(new TransportConfiguration(InVMAcceptorFactory.class.getName()));
-
-      ActiveMQServer activeMQServer = addServer(ActiveMQServers.newActiveMQServer(config, defUser, defPass));
-
-      JMSConfiguration jmsConfig = new JMSConfigurationImpl();
-      jmsConfig.getQueueConfigurations().add(new JMSQueueConfigurationImpl().setName(getQueueName()).setBindings(getQueueName()));
-      jmsConfig.getTopicConfigurations().add(new TopicConfigurationImpl().setName(getTopicName()).setBindings(getTopicName()));
-      server = new JMSServerManagerImpl(activeMQServer, jmsConfig);
-      server.setRegistry(new JndiBindingRegistry((new InVMNamingContext())));
-      return server;
-   }
-
-   private void enableMessageIDTest(Boolean enable) throws Exception {
-      try {
-         server = createServerWithExtraStompOptions(null, enable);
-         server.start();
-
-         setUpAfterServer();
-
-         String connect_frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n" + "request-id: 1\n" + "\n" + Stomp.NULL;
-         sendFrame(connect_frame);
-
-         String f = receiveFrame(10000);
-         Assert.assertTrue(f.startsWith("CONNECTED"));
-         Assert.assertTrue(f.indexOf("response-id:1") >= 0);
-
-         String frame = "SEND\n" + "destination:" + getQueuePrefix() + getQueueName() + "\n\n" + "Hello World 1" + Stomp.NULL;
-         sendFrame(frame);
-
-         frame = "SEND\n" + "destination:" + getQueuePrefix() + getQueueName() + "\n\n" + "Hello World 2" + Stomp.NULL;
-
-         sendFrame(frame);
-
-         QueueBrowser browser = session.createBrowser(queue);
-
-         Enumeration enu = browser.getEnumeration();
-
-         while (enu.hasMoreElements()) {
-            Message msg = (Message) enu.nextElement();
-            String msgId = msg.getStringProperty("amqMessageId");
-            if (enable != null && enable.booleanValue()) {
-               assertNotNull(msgId);
-               assertTrue(msgId.indexOf("STOMP") == 0);
-            } else {
-               assertNull(msgId);
-            }
-         }
-
-         browser.close();
-
-         MessageConsumer consumer = session.createConsumer(queue);
-
-         TextMessage message = (TextMessage) consumer.receive(1000);
-         Assert.assertNotNull(message);
-
-         message = (TextMessage) consumer.receive(1000);
-         Assert.assertNotNull(message);
-
-         message = (TextMessage) consumer.receive(2000);
-         Assert.assertNull(message);
-      } finally {
-         cleanUp();
-         server.stop();
-      }
-   }
-
-   protected JMSServerManager createServerWithTTL(String ttl) throws Exception {
-      return createServerWithExtraStompOptions(ttl, null);
-   }
-
-   protected JMSServerManager createServerWithExtraStompOptions(String ttl, Boolean enableMessageID) throws Exception {
-
-      Map<String, Object> params = new HashMap<>();
-      params.put(TransportConstants.PROTOCOLS_PROP_NAME, StompProtocolManagerFactory.STOMP_PROTOCOL_NAME);
-      params.put(TransportConstants.PORT_PROP_NAME, TransportConstants.DEFAULT_STOMP_PORT);
-      if (ttl != null) {
-         params.put(TransportConstants.CONNECTION_TTL, ttl);
-      }
-      if (enableMessageID != null) {
-         params.put(TransportConstants.STOMP_ENABLE_MESSAGE_ID, enableMessageID);
-      }
-      params.put(TransportConstants.STOMP_CONSUMERS_CREDIT, "-1");
-      TransportConfiguration stompTransport = new TransportConfiguration(NETTY_ACCEPTOR_FACTORY, params);
-
-      Configuration config = createBasicConfig().setPersistenceEnabled(false).addAcceptorConfiguration(stompTransport).addAcceptorConfiguration(new TransportConfiguration(INVM_ACCEPTOR_FACTORY));
-
-      ActiveMQServer activeMQServer = addServer(ActiveMQServers.newActiveMQServer(config, defUser, defPass));
-
-      JMSConfiguration jmsConfig = new JMSConfigurationImpl();
-      jmsConfig.getQueueConfigurations().add(new JMSQueueConfigurationImpl().setName(getQueueName()).setDurable(false).setBindings(getQueueName()));
-      jmsConfig.getTopicConfigurations().add(new TopicConfigurationImpl().setName(getTopicName()).setBindings(getTopicName()));
-      server = new JMSServerManagerImpl(activeMQServer, jmsConfig);
-      server.setRegistry(new JndiBindingRegistry(new InVMNamingContext()));
-      return server;
-   }
-
-   public static class MyCoreInterceptor implements Interceptor {
-
-      static List<Packet> incomingInterceptedFrames = new ArrayList<>();
-
-      @Override
-      public boolean intercept(Packet packet, RemotingConnection connection) {
-         incomingInterceptedFrames.add(packet);
-         return true;
-      }
-
-   }
-
-   public static class MyIncomingStompFrameInterceptor implements StompFrameInterceptor {
-
-      static List<StompFrame> incomingInterceptedFrames = new ArrayList<>();
-
-      @Override
-      public boolean intercept(StompFrame stompFrame, RemotingConnection connection) {
-         incomingInterceptedFrames.add(stompFrame);
-         stompFrame.addHeader("incomingInterceptedProp", "incomingInterceptedVal");
-         return true;
-      }
-   }
-
-   public static class MyOutgoingStompFrameInterceptor implements StompFrameInterceptor {
-
-      static List<StompFrame> outgoingInterceptedFrames = new ArrayList<>();
-
-      @Override
-      public boolean intercept(StompFrame stompFrame, RemotingConnection connection) {
-         outgoingInterceptedFrames.add(stompFrame);
-         stompFrame.addHeader("outgoingInterceptedProp", "outgoingInterceptedVal");
-         return true;
-      }
-   }
-
-   @Test
-   public void stompFrameInterceptor() throws Exception {
-      MyIncomingStompFrameInterceptor.incomingInterceptedFrames.clear();
-      MyOutgoingStompFrameInterceptor.outgoingInterceptedFrames.clear();
-      try {
-         List<String> incomingInterceptorList = new ArrayList<>();
-         incomingInterceptorList.add("org.apache.activemq.artemis.tests.integration.stomp.ExtraStompTest$MyIncomingStompFrameInterceptor");
-         incomingInterceptorList.add("org.apache.activemq.artemis.tests.integration.stomp.ExtraStompTest$MyCoreInterceptor");
-         List<String> outgoingInterceptorList = new ArrayList<>();
-         outgoingInterceptorList.add("org.apache.activemq.artemis.tests.integration.stomp.ExtraStompTest$MyOutgoingStompFrameInterceptor");
-
-         server = createServerWithStompInterceptor(incomingInterceptorList, outgoingInterceptorList);
-         server.start();
-
-         setUpAfterServer(); // This will make some calls through core
-
-         // So we clear them here
-         MyCoreInterceptor.incomingInterceptedFrames.clear();
-
-         String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-         sendFrame(frame);
-
-         frame = receiveFrame(100000);
-
-         frame = "SUBSCRIBE\n" + "destination:" + getQueuePrefix() + getQueueName() + "\n" + "ack:auto\n\nfff" + Stomp.NULL;
-         sendFrame(frame);
-
-         assertEquals(0, MyCoreInterceptor.incomingInterceptedFrames.size());
-         sendMessage(getName());
-
-         // Something was supposed to be called on sendMessages
-         assertTrue("core interceptor is not working", MyCoreInterceptor.incomingInterceptedFrames.size() > 0);
-
-         receiveFrame(10000);
-
-         frame = "SEND\n" + "destination:" +
-            getQueuePrefix() +
-            getQueueName() +
-            "\n\n" +
-            "Hello World" +
-            Stomp.NULL;
-         sendFrame(frame);
-
-         receiveFrame(10000);
-
-         frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-
-         sendFrame(frame);
-
-      } finally {
-         cleanUp();
-         server.stop();
-      }
-
-      List<String> incomingCommands = new ArrayList<>(4);
-      incomingCommands.add("CONNECT");
-      incomingCommands.add("SUBSCRIBE");
-      incomingCommands.add("SEND");
-      incomingCommands.add("DISCONNECT");
-
-      List<String> outgoingCommands = new ArrayList<>(3);
-      outgoingCommands.add("CONNECTED");
-      outgoingCommands.add("MESSAGE");
-      outgoingCommands.add("MESSAGE");
-
-      long timeout = System.currentTimeMillis() + 1000;
-
-      // Things are async, giving some time to things arrive before we actually assert
-      while (MyIncomingStompFrameInterceptor.incomingInterceptedFrames.size() < 4 &&
-         MyOutgoingStompFrameInterceptor.outgoingInterceptedFrames.size() < 3 &&
-         timeout > System.currentTimeMillis()) {
-         Thread.sleep(10);
-      }
-
-      Assert.assertEquals(4, MyIncomingStompFrameInterceptor.incomingInterceptedFrames.size());
-      Assert.assertEquals(3, MyOutgoingStompFrameInterceptor.outgoingInterceptedFrames.size());
-
-      for (int i = 0; i < MyIncomingStompFrameInterceptor.incomingInterceptedFrames.size(); i++) {
-         Assert.assertEquals(incomingCommands.get(i), MyIncomingStompFrameInterceptor.incomingInterceptedFrames.get(i).getCommand());
-         Assert.assertEquals("incomingInterceptedVal", MyIncomingStompFrameInterceptor.incomingInterceptedFrames.get(i).getHeader("incomingInterceptedProp"));
-      }
-
-      for (int i = 0; i < MyOutgoingStompFrameInterceptor.outgoingInterceptedFrames.size(); i++) {
-         Assert.assertEquals(outgoingCommands.get(i), MyOutgoingStompFrameInterceptor.outgoingInterceptedFrames.get(i).getCommand());
-      }
-
-      Assert.assertEquals("incomingInterceptedVal", MyOutgoingStompFrameInterceptor.outgoingInterceptedFrames.get(2).getHeader("incomingInterceptedProp"));
-      Assert.assertEquals("outgoingInterceptedVal", MyOutgoingStompFrameInterceptor.outgoingInterceptedFrames.get(2).getHeader("outgoingInterceptedProp"));
-   }
-
-   protected JMSServerManager createServerWithStompInterceptor(List<String> stompIncomingInterceptor,
-                                                               List<String> stompOutgoingInterceptor) throws Exception {
-
-      Map<String, Object> params = new HashMap<>();
-      params.put(TransportConstants.PROTOCOLS_PROP_NAME, StompProtocolManagerFactory.STOMP_PROTOCOL_NAME);
-      params.put(TransportConstants.PORT_PROP_NAME, TransportConstants.DEFAULT_STOMP_PORT);
-      params.put(TransportConstants.STOMP_CONSUMERS_CREDIT, "-1");
-      TransportConfiguration stompTransport = new TransportConfiguration(NETTY_ACCEPTOR_FACTORY, params);
-
-      Configuration config = createBasicConfig().setPersistenceEnabled(false).addAcceptorConfiguration(stompTransport).addAcceptorConfiguration(new TransportConfiguration(INVM_ACCEPTOR_FACTORY)).setIncomingInterceptorClassNames(stompIncomingInterceptor).setOutgoingInterceptorClassNames(stompOutgoingInterceptor);
-
-      ActiveMQServer hornetQServer = addServer(ActiveMQServers.newActiveMQServer(config, defUser, defPass));
-
-      JMSConfiguration jmsConfig = new JMSConfigurationImpl();
-      jmsConfig.getQueueConfigurations().add(new JMSQueueConfigurationImpl().setName(getQueueName()).setDurable(false).setBindings(getQueueName()));
-      jmsConfig.getTopicConfigurations().add(new TopicConfigurationImpl().setName(getTopicName()).setBindings(getTopicName()));
-      server = new JMSServerManagerImpl(hornetQServer, jmsConfig);
-      server.setRegistry(new JndiBindingRegistry(new InVMNamingContext()));
-      return server;
-   }
-
-}

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompConnectionCleanupTest.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompConnectionCleanupTest.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompConnectionCleanupTest.java
index 419b339..ac89c1d 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompConnectionCleanupTest.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompConnectionCleanupTest.java
@@ -19,32 +19,20 @@ package org.apache.activemq.artemis.tests.integration.stomp;
 import javax.jms.Message;
 import javax.jms.MessageConsumer;
 
-import org.apache.activemq.artemis.core.protocol.stomp.Stomp;
 import org.apache.activemq.artemis.jms.server.JMSServerManager;
+import org.apache.activemq.artemis.tests.integration.stomp.util.ClientStompFrame;
 import org.junit.Test;
 
-public class StompConnectionCleanupTest extends StompTestBase {
+public class StompConnectionCleanupTest extends StompTest {
 
    private static final long CONNECTION_TTL = 2000;
 
    // ARTEMIS-231
    @Test
    public void testConnectionCleanupWithTopicSubscription() throws Exception {
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-      frame = receiveFrame(10000);
+      conn.connect(defUser, defPass);
 
-      //We send and consumer a message to ensure a STOMP connection and server session is created
-
-      System.out.println("Received frame: " + frame);
-
-      assertTrue(frame.startsWith("CONNECTED"));
-
-      frame = "SUBSCRIBE\n" + "destination:" + getTopicPrefix() + getTopicName() + "\n" + "ack:auto\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = "DISCONNECT\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      subscribeTopic(conn, null, "auto", null);
 
       // Now we wait until the connection is cleared on the server, which will happen some time after ttl, since no data
       // is being sent
@@ -72,25 +60,16 @@ public class StompConnectionCleanupTest extends StompTestBase {
 
    @Test
    public void testConnectionCleanup() throws Exception {
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-      frame = receiveFrame(10000);
+      conn.connect(defUser, defPass);
 
-      //We send and consumer a message to ensure a STOMP connection and server session is created
+      subscribe(conn, null, "auto", null);
 
-      System.out.println("Received frame: " + frame);
+      send(conn, getQueuePrefix() + getQueueName(), null, "Hello World");
 
-      assertTrue(frame.startsWith("CONNECTED"));
+      ClientStompFrame frame = conn.receiveFrame(10000);
 
-      frame = "SUBSCRIBE\n" + "destination:" + getQueuePrefix() + getQueueName() + "\n" + "ack:auto\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = "SEND\n" + "destination:" + getQueuePrefix() + getQueueName() + "\n\n" + "Hello World" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(10000);
-      assertTrue(frame.startsWith("MESSAGE"));
-      assertTrue(frame.indexOf("destination:") > 0);
+      assertTrue(frame.getCommand().equals("MESSAGE"));
+      assertTrue(frame.getHeader("destination").equals(getQueuePrefix() + getQueueName()));
 
       // Now we wait until the connection is cleared on the server, which will happen some time after ttl, since no data
       // is being sent
@@ -118,13 +97,7 @@ public class StompConnectionCleanupTest extends StompTestBase {
 
    @Test
    public void testConnectionNotCleanedUp() throws Exception {
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-      frame = receiveFrame(10000);
-
-      //We send and consumer a message to ensure a STOMP connection and server session is created
-
-      assertTrue(frame.startsWith("CONNECTED"));
+      conn.connect(defUser, defPass);
 
       MessageConsumer consumer = session.createConsumer(queue);
 
@@ -136,8 +109,7 @@ public class StompConnectionCleanupTest extends StompTestBase {
       while (true) {
          //Send and receive a msg
 
-         frame = "SEND\n" + "destination:" + getQueuePrefix() + getQueueName() + "\n\n" + "Hello World" + Stomp.NULL;
-         sendFrame(frame);
+         send(conn, getQueuePrefix() + getQueueName(), null, "Hello World");
 
          Message msg = consumer.receive(1000);
          assertNotNull(msg);

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompOverHttpTest.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompOverHttpTest.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompOverHttpTest.java
deleted file mode 100644
index 138e37c..0000000
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompOverHttpTest.java
+++ /dev/null
@@ -1,78 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements. See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License. You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.activemq.artemis.tests.integration.stomp;
-
-import java.nio.charset.StandardCharsets;
-
-import io.netty.buffer.ByteBuf;
-import io.netty.channel.ChannelDuplexHandler;
-import io.netty.channel.ChannelHandlerContext;
-import io.netty.channel.ChannelPromise;
-import io.netty.channel.socket.SocketChannel;
-import io.netty.handler.codec.http.DefaultFullHttpRequest;
-import io.netty.handler.codec.http.DefaultHttpContent;
-import io.netty.handler.codec.http.FullHttpRequest;
-import io.netty.handler.codec.http.HttpHeaders;
-import io.netty.handler.codec.http.HttpMethod;
-import io.netty.handler.codec.http.HttpRequestEncoder;
-import io.netty.handler.codec.http.HttpResponseDecoder;
-import io.netty.handler.codec.http.HttpVersion;
-import io.netty.handler.codec.string.StringDecoder;
-import io.netty.handler.codec.string.StringEncoder;
-
-public class StompOverHttpTest extends StompTest {
-
-   @Override
-   protected void addChannelHandlers(int index, SocketChannel ch) {
-      ch.pipeline().addLast(new HttpRequestEncoder());
-      ch.pipeline().addLast(new HttpResponseDecoder());
-      ch.pipeline().addLast(new HttpHandler());
-      ch.pipeline().addLast("decoder", new StringDecoder(StandardCharsets.UTF_8));
-      ch.pipeline().addLast("encoder", new StringEncoder(StandardCharsets.UTF_8));
-      ch.pipeline().addLast(new StompClientHandler(index));
-   }
-
-   @Override
-   public String receiveFrame(long timeOut) throws Exception {
-      //we are request/response so may need to send an empty request so we get responses piggy backed
-      sendFrame(new byte[]{});
-      return super.receiveFrame(timeOut);
-   }
-
-   class HttpHandler extends ChannelDuplexHandler {
-
-      @Override
-      public void channelRead(final ChannelHandlerContext ctx, final Object msg) throws Exception {
-         if (msg instanceof DefaultHttpContent) {
-            DefaultHttpContent response = (DefaultHttpContent) msg;
-            ctx.fireChannelRead(response.content());
-         }
-      }
-
-      @Override
-      public void write(final ChannelHandlerContext ctx, final Object msg, ChannelPromise promise) throws Exception {
-         if (msg instanceof ByteBuf) {
-            ByteBuf buf = (ByteBuf) msg;
-            FullHttpRequest httpRequest = new DefaultFullHttpRequest(HttpVersion.HTTP_1_1, HttpMethod.POST, "", buf);
-            httpRequest.headers().add(HttpHeaders.Names.CONTENT_LENGTH, String.valueOf(buf.readableBytes()));
-            ctx.write(httpRequest, promise);
-         } else {
-            ctx.write(msg, promise);
-         }
-      }
-   }
-}

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompOverWebsocketTest.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompOverWebsocketTest.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompOverWebsocketTest.java
deleted file mode 100644
index 95801f7..0000000
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompOverWebsocketTest.java
+++ /dev/null
@@ -1,151 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements. See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License. You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.activemq.artemis.tests.integration.stomp;
-
-import java.net.URI;
-import java.net.URISyntaxException;
-import java.nio.charset.StandardCharsets;
-import java.util.Arrays;
-import java.util.Collection;
-import java.util.List;
-
-import io.netty.buffer.Unpooled;
-import io.netty.channel.Channel;
-import io.netty.channel.ChannelDuplexHandler;
-import io.netty.channel.ChannelHandlerContext;
-import io.netty.channel.ChannelPromise;
-import io.netty.channel.socket.SocketChannel;
-import io.netty.handler.codec.http.FullHttpResponse;
-import io.netty.handler.codec.http.HttpClientCodec;
-import io.netty.handler.codec.http.HttpObjectAggregator;
-import io.netty.handler.codec.http.websocketx.BinaryWebSocketFrame;
-import io.netty.handler.codec.http.websocketx.CloseWebSocketFrame;
-import io.netty.handler.codec.http.websocketx.PongWebSocketFrame;
-import io.netty.handler.codec.http.websocketx.TextWebSocketFrame;
-import io.netty.handler.codec.http.websocketx.WebSocketClientHandshaker;
-import io.netty.handler.codec.http.websocketx.WebSocketClientHandshakerFactory;
-import io.netty.handler.codec.http.websocketx.WebSocketFrame;
-import io.netty.handler.codec.http.websocketx.WebSocketVersion;
-import io.netty.handler.codec.string.StringDecoder;
-import org.junit.runner.RunWith;
-import org.junit.runners.Parameterized;
-
-@RunWith(Parameterized.class)
-public class StompOverWebsocketTest extends StompTest {
-
-   private ChannelPromise handshakeFuture;
-
-   private final boolean useBinaryFrames;
-
-   @Parameterized.Parameters(name = "useBinaryFrames={0}")
-   public static Collection<Object[]> data() {
-      List<Object[]> list = Arrays.asList(new Object[][]{{Boolean.TRUE}, {Boolean.FALSE}});
-      return list;
-   }
-
-   public StompOverWebsocketTest(Boolean useBinaryFrames) {
-      super();
-      this.useBinaryFrames = useBinaryFrames;
-   }
-
-   @Override
-   protected void addChannelHandlers(int index, SocketChannel ch) throws URISyntaxException {
-      ch.pipeline().addLast("http-codec", new HttpClientCodec());
-      ch.pipeline().addLast("aggregator", new HttpObjectAggregator(8192));
-      ch.pipeline().addLast(new WebsocketHandler(WebSocketClientHandshakerFactory.newHandshaker(new URI("ws://localhost:8080/websocket"), WebSocketVersion.V13, null, false, null)));
-      ch.pipeline().addLast("decoder", new StringDecoder(StandardCharsets.UTF_8));
-      ch.pipeline().addLast(new StompClientHandler(index));
-   }
-
-   @Override
-   protected void handshake() throws InterruptedException {
-      handshakeFuture.sync();
-   }
-
-   class WebsocketHandler extends ChannelDuplexHandler {
-
-      private WebSocketClientHandshaker handshaker;
-
-      WebsocketHandler(WebSocketClientHandshaker webSocketClientHandshaker) {
-         this.handshaker = webSocketClientHandshaker;
-      }
-
-      @Override
-      public void handlerAdded(ChannelHandlerContext ctx) throws Exception {
-         handshakeFuture = ctx.newPromise();
-      }
-
-      @Override
-      public void channelActive(ChannelHandlerContext ctx) throws Exception {
-         handshaker.handshake(ctx.channel());
-      }
-
-      @Override
-      public void channelInactive(ChannelHandlerContext ctx) throws Exception {
-         System.out.println("WebSocket Client disconnected!");
-      }
-
-      @Override
-      public void channelRead(ChannelHandlerContext ctx, Object msg) throws Exception {
-         Channel ch = ctx.channel();
-         if (!handshaker.isHandshakeComplete()) {
-            handshaker.finishHandshake(ch, (FullHttpResponse) msg);
-            System.out.println("WebSocket Client connected!");
-            handshakeFuture.setSuccess();
-            return;
-         }
-
-         if (msg instanceof FullHttpResponse) {
-            FullHttpResponse response = (FullHttpResponse) msg;
-            throw new Exception("Unexpected FullHttpResponse (getStatus=" + response.getStatus() + ", content=" + response.content().toString(StandardCharsets.UTF_8) + ')');
-         }
-
-         WebSocketFrame frame = (WebSocketFrame) msg;
-         if (frame instanceof BinaryWebSocketFrame) {
-            BinaryWebSocketFrame dataFrame = (BinaryWebSocketFrame) frame;
-            super.channelRead(ctx, dataFrame.content());
-         } else if (frame instanceof PongWebSocketFrame) {
-            System.out.println("WebSocket Client received pong");
-         } else if (frame instanceof CloseWebSocketFrame) {
-            System.out.println("WebSocket Client received closing");
-            ch.close();
-         }
-      }
-
-      @Override
-      public void write(ChannelHandlerContext ctx, Object msg, ChannelPromise promise) throws Exception {
-         try {
-            if (msg instanceof String) {
-               ctx.write(createFrame((String) msg), promise);
-            } else {
-               super.write(ctx, msg, promise);
-            }
-         } catch (Exception e) {
-            e.printStackTrace();  //To change body of catch statement use File | Settings | File Templates.
-         }
-      }
-   }
-
-   protected WebSocketFrame createFrame(String msg) {
-      if (useBinaryFrames) {
-         return new BinaryWebSocketFrame(Unpooled.copiedBuffer(msg, StandardCharsets.UTF_8));
-      } else {
-         return new TextWebSocketFrame(msg);
-      }
-   }
-
-}


[04/11] activemq-artemis git commit: Stomp refactor + track autocreation for addresses

Posted by jb...@apache.org.
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v11/StompV11Test.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v11/StompV11Test.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v11/StompV11Test.java
index da69d96..e8a6f25 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v11/StompV11Test.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v11/StompV11Test.java
@@ -32,8 +32,10 @@ import java.util.concurrent.TimeUnit;
 
 import org.apache.activemq.artemis.api.core.SimpleString;
 import org.apache.activemq.artemis.core.protocol.stomp.Stomp;
+import org.apache.activemq.artemis.core.server.impl.AddressInfo;
 import org.apache.activemq.artemis.core.settings.impl.AddressSettings;
 import org.apache.activemq.artemis.tests.integration.IntegrationTestLogger;
+import org.apache.activemq.artemis.tests.integration.stomp.StompTestBase;
 import org.apache.activemq.artemis.tests.integration.stomp.util.ClientStompFrame;
 import org.apache.activemq.artemis.tests.integration.stomp.util.StompClientConnection;
 import org.apache.activemq.artemis.tests.integration.stomp.util.StompClientConnectionFactory;
@@ -46,28 +48,28 @@ import org.junit.Test;
 /*
  *
  */
-public class StompV11Test extends StompV11TestBase {
+public class StompV11Test extends StompTestBase {
 
    private static final transient IntegrationTestLogger log = IntegrationTestLogger.LOGGER;
    public static final String CLIENT_ID = "myclientid";
 
-   private StompClientConnection connV11;
+   private StompClientConnection conn;
 
    @Override
    @Before
    public void setUp() throws Exception {
       super.setUp();
-      connV11 = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
+      conn = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
    }
 
    @Override
    @After
    public void tearDown() throws Exception {
       try {
-         boolean connected = connV11 != null && connV11.isConnected();
-         log.debug("Connection 11 : " + connected);
+         boolean connected = conn != null && conn.isConnected();
+         log.debug("Connection 1.1 : " + connected);
          if (connected) {
-            connV11.disconnect();
+            conn.disconnect();
          }
       } finally {
          super.tearDown();
@@ -115,276 +117,234 @@ public class StompV11Test extends StompV11TestBase {
       conn = (StompClientConnectionV11) StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
       ClientStompFrame frame = conn.connect("invaliduser", defPass);
       assertFalse(conn.isConnected());
-      assertTrue("ERROR".equals(frame.getCommand()));
+      assertTrue(Stomp.Responses.ERROR.equals(frame.getCommand()));
       assertTrue(frame.getBody().contains("Security Error occurred"));
    }
 
    @Test
    public void testNegotiation() throws Exception {
       // case 1 accept-version absent. It is a 1.0 connect
-      ClientStompFrame frame = connV11.createFrame("CONNECT");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.CONNECT)
+                                   .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                                   .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                                   .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass);
 
-      ClientStompFrame reply = connV11.sendFrame(frame);
+      ClientStompFrame reply = conn.sendFrame(frame);
 
-      assertEquals("CONNECTED", reply.getCommand());
+      assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
 
       //reply headers: version, session, server
       assertEquals(null, reply.getHeader("version"));
 
-      connV11.disconnect();
+      conn.disconnect();
 
       // case 2 accept-version=1.0, result: 1.0
-      connV11 = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
-      frame = connV11.createFrame("CONNECT");
-      frame.addHeader("accept-version", "1.0");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
+      conn = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
+      frame = conn.createFrame(Stomp.Commands.CONNECT)
+                  .addHeader(Stomp.Headers.Connect.ACCEPT_VERSION, "1.0")
+                  .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                  .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                  .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass);
 
-      reply = connV11.sendFrame(frame);
+      reply = conn.sendFrame(frame);
 
-      assertEquals("CONNECTED", reply.getCommand());
+      assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
 
       //reply headers: version, session, server
       assertEquals("1.0", reply.getHeader("version"));
 
-      connV11.disconnect();
+      conn.disconnect();
 
       // case 3 accept-version=1.1, result: 1.1
-      connV11 = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
-      frame = connV11.createFrame("CONNECT");
-      frame.addHeader("accept-version", "1.1");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
+      conn = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
+      frame = conn.createFrame(Stomp.Commands.CONNECT)
+                  .addHeader(Stomp.Headers.Connect.ACCEPT_VERSION, "1.1")
+                  .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                  .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                  .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass);
 
-      reply = connV11.sendFrame(frame);
+      reply = conn.sendFrame(frame);
 
-      assertEquals("CONNECTED", reply.getCommand());
+      assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
 
       //reply headers: version, session, server
       assertEquals("1.1", reply.getHeader("version"));
 
-      connV11.disconnect();
+      conn.disconnect();
 
       // case 4 accept-version=1.0,1.1,1.2, result 1.1
-      connV11 = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
-      frame = connV11.createFrame("CONNECT");
-      frame.addHeader("accept-version", "1.0,1.1,1.3");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
+      conn = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
+      frame = conn.createFrame(Stomp.Commands.CONNECT)
+                  .addHeader(Stomp.Headers.Connect.ACCEPT_VERSION, "1.0,1.1,1.3")
+                  .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                  .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                  .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass);
 
-      reply = connV11.sendFrame(frame);
+      reply = conn.sendFrame(frame);
 
-      assertEquals("CONNECTED", reply.getCommand());
+      assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
 
       //reply headers: version, session, server
       assertEquals("1.1", reply.getHeader("version"));
 
-      connV11.disconnect();
+      conn.disconnect();
 
       // case 5 accept-version=1.2, result error
-      connV11 = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
-      frame = connV11.createFrame("CONNECT");
-      frame.addHeader("accept-version", "1.3");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
+      conn = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
+      frame = conn.createFrame(Stomp.Commands.CONNECT)
+                  .addHeader(Stomp.Headers.Connect.ACCEPT_VERSION, "1.3")
+                  .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                  .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                  .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass);
 
-      reply = connV11.sendFrame(frame);
+      reply = conn.sendFrame(frame);
 
-      assertEquals("ERROR", reply.getCommand());
+      assertEquals(Stomp.Responses.ERROR, reply.getCommand());
 
-      System.out.println("Got error frame " + reply);
+      IntegrationTestLogger.LOGGER.info("Got error frame " + reply);
 
    }
 
    @Test
    public void testSendAndReceive() throws Exception {
-      connV11.connect(defUser, defPass);
-      ClientStompFrame frame = connV11.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-type", "text/plain");
-      frame.setBody("Hello World 1!");
+      conn.connect(defUser, defPass);
 
-      ClientStompFrame response = connV11.sendFrame(frame);
+      ClientStompFrame response = send(conn, getQueuePrefix() + getQueueName(), "text/plain", "Hello World 1!");
 
       assertNull(response);
 
-      frame.addHeader("receipt", "1234");
-      frame.setBody("Hello World 2!");
-
-      response = connV11.sendFrame(frame);
-
-      assertNotNull(response);
+      String uuid = UUID.randomUUID().toString();
 
-      assertEquals("RECEIPT", response.getCommand());
-
-      assertEquals("1234", response.getHeader("receipt-id"));
+      response = send(conn, getQueuePrefix() + getQueueName(), "text/plain", "Hello World 2!", true);
 
       //subscribe
       StompClientConnection newConn = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
       newConn.connect(defUser, defPass);
 
-      ClientStompFrame subFrame = newConn.createFrame("SUBSCRIBE");
-      subFrame.addHeader("id", "a-sub");
-      subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-      subFrame.addHeader("ack", "auto");
-
-      newConn.sendFrame(subFrame);
+      subscribe(newConn, "a-sub");
 
-      frame = newConn.receiveFrame();
+      ClientStompFrame frame = newConn.receiveFrame();
 
-      System.out.println("received " + frame);
+      IntegrationTestLogger.LOGGER.info("received " + frame);
 
-      assertEquals("MESSAGE", frame.getCommand());
+      assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
 
-      assertEquals("a-sub", frame.getHeader("subscription"));
+      assertEquals("a-sub", frame.getHeader(Stomp.Headers.Ack.SUBSCRIPTION));
 
-      assertNotNull(frame.getHeader("message-id"));
+      assertNotNull(frame.getHeader(Stomp.Headers.Message.MESSAGE_ID));
 
-      assertEquals(getQueuePrefix() + getQueueName(), frame.getHeader("destination"));
+      assertEquals(getQueuePrefix() + getQueueName(), frame.getHeader(Stomp.Headers.Message.DESTINATION));
 
       assertEquals("Hello World 1!", frame.getBody());
 
       frame = newConn.receiveFrame();
 
-      System.out.println("received " + frame);
+      IntegrationTestLogger.LOGGER.info("received " + frame);
 
-      //unsub
-      ClientStompFrame unsubFrame = newConn.createFrame("UNSUBSCRIBE");
-      unsubFrame.addHeader("id", "a-sub");
-      newConn.sendFrame(unsubFrame);
+      unsubscribe(newConn, "a-sub");
 
       newConn.disconnect();
    }
 
    @Test
    public void testHeaderContentType() throws Exception {
-      connV11.connect(defUser, defPass);
-      ClientStompFrame frame = connV11.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-type", "application/xml");
-      frame.setBody("Hello World 1!");
-
-      connV11.sendFrame(frame);
+      conn.connect(defUser, defPass);
+      send(conn, getQueuePrefix() + getQueueName(), "application/xml", "Hello World 1!");
 
       //subscribe
       StompClientConnection newConn = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
       newConn.connect(defUser, defPass);
 
-      ClientStompFrame subFrame = newConn.createFrame("SUBSCRIBE");
-      subFrame.addHeader("id", "a-sub");
-      subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-      subFrame.addHeader("ack", "auto");
+      subscribe(newConn, "a-sub");
 
-      newConn.sendFrame(subFrame);
+      ClientStompFrame frame = newConn.receiveFrame();
 
-      frame = newConn.receiveFrame();
-
-      System.out.println("received " + frame);
+      IntegrationTestLogger.LOGGER.info("received " + frame);
 
-      assertEquals("MESSAGE", frame.getCommand());
+      assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
 
-      assertEquals("application/xml", frame.getHeader("content-type"));
+      assertEquals("application/xml", frame.getHeader(Stomp.Headers.CONTENT_TYPE));
 
       //unsub
-      ClientStompFrame unsubFrame = newConn.createFrame("UNSUBSCRIBE");
-      unsubFrame.addHeader("id", "a-sub");
+      unsubscribe(newConn, "a-sub");
 
       newConn.disconnect();
    }
 
    @Test
    public void testHeaderContentLength() throws Exception {
-      connV11.connect(defUser, defPass);
-      ClientStompFrame frame = connV11.createFrame("SEND");
+      conn.connect(defUser, defPass);
 
       String body = "Hello World 1!";
       String cLen = String.valueOf(body.getBytes(StandardCharsets.UTF_8).length);
 
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-type", "application/xml");
-      frame.addHeader("content-length", cLen);
-      frame.setBody(body + "extra");
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SEND)
+                                   .addHeader(Stomp.Headers.Send.DESTINATION, getQueuePrefix() + getQueueName())
+                                   .addHeader(Stomp.Headers.CONTENT_TYPE, "application/xml")
+                                   .addHeader(Stomp.Headers.CONTENT_LENGTH, cLen)
+                                   .setBody(body + "extra");
 
-      connV11.sendFrame(frame);
+      conn.sendFrame(frame);
 
       //subscribe
       StompClientConnection newConn = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
       newConn.connect(defUser, defPass);
 
-      ClientStompFrame subFrame = newConn.createFrame("SUBSCRIBE");
-      subFrame.addHeader("id", "a-sub");
-      subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-      subFrame.addHeader("ack", "auto");
-
-      newConn.sendFrame(subFrame);
+      subscribe(newConn, "a-sub");
 
       frame = newConn.receiveFrame();
 
-      System.out.println("received " + frame);
+      IntegrationTestLogger.LOGGER.info("received " + frame);
 
-      assertEquals("MESSAGE", frame.getCommand());
+      assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
 
-      assertEquals(cLen, frame.getHeader("content-length"));
+      assertEquals(cLen, frame.getHeader(Stomp.Headers.CONTENT_LENGTH));
 
       //unsub
-      ClientStompFrame unsubFrame = newConn.createFrame("UNSUBSCRIBE");
-      unsubFrame.addHeader("id", "a-sub");
+      unsubscribe(newConn, "a-sub");
 
       newConn.disconnect();
    }
 
    @Test
    public void testHeaderEncoding() throws Exception {
-      connV11.connect(defUser, defPass);
-      ClientStompFrame frame = connV11.createFrame("SEND");
+      conn.connect(defUser, defPass);
 
       String body = "Hello World 1!";
       String cLen = String.valueOf(body.getBytes(StandardCharsets.UTF_8).length);
-
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-type", "application/xml");
-      frame.addHeader("content-length", cLen);
       String hKey = "special-header\\\\\\n\\c";
       String hVal = "\\c\\\\\\ngood";
-      frame.addHeader(hKey, hVal);
 
-      System.out.println("key: |" + hKey + "| val: |" + hVal + "|");
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SEND)
+                                   .addHeader(Stomp.Headers.Send.DESTINATION, getQueuePrefix() + getQueueName())
+                                   .addHeader(Stomp.Headers.CONTENT_TYPE, "application/xml")
+                                   .addHeader(Stomp.Headers.CONTENT_LENGTH, cLen)
+                                   .addHeader(hKey, hVal);
+
+      IntegrationTestLogger.LOGGER.info("key: |" + hKey + "| val: |" + hVal + "|");
 
       frame.setBody(body);
 
-      connV11.sendFrame(frame);
+      conn.sendFrame(frame);
 
       //subscribe
       StompClientConnection newConn = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
       newConn.connect(defUser, defPass);
 
-      ClientStompFrame subFrame = newConn.createFrame("SUBSCRIBE");
-      subFrame.addHeader("id", "a-sub");
-      subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-      subFrame.addHeader("ack", "auto");
-
-      newConn.sendFrame(subFrame);
+      subscribe(newConn, "a-sub");
 
       frame = newConn.receiveFrame();
 
-      System.out.println("received " + frame);
+      IntegrationTestLogger.LOGGER.info("received " + frame);
 
-      assertEquals("MESSAGE", frame.getCommand());
+      assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
 
       String value = frame.getHeader("special-header" + "\\" + "\n" + ":");
 
       assertEquals(":" + "\\" + "\n" + "good", value);
 
       //unsub
-      ClientStompFrame unsubFrame = newConn.createFrame("UNSUBSCRIBE");
-      unsubFrame.addHeader("id", "a-sub");
+      unsubscribe(newConn, "a-sub");
 
       newConn.disconnect();
    }
@@ -392,106 +352,96 @@ public class StompV11Test extends StompV11TestBase {
    @Test
    public void testHeartBeat() throws Exception {
       //no heart beat at all if heat-beat absent
-      ClientStompFrame frame = connV11.createFrame("CONNECT");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.CONNECT)
+                                   .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                                   .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                                   .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass);
 
-      ClientStompFrame reply = connV11.sendFrame(frame);
+      ClientStompFrame reply = conn.sendFrame(frame);
 
-      assertEquals("CONNECTED", reply.getCommand());
+      assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
 
       Thread.sleep(5000);
 
-      assertEquals(0, connV11.getFrameQueueSize());
+      assertEquals(0, conn.getFrameQueueSize());
 
-      connV11.disconnect();
+      conn.disconnect();
 
       //default heart beat for (0,0) which is default connection TTL (60000) / default heartBeatToTtlModifier (2.0) = 30000
-      connV11 = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
-      frame = connV11.createFrame("CONNECT");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
-      frame.addHeader("heart-beat", "0,0");
-      frame.addHeader("accept-version", "1.0,1.1");
+      conn = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
+      frame = conn.createFrame(Stomp.Commands.CONNECT)
+                  .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                  .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                  .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass)
+                  .addHeader(Stomp.Headers.Connect.HEART_BEAT, "0,0")
+                  .addHeader(Stomp.Headers.Connect.ACCEPT_VERSION, "1.0,1.1");
 
-      reply = connV11.sendFrame(frame);
+      reply = conn.sendFrame(frame);
 
-      assertEquals("CONNECTED", reply.getCommand());
+      assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
 
-      assertEquals("0,30000", reply.getHeader("heart-beat"));
+      assertEquals("0,30000", reply.getHeader(Stomp.Headers.Connect.HEART_BEAT));
 
       Thread.sleep(5000);
 
-      assertEquals(0, connV11.getFrameQueueSize());
+      assertEquals(0, conn.getFrameQueueSize());
 
-      connV11.disconnect();
+      conn.disconnect();
 
       //heart-beat (1,0), should receive a min client ping accepted by server
-      connV11 = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
-      frame = connV11.createFrame("CONNECT");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
-      frame.addHeader("heart-beat", "1,0");
-      frame.addHeader("accept-version", "1.0,1.1");
+      conn = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
+      frame = conn.createFrame(Stomp.Commands.CONNECT)
+                  .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                  .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                  .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass)
+                  .addHeader(Stomp.Headers.Connect.HEART_BEAT, "1,0")
+                  .addHeader(Stomp.Headers.Connect.ACCEPT_VERSION, "1.0,1.1");
 
-      reply = connV11.sendFrame(frame);
+      reply = conn.sendFrame(frame);
 
-      assertEquals("CONNECTED", reply.getCommand());
+      assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
 
-      assertEquals("0,500", reply.getHeader("heart-beat"));
+      assertEquals("0,500", reply.getHeader(Stomp.Headers.Connect.HEART_BEAT));
 
       Thread.sleep(2000);
 
       //now server side should be disconnected because we didn't send ping for 2 sec
-      frame = connV11.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-type", "text/plain");
-      frame.setBody("Hello World");
-
       //send will fail
       try {
-         connV11.sendFrame(frame);
+         send(conn, getQueuePrefix() + getQueueName(), "text/plain", "Hello World");
          fail("connection should have been destroyed by now");
       } catch (IOException e) {
          //ignore
       }
 
       //heart-beat (1,0), start a ping, then send a message, should be ok.
-      connV11 = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
-      frame = connV11.createFrame("CONNECT");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
-      frame.addHeader("heart-beat", "1,0");
-      frame.addHeader("accept-version", "1.0,1.1");
+      conn = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
+      frame = conn.createFrame(Stomp.Commands.CONNECT)
+                  .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                  .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                  .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass)
+                  .addHeader(Stomp.Headers.Connect.HEART_BEAT, "1,0")
+                  .addHeader(Stomp.Headers.Connect.ACCEPT_VERSION, "1.0,1.1");
 
-      reply = connV11.sendFrame(frame);
+      reply = conn.sendFrame(frame);
 
-      assertEquals("CONNECTED", reply.getCommand());
+      assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
 
-      assertEquals("0,500", reply.getHeader("heart-beat"));
+      assertEquals("0,500", reply.getHeader(Stomp.Headers.Connect.HEART_BEAT));
 
-      System.out.println("========== start pinger!");
+      IntegrationTestLogger.LOGGER.info("========== start pinger!");
 
-      connV11.startPinger(500);
+      conn.startPinger(500);
 
       Thread.sleep(2000);
 
       //now server side should be disconnected because we didn't send ping for 2 sec
-      frame = connV11.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-type", "text/plain");
-      frame.setBody("Hello World");
-
       //send will be ok
-      connV11.sendFrame(frame);
+      send(conn, getQueuePrefix() + getQueueName(), "text/plain", "Hello World");
 
-      connV11.stopPinger();
+      conn.stopPinger();
 
-      connV11.disconnect();
+      conn.disconnect();
 
    }
 
@@ -499,82 +449,72 @@ public class StompV11Test extends StompV11TestBase {
    @Test
    public void testHeartBeat2() throws Exception {
       //heart-beat (1,1)
-      ClientStompFrame frame = connV11.createFrame("CONNECT");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
-      frame.addHeader("heart-beat", "1,1");
-      frame.addHeader("accept-version", "1.0,1.1");
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.CONNECT)
+                                   .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                                   .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                                   .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass)
+                                   .addHeader(Stomp.Headers.Connect.HEART_BEAT, "1,1")
+                                   .addHeader(Stomp.Headers.Connect.ACCEPT_VERSION, "1.0,1.1");
 
-      ClientStompFrame reply = connV11.sendFrame(frame);
+      ClientStompFrame reply = conn.sendFrame(frame);
 
-      assertEquals("CONNECTED", reply.getCommand());
-      assertEquals("500,500", reply.getHeader("heart-beat"));
+      assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
+      assertEquals("500,500", reply.getHeader(Stomp.Headers.Connect.HEART_BEAT));
 
-      connV11.disconnect();
+      conn.disconnect();
 
       //heart-beat (500,1000)
-      connV11 = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
-      frame = connV11.createFrame("CONNECT");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
-      frame.addHeader("heart-beat", "500,1000");
-      frame.addHeader("accept-version", "1.0,1.1");
+      conn = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
+      frame = conn.createFrame(Stomp.Commands.CONNECT)
+                  .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                  .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                  .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass)
+                  .addHeader(Stomp.Headers.Connect.HEART_BEAT, "500,1000")
+                  .addHeader(Stomp.Headers.Connect.ACCEPT_VERSION, "1.0,1.1");
 
-      reply = connV11.sendFrame(frame);
+      reply = conn.sendFrame(frame);
 
-      assertEquals("CONNECTED", reply.getCommand());
+      assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
 
-      assertEquals("1000,500", reply.getHeader("heart-beat"));
+      assertEquals("1000,500", reply.getHeader(Stomp.Headers.Connect.HEART_BEAT));
 
-      System.out.println("========== start pinger!");
+      IntegrationTestLogger.LOGGER.info("========== start pinger!");
 
-      connV11.startPinger(500);
+      conn.startPinger(500);
 
       Thread.sleep(10000);
 
       //now check the frame size
-      int size = connV11.getServerPingNumber();
+      int size = conn.getServerPingNumber();
 
-      System.out.println("ping received: " + size);
+      IntegrationTestLogger.LOGGER.info("ping received: " + size);
 
       assertTrue(size > 5);
 
       //now server side should be disconnected because we didn't send ping for 2 sec
-      frame = connV11.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-type", "text/plain");
-      frame.setBody("Hello World");
-
       //send will be ok
-      connV11.sendFrame(frame);
+      send(conn, getQueuePrefix() + getQueueName(), "text/plain", "Hello World");
 
-      connV11.disconnect();
+      conn.disconnect();
    }
 
    @Test
    public void testSendWithHeartBeatsAndReceive() throws Exception {
       StompClientConnection newConn = null;
       try {
-         ClientStompFrame frame = connV11.createFrame("CONNECT");
-         frame.addHeader("host", "127.0.0.1");
-         frame.addHeader("login", this.defUser);
-         frame.addHeader("passcode", this.defPass);
-         frame.addHeader("heart-beat", "500,1000");
-         frame.addHeader("accept-version", "1.0,1.1");
+         ClientStompFrame frame = conn.createFrame(Stomp.Commands.CONNECT)
+                                      .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                                      .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                                      .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass)
+                                      .addHeader(Stomp.Headers.Connect.HEART_BEAT, "500,1000")
+                                      .addHeader(Stomp.Headers.Connect.ACCEPT_VERSION, "1.0,1.1");
 
-         connV11.sendFrame(frame);
+         conn.sendFrame(frame);
 
-         connV11.startPinger(500);
-
-         frame = connV11.createFrame("SEND");
-         frame.addHeader("destination", getQueuePrefix() + getQueueName());
-         frame.addHeader("content-type", "text/plain");
+         conn.startPinger(500);
 
          for (int i = 0; i < 10; i++) {
-            frame.setBody("Hello World " + i + "!");
-            connV11.sendFrame(frame);
+            send(conn, getQueuePrefix() + getQueueName(), "text/plain", "Hello World " + i + "!");
             Thread.sleep(500);
          }
 
@@ -582,12 +522,7 @@ public class StompV11Test extends StompV11TestBase {
          newConn = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
          newConn.connect(defUser, defPass);
 
-         ClientStompFrame subFrame = newConn.createFrame("SUBSCRIBE");
-         subFrame.addHeader("id", "a-sub");
-         subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-         subFrame.addHeader("ack", "auto");
-
-         newConn.sendFrame(subFrame);
+         subscribe(newConn, "a-sub");
 
          int cnt = 0;
 
@@ -602,38 +537,32 @@ public class StompV11Test extends StompV11TestBase {
          assertEquals(10, cnt);
 
          // unsub
-         ClientStompFrame unsubFrame = newConn.createFrame("UNSUBSCRIBE");
-         unsubFrame.addHeader("id", "a-sub");
-         newConn.sendFrame(unsubFrame);
+         unsubscribe(newConn, "a-sub");
       } finally {
          if (newConn != null)
             newConn.disconnect();
-         connV11.disconnect();
+         conn.disconnect();
       }
    }
 
    @Test
    public void testSendAndReceiveWithHeartBeats() throws Exception {
-      connV11.connect(defUser, defPass);
-      ClientStompFrame frame = connV11.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-type", "text/plain");
+      conn.connect(defUser, defPass);
 
       for (int i = 0; i < 10; i++) {
-         frame.setBody("Hello World " + i + "!");
-         connV11.sendFrame(frame);
+         send(conn, getQueuePrefix() + getQueueName(), "text/plain", "Hello World " + i + "!");
          Thread.sleep(500);
       }
 
       //subscribe
       StompClientConnection newConn = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
       try {
-         frame = newConn.createFrame("CONNECT");
-         frame.addHeader("host", "127.0.0.1");
-         frame.addHeader("login", this.defUser);
-         frame.addHeader("passcode", this.defPass);
-         frame.addHeader("heart-beat", "500,1000");
-         frame.addHeader("accept-version", "1.0,1.1");
+         ClientStompFrame frame = newConn.createFrame(Stomp.Commands.CONNECT)
+                        .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                        .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                        .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass)
+                        .addHeader(Stomp.Headers.Connect.HEART_BEAT, "500,1000")
+                        .addHeader(Stomp.Headers.Connect.ACCEPT_VERSION, "1.0,1.1");
 
          newConn.sendFrame(frame);
 
@@ -641,12 +570,7 @@ public class StompV11Test extends StompV11TestBase {
 
          Thread.sleep(500);
 
-         ClientStompFrame subFrame = newConn.createFrame("SUBSCRIBE");
-         subFrame.addHeader("id", "a-sub");
-         subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-         subFrame.addHeader("ack", "auto");
-
-         newConn.sendFrame(subFrame);
+         subscribe(newConn, "a-sub");
 
          int cnt = 0;
 
@@ -661,9 +585,7 @@ public class StompV11Test extends StompV11TestBase {
          assertEquals(10, cnt);
 
          // unsub
-         ClientStompFrame unsubFrame = newConn.createFrame("UNSUBSCRIBE");
-         unsubFrame.addHeader("id", "a-sub");
-         newConn.sendFrame(unsubFrame);
+         unsubscribe(newConn, "a-sub");
       } finally {
          newConn.disconnect();
       }
@@ -673,35 +595,30 @@ public class StompV11Test extends StompV11TestBase {
    public void testSendWithHeartBeatsAndReceiveWithHeartBeats() throws Exception {
       StompClientConnection newConn = null;
       try {
-         ClientStompFrame frame = connV11.createFrame("CONNECT");
-         frame.addHeader("host", "127.0.0.1");
-         frame.addHeader("login", this.defUser);
-         frame.addHeader("passcode", this.defPass);
-         frame.addHeader("heart-beat", "500,1000");
-         frame.addHeader("accept-version", "1.0,1.1");
+         ClientStompFrame frame = conn.createFrame(Stomp.Commands.CONNECT)
+                                      .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                                      .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                                      .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass)
+                                      .addHeader(Stomp.Headers.Connect.HEART_BEAT, "500,1000")
+                                      .addHeader(Stomp.Headers.Connect.ACCEPT_VERSION, "1.0,1.1");
 
-         connV11.sendFrame(frame);
+         conn.sendFrame(frame);
 
-         connV11.startPinger(500);
-
-         frame = connV11.createFrame("SEND");
-         frame.addHeader("destination", getQueuePrefix() + getQueueName());
-         frame.addHeader("content-type", "text/plain");
+         conn.startPinger(500);
 
          for (int i = 0; i < 10; i++) {
-            frame.setBody("Hello World " + i + "!");
-            connV11.sendFrame(frame);
+            send(conn, getQueuePrefix() + getQueueName(), "text/plain", "Hello World " + i + "!");
             Thread.sleep(500);
          }
 
          // subscribe
          newConn = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
-         frame = newConn.createFrame("CONNECT");
-         frame.addHeader("host", "127.0.0.1");
-         frame.addHeader("login", this.defUser);
-         frame.addHeader("passcode", this.defPass);
-         frame.addHeader("heart-beat", "500,1000");
-         frame.addHeader("accept-version", "1.0,1.1");
+         frame = newConn.createFrame(Stomp.Commands.CONNECT)
+                        .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                        .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                        .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass)
+                        .addHeader(Stomp.Headers.Connect.HEART_BEAT, "500,1000")
+                        .addHeader(Stomp.Headers.Connect.ACCEPT_VERSION, "1.0,1.1");
 
          newConn.sendFrame(frame);
 
@@ -709,12 +626,7 @@ public class StompV11Test extends StompV11TestBase {
 
          Thread.sleep(500);
 
-         ClientStompFrame subFrame = newConn.createFrame("SUBSCRIBE");
-         subFrame.addHeader("id", "a-sub");
-         subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-         subFrame.addHeader("ack", "auto");
-
-         newConn.sendFrame(subFrame);
+         subscribe(newConn, "a-sub");
 
          int cnt = 0;
 
@@ -728,13 +640,11 @@ public class StompV11Test extends StompV11TestBase {
          assertEquals(10, cnt);
 
          // unsub
-         ClientStompFrame unsubFrame = newConn.createFrame("UNSUBSCRIBE");
-         unsubFrame.addHeader("id", "a-sub");
-         newConn.sendFrame(unsubFrame);
+         unsubscribe(newConn, "a-sub");
       } finally {
          if (newConn != null)
             newConn.disconnect();
-         connV11.disconnect();
+         conn.disconnect();
       }
    }
 
@@ -748,14 +658,14 @@ public class StompV11Test extends StompV11TestBase {
       StompClientConnection connection = StompClientConnectionFactory.createClientConnection("1.1", "localhost", port);
 
       //no heart beat at all if heat-beat absent
-      frame = connection.createFrame("CONNECT");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
+      frame = connection.createFrame(Stomp.Commands.CONNECT)
+                        .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                        .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                        .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass);
 
       reply = connection.sendFrame(frame);
 
-      assertEquals("CONNECTED", reply.getCommand());
+      assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
 
       Thread.sleep(3000);
 
@@ -772,20 +682,20 @@ public class StompV11Test extends StompV11TestBase {
 
       //no heart beat for (0,0)
       connection = StompClientConnectionFactory.createClientConnection("1.1", "localhost", port);
-      frame = connection.createFrame("CONNECT");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
-      frame.addHeader("heart-beat", "0,0");
-      frame.addHeader("accept-version", "1.0,1.1");
+      frame = connection.createFrame(Stomp.Commands.CONNECT)
+                        .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                        .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                        .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass)
+                        .addHeader(Stomp.Headers.Connect.HEART_BEAT, "0,0")
+                        .addHeader(Stomp.Headers.Connect.ACCEPT_VERSION, "1.0,1.1");
 
       reply = connection.sendFrame(frame);
 
       IntegrationTestLogger.LOGGER.info("Reply: " + reply);
 
-      assertEquals("CONNECTED", reply.getCommand());
+      assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
 
-      assertEquals("0,500", reply.getHeader("heart-beat"));
+      assertEquals("0,500", reply.getHeader(Stomp.Headers.Connect.HEART_BEAT));
 
       Thread.sleep(3000);
 
@@ -802,30 +712,25 @@ public class StompV11Test extends StompV11TestBase {
 
       //heart-beat (1,0), should receive a min client ping accepted by server
       connection = StompClientConnectionFactory.createClientConnection("1.1", "localhost", port);
-      frame = connection.createFrame("CONNECT");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
-      frame.addHeader("heart-beat", "1,0");
-      frame.addHeader("accept-version", "1.0,1.1");
+      frame = connection.createFrame(Stomp.Commands.CONNECT)
+                        .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                        .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                        .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass)
+                        .addHeader(Stomp.Headers.Connect.HEART_BEAT, "1,0")
+                        .addHeader(Stomp.Headers.Connect.ACCEPT_VERSION, "1.0,1.1");
 
       reply = connection.sendFrame(frame);
 
-      assertEquals("CONNECTED", reply.getCommand());
+      assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
 
-      assertEquals("0,2500", reply.getHeader("heart-beat"));
+      assertEquals("0,2500", reply.getHeader(Stomp.Headers.Connect.HEART_BEAT));
 
       Thread.sleep(7000);
 
       //now server side should be disconnected because we didn't send ping for 2 sec
-      frame = connection.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-type", "text/plain");
-      frame.setBody("Hello World");
-
       //send will fail
       try {
-         connection.sendFrame(frame);
+         send(connection, getQueuePrefix() + getQueueName(), "text/plain", "Hello World");
          fail("connection should have been destroyed by now");
       } catch (IOException e) {
          //ignore
@@ -833,33 +738,28 @@ public class StompV11Test extends StompV11TestBase {
 
       //heart-beat (1,0), start a ping, then send a message, should be ok.
       connection = StompClientConnectionFactory.createClientConnection("1.1", "localhost", port);
-      frame = connection.createFrame("CONNECT");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
-      frame.addHeader("heart-beat", "1,0");
-      frame.addHeader("accept-version", "1.0,1.1");
+      frame = connection.createFrame(Stomp.Commands.CONNECT)
+                        .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                        .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                        .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass)
+                        .addHeader(Stomp.Headers.Connect.HEART_BEAT, "1,0")
+                        .addHeader(Stomp.Headers.Connect.ACCEPT_VERSION, "1.0,1.1");
 
       reply = connection.sendFrame(frame);
 
-      assertEquals("CONNECTED", reply.getCommand());
+      assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
 
-      assertEquals("0,2500", reply.getHeader("heart-beat"));
+      assertEquals("0,2500", reply.getHeader(Stomp.Headers.Connect.HEART_BEAT));
 
-      System.out.println("========== start pinger!");
+      IntegrationTestLogger.LOGGER.info("========== start pinger!");
 
       connection.startPinger(2500);
 
       Thread.sleep(7000);
 
       //now server side should be disconnected because we didn't send ping for 2 sec
-      frame = connection.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-type", "text/plain");
-      frame.setBody("Hello World");
-
       //send will be ok
-      connection.sendFrame(frame);
+      send(connection, getQueuePrefix() + getQueueName(), "text/plain", "Hello World");
 
       connection.stopPinger();
 
@@ -867,30 +767,25 @@ public class StompV11Test extends StompV11TestBase {
 
       //heart-beat (20000,0), should receive a max client ping accepted by server
       connection = StompClientConnectionFactory.createClientConnection("1.1", "localhost", port);
-      frame = connection.createFrame("CONNECT");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
-      frame.addHeader("heart-beat", "20000,0");
-      frame.addHeader("accept-version", "1.0,1.1");
+      frame = connection.createFrame(Stomp.Commands.CONNECT)
+                        .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                        .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                        .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass)
+                        .addHeader(Stomp.Headers.Connect.HEART_BEAT, "20000,0")
+                        .addHeader(Stomp.Headers.Connect.ACCEPT_VERSION, "1.0,1.1");
 
       reply = connection.sendFrame(frame);
 
-      assertEquals("CONNECTED", reply.getCommand());
+      assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
 
-      assertEquals("0,5000", reply.getHeader("heart-beat"));
+      assertEquals("0,5000", reply.getHeader(Stomp.Headers.Connect.HEART_BEAT));
 
       Thread.sleep(12000);
 
       //now server side should be disconnected because we didn't send ping for 2 sec
-      frame = connection.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-type", "text/plain");
-      frame.setBody("Hello World");
-
       //send will fail
       try {
-         connection.sendFrame(frame);
+         send(connection, getQueuePrefix() + getQueueName(), "text/plain", "Hello World");
          fail("connection should have been destroyed by now");
       } catch (IOException e) {
          //ignore
@@ -907,18 +802,18 @@ public class StompV11Test extends StompV11TestBase {
       server.getActiveMQServer().getRemotingService().createAcceptor("test", "tcp://127.0.0.1:" + port + "?heartBeatToConnectionTtlModifier=1").start();
 
       connection = StompClientConnectionFactory.createClientConnection("1.1", "localhost", port);
-      frame = connection.createFrame("CONNECT");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
-      frame.addHeader("heart-beat", "5000,0");
-      frame.addHeader("accept-version", "1.0,1.1");
+      frame = connection.createFrame(Stomp.Commands.CONNECT)
+                        .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                        .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                        .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass)
+                        .addHeader(Stomp.Headers.Connect.HEART_BEAT, "5000,0")
+                        .addHeader(Stomp.Headers.Connect.ACCEPT_VERSION, "1.0,1.1");
 
       reply = connection.sendFrame(frame);
 
-      assertEquals("CONNECTED", reply.getCommand());
+      assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
 
-      assertEquals("0,5000", reply.getHeader("heart-beat"));
+      assertEquals("0,5000", reply.getHeader(Stomp.Headers.Connect.HEART_BEAT));
 
       Thread.sleep(6000);
 
@@ -933,18 +828,18 @@ public class StompV11Test extends StompV11TestBase {
       server.getActiveMQServer().getRemotingService().createAcceptor("test", "tcp://127.0.0.1:" + port + "?heartBeatToConnectionTtlModifier=1.5").start();
 
       connection = StompClientConnectionFactory.createClientConnection("1.1", "localhost", port);
-      frame = connection.createFrame("CONNECT");
-      frame.addHeader("host", "127.0.0.1");
-      frame.addHeader("login", this.defUser);
-      frame.addHeader("passcode", this.defPass);
-      frame.addHeader("heart-beat", "5000,0");
-      frame.addHeader("accept-version", "1.0,1.1");
+      frame = connection.createFrame(Stomp.Commands.CONNECT)
+                        .addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1")
+                        .addHeader(Stomp.Headers.Connect.LOGIN, this.defUser)
+                        .addHeader(Stomp.Headers.Connect.PASSCODE, this.defPass)
+                        .addHeader(Stomp.Headers.Connect.HEART_BEAT, "5000,0")
+                        .addHeader(Stomp.Headers.Connect.ACCEPT_VERSION, "1.0,1.1");
 
       reply = connection.sendFrame(frame);
 
-      assertEquals("CONNECTED", reply.getCommand());
+      assertEquals(Stomp.Responses.CONNECTED, reply.getCommand());
 
-      assertEquals("0,5000", reply.getHeader("heart-beat"));
+      assertEquals("0,5000", reply.getHeader(Stomp.Headers.Connect.HEART_BEAT));
 
       Thread.sleep(6000);
 
@@ -953,21 +848,21 @@ public class StompV11Test extends StompV11TestBase {
 
    @Test
    public void testNack() throws Exception {
-      connV11.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      subscribe(connV11, "sub1", "client");
+      subscribe(conn, "sub1", Stomp.Headers.Subscribe.AckModeValues.CLIENT);
 
-      sendMessage(getName());
+      sendJmsMessage(getName());
 
-      ClientStompFrame frame = connV11.receiveFrame();
+      ClientStompFrame frame = conn.receiveFrame();
 
-      String messageID = frame.getHeader("message-id");
+      String messageID = frame.getHeader(Stomp.Headers.Message.MESSAGE_ID);
 
-      nack(connV11, "sub1", messageID);
+      nack(conn, "sub1", messageID);
 
-      unsubscribe(connV11, "sub1");
+      unsubscribe(conn, "sub1");
 
-      connV11.disconnect();
+      conn.disconnect();
 
       //Nack makes the message be dropped.
       MessageConsumer consumer = session.createConsumer(queue);
@@ -977,25 +872,25 @@ public class StompV11Test extends StompV11TestBase {
 
    @Test
    public void testNackWithWrongSubId() throws Exception {
-      connV11.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      subscribe(connV11, "sub1", "client");
+      subscribe(conn, "sub1", Stomp.Headers.Subscribe.AckModeValues.CLIENT);
 
-      sendMessage(getName());
+      sendJmsMessage(getName());
 
-      ClientStompFrame frame = connV11.receiveFrame();
+      ClientStompFrame frame = conn.receiveFrame();
 
-      String messageID = frame.getHeader("message-id");
+      String messageID = frame.getHeader(Stomp.Headers.Message.MESSAGE_ID);
 
-      nack(connV11, "sub2", messageID);
+      nack(conn, "sub2", messageID);
 
-      ClientStompFrame error = connV11.receiveFrame();
+      ClientStompFrame error = conn.receiveFrame();
 
-      System.out.println("Receiver error: " + error);
+      IntegrationTestLogger.LOGGER.info("Receiver error: " + error);
 
-      unsubscribe(connV11, "sub1");
+      unsubscribe(conn, "sub1");
 
-      connV11.disconnect();
+      conn.disconnect();
 
       //message should be still there
       MessageConsumer consumer = session.createConsumer(queue);
@@ -1005,25 +900,25 @@ public class StompV11Test extends StompV11TestBase {
 
    @Test
    public void testNackWithWrongMessageId() throws Exception {
-      connV11.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      subscribe(connV11, "sub1", "client");
+      subscribe(conn, "sub1", Stomp.Headers.Subscribe.AckModeValues.CLIENT);
 
-      sendMessage(getName());
+      sendJmsMessage(getName());
 
-      ClientStompFrame frame = connV11.receiveFrame();
+      ClientStompFrame frame = conn.receiveFrame();
 
-      frame.getHeader("message-id");
+      frame.getHeader(Stomp.Headers.Message.MESSAGE_ID);
 
-      nack(connV11, "sub2", "someother");
+      nack(conn, "sub2", "someother");
 
-      ClientStompFrame error = connV11.receiveFrame();
+      ClientStompFrame error = conn.receiveFrame();
 
-      System.out.println("Receiver error: " + error);
+      IntegrationTestLogger.LOGGER.info("Receiver error: " + error);
 
-      unsubscribe(connV11, "sub1");
+      unsubscribe(conn, "sub1");
 
-      connV11.disconnect();
+      conn.disconnect();
 
       //message should still there
       MessageConsumer consumer = session.createConsumer(queue);
@@ -1033,21 +928,21 @@ public class StompV11Test extends StompV11TestBase {
 
    @Test
    public void testAck() throws Exception {
-      connV11.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      subscribe(connV11, "sub1", "client");
+      subscribe(conn, "sub1", Stomp.Headers.Subscribe.AckModeValues.CLIENT);
 
-      sendMessage(getName());
+      sendJmsMessage(getName());
 
-      ClientStompFrame frame = connV11.receiveFrame();
+      ClientStompFrame frame = conn.receiveFrame();
 
-      String messageID = frame.getHeader("message-id");
+      String messageID = frame.getHeader(Stomp.Headers.Message.MESSAGE_ID);
 
-      ack(connV11, "sub1", messageID, null);
+      ack(conn, "sub1", messageID, null);
 
-      unsubscribe(connV11, "sub1");
+      unsubscribe(conn, "sub1");
 
-      connV11.disconnect();
+      conn.disconnect();
 
       //Nack makes the message be dropped.
       MessageConsumer consumer = session.createConsumer(queue);
@@ -1057,25 +952,25 @@ public class StompV11Test extends StompV11TestBase {
 
    @Test
    public void testAckWithWrongSubId() throws Exception {
-      connV11.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      subscribe(connV11, "sub1", "client");
+      subscribe(conn, "sub1", Stomp.Headers.Subscribe.AckModeValues.CLIENT);
 
-      sendMessage(getName());
+      sendJmsMessage(getName());
 
-      ClientStompFrame frame = connV11.receiveFrame();
+      ClientStompFrame frame = conn.receiveFrame();
 
-      String messageID = frame.getHeader("message-id");
+      String messageID = frame.getHeader(Stomp.Headers.Message.MESSAGE_ID);
 
-      ack(connV11, "sub2", messageID, null);
+      ack(conn, "sub2", messageID, null);
 
-      ClientStompFrame error = connV11.receiveFrame();
+      ClientStompFrame error = conn.receiveFrame();
 
-      System.out.println("Receiver error: " + error);
+      IntegrationTestLogger.LOGGER.info("Receiver error: " + error);
 
-      unsubscribe(connV11, "sub1");
+      unsubscribe(conn, "sub1");
 
-      connV11.disconnect();
+      conn.disconnect();
 
       //message should be still there
       MessageConsumer consumer = session.createConsumer(queue);
@@ -1085,25 +980,25 @@ public class StompV11Test extends StompV11TestBase {
 
    @Test
    public void testAckWithWrongMessageId() throws Exception {
-      connV11.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      subscribe(connV11, "sub1", "client");
+      subscribe(conn, "sub1", Stomp.Headers.Subscribe.AckModeValues.CLIENT);
 
-      sendMessage(getName());
+      sendJmsMessage(getName());
 
-      ClientStompFrame frame = connV11.receiveFrame();
+      ClientStompFrame frame = conn.receiveFrame();
 
-      frame.getHeader("message-id");
+      frame.getHeader(Stomp.Headers.Message.MESSAGE_ID);
 
-      ack(connV11, "sub2", "someother", null);
+      ack(conn, "sub2", "someother", null);
 
-      ClientStompFrame error = connV11.receiveFrame();
+      ClientStompFrame error = conn.receiveFrame();
 
-      System.out.println("Receiver error: " + error);
+      IntegrationTestLogger.LOGGER.info("Receiver error: " + error);
 
-      unsubscribe(connV11, "sub1");
+      unsubscribe(conn, "sub1");
 
-      connV11.disconnect();
+      conn.disconnect();
 
       //message should still there
       MessageConsumer consumer = session.createConsumer(queue);
@@ -1113,33 +1008,33 @@ public class StompV11Test extends StompV11TestBase {
 
    @Test
    public void testErrorWithReceipt() throws Exception {
-      connV11.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      subscribe(connV11, "sub1", "client");
+      subscribe(conn, "sub1", Stomp.Headers.Subscribe.AckModeValues.CLIENT);
 
-      sendMessage(getName());
+      sendJmsMessage(getName());
 
-      ClientStompFrame frame = connV11.receiveFrame();
+      ClientStompFrame frame = conn.receiveFrame();
 
-      String messageID = frame.getHeader("message-id");
+      String messageID = frame.getHeader(Stomp.Headers.Message.MESSAGE_ID);
 
-      ClientStompFrame ackFrame = connV11.createFrame("ACK");
       //give it a wrong sub id
-      ackFrame.addHeader("subscription", "sub2");
-      ackFrame.addHeader("message-id", messageID);
-      ackFrame.addHeader("receipt", "answer-me");
+      ClientStompFrame ackFrame = conn.createFrame(Stomp.Commands.ACK)
+                                      .addHeader(Stomp.Headers.Ack.SUBSCRIPTION, "sub2")
+                                      .addHeader(Stomp.Headers.Message.MESSAGE_ID, messageID)
+                                      .addHeader(Stomp.Headers.RECEIPT_REQUESTED, "answer-me");
 
-      ClientStompFrame error = connV11.sendFrame(ackFrame);
+      ClientStompFrame error = conn.sendFrame(ackFrame);
 
-      System.out.println("Receiver error: " + error);
+      IntegrationTestLogger.LOGGER.info("Receiver error: " + error);
 
-      assertEquals("ERROR", error.getCommand());
+      assertEquals(Stomp.Responses.ERROR, error.getCommand());
 
-      assertEquals("answer-me", error.getHeader("receipt-id"));
+      assertEquals("answer-me", error.getHeader(Stomp.Headers.Response.RECEIPT_ID));
 
-      unsubscribe(connV11, "sub1");
+      unsubscribe(conn, "sub1");
 
-      connV11.disconnect();
+      conn.disconnect();
 
       //message should still there
       MessageConsumer consumer = session.createConsumer(queue);
@@ -1149,33 +1044,33 @@ public class StompV11Test extends StompV11TestBase {
 
    @Test
    public void testErrorWithReceipt2() throws Exception {
-      connV11.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      subscribe(connV11, "sub1", "client");
+      subscribe(conn, "sub1", Stomp.Headers.Subscribe.AckModeValues.CLIENT);
 
-      sendMessage(getName());
+      sendJmsMessage(getName());
 
-      ClientStompFrame frame = connV11.receiveFrame();
+      ClientStompFrame frame = conn.receiveFrame();
 
-      String messageID = frame.getHeader("message-id");
+      String messageID = frame.getHeader(Stomp.Headers.Message.MESSAGE_ID);
 
-      ClientStompFrame ackFrame = connV11.createFrame("ACK");
       //give it a wrong sub id
-      ackFrame.addHeader("subscription", "sub1");
-      ackFrame.addHeader("message-id", String.valueOf(Long.valueOf(messageID) + 1));
-      ackFrame.addHeader("receipt", "answer-me");
+      ClientStompFrame ackFrame = conn.createFrame(Stomp.Commands.ACK)
+                                      .addHeader(Stomp.Headers.Ack.SUBSCRIPTION, "sub1")
+                                      .addHeader(Stomp.Headers.Message.MESSAGE_ID, String.valueOf(Long.valueOf(messageID) + 1))
+                                      .addHeader(Stomp.Headers.RECEIPT_REQUESTED, "answer-me");
 
-      ClientStompFrame error = connV11.sendFrame(ackFrame);
+      ClientStompFrame error = conn.sendFrame(ackFrame);
 
-      System.out.println("Receiver error: " + error);
+      IntegrationTestLogger.LOGGER.info("Receiver error: " + error);
 
-      assertEquals("ERROR", error.getCommand());
+      assertEquals(Stomp.Responses.ERROR, error.getCommand());
 
-      assertEquals("answer-me", error.getHeader("receipt-id"));
+      assertEquals("answer-me", error.getHeader(Stomp.Headers.Response.RECEIPT_ID));
 
-      unsubscribe(connV11, "sub1");
+      unsubscribe(conn, "sub1");
 
-      connV11.disconnect();
+      conn.disconnect();
 
       //message should still there
       MessageConsumer consumer = session.createConsumer(queue);
@@ -1185,29 +1080,29 @@ public class StompV11Test extends StompV11TestBase {
 
    @Test
    public void testAckModeClient() throws Exception {
-      connV11.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      subscribe(connV11, "sub1", "client");
+      subscribe(conn, "sub1", Stomp.Headers.Subscribe.AckModeValues.CLIENT);
 
       int num = 50;
       //send a bunch of messages
       for (int i = 0; i < num; i++) {
-         this.sendMessage("client-ack" + i);
+         this.sendJmsMessage("client-ack" + i);
       }
 
       ClientStompFrame frame = null;
 
       for (int i = 0; i < num; i++) {
-         frame = connV11.receiveFrame();
+         frame = conn.receiveFrame();
          assertNotNull(frame);
       }
 
       //ack the last
-      this.ack(connV11, "sub1", frame);
+      this.ack(conn, "sub1", frame);
 
-      unsubscribe(connV11, "sub1");
+      unsubscribe(conn, "sub1");
 
-      connV11.disconnect();
+      conn.disconnect();
 
       //no messages can be received.
       MessageConsumer consumer = session.createConsumer(queue);
@@ -1217,31 +1112,31 @@ public class StompV11Test extends StompV11TestBase {
 
    @Test
    public void testAckModeClient2() throws Exception {
-      connV11.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      subscribe(connV11, "sub1", "client");
+      subscribe(conn, "sub1", Stomp.Headers.Subscribe.AckModeValues.CLIENT);
 
       int num = 50;
       //send a bunch of messages
       for (int i = 0; i < num; i++) {
-         this.sendMessage("client-ack" + i);
+         this.sendJmsMessage("client-ack" + i);
       }
 
       ClientStompFrame frame = null;
 
       for (int i = 0; i < num; i++) {
-         frame = connV11.receiveFrame();
+         frame = conn.receiveFrame();
          assertNotNull(frame);
 
          //ack the 49th
          if (i == num - 2) {
-            this.ack(connV11, "sub1", frame);
+            this.ack(conn, "sub1", frame);
          }
       }
 
-      unsubscribe(connV11, "sub1");
+      unsubscribe(conn, "sub1");
 
-      connV11.disconnect();
+      conn.disconnect();
 
       //no messages can be received.
       MessageConsumer consumer = session.createConsumer(queue);
@@ -1253,26 +1148,26 @@ public class StompV11Test extends StompV11TestBase {
 
    @Test
    public void testAckModeAuto() throws Exception {
-      connV11.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      subscribe(connV11, "sub1", "auto");
+      subscribe(conn, "sub1", Stomp.Headers.Subscribe.AckModeValues.AUTO);
 
       int num = 50;
       //send a bunch of messages
       for (int i = 0; i < num; i++) {
-         this.sendMessage("auto-ack" + i);
+         this.sendJmsMessage("auto-ack" + i);
       }
 
       ClientStompFrame frame = null;
 
       for (int i = 0; i < num; i++) {
-         frame = connV11.receiveFrame();
+         frame = conn.receiveFrame();
          assertNotNull(frame);
       }
 
-      unsubscribe(connV11, "sub1");
+      unsubscribe(conn, "sub1");
 
-      connV11.disconnect();
+      conn.disconnect();
 
       //no messages can be received.
       MessageConsumer consumer = session.createConsumer(queue);
@@ -1282,32 +1177,32 @@ public class StompV11Test extends StompV11TestBase {
 
    @Test
    public void testAckModeClientIndividual() throws Exception {
-      connV11.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      subscribe(connV11, "sub1", "client-individual");
+      subscribe(conn, "sub1", "client-individual");
 
       int num = 50;
       //send a bunch of messages
       for (int i = 0; i < num; i++) {
-         this.sendMessage("client-individual-ack" + i);
+         this.sendJmsMessage("client-individual-ack" + i);
       }
 
       ClientStompFrame frame = null;
 
       for (int i = 0; i < num; i++) {
-         frame = connV11.receiveFrame();
+         frame = conn.receiveFrame();
          assertNotNull(frame);
 
-         System.out.println(i + " == received: " + frame);
+         IntegrationTestLogger.LOGGER.info(i + " == received: " + frame);
          //ack on even numbers
          if (i % 2 == 0) {
-            this.ack(connV11, "sub1", frame);
+            this.ack(conn, "sub1", frame);
          }
       }
 
-      unsubscribe(connV11, "sub1");
+      unsubscribe(conn, "sub1");
 
-      connV11.disconnect();
+      conn.disconnect();
 
       //no messages can be received.
       MessageConsumer consumer = session.createConsumer(queue);
@@ -1316,7 +1211,7 @@ public class StompV11Test extends StompV11TestBase {
       for (int i = 0; i < num / 2; i++) {
          message = (TextMessage) consumer.receive(1000);
          Assert.assertNotNull(message);
-         System.out.println("Legal: " + message.getText());
+         IntegrationTestLogger.LOGGER.info("Legal: " + message.getText());
       }
 
       message = (TextMessage) consumer.receive(1000);
@@ -1326,64 +1221,55 @@ public class StompV11Test extends StompV11TestBase {
 
    @Test
    public void testTwoSubscribers() throws Exception {
-      connV11.connect(defUser, defPass, CLIENT_ID);
+      conn.connect(defUser, defPass, CLIENT_ID);
 
-      this.subscribeTopic(connV11, "sub1", "auto", null);
+      this.subscribeTopic(conn, "sub1", Stomp.Headers.Subscribe.AckModeValues.AUTO, null);
 
       StompClientConnection newConn = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
       newConn.connect(defUser, defPass, "myclientid2");
 
-      this.subscribeTopic(newConn, "sub2", "auto", null);
-
-      ClientStompFrame frame = connV11.createFrame("SEND");
-      frame.addHeader("destination", getTopicPrefix() + getTopicName());
-
-      frame.setBody("Hello World");
+      this.subscribeTopic(newConn, "sub2", Stomp.Headers.Subscribe.AckModeValues.AUTO, null);
 
-      connV11.sendFrame(frame);
+      send(conn, getTopicPrefix() + getTopicName(), null, "Hello World");
 
       // receive message from socket
-      frame = connV11.receiveFrame(1000);
+      ClientStompFrame frame = conn.receiveFrame(1000);
 
-      System.out.println("received frame : " + frame);
+      IntegrationTestLogger.LOGGER.info("received frame : " + frame);
       assertEquals("Hello World", frame.getBody());
-      assertEquals("sub1", frame.getHeader("subscription"));
+      assertEquals("sub1", frame.getHeader(Stomp.Headers.Message.SUBSCRIPTION));
 
       frame = newConn.receiveFrame(1000);
 
-      System.out.println("received 2 frame : " + frame);
+      IntegrationTestLogger.LOGGER.info("received 2 frame : " + frame);
       assertEquals("Hello World", frame.getBody());
-      assertEquals("sub2", frame.getHeader("subscription"));
+      assertEquals("sub2", frame.getHeader(Stomp.Headers.Message.SUBSCRIPTION));
 
       // remove suscription
-      this.unsubscribe(connV11, "sub1", true);
+      this.unsubscribe(conn, "sub1", true);
       this.unsubscribe(newConn, "sub2", true);
 
-      connV11.disconnect();
+      conn.disconnect();
       newConn.disconnect();
    }
 
    @Test
    public void testSendAndReceiveOnDifferentConnections() throws Exception {
-      connV11.connect(defUser, defPass);
-
-      ClientStompFrame sendFrame = connV11.createFrame("SEND");
-      sendFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-      sendFrame.setBody("Hello World");
+      conn.connect(defUser, defPass);
 
-      connV11.sendFrame(sendFrame);
+      send(conn, getQueuePrefix() + getQueueName(), null, "Hello World");
 
       StompClientConnection connV11_2 = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
       connV11_2.connect(defUser, defPass);
 
-      this.subscribe(connV11_2, "sub1", "auto");
+      this.subscribe(connV11_2, "sub1", Stomp.Headers.Subscribe.AckModeValues.AUTO);
 
       ClientStompFrame frame = connV11_2.receiveFrame(2000);
 
-      assertEquals("MESSAGE", frame.getCommand());
+      assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
       assertEquals("Hello World", frame.getBody());
 
-      connV11.disconnect();
+      conn.disconnect();
       connV11_2.disconnect();
    }
 
@@ -1391,79 +1277,81 @@ public class StompV11Test extends StompV11TestBase {
 
    @Test
    public void testBeginSameTransactionTwice() throws Exception {
-      connV11.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      beginTransaction(connV11, "tx1");
+      beginTransaction(conn, "tx1");
 
-      beginTransaction(connV11, "tx1");
+      beginTransaction(conn, "tx1");
 
-      ClientStompFrame f = connV11.receiveFrame();
-      Assert.assertTrue(f.getCommand().equals("ERROR"));
+      ClientStompFrame f = conn.receiveFrame();
+      Assert.assertTrue(f.getCommand().equals(Stomp.Responses.ERROR));
    }
 
    @Test
    public void testBodyWithUTF8() throws Exception {
-      connV11.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      this.subscribe(connV11, getName(), "auto");
+      this.subscribe(conn, getName(), Stomp.Headers.Subscribe.AckModeValues.AUTO);
 
       String text = "A" + "\u00ea" + "\u00f1" + "\u00fc" + "C";
-      System.out.println(text);
-      sendMessage(text);
+      IntegrationTestLogger.LOGGER.info(text);
+      sendJmsMessage(text);
 
-      ClientStompFrame frame = connV11.receiveFrame();
-      System.out.println(frame);
-      Assert.assertTrue(frame.getCommand().equals("MESSAGE"));
-      Assert.assertNotNull(frame.getHeader("destination"));
+      ClientStompFrame frame = conn.receiveFrame();
+      IntegrationTestLogger.LOGGER.info(frame);
+      Assert.assertTrue(frame.getCommand().equals(Stomp.Responses.MESSAGE));
+      Assert.assertNotNull(frame.getHeader(Stomp.Headers.Message.DESTINATION));
       Assert.assertTrue(frame.getBody().equals(text));
 
-      connV11.disconnect();
+      conn.disconnect();
    }
 
    @Test
    public void testClientAckNotPartOfTransaction() throws Exception {
-      connV11.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      this.subscribe(connV11, getName(), "client");
+      this.subscribe(conn, getName(), Stomp.Headers.Subscribe.AckModeValues.CLIENT);
 
-      sendMessage(getName());
+      sendJmsMessage(getName());
 
-      ClientStompFrame frame = connV11.receiveFrame();
+      ClientStompFrame frame = conn.receiveFrame();
 
-      Assert.assertTrue(frame.getCommand().equals("MESSAGE"));
-      Assert.assertNotNull(frame.getHeader("destination"));
+      Assert.assertTrue(frame.getCommand().equals(Stomp.Responses.MESSAGE));
+      Assert.assertNotNull(frame.getHeader(Stomp.Headers.Message.DESTINATION));
       Assert.assertTrue(frame.getBody().equals(getName()));
-      Assert.assertNotNull(frame.getHeader("message-id"));
+      Assert.assertNotNull(frame.getHeader(Stomp.Headers.Message.MESSAGE_ID));
 
-      String messageID = frame.getHeader("message-id");
+      String messageID = frame.getHeader(Stomp.Headers.Message.MESSAGE_ID);
 
-      beginTransaction(connV11, "tx1");
+      beginTransaction(conn, "tx1");
 
-      this.ack(connV11, getName(), messageID, "tx1");
+      this.ack(conn, getName(), messageID, "tx1");
 
-      abortTransaction(connV11, "tx1");
+      abortTransaction(conn, "tx1");
 
-      frame = connV11.receiveFrame(500);
+      frame = conn.receiveFrame(500);
 
       assertNull(frame);
 
-      this.unsubscribe(connV11, getName());
+      this.unsubscribe(conn, getName());
 
-      connV11.disconnect();
+      conn.disconnect();
    }
 
    @Test
    public void testDisconnectAndError() throws Exception {
-      connV11.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
+
+      this.subscribe(conn, getName(), Stomp.Headers.Subscribe.AckModeValues.CLIENT);
 
-      this.subscribe(connV11, getName(), "client");
+      String uuid = UUID.randomUUID().toString();
 
-      ClientStompFrame frame = connV11.createFrame("DISCONNECT");
-      frame.addHeader("receipt", "1");
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.DISCONNECT)
+                                   .addHeader(Stomp.Headers.RECEIPT_REQUESTED, uuid);
 
-      ClientStompFrame result = connV11.sendFrame(frame);
+      ClientStompFrame result = conn.sendFrame(frame);
 
-      if (result == null || (!"RECEIPT".equals(result.getCommand())) || (!"1".equals(result.getHeader("receipt-id")))) {
+      if (result == null || (!Stomp.Responses.RECEIPT.equals(result.getCommand())) || (!uuid.equals(result.getHeader(Stomp.Headers.Response.RECEIPT_ID)))) {
          fail("Disconnect failed! " + result);
       }
 
@@ -1472,12 +1360,9 @@ public class StompV11Test extends StompV11TestBase {
       Thread thr = new Thread() {
          @Override
          public void run() {
-            ClientStompFrame sendFrame = connV11.createFrame("SEND");
-            sendFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-            sendFrame.setBody("Hello World");
             while (latch.getCount() != 0) {
                try {
-                  connV11.sendFrame(sendFrame);
+                  send(conn, getQueuePrefix() + getQueueName(), null, "Hello World");
                   Thread.sleep(500);
                } catch (InterruptedException e) {
                   //retry
@@ -1490,7 +1375,7 @@ public class StompV11Test extends StompV11TestBase {
                   latch.countDown();
                   break;
                } finally {
-                  connV11.destroy();
+                  conn.destroy();
                }
             }
          }
@@ -1510,66 +1395,68 @@ public class StompV11Test extends StompV11TestBase {
 
    @Test
    public void testDurableSubscriber() throws Exception {
-      connV11.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      this.subscribe(connV11, "sub1", "client", getName());
+      this.subscribe(conn, "sub1", Stomp.Headers.Subscribe.AckModeValues.CLIENT, getName());
 
-      this.subscribe(connV11, "sub1", "client", getName());
+      this.subscribe(conn, "sub1", Stomp.Headers.Subscribe.AckModeValues.CLIENT, getName());
 
-      ClientStompFrame frame = connV11.receiveFrame();
-      Assert.assertTrue(frame.getCommand().equals("ERROR"));
+      ClientStompFrame frame = conn.receiveFrame();
+      Assert.assertTrue(frame.getCommand().equals(Stomp.Responses.ERROR));
 
-      connV11.disconnect();
+      conn.disconnect();
    }
 
    @Test
    public void testDurableSubscriberWithReconnection() throws Exception {
-      connV11.connect(defUser, defPass, CLIENT_ID);
+      conn.connect(defUser, defPass, CLIENT_ID);
+
+      this.subscribeTopic(conn, "sub1", Stomp.Headers.Subscribe.AckModeValues.AUTO, getName());
 
-      this.subscribeTopic(connV11, "sub1", "auto", getName());
+      String uuid = UUID.randomUUID().toString();
 
-      ClientStompFrame frame = connV11.createFrame("DISCONNECT");
-      frame.addHeader("receipt", "1");
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.DISCONNECT)
+                                   .addHeader(Stomp.Headers.RECEIPT_REQUESTED, uuid);
 
-      ClientStompFrame result = connV11.sendFrame(frame);
+      ClientStompFrame result = conn.sendFrame(frame);
 
-      if (result == null || (!"RECEIPT".equals(result.getCommand())) || (!"1".equals(result.getHeader("receipt-id")))) {
+      if (result == null || (!Stomp.Responses.RECEIPT.equals(result.getCommand())) || (!uuid.equals(result.getHeader(Stomp.Headers.Response.RECEIPT_ID)))) {
          fail("Disconnect failed! " + result);
       }
 
       // send the message when the durable subscriber is disconnected
-      sendMessage(getName(), topic);
+      sendJmsMessage(getName(), topic);
 
-      connV11.destroy();
-      connV11 = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
-      connV11.connect(defUser, defPass, CLIENT_ID);
+      conn.destroy();
+      conn = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
+      conn.connect(defUser, defPass, CLIENT_ID);
 
-      this.subscribeTopic(connV11, "sub1", "auto", getName());
+      this.subscribeTopic(conn, "sub1", Stomp.Headers.Subscribe.AckModeValues.AUTO, getName());
 
       // we must have received the message
-      frame = connV11.receiveFrame();
+      frame = conn.receiveFrame();
 
-      Assert.assertTrue(frame.getCommand().equals("MESSAGE"));
-      Assert.assertNotNull(frame.getHeader("destination"));
+      Assert.assertTrue(frame.getCommand().equals(Stomp.Responses.MESSAGE));
+      Assert.assertNotNull(frame.getHeader(Stomp.Headers.Message.DESTINATION));
       Assert.assertEquals(getName(), frame.getBody());
 
-      this.unsubscribe(connV11, "sub1");
+      this.unsubscribe(conn, "sub1");
 
-      connV11.disconnect();
+      conn.disconnect();
    }
 
    @Test
    public void testDurableUnSubscribe() throws Exception {
-      connV11.connect(defUser, defPass, CLIENT_ID);
+      conn.connect(defUser, defPass, CLIENT_ID);
 
-      this.subscribeTopic(connV11, null, "auto", getName());
+      this.subscribeTopic(conn, null, Stomp.Headers.Subscribe.AckModeValues.AUTO, getName());
 
-      connV11.disconnect();
-      connV11.destroy();
-      connV11 = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
-      connV11.connect(defUser, defPass, CLIENT_ID);
+      conn.disconnect();
+      conn.destroy();
+      conn = StompClientConnectionFactory.createClientConnection("1.1", hostname, port);
+      conn.connect(defUser, defPass, CLIENT_ID);
 
-      this.unsubscribe(connV11, getName(), false, true);
+      this.unsubscribe(conn, getName(), null, false, true);
 
       long start = System.currentTimeMillis();
       SimpleString queueName = SimpleString.toSimpleString(CLIENT_ID + "." + getName());
@@ -1579,21 +1466,21 @@ public class StompV11Test extends StompV11TestBase {
 
       assertNull(server.getActiveMQServer().locateQueue(queueName));
 
-      connV11.disconnect();
+      conn.disconnect();
    }
 
    @Test
    public void testJMSXGroupIdCanBeSet() throws Exception {
       MessageConsumer consumer = session.createConsumer(queue);
 
-      connV11.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      ClientStompFrame frame = connV11.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("JMSXGroupID", "TEST");
-      frame.setBody("Hello World");
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SEND)
+                                   .addHeader(Stomp.Headers.Send.DESTINATION, getQueuePrefix() + getQueueName())
+                                   .addHeader("JMSXGroupID", "TEST")
+                                   .setBody("Hello World");
 
-      connV11.sendFrame(frame);
+      conn.sendFrame(frame);
 
       TextMessage message = (TextMessage) consumer.receive(1000);
       Assert.assertNotNull(message);
@@ -1607,64 +1494,64 @@ public class StompV11Test extends StompV11TestBase {
       int ctr = 10;
       String[] data = new String[ctr];
 
-      connV11.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      this.subscribe(connV11, "sub1", "auto");
+      this.subscribe(conn, "sub1", Stomp.Headers.Subscribe.AckModeValues.AUTO);
 
       for (int i = 0; i < ctr; ++i) {
          data[i] = getName() + i;
-         sendMessage(data[i]);
+         sendJmsMessage(data[i]);
       }
 
       ClientStompFrame frame = null;
 
       for (int i = 0; i < ctr; ++i) {
-         frame = connV11.receiveFrame();
+         frame = conn.receiveFrame();
          Assert.assertTrue("Message not in order", frame.getBody().equals(data[i]));
       }
 
       for (int i = 0; i < ctr; ++i) {
          data[i] = getName() + ":second:" + i;
-         sendMessage(data[i]);
+         sendJmsMessage(data[i]);
       }
 
       for (int i = 0; i < ctr; ++i) {
-         frame = connV11.receiveFrame();
+         frame = conn.receiveFrame();
          Assert.assertTrue("Message not in order", frame.getBody().equals(data[i]));
       }
 
-      connV11.disconnect();
+      conn.disconnect();
    }
 
    @Test
    public void testSubscribeWithAutoAckAndSelector() throws Exception {
-      connV11.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      this.subscribe(connV11, "sub1", "auto", null, "foo = 'zzz'");
+      this.subscribe(conn, "sub1", Stomp.Headers.Subscribe.AckModeValues.AUTO, null, "foo = 'zzz'");
 
-      sendMessage("Ignored message", "foo", "1234");
-      sendMessage("Real message", "foo", "zzz");
+      sendJmsMessage("Ignored message", "foo", "1234");
+      sendJmsMessage("Real message", "foo", "zzz");
 
-      ClientStompFrame frame = connV11.receiveFrame();
+      ClientStompFrame frame = conn.receiveFrame();
 
       Assert.assertTrue("Should have received the real message but got: " + frame, frame.getBody().equals("Real message"));
 
-      connV11.disconnect();
+      conn.disconnect();
    }
 
    @Test
    public void testRedeliveryWithClientAck() throws Exception {
-      connV11.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      this.subscribe(connV11, "subId", "client");
+      this.subscribe(conn, "subscriptionId", Stomp.Headers.Subscribe.AckModeValues.CLIENT);
 
-      sendMessage(getName());
+      sendJmsMessage(getName());
 
-      ClientStompFrame frame = connV11.receiveFrame();
+      ClientStompFrame frame = conn.receiveFrame();
 
-      assertTrue(frame.getCommand().equals("MESSAGE"));
+      assertTrue(frame.getCommand().equals(Stomp.Responses.MESSAGE));
 
-      connV11.disconnect();
+      conn.disconnect();
 
       // message should be received since message was not acknowledged
       MessageConsumer consumer = session.createConsumer(queue);
@@ -1677,7 +1564,7 @@ public class StompV11Test extends StompV11TestBase {
    public void testSendManyMessages() throws Exception {
       MessageConsumer consumer = session.createConsumer(queue);
 
-      connV11.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
       int count = 1000;
       final CountDownLatch latch = new CountDownLatch(count);
@@ -1688,30 +1575,22 @@ public class StompV11Test extends StompV11TestBase {
          }
       });
 
-      ClientStompFrame frame = connV11.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.setBody("Hello World");
-
       for (int i = 1; i <= count; i++) {
-         connV11.sendFrame(frame);
+         send(conn, getQueuePrefix() + getQueueName(), null, "Hello World");
       }
 
       assertTrue(latch.await(60, TimeUnit.SECONDS));
 
-      connV11.disconnect();
+      conn.disconnect();
    }
 
    @Test
    public void testSendMessage() throws Exception {
       MessageConsumer consumer = session.createConsumer(queue);
 
-      connV11.connect(defUser, defPass);
-
-      ClientStompFrame frame = connV11.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.setBody("Hello World");
+      conn.connect(defUser, defPass);
 
-      connV11.sendFrame(frame);
+      send(conn, getQueuePrefix() + getQueueName(), null, "Hello World");
 
       TextMessage message = (TextMessage) consumer.receive(1000);
       Assert.assertNotNull(message);
@@ -1730,18 +1609,16 @@ public class StompV11Test extends StompV11TestBase {
    public void testSendMessageWithContentLength() throws Exception {
       MessageConsumer consumer = session.createConsumer(queue);
 
-      connV11.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
       byte[] data = new byte[]{1, 0, 0, 4};
 
-      ClientStompFrame frame = connV11.createFrame("SEND");
-
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.setBody(new String(data, StandardCharsets.UTF_8));
-
-      frame.addHeader("content-length", String.valueOf(data.length));
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SEND)
+                                   .addHeader(Stomp.Headers.Send.DESTINATION, getQueuePrefix() + getQueueName())
+                                   .setBody(new String(data, StandardCharsets.UTF_8))
+                                   .addHeader(Stomp.Headers.CONTENT_LENGTH, String.valueOf(data.length));
 
-      connV11.sendFrame(frame);
+      conn.sendFrame(frame);
 
       BytesMessage message = (BytesMessage) consumer.receive(10000);
       Assert.assertNotNull(message);
@@ -1757,16 +1634,15 @@ public class StompV11Test extends StompV11TestBase {
    public void testSendMessageWithCustomHeadersAndSelector() throws Exception {
       MessageConsumer consumer = session.createConsumer(queue, "foo = 'abc'");
 
-      connV11.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      ClientStompFrame frame = connV11.createFrame("SEND");
-      frame.addHeader("foo", "abc");
-      frame.addHeader("bar", "123");
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SEND)
+                                   .addHeader("foo", "abc")
+                                   .addHeader("bar", "123")
+                                   .addHeader(Stomp.Headers.Send.DESTINATION, getQueuePrefix() + getQueueName())
+                                   .setBody("Hello World");
 
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.setBody("Hello World");
-
-      connV11.sendFrame(frame);
+      conn.sendFrame(frame);
 
       TextMessage message = (TextMessage) consumer.receive(1000);
       Assert.assertNotNull(message);
@@ -1779,14 +1655,13 @@ public class StompV11Test extends StompV11TestBase {
    public void testSendMessageWithLeadingNewLine() throws Exception {
       MessageConsumer consumer = session.createConsumer(queue);
 
-      connV11.connect(defUser, defPass);
-
-      ClientStompFrame frame = connV11.createFrame("SEND");
+      conn.connect(defUser, defPass);
 
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.setBody("Hello World");
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SEND)
+                                   .addHeader(Stomp.Headers.Send.DESTINATION, getQueuePrefix() + getQueueName())
+                                   .setBody("Hello World");
 
-      connV11.sendWickedFrame(frame);
+      conn.sendWickedFrame(frame);
 
       TextMessage message = (TextMessage) consumer.receive(1000);
       Assert.assertNotNull(message);
@@ -1800,24 +1675,17 @@ public class StompV11Test extends StompV11TestBase {
 
       assertNull(consumer.receive(1000));
 
-      connV11.disconnect();
+      conn.disconnect();
    }
 
    @Test
    public void testSendMessageWithReceipt() throws Exception {
       MessageConsumer consumer = session.createConsumer(queue);
 
-      connV11.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
-      ClientStompFrame frame = connV11.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("receipt", "1234");
-      frame.setBody("Hello World");
 
-      frame = connV11.sendFrame(frame);
-
-      assertTrue(frame.getCommand().equals("RECEIPT"));
-      assertEquals("1234", frame.getHeader("receipt-id"));
+      send(conn, getQueuePrefix() + getQueueName(), null, "Hello World", true);
 
       TextMessage message = (TextMessage) consumer.receive(1000);
       Assert.assertNotNull(message);
@@ -1829,28 +1697,27 @@ public class StompV11Test extends StompV11TestBase {
       long tmsg = message.getJMSTimestamp();
       Assert.assertTrue(Math.abs(tnow - tmsg) < 1000);
 
-      connV11.disconnect();
+      conn.disconnect();
    }
 
    @Test
    public void testSendMessageWithStandardHeaders() throws Exception {
       MessageConsumer consumer = session.createConsumer(queue);
 
-      connV11.connect(defUser, defPass);
-
-      ClientStompFrame frame = connV11.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("correlation-id", "c123");
-      frame.addHeader("persistent", "true");
-      frame.addHeader("priority", "3");
-      frame.addHeader("type", "t345");
-      frame.addHeader("JMSXGroupID", "abc");
-      frame.addHeader("foo", "abc");
-      frame.addHeader("bar", "123");
+      conn.connect(defUser, defPass);
 
-      frame.setBody("Hello World");
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SEND)
+                                   .addHeader(Stomp.Headers.Send.DESTINATION, getQueuePrefix() + getQueueName())
+                                   .addHeader(Stomp.Headers.Message.CORRELATION_ID, "c123")
+                                   .addHeader(Stomp.Headers.Message.PERSISTENT, "true")
+                                   .addHeader(Stomp.Headers.Message.PRIORITY, "3")
+                                   .addHeader(Stomp.Headers.Message.TYPE, "t345")
+                                   .addHeader("JMSXGroupID", "abc")
+                                   .addHeader("foo", "abc")
+                                   .addHeader("bar", "123")
+                                   .setBody("Hello World");
 
-      frame = connV11.sendFrame(frame);
+      frame = conn.sendFrame(frame);
 
       TextMessage message = (TextMessage) consumer.receive(1000);
       Assert.assertNotNull(message);
@@ -1864,33 +1731,32 @@ public class StompV11Test extends StompV11TestBase {
 
       Assert.assertEquals("JMSXGroupID", "abc", message.getStringProperty("JMSXGroupID"));
 
-      connV11.disconnect();
+      conn.disconnect();
    }
 
    @Test
    public void testSendMessageWithLongHeaders() throws Exception {
       MessageConsumer consumer = session.createConsumer(queue);
 
-      connV11.connect(defUser, defPass);
+      conn.connect(defUser, defPass);
 
       StringBuffer buffer = new StringBuffer();
       for (int i = 0; i < 2048; i++) {
          buffer.append("a");
       }
 
-      ClientStompFrame frame = connV11.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("cor

<TRUNCATED>

[09/11] activemq-artemis git commit: Stomp refactor + track autocreation for addresses

Posted by jb...@apache.org.
Stomp refactor + track autocreation for addresses


Project: http://git-wip-us.apache.org/repos/asf/activemq-artemis/repo
Commit: http://git-wip-us.apache.org/repos/asf/activemq-artemis/commit/84df373a
Tree: http://git-wip-us.apache.org/repos/asf/activemq-artemis/tree/84df373a
Diff: http://git-wip-us.apache.org/repos/asf/activemq-artemis/diff/84df373a

Branch: refs/heads/ARTEMIS-780
Commit: 84df373add77a74015e1c6af6c2719cc3ad53d3e
Parents: d961852
Author: jbertram <jb...@apache.com>
Authored: Tue Oct 18 19:45:02 2016 +0100
Committer: jbertram <jb...@apache.com>
Committed: Thu Nov 10 20:50:59 2016 -0600

----------------------------------------------------------------------
 .../apache/activemq/cli/test/ArtemisTest.java   |    4 +-
 .../config/ActiveMQDefaultConfiguration.java    |    3 +
 .../artemis/api/core/client/ClientSession.java  |    2 +-
 .../core/client/impl/ClientSessionImpl.java     |    4 +-
 .../core/impl/ActiveMQSessionContext.java       |    4 +-
 .../impl/wireformat/CreateAddressMessage.java   |   14 +
 .../spi/core/remoting/SessionContext.java       |    2 +-
 .../jms/client/ActiveMQMessageProducer.java     |   24 +-
 .../artemis/jms/client/ActiveMQSession.java     |   19 +-
 .../protocol/mqtt/MQTTSubscriptionManager.java  |    2 +-
 .../artemis/core/protocol/stomp/Stomp.java      |   34 +-
 .../core/protocol/stomp/StompConnection.java    |   21 +-
 .../protocol/stomp/StompProtocolManager.java    |   16 +-
 .../stomp/VersionedStompFrameHandler.java       |   14 +-
 .../core/management/impl/QueueControlImpl.java  |    2 +-
 .../journal/AbstractJournalStorageManager.java  |    7 +-
 .../codec/PersistentAddressBindingEncoding.java |   20 +-
 .../artemis/core/postoffice/PostOffice.java     |    7 +-
 .../core/postoffice/impl/PostOfficeImpl.java    |   30 +-
 .../artemis/core/server/ActiveMQServer.java     |   26 +-
 .../artemis/core/server/QueueCreator.java       |   32 -
 .../artemis/core/server/QueueDeleter.java       |   28 -
 .../artemis/core/server/QueueFactory.java       |    2 +-
 .../artemis/core/server/ServerSession.java      |    5 +-
 .../core/server/impl/ActiveMQServerImpl.java    |   57 +-
 .../artemis/core/server/impl/AddressInfo.java   |   12 +
 .../impl/AutoCreatedQueueManagerImpl.java       |   32 +-
 .../artemis/core/server/impl/DivertImpl.java    |    2 +-
 .../server/impl/PostOfficeJournalLoader.java    |    4 +-
 .../artemis/core/server/impl/QueueImpl.java     |    4 +-
 .../core/server/impl/ServerSessionImpl.java     |   25 +-
 .../management/impl/ManagementServiceImpl.java  |    3 +-
 .../core/config/impl/FileConfigurationTest.java |   59 +
 .../vertx/IncomingVertxEventHandler.java        |    2 +-
 .../integration/client/HangConsumerTest.java    |    4 +-
 .../integration/stomp/ConcurrentStompTest.java  |  136 --
 .../tests/integration/stomp/ExtraStompTest.java |  848 ---------
 .../stomp/StompConnectionCleanupTest.java       |   52 +-
 .../integration/stomp/StompOverHttpTest.java    |   78 -
 .../stomp/StompOverWebsocketTest.java           |  151 --
 .../tests/integration/stomp/StompTest.java      | 1569 +++++----------
 .../tests/integration/stomp/StompTestBase.java  |  548 +++---
 .../stomp/StompTestWithInterceptors.java        |  159 ++
 .../stomp/StompTestWithLargeMessages.java       |  438 +++++
 .../stomp/StompTestWithMessageID.java           |   77 +
 .../stomp/StompTestWithSecurity.java            |   28 +-
 .../stomp/util/AbstractClientStompFrame.java    |   77 +-
 .../util/AbstractStompClientConnection.java     |  100 +-
 .../stomp/util/ClientStompFrame.java            |   10 +-
 .../stomp/util/ClientStompFrameV10.java         |   10 +-
 .../stomp/util/ClientStompFrameV11.java         |   22 +-
 .../stomp/util/ClientStompFrameV12.java         |   38 +-
 .../stomp/util/StompClientConnection.java       |    5 +-
 .../stomp/util/StompClientConnectionV10.java    |   43 +-
 .../stomp/util/StompClientConnectionV11.java    |  104 +-
 .../stomp/util/StompClientConnectionV12.java    |   79 +-
 .../stomp/util/StompFrameFactory.java           |    2 +
 .../stomp/util/StompFrameFactoryV10.java        |   11 +-
 .../stomp/util/StompFrameFactoryV11.java        |   26 +-
 .../stomp/util/StompFrameFactoryV12.java        |   36 +-
 .../integration/stomp/v11/ExtraStompTest.java   |  342 +---
 .../integration/stomp/v11/StompV11Test.java     | 1789 +++++++-----------
 .../integration/stomp/v11/StompV11TestBase.java |  167 --
 .../integration/stomp/v12/StompV12Test.java     | 1760 +++++++----------
 .../core/server/impl/fakes/FakePostOffice.java  |    7 +-
 65 files changed, 3450 insertions(+), 5788 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-cli/src/test/java/org/apache/activemq/cli/test/ArtemisTest.java
----------------------------------------------------------------------
diff --git a/artemis-cli/src/test/java/org/apache/activemq/cli/test/ArtemisTest.java b/artemis-cli/src/test/java/org/apache/activemq/cli/test/ArtemisTest.java
index 3d89aa8..cac6229 100644
--- a/artemis-cli/src/test/java/org/apache/activemq/cli/test/ArtemisTest.java
+++ b/artemis-cli/src/test/java/org/apache/activemq/cli/test/ArtemisTest.java
@@ -548,11 +548,11 @@ public class ArtemisTest {
               ClientSessionFactory factory = locator.createSessionFactory();
               ClientSession coreSession = factory.createSession("admin", "admin", false, true, true, false, 0)) {
             for (String str : queues.split(",")) {
-               ClientSession.QueueQuery queryResult = coreSession.queueQuery(SimpleString.toSimpleString("jms.queue." + str));
+               ClientSession.QueueQuery queryResult = coreSession.queueQuery(SimpleString.toSimpleString(str));
                assertTrue("Couldn't find queue " + str, queryResult.isExists());
             }
             for (String str : topics.split(",")) {
-               ClientSession.QueueQuery queryResult = coreSession.queueQuery(SimpleString.toSimpleString("jms.topic." + str));
+               ClientSession.QueueQuery queryResult = coreSession.queueQuery(SimpleString.toSimpleString(str));
                assertTrue("Couldn't find topic " + str, queryResult.isExists());
             }
          }

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-core-client/src/main/java/org/apache/activemq/artemis/api/config/ActiveMQDefaultConfiguration.java
----------------------------------------------------------------------
diff --git a/artemis-core-client/src/main/java/org/apache/activemq/artemis/api/config/ActiveMQDefaultConfiguration.java b/artemis-core-client/src/main/java/org/apache/activemq/artemis/api/config/ActiveMQDefaultConfiguration.java
index 5511ab6..8227e06 100644
--- a/artemis-core-client/src/main/java/org/apache/activemq/artemis/api/config/ActiveMQDefaultConfiguration.java
+++ b/artemis-core-client/src/main/java/org/apache/activemq/artemis/api/config/ActiveMQDefaultConfiguration.java
@@ -1188,8 +1188,11 @@ public final class ActiveMQDefaultConfiguration {
    public static boolean getDefaultDeleteQueueOnNoConsumers() {
       return DEFAULT_DELETE_QUEUE_ON_NO_CONSUMERS;
    }
+<<<<<<< HEAD
 
    public static String getInternalNamingPrefix() {
       return DEFAULT_INTERNAL_NAMING_PREFIX;
    }
+=======
+>>>>>>> af5f1b1... ARTEMIS-782 Added configuration elements for new address model
 }

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-core-client/src/main/java/org/apache/activemq/artemis/api/core/client/ClientSession.java
----------------------------------------------------------------------
diff --git a/artemis-core-client/src/main/java/org/apache/activemq/artemis/api/core/client/ClientSession.java b/artemis-core-client/src/main/java/org/apache/activemq/artemis/api/core/client/ClientSession.java
index fbd33d3..35bc9f9 100644
--- a/artemis-core-client/src/main/java/org/apache/activemq/artemis/api/core/client/ClientSession.java
+++ b/artemis-core-client/src/main/java/org/apache/activemq/artemis/api/core/client/ClientSession.java
@@ -198,7 +198,7 @@ public interface ClientSession extends XAResource, AutoCloseable {
     */
    int getVersion();
 
-   void createAddress(final SimpleString address, final boolean multicast) throws ActiveMQException;
+   void createAddress(final SimpleString address, final boolean multicast, final boolean autoCreated) throws ActiveMQException;
 
    // Queue Operations ----------------------------------------------
 

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/client/impl/ClientSessionImpl.java
----------------------------------------------------------------------
diff --git a/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/client/impl/ClientSessionImpl.java b/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/client/impl/ClientSessionImpl.java
index 2739109..16311b0 100644
--- a/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/client/impl/ClientSessionImpl.java
+++ b/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/client/impl/ClientSessionImpl.java
@@ -279,12 +279,12 @@ public final class ClientSessionImpl implements ClientSessionInternal, FailureLi
    }
 
    @Override
-   public void createAddress(final SimpleString address, final boolean multicast) throws ActiveMQException {
+   public void createAddress(final SimpleString address, final boolean multicast, boolean autoCreated) throws ActiveMQException {
       checkClosed();
 
       startCall();
       try {
-         sessionContext.createAddress(address, multicast);
+         sessionContext.createAddress(address, multicast, autoCreated);
       } finally {
          endCall();
       }

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/protocol/core/impl/ActiveMQSessionContext.java
----------------------------------------------------------------------
diff --git a/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/protocol/core/impl/ActiveMQSessionContext.java b/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/protocol/core/impl/ActiveMQSessionContext.java
index 4e25037..919da19 100644
--- a/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/protocol/core/impl/ActiveMQSessionContext.java
+++ b/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/protocol/core/impl/ActiveMQSessionContext.java
@@ -584,8 +584,8 @@ public class ActiveMQSessionContext extends SessionContext {
    }
 
    @Override
-   public void createAddress(SimpleString address, final boolean multicast) throws ActiveMQException {
-      CreateAddressMessage request = new CreateAddressMessage(address, multicast, true);
+   public void createAddress(SimpleString address, final boolean multicast, final boolean autoCreated) throws ActiveMQException {
+      CreateAddressMessage request = new CreateAddressMessage(address, multicast, autoCreated, true);
       sessionChannel.sendBlocking(request, PacketImpl.NULL_RESPONSE);
    }
 

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/protocol/core/impl/wireformat/CreateAddressMessage.java
----------------------------------------------------------------------
diff --git a/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/protocol/core/impl/wireformat/CreateAddressMessage.java b/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/protocol/core/impl/wireformat/CreateAddressMessage.java
index 484a2ac..10c7ff3 100644
--- a/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/protocol/core/impl/wireformat/CreateAddressMessage.java
+++ b/artemis-core-client/src/main/java/org/apache/activemq/artemis/core/protocol/core/impl/wireformat/CreateAddressMessage.java
@@ -26,15 +26,19 @@ public class CreateAddressMessage extends PacketImpl {
 
    private boolean multicast;
 
+   private boolean autoCreated;
+
    private boolean requiresResponse;
 
    public CreateAddressMessage(final SimpleString address,
                                final boolean multicast,
+                               final boolean autoCreated,
                                final boolean requiresResponse) {
       this();
 
       this.address = address;
       this.multicast = multicast;
+      this.autoCreated = autoCreated;
       this.requiresResponse = requiresResponse;
    }
 
@@ -49,6 +53,7 @@ public class CreateAddressMessage extends PacketImpl {
       StringBuffer buff = new StringBuffer(getParentString());
       buff.append(", address=" + address);
       buff.append(", multicast=" + multicast);
+      buff.append(", autoCreated=" + autoCreated);
       buff.append("]");
       return buff.toString();
    }
@@ -65,6 +70,10 @@ public class CreateAddressMessage extends PacketImpl {
       return requiresResponse;
    }
 
+   public boolean isAutoCreated() {
+      return autoCreated;
+   }
+
    public void setAddress(SimpleString address) {
       this.address = address;
    }
@@ -74,6 +83,7 @@ public class CreateAddressMessage extends PacketImpl {
       buffer.writeSimpleString(address);
       buffer.writeBoolean(multicast);
       buffer.writeBoolean(requiresResponse);
+      buffer.writeBoolean(autoCreated);
    }
 
    @Override
@@ -81,6 +91,7 @@ public class CreateAddressMessage extends PacketImpl {
       address = buffer.readSimpleString();
       multicast = buffer.readBoolean();
       requiresResponse = buffer.readBoolean();
+      autoCreated = buffer.readBoolean();
    }
 
    @Override
@@ -89,6 +100,7 @@ public class CreateAddressMessage extends PacketImpl {
       int result = super.hashCode();
       result = prime * result + ((address == null) ? 0 : address.hashCode());
       result = prime * result + (multicast ? 1231 : 1237);
+      result = prime * result + (autoCreated ? 1231 : 1237);
       result = prime * result + (requiresResponse ? 1231 : 1237);
       return result;
    }
@@ -109,6 +121,8 @@ public class CreateAddressMessage extends PacketImpl {
          return false;
       if (multicast != other.multicast)
          return false;
+      if (autoCreated != other.autoCreated)
+         return false;
       if (requiresResponse != other.requiresResponse)
          return false;
       return true;

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-core-client/src/main/java/org/apache/activemq/artemis/spi/core/remoting/SessionContext.java
----------------------------------------------------------------------
diff --git a/artemis-core-client/src/main/java/org/apache/activemq/artemis/spi/core/remoting/SessionContext.java b/artemis-core-client/src/main/java/org/apache/activemq/artemis/spi/core/remoting/SessionContext.java
index 79d50c1..16e8314 100644
--- a/artemis-core-client/src/main/java/org/apache/activemq/artemis/spi/core/remoting/SessionContext.java
+++ b/artemis-core-client/src/main/java/org/apache/activemq/artemis/spi/core/remoting/SessionContext.java
@@ -166,7 +166,7 @@ public abstract class SessionContext {
 
    public abstract void deleteQueue(SimpleString queueName) throws ActiveMQException;
 
-   public abstract void createAddress(SimpleString address, boolean multicast) throws ActiveMQException;
+   public abstract void createAddress(SimpleString address, boolean multicast, boolean autoCreated) throws ActiveMQException;
 
    public abstract void createQueue(SimpleString address,
                                     SimpleString queueName,

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-jms-client/src/main/java/org/apache/activemq/artemis/jms/client/ActiveMQMessageProducer.java
----------------------------------------------------------------------
diff --git a/artemis-jms-client/src/main/java/org/apache/activemq/artemis/jms/client/ActiveMQMessageProducer.java b/artemis-jms-client/src/main/java/org/apache/activemq/artemis/jms/client/ActiveMQMessageProducer.java
index c552d69..1270c19 100644
--- a/artemis-jms-client/src/main/java/org/apache/activemq/artemis/jms/client/ActiveMQMessageProducer.java
+++ b/artemis-jms-client/src/main/java/org/apache/activemq/artemis/jms/client/ActiveMQMessageProducer.java
@@ -403,19 +403,19 @@ public class ActiveMQMessageProducer implements MessageProducer, QueueSender, To
             try {
                ClientSession.AddressQuery query = clientSession.addressQuery(address);
 
-               if (!query.isExists() && query.isAutoCreateJmsQueues()) {
-                  if (destination.isQueue() && !destination.isTemporary()) {
-                     clientSession.createAddress(address, false);
-                     clientSession.createQueue(address, address, null, true);
-                  } else if (destination.isQueue() && destination.isTemporary()) {
-                     clientSession.createAddress(address, false);
-                     clientSession.createTemporaryQueue(address, address);
-                  } else if (!destination.isQueue() && !destination.isTemporary()) {
-                     clientSession.createAddress(address, true);
-                  } else if (!destination.isQueue() && destination.isTemporary()) {
-                     clientSession.createAddress(address, true);
+               if (!query.isExists()) {
+                  if (destination.isQueue() && query.isAutoCreateJmsQueues()) {
+                     clientSession.createAddress(address, false, true);
+                     if (destination.isTemporary()) {
+                        // TODO is it right to use the address for the queue name here?
+                        clientSession.createTemporaryQueue(address, address);
+                     } else {
+                        clientSession.createQueue(address, address, null, true);
+                     }
+                  } else if (!destination.isQueue() && query.isAutoCreateJmsTopics()) {
+                     clientSession.createAddress(address, true, true);
                   }
-               } else if (!query.isExists() && !query.isAutoCreateJmsQueues()) {
+               } else if (!query.isExists() && ((destination.isQueue() && !query.isAutoCreateJmsQueues()) || (!destination.isQueue() && !query.isAutoCreateJmsTopics()))) {
                   throw new InvalidDestinationException("Destination " + address + " does not exist");
                } else {
                   connection.addKnownDestination(address);

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-jms-client/src/main/java/org/apache/activemq/artemis/jms/client/ActiveMQSession.java
----------------------------------------------------------------------
diff --git a/artemis-jms-client/src/main/java/org/apache/activemq/artemis/jms/client/ActiveMQSession.java b/artemis-jms-client/src/main/java/org/apache/activemq/artemis/jms/client/ActiveMQSession.java
index d554cf8..35bbfa0 100644
--- a/artemis-jms-client/src/main/java/org/apache/activemq/artemis/jms/client/ActiveMQSession.java
+++ b/artemis-jms-client/src/main/java/org/apache/activemq/artemis/jms/client/ActiveMQSession.java
@@ -299,13 +299,12 @@ public class ActiveMQSession implements QueueSession, TopicSession {
          if (jbd != null) {
             ClientSession.AddressQuery response = session.addressQuery(jbd.getSimpleAddress());
 
-            if (jbd.isQueue()) {
-               if (!response.isExists()) {
-                  if (response.isAutoCreateJmsQueues()) {
-                     session.createAddress(jbd.getSimpleAddress(), false);
-                  } else {
-                     throw new InvalidDestinationException("Destination " + jbd.getName() + " does not exist");
-                  }
+            if (!response.isExists() && response.isAutoCreateJmsQueues()) {
+               if (jbd.isQueue()) {
+                  session.createAddress(jbd.getSimpleAddress(), false, true);
+                  session.createQueue(jbd.getSimpleAddress(), jbd.getSimpleAddress(), null, true);
+               } else {
+                  session.createAddress(jbd.getSimpleAddress(), true, true);
                }
 
                if (response.getQueueNames().isEmpty()) {
@@ -660,6 +659,8 @@ public class ActiveMQSession implements QueueSession, TopicSession {
              */
             if (!response.isExists() || !response.getQueueNames().contains(dest.getSimpleAddress())) {
                if (response.isAutoCreateJmsQueues()) {
+                  // TODO create queue here in such a way that it is deleted when consumerCount == 0
+                  // perhaps just relying on the broker to do it is simplest (i.e. deleteOnNoConsumers)
                   session.createQueue(dest.getSimpleAddress(), dest.getSimpleAddress(), true);
                } else {
                   throw new InvalidDestinationException("Destination " + dest.getName() + " does not exist");
@@ -674,7 +675,7 @@ public class ActiveMQSession implements QueueSession, TopicSession {
 
             if (!response.isExists()) {
                if (response.isAutoCreateJmsQueues()) {
-                  session.createAddress(dest.getSimpleAddress(), true);
+                  session.createAddress(dest.getSimpleAddress(), true, true);
                } else {
                   throw new InvalidDestinationException("Topic " + dest.getName() + " does not exist");
                }
@@ -1106,7 +1107,7 @@ public class ActiveMQSession implements QueueSession, TopicSession {
 
       AddressQuery query = session.addressQuery(topic.getSimpleAddress());
 
-      if (!query.isExists() && !query.isAutoCreateJmsQueues()) {
+      if (!query.isExists() && !query.isAutoCreateJmsTopics()) {
          return null;
       } else {
          return topic;

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-protocols/artemis-mqtt-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/mqtt/MQTTSubscriptionManager.java
----------------------------------------------------------------------
diff --git a/artemis-protocols/artemis-mqtt-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/mqtt/MQTTSubscriptionManager.java b/artemis-protocols/artemis-mqtt-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/mqtt/MQTTSubscriptionManager.java
index 1187db0..1c87f29 100644
--- a/artemis-protocols/artemis-mqtt-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/mqtt/MQTTSubscriptionManager.java
+++ b/artemis-protocols/artemis-mqtt-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/mqtt/MQTTSubscriptionManager.java
@@ -93,7 +93,7 @@ public class MQTTSubscriptionManager {
 
       Queue q = session.getServer().locateQueue(queue);
       if (q == null) {
-         q = session.getServerSession().createQueue(new SimpleString(address), queue, managementFilter, false, MQTTUtil.DURABLE_MESSAGES && qos >= 0, -1, false);
+         q = session.getServerSession().createQueue(new SimpleString(address), queue, managementFilter, false, MQTTUtil.DURABLE_MESSAGES && qos >= 0, -1, false, true);
       } else {
          if (q.isDeleteOnNoConsumers()) {
             throw ActiveMQMessageBundle.BUNDLE.invalidQueueConfiguration(q.getAddress(), q.getName(), "deleteOnNoConsumers", false, true);

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/Stomp.java
----------------------------------------------------------------------
diff --git a/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/Stomp.java b/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/Stomp.java
index badcc1a..89c14e7 100644
--- a/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/Stomp.java
+++ b/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/Stomp.java
@@ -18,8 +18,6 @@ package org.apache.activemq.artemis.core.protocol.stomp;
 
 /**
  * The standard verbs and headers used for the <a href="http://stomp.codehaus.org/">STOMP</a> protocol.
- *
- * @version $Revision: 57 $
  */
 public interface Stomp {
 
@@ -27,7 +25,7 @@ public interface Stomp {
 
    String NEWLINE = "\n";
 
-   public interface Commands {
+   interface Commands {
 
       String CONNECT = "CONNECT";
 
@@ -53,7 +51,7 @@ public interface Stomp {
       String STOMP = "STOMP";
    }
 
-   public interface Responses {
+   interface Responses {
 
       String CONNECTED = "CONNECTED";
 
@@ -64,7 +62,7 @@ public interface Stomp {
       String RECEIPT = "RECEIPT";
    }
 
-   public interface Headers {
+   interface Headers {
 
       String SEPARATOR = ":";
 
@@ -78,15 +76,17 @@ public interface Stomp {
 
       String CONTENT_TYPE = "content-type";
 
-      public interface Response {
+      interface Response {
 
          String RECEIPT_ID = "receipt-id";
       }
 
-      public interface Send {
+      interface Send {
 
          String DESTINATION = "destination";
 
+         String DESTINATION_TYPE = "destination-type";
+
          String CORRELATION_ID = "correlation-id";
 
          String REPLY_TO = "reply-to";
@@ -97,10 +97,10 @@ public interface Stomp {
 
          String TYPE = "type";
 
-         Object PERSISTENT = "persistent";
+         String PERSISTENT = "persistent";
       }
 
-      public interface Message {
+      interface Message {
 
          String MESSAGE_ID = "message-id";
 
@@ -129,7 +129,7 @@ public interface Stomp {
          String VALIDATED_USER = "JMSXUserID";
       }
 
-      public interface Subscribe {
+      interface Subscribe {
 
          String DESTINATION = "destination";
 
@@ -144,6 +144,8 @@ public interface Stomp {
 
          String DURABLE_SUBSCRIPTION_NAME = "durable-subscription-name";
 
+         String SUBSCRIPTION_TYPE = "subscription-type";
+
          String NO_LOCAL = "no-local";
 
          public interface AckModeValues {
@@ -156,7 +158,7 @@ public interface Stomp {
          }
       }
 
-      public interface Unsubscribe {
+      interface Unsubscribe {
 
          String DESTINATION = "destination";
 
@@ -168,7 +170,7 @@ public interface Stomp {
          String DURABLE_SUBSCRIPTION_NAME = "durable-subscription-name";
       }
 
-      public interface Connect {
+      interface Connect {
 
          String LOGIN = "login";
 
@@ -182,10 +184,10 @@ public interface Stomp {
          String ACCEPT_VERSION = "accept-version";
          String HOST = "host";
 
-         Object HEART_BEAT = "heart-beat";
+         String HEART_BEAT = "heart-beat";
       }
 
-      public interface Error {
+      interface Error {
 
          String MESSAGE = "message";
 
@@ -193,7 +195,7 @@ public interface Stomp {
          String VERSION = "version";
       }
 
-      public interface Connected {
+      interface Connected {
 
          String SESSION = "session";
 
@@ -207,7 +209,7 @@ public interface Stomp {
          String HEART_BEAT = "heart-beat";
       }
 
-      public interface Ack {
+      interface Ack {
 
          String MESSAGE_ID = "message-id";
 

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/StompConnection.java
----------------------------------------------------------------------
diff --git a/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/StompConnection.java b/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/StompConnection.java
index 74d03d1..b4ae1b5 100644
--- a/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/StompConnection.java
+++ b/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/StompConnection.java
@@ -245,18 +245,20 @@ public final class StompConnection implements RemotingConnection {
    }
 
    public void checkDestination(String destination) throws ActiveMQStompException {
-      autoCreateDestinationIfPossible(destination);
-
       if (!manager.destinationExists(destination)) {
          throw BUNDLE.destinationNotExist(destination).setHandler(frameHandler);
       }
    }
 
-   public void autoCreateDestinationIfPossible(String queue) throws ActiveMQStompException {
-      // TODO: STOMP clients will have to prefix their destination with queue:// or topic:// so we can determine what to do here
+   public void autoCreateDestinationIfPossible(String queue, AddressInfo.RoutingType routingType) throws ActiveMQStompException {
       try {
-         manager.getServer().createOrUpdateAddressInfo(new AddressInfo(SimpleString.toSimpleString(queue)).setRoutingType(AddressInfo.RoutingType.ANYCAST));
-         manager.getServer().createQueue(SimpleString.toSimpleString(queue), SimpleString.toSimpleString(queue), null, true, false);
+         // TODO check here to see if auto-creation is enabled
+         if (routingType == null || routingType.equals(AddressInfo.RoutingType.MULTICAST)) {
+            manager.getServer().createOrUpdateAddressInfo(new AddressInfo(SimpleString.toSimpleString(queue)).setAutoCreated(true));
+         } else {
+            manager.getServer().createOrUpdateAddressInfo(new AddressInfo(SimpleString.toSimpleString(queue)).setRoutingType(AddressInfo.RoutingType.ANYCAST));
+            manager.getServer().createQueue(SimpleString.toSimpleString(queue), SimpleString.toSimpleString(queue), null, null, true, false, true);
+         }
       } catch (ActiveMQQueueExistsException e) {
          // ignore
       } catch (Exception e) {
@@ -616,8 +618,9 @@ public final class StompConnection implements RemotingConnection {
                   String ack,
                   String id,
                   String durableSubscriptionName,
-                  boolean noLocal) throws ActiveMQStompException {
-      autoCreateDestinationIfPossible(destination);
+                  boolean noLocal,
+                  AddressInfo.RoutingType subscriptionType) throws ActiveMQStompException {
+      autoCreateDestinationIfPossible(destination, subscriptionType);
       if (noLocal) {
          String noLocalFilter = CONNECTION_ID_PROP + " <> '" + getID().toString() + "'";
          if (selector == null) {
@@ -642,7 +645,7 @@ public final class StompConnection implements RemotingConnection {
       }
 
       try {
-         manager.createSubscription(this, subscriptionID, durableSubscriptionName, destination, selector, ack, noLocal);
+         manager.subscribe(this, subscriptionID, durableSubscriptionName, destination, selector, ack, noLocal);
       } catch (ActiveMQStompException e) {
          throw e;
       } catch (Exception e) {

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/StompProtocolManager.java
----------------------------------------------------------------------
diff --git a/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/StompProtocolManager.java b/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/StompProtocolManager.java
index 6029b37..0c1f7dd 100644
--- a/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/StompProtocolManager.java
+++ b/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/StompProtocolManager.java
@@ -368,13 +368,13 @@ public class StompProtocolManager extends AbstractProtocolManager<StompFrame, St
    }
    // Inner classes -------------------------------------------------
 
-   public void createSubscription(StompConnection connection,
-                                  String subscriptionID,
-                                  String durableSubscriptionName,
-                                  String destination,
-                                  String selector,
-                                  String ack,
-                                  boolean noLocal) throws Exception {
+   public void subscribe(StompConnection connection,
+                         String subscriptionID,
+                         String durableSubscriptionName,
+                         String destination,
+                         String selector,
+                         String ack,
+                         boolean noLocal) throws Exception {
       StompSession stompSession = getSession(connection);
       stompSession.setNoLocal(noLocal);
       if (stompSession.containsSubscription(subscriptionID)) {
@@ -411,7 +411,7 @@ public class StompProtocolManager extends AbstractProtocolManager<StompFrame, St
    }
 
    public boolean destinationExists(String destination) {
-      return server.getPostOffice().getAddresses().contains(SimpleString.toSimpleString(destination));
+      return server.getPostOffice().getAddressInfo(SimpleString.toSimpleString(destination)) != null;
    }
 
    public ActiveMQServer getServer() {

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/VersionedStompFrameHandler.java
----------------------------------------------------------------------
diff --git a/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/VersionedStompFrameHandler.java b/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/VersionedStompFrameHandler.java
index 003865c..cd3103b 100644
--- a/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/VersionedStompFrameHandler.java
+++ b/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/VersionedStompFrameHandler.java
@@ -28,6 +28,7 @@ import org.apache.activemq.artemis.core.protocol.stomp.v10.StompFrameHandlerV10;
 import org.apache.activemq.artemis.core.protocol.stomp.v11.StompFrameHandlerV11;
 import org.apache.activemq.artemis.core.protocol.stomp.v12.StompFrameHandlerV12;
 import org.apache.activemq.artemis.core.server.ServerMessage;
+import org.apache.activemq.artemis.core.server.impl.AddressInfo;
 import org.apache.activemq.artemis.core.server.impl.ServerMessageImpl;
 import org.apache.activemq.artemis.utils.DataConstants;
 import org.apache.activemq.artemis.utils.ExecutorFactory;
@@ -168,7 +169,10 @@ public abstract class VersionedStompFrameHandler {
       try {
          connection.validate();
          String destination = frame.getHeader(Stomp.Headers.Send.DESTINATION);
-         checkDestination(destination);
+         String destinationType = frame.getHeader(Headers.Send.DESTINATION_TYPE);
+         AddressInfo.RoutingType routingType = destinationType == null ? null : AddressInfo.RoutingType.valueOf(destinationType);
+         connection.autoCreateDestinationIfPossible(destination, routingType);
+         connection.checkDestination(destination);
          String txID = frame.getHeader(Stomp.Headers.TRANSACTION);
 
          long timestamp = System.currentTimeMillis();
@@ -197,10 +201,6 @@ public abstract class VersionedStompFrameHandler {
       return response;
    }
 
-   private void checkDestination(String destination) throws ActiveMQStompException {
-      connection.checkDestination(destination);
-   }
-
    public StompFrame onBegin(StompFrame frame) {
       StompFrame response = null;
       String txID = frame.getHeader(Stomp.Headers.TRANSACTION);
@@ -247,6 +247,8 @@ public abstract class VersionedStompFrameHandler {
       if (durableSubscriptionName == null) {
          durableSubscriptionName = request.getHeader(Stomp.Headers.Subscribe.DURABLE_SUBSCRIPTION_NAME);
       }
+      String subscriptionType = request.getHeader(Headers.Subscribe.SUBSCRIPTION_TYPE);
+      AddressInfo.RoutingType routingType = subscriptionType == null ? null : AddressInfo.RoutingType.valueOf(subscriptionType);
       boolean noLocal = false;
 
       if (request.hasHeader(Stomp.Headers.Subscribe.NO_LOCAL)) {
@@ -254,7 +256,7 @@ public abstract class VersionedStompFrameHandler {
       }
 
       try {
-         connection.subscribe(destination, selector, ack, id, durableSubscriptionName, noLocal);
+         connection.subscribe(destination, selector, ack, id, durableSubscriptionName, noLocal, routingType);
       } catch (ActiveMQStompException e) {
          response = e.getFrame();
       }

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-server/src/main/java/org/apache/activemq/artemis/core/management/impl/QueueControlImpl.java
----------------------------------------------------------------------
diff --git a/artemis-server/src/main/java/org/apache/activemq/artemis/core/management/impl/QueueControlImpl.java b/artemis-server/src/main/java/org/apache/activemq/artemis/core/management/impl/QueueControlImpl.java
index 7a1bb26..c4d25ac 100644
--- a/artemis-server/src/main/java/org/apache/activemq/artemis/core/management/impl/QueueControlImpl.java
+++ b/artemis-server/src/main/java/org/apache/activemq/artemis/core/management/impl/QueueControlImpl.java
@@ -728,7 +728,7 @@ public class QueueControlImpl extends AbstractControl implements QueueControl {
       ByteBuffer buffer = ByteBuffer.allocate(8);
       buffer.putLong(queue.getID());
       message.putBytesProperty(MessageImpl.HDR_ROUTE_TO_IDS, buffer.array());
-      postOffice.route(message, null, true);
+      postOffice.route(message, true);
       return "" + message.getMessageID();
    }
 

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-server/src/main/java/org/apache/activemq/artemis/core/persistence/impl/journal/AbstractJournalStorageManager.java
----------------------------------------------------------------------
diff --git a/artemis-server/src/main/java/org/apache/activemq/artemis/core/persistence/impl/journal/AbstractJournalStorageManager.java b/artemis-server/src/main/java/org/apache/activemq/artemis/core/persistence/impl/journal/AbstractJournalStorageManager.java
index 16ecdf3..b4247ae 100644
--- a/artemis-server/src/main/java/org/apache/activemq/artemis/core/persistence/impl/journal/AbstractJournalStorageManager.java
+++ b/artemis-server/src/main/java/org/apache/activemq/artemis/core/persistence/impl/journal/AbstractJournalStorageManager.java
@@ -1268,7 +1268,11 @@ public abstract class AbstractJournalStorageManager implements StorageManager {
 
    @Override
    public void addAddressBinding(final long tx, final AddressInfo addressInfo) throws Exception {
-      PersistentAddressBindingEncoding bindingEncoding = new PersistentAddressBindingEncoding(addressInfo.getName(), addressInfo.getRoutingType(), addressInfo.getDefaultMaxQueueConsumers());
+      PersistentAddressBindingEncoding bindingEncoding = new PersistentAddressBindingEncoding(addressInfo.getName(),
+                                                                                              addressInfo.getRoutingType(),
+                                                                                              addressInfo.getDefaultMaxQueueConsumers(),
+                                                                                              addressInfo.isDefaultDeleteOnNoConsumers(),
+                                                                                              addressInfo.isAutoCreated());
 
       readLock();
       try {
@@ -1398,7 +1402,6 @@ public abstract class AbstractJournalStorageManager implements StorageManager {
             idGenerator.loadState(record.id, buffer);
          } else if (rec == JournalRecordIds.ADDRESS_BINDING_RECORD) {
             PersistentAddressBindingEncoding bindingEncoding = newAddressBindingEncoding(id, buffer);
-            ActiveMQServerLogger.LOGGER.info("=== Loading: " + bindingEncoding);
             addressBindingInfos.add(bindingEncoding);
          } else if (rec == JournalRecordIds.GROUP_RECORD) {
             GroupingEncoding encoding = newGroupEncoding(id, buffer);

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-server/src/main/java/org/apache/activemq/artemis/core/persistence/impl/journal/codec/PersistentAddressBindingEncoding.java
----------------------------------------------------------------------
diff --git a/artemis-server/src/main/java/org/apache/activemq/artemis/core/persistence/impl/journal/codec/PersistentAddressBindingEncoding.java b/artemis-server/src/main/java/org/apache/activemq/artemis/core/persistence/impl/journal/codec/PersistentAddressBindingEncoding.java
index 3821b34..e47a210 100644
--- a/artemis-server/src/main/java/org/apache/activemq/artemis/core/persistence/impl/journal/codec/PersistentAddressBindingEncoding.java
+++ b/artemis-server/src/main/java/org/apache/activemq/artemis/core/persistence/impl/journal/codec/PersistentAddressBindingEncoding.java
@@ -31,6 +31,10 @@ public class PersistentAddressBindingEncoding implements EncodingSupport, Addres
 
    public int defaultMaxConsumers;
 
+   public boolean defaultDeleteOnNoConsumers;
+
+   public boolean autoCreated;
+
    public AddressInfo.RoutingType routingType;
 
    public PersistentAddressBindingEncoding() {
@@ -45,15 +49,23 @@ public class PersistentAddressBindingEncoding implements EncodingSupport, Addres
          routingType +
          ", defaultMaxConsumers=" +
          defaultMaxConsumers +
+         ", defaultDeleteOnNoConsumers=" +
+         defaultDeleteOnNoConsumers +
+         ", autoCreated=" +
+         autoCreated +
          "]";
    }
 
    public PersistentAddressBindingEncoding(final SimpleString name,
                                            final AddressInfo.RoutingType routingType,
-                                           final int defaultMaxConsumers) {
+                                           final int defaultMaxConsumers,
+                                           final boolean defaultDeleteOnNoConsumers,
+                                           final boolean autoCreated) {
       this.name = name;
       this.routingType = routingType;
       this.defaultMaxConsumers = defaultMaxConsumers;
+      this.defaultDeleteOnNoConsumers = defaultDeleteOnNoConsumers;
+      this.autoCreated = autoCreated;
    }
 
    @Override
@@ -85,6 +97,8 @@ public class PersistentAddressBindingEncoding implements EncodingSupport, Addres
       name = buffer.readSimpleString();
       routingType = AddressInfo.RoutingType.getType(buffer.readByte());
       defaultMaxConsumers = buffer.readInt();
+      defaultDeleteOnNoConsumers = buffer.readBoolean();
+      autoCreated = buffer.readBoolean();
    }
 
    @Override
@@ -92,10 +106,12 @@ public class PersistentAddressBindingEncoding implements EncodingSupport, Addres
       buffer.writeSimpleString(name);
       buffer.writeByte(routingType.getType());
       buffer.writeInt(defaultMaxConsumers);
+      buffer.writeBoolean(defaultDeleteOnNoConsumers);
+      buffer.writeBoolean(autoCreated);
    }
 
    @Override
    public int getEncodeSize() {
-      return SimpleString.sizeofString(name) + DataConstants.SIZE_BYTE + DataConstants.SIZE_INT;
+      return SimpleString.sizeofString(name) + DataConstants.SIZE_BYTE + DataConstants.SIZE_INT + DataConstants.SIZE_BOOLEAN + DataConstants.SIZE_BOOLEAN;
    }
 }

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-server/src/main/java/org/apache/activemq/artemis/core/postoffice/PostOffice.java
----------------------------------------------------------------------
diff --git a/artemis-server/src/main/java/org/apache/activemq/artemis/core/postoffice/PostOffice.java b/artemis-server/src/main/java/org/apache/activemq/artemis/core/postoffice/PostOffice.java
index 7902352..0abd708 100644
--- a/artemis-server/src/main/java/org/apache/activemq/artemis/core/postoffice/PostOffice.java
+++ b/artemis-server/src/main/java/org/apache/activemq/artemis/core/postoffice/PostOffice.java
@@ -24,7 +24,6 @@ import org.apache.activemq.artemis.api.core.SimpleString;
 import org.apache.activemq.artemis.core.server.ActiveMQComponent;
 import org.apache.activemq.artemis.core.server.MessageReference;
 import org.apache.activemq.artemis.core.server.Queue;
-import org.apache.activemq.artemis.core.server.QueueCreator;
 import org.apache.activemq.artemis.core.server.RoutingContext;
 import org.apache.activemq.artemis.core.server.ServerMessage;
 import org.apache.activemq.artemis.core.server.impl.AddressInfo;
@@ -77,26 +76,22 @@ public interface PostOffice extends ActiveMQComponent {
 
    Map<SimpleString, Binding> getAllBindings();
 
-   RoutingStatus route(ServerMessage message, QueueCreator queueCreator, boolean direct) throws Exception;
+   RoutingStatus route(ServerMessage message, boolean direct) throws Exception;
 
    RoutingStatus route(ServerMessage message,
-                       QueueCreator queueCreator,
                        Transaction tx,
                        boolean direct) throws Exception;
 
    RoutingStatus route(ServerMessage message,
-                       QueueCreator queueCreator,
                        Transaction tx,
                        boolean direct,
                        boolean rejectDuplicates) throws Exception;
 
    RoutingStatus route(ServerMessage message,
-                       QueueCreator queueCreator,
                        RoutingContext context,
                        boolean direct) throws Exception;
 
    RoutingStatus route(ServerMessage message,
-                       QueueCreator queueCreator,
                        RoutingContext context,
                        boolean direct,
                        boolean rejectDuplicates) throws Exception;

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-server/src/main/java/org/apache/activemq/artemis/core/postoffice/impl/PostOfficeImpl.java
----------------------------------------------------------------------
diff --git a/artemis-server/src/main/java/org/apache/activemq/artemis/core/postoffice/impl/PostOfficeImpl.java b/artemis-server/src/main/java/org/apache/activemq/artemis/core/postoffice/impl/PostOfficeImpl.java
index 1dba309..135597f 100644
--- a/artemis-server/src/main/java/org/apache/activemq/artemis/core/postoffice/impl/PostOfficeImpl.java
+++ b/artemis-server/src/main/java/org/apache/activemq/artemis/core/postoffice/impl/PostOfficeImpl.java
@@ -63,7 +63,6 @@ import org.apache.activemq.artemis.core.server.ActiveMQServerLogger;
 import org.apache.activemq.artemis.core.server.LargeServerMessage;
 import org.apache.activemq.artemis.core.server.MessageReference;
 import org.apache.activemq.artemis.core.server.Queue;
-import org.apache.activemq.artemis.core.server.QueueCreator;
 import org.apache.activemq.artemis.core.server.QueueFactory;
 import org.apache.activemq.artemis.core.server.RouteContextList;
 import org.apache.activemq.artemis.core.server.RoutingContext;
@@ -441,6 +440,11 @@ public class PostOfficeImpl implements PostOffice, NotificationListener, Binding
 
    @Override
    public AddressInfo removeAddressInfo(SimpleString address) {
+      try {
+         getServer().getManagementService().unregisterAddress(address);
+      } catch (Exception e) {
+         e.printStackTrace();
+      }
       return addressManager.removeAddressInfo(address);
    }
 
@@ -595,39 +599,34 @@ public class PostOfficeImpl implements PostOffice, NotificationListener, Binding
 
    @Override
    public RoutingStatus route(final ServerMessage message,
-                              QueueCreator queueCreator,
                               final boolean direct) throws Exception {
-      return route(message, queueCreator, (Transaction) null, direct);
+      return route(message, (Transaction) null, direct);
    }
 
    @Override
    public RoutingStatus route(final ServerMessage message,
-                              QueueCreator queueCreator,
                               final Transaction tx,
                               final boolean direct) throws Exception {
-      return route(message, queueCreator, new RoutingContextImpl(tx), direct);
+      return route(message, new RoutingContextImpl(tx), direct);
    }
 
    @Override
    public RoutingStatus route(final ServerMessage message,
-                              final QueueCreator queueCreator,
                               final Transaction tx,
                               final boolean direct,
                               final boolean rejectDuplicates) throws Exception {
-      return route(message, queueCreator, new RoutingContextImpl(tx), direct, rejectDuplicates);
+      return route(message, new RoutingContextImpl(tx), direct, rejectDuplicates);
    }
 
    @Override
    public RoutingStatus route(final ServerMessage message,
-                              final QueueCreator queueCreator,
                               final RoutingContext context,
                               final boolean direct) throws Exception {
-      return route(message, queueCreator, context, direct, true);
+      return route(message, context, direct, true);
    }
 
    @Override
    public RoutingStatus route(final ServerMessage message,
-                              final QueueCreator queueCreator,
                               final RoutingContext context,
                               final boolean direct,
                               boolean rejectDuplicates) throws Exception {
@@ -657,14 +656,15 @@ public class PostOfficeImpl implements PostOffice, NotificationListener, Binding
 
       Bindings bindings = addressManager.getBindingsForRoutingAddress(address);
 
+      // TODO auto-create queues here?
       // first check for the auto-queue creation thing
-      if (bindings == null && queueCreator != null) {
+      if (bindings == null) {
          // There is no queue with this address, we will check if it needs to be created
-         if (queueCreator.create(address)) {
+//         if (queueCreator.create(address)) {
             // TODO: this is not working!!!!
             // reassign bindings if it was created
-            bindings = addressManager.getBindingsForRoutingAddress(address);
-         }
+//            bindings = addressManager.getBindingsForRoutingAddress(address);
+//         }
       }
 
       if (bindings != null) {
@@ -704,7 +704,7 @@ public class PostOfficeImpl implements PostOffice, NotificationListener, Binding
 
                message.setAddress(dlaAddress);
 
-               route(message, null, context.getTransaction(), false);
+               route(message, context.getTransaction(), false);
                result = RoutingStatus.NO_BINDINGS_DLA;
             }
          } else {

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/ActiveMQServer.java
----------------------------------------------------------------------
diff --git a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/ActiveMQServer.java b/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/ActiveMQServer.java
index 09f679b..89af2a1 100644
--- a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/ActiveMQServer.java
+++ b/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/ActiveMQServer.java
@@ -233,30 +233,6 @@ public interface ActiveMQServer extends ActiveMQComponent {
    long getUptimeMillis();
 
    /**
-    * This is the queue creator responsible for automatic JMS Queue creations.
-    *
-    * @param queueCreator
-    */
-   void setJMSQueueCreator(QueueCreator queueCreator);
-
-   /**
-    * @see org.apache.activemq.artemis.core.server.ActiveMQServer#setJMSQueueCreator(QueueCreator)
-    */
-   QueueCreator getJMSDestinationCreator();
-
-   /**
-    * This is the queue deleter responsible for automatic JMS Queue deletions.
-    *
-    * @param queueDeleter
-    */
-   void setJMSQueueDeleter(QueueDeleter queueDeleter);
-
-   /**
-    * @see org.apache.activemq.artemis.core.server.ActiveMQServer#setJMSQueueDeleter(QueueDeleter)
-    */
-   QueueDeleter getJMSQueueDeleter();
-
-   /**
     * Returns whether the initial replication synchronization process with the backup server is complete; applicable for
     * either the live or backup server.
     */
@@ -361,7 +337,7 @@ public interface ActiveMQServer extends ActiveMQComponent {
    QueueQueryResult queueQuery(SimpleString name) throws Exception;
 
    Queue deployQueue(SimpleString address,
-                     SimpleString resourceName,
+                     SimpleString queueName,
                      SimpleString filterString,
                      boolean durable,
                      boolean temporary,

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/QueueCreator.java
----------------------------------------------------------------------
diff --git a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/QueueCreator.java b/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/QueueCreator.java
deleted file mode 100644
index f89a2b0..0000000
--- a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/QueueCreator.java
+++ /dev/null
@@ -1,32 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements. See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License. You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package org.apache.activemq.artemis.core.server;
-
-import org.apache.activemq.artemis.api.core.SimpleString;
-
-public interface QueueCreator {
-
-   /**
-    * You should return true if you even tried to create the queue and the queue was already there.
-    * As the callers of this method will use that as an indicator that they should re-route the messages.
-    * *
-    *
-    * @return True if a queue was created.
-    */
-   boolean create(SimpleString address) throws Exception;
-}

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/QueueDeleter.java
----------------------------------------------------------------------
diff --git a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/QueueDeleter.java b/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/QueueDeleter.java
deleted file mode 100644
index d062848..0000000
--- a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/QueueDeleter.java
+++ /dev/null
@@ -1,28 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more
- * contributor license agreements. See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * The ASF licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License. You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package org.apache.activemq.artemis.core.server;
-
-import org.apache.activemq.artemis.api.core.SimpleString;
-
-public interface QueueDeleter {
-
-   /**
-    * @return True if a queue was deleted.
-    */
-   boolean delete(SimpleString queueName) throws Exception;
-}

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/QueueFactory.java
----------------------------------------------------------------------
diff --git a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/QueueFactory.java b/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/QueueFactory.java
index 64e7a5d..2557b73 100644
--- a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/QueueFactory.java
+++ b/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/QueueFactory.java
@@ -29,7 +29,7 @@ import org.apache.activemq.artemis.core.postoffice.PostOffice;
  */
 public interface QueueFactory {
 
-   Queue createQueueWith(final QueueConfig config);
+   Queue createQueueWith(final QueueConfig config) throws Exception;
 
    /**
     * @deprecated Replaced by {@link #createQueueWith}

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/ServerSession.java
----------------------------------------------------------------------
diff --git a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/ServerSession.java b/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/ServerSession.java
index 910eb22..28d283d 100644
--- a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/ServerSession.java
+++ b/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/ServerSession.java
@@ -87,8 +87,6 @@ public interface ServerSession extends SecurityAuth {
 
    void markTXFailed(Throwable e);
 
-   QueueCreator getQueueCreator();
-
    List<Xid> xaGetInDoubtXids();
 
    int xaGetTimeout();
@@ -194,7 +192,8 @@ public interface ServerSession extends SecurityAuth {
                      boolean temporary,
                      boolean durable,
                      Integer maxConsumers,
-                     Boolean deleteOnNoConsumers) throws Exception;
+                     Boolean deleteOnNoConsumers,
+                     final Boolean autoCreated) throws Exception;
 
    void createSharedQueue(SimpleString address,
                           SimpleString name,

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/ActiveMQServerImpl.java
----------------------------------------------------------------------
diff --git a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/ActiveMQServerImpl.java b/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/ActiveMQServerImpl.java
index df00cc1..d119891 100644
--- a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/ActiveMQServerImpl.java
+++ b/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/ActiveMQServerImpl.java
@@ -117,8 +117,6 @@ import org.apache.activemq.artemis.core.server.PostQueueCreationCallback;
 import org.apache.activemq.artemis.core.server.PostQueueDeletionCallback;
 import org.apache.activemq.artemis.core.server.Queue;
 import org.apache.activemq.artemis.core.server.QueueConfig;
-import org.apache.activemq.artemis.core.server.QueueCreator;
-import org.apache.activemq.artemis.core.server.QueueDeleter;
 import org.apache.activemq.artemis.core.server.QueueFactory;
 import org.apache.activemq.artemis.core.server.QueueQueryResult;
 import org.apache.activemq.artemis.core.server.SecuritySettingPlugin;
@@ -269,16 +267,6 @@ public class ActiveMQServerImpl implements ActiveMQServer {
 
    private FileStoreMonitor fileStoreMonitor;
 
-   /**
-    * This will be set by the JMS Queue Manager.
-    */
-   private QueueCreator jmsQueueCreator;
-
-   /**
-    * This will be set by the JMS Queue Manager.
-    */
-   private QueueDeleter jmsQueueDeleter;
-
    private final Map<String, ServerSession> sessions = new ConcurrentHashMap<>();
 
    private final Semaphore activationLock = new Semaphore(1);
@@ -726,26 +714,6 @@ public class ActiveMQServerImpl implements ActiveMQServer {
    }
 
    @Override
-   public QueueCreator getJMSDestinationCreator() {
-      return jmsQueueCreator;
-   }
-
-   @Override
-   public void setJMSQueueCreator(QueueCreator jmsQueueCreator) {
-      this.jmsQueueCreator = jmsQueueCreator;
-   }
-
-   @Override
-   public QueueDeleter getJMSQueueDeleter() {
-      return jmsQueueDeleter;
-   }
-
-   @Override
-   public void setJMSQueueDeleter(QueueDeleter jmsQueueDeleter) {
-      this.jmsQueueDeleter = jmsQueueDeleter;
-   }
-
-   @Override
    public boolean isReplicaSync() {
       if (activation instanceof SharedNothingLiveActivation) {
          ReplicationManager replicationManager = getReplicationManager();
@@ -1288,7 +1256,7 @@ public class ActiveMQServerImpl implements ActiveMQServer {
                                                      SessionCallback callback,
                                                      OperationContext context,
                                                      boolean autoCreateJMSQueues) throws Exception {
-      return new ServerSessionImpl(name, username, password, validatedUser, minLargeMessageSize, autoCommitSends, autoCommitAcks, preAcknowledge, configuration.isPersistDeliveryCountBeforeDelivery(), xa, connection, storageManager, postOffice, resourceManager, securityStore, managementService, this, configuration.getManagementAddress(), defaultAddress == null ? null : new SimpleString(defaultAddress), callback, context, autoCreateJMSQueues ? jmsQueueCreator : null, pagingManager);
+      return new ServerSessionImpl(name, username, password, validatedUser, minLargeMessageSize, autoCommitSends, autoCommitAcks, preAcknowledge, configuration.isPersistDeliveryCountBeforeDelivery(), xa, connection, storageManager, postOffice, resourceManager, securityStore, managementService, this, configuration.getManagementAddress(), defaultAddress == null ? null : new SimpleString(defaultAddress), callback, context, pagingManager);
    }
 
    @Override
@@ -1546,17 +1514,17 @@ public class ActiveMQServerImpl implements ActiveMQServer {
 
    @Override
    public Queue deployQueue(final SimpleString address,
-                            final SimpleString resourceName,
+                            final SimpleString queueName,
                             final SimpleString filterString,
                             final boolean durable,
                             final boolean temporary,
                             final boolean autoCreated) throws Exception {
-      return deployQueue(address, resourceName, filterString, durable, temporary, autoCreated, null, null);
+      return deployQueue(address, queueName, filterString, durable, temporary, autoCreated, null, null);
    }
 
    @Override
    public Queue deployQueue(final SimpleString address,
-                            final SimpleString resourceName,
+                            final SimpleString queueName,
                             final SimpleString filterString,
                             final boolean durable,
                             final boolean temporary,
@@ -1565,9 +1533,9 @@ public class ActiveMQServerImpl implements ActiveMQServer {
                             final Boolean deleteOnNoConsumers) throws Exception {
 
       // TODO: fix logging here as this could be for a topic or queue
-      ActiveMQServerLogger.LOGGER.deployQueue(resourceName);
+      ActiveMQServerLogger.LOGGER.deployQueue(queueName);
 
-      return createQueue(address, resourceName, filterString, null, durable, temporary, true, false, autoCreated, maxConsumers, deleteOnNoConsumers);
+      return createQueue(address, queueName, filterString, null, durable, temporary, true, false, autoCreated, maxConsumers, deleteOnNoConsumers);
    }
 
    @Override
@@ -2068,6 +2036,16 @@ public class ActiveMQServerImpl implements ActiveMQServer {
       // Deploy any predefined queues
       deployQueuesFromConfiguration();
 
+      registerPostQueueDeletionCallback(new PostQueueDeletionCallback() {
+         // TODO delete auto-created addresses when queueCount == 0
+         @Override
+         public void callback(SimpleString address, SimpleString queueName) throws Exception {
+            if (getAddressInfo(address).isAutoCreated() && postOffice.getBindingsForAddress(address).getBindings().size() == 0) {
+               removeAddressInfo(address);
+            }
+         }
+      });
+
       // We need to call this here, this gives any dependent server a chance to deploy its own addresses
       // this needs to be done before clustering is fully activated
       callActivateCallbacks();
@@ -2340,7 +2318,6 @@ public class ActiveMQServerImpl implements ActiveMQServer {
                             final boolean autoCreated,
                             final Integer maxConsumers,
                             final Boolean deleteOnNoConsumers) throws Exception {
-
       final QueueBinding binding = (QueueBinding) postOffice.getBinding(queueName);
       if (binding != null) {
          if (ignoreIfExists) {
@@ -2397,7 +2374,7 @@ public class ActiveMQServerImpl implements ActiveMQServer {
       if (transientQueue) {
          queue.setConsumersRefCount(new TransientQueueManagerImpl(this, queue.getName()));
       } else if (queue.isAutoCreated()) {
-         queue.setConsumersRefCount(new AutoCreatedQueueManagerImpl(this.getJMSQueueDeleter(), queue.getName()));
+         queue.setConsumersRefCount(new AutoCreatedQueueManagerImpl(this, queue.getName()));
       }
 
       final QueueBinding localQueueBinding = new LocalQueueBinding(getAddressInfo(queue.getAddress()), queue, nodeManager.getNodeId());

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/AddressInfo.java
----------------------------------------------------------------------
diff --git a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/AddressInfo.java b/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/AddressInfo.java
index 708aeda..6ad40fa 100644
--- a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/AddressInfo.java
+++ b/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/AddressInfo.java
@@ -29,6 +29,8 @@ public class AddressInfo {
 
    private int defaultMaxQueueConsumers = ActiveMQDefaultConfiguration.getDefaultMaxQueueConsumers();
 
+   private boolean autoCreated = false;
+
    public AddressInfo(SimpleString name) {
       this.name = name;
    }
@@ -67,6 +69,15 @@ public class AddressInfo {
       return this;
    }
 
+   public boolean isAutoCreated() {
+      return autoCreated;
+   }
+
+   public AddressInfo setAutoCreated(boolean autoCreated) {
+      this.autoCreated = autoCreated;
+      return this;
+   }
+
    public SimpleString getName() {
       return name;
    }
@@ -78,6 +89,7 @@ public class AddressInfo {
       buff.append(", routingType=" + routingType);
       buff.append(", defaultMaxQueueConsumers=" + defaultMaxQueueConsumers);
       buff.append(", defaultDeleteOnNoConsumers=" + defaultDeleteOnNoConsumers);
+      buff.append(", autoCreated=" + autoCreated);
       buff.append("]");
       return buff.toString();
    }

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/AutoCreatedQueueManagerImpl.java
----------------------------------------------------------------------
diff --git a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/AutoCreatedQueueManagerImpl.java b/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/AutoCreatedQueueManagerImpl.java
index 535e53b..55fb765 100644
--- a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/AutoCreatedQueueManagerImpl.java
+++ b/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/AutoCreatedQueueManagerImpl.java
@@ -17,34 +17,48 @@
 package org.apache.activemq.artemis.core.server.impl;
 
 import org.apache.activemq.artemis.api.core.SimpleString;
+import org.apache.activemq.artemis.core.server.ActiveMQServer;
 import org.apache.activemq.artemis.core.server.ActiveMQServerLogger;
 import org.apache.activemq.artemis.core.server.AutoCreatedQueueManager;
-import org.apache.activemq.artemis.core.server.QueueDeleter;
+import org.apache.activemq.artemis.core.server.Queue;
+import org.apache.activemq.artemis.core.settings.impl.AddressSettings;
 import org.apache.activemq.artemis.utils.ReferenceCounterUtil;
 
 public class AutoCreatedQueueManagerImpl implements AutoCreatedQueueManager {
 
    private final SimpleString queueName;
 
-   private final QueueDeleter deleter;
+   private final ActiveMQServer server;
 
    private final Runnable runnable = new Runnable() {
       @Override
       public void run() {
-         try {
-            if (deleter != null) {
-               deleter.delete(queueName);
+         // TODO check auto created and deleteOnNoConsumers
+         Queue queue = server.locateQueue(queueName);
+         SimpleString address = queue.getAddress();
+         AddressSettings settings = server.getAddressSettingsRepository().getMatch(address.toString());
+         long consumerCount = queue.getConsumerCount();
+         long messageCount = queue.getMessageCount();
+
+         if (queue.getMessageCount() == 0) {
+            if (ActiveMQServerLogger.LOGGER.isDebugEnabled()) {
+               ActiveMQServerLogger.LOGGER.debug("deleting auto-created queue \"" + queueName + ".\" consumerCount = " + consumerCount + "; messageCount = " + messageCount + "; getAutoDeleteJmsQueues = " + settings.getAutoDeleteJmsQueues());
+            }
+
+            // TODO handle this exception better
+            try {
+               server.destroyQueue(queueName, null, true, false);
+            } catch (Exception e) {
+               e.printStackTrace();
             }
-         } catch (Exception e) {
-            ActiveMQServerLogger.LOGGER.errorRemovingAutoCreatedQueue(e, queueName);
          }
       }
    };
 
    private final ReferenceCounterUtil referenceCounterUtil = new ReferenceCounterUtil(runnable);
 
-   public AutoCreatedQueueManagerImpl(QueueDeleter deleter, SimpleString queueName) {
-      this.deleter = deleter;
+   public AutoCreatedQueueManagerImpl(ActiveMQServer server, SimpleString queueName) {
+      this.server = server;
       this.queueName = queueName;
    }
 

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/DivertImpl.java
----------------------------------------------------------------------
diff --git a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/DivertImpl.java b/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/DivertImpl.java
index e583fc0..5782379 100644
--- a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/DivertImpl.java
+++ b/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/DivertImpl.java
@@ -104,7 +104,7 @@ public class DivertImpl implements Divert {
          copy = message;
       }
 
-      postOffice.route(copy, null, context.getTransaction(), false);
+      postOffice.route(copy, context.getTransaction(), false);
    }
 
    @Override

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/PostOfficeJournalLoader.java
----------------------------------------------------------------------
diff --git a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/PostOfficeJournalLoader.java b/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/PostOfficeJournalLoader.java
index 76fc69b..eb31737 100644
--- a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/PostOfficeJournalLoader.java
+++ b/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/PostOfficeJournalLoader.java
@@ -151,9 +151,7 @@ public class PostOfficeJournalLoader implements JournalLoader {
             .deleteOnNoConsumers(queueBindingInfo.isDeleteOnNoConsumers())
             .maxConsumers(queueBindingInfo.getMaxConsumers());
          final Queue queue = queueFactory.createQueueWith(queueConfigBuilder.build());
-         if (queue.isAutoCreated()) {
-            queue.setConsumersRefCount(new AutoCreatedQueueManagerImpl(((PostOfficeImpl) postOffice).getServer().getJMSQueueDeleter(), queueBindingInfo.getQueueName()));
-         }
+         queue.setConsumersRefCount(new AutoCreatedQueueManagerImpl(((PostOfficeImpl)postOffice).getServer(), queueBindingInfo.getQueueName()));
 
          if (queueBindingInfo.getQueueStatusEncodings() != null) {
             for (QueueStatusEncoding encoding : queueBindingInfo.getQueueStatusEncodings()) {

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/QueueImpl.java
----------------------------------------------------------------------
diff --git a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/QueueImpl.java b/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/QueueImpl.java
index c391b90..7c614ae 100644
--- a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/QueueImpl.java
+++ b/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/QueueImpl.java
@@ -2326,7 +2326,7 @@ public class QueueImpl implements Queue {
          copyMessage.putBytesProperty(MessageImpl.HDR_ROUTE_TO_IDS, buffer.array());
       }
 
-      postOffice.route(copyMessage, null, tx, false, rejectDuplicate);
+      postOffice.route(copyMessage, tx, false, rejectDuplicate);
 
       acknowledge(tx, ref);
    }
@@ -2530,7 +2530,7 @@ public class QueueImpl implements Queue {
 
       copyMessage.setAddress(address);
 
-      postOffice.route(copyMessage, null, tx, false, rejectDuplicate);
+      postOffice.route(copyMessage, tx, false, rejectDuplicate);
 
       acknowledge(tx, ref, reason);
 

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/ServerSessionImpl.java
----------------------------------------------------------------------
diff --git a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/ServerSessionImpl.java b/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/ServerSessionImpl.java
index 3eb5fcf..80fa7b2 100644
--- a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/ServerSessionImpl.java
+++ b/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/impl/ServerSessionImpl.java
@@ -68,7 +68,6 @@ import org.apache.activemq.artemis.core.server.BindingQueryResult;
 import org.apache.activemq.artemis.core.server.LargeServerMessage;
 import org.apache.activemq.artemis.core.server.MessageReference;
 import org.apache.activemq.artemis.core.server.Queue;
-import org.apache.activemq.artemis.core.server.QueueCreator;
 import org.apache.activemq.artemis.core.server.QueueQueryResult;
 import org.apache.activemq.artemis.core.server.RoutingContext;
 import org.apache.activemq.artemis.core.server.ServerConsumer;
@@ -166,8 +165,6 @@ public class ServerSessionImpl implements ServerSession, FailureListener {
 
    private final OperationContext context;
 
-   private QueueCreator queueCreator;
-
    // Session's usage should be by definition single threaded, hence it's not needed to use a concurrentHashMap here
    protected final Map<SimpleString, Pair<UUID, AtomicLong>> targetAddressInfos = new HashMap<>();
 
@@ -202,7 +199,6 @@ public class ServerSessionImpl implements ServerSession, FailureListener {
                             final SimpleString defaultAddress,
                             final SessionCallback callback,
                             final OperationContext context,
-                            final QueueCreator queueCreator,
                             final PagingManager pagingManager) throws Exception {
       this.username = username;
 
@@ -250,8 +246,6 @@ public class ServerSessionImpl implements ServerSession, FailureListener {
       remotingConnection.addFailureListener(this);
       this.context = context;
 
-      this.queueCreator = queueCreator;
-
       if (!xa) {
          tx = newTransaction();
       }
@@ -389,11 +383,6 @@ public class ServerSessionImpl implements ServerSession, FailureListener {
       }
    }
 
-   @Override
-   public QueueCreator getQueueCreator() {
-      return queueCreator;
-   }
-
    protected void securityCheck(SimpleString address, CheckType checkType, SecurityAuth auth) throws Exception {
       if (securityEnabled) {
          securityStore.check(address, checkType, auth);
@@ -499,7 +488,7 @@ public class ServerSessionImpl implements ServerSession, FailureListener {
                             final SimpleString filterString,
                             final boolean temporary,
                             final boolean durable) throws Exception {
-      return createQueue(address, name, filterString, temporary, durable, null, null);
+      return createQueue(address, name, filterString, temporary, durable, null, null, false);
    }
 
    @Override
@@ -509,7 +498,8 @@ public class ServerSessionImpl implements ServerSession, FailureListener {
                             final boolean temporary,
                             final boolean durable,
                             final Integer maxConsumers,
-                            final Boolean deleteOnNoConsumers) throws Exception {
+                            final Boolean deleteOnNoConsumers,
+                            final Boolean autoCreated) throws Exception {
       if (durable) {
          // make sure the user has privileges to create this queue
          securityCheck(address, CheckType.CREATE_DURABLE_QUEUE, this);
@@ -519,7 +509,7 @@ public class ServerSessionImpl implements ServerSession, FailureListener {
 
       server.checkQueueCreationLimit(getUsername());
 
-      Queue queue = server.createQueue(address, name, filterString, SimpleString.toSimpleString(getUsername()), durable, temporary, maxConsumers, deleteOnNoConsumers);
+      Queue queue = server.createQueue(address, name, filterString, SimpleString.toSimpleString(getUsername()), durable, temporary, autoCreated, maxConsumers, deleteOnNoConsumers);
 
       if (temporary) {
          // Temporary queue in core simply means the queue will be deleted if
@@ -1472,7 +1462,6 @@ public class ServerSessionImpl implements ServerSession, FailureListener {
    }
 
    private void installJMSHooks() {
-      this.queueCreator = server.getJMSDestinationCreator();
    }
 
    private Map<SimpleString, Pair<UUID, AtomicLong>> cloneTargetAddresses() {
@@ -1592,11 +1581,7 @@ public class ServerSessionImpl implements ServerSession, FailureListener {
       }
 
       try {
-         if (noAutoCreateQueue) {
-            result = postOffice.route(msg, null, routingContext, direct);
-         } else {
-            result = postOffice.route(msg, queueCreator, routingContext, direct);
-         }
+         result = postOffice.route(msg, routingContext, direct);
 
          Pair<UUID, AtomicLong> value = targetAddressInfos.get(msg.getAddress());
 

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/management/impl/ManagementServiceImpl.java
----------------------------------------------------------------------
diff --git a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/management/impl/ManagementServiceImpl.java b/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/management/impl/ManagementServiceImpl.java
index 636aa82..349d36a 100644
--- a/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/management/impl/ManagementServiceImpl.java
+++ b/artemis-server/src/main/java/org/apache/activemq/artemis/core/server/management/impl/ManagementServiceImpl.java
@@ -464,7 +464,6 @@ public class ManagementServiceImpl implements ManagementService {
    public synchronized void registerInRegistry(final String resourceName, final Object managedResource) {
       unregisterFromRegistry(resourceName);
 
-      ActiveMQServerLogger.LOGGER.info("Registering: " + resourceName);
       registry.put(resourceName, managedResource);
    }
 
@@ -653,7 +652,7 @@ public class ManagementServiceImpl implements ManagementService {
                   notificationMessage.putStringProperty(new SimpleString("foobar"), new SimpleString(notification.getUID()));
                }
 
-               postOffice.route(notificationMessage, null, false);
+               postOffice.route(notificationMessage, false);
             }
          }
       }

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/artemis-server/src/test/java/org/apache/activemq/artemis/core/config/impl/FileConfigurationTest.java
----------------------------------------------------------------------
diff --git a/artemis-server/src/test/java/org/apache/activemq/artemis/core/config/impl/FileConfigurationTest.java b/artemis-server/src/test/java/org/apache/activemq/artemis/core/config/impl/FileConfigurationTest.java
index eb97b17..59f2cdf 100644
--- a/artemis-server/src/test/java/org/apache/activemq/artemis/core/config/impl/FileConfigurationTest.java
+++ b/artemis-server/src/test/java/org/apache/activemq/artemis/core/config/impl/FileConfigurationTest.java
@@ -52,6 +52,9 @@ import org.apache.activemq.artemis.core.settings.impl.SlowConsumerPolicy;
 import org.junit.Assert;
 import org.junit.Test;
 
+import static org.apache.activemq.artemis.core.config.CoreAddressConfiguration.RoutingType.ANYCAST;
+import static org.apache.activemq.artemis.core.config.CoreAddressConfiguration.RoutingType.MULTICAST;
+
 public class FileConfigurationTest extends ConfigurationImplTest {
 
    private final String fullConfigurationName = "ConfigurationTest-full-config.xml";
@@ -419,6 +422,62 @@ public class FileConfigurationTest extends ConfigurationImplTest {
       assertEquals("addr2", queueConfiguration.getAddress());
    }
 
+   private void verifyAddresses() {
+      assertEquals(2, conf.getAddressConfigurations().size());
+
+      // Addr 1
+      CoreAddressConfiguration addressConfiguration = conf.getAddressConfigurations().get(0);
+      assertEquals("addr1", addressConfiguration.getName());
+      assertEquals(ANYCAST, addressConfiguration.getRoutingType());
+      assertEquals(2, addressConfiguration.getQueueConfigurations().size());
+
+      // Addr 1 Queue 1
+      CoreQueueConfiguration queueConfiguration = addressConfiguration.getQueueConfigurations().get(0);
+
+      assertEquals("q1", queueConfiguration.getName());
+      assertFalse(queueConfiguration.isDurable());
+      assertEquals("color='blue'", queueConfiguration.getFilterString());
+      assertEquals(addressConfiguration.getDefaultDeleteOnNoConsumers(), queueConfiguration.getDeleteOnNoConsumers());
+      assertEquals("addr1", queueConfiguration.getAddress());
+      assertEquals(addressConfiguration.getDefaultMaxConsumers(), queueConfiguration.getMaxConsumers());
+
+      // Addr 1 Queue 2
+      queueConfiguration = addressConfiguration.getQueueConfigurations().get(1);
+
+      assertEquals("q2", queueConfiguration.getName());
+      assertTrue(queueConfiguration.isDurable());
+      assertEquals("color='green'", queueConfiguration.getFilterString());
+      assertEquals(new Integer(-1), queueConfiguration.getMaxConsumers());
+      assertFalse(queueConfiguration.getDeleteOnNoConsumers());
+      assertEquals("addr1", queueConfiguration.getAddress());
+
+      // Addr 2
+      addressConfiguration = conf.getAddressConfigurations().get(1);
+      assertEquals("addr2", addressConfiguration.getName());
+      assertEquals(MULTICAST, addressConfiguration.getRoutingType());
+      assertEquals(2, addressConfiguration.getQueueConfigurations().size());
+
+      // Addr 2 Queue 1
+      queueConfiguration = addressConfiguration.getQueueConfigurations().get(0);
+
+      assertEquals("q3", queueConfiguration.getName());
+      assertTrue(queueConfiguration.isDurable());
+      assertEquals("color='red'", queueConfiguration.getFilterString());
+      assertEquals(new Integer(10), queueConfiguration.getMaxConsumers());
+      assertEquals(addressConfiguration.getDefaultDeleteOnNoConsumers(), queueConfiguration.getDeleteOnNoConsumers());
+      assertEquals("addr2", queueConfiguration.getAddress());
+
+      // Addr 2 Queue 2
+      queueConfiguration = addressConfiguration.getQueueConfigurations().get(1);
+
+      assertEquals("q4", queueConfiguration.getName());
+      assertTrue(queueConfiguration.isDurable());
+      assertNull(queueConfiguration.getFilterString());
+      assertEquals(addressConfiguration.getDefaultMaxConsumers(), queueConfiguration.getMaxConsumers());
+      assertTrue(queueConfiguration.getDeleteOnNoConsumers());
+      assertEquals("addr2", queueConfiguration.getAddress());
+   }
+
    @Test
    public void testSecuritySettingPlugin() throws Exception {
       FileConfiguration fc = new FileConfiguration();

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/integration/activemq-vertx-integration/src/main/java/org/apache/activemq/artemis/integration/vertx/IncomingVertxEventHandler.java
----------------------------------------------------------------------
diff --git a/integration/activemq-vertx-integration/src/main/java/org/apache/activemq/artemis/integration/vertx/IncomingVertxEventHandler.java b/integration/activemq-vertx-integration/src/main/java/org/apache/activemq/artemis/integration/vertx/IncomingVertxEventHandler.java
index a5a5015..4d89e6d 100644
--- a/integration/activemq-vertx-integration/src/main/java/org/apache/activemq/artemis/integration/vertx/IncomingVertxEventHandler.java
+++ b/integration/activemq-vertx-integration/src/main/java/org/apache/activemq/artemis/integration/vertx/IncomingVertxEventHandler.java
@@ -154,7 +154,7 @@ class IncomingVertxEventHandler implements ConnectorService {
          manualEncodeVertxMessageBody(msg.getBodyBuffer(), message.body(), type);
 
          try {
-            postOffice.route(msg, null, false);
+            postOffice.route(msg, false);
          } catch (Exception e) {
             ActiveMQVertxLogger.LOGGER.error("failed to route msg " + msg, e);
          }


[07/11] activemq-artemis git commit: Stomp refactor + track autocreation for addresses

Posted by jb...@apache.org.
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTest.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTest.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTest.java
index 90d18ae..91ab5d3 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTest.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTest.java
@@ -42,48 +42,70 @@ import org.apache.activemq.artemis.core.postoffice.impl.LocalQueueBinding;
 import org.apache.activemq.artemis.core.protocol.stomp.Stomp;
 import org.apache.activemq.artemis.core.server.Queue;
 import org.apache.activemq.artemis.core.server.impl.ActiveMQServerImpl;
+import org.apache.activemq.artemis.core.server.impl.AddressInfo;
 import org.apache.activemq.artemis.logs.AssertionLoggerHandler;
 import org.apache.activemq.artemis.tests.integration.IntegrationTestLogger;
 import org.apache.activemq.artemis.tests.integration.mqtt.imported.FuseMQTTClientProvider;
 import org.apache.activemq.artemis.tests.integration.mqtt.imported.MQTTClientProvider;
+import org.apache.activemq.artemis.tests.integration.stomp.util.ClientStompFrame;
+import org.apache.activemq.artemis.tests.integration.stomp.util.StompClientConnection;
+import org.apache.activemq.artemis.tests.integration.stomp.util.StompClientConnectionFactory;
 import org.apache.activemq.artemis.tests.util.Wait;
 import org.apache.activemq.artemis.utils.RandomUtil;
+import org.junit.After;
 import org.junit.Assert;
+import org.junit.Before;
 import org.junit.Test;
 
 public class StompTest extends StompTestBase {
 
    private static final transient IntegrationTestLogger log = IntegrationTestLogger.LOGGER;
+   protected StompClientConnection conn;
+
+   @Override
+   @Before
+   public void setUp() throws Exception {
+      super.setUp();
+      conn = StompClientConnectionFactory.createClientConnection("1.0", hostname, port);
+   }
+
+   @Override
+   @After
+   public void tearDown() throws Exception {
+      try {
+         boolean connected = conn != null && conn.isConnected();
+         log.debug("Connection 1.0 connected: " + connected);
+         if (connected) {
+            conn.disconnect();
+         }
+      } finally {
+         super.tearDown();
+      }
+   }
 
    @Test
    public void testConnectionTTL() throws Exception {
-      int index = 1;
       int port = 61614;
 
       server.getActiveMQServer().getRemotingService().createAcceptor("test", "tcp://127.0.0.1:" + port + "?connectionTtl=1000").start();
-      createBootstrap(index, port);
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(index, frame);
-      frame = receiveFrame(index, 10000);
-
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
+      conn = StompClientConnectionFactory.createClientConnection("1.0", hostname, port);
+      conn.connect("brianm", "wombats");
 
       Thread.sleep(5000);
 
-      assertTrue(receiveFrame(index, 10000).indexOf(Stomp.Responses.ERROR) != -1);
+      ClientStompFrame frame = conn.receiveFrame();
 
-      assertChannelClosed(index);
+      assertEquals(Stomp.Responses.ERROR, frame.getCommand());
+
+      assertFalse(conn.isConnected());
    }
 
    @Test
    public void testSendManyMessages() throws Exception {
-      MessageConsumer consumer = session.createConsumer(queue);
+      conn.connect(defUser, defPass);
 
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-      frame = receiveFrame(10000);
+      MessageConsumer consumer = session.createConsumer(queue);
 
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
       int count = 1000;
       final CountDownLatch latch = new CountDownLatch(count);
       consumer.setMessageListener(new MessageListener() {
@@ -94,11 +116,8 @@ public class StompTest extends StompTestBase {
          }
       });
 
-      frame = "SEND\n" + "destination:" + getQueuePrefix() + getQueueName() + "\n\n" + "Hello World" + Stomp.NULL;
       for (int i = 1; i <= count; i++) {
-         // Thread.sleep(1);
-         // System.out.println(">>> " + i);
-         sendFrame(frame);
+         send(conn, getQueuePrefix() + getQueueName(), null, "Hello World!");
       }
 
       assertTrue(latch.await(60, TimeUnit.SECONDS));
@@ -110,11 +129,7 @@ public class StompTest extends StompTestBase {
       try {
          MessageConsumer consumer = session.createConsumer(queue);
 
-         String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-         sendFrame(frame);
-         frame = receiveFrame(10000);
-
-         Assert.assertTrue(frame.startsWith("CONNECTED"));
+         conn.connect(defUser, defPass);
          int count = 1000;
          final CountDownLatch latch = new CountDownLatch(count);
          consumer.setMessageListener(new MessageListener() {
@@ -125,13 +140,14 @@ public class StompTest extends StompTestBase {
             }
          });
 
-         ((ActiveMQServerImpl) server.getActiveMQServer()).getMonitor().setMaxUsage(0).tick();
+         ((ActiveMQServerImpl) server.getActiveMQServer()).getMonitor()
+                                                          .setMaxUsage(0)
+                                                          .tick();
 
-         frame = "SEND\n" + "destination:" + getQueuePrefix() + getQueueName() + "\n\n" + "Hello World" + Stomp.NULL;
          for (int i = 1; i <= count; i++) {
             // Thread.sleep(1);
-            // System.out.println(">>> " + i);
-            sendFrame(frame);
+            // log.info(">>> " + i);
+            send(conn, getQueuePrefix() + getQueueName(), null, "Hello World!");
          }
 
          // It should encounter the exception on logs
@@ -140,52 +156,44 @@ public class StompTest extends StompTestBase {
          AssertionLoggerHandler.clear();
          AssertionLoggerHandler.stopCapture();
       }
-
    }
 
    @Test
    public void testConnect() throws Exception {
-
-      String connect_frame = "CONNECT\n" + "login: brianm\n" +
-         "passcode: wombats\n" +
-         "request-id: 1\n" +
-         "\n" +
-         Stomp.NULL;
-      sendFrame(connect_frame);
-
-      String f = receiveFrame(10000);
-      Assert.assertTrue(f.startsWith("CONNECTED"));
-      Assert.assertTrue(f.indexOf("response-id:1") >= 0);
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.CONNECT)
+                                   .addHeader(Stomp.Headers.Connect.LOGIN, defUser)
+                                   .addHeader(Stomp.Headers.Connect.PASSCODE, defPass)
+                                   .addHeader(Stomp.Headers.Connect.REQUEST_ID, "1");
+      ClientStompFrame response = conn.sendFrame(frame);
+
+      Assert.assertTrue(response.getCommand()
+                                .equals(Stomp.Responses.CONNECTED));
+      Assert.assertTrue(response.getHeader(Stomp.Headers.Connected.RESPONSE_ID)
+                                .equals("1"));
    }
 
    @Test
    public void testDisconnectAndError() throws Exception {
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.CONNECT)
+                                   .addHeader(Stomp.Headers.Connect.LOGIN, defUser)
+                                   .addHeader(Stomp.Headers.Connect.PASSCODE, defPass)
+                                   .addHeader(Stomp.Headers.Connect.REQUEST_ID, "1");
+      ClientStompFrame response = conn.sendFrame(frame);
 
-      String connectFrame = "CONNECT\n" + "login: brianm\n" +
-         "passcode: wombats\n" +
-         "request-id: 1\n" +
-         "\n" +
-         Stomp.NULL;
-      sendFrame(connectFrame);
+      Assert.assertTrue(response.getCommand()
+                                .equals(Stomp.Responses.CONNECTED));
+      Assert.assertTrue(response.getHeader(Stomp.Headers.Connected.RESPONSE_ID)
+                                .equals("1"));
 
-      String f = receiveFrame(10000);
-      Assert.assertTrue(f.startsWith("CONNECTED"));
-      Assert.assertTrue(f.indexOf("response-id:1") >= 0);
-
-      String disconnectFrame = "DISCONNECT\n\n" + Stomp.NULL;
-      sendFrame(disconnectFrame);
-
-      waitForFrameToTakeEffect();
+      conn.disconnect();
 
       // sending a message will result in an error
-      String frame = "SEND\n" + "destination:" +
-         getQueuePrefix() +
-         getQueueName() +
-         "\n\n" +
-         "Hello World" +
-         Stomp.NULL;
-
-      assertChannelClosed();
+      try {
+         send(conn, getQueuePrefix() + getQueueName(), null, "Hello World!");
+         fail("Should have thrown an exception since connection is disconnected");
+      } catch (Exception e) {
+         // ignore
+      }
    }
 
    @Test
@@ -193,15 +201,9 @@ public class StompTest extends StompTestBase {
 
       MessageConsumer consumer = session.createConsumer(queue);
 
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
+      conn.connect(defUser, defPass);
 
-      frame = "SEND\n" + "destination:" + getQueuePrefix() + getQueueName() + "\n\n" + "Hello World" + Stomp.NULL;
-
-      sendFrame(frame);
+      send(conn, getQueuePrefix() + getQueueName(), null, "Hello World");
 
       TextMessage message = (TextMessage) consumer.receive(1000);
       Assert.assertNotNull(message);
@@ -218,21 +220,16 @@ public class StompTest extends StompTestBase {
 
    @Test
    public void sendSTOMPReceiveMQTT() throws Exception {
-      String address = "myTestAddress";
-
       // Set up MQTT Subscription
       MQTTClientProvider clientProvider = new FuseMQTTClientProvider();
-      clientProvider.connect("tcp://localhost:61616");
-      clientProvider.subscribe(address, 0);
+      clientProvider.connect("tcp://" + hostname + ":" + port);
+      clientProvider.subscribe(getTopicPrefix() + getTopicName(), 0);
 
       String stompPayload = "This is a test message";
 
       // Set up STOMP connection and send STOMP Message
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = "SEND\n" + "destination:" + address + "\n\n" + stompPayload + Stomp.NULL;
-      sendFrame(frame);
+      conn.connect(defUser, defPass);
+      send(conn, getTopicPrefix() + getTopicName(), null, stompPayload);
 
       // Receive MQTT Message
       byte[] mqttPayload = clientProvider.receive(10000);
@@ -244,44 +241,30 @@ public class StompTest extends StompTestBase {
 
    @Test
    public void sendMQTTReceiveSTOMP() throws Exception {
-      String address = "myTestAddress";
       String payload = "This is a test message";
 
-      server.getActiveMQServer().createQueue(new SimpleString(address), new SimpleString(address), null, false, false);
-
       // Set up STOMP subscription
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = "SUBSCRIBE\n" + "destination:" + address + "\n" + "ack:auto\n\n" + Stomp.NULL;
-      sendFrame(frame);
-      receiveFrame(1000);
+      conn.connect(defUser, defPass);
+      subscribe(conn, null, Stomp.Headers.Subscribe.AckModeValues.AUTO);
 
       // Send MQTT Message
       MQTTClientProvider clientProvider = new FuseMQTTClientProvider();
-      clientProvider.connect("tcp://localhost:61616");
-      clientProvider.publish(address, payload.getBytes(), 0);
+      clientProvider.connect("tcp://" + hostname + ":" + port);
+      clientProvider.publish(getQueuePrefix() + getQueueName(), payload.getBytes(), 0);
       clientProvider.disconnect();
 
       // Receive STOMP Message
-      frame = receiveFrame(1000);
-      assertTrue(frame.contains(payload));
+      ClientStompFrame frame = conn.receiveFrame();
+      assertTrue(frame.getBody()
+                      .contains(payload));
 
    }
 
    @Test
    public void testSendMessageToNonExistentQueue() throws Exception {
       String nonExistentQueue = RandomUtil.randomString();
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
-
-      frame = "SEND\n" + "destination:" + getQueuePrefix() + nonExistentQueue + "\n\n" + "Hello World" + Stomp.NULL;
-
-      sendFrame(frame);
-      receiveFrame(1000);
+      conn.connect(defUser, defPass);
+      send(conn, getQueuePrefix() + nonExistentQueue, null, "Hello World", true, AddressInfo.RoutingType.ANYCAST);
 
       MessageConsumer consumer = session.createConsumer(ActiveMQJMSClient.createQueue(nonExistentQueue));
       TextMessage message = (TextMessage) consumer.receive(1000);
@@ -297,29 +280,26 @@ public class StompTest extends StompTestBase {
       Assert.assertTrue(Math.abs(tnow - tmsg) < 1500);
 
       // closing the consumer here should trigger auto-deletion
-      assertNotNull(server.getActiveMQServer().getPostOffice().getBinding(new SimpleString(nonExistentQueue)));
+      assertNotNull(server.getActiveMQServer()
+                          .getPostOffice()
+                          .getBinding(new SimpleString(nonExistentQueue)));
       consumer.close();
-      assertNull(server.getActiveMQServer().getPostOffice().getBinding(new SimpleString(nonExistentQueue)));
+      assertNull(server.getActiveMQServer()
+                       .getPostOffice()
+                       .getBinding(new SimpleString(nonExistentQueue)));
    }
 
    @Test
    public void testSendMessageToNonExistentTopic() throws Exception {
       String nonExistentTopic = RandomUtil.randomString();
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
+      conn.connect(defUser, defPass);
 
       // first send a message to ensure that sending to a non-existent topic won't throw an error
-      frame = "SEND\n" + "destination:" + getTopicPrefix() + nonExistentTopic + "\n\n" + "Hello World" + Stomp.NULL;
-      sendFrame(frame);
-      receiveFrame(1000);
+      send(conn, getTopicPrefix() + nonExistentTopic, null, "Hello World", true);
 
       // create a subscription on the topic and send/receive another message
       MessageConsumer consumer = session.createConsumer(ActiveMQJMSClient.createTopic(nonExistentTopic));
-      sendFrame(frame);
-      receiveFrame(1000);
+      send(conn, getTopicPrefix() + nonExistentTopic, null, "Hello World", true);
       TextMessage message = (TextMessage) consumer.receive(1000);
       Assert.assertNotNull(message);
       Assert.assertEquals("Hello World", message.getText());
@@ -332,11 +312,13 @@ public class StompTest extends StompTestBase {
       long tmsg = message.getJMSTimestamp();
       Assert.assertTrue(Math.abs(tnow - tmsg) < 1500);
 
-      assertNotNull(server.getActiveMQServer().getPostOffice().getBinding(new SimpleString(nonExistentTopic)));
+      assertNotNull(server.getActiveMQServer()
+                          .getAddressInfo(new SimpleString(nonExistentTopic)));
 
-      // closing the consumer here should trigger auto-deletion of the topic
+      // closing the consumer here should trigger auto-deletion of the subscription queue and address
       consumer.close();
-      assertNull(server.getActiveMQServer().getPostOffice().getBinding(new SimpleString(nonExistentTopic)));
+      assertNull(server.getActiveMQServer()
+                       .getAddressInfo(new SimpleString(nonExistentTopic)));
    }
 
    /*
@@ -346,29 +328,22 @@ public class StompTest extends StompTestBase {
     */
    @Test
    public void testSendMessageWithLeadingNewLine() throws Exception {
+      conn.connect(defUser, defPass);
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SEND)
+                                   .addHeader(Stomp.Headers.Send.DESTINATION, getQueuePrefix() + getQueueName())
+                                   .setBody("Hello World");
+      conn.sendWickedFrame(frame);
 
       MessageConsumer consumer = session.createConsumer(queue);
-
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL + "\n";
-      sendFrame(frame);
-
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
-
-      frame = "SEND\n" + "destination:" +
-         getQueuePrefix() +
-         getQueueName() +
-         "\n\n" +
-         "Hello World" +
-         Stomp.NULL +
-         "\n";
-
-      sendFrame(frame);
-
       TextMessage message = (TextMessage) consumer.receive(1000);
       Assert.assertNotNull(message);
       Assert.assertEquals("Hello World", message.getText());
 
+      send(conn, getQueuePrefix() + getQueueName(), null, "Hello World");
+      message = (TextMessage) consumer.receive(1000);
+      Assert.assertNotNull(message);
+      Assert.assertEquals("Hello World", message.getText());
+
       // Make sure that the timestamp is valid - should
       // be very close to the current time.
       long tnow = System.currentTimeMillis();
@@ -380,25 +355,9 @@ public class StompTest extends StompTestBase {
    public void testSendMessageWithReceipt() throws Exception {
       MessageConsumer consumer = session.createConsumer(queue);
 
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
+      conn.connect(defUser, defPass);
 
-      frame = "SEND\n" + "destination:" +
-         getQueuePrefix() +
-         getQueueName() +
-         "\n" +
-         "receipt: 1234\n\n" +
-         "Hello World" +
-         Stomp.NULL;
-
-      sendFrame(frame);
-
-      String f = receiveFrame(10000);
-      Assert.assertTrue(f.startsWith("RECEIPT"));
-      Assert.assertTrue(f.indexOf("receipt-id:1234") >= 0);
+      send(conn, getQueuePrefix() + getQueueName(), null, "Hello World", true);
 
       TextMessage message = (TextMessage) consumer.receive(1000);
       Assert.assertNotNull(message);
@@ -413,30 +372,19 @@ public class StompTest extends StompTestBase {
 
    @Test
    public void testSendMessageWithContentLength() throws Exception {
-
       MessageConsumer consumer = session.createConsumer(queue);
-
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
+      conn.connect(defUser, defPass);
 
       byte[] data = new byte[]{1, 0, 0, 4};
-
-      frame = "SEND\n" + "destination:" +
-         getQueuePrefix() +
-         getQueueName() +
-         "\n" +
-         "content-length:" +
-         data.length +
-         "\n\n";
       ByteArrayOutputStream baos = new ByteArrayOutputStream();
-      baos.write(frame.getBytes(StandardCharsets.UTF_8));
       baos.write(data);
-      baos.write('\0');
       baos.flush();
-      sendFrame(new String(baos.toByteArray()));
+
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SEND)
+                                   .addHeader(Stomp.Headers.Send.DESTINATION, getQueuePrefix() + getQueueName())
+                                   .addHeader(Stomp.Headers.CONTENT_LENGTH, Integer.toString(data.length))
+                                   .setBody(new String(baos.toByteArray()));
+      conn.sendFrame(frame);
 
       BytesMessage message = (BytesMessage) consumer.receive(10000);
       Assert.assertNotNull(message);
@@ -449,30 +397,22 @@ public class StompTest extends StompTestBase {
 
    @Test
    public void testJMSXGroupIdCanBeSet() throws Exception {
-
+      final String jmsxGroupID = "JMSXGroupID";
       MessageConsumer consumer = session.createConsumer(queue);
 
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
+      conn.connect(defUser, defPass);
 
-      frame = "SEND\n" + "destination:" +
-         getQueuePrefix() +
-         getQueueName() +
-         "\n" +
-         "JMSXGroupID: TEST\n\n" +
-         "Hello World" +
-         Stomp.NULL;
-
-      sendFrame(frame);
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SEND)
+                                   .addHeader(Stomp.Headers.Send.DESTINATION, getQueuePrefix() + getQueueName())
+                                   .addHeader("JMSXGroupID", jmsxGroupID)
+                                   .setBody("Hello World");
+      conn.sendFrame(frame);
 
       TextMessage message = (TextMessage) consumer.receive(1000);
       Assert.assertNotNull(message);
       Assert.assertEquals("Hello World", message.getText());
       // differ from StompConnect
-      Assert.assertEquals("TEST", message.getStringProperty("JMSXGroupID"));
+      Assert.assertEquals(jmsxGroupID, message.getStringProperty("JMSXGroupID"));
    }
 
    @Test
@@ -480,22 +420,14 @@ public class StompTest extends StompTestBase {
 
       MessageConsumer consumer = session.createConsumer(queue, "foo = 'abc'");
 
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
+      conn.connect(defUser, defPass);
 
-      frame = "SEND\n" + "foo:abc\n" +
-         "bar:123\n" +
-         "destination:" +
-         getQueuePrefix() +
-         getQueueName() +
-         "\n\n" +
-         "Hello World" +
-         Stomp.NULL;
-
-      sendFrame(frame);
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SEND)
+                                   .addHeader(Stomp.Headers.Send.DESTINATION, getQueuePrefix() + getQueueName())
+                                   .addHeader("foo", "abc")
+                                   .addHeader("bar", "123")
+                                   .setBody("Hello World");
+      conn.sendFrame(frame);
 
       TextMessage message = (TextMessage) consumer.receive(1000);
       Assert.assertNotNull(message);
@@ -509,22 +441,14 @@ public class StompTest extends StompTestBase {
 
       MessageConsumer consumer = session.createConsumer(queue, "hyphenated_props:b-ar = '123'");
 
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
-
-      frame = "SEND\n" + "foo:abc\n" +
-         "b-ar:123\n" +
-         "destination:" +
-         getQueuePrefix() +
-         getQueueName() +
-         "\n\n" +
-         "Hello World" +
-         Stomp.NULL;
+      conn.connect(defUser, defPass);
 
-      sendFrame(frame);
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SEND)
+                                   .addHeader(Stomp.Headers.Send.DESTINATION, getQueuePrefix() + getQueueName())
+                                   .addHeader("foo", "abc")
+                                   .addHeader("b-ar", "123")
+                                   .setBody("Hello World");
+      conn.sendFrame(frame);
 
       TextMessage message = (TextMessage) consumer.receive(1000);
       Assert.assertNotNull(message);
@@ -538,27 +462,19 @@ public class StompTest extends StompTestBase {
 
       MessageConsumer consumer = session.createConsumer(queue);
 
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
-
-      frame = "SEND\n" + "correlation-id:c123\n" +
-         "persistent:true\n" +
-         "priority:3\n" +
-         "type:t345\n" +
-         "JMSXGroupID:abc\n" +
-         "foo:abc\n" +
-         "bar:123\n" +
-         "destination:" +
-         getQueuePrefix() +
-         getQueueName() +
-         "\n\n" +
-         "Hello World" +
-         Stomp.NULL;
+      conn.connect(defUser, defPass);
 
-      sendFrame(frame);
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SEND)
+                                   .addHeader(Stomp.Headers.Send.DESTINATION, getQueuePrefix() + getQueueName())
+                                   .addHeader("foo", "abc")
+                                   .addHeader("bar", "123")
+                                   .addHeader("correlation-id", "c123")
+                                   .addHeader("persistent", "true")
+                                   .addHeader("type", "t345")
+                                   .addHeader("JMSXGroupID", "abc")
+                                   .addHeader("priority", "3")
+                                   .setBody("Hello World");
+      conn.sendFrame(frame);
 
       TextMessage message = (TextMessage) consumer.receive(1000);
       Assert.assertNotNull(message);
@@ -579,33 +495,25 @@ public class StompTest extends StompTestBase {
    public void testSendMessageWithLongHeaders() throws Exception {
       MessageConsumer consumer = session.createConsumer(queue);
 
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
+      conn.connect(defUser, defPass);
 
       StringBuffer buffer = new StringBuffer();
       for (int i = 0; i < 1024; i++) {
          buffer.append("a");
       }
-      String longHeader = "longHeader:" + buffer.toString() + "\n";
-
-      frame = "SEND\n" + "correlation-id:c123\n" +
-         "persistent:true\n" +
-         "priority:3\n" +
-         "type:t345\n" +
-         "JMSXGroupID:abc\n" +
-         "foo:abc\n" +
-         longHeader +
-         "destination:" +
-         getQueuePrefix() +
-         getQueueName() +
-         "\n\n" +
-         "Hello World" +
-         Stomp.NULL;
-
-      sendFrame(frame);
+
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SEND)
+                                   .addHeader(Stomp.Headers.Send.DESTINATION, getQueuePrefix() + getQueueName())
+                                   .addHeader("foo", "abc")
+                                   .addHeader("bar", "123")
+                                   .addHeader("correlation-id", "c123")
+                                   .addHeader("persistent", "true")
+                                   .addHeader("type", "t345")
+                                   .addHeader("JMSXGroupID", "abc")
+                                   .addHeader("priority", "3")
+                                   .addHeader("longHeader", buffer.toString())
+                                   .setBody("Hello World");
+      conn.sendFrame(frame);
 
       TextMessage message = (TextMessage) consumer.receive(1000);
       Assert.assertNotNull(message);
@@ -615,37 +523,30 @@ public class StompTest extends StompTestBase {
       Assert.assertEquals("getJMSPriority", 3, message.getJMSPriority());
       Assert.assertEquals(DeliveryMode.PERSISTENT, message.getJMSDeliveryMode());
       Assert.assertEquals("foo", "abc", message.getStringProperty("foo"));
-      Assert.assertEquals("longHeader", 1024, message.getStringProperty("longHeader").length());
+      Assert.assertEquals("longHeader", 1024, message.getStringProperty("longHeader")
+                                                     .length());
 
       Assert.assertEquals("JMSXGroupID", "abc", message.getStringProperty("JMSXGroupID"));
    }
 
    @Test
    public void testSubscribeWithAutoAck() throws Exception {
+      conn.connect(defUser, defPass);
 
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(100000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
+      subscribe(conn, null, Stomp.Headers.Subscribe.AckModeValues.AUTO);
 
-      frame = "SUBSCRIBE\n" + "destination:" + getQueuePrefix() + getQueueName() + "\n" + "ack:auto\n\nfff" + Stomp.NULL;
-      sendFrame(frame);
+      sendJmsMessage(getName());
 
-      sendMessage(getName());
+      ClientStompFrame frame = conn.receiveFrame(10000);
+      Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
+      Assert.assertEquals(getQueuePrefix() + getQueueName(), frame.getHeader(Stomp.Headers.Send.DESTINATION));
+      Assert.assertEquals(getName(), frame.getBody());
 
-      frame = receiveFrame(10000);
-      System.out.println("-------- frame received: " + frame);
-      Assert.assertTrue(frame.startsWith("MESSAGE"));
-      Assert.assertTrue(frame.indexOf("destination:") > 0);
-      Assert.assertTrue(frame.indexOf(getName()) > 0);
-
-      Pattern cl = Pattern.compile("Content-length:\\s*(\\d+)", Pattern.CASE_INSENSITIVE);
-      Matcher cl_matcher = cl.matcher(frame);
+      Pattern cl = Pattern.compile(Stomp.Headers.CONTENT_LENGTH + ":\\s*(\\d+)", Pattern.CASE_INSENSITIVE);
+      Matcher cl_matcher = cl.matcher(frame.toString());
       Assert.assertFalse(cl_matcher.find());
 
-      frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      conn.disconnect();
 
       // message should not be received as it was auto-acked
       MessageConsumer consumer = session.createConsumer(queue);
@@ -656,48 +557,32 @@ public class StompTest extends StompTestBase {
 
    @Test
    public void testSubscribeWithAutoAckAndBytesMessage() throws Exception {
-
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(100000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
-
-      frame = "SUBSCRIBE\n" + "destination:" + getQueuePrefix() + getQueueName() + "\n" + "ack:auto\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      conn.connect(defUser, defPass);
+      subscribe(conn, null, Stomp.Headers.Subscribe.AckModeValues.AUTO);
 
       byte[] payload = new byte[]{1, 2, 3, 4, 5};
-      sendMessage(payload, queue);
 
-      frame = receiveFrame(10000);
+      sendJmsMessage(payload, queue);
 
-      System.out.println("Message: " + frame);
+      ClientStompFrame frame = conn.receiveFrame(10000);
 
-      Assert.assertTrue(frame.startsWith("MESSAGE"));
+      Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
 
-      Pattern cl = Pattern.compile("Content-length:\\s*(\\d+)", Pattern.CASE_INSENSITIVE);
-      Matcher cl_matcher = cl.matcher(frame);
+      Pattern cl = Pattern.compile(Stomp.Headers.CONTENT_LENGTH + ":\\s*(\\d+)", Pattern.CASE_INSENSITIVE);
+      Matcher cl_matcher = cl.matcher(frame.toString());
       Assert.assertTrue(cl_matcher.find());
       Assert.assertEquals("5", cl_matcher.group(1));
 
-      Assert.assertFalse(Pattern.compile("type:\\s*null", Pattern.CASE_INSENSITIVE).matcher(frame).find());
-      Assert.assertTrue(frame.indexOf(new String(payload)) > -1);
+      Assert.assertFalse(Pattern.compile("type:\\s*null", Pattern.CASE_INSENSITIVE).matcher(frame.toString()).find());
+      Assert.assertTrue(frame.getBody().toString().indexOf(new String(payload)) > -1);
 
-      frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      conn.disconnect();
    }
 
    @Test
    public void testSubscribeWithMessageSentWithProperties() throws Exception {
-
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(100000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
-
-      frame = "SUBSCRIBE\n" + "destination:" + getQueuePrefix() + getQueueName() + "\n" + "ack:auto\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      conn.connect(defUser, defPass);
+      subscribe(conn, null, Stomp.Headers.Subscribe.AckModeValues.AUTO);
 
       MessageProducer producer = session.createProducer(queue);
       BytesMessage message = session.createBytesMessage();
@@ -712,79 +597,55 @@ public class StompTest extends StompTestBase {
       message.writeBytes("Hello World".getBytes(StandardCharsets.UTF_8));
       producer.send(message);
 
-      frame = receiveFrame(10000);
+      ClientStompFrame frame = conn.receiveFrame(10000);
       Assert.assertNotNull(frame);
-      Assert.assertTrue(frame.startsWith("MESSAGE"));
-      Assert.assertTrue(frame.indexOf("S:") > 0);
-      Assert.assertTrue(frame.indexOf("n:") > 0);
-      Assert.assertTrue(frame.indexOf("byte:") > 0);
-      Assert.assertTrue(frame.indexOf("d:") > 0);
-      Assert.assertTrue(frame.indexOf("f:") > 0);
-      Assert.assertTrue(frame.indexOf("i:") > 0);
-      Assert.assertTrue(frame.indexOf("l:") > 0);
-      Assert.assertTrue(frame.indexOf("s:") > 0);
-      Assert.assertTrue(frame.indexOf("Hello World") > 0);
-
-      // System.out.println("out: "+frame);
-
-      frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
+      Assert.assertEquals("value", frame.getHeader("S"));
+      Assert.assertEquals("false", frame.getHeader("n"));
+      Assert.assertEquals("9", frame.getHeader("byte"));
+      Assert.assertEquals("2.0", frame.getHeader("d"));
+      Assert.assertEquals("6.0", frame.getHeader("f"));
+      Assert.assertEquals("10", frame.getHeader("i"));
+      Assert.assertEquals("121", frame.getHeader("l"));
+      Assert.assertEquals("12", frame.getHeader("s"));
+      Assert.assertEquals("Hello World", frame.getBody());
+
+      conn.disconnect();
    }
 
    @Test
    public void testSubscribeWithID() throws Exception {
+      conn.connect(defUser, defPass);
+      subscribe(conn, "mysubid", Stomp.Headers.Subscribe.AckModeValues.AUTO);
 
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      sendJmsMessage(getName());
 
-      frame = receiveFrame(100000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
+      ClientStompFrame frame = conn.receiveFrame(10000);
+      Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
+      Assert.assertEquals(getQueuePrefix() + getQueueName(), frame.getHeader(Stomp.Headers.Message.DESTINATION));
+      Assert.assertEquals("mysubid", frame.getHeader(Stomp.Headers.Message.SUBSCRIPTION));
+      Assert.assertEquals(getName(), frame.getBody());
 
-      frame = "SUBSCRIBE\n" + "destination:" +
-         getQueuePrefix() +
-         getQueueName() +
-         "\n" +
-         "ack:auto\n" +
-         "id: mysubid\n\n" +
-         Stomp.NULL;
-      sendFrame(frame);
-
-      sendMessage(getName());
-
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("MESSAGE"));
-      Assert.assertTrue(frame.indexOf("destination:") > 0);
-      Assert.assertTrue(frame.indexOf("subscription:") > 0);
-      Assert.assertTrue(frame.indexOf(getName()) > 0);
-
-      frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      conn.disconnect();
    }
 
+   //
    @Test
    public void testBodyWithUTF8() throws Exception {
-
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(100000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
-
-      frame = "SUBSCRIBE\n" + "destination:" + getQueuePrefix() + getQueueName() + "\n" + "ack:auto\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      conn.connect(defUser, defPass);
+      subscribe(conn, null, Stomp.Headers.Subscribe.AckModeValues.AUTO);
 
       String text = "A" + "\u00ea" + "\u00f1" + "\u00fc" + "C";
-      System.out.println(text);
-      sendMessage(text);
+      log.info(text);
+      sendJmsMessage(text);
 
-      frame = receiveFrame(10000);
-      System.out.println(frame);
-      Assert.assertTrue(frame.startsWith("MESSAGE"));
-      Assert.assertTrue(frame.indexOf("destination:") > 0);
-      Assert.assertTrue(frame.indexOf(text) > 0);
+      ClientStompFrame frame = conn.receiveFrame(10000);
+      log.info(frame);
+      Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
+      Assert.assertEquals(getQueuePrefix() + getQueueName(), frame.getHeader(Stomp.Headers.Message.DESTINATION));
+      Assert.assertEquals(text, frame.getBody());
 
-      frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      conn.disconnect();
    }
 
    @Test
@@ -792,88 +653,54 @@ public class StompTest extends StompTestBase {
       int ctr = 10;
       String[] data = new String[ctr];
 
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(100000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
-
-      frame = "SUBSCRIBE\n" + "destination:" + getQueuePrefix() + getQueueName() + "\n" + "ack:auto\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      conn.connect(defUser, defPass);
+      subscribe(conn, null, Stomp.Headers.Subscribe.AckModeValues.AUTO);
 
       for (int i = 0; i < ctr; ++i) {
          data[i] = getName() + i;
-         sendMessage(data[i]);
+         sendJmsMessage(data[i]);
       }
 
       for (int i = 0; i < ctr; ++i) {
-         frame = receiveFrame(1000);
-         Assert.assertTrue("Message not in order", frame.indexOf(data[i]) >= 0);
+         ClientStompFrame frame = conn.receiveFrame(1000);
+         Assert.assertTrue("Message not in order", frame.getBody().equals(data[i]));
       }
 
       // sleep a while before publishing another set of messages
-      waitForFrameToTakeEffect();
+      Thread.sleep(200);
 
       for (int i = 0; i < ctr; ++i) {
-         data[i] = getName() + ":second:" + i;
-         sendMessage(data[i]);
+         data[i] = getName() + Stomp.Headers.SEPARATOR + "second:" + i;
+         sendJmsMessage(data[i]);
       }
 
       for (int i = 0; i < ctr; ++i) {
-         frame = receiveFrame(1000);
-         Assert.assertTrue("Message not in order", frame.indexOf(data[i]) >= 0);
+         ClientStompFrame frame = conn.receiveFrame(1000);
+         Assert.assertTrue("Message not in order", frame.getBody().equals(data[i]));
       }
 
-      frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      conn.disconnect();
    }
 
    @Test
    public void testSubscribeWithAutoAckAndSelector() throws Exception {
+      conn.connect(defUser, defPass);
+      subscribe(conn, null, Stomp.Headers.Subscribe.AckModeValues.AUTO, null, "foo = 'zzz'");
 
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(100000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
-
-      frame = "SUBSCRIBE\n" + "destination:" +
-         getQueuePrefix() +
-         getQueueName() +
-         "\n" +
-         "selector: foo = 'zzz'\n" +
-         "ack:auto\n\n" +
-         Stomp.NULL;
-      sendFrame(frame);
+      sendJmsMessage("Ignored message", "foo", "1234");
+      sendJmsMessage("Real message", "foo", "zzz");
 
-      sendMessage("Ignored message", "foo", "1234");
-      sendMessage("Real message", "foo", "zzz");
+      ClientStompFrame frame = conn.receiveFrame(10000);
+      Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
+      Assert.assertTrue("Should have received the real message but got: " + frame, frame.getBody().equals("Real message"));
 
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("MESSAGE"));
-      Assert.assertTrue("Should have received the real message but got: " + frame, frame.indexOf("Real message") > 0);
-
-      frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      conn.disconnect();
    }
 
    @Test
    public void testSubscribeWithAutoAckAndHyphenatedSelector() throws Exception {
-
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(100000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
-
-      frame = "SUBSCRIBE\n" + "destination:" +
-         getQueuePrefix() +
-         getQueueName() +
-         "\n" +
-         "selector: hyphenated_props:foo-bar = 'zzz'\n" +
-         "ack:auto\n\n" +
-         Stomp.NULL;
-      sendFrame(frame);
+      conn.connect(defUser, defPass);
+      subscribe(conn, null, Stomp.Headers.Subscribe.AckModeValues.AUTO, null, "hyphenated_props:foo-bar = 'zzz'");
 
       ServerLocator serverLocator = addServerLocator(ActiveMQClient.createServerLocator("vm://0"));
       ClientSessionFactory clientSessionFactory = serverLocator.createSessionFactory();
@@ -891,40 +718,26 @@ public class StompTest extends StompTestBase {
       producer.send(ignoredMessage);
       producer.send(realMessage);
 
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("MESSAGE"));
-      Assert.assertTrue("Should have received the real message but got: " + frame, frame.indexOf("Real message") > 0);
 
-      frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      ClientStompFrame frame = conn.receiveFrame(10000);
+      Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
+      Assert.assertTrue("Should have received the real message but got: " + frame, frame.getBody().equals("Real message"));
+
+    conn.disconnect();
    }
 
    @Test
    public void testSubscribeWithClientAck() throws Exception {
+      conn.connect(defUser, defPass);
+      subscribe(conn, null, Stomp.Headers.Subscribe.AckModeValues.CLIENT);
 
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      sendJmsMessage(getName());
+      ClientStompFrame frame = conn.receiveFrame(10000);
+      Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
+      Assert.assertNotNull(frame.getHeader(Stomp.Headers.Message.MESSAGE_ID));
+      ack(conn, null, frame);
 
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
-
-      frame = "SUBSCRIBE\n" + "destination:" + getQueuePrefix() + getQueueName() + "\n" + "ack:client\n\n" + Stomp.NULL;
-
-      sendFrame(frame);
-
-      sendMessage(getName());
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("MESSAGE"));
-      Pattern cl = Pattern.compile("message-id:\\s*(\\S+)", Pattern.CASE_INSENSITIVE);
-      Matcher cl_matcher = cl.matcher(frame);
-      Assert.assertTrue(cl_matcher.find());
-      String messageID = cl_matcher.group(1);
-
-      frame = "ACK\n" + "message-id: " + messageID + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
+    conn.disconnect();
 
       // message should not be received since message was acknowledged by the client
       MessageConsumer consumer = session.createConsumer(queue);
@@ -934,23 +747,14 @@ public class StompTest extends StompTestBase {
 
    @Test
    public void testRedeliveryWithClientAck() throws Exception {
+      conn.connect(defUser, defPass);
+      subscribe(conn, null, Stomp.Headers.Subscribe.AckModeValues.CLIENT);
 
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      sendJmsMessage(getName());
+      ClientStompFrame frame = conn.receiveFrame(10000);
+      Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
 
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
-
-      frame = "SUBSCRIBE\n" + "destination:" + getQueuePrefix() + getQueueName() + "\n" + "ack:client\n\n" + Stomp.NULL;
-
-      sendFrame(frame);
-
-      sendMessage(getName());
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("MESSAGE"));
-
-      frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      conn.disconnect();
 
       // message should be received since message was not acknowledged
       MessageConsumer consumer = session.createConsumer(queue);
@@ -971,149 +775,131 @@ public class StompTest extends StompTestBase {
 
    protected void assertSubscribeWithClientAckThenConsumeWithAutoAck(boolean sendDisconnect) throws Exception {
 
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
+      conn.connect(defUser, defPass);
 
-      frame = "SUBSCRIBE\n" + "destination:" + getQueuePrefix() + getQueueName() + "\n" + "ack:client\n\n" + Stomp.NULL;
+//            String frame = Stomp.Commands.SUBSCRIBE + "\n" +
+//               Stomp.Headers.Subscribe.SUBSCRIPTION_TYPE + Stomp.Headers.SEPARATOR + AddressInfo.RoutingType.ANYCAST + "\n" +
+//               Stomp.Headers.Send.DESTINATION + Stomp.Headers.SEPARATOR + getQueuePrefix() + getQueueName() + "\n" +
+//               Stomp.Headers.Message.ACK + Stomp.Headers.SEPARATOR + "client\n\n" +
+//               Stomp.NULL;
+//
+//            sendFrame(frame);
+      subscribe(conn, null, Stomp.Headers.Subscribe.AckModeValues.CLIENT);
+      sendJmsMessage(getName());
 
-      sendFrame(frame);
-      sendMessage(getName());
-
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("MESSAGE"));
+//            frame = receiveFrame(10000);
+//            Assert.assertTrue(frame.startsWith(Stomp.Responses.MESSAGE));
+      ClientStompFrame frame = conn.receiveFrame(10000);
+      Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
 
       log.info("Reconnecting!");
 
       if (sendDisconnect) {
-         frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-         sendFrame(frame);
-         waitForFrameToTakeEffect();
-         reconnect();
+       conn.disconnect();
+//         reconnect();
+         conn.destroy();
+         conn = StompClientConnectionFactory.createClientConnection("1.0", hostname, port);
       } else {
-         reconnect(100);
-         waitForFrameToTakeEffect();
+//         reconnect(100);
+//               waitForFrameToTakeEffect();
+         conn.destroy();
+         conn = StompClientConnectionFactory.createClientConnection("1.0", hostname, port);
       }
 
       // message should be received since message was not acknowledged
-      frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
+      conn.connect(defUser, defPass);
 
-      frame = "SUBSCRIBE\n" + "destination:" + getQueuePrefix() + getQueueName() + "\n\n" + Stomp.NULL;
+//            frame = Stomp.Commands.SUBSCRIBE + "\n" +
+//               Stomp.Headers.Subscribe.SUBSCRIPTION_TYPE + Stomp.Headers.SEPARATOR + AddressInfo.RoutingType.ANYCAST + "\n" +
+//               Stomp.Headers.Subscribe.DESTINATION + Stomp.Headers.SEPARATOR + getQueuePrefix() + getQueueName() + "\n\n" +
+//               Stomp.NULL;
+//
+//            sendFrame(frame);
+      subscribe(conn, null);
 
-      sendFrame(frame);
+//            frame = receiveFrame(10000);
+//            log.info(frame);
+//            Assert.assertTrue(frame.startsWith(Stomp.Responses.MESSAGE));
+      frame = conn.receiveFrame(10000);
+      Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
 
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("MESSAGE"));
+      conn.disconnect();
+      conn.destroy();
 
-      frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
-      waitForFrameToTakeEffect();
+      conn = StompClientConnectionFactory.createClientConnection("1.0", hostname, port);
 
       // now let's make sure we don't see the message again
-      reconnect();
-
-      frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
+//      reconnect();
 
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
+      conn.connect(defUser, defPass);
 
-      frame = "SUBSCRIBE\n" + "destination:" +
-         getQueuePrefix() +
-         getQueueName() +
-         "\n" +
-         "receipt: 1234\n\n" +
-         Stomp.NULL;
+//            frame = Stomp.Commands.SUBSCRIBE + "\n" +
+//               Stomp.Headers.Subscribe.SUBSCRIPTION_TYPE + Stomp.Headers.SEPARATOR + AddressInfo.RoutingType.ANYCAST + "\n" +
+//               Stomp.Headers.Send.DESTINATION + Stomp.Headers.SEPARATOR + getQueuePrefix() + getQueueName() + "\n" +
+//               Stomp.Headers.RECEIPT_REQUESTED + Stomp.Headers.SEPARATOR + " 1234\n\n" +
+//               Stomp.NULL;
+//
+//            sendFrame(frame);
+      subscribe(conn, null, Stomp.Headers.Subscribe.AckModeValues.AUTO, null, true);
 
-      sendFrame(frame);
       // wait for SUBSCRIBE's receipt
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("RECEIPT"));
-
-      sendMessage("shouldBeNextMessage");
-
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("MESSAGE"));
-      System.out.println(frame);
-      Assert.assertTrue(frame.contains("shouldBeNextMessage"));
+//            frame = receiveFrame(10000);
+//            Assert.assertTrue(frame.startsWith(Stomp.Responses.RECEIPT));
+
+      sendJmsMessage("shouldBeNextMessage");
+
+//            frame = receiveFrame(10000);
+//            Assert.assertTrue(frame.startsWith(Stomp.Responses.MESSAGE));
+//            log.info(frame);
+//            Assert.assertTrue(frame.contains("shouldBeNextMessage"));
+      frame = conn.receiveFrame(10000);
+      Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
+      Assert.assertEquals("shouldBeNextMessage", frame.getBody());
    }
 
+
    @Test
    public void testUnsubscribe() throws Exception {
-
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-      frame = receiveFrame(100000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
-
-      frame = "SUBSCRIBE\n" + "destination:" + getQueuePrefix() + getQueueName() + "\n" + "ack:auto\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      conn.connect(defUser, defPass);
+      subscribe(conn, null, Stomp.Headers.Subscribe.AckModeValues.AUTO);
 
       // send a message to our queue
-      sendMessage("first message");
+      sendJmsMessage("first message");
 
-      // receive message from socket
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("MESSAGE"));
+      // receive message
+      ClientStompFrame frame = conn.receiveFrame(10000);
+      Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
 
       // remove suscription
-      frame = "UNSUBSCRIBE\n" + "destination:" +
-         getQueuePrefix() +
-         getQueueName() +
-         "\n" +
-         "receipt:567\n" +
-         "\n\n" +
-         Stomp.NULL;
-      sendFrame(frame);
-      waitForReceipt();
+      unsubscribe(conn, null, getQueuePrefix() + getQueueName(), true, false);
 
       // send a message to our queue
-      sendMessage("second message");
+      sendJmsMessage("second message");
 
-      frame = receiveFrame(1000);
+      frame = conn.receiveFrame(1000);
       log.info("Received frame: " + frame);
       Assert.assertNull("No message should have been received since subscription was removed", frame);
    }
 
    @Test
    public void testUnsubscribeWithID() throws Exception {
-
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-      frame = receiveFrame(100000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
-
-      frame = "SUBSCRIBE\n" + "destination:" +
-         getQueuePrefix() +
-         getQueueName() +
-         "\n" +
-         "id: mysubid\n" +
-         "ack:auto\n\n" +
-         Stomp.NULL;
-      sendFrame(frame);
+      conn.connect(defUser, defPass);
+      subscribe(conn, "mysubid", Stomp.Headers.Subscribe.AckModeValues.AUTO);
 
       // send a message to our queue
-      sendMessage("first message");
+      sendJmsMessage("first message");
 
       // receive message from socket
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("MESSAGE"));
+      ClientStompFrame frame = conn.receiveFrame(10000);
+      Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
 
       // remove suscription
-      frame = "UNSUBSCRIBE\n" + "id:mysubid\n" + "receipt: 345\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
-      waitForReceipt();
+      unsubscribe(conn, "mysubid", null, true, false);
 
       // send a message to our queue
-      sendMessage("second message");
+      sendJmsMessage("second message");
 
-      frame = receiveFrame(1000);
+      frame = conn.receiveFrame(1000);
       log.info("Received frame: " + frame);
       Assert.assertNull("No message should have been received since subscription was removed", frame);
 
@@ -1122,34 +908,15 @@ public class StompTest extends StompTestBase {
    @Test
    public void testTransactionCommit() throws Exception {
       MessageConsumer consumer = session.createConsumer(queue);
+      conn.connect(defUser, defPass);
 
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      String f = receiveFrame(1000);
-      Assert.assertTrue(f.startsWith("CONNECTED"));
-
-      frame = "BEGIN\n" + "transaction: tx1\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = "SEND\n" + "destination:" +
-         getQueuePrefix() +
-         getQueueName() +
-         "\n" +
-         "transaction: tx1\n" +
-         "receipt: 123\n" +
-         "\n\n" +
-         "Hello World" +
-         Stomp.NULL;
-      sendFrame(frame);
-      waitForReceipt();
+      beginTransaction(conn, "tx1");
+      send(conn, getQueuePrefix() + getQueueName(), null, "Hello World", true, null, "tx1");
 
       // check the message is not committed
       assertNull(consumer.receive(100));
 
-      frame = "COMMIT\n" + "transaction: tx1\n" + "receipt:456\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
-      waitForReceipt();
+      commitTransaction(conn, "tx1", true);
 
       Message message = consumer.receive(1000);
       Assert.assertNotNull("Should have received a message", message);
@@ -1158,49 +925,20 @@ public class StompTest extends StompTestBase {
    @Test
    public void testSuccessiveTransactionsWithSameID() throws Exception {
       MessageConsumer consumer = session.createConsumer(queue);
-
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      String f = receiveFrame(1000);
-      Assert.assertTrue(f.startsWith("CONNECTED"));
+      conn.connect(defUser, defPass);
 
       // first tx
-      frame = "BEGIN\n" + "transaction: tx1\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = "SEND\n" + "destination:" +
-         getQueuePrefix() +
-         getQueueName() +
-         "\n" +
-         "transaction: tx1\n" +
-         "\n\n" +
-         "Hello World" +
-         Stomp.NULL;
-      sendFrame(frame);
-
-      frame = "COMMIT\n" + "transaction: tx1\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      beginTransaction(conn, "tx1");
+      send(conn, getQueuePrefix() + getQueueName(), null, "Hello World", true, null, "tx1");
+      commitTransaction(conn, "tx1");
 
       Message message = consumer.receive(1000);
       Assert.assertNotNull("Should have received a message", message);
 
       // 2nd tx with same tx ID
-      frame = "BEGIN\n" + "transaction: tx1\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = "SEND\n" + "destination:" +
-         getQueuePrefix() +
-         getQueueName() +
-         "\n" +
-         "transaction: tx1\n" +
-         "\n\n" +
-         "Hello World" +
-         Stomp.NULL;
-      sendFrame(frame);
-
-      frame = "COMMIT\n" + "transaction: tx1\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      beginTransaction(conn, "tx1");
+      send(conn, getQueuePrefix() + getQueueName(), null, "Hello World", true, null, "tx1");
+      commitTransaction(conn, "tx1");
 
       message = consumer.receive(1000);
       Assert.assertNotNull("Should have received a message", message);
@@ -1208,67 +946,27 @@ public class StompTest extends StompTestBase {
 
    @Test
    public void testBeginSameTransactionTwice() throws Exception {
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      String f = receiveFrame(1000);
-      Assert.assertTrue(f.startsWith("CONNECTED"));
-
-      frame = "BEGIN\n" + "transaction: tx1\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      // begin the tx a 2nd time
-      frame = "BEGIN\n" + "transaction: tx1\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      f = receiveFrame(1000);
-      Assert.assertTrue(f.startsWith("ERROR"));
+      conn.connect(defUser, defPass);
+      beginTransaction(conn, "tx1");
+      beginTransaction(conn, "tx1");
 
+      ClientStompFrame frame = conn.receiveFrame(1000);
+      Assert.assertEquals(Stomp.Responses.ERROR, frame.getCommand());
    }
 
    @Test
    public void testTransactionRollback() throws Exception {
       MessageConsumer consumer = session.createConsumer(queue);
+      String txId = "tx1";
 
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      String f = receiveFrame(1000);
-      Assert.assertTrue(f.startsWith("CONNECTED"));
-
-      frame = "BEGIN\n" + "transaction: tx1\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = "SEND\n" + "destination:" +
-         getQueuePrefix() +
-         getQueueName() +
-         "\n" +
-         "transaction: tx1\n" +
-         "\n" +
-         "first message" +
-         Stomp.NULL;
-      sendFrame(frame);
-
-      // rollback first message
-      frame = "ABORT\n" + "transaction: tx1\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = "BEGIN\n" + "transaction: tx1\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = "SEND\n" + "destination:" +
-         getQueuePrefix() +
-         getQueueName() +
-         "\n" +
-         "transaction: tx1\n" +
-         "\n" +
-         "second message" +
-         Stomp.NULL;
-      sendFrame(frame);
-
-      frame = "COMMIT\n" + "transaction: tx1\n" + "receipt:789\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
-      waitForReceipt();
+      conn.connect(defUser, defPass);
+      beginTransaction(conn, txId);
+      send(conn, getQueuePrefix() + getQueueName(), null, "first message", true, null, txId);
+      abortTransaction(conn, txId);
+
+      beginTransaction(conn, txId);
+      send(conn, getQueuePrefix() + getQueueName(), null, "second message", true, null, txId);
+      commitTransaction(conn, txId);
 
       // only second msg should be received since first msg was rolled back
       TextMessage message = (TextMessage) consumer.receive(1000);
@@ -1280,91 +978,52 @@ public class StompTest extends StompTestBase {
    public void testSubscribeToTopic() throws Exception {
       final int baselineQueueCount = server.getActiveMQServer().getActiveMQServerControl().getQueueNames().length;
 
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(100000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
+      conn.connect(defUser, defPass);
 
-      frame = "SUBSCRIBE\n" + "destination:" +
-         getTopicPrefix() +
-         getTopicName() +
-         "\n" +
-         "receipt: 12\n" +
-         "\n\n" +
-         Stomp.NULL;
-      sendFrame(frame);
-      // wait for SUBSCRIBE's receipt
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("RECEIPT"));
+      subscribeTopic(conn, null, null, null, true);
 
       assertTrue("Subscription queue should be created here", Wait.waitFor(new Wait.Condition() {
 
          @Override
          public boolean isSatisfied() throws Exception {
-            if (server.getActiveMQServer().getActiveMQServerControl().getQueueNames().length - baselineQueueCount == 1) {
+            int length = server.getActiveMQServer().getActiveMQServerControl().getQueueNames().length;
+            if (length - baselineQueueCount == 1) {
                return true;
             } else {
+               log.info("Queue count: " + (length - baselineQueueCount));
                return false;
             }
          }
-      }, TimeUnit.SECONDS.toMillis(1000), TimeUnit.MILLISECONDS.toMillis(100)));
-
-      sendMessage(getName(), topic);
-
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("MESSAGE"));
-      Assert.assertTrue(frame.indexOf("destination:") > 0);
-      Assert.assertTrue(frame.indexOf(getName()) > 0);
-
-      frame = "UNSUBSCRIBE\n" + "destination:" +
-         getTopicPrefix() +
-         getTopicName() +
-         "\n" +
-         "receipt: 1234\n" +
-         "\n\n" +
-         Stomp.NULL;
-      sendFrame(frame);
-      // wait for UNSUBSCRIBE's receipt
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("RECEIPT"));
-
-      sendMessage(getName(), topic);
-
-      frame = receiveFrame(1000);
+      }, TimeUnit.SECONDS.toMillis(10), TimeUnit.MILLISECONDS.toMillis(100)));
+
+      sendJmsMessage(getName(), topic);
+
+      ClientStompFrame frame = conn.receiveFrame(1000);
+      Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
+      Assert.assertEquals(getTopicPrefix() + getTopicName(), frame.getHeader(Stomp.Headers.Send.DESTINATION));
+      Assert.assertEquals(getName(), frame.getBody());
+
+      unsubscribe(conn, null, getTopicPrefix() + getTopicName(), true, false);
+
+      sendJmsMessage(getName(), topic);
+
+      frame = conn.receiveFrame(1000);
       log.info("Received frame: " + frame);
       Assert.assertNull("No message should have been received since subscription was removed", frame);
 
       assertEquals("Subscription queue should be deleted", 0, server.getActiveMQServer().getActiveMQServerControl().getQueueNames().length - baselineQueueCount);
 
-      frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
+    conn.disconnect();
    }
-
+      //
    @Test
    public void testSubscribeToQueue() throws Exception {
       final int baselineQueueCount = server.getActiveMQServer().getActiveMQServerControl().getQueueNames().length;
 
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(100000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
-
-      frame = "SUBSCRIBE\n" + "destination:" +
-         getQueuePrefix() +
-         getQueueName() +
-         "\n" +
-         "receipt: 12\n" +
-         "\n\n" +
-         Stomp.NULL;
-      sendFrame(frame);
-      // wait for SUBSCRIBE's receipt
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("RECEIPT"));
+      conn.connect(defUser, defPass);
+      subscribe(conn, null, null, null, true);
 
       assertFalse("Queue should not be created here", Wait.waitFor(new Wait.Condition() {
-
          @Override
          public boolean isSatisfied() throws Exception {
             if (server.getActiveMQServer().getActiveMQServerControl().getQueueNames().length - baselineQueueCount == 1) {
@@ -1375,65 +1034,39 @@ public class StompTest extends StompTestBase {
          }
       }, TimeUnit.MILLISECONDS.toMillis(1000), TimeUnit.MILLISECONDS.toMillis(100)));
 
-      sendMessage(getName(), queue);
+      sendJmsMessage(getName(), queue);
 
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("MESSAGE"));
-      Assert.assertTrue(frame.indexOf("destination:") > 0);
-      Assert.assertTrue(frame.indexOf(getName()) > 0);
+      ClientStompFrame frame = conn.receiveFrame(1000);
+      Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
+      Assert.assertEquals(getQueuePrefix() + getQueueName(), frame.getHeader(Stomp.Headers.Send.DESTINATION));
+      Assert.assertEquals(getName(), frame.getBody());
 
-      frame = "UNSUBSCRIBE\n" + "destination:" +
-         getQueuePrefix() +
-         getQueueName() +
-         "\n" +
-         "receipt: 1234\n" +
-         "\n\n" +
-         Stomp.NULL;
-      sendFrame(frame);
-      // wait for UNSUBSCRIBE's receipt
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("RECEIPT"));
+      unsubscribe(conn, null, getQueuePrefix() + getQueueName(), true, false);
 
-      sendMessage(getName(), queue);
+      sendJmsMessage(getName(), queue);
 
-      frame = receiveFrame(1000);
+      frame = conn.receiveFrame(1000);
       log.info("Received frame: " + frame);
       Assert.assertNull("No message should have been received since subscription was removed", frame);
 
       assertEquals("Subscription queue should not be deleted", baselineQueueCount, server.getActiveMQServer().getActiveMQServerControl().getQueueNames().length);
 
-      frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      conn.disconnect();
    }
 
    @Test
    public void testSubscribeToNonExistentQueue() throws Exception {
       String nonExistentQueue = RandomUtil.randomString();
 
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(100000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
+      conn.connect(defUser, defPass);
+      subscribe(conn, null, null, null, null, getQueuePrefix() + nonExistentQueue, true);
 
-      frame = "SUBSCRIBE\n" + "destination:" +
-         getQueuePrefix() +
-         nonExistentQueue +
-         "\n" +
-         "receipt: 12\n" +
-         "\n\n" +
-         Stomp.NULL;
-      sendFrame(frame);
-      // wait for SUBSCRIBE's receipt
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("RECEIPT"));
-
-      sendMessage(getName(), ActiveMQJMSClient.createQueue(nonExistentQueue));
+      sendJmsMessage(getName(), ActiveMQJMSClient.createQueue(nonExistentQueue));
 
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("MESSAGE"));
-      Assert.assertTrue(frame.indexOf("destination:") > 0);
-      Assert.assertTrue(frame.indexOf(getName()) > 0);
+      ClientStompFrame frame = conn.receiveFrame(1000);
+      Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
+      Assert.assertEquals(getQueuePrefix() + nonExistentQueue, frame.getHeader(Stomp.Headers.Send.DESTINATION));
+      Assert.assertEquals(getName(), frame.getBody());
 
       assertNotNull(server.getActiveMQServer().getPostOffice().getBinding(new SimpleString(nonExistentQueue)));
 
@@ -1449,322 +1082,160 @@ public class StompTest extends StompTestBase {
          }
       }, 1000, 50));
 
-      frame = "UNSUBSCRIBE\n" + "destination:" +
-         getQueuePrefix() +
-         nonExistentQueue +
-         "\n" +
-         "receipt: 1234\n" +
-         "\n\n" +
-         Stomp.NULL;
-      sendFrame(frame);
-      // wait for UNSUBSCRIBE's receipt
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("RECEIPT"));
+      unsubscribe(conn, null, getQueuePrefix() + nonExistentQueue, true, false);
 
       assertNull(server.getActiveMQServer().getPostOffice().getBinding(new SimpleString(nonExistentQueue)));
 
-      sendMessage(getName(), ActiveMQJMSClient.createQueue(nonExistentQueue));
+      sendJmsMessage(getName(), ActiveMQJMSClient.createQueue(nonExistentQueue));
 
-      frame = receiveFrame(1000);
+      frame = conn.receiveFrame(1000);
       log.info("Received frame: " + frame);
       Assert.assertNull("No message should have been received since subscription was removed", frame);
 
-      frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      conn.disconnect();
    }
 
    @Test
    public void testDurableSubscriberWithReconnection() throws Exception {
+      conn.connect(defUser, defPass, "myclientid");
+      subscribeTopic(conn, null, null, getName());
+
+      conn.disconnect();
 
-      String connectFame = "CONNECT\n" + "login: brianm\n" +
-         "passcode: wombats\n" +
-         "client-id: myclientid\n\n" +
-         Stomp.NULL;
-      sendFrame(connectFame);
-
-      String frame = receiveFrame(100000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
-
-      String subscribeFrame = "SUBSCRIBE\n" + "destination:" +
-         getTopicPrefix() +
-         getTopicName() +
-         "\n" +
-         "durable-subscriber-name: " +
-         getName() +
-         "\n" +
-         "\n\n" +
-         Stomp.NULL;
-      sendFrame(subscribeFrame);
-      waitForFrameToTakeEffect();
-
-      String disconnectFrame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-      sendFrame(disconnectFrame);
-      waitForFrameToTakeEffect();
+      Thread.sleep(500);
 
       // send the message when the durable subscriber is disconnected
-      sendMessage(getName(), topic);
-
-      reconnect(100);
-      sendFrame(connectFame);
-      frame = receiveFrame(100000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
-
-      sendFrame(subscribeFrame);
-
-      // we must have received the message
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("MESSAGE"));
-      Assert.assertTrue(frame.indexOf("destination:") > 0);
-      Assert.assertTrue(frame.indexOf(getName()) > 0);
-
-      String unsubscribeFrame = "UNSUBSCRIBE\n" + "destination:" +
-         getTopicPrefix() +
-         getTopicName() +
-         "\n" +
-         "receipt: 1234\n" +
-         "\n\n" +
-         Stomp.NULL;
-      sendFrame(unsubscribeFrame);
-      // wait for UNSUBSCRIBE's receipt
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("RECEIPT"));
-
-      sendFrame(disconnectFrame);
+      sendJmsMessage(getName(), topic);
+
+      conn.destroy();
+      conn = StompClientConnectionFactory.createClientConnection("1.0", hostname, port);
+      conn.connect(defUser, defPass, "myclientid");
+
+      subscribeTopic(conn, null, null, getName());
+
+      ClientStompFrame frame = conn.receiveFrame(3000);
+      assertNotNull("Should have received a message from the durable subscription", frame);
+      Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
+      Assert.assertEquals(getTopicPrefix() + getTopicName(), frame.getHeader(Stomp.Headers.Send.DESTINATION));
+      Assert.assertEquals(getName(), frame.getBody());
+
+      unsubscribe(conn, null, getTopicPrefix() + getTopicName(), true, true);
+
+      conn.disconnect();
    }
 
    @Test
    public void testDurableSubscriber() throws Exception {
-
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n" + "client-id: myclientid\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(100000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
-
-      String subscribeFrame = "SUBSCRIBE\n" + "destination:" +
-         getTopicPrefix() +
-         getTopicName() +
-         "\n" +
-         "receipt: 12\n" +
-         "durable-subscriber-name: " +
-         getName() +
-         "\n" +
-         "\n\n" +
-         Stomp.NULL;
-      sendFrame(subscribeFrame);
-      // wait for SUBSCRIBE's receipt
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("RECEIPT"));
+      conn.connect(defUser, defPass, "myclientid");
+      subscribeTopic(conn, null, null, getName(), true);
+      ClientStompFrame response = subscribeTopic(conn, null, null, getName(), true);
 
       // creating a subscriber with the same durable-subscriber-name must fail
-      sendFrame(subscribeFrame);
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("ERROR"));
+      Assert.assertEquals(Stomp.Responses.ERROR, response.getCommand());
 
-      frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      conn.disconnect();
    }
 
    @Test
    public void testDurableUnSubscribe() throws Exception {
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n" + "client-id: myclientid\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(1000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
-
-      String subscribeFrame = "SUBSCRIBE\n" + "destination:" +
-         getTopicPrefix() +
-         getTopicName() +
-         "\n" +
-         "receipt: 12\n" +
-         "durable-subscriber-name: " +
-         getName() +
-         "\n" +
-         "\n\n" +
-         Stomp.NULL;
-      sendFrame(subscribeFrame);
-      // wait for SUBSCRIBE's receipt
-      frame = receiveFrame(1000);
-      Assert.assertTrue(frame.startsWith("RECEIPT"));
-
-      frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
-      waitForFrameToTakeEffect();
+      conn.connect(defUser, defPass, "myclientid");
+      subscribeTopic(conn, null, null, getName(), true);
+      conn.disconnect();
+      Thread.sleep(500);
 
       assertNotNull(server.getActiveMQServer().locateQueue(SimpleString.toSimpleString("myclientid." + getName())));
 
-      reconnect(100);
-      frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n" + "client-id: myclientid\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(1000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
+      conn.destroy();
+      conn = StompClientConnectionFactory.createClientConnection("1.0", hostname, port);
 
-      String unsubscribeFrame = "UNSUBSCRIBE\n" + "destination:" +
-         getTopicPrefix() +
-         getTopicName() +
-         "\n" +
-         "durable-subscriber-name: " +
-         getName() +
-         "\n" +
-         "\n\n" +
-         Stomp.NULL;
-      sendFrame(unsubscribeFrame);
-
-      frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
-      waitForFrameToTakeEffect();
+      conn.connect(defUser, defPass, "myclientid");
+      unsubscribe(conn, getName(), getTopicPrefix() + getTopicName(), false, true);
+      conn.disconnect();
+      Thread.sleep(500);
 
       assertNull(server.getActiveMQServer().locateQueue(SimpleString.toSimpleString("myclientid." + getName())));
    }
 
    @Test
    public void testSubscribeToTopicWithNoLocal() throws Exception {
+      conn.connect(defUser, defPass);
+      subscribeTopic(conn, null, null, null, true, true);
 
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(100000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
-
-      frame = "SUBSCRIBE\n" + "destination:" +
-         getTopicPrefix() +
-         getTopicName() +
-         "\n" +
-         "receipt: 12\n" +
-         "no-local: true\n" +
-         "\n\n" +
-         Stomp.NULL;
-      sendFrame(frame);
-      // wait for SUBSCRIBE's receipt
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("RECEIPT"));
-
-      // send a message on the same connection => it should not be received
-      frame = "SEND\n" + "destination:" + getTopicPrefix() + getTopicName() + "\n\n" + "Hello World" + Stomp.NULL;
-      sendFrame(frame);
+      // send a message on the same connection => it should not be received is noLocal = true on subscribe
+      send(conn, getTopicPrefix() + getTopicName(), null, "Hello World");
 
-      frame = receiveFrame(2000);
+      ClientStompFrame frame = conn.receiveFrame(2000);
       log.info("Received frame: " + frame);
       Assert.assertNull("No message should have been received since subscription was removed", frame);
 
       // send message on another JMS connection => it should be received
-      sendMessage(getName(), topic);
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("MESSAGE"));
-      Assert.assertTrue(frame.indexOf("destination:") > 0);
-      Assert.assertTrue(frame.indexOf(getName()) > 0);
-
-      frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      sendJmsMessage(getName(), topic);
+      frame = conn.receiveFrame(10000);
+      Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
+      Assert.assertEquals(getTopicPrefix() + getTopicName(), frame.getHeader(Stomp.Headers.Send.DESTINATION));
+      Assert.assertEquals(getName(), frame.getBody());
+
+      conn.disconnect();
    }
 
    @Test
    public void testTopicExistsAfterNoUnsubscribeDisconnect() throws Exception {
+      conn.connect(defUser, defPass);
+      subscribeTopic(conn, null, null, null, true);
 
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(100000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
+      // disconnect, _without unsubscribing_
+      conn.disconnect();
 
-      frame = "SUBSCRIBE\n" + "destination:" +
-         getTopicPrefix() +
-         getTopicName() +
-         "\n" +
-         "receipt: 12\n" +
-         "\n\n" +
-         Stomp.NULL;
-      sendFrame(frame);
-      // wait for SUBSCRIBE's receipt
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("RECEIPT"));
+      Thread.sleep(500);
 
-      // disconnect, _without unsubscribing_
-      frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
-      waitForFrameToTakeEffect();
+      conn.destroy();
 
       // connect again
-      reconnect();
-      frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(100000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
+      conn = StompClientConnectionFactory.createClientConnection("1.0", hostname, port);
+      conn.connect(defUser, defPass);
 
       // send a receipted message to the topic
-      frame = "SEND\n" + "destination:" + getTopicPrefix() + getTopicName() + "\nreceipt:42\n\n\n" + "Hello World" + Stomp.NULL;
-      sendFrame(frame);
-
-      // the topic should exist and receive the message, and we should get the requested receipt
-      frame = receiveFrame(2000);
-      log.info("Received frame: " + frame);
-      Assert.assertTrue(frame.startsWith("RECEIPT"));
+      ClientStompFrame response = send(conn, getTopicPrefix() + getTopicName(), null, "Hello World", true);
+      assertEquals(Stomp.Responses.RECEIPT, response.getCommand());
 
       // ...and nothing else
-      frame = receiveFrame(2000);
+      ClientStompFrame frame = conn.receiveFrame(2000);
       log.info("Received frame: " + frame);
       Assert.assertNull(frame);
 
-      frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      conn.disconnect();
    }
 
    @Test
    public void testClientAckNotPartOfTransaction() throws Exception {
+      conn.connect(defUser, defPass);
+      subscribe(conn, null, Stomp.Headers.Subscribe.AckModeValues.CLIENT);
 
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(100000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
-
-      frame = "SUBSCRIBE\n" + "destination:" +
-         getQueuePrefix() +
-         getQueueName() +
-         "\n" +
-         "ack:client\n" +
-         "\n\n" +
-         Stomp.NULL;
-      sendFrame(frame);
-
-      sendMessage(getName());
-
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("MESSAGE"));
-      Assert.assertTrue(frame.indexOf("destination:") > 0);
-      Assert.assertTrue(frame.indexOf(getName()) > 0);
-      Assert.assertTrue(frame.indexOf("message-id:") > 0);
-      Pattern cl = Pattern.compile("message-id:\\s*(\\S+)", Pattern.CASE_INSENSITIVE);
-      Matcher cl_matcher = cl.matcher(frame);
-      Assert.assertTrue(cl_matcher.find());
-      String messageID = cl_matcher.group(1);
-
-      frame = "BEGIN\n" + "transaction: tx1\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      sendJmsMessage(getName());
 
-      frame = "ACK\n" + "message-id:" + messageID + "\n" + "transaction: tx1\n" + "\n" + "second message" + Stomp.NULL;
-      sendFrame(frame);
+      ClientStompFrame frame = conn.receiveFrame(10000);
+      Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
+      Assert.assertEquals(getQueuePrefix() + getQueueName(), frame.getHeader(Stomp.Headers.Send.DESTINATION));
+      String messageID = frame.getHeader(Stomp.Headers.Message.MESSAGE_ID);
+      Assert.assertNotNull(messageID);
+      Assert.assertEquals(getName(), frame.getBody());
 
-      frame = "ABORT\n" + "transaction: tx1\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      beginTransaction(conn, "tx1");
+      ack(conn, null, messageID, "tx1");
+      abortTransaction(conn, "tx1");
 
-      frame = receiveFrame(1000);
+      frame = conn.receiveFrame(1000);
       Assert.assertNull("No message should have been received as the message was acked even though the transaction has been aborted", frame);
 
-      frame = "UNSUBSCRIBE\n" + "destination:" + getQueuePrefix() + getQueueName() + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      unsubscribe(conn, null, getQueuePrefix() + getQueueName(), false, false);
 
-      frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      conn.disconnect();
    }
 
    // HORNETQ-1007
    @Test
    public void testMultiProtocolConsumers() throws Exception {
-      final int TIME_OUT = 5000;
+      final int TIME_OUT = 2000;
 
       int count = 1000;
 
@@ -1773,21 +1244,8 @@ public class StompTest extends StompTestBase {
       MessageConsumer consumer2 = session.createConsumer(topic);
 
       // connect and subscribe STOMP consumer
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-      frame = receiveFrame(TIME_OUT);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
-      frame = "SUBSCRIBE\n" + "destination:" +
-         getTopicPrefix() +
-         getTopicName() +
-         "\n" +
-         "receipt: 12\n" +
-         "\n\n" +
-         Stomp.NULL;
-      sendFrame(frame);
-      // wait for SUBSCRIBE's receipt
-      frame = receiveFrame(TIME_OUT);
-      Assert.assertTrue(frame.startsWith("RECEIPT"));
+      conn.connect(defUser, defPass);
+      subscribeTopic(conn, null, null, null, true);
 
       MessageProducer producer = session.createProducer(topic);
       TextMessage message = session.createTextMessage(getName());
@@ -1796,58 +1254,37 @@ public class StompTest extends StompTestBase {
          producer.send(message);
          Assert.assertNotNull(consumer1.receive(TIME_OUT));
          Assert.assertNotNull(consumer2.receive(TIME_OUT));
-         frame = receiveFrame(TIME_OUT);
-         Assert.assertTrue(frame.startsWith("MESSAGE"));
-         Assert.assertTrue(frame.indexOf("destination:") > 0);
-         Assert.assertTrue(frame.indexOf(getName()) > 0);
+         ClientStompFrame frame = conn.receiveFrame(TIME_OUT);
+         Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
+         Assert.assertEquals(getTopicPrefix() + getTopicName(), frame.getHeader(Stomp.Headers.Send.DESTINATION));
+         Assert.assertEquals(getName(), frame.getBody());
       }
 
       consumer1.close();
       consumer2.close();
-      frame = "UNSUBSCRIBE\n" + "destination:" +
-         getTopicPrefix() +
-         getTopicName() +
-         "\n" +
-         "receipt: 1234\n" +
-         "\n\n" +
-         Stomp.NULL;
-      sendFrame(frame);
-      // wait for UNSUBSCRIBE's receipt
-      frame = receiveFrame(TIME_OUT);
-      Assert.assertTrue(frame.startsWith("RECEIPT"));
-
-      sendMessage(getName(), topic);
-
-      frame = receiveFrame(TIME_OUT);
+      unsubscribe(conn, null, getTopicPrefix() + getTopicName(), true, false);
+
+      sendJmsMessage(getName(), topic);
+
+      ClientStompFrame frame = conn.receiveFrame(TIME_OUT);
       log.info("Received frame: " + frame);
       Assert.assertNull("No message should have been received since subscription was removed", frame);
 
-      frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      conn.disconnect();
    }
 
    @Test
    //stomp should return an ERROR when acking a non-existent message
    public void testUnexpectedAck() throws Exception {
-
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(100000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
-
       String messageID = "888888";
-      frame = "ACK\n" + "message-id:" + messageID + "\n" + "\n" + Stomp.NULL;
-      sendFrame(frame);
 
-      frame = receiveFrame(100000);
-      assertNotNull(frame);
+      conn.connect(defUser, defPass);
+      ack(conn, null, messageID, null);
 
-      System.out.println("received frame: " + frame);
-      assertTrue(frame.startsWith("ERROR"));
+      ClientStompFrame frame = conn.receiveFrame(1000);
+      assertNotNull(frame);
+      assertEquals(Stomp.Responses.ERROR, frame.getCommand());
 
-      frame = "DISCONNECT\n" + "\n\n" + Stomp.NULL;
-      sendFrame(frame);
+      conn.disconnect();
    }
-
 }


[11/11] activemq-artemis git commit: Implement STOMP destination prefixes

Posted by jb...@apache.org.
Implement STOMP destination prefixes


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

Branch: refs/heads/ARTEMIS-780
Commit: a25a8c4814c01c072e51cae52f0907a856deb5cd
Parents: 0371822
Author: jbertram <jb...@apache.com>
Authored: Fri Nov 11 13:12:38 2016 -0600
Committer: jbertram <jb...@apache.com>
Committed: Fri Nov 11 13:12:38 2016 -0600

----------------------------------------------------------------------
 .../remoting/impl/netty/TransportConstants.java |  10 ++
 .../core/protocol/stomp/StompConnection.java    |  36 ++++--
 .../stomp/VersionedStompFrameHandler.java       |  33 ++++-
 .../tests/integration/stomp/StompTest.java      | 126 ++++++++++++++++++-
 .../tests/integration/stomp/StompTestBase.java  |   1 +
 .../integration/stomp/v11/StompV11Test.java     |   2 +-
 6 files changed, 190 insertions(+), 18 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/a25a8c48/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 dfa2ce2..2007a21 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
@@ -203,6 +203,14 @@ public class TransportConstants {
 
    public static final String STOMP_MIN_LARGE_MESSAGE_SIZE = "stomp-min-large-message-size";
 
+   public static final String STOMP_ANYCAST_PREFIX = "stompAnycastPrefix";
+
+   public static final String DEFAULT_STOMP_ANYCAST_PREFIX = "";
+
+   public static final String STOMP_MULTICAST_PREFIX = "stompMulticastPrefix";
+
+   public static final String DEFAULT_STOMP_MULTICAST_PREFIX = "";
+
    public static final String NETTY_CONNECT_TIMEOUT = "connect-timeout-millis";
 
    public static final int DEFAULT_NETTY_CONNECT_TIMEOUT = -1;
@@ -242,6 +250,8 @@ public class TransportConstants {
       allowableAcceptorKeys.add(TransportConstants.CLUSTER_CONNECTION);
       allowableAcceptorKeys.add(TransportConstants.STOMP_CONSUMERS_CREDIT);
       allowableAcceptorKeys.add(TransportConstants.STOMP_MIN_LARGE_MESSAGE_SIZE);
+      allowableAcceptorKeys.add(TransportConstants.STOMP_ANYCAST_PREFIX);
+      allowableAcceptorKeys.add(TransportConstants.STOMP_MULTICAST_PREFIX);
       allowableAcceptorKeys.add(TransportConstants.CONNECTION_TTL);
       allowableAcceptorKeys.add(TransportConstants.CONNECTION_TTL_MAX);
       allowableAcceptorKeys.add(TransportConstants.CONNECTION_TTL_MIN);

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/a25a8c48/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/StompConnection.java
----------------------------------------------------------------------
diff --git a/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/StompConnection.java b/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/StompConnection.java
index b4ae1b5..a6eab6b 100644
--- a/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/StompConnection.java
+++ b/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/StompConnection.java
@@ -86,6 +86,12 @@ public final class StompConnection implements RemotingConnection {
 
    private final boolean enableMessageID;
 
+   private final int minLargeMessageSize;
+
+   private final String anycastPrefix;
+
+   private final String multicastPrefix;
+
    private StompVersions version;
 
    private VersionedStompFrameHandler frameHandler;
@@ -97,8 +103,6 @@ public final class StompConnection implements RemotingConnection {
 
    private final Object sendLock = new Object();
 
-   private final int minLargeMessageSize;
-
    private final ScheduledExecutorService scheduledExecutorService;
 
    private final ExecutorFactory factory;
@@ -161,6 +165,8 @@ public final class StompConnection implements RemotingConnection {
 
       this.enableMessageID = ConfigurationHelper.getBooleanProperty(TransportConstants.STOMP_ENABLE_MESSAGE_ID, false, acceptorUsed.getConfiguration());
       this.minLargeMessageSize = ConfigurationHelper.getIntProperty(TransportConstants.STOMP_MIN_LARGE_MESSAGE_SIZE, ActiveMQClient.DEFAULT_MIN_LARGE_MESSAGE_SIZE, acceptorUsed.getConfiguration());
+      this.anycastPrefix = ConfigurationHelper.getStringProperty(TransportConstants.STOMP_ANYCAST_PREFIX, TransportConstants.DEFAULT_STOMP_ANYCAST_PREFIX, acceptorUsed.getConfiguration());
+      this.multicastPrefix = ConfigurationHelper.getStringProperty(TransportConstants.STOMP_MULTICAST_PREFIX, TransportConstants.DEFAULT_STOMP_MULTICAST_PREFIX, acceptorUsed.getConfiguration());
    }
 
    @Override
@@ -252,12 +258,14 @@ public final class StompConnection implements RemotingConnection {
 
    public void autoCreateDestinationIfPossible(String queue, AddressInfo.RoutingType routingType) throws ActiveMQStompException {
       try {
-         // TODO check here to see if auto-creation is enabled
-         if (routingType == null || routingType.equals(AddressInfo.RoutingType.MULTICAST)) {
-            manager.getServer().createOrUpdateAddressInfo(new AddressInfo(SimpleString.toSimpleString(queue)).setAutoCreated(true));
-         } else {
-            manager.getServer().createOrUpdateAddressInfo(new AddressInfo(SimpleString.toSimpleString(queue)).setRoutingType(AddressInfo.RoutingType.ANYCAST));
-            manager.getServer().createQueue(SimpleString.toSimpleString(queue), SimpleString.toSimpleString(queue), null, null, true, false, true);
+         if (manager.getServer().getAddressInfo(SimpleString.toSimpleString(queue)) == null) {
+            // TODO check here to see if auto-creation is enabled
+            if (routingType.equals(AddressInfo.RoutingType.MULTICAST)) {
+               manager.getServer().createOrUpdateAddressInfo(new AddressInfo(SimpleString.toSimpleString(queue)).setAutoCreated(true));
+            } else {
+               manager.getServer().createOrUpdateAddressInfo(new AddressInfo(SimpleString.toSimpleString(queue)).setRoutingType(AddressInfo.RoutingType.ANYCAST).setAutoCreated(true));
+               manager.getServer().createQueue(SimpleString.toSimpleString(queue), SimpleString.toSimpleString(queue), null, null, true, false, true);
+            }
          }
       } catch (ActiveMQQueueExistsException e) {
          // ignore
@@ -561,7 +569,7 @@ public final class StompConnection implements RemotingConnection {
       if (stompSession.isNoLocal()) {
          message.putStringProperty(CONNECTION_ID_PROP, getID().toString());
       }
-      if (enableMessageID()) {
+      if (isEnableMessageID()) {
          message.putStringProperty("amqMessageId", "STOMP" + message.getMessageID());
       }
       try {
@@ -712,7 +720,7 @@ public final class StompConnection implements RemotingConnection {
       return this.frameHandler;
    }
 
-   public boolean enableMessageID() {
+   public boolean isEnableMessageID() {
       return enableMessageID;
    }
 
@@ -720,6 +728,14 @@ public final class StompConnection implements RemotingConnection {
       return minLargeMessageSize;
    }
 
+   public String getAnycastPrefix() {
+      return anycastPrefix;
+   }
+
+   public String getMulticastPrefix() {
+      return multicastPrefix;
+   }
+
    public StompProtocolManager getManager() {
       return manager;
    }

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/a25a8c48/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/VersionedStompFrameHandler.java
----------------------------------------------------------------------
diff --git a/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/VersionedStompFrameHandler.java b/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/VersionedStompFrameHandler.java
index cd3103b..06af785 100644
--- a/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/VersionedStompFrameHandler.java
+++ b/artemis-protocols/artemis-stomp-protocol/src/main/java/org/apache/activemq/artemis/core/protocol/stomp/VersionedStompFrameHandler.java
@@ -168,9 +168,8 @@ public abstract class VersionedStompFrameHandler {
       StompFrame response = null;
       try {
          connection.validate();
-         String destination = frame.getHeader(Stomp.Headers.Send.DESTINATION);
-         String destinationType = frame.getHeader(Headers.Send.DESTINATION_TYPE);
-         AddressInfo.RoutingType routingType = destinationType == null ? null : AddressInfo.RoutingType.valueOf(destinationType);
+         String destination = getDestination(frame);
+         AddressInfo.RoutingType routingType = getRoutingType(frame.getHeader(Headers.Send.DESTINATION_TYPE), frame.getHeader(Headers.Send.DESTINATION));
          connection.autoCreateDestinationIfPossible(destination, routingType);
          connection.checkDestination(destination);
          String txID = frame.getHeader(Stomp.Headers.TRANSACTION);
@@ -238,7 +237,7 @@ public abstract class VersionedStompFrameHandler {
 
    public StompFrame onSubscribe(StompFrame request) {
       StompFrame response = null;
-      String destination = request.getHeader(Stomp.Headers.Subscribe.DESTINATION);
+      String destination = getDestination(request);
 
       String selector = request.getHeader(Stomp.Headers.Subscribe.SELECTOR);
       String ack = request.getHeader(Stomp.Headers.Subscribe.ACK_MODE);
@@ -247,8 +246,7 @@ public abstract class VersionedStompFrameHandler {
       if (durableSubscriptionName == null) {
          durableSubscriptionName = request.getHeader(Stomp.Headers.Subscribe.DURABLE_SUBSCRIPTION_NAME);
       }
-      String subscriptionType = request.getHeader(Headers.Subscribe.SUBSCRIPTION_TYPE);
-      AddressInfo.RoutingType routingType = subscriptionType == null ? null : AddressInfo.RoutingType.valueOf(subscriptionType);
+      AddressInfo.RoutingType routingType = getRoutingType(request.getHeader(Headers.Subscribe.SUBSCRIPTION_TYPE), request.getHeader(Headers.Subscribe.DESTINATION));
       boolean noLocal = false;
 
       if (request.hasHeader(Stomp.Headers.Subscribe.NO_LOCAL)) {
@@ -264,6 +262,17 @@ public abstract class VersionedStompFrameHandler {
       return response;
    }
 
+   public String getDestination(StompFrame request) {
+      String destination = request.getHeader(Headers.Subscribe.DESTINATION);
+      if (connection.getMulticastPrefix().length() > 0 && destination.startsWith(connection.getMulticastPrefix())) {
+         destination = destination.substring(connection.getMulticastPrefix().length());
+      } else if (connection.getAnycastPrefix().length() > 0 && destination.startsWith(connection.getAnycastPrefix())) {
+         destination = destination.substring(connection.getAnycastPrefix().length());
+      }
+
+      return destination;
+   }
+
    public StompFrame postprocess(StompFrame request) {
       StompFrame response = null;
       if (request.hasHeader(Stomp.Headers.RECEIPT_REQUESTED)) {
@@ -334,4 +343,16 @@ public abstract class VersionedStompFrameHandler {
       connection.destroy();
    }
 
+   private AddressInfo.RoutingType getRoutingType(String typeHeader, String destination) {
+      AddressInfo.RoutingType routingType = AddressInfo.RoutingType.ANYCAST; // default
+      if (typeHeader != null) {
+         routingType = AddressInfo.RoutingType.valueOf(typeHeader);
+      } else if (destination != null && !connection.getAnycastPrefix().equals(connection.getMulticastPrefix())) {
+         if (connection.getMulticastPrefix().length() > 0 && destination.startsWith(connection.getMulticastPrefix())) {
+            routingType = AddressInfo.RoutingType.MULTICAST;
+         }
+      }
+      return routingType;
+   }
+
 }

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/a25a8c48/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTest.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTest.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTest.java
index 8e54b76..19e9ebe 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTest.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTest.java
@@ -25,6 +25,7 @@ import javax.jms.MessageProducer;
 import javax.jms.TextMessage;
 import java.io.ByteArrayOutputStream;
 import java.nio.charset.StandardCharsets;
+import java.util.UUID;
 import java.util.concurrent.CountDownLatch;
 import java.util.concurrent.TimeUnit;
 import java.util.regex.Matcher;
@@ -40,6 +41,7 @@ import org.apache.activemq.artemis.api.core.client.ServerLocator;
 import org.apache.activemq.artemis.api.jms.ActiveMQJMSClient;
 import org.apache.activemq.artemis.core.postoffice.impl.LocalQueueBinding;
 import org.apache.activemq.artemis.core.protocol.stomp.Stomp;
+import org.apache.activemq.artemis.core.protocol.stomp.StompProtocolManagerFactory;
 import org.apache.activemq.artemis.core.server.Queue;
 import org.apache.activemq.artemis.core.server.impl.ActiveMQServerImpl;
 import org.apache.activemq.artemis.core.server.impl.AddressInfo;
@@ -295,7 +297,7 @@ public class StompTest extends StompTestBase {
       conn.connect(defUser, defPass);
 
       // first send a message to ensure that sending to a non-existent topic won't throw an error
-      send(conn, getTopicPrefix() + nonExistentTopic, null, "Hello World", true);
+      send(conn, getTopicPrefix() + nonExistentTopic, null, "Hello World", true, AddressInfo.RoutingType.MULTICAST);
 
       // create a subscription on the topic and send/receive another message
       MessageConsumer consumer = session.createConsumer(ActiveMQJMSClient.createTopic(nonExistentTopic));
@@ -317,6 +319,7 @@ public class StompTest extends StompTestBase {
 
       // closing the consumer here should trigger auto-deletion of the subscription queue and address
       consumer.close();
+      Thread.sleep(200);
       assertNull(server.getActiveMQServer()
                        .getAddressInfo(new SimpleString(nonExistentTopic)));
    }
@@ -1248,4 +1251,125 @@ public class StompTest extends StompTestBase {
 
       conn.disconnect();
    }
+
+   @Test
+   public void testDotAnycastPrefixOnSend() throws Exception {
+      testPrefix("jms.queue.", AddressInfo.RoutingType.ANYCAST, true);
+   }
+
+   @Test
+   public void testDotMulticastPrefixOnSend() throws Exception {
+      testPrefix("jms.topic.", AddressInfo.RoutingType.MULTICAST, true);
+   }
+
+   @Test
+   public void testDotAnycastPrefixOnSubscribe() throws Exception {
+      testPrefix("jms.queue.", AddressInfo.RoutingType.ANYCAST, false);
+   }
+
+   @Test
+   public void testDotMulticastPrefixOnSubscribe() throws Exception {
+      testPrefix("jms.topic.", AddressInfo.RoutingType.MULTICAST, false);
+   }
+
+   @Test
+   public void testSlashAnycastPrefixOnSend() throws Exception {
+      testPrefix("/queue/", AddressInfo.RoutingType.ANYCAST, true);
+   }
+
+   @Test
+   public void testSlashMulticastPrefixOnSend() throws Exception {
+      testPrefix("/topic/", AddressInfo.RoutingType.MULTICAST, true);
+   }
+
+   @Test
+   public void testSlashAnycastPrefixOnSubscribe() throws Exception {
+      testPrefix("/queue/", AddressInfo.RoutingType.ANYCAST, false);
+   }
+
+   @Test
+   public void testSlashMulticastPrefixOnSubscribe() throws Exception {
+      testPrefix("/topic/", AddressInfo.RoutingType.MULTICAST, false);
+   }
+
+   public void testPrefix(final String prefix, final AddressInfo.RoutingType routingType, final boolean send) throws Exception {
+      int port = 61614;
+      final String ADDRESS = UUID.randomUUID().toString();
+      final String PREFIXED_ADDRESS = prefix + ADDRESS;
+      String param = routingType.toString();
+      String urlParam = "stomp" + param.substring(0, 1) + param.substring(1).toLowerCase() + "Prefix";
+      server.getActiveMQServer().getRemotingService().createAcceptor("test", "tcp://" + hostname + ":" + port + "?protocols=" + StompProtocolManagerFactory.STOMP_PROTOCOL_NAME + "&" + urlParam + "=" + prefix).start();
+      conn = StompClientConnectionFactory.createClientConnection("1.0", hostname, port);
+      conn.connect(defUser, defPass);
+
+      // since this queue doesn't exist the broker should create a new address using the routing type matching the prefix
+      if (send) {
+         send(conn, PREFIXED_ADDRESS, null, "Hello World", true);
+      } else {
+         String uuid = UUID.randomUUID().toString();
+
+         ClientStompFrame frame = conn.createFrame(Stomp.Commands.SUBSCRIBE)
+                                      .addHeader(Stomp.Headers.Subscribe.DESTINATION, PREFIXED_ADDRESS)
+                                      .addHeader(Stomp.Headers.RECEIPT_REQUESTED, uuid);
+
+         frame = conn.sendFrame(frame);
+
+         assertEquals(uuid, frame.getHeader(Stomp.Headers.Response.RECEIPT_ID));
+      }
+
+      AddressInfo addressInfo = server.getActiveMQServer().getAddressInfo(SimpleString.toSimpleString(ADDRESS));
+      assertNotNull("No address was created with the name " + ADDRESS, addressInfo);
+      assertEquals(AddressInfo.RoutingType.valueOf(param), addressInfo.getRoutingType());
+
+      conn.disconnect();
+   }
+
+   @Test
+   public void testDotPrefixedSendAndRecieveAnycast() throws Exception {
+      testPrefixedSendAndRecieve("jms.queue.", AddressInfo.RoutingType.ANYCAST);
+   }
+
+   @Test
+   public void testDotPrefixedSendAndRecieveMulticast() throws Exception {
+      testPrefixedSendAndRecieve("jms.topic.", AddressInfo.RoutingType.MULTICAST);
+   }
+
+   @Test
+   public void testSlashPrefixedSendAndRecieveAnycast() throws Exception {
+      testPrefixedSendAndRecieve("/queue/", AddressInfo.RoutingType.ANYCAST);
+   }
+
+   @Test
+   public void testSlashPrefixedSendAndRecieveMulticast() throws Exception {
+      testPrefixedSendAndRecieve("/topic/", AddressInfo.RoutingType.MULTICAST);
+   }
+
+   public void testPrefixedSendAndRecieve(final String prefix, AddressInfo.RoutingType routingType) throws Exception {
+      int port = 61614;
+      final String ADDRESS = UUID.randomUUID().toString();
+      final String PREFIXED_ADDRESS = prefix + ADDRESS;
+      String param = routingType.toString();
+      String urlParam = "stomp" + param.substring(0, 1) + param.substring(1).toLowerCase() + "Prefix";
+      server.getActiveMQServer().getRemotingService().createAcceptor("test", "tcp://" + hostname + ":" + port + "?protocols=" + StompProtocolManagerFactory.STOMP_PROTOCOL_NAME + "&" + urlParam + "=" + prefix).start();
+      conn = StompClientConnectionFactory.createClientConnection("1.0", hostname, port);
+      conn.connect(defUser, defPass);
+      String uuid = UUID.randomUUID().toString();
+
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SUBSCRIBE)
+                                   .addHeader(Stomp.Headers.Subscribe.DESTINATION, PREFIXED_ADDRESS)
+                                   .addHeader(Stomp.Headers.RECEIPT_REQUESTED, uuid);
+
+      frame = conn.sendFrame(frame);
+      assertEquals(uuid, frame.getHeader(Stomp.Headers.Response.RECEIPT_ID));
+
+      send(conn, ADDRESS, null, "Hello World", true);
+
+      frame = conn.receiveFrame(10000);
+      Assert.assertNotNull("Should have received a message", frame);
+      Assert.assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
+      Assert.assertEquals(ADDRESS, frame.getHeader(Stomp.Headers.Send.DESTINATION));
+      Assert.assertEquals("Hello World", frame.getBody());
+
+      conn.disconnect();
+   }
 }

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/a25a8c48/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestBase.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestBase.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestBase.java
index 3ccca7d..278d80e 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestBase.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestBase.java
@@ -414,6 +414,7 @@ public abstract class StompTestBase extends ActiveMQTestBase {
                                           boolean receipt,
                                           boolean noLocal) throws IOException, InterruptedException {
       ClientStompFrame frame = conn.createFrame(Stomp.Commands.SUBSCRIBE)
+                                   .addHeader(Stomp.Headers.Subscribe.SUBSCRIPTION_TYPE, AddressInfo.RoutingType.MULTICAST.toString())
                                    .addHeader(Stomp.Headers.Subscribe.DESTINATION, getTopicPrefix() + getTopicName());
       if (subscriptionId != null) {
          frame.addHeader(Stomp.Headers.Subscribe.ID, subscriptionId);

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/a25a8c48/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v11/StompV11Test.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v11/StompV11Test.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v11/StompV11Test.java
index e8a6f25..7cb02a3 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v11/StompV11Test.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v11/StompV11Test.java
@@ -2129,7 +2129,6 @@ public class StompV11Test extends StompTestBase {
 
    @Test
    public void testSendMessageToNonExistentQueueWithoutAutoCreation() throws Exception {
-      // TODO fix this test by checking auto-create settings
       AddressSettings addressSettings = new AddressSettings();
       addressSettings.setAutoCreateJmsQueues(false);
       server.getActiveMQServer().getAddressSettingsRepository().addMatch("#", addressSettings);
@@ -2139,6 +2138,7 @@ public class StompV11Test extends StompTestBase {
 
       ClientStompFrame frame = send(conn, "NonExistentQueue" + uuid, null, "Hello World", true, AddressInfo.RoutingType.ANYCAST);
 
+      // TODO fix this test by checking auto-create settings
       assertTrue(frame.getCommand().equals(Stomp.Responses.ERROR));
       IntegrationTestLogger.LOGGER.info("message: " + frame.getHeader("message"));
 


[05/11] activemq-artemis git commit: Stomp refactor + track autocreation for addresses

Posted by jb...@apache.org.
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompClientConnectionV10.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompClientConnectionV10.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompClientConnectionV10.java
index 7a1a529..d32823b 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompClientConnectionV10.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompClientConnectionV10.java
@@ -18,52 +18,47 @@ package org.apache.activemq.artemis.tests.integration.stomp.util;
 
 import java.io.IOException;
 
-/**
- * pls use factory to create frames.
- */
+import org.apache.activemq.artemis.core.protocol.stomp.Stomp;
+import org.apache.activemq.artemis.tests.integration.IntegrationTestLogger;
+
 public class StompClientConnectionV10 extends AbstractStompClientConnection {
 
    public StompClientConnectionV10(String host, int port) throws IOException {
       super("1.0", host, port);
    }
 
+   public StompClientConnectionV10(String version, String host, int port) throws IOException {
+      super(version, host, port);
+   }
+
    @Override
    public ClientStompFrame connect(String username, String passcode) throws IOException, InterruptedException {
-      ClientStompFrame frame = factory.newFrame(CONNECT_COMMAND);
-      frame.addHeader(LOGIN_HEADER, username);
-      frame.addHeader(PASSCODE_HEADER, passcode);
-
-      ClientStompFrame response = this.sendFrame(frame);
-
-      if (response.getCommand().equals(CONNECTED_COMMAND)) {
-         connected = true;
-      } else {
-         System.out.println("Connection failed with: " + response);
-         connected = false;
-      }
-      return response;
+      return connect(username, passcode, null);
    }
 
    @Override
-   public void connect(String username, String passcode, String clientID) throws IOException, InterruptedException {
-      ClientStompFrame frame = factory.newFrame(CONNECT_COMMAND);
-      frame.addHeader(LOGIN_HEADER, username);
-      frame.addHeader(PASSCODE_HEADER, passcode);
-      frame.addHeader(CLIENT_ID_HEADER, clientID);
+   public ClientStompFrame connect(String username, String passcode, String clientID) throws IOException, InterruptedException {
+      ClientStompFrame frame = factory.newFrame(Stomp.Commands.CONNECT);
+      frame.addHeader(Stomp.Headers.Connect.LOGIN, username);
+      frame.addHeader(Stomp.Headers.Connect.PASSCODE, passcode);
+      if (clientID != null) {
+         frame.addHeader(Stomp.Headers.Connect.CLIENT_ID, clientID);
+      }
 
       ClientStompFrame response = this.sendFrame(frame);
 
-      if (response.getCommand().equals(CONNECTED_COMMAND)) {
+      if (response.getCommand().equals(Stomp.Responses.CONNECTED)) {
          connected = true;
       } else {
-         System.out.println("Connection failed with: " + response);
+         IntegrationTestLogger.LOGGER.warn("Connection failed with: " + response);
          connected = false;
       }
+      return response;
    }
 
    @Override
    public void disconnect() throws IOException, InterruptedException {
-      ClientStompFrame frame = factory.newFrame(DISCONNECT_COMMAND);
+      ClientStompFrame frame = factory.newFrame(Stomp.Commands.DISCONNECT);
       this.sendFrame(frame);
 
       close();

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompClientConnectionV11.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompClientConnectionV11.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompClientConnectionV11.java
index aa07145..cfc8f92 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompClientConnectionV11.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompClientConnectionV11.java
@@ -17,55 +17,40 @@
 package org.apache.activemq.artemis.tests.integration.stomp.util;
 
 import java.io.IOException;
+import java.util.UUID;
 
-public class StompClientConnectionV11 extends AbstractStompClientConnection {
+import org.apache.activemq.artemis.core.protocol.stomp.Stomp;
+
+public class StompClientConnectionV11 extends StompClientConnectionV10 {
 
    public StompClientConnectionV11(String host, int port) throws IOException {
       super("1.1", host, port);
    }
 
-   @Override
-   public ClientStompFrame connect(String username, String passcode) throws IOException, InterruptedException {
-      ClientStompFrame frame = factory.newFrame(CONNECT_COMMAND);
-      frame.addHeader(ACCEPT_HEADER, "1.1");
-      frame.addHeader(HOST_HEADER, "localhost");
-      if (username != null) {
-         frame.addHeader(LOGIN_HEADER, username);
-         frame.addHeader(PASSCODE_HEADER, passcode);
-      }
-
-      ClientStompFrame response = this.sendFrame(frame);
-
-      if (response.getCommand().equals(CONNECTED_COMMAND)) {
-         String version = response.getHeader(VERSION_HEADER);
-         assert (version.equals("1.1"));
-
-         this.username = username;
-         this.passcode = passcode;
-         this.connected = true;
-      } else {
-         connected = false;
-      }
-      return response;
+   public StompClientConnectionV11(String version, String host, int port) throws IOException {
+      super(version, host, port);
    }
 
    @Override
-   public void connect(String username, String passcode, String clientID) throws IOException, InterruptedException {
-      ClientStompFrame frame = factory.newFrame(CONNECT_COMMAND);
-      frame.addHeader(ACCEPT_HEADER, "1.1");
-      frame.addHeader(HOST_HEADER, "localhost");
-      frame.addHeader(CLIENT_ID_HEADER, clientID);
+   public ClientStompFrame connect(String username, String passcode, String clientID) throws IOException, InterruptedException {
+      ClientStompFrame frame = factory.newFrame(Stomp.Commands.CONNECT);
+      frame.addHeader(Stomp.Headers.Connect.ACCEPT_VERSION, getVersion());
+      frame.addHeader(Stomp.Headers.Connect.HOST, "localhost");
+      if (clientID != null) {
+         frame.addHeader(Stomp.Headers.Connect.CLIENT_ID, clientID);
+      }
 
       if (username != null) {
-         frame.addHeader(LOGIN_HEADER, username);
-         frame.addHeader(PASSCODE_HEADER, passcode);
+         frame.addHeader(Stomp.Headers.Connect.LOGIN, username);
+         frame.addHeader(Stomp.Headers.Connect.PASSCODE, passcode);
       }
 
       ClientStompFrame response = this.sendFrame(frame);
 
-      if (response.getCommand().equals(CONNECTED_COMMAND)) {
-         String version = response.getHeader(VERSION_HEADER);
-         assert (version.equals("1.1"));
+      if (Stomp.Responses.CONNECTED.equals(response.getCommand())) {
+         String version = response.getHeader(Stomp.Headers.Connected.VERSION);
+         if (!version.equals(getVersion()))
+            throw new IllegalStateException("incorrect version!");
 
          this.username = username;
          this.passcode = passcode;
@@ -73,22 +58,24 @@ public class StompClientConnectionV11 extends AbstractStompClientConnection {
       } else {
          connected = false;
       }
+      return response;
    }
 
    public void connect1(String username, String passcode) throws IOException, InterruptedException {
-      ClientStompFrame frame = factory.newFrame(STOMP_COMMAND);
-      frame.addHeader(ACCEPT_HEADER, "1.0,1.1");
-      frame.addHeader(HOST_HEADER, "127.0.0.1");
+      ClientStompFrame frame = factory.newFrame(Stomp.Commands.STOMP);
+      frame.addHeader(Stomp.Headers.Connect.ACCEPT_VERSION, "1.0,1.1");
+      frame.addHeader(Stomp.Headers.Connect.HOST, "127.0.0.1");
       if (username != null) {
-         frame.addHeader(LOGIN_HEADER, username);
-         frame.addHeader(PASSCODE_HEADER, passcode);
+         frame.addHeader(Stomp.Headers.Connect.LOGIN, username);
+         frame.addHeader(Stomp.Headers.Connect.PASSCODE, passcode);
       }
 
       ClientStompFrame response = this.sendFrame(frame);
 
-      if (response.getCommand().equals(CONNECTED_COMMAND)) {
-         String version = response.getHeader(VERSION_HEADER);
-         assert (version.equals("1.1"));
+      if (Stomp.Responses.CONNECTED.equals(response.getCommand())) {
+         String version = response.getHeader(Stomp.Headers.Connected.VERSION);
+         if (!version.equals(getVersion()))
+            throw new IllegalStateException("incorrect version!");
 
          this.username = username;
          this.passcode = passcode;
@@ -103,12 +90,15 @@ public class StompClientConnectionV11 extends AbstractStompClientConnection {
    public void disconnect() throws IOException, InterruptedException {
       stopPinger();
 
-      ClientStompFrame frame = factory.newFrame(DISCONNECT_COMMAND);
-      frame.addHeader("receipt", "1");
+      ClientStompFrame frame = factory.newFrame(Stomp.Commands.DISCONNECT);
+
+      String uuid = UUID.randomUUID().toString();
+
+      frame.addHeader(Stomp.Headers.RECEIPT_REQUESTED, uuid);
 
       ClientStompFrame result = this.sendFrame(frame);
 
-      if (result == null || (!"RECEIPT".equals(result.getCommand())) || (!"1".equals(result.getHeader("receipt-id")))) {
+      if (result == null || (!Stomp.Responses.RECEIPT.equals(result.getCommand())) || (!uuid.equals(result.getHeader(Stomp.Headers.Response.RECEIPT_ID)))) {
          throw new IOException("Disconnect failed! " + result);
       }
 
@@ -122,4 +112,28 @@ public class StompClientConnectionV11 extends AbstractStompClientConnection {
       return factory.newFrame(command);
    }
 
+   @Override
+   public void startPinger(long interval) {
+      pinger = new Pinger(interval);
+      pinger.startPing();
+   }
+
+   @Override
+   public void stopPinger() {
+      if (pinger != null) {
+         pinger.stopPing();
+         try {
+            pinger.join();
+         } catch (InterruptedException e) {
+            e.printStackTrace();
+         }
+         pinger = null;
+      }
+   }
+
+   @Override
+   public int getServerPingNumber() {
+      return serverPingCounter;
+   }
+
 }

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompClientConnectionV12.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompClientConnectionV12.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompClientConnectionV12.java
index fb77832..2d8f354 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompClientConnectionV12.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompClientConnectionV12.java
@@ -18,90 +18,13 @@ package org.apache.activemq.artemis.tests.integration.stomp.util;
 
 import java.io.IOException;
 
-public class StompClientConnectionV12 extends AbstractStompClientConnection {
+public class StompClientConnectionV12 extends StompClientConnectionV11 {
 
    public StompClientConnectionV12(String host, int port) throws IOException {
       super("1.2", host, port);
    }
 
-   @Override
-   public ClientStompFrame createFrame(String command) {
-      return factory.newFrame(command);
-   }
-
-   @Override
-   public ClientStompFrame connect(String username, String passcode) throws IOException, InterruptedException {
-      ClientStompFrame frame = factory.newFrame(CONNECT_COMMAND);
-      frame.addHeader(ACCEPT_HEADER, "1.2");
-      frame.addHeader(HOST_HEADER, "localhost");
-      if (username != null) {
-         frame.addHeader(LOGIN_HEADER, username);
-         frame.addHeader(PASSCODE_HEADER, passcode);
-      }
-
-      ClientStompFrame response = this.sendFrame(frame);
-
-      if (response.getCommand().equals(CONNECTED_COMMAND)) {
-         String version = response.getHeader(VERSION_HEADER);
-         if (!version.equals("1.2"))
-            throw new IllegalStateException("incorrect version!");
-
-         this.username = username;
-         this.passcode = passcode;
-         this.connected = true;
-      } else {
-         connected = false;
-      }
-      return response;
-   }
-
-   @Override
-   public void disconnect() throws IOException, InterruptedException {
-      stopPinger();
-
-      ClientStompFrame frame = factory.newFrame(DISCONNECT_COMMAND);
-      frame.addHeader("receipt", "1");
-
-      ClientStompFrame result = this.sendFrame(frame);
-
-      if (result == null || (!"RECEIPT".equals(result.getCommand())) || (!"1".equals(result.getHeader("receipt-id")))) {
-         throw new IOException("Disconnect failed! " + result);
-      }
-
-      close();
-
-      connected = false;
-   }
-
-   @Override
-   public void connect(String username, String passcode, String clientID) throws Exception {
-      ClientStompFrame frame = factory.newFrame(CONNECT_COMMAND);
-      frame.addHeader(ACCEPT_HEADER, "1.2");
-      frame.addHeader(HOST_HEADER, "localhost");
-      frame.addHeader(CLIENT_ID_HEADER, clientID);
-
-      if (username != null) {
-         frame.addHeader(LOGIN_HEADER, username);
-         frame.addHeader(PASSCODE_HEADER, passcode);
-      }
-
-      ClientStompFrame response = this.sendFrame(frame);
-
-      if (response.getCommand().equals(CONNECTED_COMMAND)) {
-         String version = response.getHeader(VERSION_HEADER);
-         if (!version.equals("1.2"))
-            throw new IllegalStateException("incorrect version!");
-
-         this.username = username;
-         this.passcode = passcode;
-         this.connected = true;
-      } else {
-         connected = false;
-      }
-   }
-
    public ClientStompFrame createAnyFrame(String command) {
       return factory.newAnyFrame(command);
    }
-
 }

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactory.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactory.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactory.java
index 3ec03cf..1c78c5a 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactory.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactory.java
@@ -24,4 +24,6 @@ public interface StompFrameFactory {
 
    ClientStompFrame newAnyFrame(String command);
 
+   String[] handleHeaders(String header);
+
 }

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactoryV10.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactoryV10.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactoryV10.java
index 5ed8566..8813fd6 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactoryV10.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactoryV10.java
@@ -38,18 +38,18 @@ import java.util.StringTokenizer;
 public class StompFrameFactoryV10 implements StompFrameFactory {
 
    @Override
-   public ClientStompFrame createFrame(String data) {
+   public ClientStompFrame createFrame(final String data) {
       //split the string at "\n\n"
       String[] dataFields = data.split("\n\n");
 
       StringTokenizer tokenizer = new StringTokenizer(dataFields[0], "\n");
 
       String command = tokenizer.nextToken();
-      ClientStompFrame frame = new ClientStompFrameV10(command);
+      ClientStompFrame frame = newFrame(command);
 
       while (tokenizer.hasMoreTokens()) {
          String header = tokenizer.nextToken();
-         String[] fields = header.split(":");
+         String[] fields = handleHeaders(header);
          frame.addHeader(fields[0], fields[1]);
       }
 
@@ -61,6 +61,11 @@ public class StompFrameFactoryV10 implements StompFrameFactory {
    }
 
    @Override
+   public String[] handleHeaders(String header) {
+      return header.split(":");
+   }
+
+   @Override
    public ClientStompFrame newFrame(String command) {
       return new ClientStompFrameV10(command);
    }

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactoryV11.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactoryV11.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactoryV11.java
index 4de0d7d..807b3f0 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactoryV11.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactoryV11.java
@@ -36,32 +36,10 @@ import java.util.StringTokenizer;
  * 13. RECEIPT
  * 14. ERROR
  */
-public class StompFrameFactoryV11 implements StompFrameFactory {
+public class StompFrameFactoryV11 extends StompFrameFactoryV10 {
 
    @Override
-   public ClientStompFrame createFrame(final String data) {
-      //split the string at "\n\n"
-      String[] dataFields = data.split("\n\n");
-
-      StringTokenizer tokenizer = new StringTokenizer(dataFields[0], "\n");
-
-      String command = tokenizer.nextToken();
-      ClientStompFrame frame = new ClientStompFrameV11(command);
-
-      while (tokenizer.hasMoreTokens()) {
-         String header = tokenizer.nextToken();
-         String[] fields = splitAndDecodeHeader(header);
-         frame.addHeader(fields[0], fields[1]);
-      }
-
-      //body (without null byte)
-      if (dataFields.length == 2) {
-         frame.setBody(dataFields[1]);
-      }
-      return frame;
-   }
-
-   private String[] splitAndDecodeHeader(String header) {
+   public String[] handleHeaders(String header) {
       // split the header into the key and value at the ":" since there shouldn't be any unescaped colons in the header
       // except for the one separating the key and value
       String[] result = header.split(":");

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactoryV12.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactoryV12.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactoryV12.java
index 5223b4e..dbd32e0 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactoryV12.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompFrameFactoryV12.java
@@ -18,42 +18,10 @@ package org.apache.activemq.artemis.tests.integration.stomp.util;
 
 import java.util.StringTokenizer;
 
-public class StompFrameFactoryV12 implements StompFrameFactory {
+public class StompFrameFactoryV12 extends StompFrameFactoryV11 {
 
    @Override
-   public ClientStompFrame createFrame(String data) {
-      //split the string at "\n\n"
-      String[] dataFields = data.split("\n\n");
-
-      StringTokenizer tokenizer = new StringTokenizer(dataFields[0], "\n");
-
-      String command = tokenizer.nextToken();
-      ClientStompFrame frame = new ClientStompFrameV12(command);
-
-      while (tokenizer.hasMoreTokens()) {
-         String header = tokenizer.nextToken();
-         String[] fields = splitAndDecodeHeader(header);
-         frame.addHeader(fields[0], fields[1]);
-      }
-
-      //body (without null byte)
-      if (dataFields.length == 2) {
-         frame.setBody(dataFields[1]);
-      }
-      return frame;
-   }
-
-   public void printByteHeader(String headers) {
-      StringBuffer buffer = new StringBuffer();
-
-      for (int i = 0; i < headers.length(); i++) {
-         char c = headers.charAt(i);
-         buffer.append((byte) c + " ");
-      }
-      System.out.println("header in byte : " + buffer.toString());
-   }
-
-   private String[] splitAndDecodeHeader(String header) {
+   public String[] handleHeaders(String header) {
       // split the header into the key and value at the ":" since there shouldn't be any unescaped colons in the header
       // except for the one separating the key and value
       String[] result = header.split(":");

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v11/ExtraStompTest.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v11/ExtraStompTest.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v11/ExtraStompTest.java
index a5d3068..5414a9f 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v11/ExtraStompTest.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/v11/ExtraStompTest.java
@@ -18,6 +18,8 @@ package org.apache.activemq.artemis.tests.integration.stomp.v11;
 
 import java.nio.charset.StandardCharsets;
 
+import org.apache.activemq.artemis.core.protocol.stomp.Stomp;
+import org.apache.activemq.artemis.tests.integration.stomp.StompTestBase;
 import org.apache.activemq.artemis.tests.integration.stomp.util.ClientStompFrame;
 import org.apache.activemq.artemis.tests.integration.stomp.util.StompClientConnection;
 import org.apache.activemq.artemis.tests.integration.stomp.util.StompClientConnectionFactory;
@@ -28,15 +30,18 @@ import org.junit.Test;
 /*
  * Some Stomp tests against server with persistence enabled are put here.
  */
-public class ExtraStompTest extends StompV11TestBase {
+public class ExtraStompTest extends StompTestBase {
 
    private StompClientConnection connV10;
    private StompClientConnection connV11;
 
+   public boolean isPersistenceEnabled() {
+      return true;
+   }
+
    @Override
    @Before
    public void setUp() throws Exception {
-      persistenceEnabled = true;
       super.setUp();
       connV10 = StompClientConnectionFactory.createClientConnection("1.0", hostname, port);
       connV10.connect(defUser, defPass);
@@ -57,331 +62,142 @@ public class ExtraStompTest extends StompV11TestBase {
 
    @Test
    public void testSendAndReceive10() throws Exception {
-      String msg1 = "Hello World 1!";
-      String msg2 = "Hello World 2!";
-
-      ClientStompFrame frame = connV10.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-length", String.valueOf(msg1.getBytes(StandardCharsets.UTF_8).length));
-      frame.addHeader("persistent", "true");
-      frame.setBody(msg1);
-
-      connV10.sendFrame(frame);
-
-      ClientStompFrame frame2 = connV10.createFrame("SEND");
-      frame2.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame2.addHeader("content-length", String.valueOf(msg2.getBytes(StandardCharsets.UTF_8).length));
-      frame2.addHeader("persistent", "true");
-      frame2.setBody(msg2);
-
-      connV10.sendFrame(frame2);
-
-      ClientStompFrame subFrame = connV10.createFrame("SUBSCRIBE");
-      subFrame.addHeader("id", "a-sub");
-      subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-      subFrame.addHeader("ack", "auto");
-
-      connV10.sendFrame(subFrame);
-
-      frame = connV10.receiveFrame();
-
-      System.out.println("received " + frame);
-
-      assertEquals("MESSAGE", frame.getCommand());
-
-      assertEquals("a-sub", frame.getHeader("subscription"));
-
-      assertNotNull(frame.getHeader("message-id"));
-
-      assertEquals(getQueuePrefix() + getQueueName(), frame.getHeader("destination"));
-
-      assertEquals(msg1, frame.getBody());
-
-      frame = connV10.receiveFrame();
-
-      System.out.println("received " + frame);
-
-      assertEquals("MESSAGE", frame.getCommand());
-
-      assertEquals("a-sub", frame.getHeader("subscription"));
-
-      assertNotNull(frame.getHeader("message-id"));
-
-      assertEquals(getQueuePrefix() + getQueueName(), frame.getHeader("destination"));
-
-      assertEquals(msg2, frame.getBody());
-
-      //unsub
-      ClientStompFrame unsubFrame = connV10.createFrame("UNSUBSCRIBE");
-      unsubFrame.addHeader("id", "a-sub");
-      connV10.sendFrame(unsubFrame);
-
+      testSendAndReceive(connV10);
    }
 
    @Test
    public void testSendAndReceive11() throws Exception {
+      testSendAndReceive(connV11);
+   }
+
+   public void testSendAndReceive(StompClientConnection conn) throws Exception {
       String msg1 = "Hello World 1!";
       String msg2 = "Hello World 2!";
 
-      ClientStompFrame frame = connV11.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-length", String.valueOf(msg1.getBytes(StandardCharsets.UTF_8).length));
-      frame.addHeader("persistent", "true");
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SEND);
+      frame.addHeader(Stomp.Headers.Subscribe.DESTINATION, getQueuePrefix() + getQueueName());
+      frame.addHeader(Stomp.Headers.CONTENT_LENGTH, String.valueOf(msg1.getBytes(StandardCharsets.UTF_8).length));
+      frame.addHeader(Stomp.Headers.Send.PERSISTENT, Boolean.TRUE.toString());
       frame.setBody(msg1);
 
-      connV11.sendFrame(frame);
+      conn.sendFrame(frame);
 
-      ClientStompFrame frame2 = connV11.createFrame("SEND");
-      frame2.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame2.addHeader("content-length", String.valueOf(msg2.getBytes(StandardCharsets.UTF_8).length));
-      frame2.addHeader("persistent", "true");
+      ClientStompFrame frame2 = conn.createFrame(Stomp.Commands.SEND);
+      frame2.addHeader(Stomp.Headers.Subscribe.DESTINATION, getQueuePrefix() + getQueueName());
+      frame2.addHeader(Stomp.Headers.CONTENT_LENGTH, String.valueOf(msg2.getBytes(StandardCharsets.UTF_8).length));
+      frame2.addHeader(Stomp.Headers.Send.PERSISTENT, Boolean.TRUE.toString());
       frame2.setBody(msg2);
 
-      connV11.sendFrame(frame2);
-
-      ClientStompFrame subFrame = connV11.createFrame("SUBSCRIBE");
-      subFrame.addHeader("id", "a-sub");
-      subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-      subFrame.addHeader("ack", "auto");
-
-      connV11.sendFrame(subFrame);
-
-      frame = connV11.receiveFrame();
-
-      System.out.println("received " + frame);
-
-      assertEquals("MESSAGE", frame.getCommand());
+      conn.sendFrame(frame2);
 
-      assertEquals("a-sub", frame.getHeader("subscription"));
+      subscribe(conn, "a-sub");
 
-      assertNotNull(frame.getHeader("message-id"));
-
-      assertEquals(getQueuePrefix() + getQueueName(), frame.getHeader("destination"));
+      frame = conn.receiveFrame();
 
+      assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
+      assertEquals("a-sub", frame.getHeader(Stomp.Headers.Message.SUBSCRIPTION));
+      assertNotNull(frame.getHeader(Stomp.Headers.Message.MESSAGE_ID));
+      assertEquals(getQueuePrefix() + getQueueName(), frame.getHeader(Stomp.Headers.Subscribe.DESTINATION));
       assertEquals(msg1, frame.getBody());
 
-      frame = connV11.receiveFrame();
-
-      System.out.println("received " + frame);
-
-      assertEquals("MESSAGE", frame.getCommand());
-
-      assertEquals("a-sub", frame.getHeader("subscription"));
-
-      assertNotNull(frame.getHeader("message-id"));
-
-      assertEquals(getQueuePrefix() + getQueueName(), frame.getHeader("destination"));
+      frame = conn.receiveFrame();
 
+      assertEquals(Stomp.Responses.MESSAGE, frame.getCommand());
+      assertEquals("a-sub", frame.getHeader(Stomp.Headers.Message.SUBSCRIPTION));
+      assertNotNull(frame.getHeader(Stomp.Headers.Message.MESSAGE_ID));
+      assertEquals(getQueuePrefix() + getQueueName(), frame.getHeader(Stomp.Headers.Subscribe.DESTINATION));
       assertEquals(msg2, frame.getBody());
 
-      //unsub
-      ClientStompFrame unsubFrame = connV11.createFrame("UNSUBSCRIBE");
-      unsubFrame.addHeader("id", "a-sub");
-      connV11.sendFrame(unsubFrame);
+      unsubscribe(conn, "a-sub");
    }
 
    @Test
    public void testNoGarbageAfterPersistentMessageV10() throws Exception {
-      ClientStompFrame subFrame = connV10.createFrame("SUBSCRIBE");
-      subFrame.addHeader("id", "a-sub");
-      subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-      subFrame.addHeader("ack", "auto");
-
-      connV10.sendFrame(subFrame);
+      testNoGarbageAfterPersistentMessage(connV10);
+   }
 
-      ClientStompFrame frame = connV10.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-length", "11");
-      frame.addHeader("persistent", "true");
+   @Test
+   public void testNoGarbageAfterPersistentMessageV11() throws Exception {
+      testNoGarbageAfterPersistentMessage(connV11);
+   }   
+   
+   public void testNoGarbageAfterPersistentMessage(StompClientConnection conn) throws Exception {
+      subscribe(conn, "a-sub");
+
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SEND);
+      frame.addHeader(Stomp.Headers.Subscribe.DESTINATION, getQueuePrefix() + getQueueName());
+      frame.addHeader(Stomp.Headers.CONTENT_LENGTH, "11");
+      frame.addHeader(Stomp.Headers.Send.PERSISTENT, Boolean.TRUE.toString());
       frame.setBody("Hello World");
 
-      connV10.sendFrame(frame);
+      conn.sendFrame(frame);
 
-      frame = connV10.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-length", "11");
-      frame.addHeader("persistent", "true");
+      frame = conn.createFrame(Stomp.Commands.SEND);
+      frame.addHeader(Stomp.Headers.Subscribe.DESTINATION, getQueuePrefix() + getQueueName());
+      frame.addHeader(Stomp.Headers.CONTENT_LENGTH, "11");
+      frame.addHeader(Stomp.Headers.Send.PERSISTENT, Boolean.TRUE.toString());
       frame.setBody("Hello World");
 
-      connV10.sendFrame(frame);
-
-      frame = connV10.receiveFrame(10000);
+      conn.sendFrame(frame);
 
-      System.out.println("received: " + frame);
+      frame = conn.receiveFrame(10000);
 
       assertEquals("Hello World", frame.getBody());
 
       //if activemq sends trailing garbage bytes, the second message
       //will not be normal
-      frame = connV10.receiveFrame(10000);
-
-      System.out.println("received: " + frame);
+      frame = conn.receiveFrame(10000);
 
       assertEquals("Hello World", frame.getBody());
 
-      //unsub
-      ClientStompFrame unsubFrame = connV10.createFrame("UNSUBSCRIBE");
-      unsubFrame.addHeader("id", "a-sub");
-      connV10.sendFrame(unsubFrame);
-
+      unsubscribe(conn, "a-sub");
    }
 
    @Test
    public void testNoGarbageOnPersistentRedeliveryV10() throws Exception {
-
-      ClientStompFrame frame = connV10.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-length", "11");
-      frame.addHeader("persistent", "true");
-      frame.setBody("Hello World");
-
-      connV10.sendFrame(frame);
-
-      frame = connV10.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-length", "11");
-      frame.addHeader("persistent", "true");
-      frame.setBody("Hello World");
-
-      connV10.sendFrame(frame);
-
-      ClientStompFrame subFrame = connV10.createFrame("SUBSCRIBE");
-      subFrame.addHeader("id", "a-sub");
-      subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-      subFrame.addHeader("ack", "client");
-
-      connV10.sendFrame(subFrame);
-
-      // receive but don't ack
-      frame = connV10.receiveFrame(10000);
-      frame = connV10.receiveFrame(10000);
-
-      System.out.println("received: " + frame);
-
-      //unsub
-      ClientStompFrame unsubFrame = connV10.createFrame("UNSUBSCRIBE");
-      unsubFrame.addHeader("id", "a-sub");
-      connV10.sendFrame(unsubFrame);
-
-      subFrame = connV10.createFrame("SUBSCRIBE");
-      subFrame.addHeader("id", "a-sub");
-      subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-      subFrame.addHeader("ack", "auto");
-
-      connV10.sendFrame(subFrame);
-
-      frame = connV10.receiveFrame(10000);
-      frame = connV10.receiveFrame(10000);
-
-      //second receive will get problem if trailing bytes
-      assertEquals("Hello World", frame.getBody());
-
-      System.out.println("received again: " + frame);
-
-      //unsub
-      unsubFrame = connV10.createFrame("UNSUBSCRIBE");
-      unsubFrame.addHeader("id", "a-sub");
-      connV10.sendFrame(unsubFrame);
+      testNoGarbageOnPersistentRedelivery(connV10);
    }
 
    @Test
-   public void testNoGarbageAfterPersistentMessageV11() throws Exception {
-      ClientStompFrame subFrame = connV11.createFrame("SUBSCRIBE");
-      subFrame.addHeader("id", "a-sub");
-      subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-      subFrame.addHeader("ack", "auto");
-
-      connV11.sendFrame(subFrame);
-      ClientStompFrame frame = connV11.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-length", "11");
-      frame.addHeader("persistent", "true");
-      frame.setBody("Hello World");
-
-      connV11.sendFrame(frame);
-
-      frame = connV11.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-length", "11");
-      frame.addHeader("persistent", "true");
-      frame.setBody("Hello World");
-
-      connV11.sendFrame(frame);
-      frame = connV11.receiveFrame(10000);
-
-      System.out.println("received: " + frame);
-
-      assertEquals("Hello World", frame.getBody());
-
-      //if activemq sends trailing garbage bytes, the second message
-      //will not be normal
-      frame = connV11.receiveFrame(10000);
-
-      System.out.println("received: " + frame);
-
-      assertEquals("Hello World", frame.getBody());
-
-      //unsub
-      ClientStompFrame unsubFrame = connV11.createFrame("UNSUBSCRIBE");
-      unsubFrame.addHeader("id", "a-sub");
-      connV11.sendFrame(unsubFrame);
+   public void testNoGarbageOnPersistentRedeliveryV11() throws Exception {
+      testNoGarbageOnPersistentRedelivery(connV11);
    }
 
-   @Test
-   public void testNoGarbageOnPersistentRedeliveryV11() throws Exception {
-      ClientStompFrame frame = connV11.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-length", "11");
-      frame.addHeader("persistent", "true");
+   public void testNoGarbageOnPersistentRedelivery(StompClientConnection conn) throws Exception {
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SEND);
+      frame.addHeader(Stomp.Headers.Subscribe.DESTINATION, getQueuePrefix() + getQueueName());
+      frame.addHeader(Stomp.Headers.CONTENT_LENGTH, "11");
+      frame.addHeader(Stomp.Headers.Send.PERSISTENT, Boolean.TRUE.toString());
       frame.setBody("Hello World");
 
-      connV11.sendFrame(frame);
+      conn.sendFrame(frame);
 
-      frame = connV11.createFrame("SEND");
-      frame.addHeader("destination", getQueuePrefix() + getQueueName());
-      frame.addHeader("content-length", "11");
-      frame.addHeader("persistent", "true");
+      frame = conn.createFrame(Stomp.Commands.SEND);
+      frame.addHeader(Stomp.Headers.Subscribe.DESTINATION, getQueuePrefix() + getQueueName());
+      frame.addHeader(Stomp.Headers.CONTENT_LENGTH, "11");
+      frame.addHeader(Stomp.Headers.Send.PERSISTENT, Boolean.TRUE.toString());
       frame.setBody("Hello World");
 
-      connV11.sendFrame(frame);
-
-      ClientStompFrame subFrame = connV11.createFrame("SUBSCRIBE");
-      subFrame.addHeader("id", "a-sub");
-      subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-      subFrame.addHeader("ack", "client");
+      conn.sendFrame(frame);
 
-      connV11.sendFrame(subFrame);
+      subscribe(conn, "a-sub", Stomp.Headers.Subscribe.AckModeValues.CLIENT);
 
       // receive but don't ack
-      frame = connV11.receiveFrame(10000);
-      frame = connV11.receiveFrame(10000);
-
-      System.out.println("received: " + frame);
+      frame = conn.receiveFrame(10000);
+      frame = conn.receiveFrame(10000);
 
-      //unsub
-      ClientStompFrame unsubFrame = connV11.createFrame("UNSUBSCRIBE");
-      unsubFrame.addHeader("id", "a-sub");
-      connV11.sendFrame(unsubFrame);
-
-      subFrame = connV11.createFrame("SUBSCRIBE");
-      subFrame.addHeader("id", "a-sub");
-      subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
-      subFrame.addHeader("ack", "auto");
+      unsubscribe(conn, "a-sub");
 
-      connV11.sendFrame(subFrame);
+      subscribe(conn, "a-sub");
 
-      frame = connV11.receiveFrame(10000);
-      frame = connV11.receiveFrame(10000);
+      frame = conn.receiveFrame(10000);
+      frame = conn.receiveFrame(10000);
 
       //second receive will get problem if trailing bytes
       assertEquals("Hello World", frame.getBody());
 
-      System.out.println("received again: " + frame);
-
       //unsub
-      unsubFrame = connV11.createFrame("UNSUBSCRIBE");
-      unsubFrame.addHeader("id", "a-sub");
-      connV11.sendFrame(unsubFrame);
+      unsubscribe(conn, "a-sub");
    }
 
 }


[06/11] activemq-artemis git commit: Stomp refactor + track autocreation for addresses

Posted by jb...@apache.org.
http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestBase.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestBase.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestBase.java
index 26f2a2f..a55f471 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestBase.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestBase.java
@@ -26,34 +26,17 @@ import javax.jms.Session;
 import javax.jms.TextMessage;
 import javax.jms.Topic;
 import java.io.IOException;
-import java.net.Socket;
-import java.net.URISyntaxException;
 import java.nio.charset.StandardCharsets;
-import java.util.ArrayList;
 import java.util.HashMap;
 import java.util.HashSet;
 import java.util.List;
 import java.util.Map;
-import java.util.concurrent.ArrayBlockingQueue;
-import java.util.concurrent.BlockingQueue;
-import java.util.concurrent.TimeUnit;
-
-import io.netty.bootstrap.Bootstrap;
-import io.netty.buffer.ByteBuf;
-import io.netty.buffer.Unpooled;
-import io.netty.channel.Channel;
-import io.netty.channel.ChannelHandlerContext;
-import io.netty.channel.ChannelInitializer;
-import io.netty.channel.ChannelOption;
-import io.netty.channel.EventLoopGroup;
-import io.netty.channel.SimpleChannelInboundHandler;
-import io.netty.channel.nio.NioEventLoopGroup;
-import io.netty.channel.socket.SocketChannel;
-import io.netty.channel.socket.nio.NioSocketChannel;
-import io.netty.handler.codec.string.StringDecoder;
-import io.netty.handler.codec.string.StringEncoder;
+import java.util.UUID;
+
 import org.apache.activemq.artemis.api.core.TransportConfiguration;
 import org.apache.activemq.artemis.core.config.Configuration;
+import org.apache.activemq.artemis.core.protocol.mqtt.MQTTProtocolManagerFactory;
+import org.apache.activemq.artemis.core.protocol.stomp.Stomp;
 import org.apache.activemq.artemis.core.protocol.stomp.StompProtocolManagerFactory;
 import org.apache.activemq.artemis.core.registry.JndiBindingRegistry;
 import org.apache.activemq.artemis.core.remoting.impl.invm.InVMAcceptorFactory;
@@ -63,6 +46,7 @@ import org.apache.activemq.artemis.core.remoting.impl.netty.TransportConstants;
 import org.apache.activemq.artemis.core.security.Role;
 import org.apache.activemq.artemis.core.server.ActiveMQServer;
 import org.apache.activemq.artemis.core.server.ActiveMQServers;
+import org.apache.activemq.artemis.core.server.impl.AddressInfo;
 import org.apache.activemq.artemis.jms.client.ActiveMQConnectionFactory;
 import org.apache.activemq.artemis.jms.client.ActiveMQJMSConnectionFactory;
 import org.apache.activemq.artemis.jms.server.JMSServerManager;
@@ -73,13 +57,16 @@ import org.apache.activemq.artemis.jms.server.config.impl.TopicConfigurationImpl
 import org.apache.activemq.artemis.jms.server.impl.JMSServerManagerImpl;
 import org.apache.activemq.artemis.spi.core.security.ActiveMQJAASSecurityManager;
 import org.apache.activemq.artemis.tests.integration.IntegrationTestLogger;
+import org.apache.activemq.artemis.tests.integration.stomp.util.ClientStompFrame;
+import org.apache.activemq.artemis.tests.integration.stomp.util.StompClientConnection;
 import org.apache.activemq.artemis.tests.unit.util.InVMNamingContext;
 import org.apache.activemq.artemis.tests.util.ActiveMQTestBase;
-import org.junit.After;
 import org.junit.Before;
 
 public abstract class StompTestBase extends ActiveMQTestBase {
 
+   protected String hostname = "127.0.0.1";
+
    protected final int port = 61613;
 
    private ConnectionFactory connectionFactory;
@@ -98,98 +85,56 @@ public abstract class StompTestBase extends ActiveMQTestBase {
 
    protected String defPass = "wombats";
 
-   protected boolean autoCreateServer = true;
-
-   private List<Bootstrap> bootstraps = new ArrayList<>();
-
-   //   private Channel channel;
-
-   private List<BlockingQueue<String>> priorityQueues = new ArrayList<>();
-
-   private List<EventLoopGroup> groups = new ArrayList<>();
-
-   private List<Channel> channels = new ArrayList<>();
-
    // Implementation methods
    // -------------------------------------------------------------------------
-   @Override
-   @Before
-   public void setUp() throws Exception {
-      super.setUp();
-      if (autoCreateServer) {
-         server = createServer();
-         addServer(server.getActiveMQServer());
-         server.start();
-         connectionFactory = createConnectionFactory();
-         createBootstrap();
-
-         if (isSecurityEnabled()) {
-            connection = connectionFactory.createConnection("brianm", "wombats");
-         } else {
-            connection = connectionFactory.createConnection();
-         }
-         session = connection.createSession(false, Session.AUTO_ACKNOWLEDGE);
-         queue = session.createQueue(getQueueName());
-         topic = session.createTopic(getTopicName());
-         connection.start();
-      }
+   public boolean isCompressLargeMessages() {
+      return false;
    }
 
-   private void createBootstrap() {
-      createBootstrap(0, port);
+   public boolean isSecurityEnabled() {
+      return false;
    }
 
-   protected void createBootstrap(int port) {
-      createBootstrap(0, port);
+   public boolean isPersistenceEnabled() {
+      return false;
    }
 
-   protected void createBootstrap(final int index, int port) {
-      priorityQueues.add(index, new ArrayBlockingQueue<String>(1000));
-      groups.add(index, new NioEventLoopGroup());
-      bootstraps.add(index, new Bootstrap());
-      bootstraps.get(index).group(groups.get(index)).channel(NioSocketChannel.class).option(ChannelOption.TCP_NODELAY, true).handler(new ChannelInitializer<SocketChannel>() {
-         @Override
-         public void initChannel(SocketChannel ch) throws Exception {
-            addChannelHandlers(index, ch);
-         }
-      });
-
-      // Start the client.
-      try {
-         channels.add(index, bootstraps.get(index).connect("localhost", port).sync().channel());
-         handshake();
-      } catch (InterruptedException e) {
-         e.printStackTrace();  //To change body of catch statement use File | Settings | File Templates.
-      }
-
+   public boolean isEnableStompMessageId() {
+      return false;
    }
 
-   protected void handshake() throws InterruptedException {
+   public Integer getStompMinLargeMessageSize() {
+      return null;
    }
 
-   protected void addChannelHandlers(int index, SocketChannel ch) throws URISyntaxException {
-      ch.pipeline().addLast("decoder", new StringDecoder(StandardCharsets.UTF_8));
-      ch.pipeline().addLast("encoder", new StringEncoder(StandardCharsets.UTF_8));
-      ch.pipeline().addLast(new StompClientHandler(index));
+   public List<String> getIncomingInterceptors() {
+      return null;
    }
 
-   protected void setUpAfterServer() throws Exception {
-      setUpAfterServer(false);
+   public List<String> getOutgoingInterceptors() {
+      return null;
    }
 
-   protected void setUpAfterServer(boolean jmsCompressLarge) throws Exception {
+   @Override
+   @Before
+   public void setUp() throws Exception {
+      super.setUp();
+
+      server = createServer();
+       server.start();
       connectionFactory = createConnectionFactory();
-      ActiveMQConnectionFactory activeMQConnectionFactory = (ActiveMQConnectionFactory) connectionFactory;
 
-      activeMQConnectionFactory.setCompressLargeMessage(jmsCompressLarge);
-      createBootstrap();
+      ((ActiveMQConnectionFactory)connectionFactory).setCompressLargeMessage(isCompressLargeMessages());
 
-      connection = connectionFactory.createConnection();
-      connection.start();
+      if (isSecurityEnabled()) {
+         connection = connectionFactory.createConnection("brianm", "wombats");
+      } else {
+         connection = connectionFactory.createConnection();
+      }
       session = connection.createSession(false, Session.AUTO_ACKNOWLEDGE);
       queue = session.createQueue(getQueueName());
       topic = session.createTopic(getTopicName());
-
+      connection.start();
    }
 
    /**
@@ -198,14 +143,30 @@ public abstract class StompTestBase extends ActiveMQTestBase {
     */
    protected JMSServerManager createServer() throws Exception {
       Map<String, Object> params = new HashMap<>();
-      params.put(TransportConstants.PROTOCOLS_PROP_NAME, StompProtocolManagerFactory.STOMP_PROTOCOL_NAME);
+      params.put(TransportConstants.PROTOCOLS_PROP_NAME, StompProtocolManagerFactory.STOMP_PROTOCOL_NAME + ","  + MQTTProtocolManagerFactory.MQTT_PROTOCOL_NAME);
       params.put(TransportConstants.PORT_PROP_NAME, TransportConstants.DEFAULT_STOMP_PORT);
       params.put(TransportConstants.STOMP_CONSUMERS_CREDIT, "-1");
+      if (isEnableStompMessageId()) {
+         params.put(TransportConstants.STOMP_ENABLE_MESSAGE_ID, true);
+      }
+      if (getStompMinLargeMessageSize() != null) {
+         params.put(TransportConstants.STOMP_MIN_LARGE_MESSAGE_SIZE, 2048);
+      }
       TransportConfiguration stompTransport = new TransportConfiguration(NettyAcceptorFactory.class.getName(), params);
-      TransportConfiguration allTransport = new TransportConfiguration(NettyAcceptorFactory.class.getName());
 
-      Configuration config = createBasicConfig().setSecurityEnabled(isSecurityEnabled()).setPersistenceEnabled(true).addAcceptorConfiguration(stompTransport).addAcceptorConfiguration(new TransportConfiguration(InVMAcceptorFactory.class.getName()));
-      config.addAcceptorConfiguration(allTransport);
+      Configuration config = createBasicConfig().setSecurityEnabled(isSecurityEnabled())
+                                                .setPersistenceEnabled(isPersistenceEnabled())
+                                                .addAcceptorConfiguration(stompTransport)
+                                                .addAcceptorConfiguration(new TransportConfiguration(InVMAcceptorFactory.class.getName()))
+                                                .setConnectionTtlCheckInterval(500);
+
+      if (getIncomingInterceptors() != null) {
+         config.setIncomingInterceptorClassNames(getIncomingInterceptors());
+      }
+
+      if (getOutgoingInterceptors() != null) {
+         config.setOutgoingInterceptorClassNames(getOutgoingInterceptors());
+      }
 
       ActiveMQServer activeMQServer = addServer(ActiveMQServers.newActiveMQServer(config, defUser, defPass));
 
@@ -222,195 +183,348 @@ public abstract class StompTestBase extends ActiveMQTestBase {
       }
 
       JMSConfiguration jmsConfig = new JMSConfigurationImpl();
-      jmsConfig.getQueueConfigurations().add(new JMSQueueConfigurationImpl().setName(getQueueName()).setDurable(false).setBindings(getQueueName()));
+      jmsConfig.getQueueConfigurations().add(new JMSQueueConfigurationImpl().setName(getQueueName()).setBindings(getQueueName()));
       jmsConfig.getTopicConfigurations().add(new TopicConfigurationImpl().setName(getTopicName()).setBindings(getTopicName()));
       server = new JMSServerManagerImpl(activeMQServer, jmsConfig);
       server.setRegistry(new JndiBindingRegistry(new InVMNamingContext()));
       return server;
    }
 
-   @Override
-   @After
-   public void tearDown() throws Exception {
-      if (autoCreateServer) {
-         connection.close();
-
-         for (EventLoopGroup group : groups) {
-            if (group != null) {
-               for (Channel channel : channels) {
-                  channel.close();
-               }
-               group.shutdownGracefully(0, 5000, TimeUnit.MILLISECONDS);
-            }
-         }
-      }
-      super.tearDown();
+   protected ConnectionFactory createConnectionFactory() {
+      return new ActiveMQJMSConnectionFactory(false, new TransportConfiguration(InVMConnectorFactory.class.getName()));
    }
 
-   protected void cleanUp() throws Exception {
-      connection.close();
-      if (groups.get(0) != null) {
-         groups.get(0).shutdown();
-      }
+   protected String getQueueName() {
+      return "testQueue";
    }
 
-   protected void reconnect() throws Exception {
-      reconnect(0);
+   protected String getQueuePrefix() {
+      return "";
    }
 
-   protected void reconnect(long sleep) throws Exception {
-      groups.get(0).shutdown();
+   protected String getTopicName() {
+      return "testtopic";
+   }
 
-      if (sleep > 0) {
-         Thread.sleep(sleep);
-      }
+   protected String getTopicPrefix() {
+      return "";
+   }
 
-      createBootstrap();
+   public void sendJmsMessage(String msg) throws Exception {
+      sendJmsMessage(msg, queue);
    }
 
-   protected ConnectionFactory createConnectionFactory() {
-      return new ActiveMQJMSConnectionFactory(false, new TransportConfiguration(InVMConnectorFactory.class.getName()));
+   public void sendJmsMessage(String msg, Destination destination) throws Exception {
+      MessageProducer producer = session.createProducer(destination);
+      TextMessage message = session.createTextMessage(msg);
+      producer.send(message);
+      IntegrationTestLogger.LOGGER.info("Sent message from JMS client to: " + destination);
    }
 
-   protected Socket createSocket() throws IOException {
-      return new Socket("localhost", port);
+   public void sendJmsMessage(byte[] data, Destination destination) throws Exception {
+      sendJmsMessage(data, "foo", "xyz", destination);
    }
 
-   protected String getQueueName() {
-      return "test";
+   public void sendJmsMessage(String msg, String propertyName, String propertyValue) throws Exception {
+      sendJmsMessage(msg.getBytes(StandardCharsets.UTF_8), propertyName, propertyValue, queue);
    }
 
-   protected String getQueuePrefix() {
-      return "";
+   public void sendJmsMessage(byte[] data,
+                              String propertyName,
+                              String propertyValue,
+                              Destination destination) throws Exception {
+      MessageProducer producer = session.createProducer(destination);
+      BytesMessage message = session.createBytesMessage();
+      message.setStringProperty(propertyName, propertyValue);
+      message.writeBytes(data);
+      producer.send(message);
    }
 
-   protected String getTopicName() {
-      return "testtopic";
+   public void abortTransaction(StompClientConnection conn, String txID) throws IOException, InterruptedException {
+      ClientStompFrame abortFrame = conn.createFrame(Stomp.Commands.ABORT)
+                                        .addHeader(Stomp.Headers.TRANSACTION, txID);
+
+      conn.sendFrame(abortFrame);
    }
 
-   protected String getTopicPrefix() {
-      return "";
+   public void beginTransaction(StompClientConnection conn, String txID) throws IOException, InterruptedException {
+      ClientStompFrame beginFrame = conn.createFrame(Stomp.Commands.BEGIN)
+                                        .addHeader(Stomp.Headers.TRANSACTION, txID);
+
+      conn.sendFrame(beginFrame);
    }
 
-   protected void assertChannelClosed() throws InterruptedException {
-      assertChannelClosed(0);
+   public void commitTransaction(StompClientConnection conn, String txID) throws IOException, InterruptedException {
+      commitTransaction(conn, txID, false);
    }
 
-   protected void assertChannelClosed(int index) throws InterruptedException {
-      boolean closed = channels.get(index).closeFuture().await(5000);
-      assertTrue("channel not closed", closed);
+   public void commitTransaction(StompClientConnection conn,
+                                 String txID,
+                                 boolean receipt) throws IOException, InterruptedException {
+      ClientStompFrame beginFrame = conn.createFrame(Stomp.Commands.COMMIT)
+                                        .addHeader(Stomp.Headers.TRANSACTION, txID);
+      String uuid = UUID.randomUUID().toString();
+      if (receipt) {
+         beginFrame.addHeader(Stomp.Headers.RECEIPT_REQUESTED, uuid);
+      }
+      ClientStompFrame resp = conn.sendFrame(beginFrame);
+      if (receipt) {
+         assertEquals(uuid, resp.getHeader(Stomp.Headers.Response.RECEIPT_ID));
+      }
    }
 
-   public void sendFrame(String data) throws Exception {
-      IntegrationTestLogger.LOGGER.info("Sending: " + data);
-      sendFrame(0, data);
+   public void ack(StompClientConnection conn,
+                   String subscriptionId,
+                   ClientStompFrame messageIdFrame) throws IOException, InterruptedException {
+      String messageID = messageIdFrame.getHeader(Stomp.Headers.Message.MESSAGE_ID);
+
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.ACK)
+                                      .addHeader(Stomp.Headers.Message.MESSAGE_ID, messageID);
+
+      if (subscriptionId != null) {
+         frame.addHeader(Stomp.Headers.Ack.SUBSCRIPTION, subscriptionId);
+      }
+
+      ClientStompFrame response = conn.sendFrame(frame);
+      if (response != null) {
+         throw new IOException("failed to ack " + response);
+      }
    }
 
-   public void sendFrame(int index, String data) throws Exception {
-      channels.get(index).writeAndFlush(data);
+   public void ack(StompClientConnection conn,
+                   String subscriptionId,
+                   String mid,
+                   String txID) throws IOException, InterruptedException {
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.ACK)
+                                      .addHeader(Stomp.Headers.Ack.SUBSCRIPTION, subscriptionId)
+                                      .addHeader(Stomp.Headers.Message.MESSAGE_ID, mid);
+      if (txID != null) {
+         frame.addHeader(Stomp.Headers.TRANSACTION, txID);
+      }
+
+      conn.sendFrame(frame);
    }
 
-   public void sendFrame(byte[] data) throws Exception {
-      sendFrame(0, data);
+   public void nack(StompClientConnection conn, String subscriptionId, String messageId) throws IOException, InterruptedException {
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.NACK)
+                                      .addHeader(Stomp.Headers.Ack.SUBSCRIPTION, subscriptionId)
+                                      .addHeader(Stomp.Headers.Message.MESSAGE_ID, messageId);
+
+      conn.sendFrame(frame);
    }
 
-   public void sendFrame(int index, byte[] data) throws Exception {
-      ByteBuf buffer = Unpooled.buffer(data.length);
-      buffer.writeBytes(data);
-      channels.get(index).writeAndFlush(buffer);
+   public ClientStompFrame subscribe(StompClientConnection conn,
+                                     String subscriptionId) throws IOException, InterruptedException {
+      return subscribe(conn, subscriptionId, Stomp.Headers.Subscribe.AckModeValues.AUTO, null, null);
    }
 
-   public String receiveFrame(long timeOut) throws Exception {
-      return receiveFrame(0, timeOut);
+   public ClientStompFrame subscribe(StompClientConnection conn,
+                                     String subscriptionId,
+                                     String ack) throws IOException, InterruptedException {
+      return subscribe(conn, subscriptionId, ack, null, null);
    }
 
-   public String receiveFrame(int index, long timeOut) throws Exception {
-      String msg = priorityQueues.get(index).poll(timeOut, TimeUnit.MILLISECONDS);
-      return msg;
+   public ClientStompFrame subscribe(StompClientConnection conn,
+                                     String subscriptionId,
+                                     String ack,
+                                     String durableId) throws IOException, InterruptedException {
+      return subscribe(conn, subscriptionId, ack, durableId, null);
    }
 
-   public void sendMessage(String msg) throws Exception {
-      sendMessage(msg, queue);
+   public ClientStompFrame subscribe(StompClientConnection conn,
+                                     String subscriptionId,
+                                     String ack,
+                                     String durableId,
+                                     boolean receipt) throws IOException, InterruptedException {
+      return subscribe(conn, subscriptionId, ack, durableId, null, receipt);
    }
 
-   public void sendMessage(String msg, Destination destination) throws Exception {
-      MessageProducer producer = session.createProducer(destination);
-      TextMessage message = session.createTextMessage(msg);
-      producer.send(message);
+   public ClientStompFrame subscribe(StompClientConnection conn,
+                                     String subscriptionId,
+                                     String ack,
+                                     String durableId,
+                                     String selector) throws IOException, InterruptedException {
+      return subscribe(conn, subscriptionId, ack, durableId, selector, false);
    }
 
-   public void sendMessage(byte[] data, Destination destination) throws Exception {
-      sendMessage(data, "foo", "xyz", destination);
+   public ClientStompFrame subscribe(StompClientConnection conn,
+                                     String subscriptionId,
+                                     String ack,
+                                     String durableId,
+                                     String selector,
+                                     boolean receipt) throws IOException, InterruptedException {
+      return subscribe(conn, subscriptionId, ack, durableId, selector, getQueuePrefix() + getQueueName(), receipt);
    }
 
-   public void sendMessage(String msg, String propertyName, String propertyValue) throws Exception {
-      sendMessage(msg.getBytes(StandardCharsets.UTF_8), propertyName, propertyValue, queue);
+   public ClientStompFrame subscribe(StompClientConnection conn,
+                                     String subscriptionId,
+                                     String ack,
+                                     String durableId,
+                                     String selector,
+                                     String destination,
+                                     boolean receipt) throws IOException, InterruptedException {
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SUBSCRIBE)
+                                   .addHeader(Stomp.Headers.Subscribe.SUBSCRIPTION_TYPE, AddressInfo.RoutingType.ANYCAST.toString())
+                                   .addHeader(Stomp.Headers.Subscribe.DESTINATION, destination);
+      if (subscriptionId != null) {
+         frame.addHeader(Stomp.Headers.Subscribe.ID, subscriptionId);
+      }
+      if (ack != null) {
+         frame.addHeader(Stomp.Headers.Subscribe.ACK_MODE, ack);
+      }
+      if (durableId != null) {
+         frame.addHeader(Stomp.Headers.Subscribe.DURABLE_SUBSCRIPTION_NAME, durableId);
+      }
+      if (selector != null) {
+         frame.addHeader(Stomp.Headers.Subscribe.SELECTOR, selector);
+      }
+      String uuid = UUID.randomUUID().toString();
+      if (receipt) {
+         frame.addHeader(Stomp.Headers.RECEIPT_REQUESTED, uuid);
+      }
+
+      frame = conn.sendFrame(frame);
+
+      if (receipt) {
+         assertEquals(uuid, frame.getHeader(Stomp.Headers.Response.RECEIPT_ID));
+      }
+
+      return frame;
    }
 
-   public void sendMessage(byte[] data,
-                           String propertyName,
-                           String propertyValue,
-                           Destination destination) throws Exception {
-      MessageProducer producer = session.createProducer(destination);
-      BytesMessage message = session.createBytesMessage();
-      message.setStringProperty(propertyName, propertyValue);
-      message.writeBytes(data);
-      producer.send(message);
+   public ClientStompFrame subscribeTopic(StompClientConnection conn,
+                                          String subscriptionId,
+                                          String ack,
+                                          String durableId) throws IOException, InterruptedException {
+      return subscribeTopic(conn, subscriptionId, ack, durableId, false);
    }
 
-   protected void waitForReceipt() throws Exception {
-      String frame = receiveFrame(50000);
-      assertNotNull(frame);
-      assertTrue(frame.indexOf("RECEIPT") > -1);
+   public ClientStompFrame subscribeTopic(StompClientConnection conn,
+                                          String subscriptionId,
+                                          String ack,
+                                          String durableId,
+                                          boolean receipt) throws IOException, InterruptedException {
+      return subscribeTopic(conn, subscriptionId, ack, durableId, receipt, false);
    }
 
-   protected void waitForFrameToTakeEffect() throws InterruptedException {
-      // bit of a dirty hack :)
-      // another option would be to force some kind of receipt to be returned
-      // from the frame
-      Thread.sleep(500);
+   public ClientStompFrame subscribeTopic(StompClientConnection conn,
+                                          String subscriptionId,
+                                          String ack,
+                                          String durableId,
+                                          boolean receipt,
+                                          boolean noLocal) throws IOException, InterruptedException {
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SUBSCRIBE)
+                                   .addHeader(Stomp.Headers.Subscribe.DESTINATION, getTopicPrefix() + getTopicName());
+      if (subscriptionId != null) {
+         frame.addHeader(Stomp.Headers.Subscribe.ID, subscriptionId);
+      }
+      if (ack != null) {
+         frame.addHeader(Stomp.Headers.Subscribe.ACK_MODE, ack);
+      }
+      if (durableId != null) {
+         frame.addHeader(Stomp.Headers.Subscribe.DURABLE_SUBSCRIPTION_NAME, durableId);
+      }
+      String uuid = UUID.randomUUID().toString();
+      if (receipt) {
+         frame.addHeader(Stomp.Headers.RECEIPT_REQUESTED, uuid);
+      }
+      if (noLocal) {
+         frame.addHeader(Stomp.Headers.Subscribe.NO_LOCAL, "true");
+      }
+
+      frame = conn.sendFrame(frame);
+
+      if (receipt) {
+         assertNotNull("Requested receipt, but response is null", frame);
+         assertTrue(frame.getHeader(Stomp.Headers.Response.RECEIPT_ID).equals(uuid));
+      }
+
+      return frame;
    }
 
-   public boolean isSecurityEnabled() {
-      return false;
+   public ClientStompFrame unsubscribe(StompClientConnection conn, String subscriptionId) throws IOException, InterruptedException {
+      return unsubscribe(conn, subscriptionId, null, false, false);
    }
 
-   class StompClientHandler extends SimpleChannelInboundHandler<String> {
+   public ClientStompFrame unsubscribe(StompClientConnection conn,
+                                       String subscriptionId,
+                                       boolean receipt) throws IOException, InterruptedException {
+      return unsubscribe(conn, subscriptionId, null, receipt, false);
+   }
 
-      int index = 0;
+   public ClientStompFrame unsubscribe(StompClientConnection conn,
+                                       String subscriptionId,
+                                       String destination,
+                                       boolean receipt,
+                                       boolean durable) throws IOException, InterruptedException {
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.UNSUBSCRIBE);
+      if (durable && subscriptionId != null) {
+         frame.addHeader(Stomp.Headers.Unsubscribe.DURABLE_SUBSCRIPTION_NAME, subscriptionId);
+      } else if (!durable && subscriptionId != null) {
+         frame.addHeader(Stomp.Headers.Unsubscribe.ID, subscriptionId);
+      }
 
-      StompClientHandler(int index) {
-         this.index = index;
+      if (destination != null) {
+         frame.addHeader(Stomp.Headers.Unsubscribe.DESTINATION, destination);
       }
 
-      StringBuffer currentMessage = new StringBuffer("");
+      String uuid = UUID.randomUUID().toString();
 
-      @Override
-      protected void channelRead0(ChannelHandlerContext ctx, String msg) throws Exception {
-         currentMessage.append(msg);
-         String fullMessage = currentMessage.toString();
-         if (fullMessage.contains("\0\n")) {
-            int messageEnd = fullMessage.indexOf("\0\n");
-            String actualMessage = fullMessage.substring(0, messageEnd);
-            fullMessage = fullMessage.substring(messageEnd + 2);
-            currentMessage = new StringBuffer("");
-            BlockingQueue queue = priorityQueues.get(index);
-            if (queue == null) {
-               queue = new ArrayBlockingQueue(1000);
-               priorityQueues.add(index, queue);
-            }
-            queue.add(actualMessage);
-            if (fullMessage.length() > 0) {
-               channelRead(ctx, fullMessage);
-            }
-         }
+      if (receipt) {
+         frame.addHeader(Stomp.Headers.RECEIPT_REQUESTED, uuid);
       }
 
-      @Override
-      public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) throws Exception {
-         cause.printStackTrace();
-         ctx.close();
+      frame = conn.sendFrame(frame);
+
+      if (receipt) {
+         assertEquals(Stomp.Responses.RECEIPT, frame.getCommand());
+         assertEquals(uuid, frame.getHeader(Stomp.Headers.Response.RECEIPT_ID));
       }
+
+      return frame;
+   }
+
+   public ClientStompFrame send(StompClientConnection conn, String destination, String contentType, String body) throws IOException, InterruptedException {
+      return send(conn, destination, contentType, body, false);
    }
 
+   public ClientStompFrame send(StompClientConnection conn, String destination, String contentType, String body, boolean receipt) throws IOException, InterruptedException {
+      return send(conn, destination, contentType, body, receipt, null);
+   }
+
+   public ClientStompFrame send(StompClientConnection conn, String destination, String contentType, String body, boolean receipt, AddressInfo.RoutingType destinationType) throws IOException, InterruptedException {
+      return send(conn, destination, contentType, body, receipt, destinationType, null);
+   }
+
+   public ClientStompFrame send(StompClientConnection conn, String destination, String contentType, String body, boolean receipt, AddressInfo.RoutingType destinationType, String txId) throws IOException, InterruptedException {
+      ClientStompFrame frame = conn.createFrame(Stomp.Commands.SEND)
+                                   .addHeader(Stomp.Headers.Send.DESTINATION, destination)
+                                   .setBody(body);
+
+      if (contentType != null) {
+         frame.addHeader(Stomp.Headers.CONTENT_TYPE, contentType);
+      }
+
+      if (destinationType != null) {
+         frame.addHeader(Stomp.Headers.Send.DESTINATION_TYPE, destinationType.toString());
+      }
+
+      if (txId != null) {
+         frame.addHeader(Stomp.Headers.TRANSACTION, txId);
+      }
+
+      String uuid = UUID.randomUUID().toString();
+
+      if (receipt) {
+         frame.addHeader(Stomp.Headers.RECEIPT_REQUESTED, uuid);
+      }
+      frame = conn.sendFrame(frame);
+
+      if (receipt) {
+         assertEquals(Stomp.Responses.RECEIPT, frame.getCommand());
+         assertEquals(uuid, frame.getHeader(Stomp.Headers.Response.RECEIPT_ID));
+      }
+
+      return frame;
+   }
 }

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestWithInterceptors.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestWithInterceptors.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestWithInterceptors.java
new file mode 100644
index 0000000..9bb9bf2
--- /dev/null
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestWithInterceptors.java
@@ -0,0 +1,159 @@
+/**
+ * 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.tests.integration.stomp;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import org.apache.activemq.artemis.api.core.Interceptor;
+import org.apache.activemq.artemis.core.protocol.core.Packet;
+import org.apache.activemq.artemis.core.protocol.stomp.StompFrame;
+import org.apache.activemq.artemis.core.protocol.stomp.StompFrameInterceptor;
+import org.apache.activemq.artemis.spi.core.protocol.RemotingConnection;
+import org.apache.activemq.artemis.tests.integration.IntegrationTestLogger;
+import org.apache.activemq.artemis.tests.integration.stomp.util.ClientStompFrame;
+import org.apache.activemq.artemis.tests.integration.stomp.util.StompClientConnection;
+import org.apache.activemq.artemis.tests.integration.stomp.util.StompClientConnectionFactory;
+import org.junit.Assert;
+import org.junit.Test;
+
+public class StompTestWithInterceptors extends StompTestBase {
+
+   @Override
+   public List<String> getIncomingInterceptors() {
+      List<String> stompIncomingInterceptor = new ArrayList<>();
+      stompIncomingInterceptor.add("org.apache.activemq.artemis.tests.integration.stomp.StompTestWithInterceptors$MyIncomingStompFrameInterceptor");
+      stompIncomingInterceptor.add("org.apache.activemq.artemis.tests.integration.stomp.StompTestWithInterceptors$MyCoreInterceptor");
+
+      return stompIncomingInterceptor;
+   }
+
+   @Override
+   public List<String> getOutgoingInterceptors() {
+      List<String> stompOutgoingInterceptor = new ArrayList<>();
+      stompOutgoingInterceptor.add("org.apache.activemq.artemis.tests.integration.stomp.StompTestWithInterceptors$MyOutgoingStompFrameInterceptor");
+
+      return stompOutgoingInterceptor;
+   }
+
+   @Test
+   public void stompFrameInterceptor() throws Exception {
+      MyIncomingStompFrameInterceptor.incomingInterceptedFrames.clear();
+      MyOutgoingStompFrameInterceptor.outgoingInterceptedFrames.clear();
+
+      Thread.sleep(200);
+
+      // So we clear them here
+      MyCoreInterceptor.incomingInterceptedFrames.clear();
+
+      StompClientConnection conn = StompClientConnectionFactory.createClientConnection("1.0", hostname, port);
+      conn.connect(defUser, defPass);
+
+      ClientStompFrame subFrame = conn.createFrame("SUBSCRIBE");
+      subFrame.addHeader("subscription-type", "ANYCAST");
+      subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
+      subFrame.addHeader("ack", "auto");
+      conn.sendFrame(subFrame);
+
+      assertEquals(0, MyCoreInterceptor.incomingInterceptedFrames.size());
+      sendJmsMessage(getName());
+
+      // Something was supposed to be called on sendMessages
+      assertTrue("core interceptor is not working", MyCoreInterceptor.incomingInterceptedFrames.size() > 0);
+
+      conn.receiveFrame(10000);
+
+      ClientStompFrame frame = conn.createFrame("SEND");
+      frame.addHeader("destination", getQueuePrefix() + getQueueName());
+      frame.setBody("Hello World");
+      conn.sendFrame(frame);
+
+      conn.disconnect();
+
+      List<String> incomingCommands = new ArrayList<>(4);
+      incomingCommands.add("CONNECT");
+      incomingCommands.add("SUBSCRIBE");
+      incomingCommands.add("SEND");
+      incomingCommands.add("DISCONNECT");
+
+      List<String> outgoingCommands = new ArrayList<>(3);
+      outgoingCommands.add("CONNECTED");
+      outgoingCommands.add("MESSAGE");
+      outgoingCommands.add("MESSAGE");
+
+      long timeout = System.currentTimeMillis() + 1000;
+
+      // Things are async, giving some time to things arrive before we actually assert
+      while (MyIncomingStompFrameInterceptor.incomingInterceptedFrames.size() < 4 &&
+         MyOutgoingStompFrameInterceptor.outgoingInterceptedFrames.size() < 3 &&
+         timeout > System.currentTimeMillis()) {
+         Thread.sleep(10);
+      }
+
+      Assert.assertEquals(4, MyIncomingStompFrameInterceptor.incomingInterceptedFrames.size());
+      Assert.assertEquals(3, MyOutgoingStompFrameInterceptor.outgoingInterceptedFrames.size());
+
+      for (int i = 0; i < MyIncomingStompFrameInterceptor.incomingInterceptedFrames.size(); i++) {
+         Assert.assertEquals(incomingCommands.get(i), MyIncomingStompFrameInterceptor.incomingInterceptedFrames.get(i).getCommand());
+         Assert.assertEquals("incomingInterceptedVal", MyIncomingStompFrameInterceptor.incomingInterceptedFrames.get(i).getHeader("incomingInterceptedProp"));
+      }
+
+      for (int i = 0; i < MyOutgoingStompFrameInterceptor.outgoingInterceptedFrames.size(); i++) {
+         Assert.assertEquals(outgoingCommands.get(i), MyOutgoingStompFrameInterceptor.outgoingInterceptedFrames.get(i).getCommand());
+      }
+
+      Assert.assertEquals("incomingInterceptedVal", MyOutgoingStompFrameInterceptor.outgoingInterceptedFrames.get(2).getHeader("incomingInterceptedProp"));
+      Assert.assertEquals("outgoingInterceptedVal", MyOutgoingStompFrameInterceptor.outgoingInterceptedFrames.get(2).getHeader("outgoingInterceptedProp"));
+   }
+
+   public static class MyCoreInterceptor implements Interceptor {
+
+      static List<Packet> incomingInterceptedFrames = new ArrayList<>();
+
+      @Override
+      public boolean intercept(Packet packet, RemotingConnection connection) {
+         IntegrationTestLogger.LOGGER.info("Core intercepted: " + packet);
+         incomingInterceptedFrames.add(packet);
+         return true;
+      }
+   }
+
+   public static class MyIncomingStompFrameInterceptor implements StompFrameInterceptor {
+
+      static List<StompFrame> incomingInterceptedFrames = new ArrayList<>();
+
+      @Override
+      public boolean intercept(StompFrame stompFrame, RemotingConnection connection) {
+         incomingInterceptedFrames.add(stompFrame);
+         stompFrame.addHeader("incomingInterceptedProp", "incomingInterceptedVal");
+         return true;
+      }
+   }
+
+   public static class MyOutgoingStompFrameInterceptor implements StompFrameInterceptor {
+
+      static List<StompFrame> outgoingInterceptedFrames = new ArrayList<>();
+
+      @Override
+      public boolean intercept(StompFrame stompFrame, RemotingConnection connection) {
+         outgoingInterceptedFrames.add(stompFrame);
+         stompFrame.addHeader("outgoingInterceptedProp", "outgoingInterceptedVal");
+         return true;
+      }
+   }
+}

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestWithLargeMessages.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestWithLargeMessages.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestWithLargeMessages.java
new file mode 100644
index 0000000..929534f
--- /dev/null
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestWithLargeMessages.java
@@ -0,0 +1,438 @@
+/*
+ * 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.tests.integration.stomp;
+
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.Map;
+
+import org.apache.activemq.artemis.api.core.SimpleString;
+import org.apache.activemq.artemis.api.core.TransportConfiguration;
+import org.apache.activemq.artemis.api.core.client.ActiveMQClient;
+import org.apache.activemq.artemis.core.config.Configuration;
+import org.apache.activemq.artemis.core.protocol.stomp.StompProtocolManagerFactory;
+import org.apache.activemq.artemis.core.registry.JndiBindingRegistry;
+import org.apache.activemq.artemis.core.remoting.impl.invm.InVMAcceptorFactory;
+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.security.Role;
+import org.apache.activemq.artemis.core.server.ActiveMQServer;
+import org.apache.activemq.artemis.core.server.ActiveMQServers;
+import org.apache.activemq.artemis.jms.server.JMSServerManager;
+import org.apache.activemq.artemis.jms.server.config.JMSConfiguration;
+import org.apache.activemq.artemis.jms.server.config.impl.JMSConfigurationImpl;
+import org.apache.activemq.artemis.jms.server.config.impl.JMSQueueConfigurationImpl;
+import org.apache.activemq.artemis.jms.server.config.impl.TopicConfigurationImpl;
+import org.apache.activemq.artemis.jms.server.impl.JMSServerManagerImpl;
+import org.apache.activemq.artemis.spi.core.security.ActiveMQJAASSecurityManager;
+import org.apache.activemq.artemis.tests.integration.IntegrationTestLogger;
+import org.apache.activemq.artemis.tests.integration.largemessage.LargeMessageTestBase;
+import org.apache.activemq.artemis.tests.integration.stomp.util.ClientStompFrame;
+import org.apache.activemq.artemis.tests.integration.stomp.util.StompClientConnection;
+import org.apache.activemq.artemis.tests.integration.stomp.util.StompClientConnectionFactory;
+import org.apache.activemq.artemis.tests.unit.util.InVMNamingContext;
+import org.junit.Assert;
+import org.junit.Before;
+import org.junit.Test;
+
+public class StompTestWithLargeMessages extends StompTestBase {
+
+   @Override
+   @Before
+   public void setUp() throws Exception {
+      super.setUp();
+   }
+
+   @Override
+   public boolean isCompressLargeMessages() {
+      return true;
+   }
+
+   @Override
+   public boolean isPersistenceEnabled() {
+      return true;
+   }
+
+   @Override
+   public Integer getStompMinLargeMessageSize() {
+      return 2048;
+   }
+
+   //stomp sender -> large -> stomp receiver
+   @Test
+   public void testSendReceiveLargePersistentMessages() throws Exception {
+      StompClientConnection conn = StompClientConnectionFactory.createClientConnection("1.0", hostname, port);
+      conn.connect(defUser, defPass);
+
+      int count = 10;
+      int msgSize = 1024 * 1024;
+      char[] contents = new char[msgSize];
+      for (int i = 0; i < msgSize; i++) {
+         contents[i] = 'A';
+      }
+      String body = new String(contents);
+
+      for (int i = 0; i < count; i++) {
+         ClientStompFrame frame = conn.createFrame("SEND");
+         frame.addHeader("destination", getQueuePrefix() + getQueueName());
+         frame.addHeader("persistent", "true");
+         frame.setBody(body);
+         conn.sendFrame(frame);
+      }
+
+      ClientStompFrame subFrame = conn.createFrame("SUBSCRIBE");
+      subFrame.addHeader("subscription-type", "ANYCAST");
+      subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
+      subFrame.addHeader("ack", "auto");
+      conn.sendFrame(subFrame);
+
+      for (int i = 0; i < count; i++) {
+         ClientStompFrame frame = conn.receiveFrame(60000);
+         Assert.assertNotNull(frame);
+         System.out.println("part of frame: " + frame.getBody().substring(0, 200));
+         Assert.assertTrue(frame.getCommand().equals("MESSAGE"));
+         Assert.assertTrue(frame.getHeader("destination").equals(getQueuePrefix() + getQueueName()));
+         int index = frame.getBody().indexOf("AAAA");
+         assertEquals(msgSize, (frame.getBody().length() - index));
+      }
+
+      ClientStompFrame unsubFrame = conn.createFrame("UNSUBSCRIBE");
+      unsubFrame.addHeader("destination", getQueuePrefix() + getQueueName());
+      unsubFrame.addHeader("receipt", "567");
+      ClientStompFrame response = conn.sendFrame(unsubFrame);
+      assertNotNull(response);
+      assertNotNull(response.getCommand().equals("RECEIPT"));
+
+      conn.disconnect();
+   }
+
+   //core sender -> large -> stomp receiver
+   @Test
+   public void testReceiveLargePersistentMessagesFromCore() throws Exception {
+      StompClientConnection conn = StompClientConnectionFactory.createClientConnection("1.0", hostname, port);
+      conn.connect(defUser, defPass);
+
+      int msgSize = 3 * ActiveMQClient.DEFAULT_MIN_LARGE_MESSAGE_SIZE;
+      char[] contents = new char[msgSize];
+      for (int i = 0; i < msgSize; i++) {
+         contents[i] = 'B';
+      }
+      String msg = new String(contents);
+
+      int count = 10;
+      for (int i = 0; i < count; i++) {
+         this.sendJmsMessage(msg);
+      }
+
+      ClientStompFrame subFrame = conn.createFrame("SUBSCRIBE");
+      subFrame.addHeader("subscription-type", "ANYCAST");
+      subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
+      subFrame.addHeader("ack", "auto");
+      conn.sendFrame(subFrame);
+
+      for (int i = 0; i < count; i++) {
+         ClientStompFrame frame = conn.receiveFrame(60000);
+         Assert.assertNotNull(frame);
+         System.out.println("part of frame: " + frame.getBody().substring(0, 200));
+         Assert.assertTrue(frame.getCommand().equals("MESSAGE"));
+         Assert.assertTrue(frame.getHeader("destination").equals(getQueuePrefix() + getQueueName()));
+         int index = frame.getBody().indexOf("BBB");
+         assertEquals(msgSize, (frame.getBody().length() - index));
+      }
+
+      ClientStompFrame unsubFrame = conn.createFrame("UNSUBSCRIBE");
+      unsubFrame.addHeader("destination", getQueuePrefix() + getQueueName());
+      unsubFrame.addHeader("receipt", "567");
+      ClientStompFrame response = conn.sendFrame(unsubFrame);
+      assertNotNull(response);
+      assertNotNull(response.getCommand().equals("RECEIPT"));
+
+      conn.disconnect();
+   }
+
+   //stomp v12 sender -> large -> stomp v12 receiver
+   @Test
+   public void testSendReceiveLargePersistentMessagesV12() throws Exception {
+      StompClientConnection connV12 = StompClientConnectionFactory.createClientConnection("1.2", "localhost", port);
+      connV12.connect(defUser, defPass);
+
+      int count = 10;
+      int szBody = 1024 * 1024;
+      char[] contents = new char[szBody];
+      for (int i = 0; i < szBody; i++) {
+         contents[i] = 'A';
+      }
+      String body = new String(contents);
+
+      ClientStompFrame frame = connV12.createFrame("SEND");
+      frame.addHeader("destination-type", "ANYCAST");
+      frame.addHeader("destination", getQueuePrefix() + getQueueName());
+      frame.addHeader("persistent", "true");
+      frame.setBody(body);
+
+      for (int i = 0; i < count; i++) {
+         connV12.sendFrame(frame);
+      }
+
+      ClientStompFrame subFrame = connV12.createFrame("SUBSCRIBE");
+      subFrame.addHeader("id", "a-sub");
+      subFrame.addHeader("subscription-type", "ANYCAST");
+      subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
+      subFrame.addHeader("ack", "auto");
+
+      connV12.sendFrame(subFrame);
+
+      for (int i = 0; i < count; i++) {
+         ClientStompFrame receiveFrame = connV12.receiveFrame(30000);
+
+         Assert.assertNotNull(receiveFrame);
+         System.out.println("part of frame: " + receiveFrame.getBody().substring(0, 20));
+         Assert.assertTrue(receiveFrame.getCommand().equals("MESSAGE"));
+         Assert.assertEquals(receiveFrame.getHeader("destination"), getQueuePrefix() + getQueueName());
+         assertEquals(szBody, receiveFrame.getBody().length());
+      }
+
+      // remove susbcription
+      ClientStompFrame unsubFrame = connV12.createFrame("UNSUBSCRIBE");
+      unsubFrame.addHeader("id", "a-sub");
+      connV12.sendFrame(unsubFrame);
+
+      connV12.disconnect();
+   }
+
+   //core sender -> large -> stomp v12 receiver
+   @Test
+   public void testReceiveLargePersistentMessagesFromCoreV12() throws Exception {
+      int msgSize = 3 * ActiveMQClient.DEFAULT_MIN_LARGE_MESSAGE_SIZE;
+      char[] contents = new char[msgSize];
+      for (int i = 0; i < msgSize; i++) {
+         contents[i] = 'B';
+      }
+      String msg = new String(contents);
+
+      int count = 10;
+      for (int i = 0; i < count; i++) {
+         this.sendJmsMessage(msg);
+      }
+
+      StompClientConnection connV12 = StompClientConnectionFactory.createClientConnection("1.2", "localhost", port);
+      connV12.connect(defUser, defPass);
+
+      ClientStompFrame subFrame = connV12.createFrame("SUBSCRIBE");
+      subFrame.addHeader("id", "a-sub");
+      subFrame.addHeader("subscription-type", "ANYCAST");
+      subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
+      subFrame.addHeader("ack", "auto");
+      connV12.sendFrame(subFrame);
+
+      for (int i = 0; i < count; i++) {
+         ClientStompFrame receiveFrame = connV12.receiveFrame(30000);
+
+         Assert.assertNotNull(receiveFrame);
+         System.out.println("part of frame: " + receiveFrame.getBody().substring(0, 20));
+         Assert.assertTrue(receiveFrame.getCommand().equals("MESSAGE"));
+         Assert.assertEquals(receiveFrame.getHeader("destination"), getQueuePrefix() + getQueueName());
+         assertEquals(msgSize, receiveFrame.getBody().length());
+      }
+
+      // remove susbcription
+      ClientStompFrame unsubFrame = connV12.createFrame("UNSUBSCRIBE");
+      unsubFrame.addHeader("id", "a-sub");
+      connV12.sendFrame(unsubFrame);
+
+      connV12.disconnect();
+   }
+
+   //core sender -> large (compressed regular) -> stomp v10 receiver
+   @Test
+   public void testReceiveLargeCompressedToRegularPersistentMessagesFromCore() throws Exception {
+      StompClientConnection conn = StompClientConnectionFactory.createClientConnection("1.0", hostname, port);
+      conn.connect(defUser, defPass);
+
+      LargeMessageTestBase.TestLargeMessageInputStream input = new LargeMessageTestBase.TestLargeMessageInputStream(ActiveMQClient.DEFAULT_MIN_LARGE_MESSAGE_SIZE, true);
+      LargeMessageTestBase.adjustLargeCompression(true, input, ActiveMQClient.DEFAULT_MIN_LARGE_MESSAGE_SIZE);
+
+      char[] contents = input.toArray();
+      String msg = new String(contents);
+
+      String leadingPart = msg.substring(0, 100);
+
+      int count = 10;
+      for (int i = 0; i < count; i++) {
+         this.sendJmsMessage(msg);
+      }
+
+      ClientStompFrame subFrame = conn.createFrame("SUBSCRIBE");
+      subFrame.addHeader("subscription-type", "ANYCAST");
+      subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
+      subFrame.addHeader("ack", "auto");
+      conn.sendFrame(subFrame);
+
+      for (int i = 0; i < count; i++) {
+         ClientStompFrame receiveFrame = conn.receiveFrame(30000);
+         Assert.assertNotNull(receiveFrame);
+         System.out.println("part of frame: " + receiveFrame.getBody().substring(0, 250));
+         Assert.assertTrue(receiveFrame.getCommand().equals("MESSAGE"));
+         Assert.assertEquals(receiveFrame.getHeader("destination"), getQueuePrefix() + getQueueName());
+         int index = receiveFrame.getBody().indexOf(leadingPart);
+         assertEquals(msg.length(), (receiveFrame.getBody().length() - index));
+      }
+
+      // remove suscription
+      ClientStompFrame unsubFrame = conn.createFrame("UNSUBSCRIBE");
+      unsubFrame.addHeader("destination", getQueuePrefix() + getQueueName());
+      unsubFrame.addHeader("receipt", "567");
+      ClientStompFrame response = conn.sendFrame(unsubFrame);
+      assertNotNull(response);
+      assertNotNull(response.getCommand().equals("RECEIPT"));
+
+      conn.disconnect();
+   }
+
+   //core sender -> large (compressed regular) -> stomp v12 receiver
+   @Test
+   public void testReceiveLargeCompressedToRegularPersistentMessagesFromCoreV12() throws Exception {
+      LargeMessageTestBase.TestLargeMessageInputStream input = new LargeMessageTestBase.TestLargeMessageInputStream(ActiveMQClient.DEFAULT_MIN_LARGE_MESSAGE_SIZE, true);
+      LargeMessageTestBase.adjustLargeCompression(true, input, ActiveMQClient.DEFAULT_MIN_LARGE_MESSAGE_SIZE);
+
+      char[] contents = input.toArray();
+      String msg = new String(contents);
+
+      int count = 10;
+      for (int i = 0; i < count; i++) {
+         this.sendJmsMessage(msg);
+      }
+
+      StompClientConnection connV12 = StompClientConnectionFactory.createClientConnection("1.2", "localhost", port);
+      connV12.connect(defUser, defPass);
+
+      ClientStompFrame subFrame = connV12.createFrame("SUBSCRIBE");
+      subFrame.addHeader("id", "a-sub");
+      subFrame.addHeader("subscription-type", "ANYCAST");
+      subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
+      subFrame.addHeader("ack", "auto");
+
+      connV12.sendFrame(subFrame);
+
+      for (int i = 0; i < count; i++) {
+         ClientStompFrame receiveFrame = connV12.receiveFrame(30000);
+
+         Assert.assertNotNull(receiveFrame);
+         System.out.println("part of frame: " + receiveFrame.getBody().substring(0, 20));
+         Assert.assertTrue(receiveFrame.getCommand().equals("MESSAGE"));
+         Assert.assertEquals(receiveFrame.getHeader("destination"), getQueuePrefix() + getQueueName());
+         assertEquals(contents.length, receiveFrame.getBody().length());
+      }
+
+      // remove susbcription
+      ClientStompFrame unsubFrame = connV12.createFrame("UNSUBSCRIBE");
+      unsubFrame.addHeader("id", "a-sub");
+      connV12.sendFrame(unsubFrame);
+
+      connV12.disconnect();
+   }
+
+   //core sender -> large (compressed large) -> stomp v12 receiver
+   @Test
+   public void testReceiveLargeCompressedToLargePersistentMessagesFromCoreV12() throws Exception {
+      LargeMessageTestBase.TestLargeMessageInputStream input = new LargeMessageTestBase.TestLargeMessageInputStream(ActiveMQClient.DEFAULT_MIN_LARGE_MESSAGE_SIZE, true);
+      input.setSize(10 * ActiveMQClient.DEFAULT_MIN_LARGE_MESSAGE_SIZE);
+      LargeMessageTestBase.adjustLargeCompression(false, input, 10 * ActiveMQClient.DEFAULT_MIN_LARGE_MESSAGE_SIZE);
+
+      char[] contents = input.toArray();
+      String msg = new String(contents);
+
+      int count = 10;
+      for (int i = 0; i < count; i++) {
+         this.sendJmsMessage(msg);
+      }
+
+      IntegrationTestLogger.LOGGER.info("Message count for " + getQueueName() + ": " + server.getActiveMQServer().locateQueue(SimpleString.toSimpleString(getQueueName())).getMessageCount());
+
+      StompClientConnection connV12 = StompClientConnectionFactory.createClientConnection("1.2", hostname, port);
+      connV12.connect(defUser, defPass);
+
+      ClientStompFrame subFrame = connV12.createFrame("SUBSCRIBE");
+      subFrame.addHeader("id", "a-sub");
+      subFrame.addHeader("subscription-type", "ANYCAST");
+      subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
+      subFrame.addHeader("ack", "auto");
+
+      connV12.sendFrame(subFrame);
+
+      for (int i = 0; i < count; i++) {
+         ClientStompFrame receiveFrame = connV12.receiveFrame(30000);
+
+         Assert.assertNotNull(receiveFrame);
+         System.out.println("part of frame: " + receiveFrame.getBody().substring(0, 20));
+         Assert.assertTrue(receiveFrame.getCommand().equals("MESSAGE"));
+         Assert.assertEquals(receiveFrame.getHeader("destination"), getQueuePrefix() + getQueueName());
+         assertEquals(contents.length, receiveFrame.getBody().length());
+      }
+
+      // remove susbcription
+      ClientStompFrame unsubFrame = connV12.createFrame("UNSUBSCRIBE");
+      unsubFrame.addHeader("id", "a-sub");
+      connV12.sendFrame(unsubFrame);
+
+      connV12.disconnect();
+   }
+
+   //core sender -> large (compressed large) -> stomp v10 receiver
+   @Test
+   public void testReceiveLargeCompressedToLargePersistentMessagesFromCore() throws Exception {
+      LargeMessageTestBase.TestLargeMessageInputStream input = new LargeMessageTestBase.TestLargeMessageInputStream(ActiveMQClient.DEFAULT_MIN_LARGE_MESSAGE_SIZE, true);
+      input.setSize(10 * ActiveMQClient.DEFAULT_MIN_LARGE_MESSAGE_SIZE);
+      LargeMessageTestBase.adjustLargeCompression(false, input, 10 * ActiveMQClient.DEFAULT_MIN_LARGE_MESSAGE_SIZE);
+
+      char[] contents = input.toArray();
+      String msg = new String(contents);
+
+      String leadingPart = msg.substring(0, 100);
+
+      int count = 10;
+      for (int i = 0; i < count; i++) {
+         this.sendJmsMessage(msg);
+      }
+
+      StompClientConnection conn = StompClientConnectionFactory.createClientConnection("1.0", hostname, port);
+      conn.connect(defUser, defPass);
+
+      ClientStompFrame subFrame = conn.createFrame("SUBSCRIBE");
+      subFrame.addHeader("subscription-type", "ANYCAST");
+      subFrame.addHeader("destination", getQueuePrefix() + getQueueName());
+      subFrame.addHeader("ack", "auto");
+      conn.sendFrame(subFrame);
+
+      for (int i = 0; i < count; i++) {
+         ClientStompFrame frame = conn.receiveFrame(60000);
+         Assert.assertNotNull(frame);
+         System.out.println("part of frame: " + frame.getBody().substring(0, 250));
+         Assert.assertTrue(frame.getCommand().equals("MESSAGE"));
+         Assert.assertTrue(frame.getHeader("destination").equals(getQueuePrefix() + getQueueName()));
+         int index = frame.getBody().toString().indexOf(leadingPart);
+         assertEquals(msg.length(), (frame.getBody().toString().length() - index));
+      }
+
+      ClientStompFrame unsubFrame = conn.createFrame("UNSUBSCRIBE");
+      unsubFrame.addHeader("destination", getQueuePrefix() + getQueueName());
+      unsubFrame.addHeader("receipt", "567");
+      conn.sendFrame(unsubFrame);
+
+      conn.disconnect();
+   }
+}

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestWithMessageID.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestWithMessageID.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestWithMessageID.java
new file mode 100644
index 0000000..fc44437
--- /dev/null
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestWithMessageID.java
@@ -0,0 +1,77 @@
+/**
+ * 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.tests.integration.stomp;
+
+import javax.jms.Message;
+import javax.jms.MessageConsumer;
+import javax.jms.QueueBrowser;
+import javax.jms.TextMessage;
+import java.util.Enumeration;
+
+import org.apache.activemq.artemis.tests.integration.stomp.util.ClientStompFrame;
+import org.apache.activemq.artemis.tests.integration.stomp.util.StompClientConnection;
+import org.apache.activemq.artemis.tests.integration.stomp.util.StompClientConnectionFactory;
+import org.junit.Assert;
+import org.junit.Test;
+
+public class StompTestWithMessageID extends StompTestBase {
+
+   public boolean isEnableStompMessageId() {
+      return true;
+   }
+
+   @Test
+   public void testEnableMessageID() throws Exception {
+      StompClientConnection conn = StompClientConnectionFactory.createClientConnection("1.0", hostname, port);
+      conn.connect(defUser, defPass);
+
+      ClientStompFrame frame = conn.createFrame("SEND");
+      frame.addHeader("destination", getQueuePrefix() + getQueueName());
+      frame.setBody("Hello World 1");
+      conn.sendFrame(frame);
+
+      frame = conn.createFrame("SEND");
+      frame.addHeader("destination", getQueuePrefix() + getQueueName());
+      frame.setBody("Hello World 2");
+      conn.sendFrame(frame);
+
+      QueueBrowser browser = session.createBrowser(queue);
+
+      Enumeration enu = browser.getEnumeration();
+
+      while (enu.hasMoreElements()) {
+         Message msg = (Message) enu.nextElement();
+         String msgId = msg.getStringProperty("amqMessageId");
+         assertNotNull(msgId);
+         assertTrue(msgId.indexOf("STOMP") == 0);
+      }
+
+      browser.close();
+
+      MessageConsumer consumer = session.createConsumer(queue);
+
+      TextMessage message = (TextMessage) consumer.receive(1000);
+      Assert.assertNotNull(message);
+
+      message = (TextMessage) consumer.receive(1000);
+      Assert.assertNotNull(message);
+
+      message = (TextMessage) consumer.receive(2000);
+      Assert.assertNull(message);
+   }
+}

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestWithSecurity.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestWithSecurity.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestWithSecurity.java
index e9d5550..a6ce6c9 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestWithSecurity.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/StompTestWithSecurity.java
@@ -19,27 +19,34 @@ package org.apache.activemq.artemis.tests.integration.stomp;
 import javax.jms.MessageConsumer;
 import javax.jms.TextMessage;
 
-import org.apache.activemq.artemis.core.protocol.stomp.Stomp;
+import org.apache.activemq.artemis.tests.integration.stomp.util.ClientStompFrame;
+import org.apache.activemq.artemis.tests.integration.stomp.util.StompClientConnection;
+import org.apache.activemq.artemis.tests.integration.stomp.util.StompClientConnectionFactory;
 import org.junit.Assert;
 import org.junit.Test;
 
 public class StompTestWithSecurity extends StompTestBase {
 
+   @Override
+   public boolean isSecurityEnabled() {
+      return true;
+   }
+
    @Test
    public void testJMSXUserID() throws Exception {
       server.getActiveMQServer().getConfiguration().setPopulateValidatedUser(true);
 
       MessageConsumer consumer = session.createConsumer(queue);
 
-      String frame = "CONNECT\n" + "login: brianm\n" + "passcode: wombats\n\n" + Stomp.NULL;
-      sendFrame(frame);
-
-      frame = receiveFrame(10000);
-      Assert.assertTrue(frame.startsWith("CONNECTED"));
+      StompClientConnection conn = StompClientConnectionFactory.createClientConnection("1.0", hostname, port);
+      conn.connect(defUser, defPass);
 
-      frame = "SEND\n" + "destination:" + getQueuePrefix() + getQueueName() + "\n\n" + "Hello World" + Stomp.NULL;
+      ClientStompFrame frame = conn.createFrame("SEND");
+      frame.addHeader("destination", getQueuePrefix() + getQueueName());
+      frame.setBody("Hello World");
+      conn.sendFrame(frame);
 
-      sendFrame(frame);
+      conn.disconnect();
 
       TextMessage message = (TextMessage) consumer.receive(1000);
       Assert.assertNotNull(message);
@@ -54,9 +61,4 @@ public class StompTestWithSecurity extends StompTestBase {
       long tmsg = message.getJMSTimestamp();
       Assert.assertTrue(Math.abs(tnow - tmsg) < 1000);
    }
-
-   @Override
-   public boolean isSecurityEnabled() {
-      return true;
-   }
 }

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/AbstractClientStompFrame.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/AbstractClientStompFrame.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/AbstractClientStompFrame.java
index 06771bb..c48fd8d 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/AbstractClientStompFrame.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/AbstractClientStompFrame.java
@@ -24,9 +24,9 @@ import java.util.Iterator;
 import java.util.List;
 import java.util.Set;
 
-public abstract class AbstractClientStompFrame implements ClientStompFrame {
+import org.apache.activemq.artemis.core.protocol.stomp.Stomp;
 
-   protected static final String HEADER_RECEIPT = "receipt";
+public abstract class AbstractClientStompFrame implements ClientStompFrame {
 
    protected static final Set<String> validCommands = new HashSet<>();
    protected String command;
@@ -36,19 +36,19 @@ public abstract class AbstractClientStompFrame implements ClientStompFrame {
    protected String EOL = "\n";
 
    static {
-      validCommands.add("CONNECT");
-      validCommands.add("CONNECTED");
-      validCommands.add("SEND");
-      validCommands.add("RECEIPT");
-      validCommands.add("SUBSCRIBE");
-      validCommands.add("UNSUBSCRIBE");
-      validCommands.add("MESSAGE");
-      validCommands.add("BEGIN");
-      validCommands.add("COMMIT");
-      validCommands.add("ABORT");
-      validCommands.add("ACK");
-      validCommands.add("DISCONNECT");
-      validCommands.add("ERROR");
+      validCommands.add(Stomp.Commands.CONNECT);
+      validCommands.add(Stomp.Responses.CONNECTED);
+      validCommands.add(Stomp.Commands.SEND);
+      validCommands.add(Stomp.Responses.RECEIPT);
+      validCommands.add(Stomp.Commands.SUBSCRIBE);
+      validCommands.add(Stomp.Commands.UNSUBSCRIBE);
+      validCommands.add(Stomp.Responses.MESSAGE);
+      validCommands.add(Stomp.Commands.BEGIN);
+      validCommands.add(Stomp.Commands.COMMIT);
+      validCommands.add(Stomp.Commands.ABORT);
+      validCommands.add(Stomp.Commands.ACK);
+      validCommands.add(Stomp.Commands.DISCONNECT);
+      validCommands.add(Stomp.Responses.ERROR);
    }
 
    public AbstractClientStompFrame(String command) {
@@ -80,37 +80,15 @@ public abstract class AbstractClientStompFrame implements ClientStompFrame {
 
    @Override
    public ByteBuffer toByteBuffer() {
-      if (isPing()) {
-         ByteBuffer buffer = ByteBuffer.allocateDirect(1);
-         buffer.put((byte) 0x0A);
-         buffer.rewind();
-         return buffer;
-      }
-      StringBuffer sb = new StringBuffer();
-      sb.append(command + EOL);
-      int n = headers.size();
-      for (int i = 0; i < n; i++) {
-         sb.append(headers.get(i).key + ":" + headers.get(i).val + EOL);
-      }
-      sb.append(EOL);
-      if (body != null) {
-         sb.append(body);
-      }
-      sb.append((char) 0);
-
-      String data = sb.toString();
-
-      byte[] byteValue = data.getBytes(StandardCharsets.UTF_8);
-
-      ByteBuffer buffer = ByteBuffer.allocateDirect(byteValue.length);
-      buffer.put(byteValue);
-
-      buffer.rewind();
-      return buffer;
+      return toByteBufferInternal(null);
    }
 
    @Override
    public ByteBuffer toByteBufferWithExtra(String str) {
+      return toByteBufferInternal(str);
+   }
+
+   public ByteBuffer toByteBufferInternal(String str) {
       StringBuffer sb = new StringBuffer();
       sb.append(command + EOL);
       int n = headers.size();
@@ -122,7 +100,9 @@ public abstract class AbstractClientStompFrame implements ClientStompFrame {
          sb.append(body);
       }
       sb.append((char) 0);
-      sb.append(str);
+      if (str != null) {
+         sb.append(str);
+      }
 
       String data = sb.toString();
 
@@ -137,26 +117,29 @@ public abstract class AbstractClientStompFrame implements ClientStompFrame {
 
    @Override
    public boolean needsReply() {
-      if ("CONNECT".equals(command) || headerKeys.contains(HEADER_RECEIPT)) {
+      if (Stomp.Commands.CONNECT.equals(command) || headerKeys.contains(Stomp.Headers.RECEIPT_REQUESTED)) {
          return true;
       }
       return false;
    }
 
    @Override
-   public void setCommand(String command) {
+   public ClientStompFrame setCommand(String command) {
       this.command = command;
+      return this;
    }
 
    @Override
-   public void addHeader(String key, String val) {
+   public ClientStompFrame addHeader(String key, String val) {
       headers.add(new Header(key, val));
       headerKeys.add(key);
+      return this;
    }
 
    @Override
-   public void setBody(String body) {
+   public ClientStompFrame setBody(String body) {
       this.body = body;
+      return this;
    }
 
    @Override

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/AbstractStompClientConnection.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/AbstractStompClientConnection.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/AbstractStompClientConnection.java
index ce94ec3..d8a487e 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/AbstractStompClientConnection.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/AbstractStompClientConnection.java
@@ -27,29 +27,12 @@ import java.util.concurrent.BlockingQueue;
 import java.util.concurrent.LinkedBlockingQueue;
 import java.util.concurrent.TimeUnit;
 
+import org.apache.activemq.artemis.core.protocol.stomp.Stomp;
 import org.apache.activemq.artemis.tests.integration.IntegrationTestLogger;
 
 public abstract class AbstractStompClientConnection implements StompClientConnection {
 
-   public static final String STOMP_COMMAND = "STOMP";
-
-   public static final String ACCEPT_HEADER = "accept-version";
-   public static final String HOST_HEADER = "host";
-   public static final String VERSION_HEADER = "version";
-   public static final String RECEIPT_HEADER = "receipt";
-
-   protected static final String CONNECT_COMMAND = "CONNECT";
-   protected static final String CONNECTED_COMMAND = "CONNECTED";
-   protected static final String DISCONNECT_COMMAND = "DISCONNECT";
-
-   protected static final String LOGIN_HEADER = "login";
-   protected static final String PASSCODE_HEADER = "passcode";
-
-   //ext
-   protected static final String CLIENT_ID_HEADER = "client-id";
-
    protected Pinger pinger;
-
    protected String version;
    protected String host;
    protected int port;
@@ -58,13 +41,10 @@ public abstract class AbstractStompClientConnection implements StompClientConnec
    protected StompFrameFactory factory;
    protected final SocketChannel socketChannel;
    protected ByteBuffer readBuffer;
-
    protected List<Byte> receiveList;
-
    protected BlockingQueue<ClientStompFrame> frameQueue = new LinkedBlockingQueue<>();
-
    protected boolean connected = false;
-   private int serverPingCounter;
+   protected int serverPingCounter;
 
    public AbstractStompClientConnection(String version, String host, int port) throws IOException {
       this.version = version;
@@ -90,11 +70,15 @@ public abstract class AbstractStompClientConnection implements StompClientConnec
       new ReaderThread().start();
    }
 
-   @Override
-   public ClientStompFrame sendFrame(ClientStompFrame frame) throws IOException, InterruptedException {
+   private ClientStompFrame sendFrameInternal(ClientStompFrame frame, boolean wicked) throws IOException, InterruptedException {
       ClientStompFrame response = null;
-      IntegrationTestLogger.LOGGER.info("Sending frame:\n" + frame);
-      ByteBuffer buffer = frame.toByteBuffer();
+      IntegrationTestLogger.LOGGER.info("Sending " + (wicked ? "*wicked* " : "") + "frame:\n" + frame);
+      ByteBuffer buffer;
+      if (wicked) {
+         buffer = frame.toByteBufferWithExtra("\n");
+      } else {
+         buffer = frame.toByteBuffer();
+      }
       while (buffer.remaining() > 0) {
          socketChannel.write(buffer);
       }
@@ -105,7 +89,7 @@ public abstract class AbstractStompClientConnection implements StompClientConnec
 
          //filter out server ping
          while (response != null) {
-            if (response.getCommand().equals("STOMP")) {
+            if (response.getCommand().equals(Stomp.Commands.STOMP)) {
                response = receiveFrame();
             } else {
                break;
@@ -113,32 +97,19 @@ public abstract class AbstractStompClientConnection implements StompClientConnec
          }
       }
 
+      IntegrationTestLogger.LOGGER.info("Received:\n" + response);
+
       return response;
    }
 
    @Override
-   public ClientStompFrame sendWickedFrame(ClientStompFrame frame) throws IOException, InterruptedException {
-      ClientStompFrame response = null;
-      ByteBuffer buffer = frame.toByteBufferWithExtra("\n");
-
-      while (buffer.remaining() > 0) {
-         socketChannel.write(buffer);
-      }
-
-      //now response
-      if (frame.needsReply()) {
-         response = receiveFrame();
+   public ClientStompFrame sendFrame(ClientStompFrame frame) throws IOException, InterruptedException {
+      return sendFrameInternal(frame, false);
+   }
 
-         //filter out server ping
-         while (response != null) {
-            if (response.getCommand().equals("STOMP")) {
-               response = receiveFrame();
-            } else {
-               break;
-            }
-         }
-      }
-      return response;
+   @Override
+   public ClientStompFrame sendWickedFrame(ClientStompFrame frame) throws IOException, InterruptedException {
+      return sendFrameInternal(frame, true);
    }
 
    @Override
@@ -186,17 +157,12 @@ public abstract class AbstractStompClientConnection implements StompClientConnec
       readBuffer.rewind();
    }
 
-   @Override
-   public int getServerPingNumber() {
-      return serverPingCounter;
-   }
-
    protected void incrementServerPing() {
       serverPingCounter++;
    }
 
    private boolean validateFrame(ClientStompFrame f) {
-      String h = f.getHeader("content-length");
+      String h = f.getHeader(Stomp.Headers.CONTENT_LENGTH);
       if (h != null) {
          int len = Integer.valueOf(h);
          if (f.getBody().getBytes(StandardCharsets.UTF_8).length < len) {
@@ -271,34 +237,15 @@ public abstract class AbstractStompClientConnection implements StompClientConnec
       return this.frameQueue.size();
    }
 
-   @Override
-   public void startPinger(long interval) {
-      pinger = new Pinger(interval);
-      pinger.startPing();
-   }
-
-   @Override
-   public void stopPinger() {
-      if (pinger != null) {
-         pinger.stopPing();
-         try {
-            pinger.join();
-         } catch (InterruptedException e) {
-            e.printStackTrace();
-         }
-         pinger = null;
-      }
-   }
-
-   private class Pinger extends Thread {
+   protected class Pinger extends Thread {
 
       long pingInterval;
       ClientStompFrame pingFrame;
       volatile boolean stop = false;
 
-      private Pinger(long interval) {
+      Pinger(long interval) {
          this.pingInterval = interval;
-         pingFrame = createFrame("STOMP");
+         pingFrame = createFrame(Stomp.Commands.STOMP);
          pingFrame.setBody("\n");
          pingFrame.setForceOneway();
          pingFrame.setPing(true);
@@ -329,5 +276,4 @@ public abstract class AbstractStompClientConnection implements StompClientConnec
          }
       }
    }
-
 }

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/ClientStompFrame.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/ClientStompFrame.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/ClientStompFrame.java
index 53bced4..93801f9 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/ClientStompFrame.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/ClientStompFrame.java
@@ -27,11 +27,11 @@ public interface ClientStompFrame {
 
    boolean needsReply();
 
-   void setCommand(String command);
+   ClientStompFrame setCommand(String command);
 
-   void addHeader(String string, String string2);
+   ClientStompFrame addHeader(String string, String string2);
 
-   void setBody(String string);
+   ClientStompFrame setBody(String string);
 
    String getCommand();
 
@@ -43,8 +43,8 @@ public interface ClientStompFrame {
 
    boolean isPing();
 
-   void setForceOneway();
+   ClientStompFrame setForceOneway();
 
-   void setPing(boolean b);
+   ClientStompFrame setPing(boolean b);
 
 }

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/ClientStompFrameV10.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/ClientStompFrameV10.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/ClientStompFrameV10.java
index 5273236..92629ab 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/ClientStompFrameV10.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/ClientStompFrameV10.java
@@ -30,18 +30,18 @@ public class ClientStompFrameV10 extends AbstractClientStompFrame {
    }
 
    @Override
-   public boolean isPing() {
-      return false;
+   public ClientStompFrame setForceOneway() {
+      throw new IllegalStateException("Doesn't apply with V1.0!");
    }
 
    @Override
-   public void setForceOneway() {
+   public ClientStompFrame setPing(boolean b) {
       throw new IllegalStateException("Doesn't apply with V1.0!");
    }
 
    @Override
-   public void setPing(boolean b) {
-      throw new IllegalStateException("Doesn't apply with V1.0!");
+   public boolean isPing() {
+      return false;
    }
 
 }

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/ClientStompFrameV11.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/ClientStompFrameV11.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/ClientStompFrameV11.java
index 22d7146..4d8d1e0 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/ClientStompFrameV11.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/ClientStompFrameV11.java
@@ -16,14 +16,13 @@
  */
 package org.apache.activemq.artemis.tests.integration.stomp.util;
 
-/**
- * pls use factory to create frames.
- */
-public class ClientStompFrameV11 extends AbstractClientStompFrame {
+import org.apache.activemq.artemis.core.protocol.stomp.Stomp;
+
+public class ClientStompFrameV11 extends ClientStompFrameV10 {
 
    static {
-      validCommands.add("NACK");
-      validCommands.add("STOMP");
+      validCommands.add(Stomp.Commands.NACK);
+      validCommands.add(Stomp.Commands.STOMP);
    }
 
    boolean forceOneway = false;
@@ -38,8 +37,9 @@ public class ClientStompFrameV11 extends AbstractClientStompFrame {
    }
 
    @Override
-   public void setForceOneway() {
+   public ClientStompFrame setForceOneway() {
       forceOneway = true;
+      return this;
    }
 
    @Override
@@ -47,15 +47,17 @@ public class ClientStompFrameV11 extends AbstractClientStompFrame {
       if (forceOneway)
          return false;
 
-      if ("CONNECT".equals(command) || "STOMP".equals(command) || headerKeys.contains(HEADER_RECEIPT)) {
+      if (Stomp.Commands.STOMP.equals(command)) {
          return true;
       }
-      return false;
+
+      return super.needsReply();
    }
 
    @Override
-   public void setPing(boolean b) {
+   public ClientStompFrame setPing(boolean b) {
       isPing = b;
+      return this;
    }
 
    @Override

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/ClientStompFrameV12.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/ClientStompFrameV12.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/ClientStompFrameV12.java
index 5ca530e..eaffd1c 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/ClientStompFrameV12.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/ClientStompFrameV12.java
@@ -16,17 +16,7 @@
  */
 package org.apache.activemq.artemis.tests.integration.stomp.util;
 
-/**
- */
-public class ClientStompFrameV12 extends AbstractClientStompFrame {
-
-   static {
-      validCommands.add("NACK");
-      validCommands.add("STOMP");
-   }
-
-   boolean forceOneway = false;
-   boolean isPing = false;
+public class ClientStompFrameV12 extends ClientStompFrameV11 {
 
    public ClientStompFrameV12(String command) {
       this(command, true, true);
@@ -45,32 +35,6 @@ public class ClientStompFrameV12 extends AbstractClientStompFrame {
    }
 
    @Override
-   public void setForceOneway() {
-      forceOneway = true;
-   }
-
-   @Override
-   public boolean needsReply() {
-      if (forceOneway)
-         return false;
-
-      if ("CONNECT".equals(command) || "STOMP".equals(command) || headerKeys.contains(HEADER_RECEIPT)) {
-         return true;
-      }
-      return false;
-   }
-
-   @Override
-   public void setPing(boolean b) {
-      isPing = b;
-   }
-
-   @Override
-   public boolean isPing() {
-      return isPing;
-   }
-
-   @Override
    public String toString() {
       return "[1.2]" + super.toString();
    }

http://git-wip-us.apache.org/repos/asf/activemq-artemis/blob/84df373a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompClientConnection.java
----------------------------------------------------------------------
diff --git a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompClientConnection.java b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompClientConnection.java
index 12f52d0..7be09a5 100644
--- a/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompClientConnection.java
+++ b/tests/integration-tests/src/test/java/org/apache/activemq/artemis/tests/integration/stomp/util/StompClientConnection.java
@@ -18,9 +18,6 @@ package org.apache.activemq.artemis.tests.integration.stomp.util;
 
 import java.io.IOException;
 
-/**
- * pls use factory to create frames.
- */
 public interface StompClientConnection {
 
    ClientStompFrame sendFrame(ClientStompFrame frame) throws IOException, InterruptedException;
@@ -35,7 +32,7 @@ public interface StompClientConnection {
 
    ClientStompFrame connect(String defUser, String defPass) throws Exception;
 
-   void connect(String defUser, String defPass, String clientId) throws Exception;
+   ClientStompFrame connect(String defUser, String defPass, String clientId) throws Exception;
 
    boolean isConnected();