[英]How to use different Junit TestRunner in Eclipse and Ant?
我有几个JBehave测试,我想从Eclipse和Ant运行。 在Eclipse中,我希望看到一个包含在图形输出中执行的所有不同故事,场景和步骤的树,因此我在执行此操作的测试中添加了一个自定义运行器:
@RunWith(de.codecentric.jbehave.junit.monitoring.JUnitReportingRunner.class)
public class MyStoryTest extends org.jbehave.core.junit.JUnitStories
{
// ...
}
但是相反,当使用Ant和Continuous Integration服务器运行测试时,我希望只将每个故事都看作输出中的单个项目。 这通常在没有任何注释的情况下实现:
public class MyStoryTest extends JUnitStories
{
// ...
}
那么我如何告诉Ant(junit Ant任务)使用与Eclipse不同的跑步者? 让事情变得更复杂:目前我在Eclipse(而不是Ant)中使用测试套件来运行测试:
@RunWith(org.junit.extensions.cpsuite.ClasspathSuite.class)
@org.junit.extensions.cpsuite.ClassnameFilters("foo.mypackage.tests.*")
public class MyStoriesTestSuite
{
// Nothing more to say ;)
}
有任何想法吗?
干杯,蒂尔曼
几周前我做了一些黑客攻击,可以满足你的需求。 我意识到,在单元测试运行的情况下由Eclipse执行的java命令在其名称中始终包含一个包。 所以,如果这回复为真,那么你可能正在Eclipse下运行测试:
System.getProperty( "sun.java.command" ).contains( "org.eclipse.jdt" )
我知道,它不是百分之百的解决方案,但通常都有效,而且总比没有好 。
我为您创建并测试了一个Runner + Annotation对:
注释 :
package org.junit.annotation;
import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
import org.junit.runner.Runner;
import org.junit.runners.JUnit4;
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Target( ElementType.TYPE )
public @interface RunWithInEnvironment {
Class<? extends Runner> eclipse();
Class<? extends Runner> defaultRunner() default JUnit4.class;
}
默认情况下,它使用JUnit4作为defaultrunner,这实际上是JUnit4的默认值。
Runner ,它使用注释的信息:
package org.junit.runners;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.fail;
import java.lang.reflect.Constructor;
import java.lang.reflect.InvocationTargetException;
import org.junit.annotation.RunWithInEnvironment;
import org.junit.runner.Description;
import org.junit.runner.Runner;
import org.junit.runner.notification.RunNotifier;
public class EnvironmentDependentRunner extends Runner {
protected Class<?> testClass;
protected Runner delegate;
public EnvironmentDependentRunner(Class<?> testClass) {
super();
this.testClass = testClass;
RunWithInEnvironment annotation = findAnnotationInClassHierarchy(testClass);
assertNotNull( EnvironmentDependentRunner.class.getSimpleName() + " can be used only with test classes, that are annotated with " + RunWithInEnvironment.class.getSimpleName() + " annotation somewhere in their class hierarchy!", annotation );
Class<? extends Runner> delegateClass = null;
if ( System.getProperty( "sun.java.command" ).contains( "org.eclipse.jdt" ) && annotation.eclipse() != null ) {
delegateClass = annotation.eclipse();
}
else {
delegateClass = annotation.defaultRunner();
}
try {
Constructor<? extends Runner> constructor = delegateClass.getConstructor( Class.class );
delegate = constructor.newInstance(testClass);
} catch (NoSuchMethodException e) {
fail( delegateClass.getName() + " must contain a public constructor with a " + Class.class.getName() + " argument.");
} catch (SecurityException e) {
throw new RuntimeException("SecurityException during instantiation of " + delegateClass.getName() );
} catch (InstantiationException e) {
throw new RuntimeException("Error while creating " + delegateClass.getName() );
} catch (IllegalAccessException e) {
throw new RuntimeException("Error while creating " + delegateClass.getName() );
} catch (IllegalArgumentException e) {
throw new RuntimeException("Error while creating " + delegateClass.getName() );
} catch (InvocationTargetException e) {
throw new RuntimeException("Error while creating " + delegateClass.getName() );
}
}
private RunWithInEnvironment findAnnotationInClassHierarchy(Class<?> testClass) {
RunWithInEnvironment annotation = testClass.getAnnotation(RunWithInEnvironment.class);
if (annotation != null) {
return annotation;
}
Class<?> superClass = testClass.getSuperclass();
if (superClass != null) {
return findAnnotationInClassHierarchy(superClass);
}
return null;
}
@Override
public Description getDescription() {
return delegate.getDescription();
}
@Override
public void run(RunNotifier arg0) {
delegate.run(arg0);
}
}
一个用法示例 :
@RunWithInEnvironment( eclipse=JUnit4.class, defaultRunner=Parameterized.class)
@RunWith( EnvironmentDependentRunner.class)
public class FooTest {
...
}
所以这个测试将在Eclipse中运行JUnit4 runner,在Eclipse外部使用Parameterized。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.