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 * Idea by Rachel Davies, Original code by Stacy Curl                        *
009 *****************************************************************************/
010
011package org.picocontainer.injectors;
012
013import com.thoughtworks.xstream.XStream;
014import com.thoughtworks.xstream.converters.Converter;
015import com.thoughtworks.xstream.converters.MarshallingContext;
016import com.thoughtworks.xstream.converters.UnmarshallingContext;
017import com.thoughtworks.xstream.io.HierarchicalStreamReader;
018import com.thoughtworks.xstream.io.HierarchicalStreamWriter;
019import org.junit.Before;
020import org.junit.Test;
021import org.picocontainer.Characteristics;
022import org.picocontainer.ComponentAdapter;
023import org.picocontainer.ComponentFactory;
024import org.picocontainer.DefaultPicoContainer;
025import org.picocontainer.Parameter;
026import org.picocontainer.PicoCompositionException;
027import org.picocontainer.lifecycle.NullLifecycleStrategy;
028import org.picocontainer.lifecycle.ReflectionLifecycleStrategy;
029import org.picocontainer.monitors.ConsoleComponentMonitor;
030import org.picocontainer.monitors.NullComponentMonitor;
031import org.picocontainer.tck.AbstractComponentFactoryTest;
032import org.picocontainer.testmodel.SimpleTouchable;
033import org.picocontainer.testmodel.Touchable;
034
035import java.util.HashMap;
036import java.util.Map;
037import java.util.Properties;
038
039import static org.junit.Assert.assertEquals;
040import static org.junit.Assert.assertNotNull;
041import static org.junit.Assert.assertTrue;
042
043public class AdaptingInjectionTestCase extends AbstractComponentFactoryTest {
044
045    XStream xs;
046
047    @Before
048    public void setUp() throws Exception {
049        super.setUp();
050        xs = new XStream();
051        xs.alias("RLS", ReflectionLifecycleStrategy.class);
052        xs.alias("CCM", ConsoleComponentMonitor.class);
053        xs.alias("Method-Injection", AnnotatedMethodInjector.class);
054        xs.alias("Field-Injection", AnnotatedFieldInjector.class);
055        xs.alias("Constructor-Injection", ConstructorInjector.class);
056        //xs.alias("CCM", ConsoleComponentMonitor.class);
057        xs.registerConverter(new Converter() {
058            public boolean canConvert(Class aClass) {
059                return aClass.getName().equals("org.picocontainer.monitors.ConsoleComponentMonitor") ||
060                       aClass.getName().equals("org.picocontainer.lifecycle.ReflectionLifecycleStrategy");
061
062            }
063
064            public void marshal(Object object,
065                                HierarchicalStreamWriter hierarchicalStreamWriter,
066                                MarshallingContext marshallingContext)
067            {
068            }
069
070            public Object unmarshal(HierarchicalStreamReader hierarchicalStreamReader,
071                                    UnmarshallingContext unmarshallingContext)
072            {
073                return null;
074            }
075        });
076
077    }
078
079    protected ComponentFactory createComponentFactory() {
080        return new AdaptingInjection();
081    }
082
083    @Test public void testInstantiateComponentWithNoDependencies() throws PicoCompositionException {
084        ComponentAdapter componentAdapter =
085            createComponentFactory().createComponentAdapter(new NullComponentMonitor(),
086                                                            new NullLifecycleStrategy(),
087                                                            new Properties(Characteristics.CDI),
088                                                            Touchable.class,
089                                                            SimpleTouchable.class,
090                                                            (Parameter[])null);
091
092        Object comp = componentAdapter.getComponentInstance(new DefaultPicoContainer(), ComponentAdapter.NOTHING.class);
093        assertNotNull(comp);
094        assertTrue(comp instanceof SimpleTouchable);
095    }
096
097    @Test public void testSingleUsecanBeInstantiatedByDefaultComponentAdapter() {
098        ComponentAdapter componentAdapter = createComponentFactory().createComponentAdapter(new NullComponentMonitor(),
099                                                                                            new NullLifecycleStrategy(),
100                                                                                            new Properties(
101                                                                                                Characteristics.CDI),
102                                                                                            "o",
103                                                                                            Object.class,
104                                                                                            (Parameter[])null);
105        Object component = componentAdapter.getComponentInstance(new DefaultPicoContainer(), ComponentAdapter.NOTHING.class);
106        assertNotNull(component);
107    }
108
109
110    @Test public void testFactoryMakesConstructorInjector() {
111
112        ComponentFactory cf = createComponentFactory();
113
114        ConsoleComponentMonitor cm = new ConsoleComponentMonitor();
115        ComponentAdapter ca = cf.createComponentAdapter(cm, new NullLifecycleStrategy(), new Properties(),
116                                                        Map.class, HashMap.class, Parameter.DEFAULT);
117
118        String foo = xs.toXML(ca).replace("\"", "");
119
120        assertEquals("<Constructor-Injection>\n" +
121                     "  <componentKey class=java-class>java.util.Map</componentKey>\n" +
122                     "  <componentImplementation>java.util.HashMap</componentImplementation>\n" +
123                     "  <componentMonitor class=CCM/>\n" +
124                     "  <useNames>false</useNames>\n" +
125                     "  <rememberChosenConstructor>true</rememberChosenConstructor>\n" +
126                     "  <enableEmjection>false</enableEmjection>\n" +
127                     "  <allowNonPublicClasses>false</allowNonPublicClasses>\n" +
128                     "</Constructor-Injection>", foo);
129
130
131    }
132
133    @Test public void testFactoryMakesFieldAnnotationInjector() {
134
135        ComponentFactory cf = createComponentFactory();
136
137        ConsoleComponentMonitor cm = new ConsoleComponentMonitor();
138        ComponentAdapter ca = cf.createComponentAdapter(cm,
139                                                        new NullLifecycleStrategy(),
140                                                        new Properties(),
141                                                        AnnotatedFieldInjectorTestCase.Helicopter.class,
142                                                        AnnotatedFieldInjectorTestCase.Helicopter.class,
143                                                        Parameter.DEFAULT);
144
145        String foo = xs.toXML(ca).replace("\"", "");
146
147        assertEquals("<Field-Injection>\n" +
148                     "  <componentKey class=java-class>org.picocontainer.injectors.AnnotatedFieldInjectorTestCase$Helicopter</componentKey>\n" +
149                     "  <componentImplementation>org.picocontainer.injectors.AnnotatedFieldInjectorTestCase$Helicopter</componentImplementation>\n" +
150                     "  <componentMonitor class=CCM/>\n" +
151                "  <useNames>false</useNames>\n" +
152                "  <injectionAnnotation>org.picocontainer.annotations.Inject</injectionAnnotation>\n" +
153                     "</Field-Injection>", foo);
154
155
156    }
157
158    @Test public void testFactoryMakesMethodAnnotationInjector() {
159
160        ComponentFactory cf = createComponentFactory();
161
162        ConsoleComponentMonitor cm = new ConsoleComponentMonitor();
163        ComponentAdapter ca = cf.createComponentAdapter(cm,
164                                                        new NullLifecycleStrategy(),
165                                                        new Properties(),
166                                                        AnnotatedMethodInjectorTestCase.AnnotatedBurp.class,
167                                                        AnnotatedMethodInjectorTestCase.AnnotatedBurp.class,
168                                                        Parameter.DEFAULT);
169
170        String foo = xs.toXML(ca).replace("\"", "");
171
172        assertEquals("<Method-Injection>\n" +
173                     "  <componentKey class=java-class>org.picocontainer.injectors.AnnotatedMethodInjectorTestCase$AnnotatedBurp</componentKey>\n" +
174                     "  <componentImplementation>org.picocontainer.injectors.AnnotatedMethodInjectorTestCase$AnnotatedBurp</componentImplementation>\n" +
175                     "  <componentMonitor class=CCM/>\n" +
176                     "  <useNames>false</useNames>\n" +
177                     "  <prefix></prefix>\n" +
178                     "  <optional>false</optional>\n" +
179                     "  <notThisOneThough></notThisOneThough>\n" +
180                     "  <injectionAnnotation>org.picocontainer.annotations.Inject</injectionAnnotation>\n" +
181                     "</Method-Injection>", foo);
182
183
184    }
185
186
187}