aboutsummaryrefslogtreecommitdiff
path: root/src/main/java/org/junit/runners/BlockJUnit4ClassRunner.java
diff options
context:
space:
mode:
Diffstat (limited to 'src/main/java/org/junit/runners/BlockJUnit4ClassRunner.java')
-rw-r--r--src/main/java/org/junit/runners/BlockJUnit4ClassRunner.java172
1 files changed, 68 insertions, 104 deletions
diff --git a/src/main/java/org/junit/runners/BlockJUnit4ClassRunner.java b/src/main/java/org/junit/runners/BlockJUnit4ClassRunner.java
index 455341a..4d06199 100644
--- a/src/main/java/org/junit/runners/BlockJUnit4ClassRunner.java
+++ b/src/main/java/org/junit/runners/BlockJUnit4ClassRunner.java
@@ -3,10 +3,8 @@ package org.junit.runners;
import static org.junit.internal.runners.rules.RuleMemberValidator.RULE_METHOD_VALIDATOR;
import static org.junit.internal.runners.rules.RuleMemberValidator.RULE_VALIDATOR;
-import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.ConcurrentHashMap;
-import java.util.concurrent.ConcurrentMap;
import java.util.concurrent.TimeUnit;
import org.junit.After;
@@ -23,18 +21,14 @@ import org.junit.internal.runners.statements.InvokeMethod;
import org.junit.internal.runners.statements.RunAfters;
import org.junit.internal.runners.statements.RunBefores;
import org.junit.rules.MethodRule;
+import org.junit.rules.RunRules;
import org.junit.rules.TestRule;
import org.junit.runner.Description;
import org.junit.runner.notification.RunNotifier;
-import org.junit.runners.model.FrameworkMember;
import org.junit.runners.model.FrameworkMethod;
import org.junit.runners.model.InitializationError;
-import org.junit.runners.model.MemberValueConsumer;
import org.junit.runners.model.MultipleFailureException;
import org.junit.runners.model.Statement;
-import org.junit.runners.model.TestClass;
-import org.junit.validator.PublicClassValidator;
-import org.junit.validator.TestClassValidator;
/**
* Implements the JUnit 4 standard test case class model, as defined by the
@@ -61,27 +55,14 @@ import org.junit.validator.TestClassValidator;
* @since 4.5
*/
public class BlockJUnit4ClassRunner extends ParentRunner<FrameworkMethod> {
- private static TestClassValidator PUBLIC_CLASS_VALIDATOR = new PublicClassValidator();
-
- private final ConcurrentMap<FrameworkMethod, Description> methodDescriptions = new ConcurrentHashMap<FrameworkMethod, Description>();
-
- /**
- * Creates a BlockJUnit4ClassRunner to run {@code testClass}
- *
- * @throws InitializationError if the test class is malformed.
- */
- public BlockJUnit4ClassRunner(Class<?> testClass) throws InitializationError {
- super(testClass);
- }
-
+ private final ConcurrentHashMap<FrameworkMethod, Description> methodDescriptions = new ConcurrentHashMap<FrameworkMethod, Description>();
/**
- * Creates a BlockJUnit4ClassRunner to run {@code testClass}.
+ * Creates a BlockJUnit4ClassRunner to run {@code klass}
*
* @throws InitializationError if the test class is malformed.
- * @since 4.13
*/
- protected BlockJUnit4ClassRunner(TestClass testClass) throws InitializationError {
- super(testClass);
+ public BlockJUnit4ClassRunner(Class<?> klass) throws InitializationError {
+ super(klass);
}
//
@@ -94,16 +75,10 @@ public class BlockJUnit4ClassRunner extends ParentRunner<FrameworkMethod> {
if (isIgnored(method)) {
notifier.fireTestIgnored(description);
} else {
- Statement statement = new Statement() {
- @Override
- public void evaluate() throws Throwable {
- methodBlock(method).evaluate();
- }
- };
- runLeaf(statement, description, notifier);
+ runLeaf(methodBlock(method), description, notifier);
}
}
-
+
/**
* Evaluates whether {@link FrameworkMethod}s are ignored based on the
* {@link Ignore} annotation.
@@ -148,7 +123,6 @@ public class BlockJUnit4ClassRunner extends ParentRunner<FrameworkMethod> {
protected void collectInitializationErrors(List<Throwable> errors) {
super.collectInitializationErrors(errors);
- validatePublicConstructor(errors);
validateNoNonStaticInnerClass(errors);
validateConstructor(errors);
validateInstanceMethods(errors);
@@ -156,12 +130,6 @@ public class BlockJUnit4ClassRunner extends ParentRunner<FrameworkMethod> {
validateMethods(errors);
}
- private void validatePublicConstructor(List<Throwable> errors) {
- if (getTestClass().getJavaClass() != null) {
- errors.addAll(PUBLIC_CLASS_VALIDATOR.validateTestClass(getTestClass()));
- }
- }
-
protected void validateNoNonStaticInnerClass(List<Throwable> errors) {
if (getTestClass().isANonStaticInnerClass()) {
String gripe = "The inner class " + getTestClass().getName()
@@ -212,7 +180,6 @@ public class BlockJUnit4ClassRunner extends ParentRunner<FrameworkMethod> {
* Adds to {@code errors} for each method annotated with {@code @Test},
* {@code @Before}, or {@code @After} that is not a public, void instance
* method with no arguments.
- * @deprecated
*/
@Deprecated
protected void validateInstanceMethods(List<Throwable> errors) {
@@ -220,7 +187,7 @@ public class BlockJUnit4ClassRunner extends ParentRunner<FrameworkMethod> {
validatePublicVoidNoArgMethods(Before.class, false, errors);
validateTestMethods(errors);
- if (computeTestMethods().isEmpty()) {
+ if (computeTestMethods().size() == 0) {
errors.add(new Exception("No runnable methods"));
}
}
@@ -251,16 +218,6 @@ public class BlockJUnit4ClassRunner extends ParentRunner<FrameworkMethod> {
}
/**
- * Returns a new fixture to run a particular test {@code method} against.
- * Default implementation executes the no-argument {@link #createTest()} method.
- *
- * @since 4.13
- */
- protected Object createTest(FrameworkMethod method) throws Exception {
- return createTest();
- }
-
- /**
* Returns the name that describes {@code method} for {@link Description}s.
* Default implementation is the method's name
*/
@@ -275,10 +232,10 @@ public class BlockJUnit4ClassRunner extends ParentRunner<FrameworkMethod> {
* Here is an outline of the default implementation:
*
* <ul>
- * <li>Invoke {@code method} on the result of {@link #createTest(org.junit.runners.model.FrameworkMethod)}, and
+ * <li>Invoke {@code method} on the result of {@code createTest()}, and
* throw any exceptions thrown by either operation.
- * <li>HOWEVER, if {@code method}'s {@code @Test} annotation has the {@link Test#expected()}
- * attribute, return normally only if the previous step threw an
+ * <li>HOWEVER, if {@code method}'s {@code @Test} annotation has the {@code
+ * expecting} attribute, return normally only if the previous step threw an
* exception of the correct type, and throw an exception otherwise.
* <li>HOWEVER, if {@code method}'s {@code @Test} annotation has the {@code
* timeout} attribute, throw an exception if the previous step takes more
@@ -300,13 +257,13 @@ public class BlockJUnit4ClassRunner extends ParentRunner<FrameworkMethod> {
* This can be overridden in subclasses, either by overriding this method,
* or the implementations creating each sub-statement.
*/
- protected Statement methodBlock(final FrameworkMethod method) {
+ protected Statement methodBlock(FrameworkMethod method) {
Object test;
try {
test = new ReflectiveCallable() {
@Override
protected Object runReflectiveCall() throws Throwable {
- return createTest(method);
+ return createTest();
}
}.run();
} catch (Throwable e) {
@@ -319,7 +276,6 @@ public class BlockJUnit4ClassRunner extends ParentRunner<FrameworkMethod> {
statement = withBefores(method, test, statement);
statement = withAfters(method, test, statement);
statement = withRules(method, test, statement);
- statement = withInterruptIsolation(statement);
return statement;
}
@@ -336,22 +292,21 @@ public class BlockJUnit4ClassRunner extends ParentRunner<FrameworkMethod> {
/**
* Returns a {@link Statement}: if {@code method}'s {@code @Test} annotation
- * has the {@link Test#expected()} attribute, return normally only if {@code next}
+ * has the {@code expecting} attribute, return normally only if {@code next}
* throws an exception of the correct type, and throw an exception
* otherwise.
*/
protected Statement possiblyExpectingExceptions(FrameworkMethod method,
Object test, Statement next) {
Test annotation = method.getAnnotation(Test.class);
- Class<? extends Throwable> expectedExceptionClass = getExpectedException(annotation);
- return expectedExceptionClass != null ? new ExpectException(next, expectedExceptionClass) : next;
+ return expectsException(annotation) ? new ExpectException(next,
+ getExpectedException(annotation)) : next;
}
/**
* Returns a {@link Statement}: if {@code method}'s {@code @Test} annotation
* has the {@code timeout} attribute, throw an exception if {@code next}
* takes more than the specified number of milliseconds.
- * @deprecated
*/
@Deprecated
protected Statement withPotentialTimeout(FrameworkMethod method,
@@ -393,23 +348,28 @@ public class BlockJUnit4ClassRunner extends ParentRunner<FrameworkMethod> {
target);
}
- private Statement withRules(FrameworkMethod method, Object target, Statement statement) {
- RuleContainer ruleContainer = new RuleContainer();
- CURRENT_RULE_CONTAINER.set(ruleContainer);
- try {
- List<TestRule> testRules = getTestRules(target);
- for (MethodRule each : rules(target)) {
- if (!(each instanceof TestRule && testRules.contains(each))) {
- ruleContainer.add(each);
- }
- }
- for (TestRule rule : testRules) {
- ruleContainer.add(rule);
+ private Statement withRules(FrameworkMethod method, Object target,
+ Statement statement) {
+ List<TestRule> testRules = getTestRules(target);
+ Statement result = statement;
+ result = withMethodRules(method, testRules, target, result);
+ result = withTestRules(method, testRules, result);
+
+ return result;
+ }
+
+ private Statement withMethodRules(FrameworkMethod method, List<TestRule> testRules,
+ Object target, Statement result) {
+ for (org.junit.rules.MethodRule each : getMethodRules(target)) {
+ if (!testRules.contains(each)) {
+ result = each.apply(result, method, target);
}
- } finally {
- CURRENT_RULE_CONTAINER.remove();
}
- return ruleContainer.apply(method, describeChild(method), target, statement);
+ return result;
+ }
+
+ private List<org.junit.rules.MethodRule> getMethodRules(Object target) {
+ return rules(target);
}
/**
@@ -418,12 +378,27 @@ public class BlockJUnit4ClassRunner extends ParentRunner<FrameworkMethod> {
* test
*/
protected List<MethodRule> rules(Object target) {
- RuleCollector<MethodRule> collector = new RuleCollector<MethodRule>();
- getTestClass().collectAnnotatedMethodValues(target, Rule.class, MethodRule.class,
- collector);
- getTestClass().collectAnnotatedFieldValues(target, Rule.class, MethodRule.class,
- collector);
- return collector.result;
+ List<MethodRule> rules = getTestClass().getAnnotatedMethodValues(target,
+ Rule.class, MethodRule.class);
+
+ rules.addAll(getTestClass().getAnnotatedFieldValues(target,
+ Rule.class, MethodRule.class));
+
+ return rules;
+ }
+
+ /**
+ * Returns a {@link Statement}: apply all non-static fields
+ * annotated with {@link Rule}.
+ *
+ * @param statement The base statement
+ * @return a RunRules statement if any class-level {@link Rule}s are
+ * found, or the base statement
+ */
+ private Statement withTestRules(FrameworkMethod method, List<TestRule> testRules,
+ Statement statement) {
+ return testRules.isEmpty() ? statement :
+ new RunRules(statement, testRules, describeChild(method));
}
/**
@@ -432,10 +407,13 @@ public class BlockJUnit4ClassRunner extends ParentRunner<FrameworkMethod> {
* test
*/
protected List<TestRule> getTestRules(Object target) {
- RuleCollector<TestRule> collector = new RuleCollector<TestRule>();
- getTestClass().collectAnnotatedMethodValues(target, Rule.class, TestRule.class, collector);
- getTestClass().collectAnnotatedFieldValues(target, Rule.class, TestRule.class, collector);
- return collector.result;
+ List<TestRule> result = getTestClass().getAnnotatedMethodValues(target,
+ Rule.class, TestRule.class);
+
+ result.addAll(getTestClass().getAnnotatedFieldValues(target,
+ Rule.class, TestRule.class));
+
+ return result;
}
private Class<? extends Throwable> getExpectedException(Test annotation) {
@@ -446,28 +424,14 @@ public class BlockJUnit4ClassRunner extends ParentRunner<FrameworkMethod> {
}
}
+ private boolean expectsException(Test annotation) {
+ return getExpectedException(annotation) != null;
+ }
+
private long getTimeout(Test annotation) {
if (annotation == null) {
return 0;
}
return annotation.timeout();
}
-
- private static final ThreadLocal<RuleContainer> CURRENT_RULE_CONTAINER =
- new ThreadLocal<RuleContainer>();
-
- private static class RuleCollector<T> implements MemberValueConsumer<T> {
- final List<T> result = new ArrayList<T>();
-
- public void accept(FrameworkMember<?> member, T value) {
- Rule rule = member.getAnnotation(Rule.class);
- if (rule != null) {
- RuleContainer container = CURRENT_RULE_CONTAINER.get();
- if (container != null) {
- container.setOrder(value, rule.order());
- }
- }
- result.add(value);
- }
- }
}