blob: ec5545999ac9f49b674bf000f73a103a6d15aa47 [file] [log] [blame]
package org.apache.maven.surefire.common.junit3;
/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
import java.lang.reflect.Constructor;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.lang.reflect.Modifier;
import org.apache.maven.surefire.api.util.ReflectionUtils;
/**
* Reflection facade for JUnit3 classes
*
*/
public final class JUnit3Reflector
{
private static final String TEST_CASE = "junit.framework.Test";
private static final String TEST_RESULT = "junit.framework.TestResult";
private static final String TEST_LISTENER = "junit.framework.TestListener";
private static final String TEST = "junit.framework.Test";
private static final String ADD_LISTENER_METHOD = "addListener";
private static final String RUN_METHOD = "run";
private static final String TEST_SUITE = "junit.framework.TestSuite";
private static final Class[] EMPTY_CLASS_ARRAY = { };
private static final Object[] EMPTY_OBJECT_ARRAY = { };
private final Class[] interfacesImplementedByDynamicProxy;
private final Class<?> testResultClass;
private final Method addListenerMethod;
private final Method testInterfaceRunMethod;
private final Class<?> testInterface;
private final Class<?> testCase;
private final Constructor testsSuiteConstructor;
public JUnit3Reflector( ClassLoader testClassLoader )
{
testResultClass = ReflectionUtils.tryLoadClass( testClassLoader, TEST_RESULT );
testCase = ReflectionUtils.tryLoadClass( testClassLoader, TEST_CASE );
testInterface = ReflectionUtils.tryLoadClass( testClassLoader, TEST );
interfacesImplementedByDynamicProxy =
new Class[]{ ReflectionUtils.tryLoadClass( testClassLoader, TEST_LISTENER ) };
Class<?>[] constructorParamTypes = { Class.class };
Class<?> testSuite = ReflectionUtils.tryLoadClass( testClassLoader, TEST_SUITE );
// The interface implemented by the dynamic proxy (TestListener), happens to be
// the same as the param types of TestResult.addTestListener
if ( isJUnit3Available() )
{
testsSuiteConstructor = ReflectionUtils.getConstructor( testSuite, constructorParamTypes );
addListenerMethod =
tryGetMethod( testResultClass, ADD_LISTENER_METHOD, interfacesImplementedByDynamicProxy );
testInterfaceRunMethod = getMethod( testInterface, RUN_METHOD, testResultClass );
}
else
{
testsSuiteConstructor = null;
addListenerMethod = null;
testInterfaceRunMethod = null;
}
}
// Switch to reflectionutils when building with 2.7.2
private static Method tryGetMethod( Class<?> clazz, String methodName, Class<?>... parameters )
{
try
{
return clazz.getMethod( methodName, parameters );
}
catch ( NoSuchMethodException e )
{
return null;
}
}
private static Method getMethod( Class<?> clazz, String methodName, Class<?>... parameters )
{
try
{
return clazz.getMethod( methodName, parameters );
}
catch ( NoSuchMethodException e )
{
throw new RuntimeException( "When finding method " + methodName, e );
}
}
public Object constructTestObject( Class testClass )
throws IllegalAccessException, InvocationTargetException, NoSuchMethodException, InstantiationException
{
Object testObject = createInstanceFromSuiteMethod( testClass );
if ( testObject == null && testCase.isAssignableFrom( testClass ) )
{
testObject = testsSuiteConstructor.newInstance( testClass );
}
if ( testObject == null )
{
Constructor testConstructor = getTestConstructor( testClass );
if ( testConstructor.getParameterTypes().length == 0 )
{
testObject = testConstructor.newInstance( EMPTY_OBJECT_ARRAY );
}
else
{
testObject = testConstructor.newInstance( testClass.getName() );
}
}
return testObject;
}
private static Object createInstanceFromSuiteMethod( Class<?> testClass )
throws IllegalAccessException, InvocationTargetException
{
Object testObject = null;
try
{
Method suiteMethod = testClass.getMethod( "suite", EMPTY_CLASS_ARRAY );
if ( Modifier.isPublic( suiteMethod.getModifiers() ) && Modifier.isStatic( suiteMethod.getModifiers() ) )
{
testObject = suiteMethod.invoke( null, EMPTY_OBJECT_ARRAY );
}
}
catch ( NoSuchMethodException e )
{
// No suite method
}
return testObject;
}
private static Constructor getTestConstructor( Class<?> testClass )
throws NoSuchMethodException
{
try
{
return testClass.getConstructor( String.class );
}
catch ( NoSuchMethodException e )
{
return testClass.getConstructor( EMPTY_CLASS_ARRAY );
}
}
public Class[] getInterfacesImplementedByDynamicProxy()
{
return interfacesImplementedByDynamicProxy;
}
public Class<?> getTestResultClass()
{
return testResultClass;
}
public Method getAddListenerMethod()
{
return addListenerMethod;
}
public Method getTestInterfaceRunMethod()
{
return testInterfaceRunMethod;
}
public Class<?> getTestInterface()
{
return testInterface;
}
public Method getRunMethod( Class<?> testClass )
{
return getMethod( testClass, RUN_METHOD, getTestResultClass() );
}
public boolean isJUnit3Available()
{
return testResultClass != null;
}
}