KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > apache > commons > beanutils > locale > LocaleBeanificationTestCase


1 /*
2  * Copyright 2001-2004 The Apache Software Foundation.
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 org.apache.commons.beanutils.locale;
18
19 import java.util.*;
20
21 import java.lang.ref.WeakReference JavaDoc;
22 import java.lang.ref.ReferenceQueue JavaDoc;
23
24 import junit.framework.TestCase;
25 import junit.framework.Test;
26 import junit.framework.TestSuite;
27
28 import org.apache.commons.collections.ReferenceMap;
29 import org.apache.commons.logging.LogFactory;
30
31 import org.apache.commons.beanutils.ContextClassLoaderLocal;
32 import org.apache.commons.beanutils.PrimitiveBean;
33
34 /**
35  * <p>
36  * Test Case for changes made during LocaleBeanutils Beanification.
37  * This is basically a cut-and-correct version of the beanutils beanifications tests.
38  * </p>
39  *
40  * @author Robert Burrell Donkin
41  * @author Juozas Baliuka
42  * @version $Revision: 1.2 $ $Date: 2004/02/28 13:18:37 $
43  */

44
45 public class LocaleBeanificationTestCase extends TestCase {
46     
47     // ---------------------------------------------------- Constants
48

49     /** Maximum number of iterations before our test fails */
50     public static final int MAX_GC_ITERATIONS = 50;
51     
52     // ---------------------------------------------------- Instance Variables
53

54
55     // ---------------------------------------------------------- Constructors
56

57
58     /**
59      * Construct a new instance of this test case.
60      *
61      * @param name Name of the test case
62      */

63     public LocaleBeanificationTestCase(String JavaDoc name) {
64         super(name);
65     }
66
67
68     // -------------------------------------------------- Overall Test Methods
69

70
71     /**
72      * Set up instance variables required by this test case.
73      */

74     public void setUp() {
75
76         LocaleConvertUtils.deregister();
77
78     }
79
80
81     /**
82      * Return the tests included in this test suite.
83      */

84     public static Test suite() {
85         return (new TestSuite(LocaleBeanificationTestCase.class));
86     }
87
88
89     /**
90      * Tear down instance variables required by this test case.
91      */

92     public void tearDown() {
93         ; // No action required
94
}
95
96
97     // ------------------------------------------------ Individual Test Methods
98

99     /** Test of the methodology we'll use for some of the later tests */
100     public void testMemoryTestMethodology() throws Exception JavaDoc {
101         // test methodology
102
// many thanks to Juozas Baliuka for suggesting this method
103
ClassLoader JavaDoc loader = new ClassLoader JavaDoc() {};
104         WeakReference JavaDoc reference = new WeakReference JavaDoc(loader);
105         Class JavaDoc myClass = loader.loadClass("org.apache.commons.beanutils.BetaBean");
106         
107         assertNotNull("Weak reference released early", reference.get());
108         
109         // dereference class loader and class:
110
loader = null;
111         myClass = null;
112         
113         int iterations = 0;
114         int bytz = 2;
115         while(true) {
116             System.gc();
117             if(iterations++ > MAX_GC_ITERATIONS){
118                 fail("Max iterations reached before resource released.");
119             }
120             if( reference.get() == null ) {
121                 break;
122                 
123             } else {
124                 // create garbage:
125
byte[] b = new byte[bytz];
126                 bytz = bytz * 2;
127             }
128         }
129     }
130     
131     /** Tests whether classloaders and beans are released from memory by the map used by beanutils */
132     public void testMemoryLeak2() throws Exception JavaDoc {
133         // tests when the map used by beanutils has the right behaviour
134

135         if (isPre14JVM()) {
136             System.out.println("WARNING: CANNOT TEST MEMORY LEAK ON PRE1.4 JVM");
137             return;
138         }
139         
140         // many thanks to Juozas Baliuka for suggesting this methodology
141
TestClassLoader loader = new TestClassLoader();
142         ReferenceQueue JavaDoc queue = new ReferenceQueue JavaDoc();
143         WeakReference JavaDoc loaderReference = new WeakReference JavaDoc(loader, queue);
144         Integer JavaDoc test = new Integer JavaDoc(1);
145         
146         WeakReference JavaDoc testReference = new WeakReference JavaDoc(test, queue);
147         //Map map = new ReferenceMap(ReferenceMap.WEAK, ReferenceMap.HARD, true);
148
Map map = new WeakHashMap();
149         map.put(loader, test);
150         
151         assertEquals("In map", test, map.get(loader));
152         assertNotNull("Weak reference released early (1)", loaderReference.get());
153         assertNotNull("Weak reference released early (2)", testReference.get());
154         
155         // dereference strong references
156
loader = null;
157         test = null;
158         
159         int iterations = 0;
160         int bytz = 2;
161         while(true) {
162             System.gc();
163             if(iterations++ > MAX_GC_ITERATIONS){
164                 fail("Max iterations reached before resource released.");
165             }
166             map.isEmpty();
167             
168             if(
169                 loaderReference.get() == null &&
170                 testReference.get() == null) {
171                 break;
172                 
173             } else {
174                 // create garbage:
175
byte[] b = new byte[bytz];
176                 bytz = bytz * 2;
177             }
178         }
179     }
180     
181     /** Tests whether classloaders and beans are released from memory */
182     public void testMemoryLeak() throws Exception JavaDoc {
183         if (isPre14JVM()) {
184             System.out.println("WARNING: CANNOT TEST MEMORY LEAK ON PRE1.4 JVM");
185             return;
186         }
187         
188         // many thanks to Juozas Baliuka for suggesting this methodology
189
TestClassLoader loader = new TestClassLoader();
190         WeakReference JavaDoc loaderReference = new WeakReference JavaDoc(loader);
191         LocaleBeanUtilsBean.getLocaleBeanUtilsInstance();
192
193         class GetBeanUtilsBeanThread extends Thread JavaDoc {
194             
195             LocaleBeanUtilsBean beanUtils;
196             LocaleConvertUtilsBean convertUtils;
197         
198             GetBeanUtilsBeanThread() {}
199             
200             public void run() {
201                 beanUtils = LocaleBeanUtilsBean.getLocaleBeanUtilsInstance();
202                 convertUtils = LocaleConvertUtilsBean.getInstance();
203                 // XXX Log keeps a reference around!
204
LogFactory.releaseAll();
205             }
206             
207             public String JavaDoc toString() {
208                 return "GetBeanUtilsBeanThread";
209             }
210         }
211         
212     
213         GetBeanUtilsBeanThread thread = new GetBeanUtilsBeanThread();
214         WeakReference JavaDoc threadWeakReference = new WeakReference JavaDoc(thread);
215         thread.setContextClassLoader(loader);
216
217         thread.start();
218         thread.join();
219         
220         WeakReference JavaDoc beanUtilsReference = new WeakReference JavaDoc(thread.beanUtils);
221         WeakReference JavaDoc convertUtilsReference = new WeakReference JavaDoc(thread.convertUtils);
222         
223         assertNotNull("Weak reference released early (1)", loaderReference.get());
224         assertNotNull("Weak reference released early (2)", beanUtilsReference.get());
225         assertNotNull("Weak reference released early (4)", convertUtilsReference.get());
226         
227         // dereference strong references
228
loader = null;
229         thread.setContextClassLoader(null);
230         thread = null;
231         
232         int iterations = 0;
233         int bytz = 2;
234         while(true) {
235             LocaleBeanUtilsBean.getLocaleBeanUtilsInstance();
236             System.gc();
237             if(iterations++ > MAX_GC_ITERATIONS){
238                 fail("Max iterations reached before resource released.");
239             }
240
241             if(
242                 loaderReference.get() == null &&
243                 beanUtilsReference.get() == null &&
244                 convertUtilsReference.get() == null) {
245                 break;
246                 
247             } else {
248                 // create garbage:
249
byte[] b = new byte[bytz];
250                 bytz = bytz * 2;
251             }
252         }
253     }
254     
255     /**
256      * Tests whether difference instances are loaded by different
257      * context classloaders.
258      */

259     public void testGetByContextClassLoader() throws Exception JavaDoc {
260             
261         class GetBeanUtilsBeanThread extends Thread JavaDoc {
262             
263             private Signal signal;
264         
265             GetBeanUtilsBeanThread(Signal signal) {
266                 this.signal = signal;
267             }
268             
269             public void run() {
270                 signal.setSignal(2);
271                 signal.setBean(LocaleBeanUtilsBean.getLocaleBeanUtilsInstance());
272                 signal.setConvertUtils(LocaleConvertUtilsBean.getInstance());
273             }
274             
275             public String JavaDoc toString() {
276                 return "GetBeanUtilsBeanThread";
277             }
278         }
279             
280         Signal signal = new Signal();
281         signal.setSignal(1);
282         
283         GetBeanUtilsBeanThread thread = new GetBeanUtilsBeanThread(signal);
284         thread.setContextClassLoader(new TestClassLoader());
285         
286         thread.start();
287         thread.join();
288         
289         assertEquals("Signal not set by test thread", 2, signal.getSignal());
290         assertTrue(
291                     "Different LocaleBeanUtilsBean instances per context classloader",
292                     LocaleBeanUtilsBean.getInstance() != signal.getBean());
293         assertTrue(
294                     "Different LocaleConvertUtilsBean instances per context classloader",
295                     LocaleConvertUtilsBean.getInstance() != signal.getConvertUtils());
296     }
297     
298     
299     /**
300      * Tests whether difference instances are loaded by different
301      * context classloaders.
302      */

303     public void testContextClassLoaderLocal() throws Exception JavaDoc {
304             
305         class CCLLTesterThread extends Thread JavaDoc {
306             
307             private Signal signal;
308             private ContextClassLoaderLocal ccll;
309         
310             CCLLTesterThread(Signal signal, ContextClassLoaderLocal ccll) {
311                 this.signal = signal;
312                 this.ccll = ccll;
313             }
314             
315             public void run() {
316                 ccll.set(new Integer JavaDoc(1789));
317                 signal.setSignal(2);
318                 signal.setMarkerObject(ccll.get());
319             }
320             
321             public String JavaDoc toString() {
322                 return "CCLLTesterThread";
323             }
324         }
325             
326         ContextClassLoaderLocal ccll = new ContextClassLoaderLocal();
327         ccll.set(new Integer JavaDoc(1776));
328         assertEquals("Start thread sets value", new Integer JavaDoc(1776), ccll.get());
329         
330         Signal signal = new Signal();
331         signal.setSignal(1);
332         
333         CCLLTesterThread thread = new CCLLTesterThread(signal, ccll);
334         thread.setContextClassLoader(new TestClassLoader());
335         
336         thread.start();
337         thread.join();
338         
339         assertEquals("Signal not set by test thread", 2, signal.getSignal());
340         assertEquals("Second thread preserves value", new Integer JavaDoc(1776), ccll.get());
341         assertEquals("Second thread gets value it set", new Integer JavaDoc(1789), signal.getMarkerObject());
342     }
343     
344     /** Tests whether calls are independent for different classloaders */
345     public void testContextClassloaderIndependence() throws Exception JavaDoc {
346     
347         class TestIndependenceThread extends Thread JavaDoc {
348             private Signal signal;
349             private PrimitiveBean bean;
350         
351             TestIndependenceThread(Signal signal, PrimitiveBean bean) {
352                 this.signal = signal;
353                 this.bean = bean;
354             }
355             
356             public void run() {
357                 try {
358                     signal.setSignal(3);
359                     LocaleConvertUtils.register(new LocaleConverter() {
360                                             public Object JavaDoc convert(Class JavaDoc type, Object JavaDoc value) {
361                                                 return new Integer JavaDoc(9);
362                                             }
363                                             public Object JavaDoc convert(Class JavaDoc type, Object JavaDoc value, String JavaDoc pattern) {
364                                                 return new Integer JavaDoc(9);
365                                             }
366                                                 }, Integer.TYPE, Locale.getDefault());
367                     LocaleBeanUtils.setProperty(bean, "int", "1");
368                 } catch (Exception JavaDoc e) {
369                     e.printStackTrace();
370                     signal.setException(e);
371                 }
372             }
373             
374             public String JavaDoc toString() {
375                 return "TestIndependenceThread";
376             }
377         }
378         
379         PrimitiveBean bean = new PrimitiveBean();
380         LocaleBeanUtils.setProperty(bean, "int", new Integer JavaDoc(1));
381         assertEquals("Wrong property value (1)", 1, bean.getInt());
382
383         LocaleConvertUtils.register(new LocaleConverter() {
384                                 public Object JavaDoc convert(Class JavaDoc type, Object JavaDoc value) {
385                                     return new Integer JavaDoc(5);
386                                 }
387                                 public Object JavaDoc convert(Class JavaDoc type, Object JavaDoc value, String JavaDoc pattern) {
388                                     return new Integer JavaDoc(5);
389                                 }
390                                     }, Integer.TYPE, Locale.getDefault());
391         LocaleBeanUtils.setProperty(bean, "int", "1");
392         assertEquals("Wrong property value(2)", 5, bean.getInt());
393     
394         Signal signal = new Signal();
395         signal.setSignal(1);
396         TestIndependenceThread thread = new TestIndependenceThread(signal, bean);
397         thread.setContextClassLoader(new TestClassLoader());
398         
399         thread.start();
400         thread.join();
401         
402         assertNull("Exception thrown by test thread:" + signal.getException(), signal.getException());
403         assertEquals("Signal not set by test thread", 3, signal.getSignal());
404         assertEquals("Wrong property value(3)", 9, bean.getInt());
405         
406     }
407     
408     /** Tests whether different threads can set beanutils instances correctly */
409     public void testBeanUtilsBeanSetInstance() throws Exception JavaDoc {
410             
411         class SetInstanceTesterThread extends Thread JavaDoc {
412             
413             private Signal signal;
414             private LocaleBeanUtilsBean bean;
415         
416             SetInstanceTesterThread(Signal signal, LocaleBeanUtilsBean bean) {
417                 this.signal = signal;
418                 this.bean = bean;
419             }
420             
421             public void run() {
422                 LocaleBeanUtilsBean.setInstance(bean);
423                 signal.setSignal(21);
424                 signal.setBean(LocaleBeanUtilsBean.getLocaleBeanUtilsInstance());
425             }
426             
427             public String JavaDoc toString() {
428                 return "SetInstanceTesterThread";
429             }
430         }
431         
432         Signal signal = new Signal();
433         signal.setSignal(1);
434
435         LocaleBeanUtilsBean beanOne = new LocaleBeanUtilsBean();
436         LocaleBeanUtilsBean beanTwo = new LocaleBeanUtilsBean();
437         
438         SetInstanceTesterThread thread = new SetInstanceTesterThread(signal, beanTwo);
439         thread.setContextClassLoader(new TestClassLoader());
440         
441         LocaleBeanUtilsBean.setInstance(beanOne);
442         assertEquals("Start thread gets right instance", beanOne, LocaleBeanUtilsBean.getLocaleBeanUtilsInstance());
443         
444         thread.start();
445         thread.join();
446         
447         assertEquals("Signal not set by test thread", 21, signal.getSignal());
448         assertEquals("Second thread preserves value", beanOne, LocaleBeanUtilsBean.getLocaleBeanUtilsInstance());
449         assertEquals("Second thread gets value it set", beanTwo, signal.getBean());
450     }
451     
452     /** Tests whether the unset method works*/
453     public void testContextClassLoaderUnset() throws Exception JavaDoc {
454         LocaleBeanUtilsBean beanOne = new LocaleBeanUtilsBean();
455         ContextClassLoaderLocal ccll = new ContextClassLoaderLocal();
456         ccll.set(beanOne);
457         assertEquals("Start thread gets right instance", beanOne, ccll.get());
458         ccll.unset();
459         assertTrue("Unset works", !beanOne.equals(ccll.get()));
460     }
461     
462     private boolean isPre14JVM() {
463         // some pre 1.4 JVM have buggy WeakHashMap implementations
464
// this is used to test for those JVM
465
String JavaDoc version = System.getProperty("java.specification.version");
466         StringTokenizer tokenizer = new StringTokenizer(version,".");
467         if (tokenizer.nextToken().equals("1")) {
468             String JavaDoc minorVersion = tokenizer.nextToken();
469             if (minorVersion.equals("0")) return true;
470             if (minorVersion.equals("1")) return true;
471             if (minorVersion.equals("2")) return true;
472             if (minorVersion.equals("3")) return true;
473         }
474         return false;
475     }
476     
477     // ---- Auxillary classes
478

479     class TestClassLoader extends ClassLoader JavaDoc {
480         public String JavaDoc toString() {
481             return "TestClassLoader";
482         }
483     }
484     
485     class Signal {
486         private Exception JavaDoc e;
487         private int signal = 0;
488         private LocaleBeanUtilsBean bean;
489         private LocaleConvertUtilsBean convertUtils;
490         private Object JavaDoc marker;
491         
492         public Exception JavaDoc getException() {
493             return e;
494         }
495         
496         public void setException(Exception JavaDoc e) {
497             this.e = e;
498         }
499         
500         public int getSignal() {
501             return signal;
502         }
503         
504         public void setSignal(int signal) {
505             this.signal = signal;
506         }
507         
508         public Object JavaDoc getMarkerObject() {
509             return marker;
510         }
511         
512         public void setMarkerObject(Object JavaDoc marker) {
513             this.marker = marker;
514         }
515         
516         public LocaleBeanUtilsBean getBean() {
517             return bean;
518         }
519         
520         public void setBean(LocaleBeanUtilsBean bean) {
521             this.bean = bean;
522         }
523         
524         public LocaleConvertUtilsBean getConvertUtils() {
525             return convertUtils;
526         }
527         
528         public void setConvertUtils(LocaleConvertUtilsBean convertUtils) {
529             this.convertUtils = convertUtils;
530         }
531     }
532 }
533
534
Popular Tags