| package org.junit.runner.manipulation; |
| |
| import org.junit.runner.Description; |
| import org.junit.runner.Request; |
| |
| /** |
| * The canonical case of filtering is when you want to run a single test method in a class. Rather |
| * than introduce runner API just for that one case, JUnit provides a general filtering mechanism. |
| * If you want to filter the tests to be run, extend <code>Filter</code> and apply an instance of |
| * your filter to the {@link org.junit.runner.Request} before running it (see |
| * {@link org.junit.runner.JUnitCore#run(Request)}. Alternatively, apply a <code>Filter</code> to |
| * a {@link org.junit.runner.Runner} before running tests (for example, in conjunction with |
| * {@link org.junit.runner.RunWith}. |
| * |
| * @since 4.0 |
| */ |
| public abstract class Filter { |
| /** |
| * A null <code>Filter</code> that passes all tests through. |
| */ |
| public static final Filter ALL = new Filter() { |
| @Override |
| public boolean shouldRun(Description description) { |
| return true; |
| } |
| |
| @Override |
| public String describe() { |
| return "all tests"; |
| } |
| |
| @Override |
| public void apply(Object child) throws NoTestsRemainException { |
| // do nothing |
| } |
| |
| @Override |
| public Filter intersect(Filter second) { |
| return second; |
| } |
| }; |
| |
| /** |
| * Returns a {@code Filter} that only runs the single method described by |
| * {@code desiredDescription} |
| */ |
| public static Filter matchMethodDescription(final Description desiredDescription) { |
| return new Filter() { |
| @Override |
| public boolean shouldRun(Description description) { |
| if (description.isTest()) { |
| return desiredDescription.equals(description); |
| } |
| |
| // explicitly check if any children want to run |
| for (Description each : description.getChildren()) { |
| if (shouldRun(each)) { |
| return true; |
| } |
| } |
| return false; |
| } |
| |
| @Override |
| public String describe() { |
| return String.format("Method %s", desiredDescription.getDisplayName()); |
| } |
| }; |
| } |
| |
| |
| /** |
| * @param description the description of the test to be run |
| * @return <code>true</code> if the test should be run |
| */ |
| public abstract boolean shouldRun(Description description); |
| |
| /** |
| * Returns a textual description of this Filter |
| * |
| * @return a textual description of this Filter |
| */ |
| public abstract String describe(); |
| |
| /** |
| * Invoke with a {@link org.junit.runner.Runner} to cause all tests it intends to run |
| * to first be checked with the filter. Only those that pass the filter will be run. |
| * |
| * @param child the runner to be filtered by the receiver |
| * @throws NoTestsRemainException if the receiver removes all tests |
| */ |
| public void apply(Object child) throws NoTestsRemainException { |
| if (!(child instanceof Filterable)) { |
| return; |
| } |
| Filterable filterable = (Filterable) child; |
| filterable.filter(this); |
| } |
| |
| /** |
| * Returns a new Filter that accepts the intersection of the tests accepted |
| * by this Filter and {@code second} |
| */ |
| public Filter intersect(final Filter second) { |
| if (second == this || second == ALL) { |
| return this; |
| } |
| final Filter first = this; |
| return new Filter() { |
| @Override |
| public boolean shouldRun(Description description) { |
| return first.shouldRun(description) |
| && second.shouldRun(description); |
| } |
| |
| @Override |
| public String describe() { |
| return first.describe() + " and " + second.describe(); |
| } |
| }; |
| } |
| } |