1   /**
2    *  Copyright 2003-2007 Greg Luck
3    *
4    *  Licensed under the Apache License, Version 2.0 (the "License");
5    *  you may not use this file except in compliance with the License.
6    *  You may obtain a copy of the License at
7    *
8    *      http://www.apache.org/licenses/LICENSE-2.0
9    *
10   *  Unless required by applicable law or agreed to in writing, software
11   *  distributed under the License is distributed on an "AS IS" BASIS,
12   *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13   *  See the License for the specific language governing permissions and
14   *  limitations under the License.
15   */
16  
17  package net.sf.ehcache;
18  
19  import junit.framework.TestCase;
20  
21  import javax.management.MBeanServer;
22  import javax.management.MBeanServerFactory;
23  import java.io.File;
24  import java.io.IOException;
25  import java.util.List;
26  import java.lang.reflect.Method;
27  
28  import org.apache.commons.logging.Log;
29  import org.apache.commons.logging.LogFactory;
30  
31  /**
32   * Common fields and methods required by most test cases
33   *
34   * @author <a href="mailto:gluck@thoughtworks.com">Greg Luck</a>
35   * @version $Id: AbstractCacheTest.java 512 2007-07-10 09:18:45Z gregluck $
36   */
37  public abstract class AbstractCacheTest extends TestCase {
38  
39      /**
40       * Where the config is
41       */
42      public static final String SRC_CONFIG_DIR = "src/main/config/";
43  
44      /**
45       * Where the test config is
46       */
47      public static final String TEST_CONFIG_DIR = "src/test/resources/";
48      /**
49       * Where the test classes are compiled.
50       */
51      public static final String TEST_CLASSES_DIR = "target/test-classes/";
52  
53  
54      private static final Log LOG = LogFactory.getLog(AbstractCacheTest.class.getName());
55  
56      /**
57       * name for sample cache 1
58       */
59      protected final String sampleCache1 = "sampleCache1";
60      /**
61       * name for sample cache 2
62       */
63      protected final String sampleCache2 = "sampleCache2";
64      /**
65       * the CacheManager instance
66       */
67      protected CacheManager manager;
68  
69      /**
70       * setup test
71       */
72      protected void setUp() throws Exception {
73          manager = CacheManager.create();
74      }
75  
76      /**
77       * teardown
78       */
79      protected void tearDown() throws Exception {
80          if (manager != null) {
81              manager.shutdown();
82          }
83      }
84  
85  
86      /**
87       * Force the VM to grow to its full size. This stops SoftReferences from being reclaimed in favour of
88       * Heap growth. Only an issue when a VM is cold.
89       */
90      static public void forceVMGrowth() {
91          allocateFiftyMegabytes();
92          System.gc();
93          try {
94              Thread.sleep(200);
95          } catch (InterruptedException e) {
96              //
97          }
98          System.gc();
99      }
100 
101     private static void allocateFiftyMegabytes() {
102         byte[] forceVMGrowth = new byte[50000000];
103     }
104 
105 
106     /**
107      * @param name
108      * @throws IOException
109      */
110     protected void deleteFile(String name) throws IOException {
111         String diskPath = System.getProperty("java.io.tmpdir");
112         final File diskDir = new File(diskPath);
113         File dataFile = new File(diskDir, name + ".data");
114         if (dataFile.exists()) {
115             dataFile.delete();
116         }
117         File indexFile = new File(diskDir, name + ".index");
118         if (indexFile.exists()) {
119             indexFile.delete();
120         }
121     }
122 
123     /**
124      * Measure memory used by the VM.
125      *
126      * @return
127      * @throws InterruptedException
128      */
129     protected long measureMemoryUse() throws InterruptedException {
130         System.gc();
131         Thread.sleep(2000);
132         System.gc();
133         return Runtime.getRuntime().totalMemory() - Runtime.getRuntime().freeMemory();
134     }
135 
136     /**
137      * Runs a set of threads, for a fixed amount of time.
138      */
139     protected void runThreads(final List executables) throws Exception {
140 
141         final long endTime = System.currentTimeMillis() + 10000;
142         final Throwable[] errors = new Throwable[1];
143 
144         // Spin up the threads
145         final Thread[] threads = new Thread[executables.size()];
146         for (int i = 0; i < threads.length; i++) {
147             final Executable executable = (Executable) executables.get(i);
148             threads[i] = new Thread() {
149                 public void run() {
150                     try {
151                         // Run the thread until the given end time
152                         while (System.currentTimeMillis() < endTime) {
153                             executable.execute();
154                         }
155                     } catch (Throwable t) {
156                         // Hang on to any errors
157                         errors[0] = t;
158                     }
159                 }
160             };
161             threads[i].start();
162         }
163 
164         // Wait for the threads to finish
165         for (int i = 0; i < threads.length; i++) {
166             threads[i].join();
167         }
168 
169         // Throw any error that happened
170         if (errors[0] != null) {
171             throw new Exception("Test thread failed.", errors[0]);
172         }
173     }
174 
175     /**
176      * Obtains an MBeanServer, which varies with Java version
177      * @return
178      */
179     public MBeanServer createMBeanServer() {
180         try {
181             Class managementFactoryClass = Class.forName("java.lang.management.ManagementFactory");
182             Method method = managementFactoryClass.getMethod("getPlatformMBeanServer", null);
183             return (MBeanServer) method.invoke(null, null);
184         } catch (Exception e) {
185             LOG.info("JDK1.5 ManagementFactory not found. Falling back to JMX1.2.1", e);
186             return MBeanServerFactory.createMBeanServer("SimpleAgent");
187         }
188     }
189 
190 
191     /**
192      * A runnable, that can throw an exception.
193      */
194     protected interface Executable {
195         /**
196          * Executes this object.
197          *
198          * @throws Exception
199          */
200         void execute() throws Exception;
201     }
202 
203 }