    001    /*****************************************************************************
    002     * Copyright (C) PicoContainer Organization. All rights reserved.            *
    003     * ------------------------------------------------------------------------- *
    004     * The software in this package is published under the terms of the BSD      *
    005     * style license a copy of which has been included with this distribution in *
    006     * the LICENSE.txt file.                                                     *
    007     *                                                                           *
    008     * Original code by                                                          *
    009     *****************************************************************************/
    010    package org.picocontainer.behaviors;
    011
    012    import static org.junit.Assert.assertEquals;
    013    import static org.junit.Assert.assertFalse;
    014    import static org.junit.Assert.assertNotNull;
    015    import static org.junit.Assert.assertSame;
    016
    017    import org.junit.Test;
    018    import org.picocontainer.DefaultPicoContainer;
    019
    020    public class ThreadCachingTestCase {
    021
    022        public static class Foo {
    023            public Foo(StringBuilder sb) {
    024                sb.append("<Foo");
    025            }
    026        }
    027
    028        public static class Bar {
    029            private final Foo foo;
    030            public Bar(StringBuilder sb, Foo foo) {
    031                this.foo = foo;
    032                sb.append("<Bar");
    033            }
    034        }
    035
    036        @Test public void testThatForASingleThreadTheBehaviorIsTheSameAsPlainCaching() {
    037
    038            DefaultPicoContainer parent = new DefaultPicoContainer(new Caching());
    039            DefaultPicoContainer child = new DefaultPicoContainer(new ThreadCaching(), parent);
    040
    041            parent.addComponent(StringBuilder.class);
    042            child.addComponent(Foo.class);
    043
    044            StringBuilder sb = parent.getComponent(StringBuilder.class);
    045            Foo foo = child.getComponent(Foo.class);
    046            Foo foo2 = child.getComponent(Foo.class);
    047            assertNotNull(foo);
    048            assertNotNull(foo2);
    049            assertEquals(foo,foo2);
    050            assertEquals("<Foo", sb.toString());
    051            assertEquals("ThreadCached:ConstructorInjector-class org.picocontainer.behaviors.ThreadCachingTestCase$Foo", child.getComponentAdapter(Foo.class).toString());
    052        }
    053
    054        @Test public void testThatTwoThreadsHaveSeparatedCacheValues() {
    055
    056            final Foo[] foos = new Foo[4];
    057
    058            DefaultPicoContainer parent = new DefaultPicoContainer(new Caching());
    059            final DefaultPicoContainer child = new DefaultPicoContainer(new ThreadCaching(), parent);
    060
    061            parent.addComponent(StringBuilder.class);
    062            child.addComponent(Foo.class);
    063
    064            StringBuilder sb = parent.getComponent(StringBuilder.class);
    065            foos[0] = child.getComponent(Foo.class);
    066
    067            Thread thread = new Thread() {
    068                public void run() {
    069                    foos[1] = child.getComponent(Foo.class);
    070                    foos[3] = child.getComponent(Foo.class);
    071                }
    072            };
    073            thread.start();
    074            foos[2] = child.getComponent(Foo.class);
    075            try {
    076                Thread.sleep(100);
    077            } catch (InterruptedException e) {
    078            }
    079
    080            assertNotNull(foos[0]);
    081            assertNotNull(foos[1]);
    082            assertNotNull(foos[2]);
    083            assertNotNull(foos[3]);
    084            assertSame(foos[0],foos[2]);
    085            assertEquals(foos[1],foos[3]);
    086            assertFalse(foos[0] == foos[1]);
    087            assertEquals("<Foo<Foo", sb.toString());
    088            assertEquals("ThreadCached:ConstructorInjector-class org.picocontainer.behaviors.ThreadCachingTestCase$Foo", child.getComponentAdapter(Foo.class).toString());
    089        }
    090
    091        @Test public void testThatTwoThreadsHaveSeparatedCacheValuesForThreeScopeScenario() {
    092
    093            final Foo[] foos = new Foo[4];
    094            final Bar[] bars = new Bar[4];
    095
    096            DefaultPicoContainer appScope = new DefaultPicoContainer(new Caching());
    097            final DefaultPicoContainer sessionScope = new DefaultPicoContainer(new ThreadCaching(), appScope);
    098            final DefaultPicoContainer requestScope = new DefaultPicoContainer(new ThreadCaching(), sessionScope);
    099
    100            appScope.addComponent(StringBuilder.class);
    101            sessionScope.addComponent(Foo.class);
    102            requestScope.addComponent(Bar.class);
    103
    104            StringBuilder sb = appScope.getComponent(StringBuilder.class);
    105            foos[0] = sessionScope.getComponent(Foo.class);
    106            bars[0] = requestScope.getComponent(Bar.class);
    107
    108            Thread thread = new Thread() {
    109                public void run() {
    110                    foos[1] = sessionScope.getComponent(Foo.class);
    111                    bars[1] = requestScope.getComponent(Bar.class);
    112                    foos[3] = sessionScope.getComponent(Foo.class);
    113                    bars[3] = requestScope.getComponent(Bar.class);
    114                }
    115            };
    116            thread.start();
    117            foos[2] = sessionScope.getComponent(Foo.class);
    118            bars[2] = requestScope.getComponent(Bar.class);
    119            try {
    120                Thread.sleep(100);
    121            } catch (InterruptedException e) {
    122            }
    123
    124            assertSame(bars[0],bars[2]);
    125            assertEquals(bars[1],bars[3]);
    126            assertFalse(bars[0] == bars[1]);
    127            assertSame(bars[0].foo,foos[0]);
    128            assertSame(bars[1].foo,foos[1]);
    129            assertSame(bars[2].foo,foos[2]);
    130            assertSame(bars[3].foo,foos[3]);
    131            assertEquals("<Foo<Bar<Foo<Bar", sb.toString());
    132            assertEquals("ThreadCached:ConstructorInjector-class org.picocontainer.behaviors.ThreadCachingTestCase$Foo", sessionScope.getComponentAdapter(Foo.class).toString());
    133        }
    134
    135
    136    }