summaryrefslogtreecommitdiff
path: root/qpid/java/qpid-test-utils/src
diff options
context:
space:
mode:
authorRobert Gemmell <robbie@apache.org>2013-09-23 23:42:30 +0000
committerRobert Gemmell <robbie@apache.org>2013-09-23 23:42:30 +0000
commit469aa371040b2e0685f269937a4e49527a35e00c (patch)
tree3896ba9cbfa5c23e9ebc187e25e673a253903670 /qpid/java/qpid-test-utils/src
parent59710ea96cf37dc3859ada1dc5fb095b0b2bc6b4 (diff)
downloadqpid-python-469aa371040b2e0685f269937a4e49527a35e00c.tar.gz
QPID-5160: add a qpid-test-utils module instead of making every modules tests rely on the tests dir from the common module
git-svn-id: https://svn.apache.org/repos/asf/qpid/trunk@1525738 13f79535-47bb-0310-9956-ffa450edef68
Diffstat (limited to 'qpid/java/qpid-test-utils/src')
-rw-r--r--qpid/java/qpid-test-utils/src/main/java/org/apache/qpid/test/utils/PortHelper.java127
-rw-r--r--qpid/java/qpid-test-utils/src/main/java/org/apache/qpid/test/utils/QpidTestCase.java284
-rw-r--r--qpid/java/qpid-test-utils/src/main/java/org/apache/qpid/test/utils/TestFileUtils.java233
-rw-r--r--qpid/java/qpid-test-utils/src/main/java/org/apache/qpid/test/utils/TestSSLConstants.java37
4 files changed, 681 insertions, 0 deletions
diff --git a/qpid/java/qpid-test-utils/src/main/java/org/apache/qpid/test/utils/PortHelper.java b/qpid/java/qpid-test-utils/src/main/java/org/apache/qpid/test/utils/PortHelper.java
new file mode 100644
index 0000000000..d3586c364f
--- /dev/null
+++ b/qpid/java/qpid-test-utils/src/main/java/org/apache/qpid/test/utils/PortHelper.java
@@ -0,0 +1,127 @@
+/*
+ * 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.qpid.test.utils;
+
+import java.io.IOException;
+import java.net.DatagramSocket;
+import java.net.ServerSocket;
+import java.util.Set;
+
+import org.apache.log4j.Logger;
+
+public class PortHelper
+{
+ private static final Logger _logger = Logger.getLogger(PortHelper.class);
+
+ private static final int DEFAULT_TIMEOUT_MILLIS = 5000;
+
+ private int timeout = DEFAULT_TIMEOUT_MILLIS;
+
+ public void waitUntilPortsAreFree(Set<Integer> ports)
+ {
+ _logger.debug("Checking if ports " + ports + " are free...");
+
+ for (Integer port : ports)
+ {
+ waitUntilPortIsFree(port);
+ }
+
+ _logger.debug("ports " + ports + " are free");
+ }
+
+ private void waitUntilPortIsFree(int port)
+ {
+ long startTime = System.currentTimeMillis();
+ long deadline = startTime + timeout;
+ boolean alreadyFailed = false;
+
+ while (true)
+ {
+ if (System.currentTimeMillis() > deadline)
+ {
+ throw new RuntimeException("Timed out after " + timeout + " ms waiting for port " + port + " to become available");
+ }
+
+ if (isPortAvailable(port))
+ {
+ if(alreadyFailed)
+ {
+ _logger.debug("port " + port + " is now available");
+ }
+ return;
+ }
+ else
+ {
+ alreadyFailed = true;
+ }
+
+ try
+ {
+ Thread.sleep(500);
+ }
+ catch (InterruptedException e)
+ {
+ Thread.currentThread().interrupt();
+ }
+ }
+ }
+
+ public boolean isPortAvailable(int port)
+ {
+ ServerSocket serverSocket = null;
+ DatagramSocket datagramSocket = null;
+
+ try
+ {
+ serverSocket = new ServerSocket(port);
+ serverSocket.setReuseAddress(true); // ensures that the port is subsequently usable
+ datagramSocket = new DatagramSocket(port);
+ datagramSocket.setReuseAddress(true);
+ return true;
+ }
+ catch (IOException e)
+ {
+ _logger.debug("port " + port + " is not free");
+ return false;
+ }
+ finally
+ {
+ if (serverSocket != null)
+ {
+ try
+ {
+ serverSocket.close();
+ }
+ catch (IOException e)
+ {
+ throw new RuntimeException("Couldn't close port " + port + " that we created to check its availability", e);
+ }
+ }
+ if(datagramSocket != null)
+ {
+ datagramSocket.close();
+ }
+ }
+ }
+
+ public void setTimeout(int timeout)
+ {
+ this.timeout = timeout;
+ }
+}
diff --git a/qpid/java/qpid-test-utils/src/main/java/org/apache/qpid/test/utils/QpidTestCase.java b/qpid/java/qpid-test-utils/src/main/java/org/apache/qpid/test/utils/QpidTestCase.java
new file mode 100644
index 0000000000..8f556ece5a
--- /dev/null
+++ b/qpid/java/qpid-test-utils/src/main/java/org/apache/qpid/test/utils/QpidTestCase.java
@@ -0,0 +1,284 @@
+/*
+ *
+ * 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.qpid.test.utils;
+
+import junit.framework.TestCase;
+import junit.framework.TestResult;
+import org.apache.log4j.Level;
+import org.apache.log4j.Logger;
+
+import java.io.BufferedReader;
+import java.io.File;
+import java.io.FileReader;
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.NoSuchElementException;
+
+
+public class QpidTestCase extends TestCase
+{
+ public static final String QPID_HOME = System.getProperty("QPID_HOME");
+ public static final String TEST_RESOURCES_DIR = QPID_HOME + "/../test-profiles/test_resources/";
+ public static final String TMP_FOLDER = System.getProperty("java.io.tmpdir");
+ public static final String LOG4J_CONFIG_FILE_PATH = System.getProperty("log4j.configuration.file");
+
+ private static final Logger _logger = Logger.getLogger(QpidTestCase.class);
+
+ private final Map<Logger, Level> _loggerLevelSetForTest = new HashMap<Logger, Level>();
+ private final Map<String, String> _propertiesSetForTest = new HashMap<String, String>();
+
+ private String _testName;
+
+ /**
+ * Some tests are excluded when the property test.excludes is set to true.
+ * An exclusion list is either a file (prop test.excludesfile) which contains one test name
+ * to be excluded per line or a String (prop test.excludeslist) where tests to be excluded are
+ * separated by " ". Excluded tests are specified following the format:
+ * className#testName where className is the class of the test to be
+ * excluded and testName is the name of the test to be excluded.
+ * className#* excludes all the tests of the specified class.
+ */
+ static
+ {
+ if (Boolean.getBoolean("test.exclude"))
+ {
+ _logger.info("Some tests should be excluded, building the exclude list");
+ String exclusionListURIs = System.getProperties().getProperty("test.excludefiles", "");
+ String exclusionListString = System.getProperties().getProperty("test.excludelist", "");
+ List<String> exclusionList = new ArrayList<String>();
+
+ for (String uri : exclusionListURIs.split(";\\s*"))
+ {
+ File file = new File(uri);
+ if (file.exists())
+ {
+ _logger.info("Using exclude file: " + uri);
+ try
+ {
+ BufferedReader in = new BufferedReader(new FileReader(file));
+ String excludedTest = in.readLine();
+ do
+ {
+ exclusionList.add(excludedTest);
+ excludedTest = in.readLine();
+ }
+ while (excludedTest != null);
+ }
+ catch (IOException e)
+ {
+ _logger.warn("Exception when reading exclusion list", e);
+ }
+ }
+ else
+ {
+ _logger.info("Specified exclude file does not exist: " + uri);
+ }
+ }
+
+ if (!exclusionListString.equals(""))
+ {
+ _logger.info("Using excludeslist: " + exclusionListString);
+ for (String test : exclusionListString.split("\\s+"))
+ {
+ exclusionList.add(test);
+ }
+ }
+
+ _exclusionList = exclusionList;
+ }
+ }
+
+ protected static final String MESSAGE_STORE_CLASS_NAME_KEY = "messagestore.class.name";
+ protected static final String CONFIGURATION_STORE_CLASS_NAME_KEY = "configurationstore.class.name";
+
+ protected static final String MEMORY_STORE_CLASS_NAME = "org.apache.qpid.server.store.MemoryMessageStore";
+
+ private static List<String> _exclusionList;
+
+ public QpidTestCase()
+ {
+ super();
+ }
+
+ public void run(TestResult testResult)
+ {
+ if (_exclusionList != null && (_exclusionList.contains(getClass().getPackage().getName() + ".*") ||
+ _exclusionList.contains(getClass().getName() + "#*") ||
+ _exclusionList.contains(getClass().getName() + "#" + getName())))
+ {
+ _logger.info("Test: " + getName() + " is excluded");
+ testResult.endTest(this);
+ }
+ else
+ {
+ super.run(testResult);
+ }
+ }
+
+ public String getTestProfileMessageStoreClassName()
+ {
+ final String storeClass = System.getProperty(MESSAGE_STORE_CLASS_NAME_KEY);
+ _logger.debug("MESSAGE_STORE_CLASS_NAME_KEY " + storeClass);
+
+ return storeClass != null ? storeClass : MEMORY_STORE_CLASS_NAME ;
+ }
+
+
+ public static final int MIN_PORT_NUMBER = 1;
+ public static final int MAX_PORT_NUMBER = 49151;
+
+
+ /**
+ * Gets the next available port starting at a port.
+ *
+ * @param fromPort the port to scan for availability
+ * @throws NoSuchElementException if there are no ports available
+ */
+ public int getNextAvailable(int fromPort)
+ {
+ if ((fromPort < MIN_PORT_NUMBER) || (fromPort > MAX_PORT_NUMBER))
+ {
+ throw new IllegalArgumentException("Invalid start port: " + fromPort);
+ }
+
+ PortHelper portHelper = new PortHelper();
+ for (int i = fromPort; i <= MAX_PORT_NUMBER; i++)
+ {
+ if (portHelper.isPortAvailable(i)) {
+ return i;
+ }
+ }
+
+ throw new NoSuchElementException("Could not find an available port above " + fromPort);
+ }
+
+ public int findFreePort()
+ {
+ return getNextAvailable(10000);
+ }
+
+ /**
+ * Set a System property for duration of this test only. The tearDown will
+ * guarantee to reset the property to its previous value after the test
+ * completes.
+ *
+ * @param property The property to set
+ * @param value the value to set it to, if null, the property will be cleared
+ */
+ protected void setTestSystemProperty(final String property, final String value)
+ {
+ if (!_propertiesSetForTest.containsKey(property))
+ {
+ // Record the current value so we can revert it later.
+ _propertiesSetForTest.put(property, System.getProperty(property));
+ }
+
+ if (value == null)
+ {
+ System.clearProperty(property);
+ }
+ else
+ {
+ System.setProperty(property, value);
+ }
+
+ _logger.info("Set system property \"" + property + "\" to: \"" + value + "\"");
+ }
+
+ /**
+ * Restore the System property values that were set by this test run.
+ */
+ protected void revertTestSystemProperties()
+ {
+ if(!_propertiesSetForTest.isEmpty())
+ {
+ _logger.debug("reverting " + _propertiesSetForTest.size() + " test properties");
+ for (String key : _propertiesSetForTest.keySet())
+ {
+ String value = _propertiesSetForTest.get(key);
+ if (value != null)
+ {
+ System.setProperty(key, value);
+ }
+ else
+ {
+ System.clearProperty(key);
+ }
+ }
+
+ _propertiesSetForTest.clear();
+ }
+ }
+
+ /**
+ * Adjust the VMs Log4j Settings just for this test run
+ *
+ * @param logger the logger to change
+ * @param level the level to set
+ */
+ protected void setLoggerLevel(Logger logger, Level level)
+ {
+ assertNotNull("Cannot set level of null logger", logger);
+ assertNotNull("Cannot set Logger("+logger.getName()+") to null level.",level);
+
+ if (!_loggerLevelSetForTest.containsKey(logger))
+ {
+ // Record the current value so we can revert it later.
+ _loggerLevelSetForTest.put(logger, logger.getLevel());
+ }
+
+ logger.setLevel(level);
+ }
+
+ /**
+ * Restore the logging levels defined by this test.
+ */
+ protected void revertLoggingLevels()
+ {
+ for (Logger logger : _loggerLevelSetForTest.keySet())
+ {
+ logger.setLevel(_loggerLevelSetForTest.get(logger));
+ }
+
+ _loggerLevelSetForTest.clear();
+ }
+
+ protected void tearDown() throws java.lang.Exception
+ {
+ _logger.info("========== tearDown " + _testName + " ==========");
+ revertTestSystemProperties();
+ revertLoggingLevels();
+ }
+
+ protected void setUp() throws Exception
+ {
+ _testName = getClass().getSimpleName() + "." + getName();
+ _logger.info("========== start " + _testName + " ==========");
+ }
+
+ protected String getTestName()
+ {
+ return _testName;
+ }
+}
diff --git a/qpid/java/qpid-test-utils/src/main/java/org/apache/qpid/test/utils/TestFileUtils.java b/qpid/java/qpid-test-utils/src/main/java/org/apache/qpid/test/utils/TestFileUtils.java
new file mode 100644
index 0000000000..d04413f06f
--- /dev/null
+++ b/qpid/java/qpid-test-utils/src/main/java/org/apache/qpid/test/utils/TestFileUtils.java
@@ -0,0 +1,233 @@
+/*
+ *
+ * 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.qpid.test.utils;
+
+import java.io.File;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+
+import java.io.FileOutputStream;
+
+import junit.framework.TestCase;
+
+/**
+ * Utility methods intended to be used in tests that manipulate files
+ */
+public class TestFileUtils
+{
+ private static final String SYSTEM_TMP_DIR = System.getProperty("java.io.tmpdir");
+ private static final String SUFFIX = "tmp";
+
+ /**
+ * Create and return a temporary directory that will be deleted on exit.
+ */
+ public static File createTestDirectory()
+ {
+ String dirNameStem = TestFileUtils.class.getSimpleName() + "-testDir";
+ return createTestDirectory(dirNameStem, true);
+ }
+
+ /**
+ * Creates an empty directory with a name like /tmp/dirNameStem-12345678
+ */
+ public static File createTestDirectory(String dirNameStem, boolean deleteOnExit)
+ {
+ File testDir = new File(SYSTEM_TMP_DIR, dirNameStem + "-" + System.currentTimeMillis());
+ if (testDir.exists())
+ {
+ delete(testDir, true);
+ }
+
+ testDir.mkdirs();
+
+ if (deleteOnExit)
+ {
+ testDir.deleteOnExit();
+ }
+
+ return testDir;
+ }
+
+ public static File createTempFile(TestCase testcase)
+ {
+ return createTempFile(testcase, SUFFIX);
+ }
+
+ public static File createTempFile(TestCase testcase, String suffix)
+ {
+ String prefix = testcase.getClass().getSimpleName() + "-" + testcase.getName();
+
+ File tmpFile;
+ try
+ {
+ tmpFile = File.createTempFile(prefix, suffix);
+ tmpFile.deleteOnExit();
+ }
+ catch (IOException e)
+ {
+ throw new RuntimeException("Cannot create temporary file with prefix " + prefix + " and suffix " + SUFFIX, e);
+ }
+
+ return tmpFile;
+ }
+
+ /**
+ * Creates a temporary file from the resource name given, using the resource name as the file suffix.
+ *
+ * This is required because the tests use the jar files as their class path.
+ */
+ public static File createTempFileFromResource(TestCase testCase, String resourceName)
+ {
+ File dst = createTempFile(testCase, resourceName);
+ InputStream in = testCase.getClass().getResourceAsStream(resourceName);
+ try
+ {
+ copy(in, dst);
+ }
+ catch (Exception e)
+ {
+ throw new RuntimeException("Cannot copy resource " + resourceName +
+ " to temp file " + dst.getAbsolutePath(), e);
+ }
+ dst.deleteOnExit();
+ return dst;
+ }
+
+ /**
+ * Creates a temporary file for given test with given suffix in file name.
+ * The given content is stored in the file using UTF-8 encoding.
+ */
+ public static File createTempFile(TestCase testcase, String suffix, String content)
+ {
+ File file = createTempFile(testcase, suffix);
+ if (content != null)
+ {
+ FileOutputStream fos = null;
+ try
+ {
+ fos = new FileOutputStream(file);
+ fos.write(content.getBytes("UTF-8"));
+ fos.flush();
+ }
+ catch (Exception e)
+ {
+ throw new RuntimeException("Cannot add the content into temp file " + file.getAbsolutePath(), e);
+ }
+ finally
+ {
+ if (fos != null)
+ {
+ try
+ {
+ fos.close();
+ }
+ catch (IOException e)
+ {
+ throw new RuntimeException("Cannot close output stream into temp file " + file.getAbsolutePath(), e);
+ }
+ }
+ }
+ }
+ return file;
+ }
+
+ /**
+ * Delete a given file/directory,
+ * A directory will always require the recursive flag to be set.
+ * if a directory is specified and recursive set then delete the whole tree
+ *
+ * @param file the File object to start at
+ * @param recursive boolean to recurse if a directory is specified.
+ *
+ * @return <code>true</code> if and only if the file or directory is
+ * successfully deleted; <code>false</code> otherwise
+ */
+ public static boolean delete(File file, boolean recursive)
+ {
+ boolean success = true;
+
+ if (file.isDirectory())
+ {
+ if (recursive)
+ {
+ File[] files = file.listFiles();
+
+ // This can occur if the file is deleted outside the JVM
+ if (files == null)
+ {
+ return false;
+ }
+
+ for (int i = 0; i < files.length; i++)
+ {
+ success = delete(files[i], true) && success;
+ }
+
+ return success && file.delete();
+ }
+
+ return false;
+ }
+
+ return file.delete();
+ }
+
+ /**
+ * Copies the specified InputStream to the specified destination file. If the destination file does not exist,
+ * it is created.
+ *
+ * @param in The InputStream
+ * @param dst The destination file name.
+ * @throws IOException
+ */
+ public static void copy(InputStream in, File dst) throws IOException
+ {
+ try
+ {
+ if (!dst.exists())
+ {
+ dst.createNewFile();
+ }
+
+ OutputStream out = new FileOutputStream(dst);
+
+ try
+ {
+ // Transfer bytes from in to out
+ byte[] buf = new byte[1024];
+ int len;
+ while ((len = in.read(buf)) > 0)
+ {
+ out.write(buf, 0, len);
+ }
+ }
+ finally
+ {
+ out.close();
+ }
+ }
+ finally
+ {
+ in.close();
+ }
+ }
+}
diff --git a/qpid/java/qpid-test-utils/src/main/java/org/apache/qpid/test/utils/TestSSLConstants.java b/qpid/java/qpid-test-utils/src/main/java/org/apache/qpid/test/utils/TestSSLConstants.java
new file mode 100644
index 0000000000..c48f164d98
--- /dev/null
+++ b/qpid/java/qpid-test-utils/src/main/java/org/apache/qpid/test/utils/TestSSLConstants.java
@@ -0,0 +1,37 @@
+/*
+ * 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.qpid.test.utils;
+
+public interface TestSSLConstants
+{
+ String KEYSTORE = "test-profiles/test_resources/ssl/java_client_keystore.jks";
+ String UNTRUSTED_KEYSTORE = "test-profiles/test_resources/ssl/java_client_untrusted_keystore.jks";
+ String KEYSTORE_PASSWORD = "password";
+ String TRUSTSTORE = "test-profiles/test_resources/ssl/java_client_truststore.jks";
+ String TRUSTSTORE_PASSWORD = "password";
+
+ String BROKER_KEYSTORE = "test-profiles/test_resources/ssl/java_broker_keystore.jks";
+ String BROKER_KEYSTORE_PASSWORD = "password";
+
+ String BROKER_PEERSTORE = "test-profiles/test_resources/ssl/java_broker_peerstore.jks";
+ String BROKER_PEERSTORE_PASSWORD = "password";
+
+ String BROKER_TRUSTSTORE = "test-profiles/test_resources/ssl/java_broker_truststore.jks";
+ String BROKER_TRUSTSTORE_PASSWORD = "password";
+}