View Javadoc
1   package org.apache.maven.scm;
2   
3   /*
4    * Licensed to the Apache Software Foundation (ASF) under one
5    * or more contributor license agreements.  See the NOTICE file
6    * distributed with this work for additional information
7    * regarding copyright ownership.  The ASF licenses this file
8    * to you under the Apache License, Version 2.0 (the
9    * "License"); you may not use this file except in compliance
10   * with the License.  You may obtain a copy of the License at
11   *
12   *   http://www.apache.org/licenses/LICENSE-2.0
13   *
14   * Unless required by applicable law or agreed to in writing,
15   * software distributed under the License is distributed on an
16   * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
17   * KIND, either express or implied.  See the License for the
18   * specific language governing permissions and limitations
19   * under the License.
20   */
21  
22  import java.io.File;
23  import java.io.InputStream;
24  import java.util.Map;
25  
26  import com.google.inject.Module;
27  import org.codehaus.plexus.ContainerConfiguration;
28  import org.codehaus.plexus.DefaultContainerConfiguration;
29  import org.codehaus.plexus.DefaultPlexusContainer;
30  import org.codehaus.plexus.PlexusConstants;
31  import org.codehaus.plexus.PlexusContainer;
32  import org.codehaus.plexus.PlexusContainerException;
33  import org.codehaus.plexus.configuration.PlexusConfiguration;
34  import org.codehaus.plexus.context.Context;
35  import org.codehaus.plexus.context.DefaultContext;
36  import org.junit.After;
37  import org.junit.Before;
38  import org.junit.Rule;
39  import org.junit.rules.TestName;
40  
41  import static org.junit.Assert.fail;
42  
43  /**
44   * Based on PlexusTestCase from org.sonatype.sisu:sisu-inject-plexus.
45   * Note: this class is copied from maven-release.
46   *
47   * @author Robert Scholte
48   */
49  public abstract class PlexusJUnit4TestSupport
50  {
51      private PlexusContainer container;
52  
53      private static String basedir;
54  
55      @Rule
56      public TestName testName = new TestName();
57  
58      @Before
59      public void setUp()
60              throws Exception
61      {
62          basedir = getBasedir();
63      }
64  
65      protected String getName()
66      {
67          return testName.getMethodName();
68      }
69  
70      protected void setupContainer()
71      {
72          // ----------------------------------------------------------------------------
73          // Context Setup
74          // ----------------------------------------------------------------------------
75  
76          final DefaultContext context = new DefaultContext();
77  
78          context.put( "basedir", getBasedir() );
79  
80          customizeContext( context );
81  
82          final boolean hasPlexusHome = context.contains( "plexus.home" );
83  
84          if ( !hasPlexusHome )
85          {
86              final File f = getTestFile( "target/plexus-home" );
87  
88              if ( !f.isDirectory() )
89              {
90                  f.mkdir();
91              }
92  
93              context.put( "plexus.home", f.getAbsolutePath() );
94          }
95  
96          // ----------------------------------------------------------------------------
97          // Configuration
98          // ----------------------------------------------------------------------------
99  
100         final String config = getCustomConfigurationName();
101 
102         final ContainerConfiguration containerConfiguration =
103                 new DefaultContainerConfiguration()
104                         .setName( "test" )
105                         .setContext( context.getContextData() )
106                         .setAutoWiring( true )
107                         .setClassPathScanning( PlexusConstants.SCANNING_CACHE );
108 
109         if ( config != null )
110         {
111             containerConfiguration.setContainerConfiguration( config );
112         }
113         else
114         {
115             final String resource = getConfigurationName( null );
116 
117             containerConfiguration.setContainerConfiguration( resource );
118         }
119 
120         customizeContainerConfiguration( containerConfiguration );
121 
122         try
123         {
124             container = new DefaultPlexusContainer( containerConfiguration, getCustomModules() );
125         }
126         catch ( final PlexusContainerException e )
127         {
128             e.printStackTrace();
129             fail( "Failed to create plexus container." );
130         }
131     }
132 
133     /**
134      * Allows test to define custom modules.
135      */
136     protected Module[] getCustomModules()
137     {
138         return new Module[0];
139     }
140 
141     /**
142      * Allow custom test case implementations do augment the default container configuration before executing tests.
143      *
144      * @param containerConfiguration
145      */
146     protected void customizeContainerConfiguration( final ContainerConfiguration containerConfiguration )
147     {
148     }
149 
150     protected void customizeContext( final Context context )
151     {
152     }
153 
154     protected PlexusConfiguration customizeComponentConfiguration()
155     {
156         return null;
157     }
158 
159     @After
160     public void tearDown()
161             throws Exception
162     {
163         if ( container != null )
164         {
165             container.dispose();
166 
167             container = null;
168         }
169     }
170 
171     protected PlexusContainer getContainer()
172     {
173         if ( container == null )
174         {
175             setupContainer();
176         }
177 
178         return container;
179     }
180 
181     protected InputStream getConfiguration()
182             throws Exception
183     {
184         return getConfiguration( null );
185     }
186 
187     @SuppressWarnings( "unused" )
188     protected InputStream getConfiguration( final String subname )
189             throws Exception
190     {
191         return getResourceAsStream( getConfigurationName( subname ) );
192     }
193 
194     protected String getCustomConfigurationName()
195     {
196         return null;
197     }
198 
199     /**
200      * Allow the retrieval of a container configuration that is based on the name of the test class being run. So if you
201      * have a test class called org.foo.FunTest, then this will produce a resource name of org/foo/FunTest.xml which
202      * would be used to configure the Plexus container before running your test.
203      *
204      * @param subname
205      * @return
206      */
207     protected String getConfigurationName( final String subname )
208     {
209         return getClass().getName().replace( '.', '/' ) + ".xml";
210     }
211 
212     protected InputStream getResourceAsStream( final String resource )
213     {
214         return getClass().getResourceAsStream( resource );
215     }
216 
217     protected ClassLoader getClassLoader()
218     {
219         return getClass().getClassLoader();
220     }
221 
222     // ----------------------------------------------------------------------
223     // Container access
224     // ----------------------------------------------------------------------
225 
226     protected Object lookup( final String componentKey )
227             throws Exception
228     {
229         return getContainer().lookup( componentKey );
230     }
231 
232     protected Object lookup( final String role, final String roleHint )
233             throws Exception
234     {
235         return getContainer().lookup( role, roleHint );
236     }
237 
238     protected <T> T lookup( final Class<T> componentClass )
239             throws Exception
240     {
241         return getContainer().lookup( componentClass );
242     }
243 
244     protected <T> T lookup( final Class<T> componentClass, final String roleHint )
245             throws Exception
246     {
247         return getContainer().lookup( componentClass, roleHint );
248     }
249 
250     protected <T> Map<String, T> lookupMap( final Class<T> componentClass )
251             throws Exception
252     {
253         return getContainer().lookupMap( componentClass );
254     }
255 
256     protected void release( final Object component )
257             throws Exception
258     {
259         getContainer().release( component );
260     }
261 
262     // ----------------------------------------------------------------------
263     // Helper methods for sub classes
264     // ----------------------------------------------------------------------
265 
266     public static File getTestFile( final String path )
267     {
268         return new File( getBasedir(), path );
269     }
270 
271     @SuppressWarnings( "hiding" )
272     public static File getTestFile( final String basedir, final String path )
273     {
274         File basedirFile = new File( basedir );
275 
276         if ( !basedirFile.isAbsolute() )
277         {
278             basedirFile = getTestFile( basedir );
279         }
280 
281         return new File( basedirFile, path );
282     }
283 
284     public static String getTestPath( final String path )
285     {
286         return getTestFile( path ).getAbsolutePath();
287     }
288 
289     @SuppressWarnings( "hiding" )
290     public static String getTestPath( final String basedir, final String path )
291     {
292         return getTestFile( basedir, path ).getAbsolutePath();
293     }
294 
295     public static String getBasedir()
296     {
297         if ( basedir != null )
298         {
299             return basedir;
300         }
301 
302         basedir = System.getProperty( "basedir" );
303 
304         if ( basedir == null )
305         {
306             basedir = new File( "" ).getAbsolutePath();
307         }
308 
309         return basedir;
310     }
311 
312     public String getTestConfiguration()
313     {
314         return getTestConfiguration( getClass() );
315     }
316 
317     public static String getTestConfiguration( final Class<?> clazz )
318     {
319         final String s = clazz.getName().replace( '.', '/' );
320 
321         return s.substring( 0, s.indexOf( "$" ) ) + ".xml";
322     }
323 }