1 |
| package org.jboss.cache.eviction; |
2 |
| |
3 |
| import junit.framework.Test; |
4 |
| import junit.framework.TestCase; |
5 |
| import junit.framework.TestSuite; |
6 |
| import org.jboss.cache.CacheImpl; |
7 |
| import org.jboss.cache.DefaultCacheFactory; |
8 |
| import org.jboss.cache.Fqn; |
9 |
| import org.jboss.cache.lock.IsolationLevel; |
10 |
| import org.jboss.cache.misc.TestingUtil; |
11 |
| |
12 |
| |
13 |
| |
14 |
| |
15 |
| |
16 |
| |
17 |
| |
18 |
| |
19 |
| public class LRUPolicyTest extends TestCase |
20 |
| { |
21 |
| CacheImpl cache_; |
22 |
| int wakeupIntervalMillis_ = 0; |
23 |
| final String ROOT_STR = "/test"; |
24 |
| Throwable t1_ex, t2_ex; |
25 |
| final long DURATION = 10000; |
26 |
| boolean isTrue; |
27 |
| |
28 |
7
| public LRUPolicyTest(String s)
|
29 |
| { |
30 |
7
| super(s);
|
31 |
| } |
32 |
| |
33 |
7
| public void setUp() throws Exception
|
34 |
| { |
35 |
7
| super.setUp();
|
36 |
7
| initCaches();
|
37 |
7
| wakeupIntervalMillis_ = cache_.getConfiguration().getEvictionConfig().getWakeupIntervalSeconds() * 1000;
|
38 |
7
| log("wakeupInterval is " + wakeupIntervalMillis_);
|
39 |
7
| if (wakeupIntervalMillis_ < 0)
|
40 |
| { |
41 |
0
| fail("testEviction(): eviction thread wake up interval is illegal " + wakeupIntervalMillis_);
|
42 |
| } |
43 |
| |
44 |
7
| t1_ex = t2_ex = null;
|
45 |
7
| isTrue = true;
|
46 |
| } |
47 |
| |
48 |
7
| public void initCaches() throws Exception
|
49 |
| { |
50 |
7
| cache_ = (CacheImpl) DefaultCacheFactory.getInstance().createCache("META-INF/local-lru-eviction-service.xml", false);
|
51 |
7
| cache_.getConfiguration().setTransactionManagerLookupClass("org.jboss.cache.DummyTransactionManagerLookup");
|
52 |
7
| cache_.getConfiguration().setIsolationLevel(IsolationLevel.SERIALIZABLE);
|
53 |
7
| cache_.start();
|
54 |
| } |
55 |
| |
56 |
7
| public void tearDown() throws Exception
|
57 |
| { |
58 |
7
| super.tearDown();
|
59 |
7
| cache_.stop();
|
60 |
| } |
61 |
| |
62 |
1
| public void testInUseEviction() throws Exception
|
63 |
| { |
64 |
1
| String rootStr = "/org/jboss/test/data/inuse/";
|
65 |
1
| Fqn fqn;
|
66 |
| |
67 |
| |
68 |
| |
69 |
1
| for (int i = 0; i < 10; i++)
|
70 |
| { |
71 |
10
| String str = rootStr + i;
|
72 |
10
| fqn = Fqn.fromString(str);
|
73 |
10
| cache_.put(fqn, str, str);
|
74 |
| } |
75 |
| |
76 |
1
| TestingUtil.sleepThread(wakeupIntervalMillis_ + 500);
|
77 |
1
| System.out.println("***************************** marking as in-use");
|
78 |
1
| cache_.getRegionManager().getRegion(Fqn.fromString(rootStr + 5), false).markNodeCurrentlyInUse(Fqn.fromString(rootStr + 5), 0);
|
79 |
| |
80 |
1
| for (int i = 10; i < 15; i++)
|
81 |
| { |
82 |
5
| String str = rootStr + i;
|
83 |
5
| fqn = Fqn.fromString(str);
|
84 |
5
| cache_.put(fqn, str, str);
|
85 |
| } |
86 |
| |
87 |
1
| TestingUtil.sleepThread(wakeupIntervalMillis_ + 500);
|
88 |
| |
89 |
1
| for (int i = 0; i < 5; i++)
|
90 |
| { |
91 |
5
| assertNull(cache_.get(Fqn.fromString(rootStr + i)));
|
92 |
| } |
93 |
| |
94 |
1
| assertNotNull(cache_.get(Fqn.fromString(rootStr + 5)));
|
95 |
| |
96 |
1
| for (int i = 6; i < 11; i++)
|
97 |
| { |
98 |
5
| assertNull(cache_.get(Fqn.fromString(rootStr + i)));
|
99 |
| } |
100 |
1
| for (int i = 11; i < 15; i++)
|
101 |
| { |
102 |
4
| assertNotNull(cache_.get(Fqn.fromString(rootStr + i)));
|
103 |
| } |
104 |
| } |
105 |
| |
106 |
1
| public void testEviction()
|
107 |
| { |
108 |
1
| String rootStr = "/org/jboss/test/data/";
|
109 |
1
| for (int i = 0; i < 10; i++)
|
110 |
| { |
111 |
10
| String str = rootStr + i;
|
112 |
10
| Fqn fqn = Fqn.fromString(str);
|
113 |
10
| try
|
114 |
| { |
115 |
10
| cache_.put(fqn, str, str);
|
116 |
| } |
117 |
| catch (Exception e) |
118 |
| { |
119 |
0
| fail("Failed to insert data" + e);
|
120 |
0
| e.printStackTrace();
|
121 |
| } |
122 |
| } |
123 |
1
| System.out.println(cache_.toString());
|
124 |
1
| TestingUtil.sleepThread(wakeupIntervalMillis_ + 500);
|
125 |
1
| System.out.println(cache_.toString());
|
126 |
1
| try
|
127 |
| { |
128 |
1
| String val = (String) cache_.get(rootStr + "3", rootStr + "3");
|
129 |
1
| assertNull("DataNode should be empty ", val);
|
130 |
| } |
131 |
| catch (Exception e) |
132 |
| { |
133 |
0
| e.printStackTrace();
|
134 |
0
| fail("Failed to get" + e);
|
135 |
| } |
136 |
| } |
137 |
| |
138 |
1
| public void testNodeVisited()
|
139 |
| { |
140 |
1
| String rootStr = "/org/jboss/test/data/";
|
141 |
| |
142 |
1
| System.out.println("REGIONS: " + cache_.getRegionManager().dumpRegions());
|
143 |
| |
144 |
1
| for (int i = 0; i < 10; i++)
|
145 |
| { |
146 |
10
| String str = rootStr + i;
|
147 |
10
| Fqn fqn = Fqn.fromString(str);
|
148 |
10
| try
|
149 |
| { |
150 |
10
| cache_.put(fqn, str, str);
|
151 |
| } |
152 |
| catch (Exception e) |
153 |
| { |
154 |
0
| fail("Failed to insert data" + e);
|
155 |
0
| e.printStackTrace();
|
156 |
| } |
157 |
| } |
158 |
1
| System.out.println("cache is:\n" + cache_.toString(true));
|
159 |
| |
160 |
1
| int period = (wakeupIntervalMillis_ / 2 + 500);
|
161 |
1
| log("sleeping for " + period + "ms");
|
162 |
1
| TestingUtil.sleepThread(period);
|
163 |
1
| String str = rootStr + "7";
|
164 |
1
| Fqn fqn = Fqn.fromString(str);
|
165 |
1
| try
|
166 |
| { |
167 |
1
| cache_.get(fqn, str);
|
168 |
1
| System.out.println("-- sleeping for " + period + "ms");
|
169 |
1
| TestingUtil.sleepThread(period);
|
170 |
1
| cache_.get(fqn, str);
|
171 |
1
| System.out.println("-- sleeping for " + period + "ms");
|
172 |
1
| TestingUtil.sleepThread(period);
|
173 |
1
| String val = (String) cache_.get(rootStr + "3", rootStr + "3");
|
174 |
1
| System.out.println("-- val=" + val);
|
175 |
1
| assertNull("DataNode should be empty ", val);
|
176 |
1
| val = (String) cache_.get(rootStr + "7", rootStr + "7");
|
177 |
1
| System.out.println("-- val=" + val);
|
178 |
1
| assertNotNull("DataNode should not be empty ", val);
|
179 |
1
| System.out.println("-- sleeping for " + (wakeupIntervalMillis_ + 1000) + "ms");
|
180 |
1
| TestingUtil.sleepThread(wakeupIntervalMillis_ + 1000);
|
181 |
1
| val = (String) cache_.get(rootStr + "7", rootStr + "7");
|
182 |
1
| System.out.println("-- val=" + val);
|
183 |
1
| assertNull("DataNode should be empty ", val);
|
184 |
| } |
185 |
| catch (Exception e) |
186 |
| { |
187 |
0
| e.printStackTrace();
|
188 |
0
| fail("Failed to evict" + e);
|
189 |
| } |
190 |
| } |
191 |
| |
192 |
1
| public void testNodeRemoved()
|
193 |
| { |
194 |
1
| String rootStr = "/org/jboss/test/data/";
|
195 |
1
| for (int i = 0; i < 10; i++)
|
196 |
| { |
197 |
10
| String str = rootStr + i + "/" + i;
|
198 |
10
| Fqn fqn = Fqn.fromString(str);
|
199 |
10
| try
|
200 |
| { |
201 |
10
| cache_.put(fqn, str, str);
|
202 |
| } |
203 |
| catch (Exception e) |
204 |
| { |
205 |
0
| fail("Failed to insert data" + e);
|
206 |
0
| e.printStackTrace();
|
207 |
| } |
208 |
| } |
209 |
| |
210 |
1
| int period = (wakeupIntervalMillis_ / 2 + 500);
|
211 |
1
| log("period is " + period);
|
212 |
| |
213 |
1
| String str1 = rootStr + "7";
|
214 |
1
| Fqn fqn1 = Fqn.fromString(str1);
|
215 |
1
| String str2 = rootStr + "7/7";
|
216 |
1
| Fqn fqn2 = Fqn.fromString(str2);
|
217 |
1
| try
|
218 |
| { |
219 |
1
| cache_.get(fqn1, str1);
|
220 |
1
| cache_.get(fqn2, str2);
|
221 |
1
| TestingUtil.sleepThread(period);
|
222 |
1
| cache_.get(fqn1, str1);
|
223 |
1
| cache_.get(fqn2, str2);
|
224 |
1
| TestingUtil.sleepThread(period);
|
225 |
1
| String val = (String) cache_.get(rootStr + "7/7", rootStr + "7/7");
|
226 |
1
| assertNotNull("DataNode should not be empty ", val);
|
227 |
1
| cache_.remove(fqn1);
|
228 |
1
| TestingUtil.sleepThread(wakeupIntervalMillis_ + 500);
|
229 |
1
| val = (String) cache_.get(rootStr + "7/7", rootStr + "7/7");
|
230 |
1
| assertNull("DataNode should be empty ", val);
|
231 |
| } |
232 |
| catch (Exception e) |
233 |
| { |
234 |
0
| e.printStackTrace();
|
235 |
0
| fail("Failed to evict" + e);
|
236 |
| } |
237 |
| } |
238 |
| |
239 |
1
| public void testCompleteRemoval() throws Exception
|
240 |
| { |
241 |
1
| String rootStr = "/test/";
|
242 |
| |
243 |
| |
244 |
| |
245 |
1
| Fqn parent = Fqn.fromString(rootStr + "parent");
|
246 |
1
| cache_.put(parent, "key", "value");
|
247 |
1
| cache_.put(new Fqn(parent, "child"), "key", "value");
|
248 |
| |
249 |
| |
250 |
| |
251 |
1
| TestingUtil.sleepThread((wakeupIntervalMillis_ * 4) + 100);
|
252 |
1
| assertFalse("Parent completely removed", cache_.getRoot().hasChild(parent));
|
253 |
| } |
254 |
| |
255 |
| |
256 |
| class MyPutter extends Thread |
257 |
| { |
258 |
| |
259 |
10
| public MyPutter(String name)
|
260 |
| { |
261 |
10
| super(name);
|
262 |
| } |
263 |
| |
264 |
10
| public void run()
|
265 |
| { |
266 |
10
| int i = 0;
|
267 |
10
| final String myName = ROOT_STR + "/test1/node" + getName();
|
268 |
10
| while (isTrue)
|
269 |
| { |
270 |
12918
| try
|
271 |
| { |
272 |
12918
| cache_.put(myName + i++, "value", i);
|
273 |
12918
| sleep(1);
|
274 |
| } |
275 |
| catch (Throwable e) |
276 |
| { |
277 |
0
| e.printStackTrace();
|
278 |
0
| if (t1_ex == null)
|
279 |
| { |
280 |
0
| t1_ex = e;
|
281 |
| } |
282 |
| } |
283 |
| } |
284 |
| } |
285 |
| } |
286 |
| |
287 |
| |
288 |
1
| public void testConcurrentPutAndEvict() throws Exception
|
289 |
| { |
290 |
1
| cache_.stop();
|
291 |
1
| cache_.destroy();
|
292 |
1
| cache_.getConfiguration().setIsolationLevel(IsolationLevel.REPEATABLE_READ);
|
293 |
1
| cache_.create();
|
294 |
1
| cache_.start();
|
295 |
1
| cache_.put(ROOT_STR + "/concurrentPutAndEvict", "value", 1);
|
296 |
| |
297 |
1
| for (int i = 0; i < 10; i++)
|
298 |
| { |
299 |
10
| new MyPutter("Putter" + i).start();
|
300 |
| } |
301 |
| |
302 |
1
| int counter = 0;
|
303 |
1
| while (true)
|
304 |
| { |
305 |
11
| counter++;
|
306 |
11
| if (t1_ex != null)
|
307 |
| { |
308 |
0
| fail("Exception generated in put() " + t1_ex);
|
309 |
| } |
310 |
11
| log("nodes/locks: " + cache_.getNumberOfNodes() + "/" + cache_.getNumberOfLocksHeld());
|
311 |
11
| TestingUtil.sleepThread(1000);
|
312 |
11
| if (counter > 10)
|
313 |
| { |
314 |
1
| isTrue = false;
|
315 |
1
| break;
|
316 |
| } |
317 |
| } |
318 |
| } |
319 |
| |
320 |
1
| public void testForEvictionInternalError()
|
321 |
| { |
322 |
1
| try
|
323 |
| { |
324 |
| |
325 |
1
| String rootStr = "/test/testdata";
|
326 |
| |
327 |
1
| for (int i = 0; i < 10; i++)
|
328 |
| { |
329 |
10
| String str = rootStr + i;
|
330 |
10
| Fqn fqn = Fqn.fromString(str);
|
331 |
10
| try
|
332 |
| { |
333 |
10
| cache_.put(fqn, str, str);
|
334 |
| } |
335 |
| catch (Exception e) |
336 |
| { |
337 |
0
| fail("Failed to insert data" + e);
|
338 |
0
| e.printStackTrace();
|
339 |
| } |
340 |
| } |
341 |
| |
342 |
| |
343 |
1
| TestingUtil.sleepThread(2 * wakeupIntervalMillis_ + 2000);
|
344 |
| |
345 |
1
| String val = (String) cache_.get(rootStr + "3", rootStr + "3");
|
346 |
1
| assertNull("DataNode should be empty ", val);
|
347 |
| |
348 |
| |
349 |
1
| for (int i = 0; i < 10; i++)
|
350 |
| { |
351 |
10
| String str = rootStr + i;
|
352 |
10
| Fqn fqn = Fqn.fromString(str);
|
353 |
10
| try
|
354 |
| { |
355 |
10
| cache_.put(fqn, str, str);
|
356 |
| } |
357 |
| catch (Exception e) |
358 |
| { |
359 |
0
| fail("Failed to insert data" + e);
|
360 |
0
| e.printStackTrace();
|
361 |
| } |
362 |
| } |
363 |
| |
364 |
| |
365 |
1
| Fqn root = cache_.get("/").getFqn();
|
366 |
1
| cache_.remove(root);
|
367 |
| |
368 |
| |
369 |
1
| TestingUtil.sleepThread(2 * wakeupIntervalMillis_ + 1000);
|
370 |
| |
371 |
1
| val = (String) cache_.get(rootStr + "3", rootStr + "3");
|
372 |
1
| assertNull("DataNode should be empty ", val);
|
373 |
| |
374 |
| } |
375 |
| catch (Exception e) |
376 |
| { |
377 |
0
| e.printStackTrace();
|
378 |
0
| fail("Failed to get" + e);
|
379 |
| } |
380 |
| } |
381 |
| |
382 |
20
| void log(String msg)
|
383 |
| { |
384 |
20
| System.out.println("-- " + msg);
|
385 |
| } |
386 |
| |
387 |
1
| public static Test suite()
|
388 |
| { |
389 |
1
| return new TestSuite(LRUPolicyTest.class);
|
390 |
| } |
391 |
| |
392 |
0
| public static void main(String[] args)
|
393 |
| { |
394 |
0
| junit.textui.TestRunner.run(suite());
|
395 |
| } |
396 |
| |
397 |
| } |