or run

npx @tessl/cli init
Log in

Version

Tile

Overview

Evals

Files

Files

docs

annotations.mdassertions.mdassumptions.mdcategories.mdindex.mdmatchers.mdrules.mdstandard-runners.mdtest-runners.mdtheories.md

test-runners.mddocs/

0

# Test Runners

1

2

Test runners are responsible for executing tests and reporting results. JUnit provides `JUnitCore` as the main facade for running tests programmatically, while the `Runner` class hierarchy enables custom test execution strategies.

3

4

## Capabilities

5

6

### JUnitCore

7

8

The main entry point for running tests programmatically. Can be used from the command line or from Java code to execute test classes and collect results.

9

10

```java { .api }

11

/**

12

* Facade for running tests and collecting results

13

*/

14

public class JUnitCore {

15

/**

16

* Run tests from command line

17

* @param args - Fully qualified class names of test classes

18

*/

19

public static void main(String... args);

20

21

/**

22

* Run tests and return results

23

* @param classes - Test classes to run

24

* @return Results of test execution

25

*/

26

public Result run(Class<?>... classes);

27

28

/**

29

* Run tests and return results (alias for run)

30

* @param classes - Test classes to run

31

* @return Results of test execution

32

*/

33

public Result runClasses(Class<?>... classes);

34

35

/**

36

* Run tests using a Request

37

* @param request - Configured test request

38

* @return Results of test execution

39

*/

40

public Result run(Request request);

41

42

/**

43

* Run tests with a specific runner

44

* @param runner - Runner to use

45

* @return Results of test execution

46

*/

47

public Result run(Runner runner);

48

49

/**

50

* Run a JUnit 3.x style test

51

* @param test - JUnit 3.x Test to run

52

* @return Results of test execution

53

*/

54

public Result run(junit.framework.Test test);

55

56

/**

57

* Add a listener to be notified of test events

58

* @param listener - Listener to add

59

*/

60

public void addListener(RunListener listener);

61

62

/**

63

* Remove a previously added listener

64

* @param listener - Listener to remove

65

*/

66

public void removeListener(RunListener listener);

67

68

/**

69

* Get JUnit version string

70

* @return Version string (e.g., "4.13.2")

71

*/

72

public String getVersion();

73

}

74

```

75

76

**Usage Examples:**

77

78

```java

79

import org.junit.runner.JUnitCore;

80

import org.junit.runner.Result;

81

import org.junit.runner.notification.Failure;

82

83

public class TestRunner {

84

public static void main(String[] args) {

85

// Run single test class

86

Result result = JUnitCore.runClasses(MyTest.class);

87

System.out.println("Tests run: " + result.getRunCount());

88

System.out.println("Failures: " + result.getFailureCount());

89

90

// Run multiple test classes

91

Result multiResult = JUnitCore.runClasses(

92

TestClass1.class,

93

TestClass2.class,

94

TestClass3.class

95

);

96

97

// Check results

98

if (!multiResult.wasSuccessful()) {

99

System.out.println("Some tests failed:");

100

for (Failure failure : multiResult.getFailures()) {

101

System.out.println(failure.toString());

102

}

103

}

104

105

// Print execution time

106

System.out.println("Execution time: " + multiResult.getRunTime() + "ms");

107

}

108

}

109

```

110

111

```java

112

import org.junit.runner.JUnitCore;

113

import org.junit.runner.Result;

114

import org.junit.runner.notification.RunListener;

115

import org.junit.runner.Description;

116

import org.junit.runner.notification.Failure;

117

118

public class CustomTestRunner {

119

public static void main(String[] args) {

120

JUnitCore core = new JUnitCore();

121

122

// Add custom listener

123

core.addListener(new RunListener() {

124

@Override

125

public void testStarted(Description description) {

126

System.out.println("Starting: " + description.getDisplayName());

127

}

128

129

@Override

130

public void testFinished(Description description) {

131

System.out.println("Finished: " + description.getDisplayName());

132

}

133

134

@Override

135

public void testFailure(Failure failure) {

136

System.out.println("Failed: " + failure.getDescription().getDisplayName());

137

}

138

});

139

140

Result result = core.run(MyTest.class);

141

System.exit(result.wasSuccessful() ? 0 : 1);

142

}

143

}

144

```

145

146

### Result

147

148

Collects and summarizes test execution results. Contains counts of runs, failures, and ignored tests, along with timing information.

149

150

```java { .api }

151

/**

152

* Test execution results

153

*/

154

public class Result implements Serializable {

155

/**

156

* Get number of tests that were run

157

* @return Count of executed tests

158

*/

159

public int getRunCount();

160

161

/**

162

* Get number of tests that failed

163

* @return Count of failed tests

164

*/

165

public int getFailureCount();

166

167

/**

168

* Get number of tests that were ignored

169

* @return Count of ignored tests

170

*/

171

public int getIgnoreCount();

172

173

/**

174

* Get number of assumption failures

175

* @return Count of assumption failures (tests skipped)

176

*/

177

public int getAssumptionFailureCount();

178

179

/**

180

* Get total execution time in milliseconds

181

* @return Execution time in milliseconds

182

*/

183

public long getRunTime();

184

185

/**

186

* Get list of all failures

187

* @return List of Failure objects

188

*/

189

public List<Failure> getFailures();

190

191

/**

192

* Check if all tests passed

193

* @return true if no failures or assumption violations

194

*/

195

public boolean wasSuccessful();

196

197

/**

198

* Create a listener that populates this result

199

* @return RunListener that updates this result

200

*/

201

public RunListener createListener();

202

}

203

```

204

205

**Usage Examples:**

206

207

```java

208

import org.junit.runner.JUnitCore;

209

import org.junit.runner.Result;

210

import org.junit.runner.notification.Failure;

211

212

public class ResultAnalyzer {

213

public static void analyzeResults(Result result) {

214

System.out.println("=== Test Results ===");

215

System.out.println("Tests run: " + result.getRunCount());

216

System.out.println("Failures: " + result.getFailureCount());

217

System.out.println("Ignored: " + result.getIgnoreCount());

218

System.out.println("Assumptions failed: " + result.getAssumptionFailureCount());

219

System.out.println("Time: " + result.getRunTime() + "ms");

220

System.out.println("Success: " + result.wasSuccessful());

221

222

if (!result.wasSuccessful()) {

223

System.out.println("\n=== Failures ===");

224

for (Failure failure : result.getFailures()) {

225

System.out.println(failure.getTestHeader());

226

System.out.println(failure.getMessage());

227

System.out.println(failure.getTrace());

228

}

229

}

230

}

231

232

public static void main(String[] args) {

233

Result result = JUnitCore.runClasses(MyTest.class);

234

analyzeResults(result);

235

}

236

}

237

```

238

239

### Runner

240

241

Abstract base class for test runners. Custom runners extend this class to implement specialized test execution strategies.

242

243

```java { .api }

244

/**

245

* Base class for test runners

246

*/

247

public abstract class Runner implements Describable {

248

/**

249

* Get description of tests this runner will execute

250

* @return Description object

251

*/

252

public abstract Description getDescription();

253

254

/**

255

* Run the tests, notifying the given notifier of events

256

* @param notifier - Notifier for test events

257

*/

258

public abstract void run(RunNotifier notifier);

259

260

/**

261

* Get count of tests that will be run

262

* @return Number of tests

263

*/

264

public int testCount();

265

}

266

```

267

268

**Usage Examples:**

269

270

```java

271

import org.junit.runner.Runner;

272

import org.junit.runner.Description;

273

import org.junit.runner.notification.RunNotifier;

274

import org.junit.runners.model.InitializationError;

275

276

public class CustomRunner extends Runner {

277

private Class<?> testClass;

278

279

public CustomRunner(Class<?> testClass) throws InitializationError {

280

this.testClass = testClass;

281

}

282

283

@Override

284

public Description getDescription() {

285

return Description.createSuiteDescription(testClass);

286

}

287

288

@Override

289

public void run(RunNotifier notifier) {

290

Description description = getDescription();

291

notifier.fireTestStarted(description);

292

293

try {

294

// Custom test execution logic

295

Object testInstance = testClass.getDeclaredConstructor().newInstance();

296

// Run test methods...

297

notifier.fireTestFinished(description);

298

} catch (Exception e) {

299

notifier.fireTestFailure(new Failure(description, e));

300

}

301

}

302

}

303

```

304

305

### Request

306

307

Encapsulates a request to run tests with specific configuration. Supports filtering, sorting, and custom runners.

308

309

```java { .api }

310

/**

311

* A request to run tests

312

*/

313

public abstract class Request {

314

/**

315

* Create a request to run all tests in classes

316

* @param computer - Strategy for running tests

317

* @param classes - Test classes to run

318

* @return Request object

319

*/

320

public static Request classes(Computer computer, Class<?>... classes);

321

322

/**

323

* Create a request to run all tests in classes

324

* @param classes - Test classes to run

325

* @return Request object

326

*/

327

public static Request classes(Class<?>... classes);

328

329

/**

330

* Create a request to run tests with a custom runner

331

* @param runner - Runner to use

332

* @return Request object

333

*/

334

public static Request runner(Runner runner);

335

336

/**

337

* Create a request to run a single method

338

* @param clazz - Test class

339

* @param methodName - Method name

340

* @return Request object

341

*/

342

public static Request method(Class<?> clazz, String methodName);

343

344

/**

345

* Create a request for a test suite

346

* @param clazz - Test class

347

* @return Request object

348

*/

349

public static Request aClass(Class<?> clazz);

350

351

/**

352

* Create a request for a test class without JUnit 3 suite() method

353

* @param clazz - Test class

354

* @return Request object

355

*/

356

public static Request classWithoutSuiteMethod(Class<?> clazz);

357

358

/**

359

* Create a request that will report an error

360

* @param klass - Test class that has error

361

* @param cause - Exception that caused the error

362

* @return Request object

363

*/

364

public static Request errorReport(Class<?> klass, Throwable cause);

365

366

/**

367

* Get the runner for this request

368

* @return Runner object

369

*/

370

public abstract Runner getRunner();

371

372

/**

373

* Filter the tests to run

374

* @param filter - Filter to apply

375

* @return Filtered request

376

*/

377

public Request filterWith(Filter filter);

378

379

/**

380

* Filter the tests by description

381

* @param desiredDescription - Description to match

382

* @return Filtered request

383

*/

384

public Request filterWith(Description desiredDescription);

385

386

/**

387

* Sort the tests

388

* @param comparator - Comparison function for ordering

389

* @return Sorted request

390

*/

391

public Request sortWith(Comparator<Description> comparator);

392

393

/**

394

* Order the tests using an Ordering

395

* @param ordering - Ordering to apply

396

* @return Ordered request

397

*/

398

public Request orderWith(Ordering ordering);

399

}

400

```

401

402

**Usage Examples:**

403

404

```java

405

import org.junit.runner.JUnitCore;

406

import org.junit.runner.Request;

407

import org.junit.runner.Result;

408

409

public class RequestExamples {

410

public static void runSingleMethod() {

411

// Run just one test method

412

Request request = Request.method(MyTest.class, "testAddition");

413

Result result = new JUnitCore().run(request);

414

}

415

416

public static void runWithFilter() {

417

// Run only fast tests

418

Request request = Request.aClass(MyTest.class);

419

request = request.filterWith(new CategoryFilter(FastTests.class));

420

Result result = new JUnitCore().run(request);

421

}

422

423

public static void runSorted() {

424

// Run tests in specific order

425

Request request = Request.aClass(MyTest.class);

426

request = request.sortWith(new Comparator<Description>() {

427

public int compare(Description d1, Description d2) {

428

return d1.getMethodName().compareTo(d2.getMethodName());

429

}

430

});

431

Result result = new JUnitCore().run(request);

432

}

433

}

434

```

435

436

### RunNotifier

437

438

Notifies listeners about test execution events. Used by runners to report test progress.

439

440

```java { .api }

441

/**

442

* Notifies listeners of test execution events

443

*/

444

public class RunNotifier {

445

/**

446

* Add a listener

447

* @param listener - Listener to add

448

*/

449

public void addListener(RunListener listener);

450

451

/**

452

* Add a listener at the front of the list

453

* @param listener - Listener to add first

454

*/

455

public void addFirstListener(RunListener listener);

456

457

/**

458

* Remove a listener

459

* @param listener - Listener to remove

460

*/

461

public void removeListener(RunListener listener);

462

463

/**

464

* Notify that a test suite is starting

465

* @param description - Description of suite

466

*/

467

public void fireTestSuiteStarted(Description description);

468

469

/**

470

* Notify that a test suite finished

471

* @param description - Description of suite

472

*/

473

public void fireTestSuiteFinished(Description description);

474

475

/**

476

* Notify that test run started

477

* @param description - Description of run

478

*/

479

public void fireTestRunStarted(Description description);

480

481

/**

482

* Notify that test run finished

483

* @param result - Result of test run

484

*/

485

public void fireTestRunFinished(Result result);

486

487

/**

488

* Notify that a test started

489

* @param description - Description of test

490

*/

491

public void fireTestStarted(Description description);

492

493

/**

494

* Notify that a test finished

495

* @param description - Description of test

496

*/

497

public void fireTestFinished(Description description);

498

499

/**

500

* Notify that a test failed

501

* @param failure - Failure information

502

*/

503

public void fireTestFailure(Failure failure);

504

505

/**

506

* Notify that a test was ignored

507

* @param description - Description of ignored test

508

*/

509

public void fireTestIgnored(Description description);

510

511

/**

512

* Notify that an assumption failed (test skipped)

513

* @param failure - Assumption failure

514

*/

515

public void fireTestAssumptionFailed(Failure failure);

516

517

/**

518

* Request that test run stop

519

*/

520

public void pleaseStop();

521

}

522

```

523

524

### RunListener

525

526

Abstract class for listening to test execution events. Extend this to create custom test reporters or loggers.

527

528

```java { .api }

529

/**

530

* Listener for test execution events

531

*/

532

public abstract class RunListener {

533

/**

534

* Called when test run starts

535

* @param description - Description of test run

536

*/

537

public void testRunStarted(Description description) throws Exception;

538

539

/**

540

* Called when test run finishes

541

* @param result - Result of test run

542

*/

543

public void testRunFinished(Result result) throws Exception;

544

545

/**

546

* Called when test suite starts

547

* @param description - Description of suite

548

*/

549

public void testSuiteStarted(Description description) throws Exception;

550

551

/**

552

* Called when test suite finishes

553

* @param description - Description of suite

554

*/

555

public void testSuiteFinished(Description description) throws Exception;

556

557

/**

558

* Called when a test starts

559

* @param description - Description of test

560

*/

561

public void testStarted(Description description) throws Exception;

562

563

/**

564

* Called when a test finishes

565

* @param description - Description of test

566

*/

567

public void testFinished(Description description) throws Exception;

568

569

/**

570

* Called when a test fails

571

* @param failure - Failure information

572

*/

573

public void testFailure(Failure failure) throws Exception;

574

575

/**

576

* Called when an assumption fails (test skipped)

577

* @param failure - Assumption failure

578

*/

579

public void testAssumptionFailure(Failure failure);

580

581

/**

582

* Called when a test is ignored

583

* @param description - Description of ignored test

584

*/

585

public void testIgnored(Description description) throws Exception;

586

}

587

```

588

589

**Usage Examples:**

590

591

```java

592

import org.junit.runner.notification.RunListener;

593

import org.junit.runner.Description;

594

import org.junit.runner.notification.Failure;

595

import org.junit.runner.Result;

596

597

public class DetailedLogger extends RunListener {

598

private long startTime;

599

600

@Override

601

public void testRunStarted(Description description) {

602

System.out.println("Starting test run: " + description.getDisplayName());

603

startTime = System.currentTimeMillis();

604

}

605

606

@Override

607

public void testRunFinished(Result result) {

608

long duration = System.currentTimeMillis() - startTime;

609

System.out.println("Test run finished in " + duration + "ms");

610

System.out.println("Tests: " + result.getRunCount());

611

System.out.println("Failures: " + result.getFailureCount());

612

System.out.println("Ignored: " + result.getIgnoreCount());

613

}

614

615

@Override

616

public void testStarted(Description description) {

617

System.out.println(" Running: " + description.getMethodName());

618

}

619

620

@Override

621

public void testFinished(Description description) {

622

System.out.println(" Finished: " + description.getMethodName());

623

}

624

625

@Override

626

public void testFailure(Failure failure) {

627

System.err.println(" FAILED: " + failure.getDescription().getMethodName());

628

System.err.println(" " + failure.getMessage());

629

}

630

631

@Override

632

public void testIgnored(Description description) {

633

System.out.println(" IGNORED: " + description.getMethodName());

634

}

635

}

636

637

// Usage

638

JUnitCore core = new JUnitCore();

639

core.addListener(new DetailedLogger());

640

core.run(MyTest.class);

641

```

642

643

### Filter

644

645

Filters tests based on custom criteria. Runners that implement `Filterable` can have filters applied to remove tests that don't match. Commonly used to run specific test methods or exclude certain categories.

646

647

```java { .api }

648

/**

649

* Abstract base class for filtering tests

650

*/

651

public abstract class Filter {

652

/**

653

* A null Filter that passes all tests through

654

*/

655

public static final Filter ALL;

656

657

/**

658

* Returns a Filter that only runs the single method described by desiredDescription

659

* @param desiredDescription - Description to match

660

* @return Filter that matches only this description

661

*/

662

public static Filter matchMethodDescription(Description desiredDescription);

663

664

/**

665

* Determine if the test should be run

666

* @param description - Description of the test

667

* @return true if the test should be run

668

*/

669

public abstract boolean shouldRun(Description description);

670

671

/**

672

* Returns a textual description of this Filter

673

* @return Description string

674

*/

675

public abstract String describe();

676

677

/**

678

* Invoke with a Runner to cause all tests it intends to run to first be checked with the filter

679

* @param child - The runner to be filtered

680

* @throws NoTestsRemainException if the receiver removes all tests

681

*/

682

public void apply(Object child) throws NoTestsRemainException;

683

684

/**

685

* Returns a new Filter that accepts the intersection of tests accepted by this Filter and second

686

* @param second - Filter to intersect with

687

* @return Intersected filter

688

*/

689

public Filter intersect(Filter second);

690

}

691

```

692

693

**Usage Examples:**

694

695

```java

696

import org.junit.runner.JUnitCore;

697

import org.junit.runner.Request;

698

import org.junit.runner.manipulation.Filter;

699

import org.junit.runner.Description;

700

701

public class FilterExamples {

702

// Run only a single test method

703

public static void runSingleMethod() {

704

Request request = Request.aClass(MyTest.class);

705

Description methodDesc = Description.createTestDescription(

706

MyTest.class, "testAddition");

707

request = request.filterWith(Filter.matchMethodDescription(methodDesc));

708

new JUnitCore().run(request);

709

}

710

711

// Custom filter for fast tests

712

public static void runFastTests() {

713

Request request = Request.aClass(MyTest.class);

714

request = request.filterWith(new Filter() {

715

@Override

716

public boolean shouldRun(Description description) {

717

// Run if annotated with @Fast or if it's a suite

718

return description.getAnnotation(Fast.class) != null

719

|| !description.isTest();

720

}

721

722

@Override

723

public String describe() {

724

return "fast tests only";

725

}

726

});

727

new JUnitCore().run(request);

728

}

729

730

// Combine multiple filters

731

public static void runIntersectedFilters() {

732

Filter fastFilter = new FastTestFilter();

733

Filter categoryFilter = new CategoryFilter(DatabaseTests.class);

734

735

// Run tests that match both filters

736

Filter combined = fastFilter.intersect(categoryFilter);

737

Request request = Request.aClass(MyTest.class).filterWith(combined);

738

new JUnitCore().run(request);

739

}

740

}

741

```

742

743

### Filterable

744

745

Interface for runners that support test filtering. Implement this interface to allow tests to be filtered at runtime.

746

747

```java { .api }

748

/**

749

* Interface for runners that allow filtering

750

*/

751

public interface Filterable {

752

/**

753

* Remove tests that don't pass the parameter filter

754

* @param filter - The Filter to apply

755

* @throws NoTestsRemainException if all tests are filtered out

756

*/

757

void filter(Filter filter) throws NoTestsRemainException;

758

}

759

```

760

761

### Sortable

762

763

Interface for runners that support test sorting. Implement this interface to allow tests to be sorted by custom criteria.

764

765

```java { .api }

766

/**

767

* Interface for runners that allow sorting of tests

768

*/

769

public interface Sortable {

770

/**

771

* Sorts the tests using sorter

772

* @param sorter - The Sorter to use for sorting the tests

773

*/

774

void sort(Sorter sorter);

775

}

776

```

777

778

### Orderable

779

780

Interface for runners that support test ordering. Extends `Sortable` to provide more powerful ordering capabilities through the `Orderer` class. While `Sortable` uses comparators for simple sorting, `Orderable` supports complex ordering strategies including shuffling and custom ordering algorithms.

781

782

```java { .api }

783

/**

784

* Interface for runners that allow ordering of tests

785

*

786

* Beware of using this interface to cope with order dependencies between tests.

787

* Tests that are isolated from each other are less expensive to maintain and

788

* can be run individually.

789

*

790

* @since 4.13

791

*/

792

public interface Orderable extends Sortable {

793

/**

794

* Orders the tests using orderer

795

* @param orderer - The Orderer to apply

796

* @throws InvalidOrderingException if orderer does something invalid (like remove or add children)

797

*/

798

void order(Orderer orderer) throws InvalidOrderingException;

799

}

800

```

801

802

**Usage Examples:**

803

804

```java

805

import org.junit.runner.manipulation.Orderable;

806

import org.junit.runner.manipulation.Orderer;

807

import org.junit.runner.manipulation.Ordering;

808

import org.junit.runner.manipulation.InvalidOrderingException;

809

import org.junit.runner.Description;

810

import java.util.Random;

811

812

public class OrderableRunnerExample {

813

// Using Request.orderWith() to order tests (recommended approach)

814

public static void orderTestsWithShuffle() {

815

Request request = Request.aClass(MyTest.class);

816

817

// Create a shuffled ordering with a specific seed for reproducibility

818

Random random = new Random(12345L);

819

Ordering ordering = Ordering.shuffledBy(random);

820

821

// Apply ordering to request

822

request = request.orderWith(ordering);

823

new JUnitCore().run(request);

824

}

825

826

// Custom runner implementing Orderable

827

public static class CustomOrderableRunner extends Runner implements Orderable {

828

private List<Description> children;

829

830

@Override

831

public void order(Orderer orderer) throws InvalidOrderingException {

832

// Let the orderer determine the order

833

children = orderer.order(children);

834

}

835

836

@Override

837

public void sort(Sorter sorter) {

838

// Also support simple sorting

839

Collections.sort(children, sorter);

840

}

841

842

@Override

843

public Description getDescription() {

844

Description suite = Description.createSuiteDescription("Custom Suite");

845

for (Description child : children) {

846

suite.addChild(child);

847

}

848

return suite;

849

}

850

851

@Override

852

public void run(RunNotifier notifier) {

853

// Run tests in the ordered sequence

854

for (Description child : children) {

855

notifier.fireTestStarted(child);

856

// Execute test...

857

notifier.fireTestFinished(child);

858

}

859

}

860

}

861

}

862

```

863

864

### Sorter

865

866

Orders tests using a comparator. Generally used through `Request.sortWith()` rather than directly.

867

868

```java { .api }

869

/**

870

* Orders tests based on a comparator

871

*/

872

public class Sorter extends Ordering implements Comparator<Description> {

873

/**

874

* NULL is a Sorter that leaves elements in an undefined order

875

*/

876

public static final Sorter NULL;

877

878

/**

879

* Creates a Sorter that uses comparator to sort tests

880

* @param comparator - The Comparator to use when sorting tests

881

*/

882

public Sorter(Comparator<Description> comparator);

883

884

/**

885

* Sorts the tests in target using comparator

886

* @param target - Runner to sort (typically implements Sortable)

887

*/

888

public void apply(Object target);

889

890

/**

891

* Compare two descriptions

892

* @param o1 - First description

893

* @param o2 - Second description

894

* @return Comparison result

895

*/

896

public int compare(Description o1, Description o2);

897

}

898

```

899

900

**Usage Examples:**

901

902

```java

903

import org.junit.runner.JUnitCore;

904

import org.junit.runner.Request;

905

import org.junit.runner.manipulation.Sorter;

906

import org.junit.runner.Description;

907

import java.util.Comparator;

908

909

public class SorterExamples {

910

// Sort tests alphabetically by method name

911

public static void runAlphabetically() {

912

Request request = Request.aClass(MyTest.class);

913

request = request.sortWith(new Comparator<Description>() {

914

public int compare(Description d1, Description d2) {

915

return d1.getMethodName().compareTo(d2.getMethodName());

916

}

917

});

918

new JUnitCore().run(request);

919

}

920

921

// Sort tests by annotation priority

922

public static void runByPriority() {

923

Sorter sorter = new Sorter(new Comparator<Description>() {

924

public int compare(Description d1, Description d2) {

925

Priority p1 = d1.getAnnotation(Priority.class);

926

Priority p2 = d2.getAnnotation(Priority.class);

927

int priority1 = (p1 != null) ? p1.value() : Integer.MAX_VALUE;

928

int priority2 = (p2 != null) ? p2.value() : Integer.MAX_VALUE;

929

return Integer.compare(priority1, priority2);

930

}

931

});

932

933

Request request = Request.aClass(MyTest.class);

934

request = request.sortWith(sorter);

935

new JUnitCore().run(request);

936

}

937

}

938

```

939

940

### Alphanumeric

941

942

Built-in sorter that orders tests alphanumerically by display name. Implements both `Sorter` and `Ordering.Factory`, making it usable with both the `sortWith()` and `orderWith()` APIs. This is a convenient way to get consistent, alphabetical test execution without writing custom comparison logic.

943

944

```java { .api }

945

/**

946

* A sorter that orders tests alphanumerically by test name

947

* @since 4.13

948

*/

949

public final class Alphanumeric extends Sorter implements Ordering.Factory {

950

/**

951

* Creates an Alphanumeric sorter

952

*/

953

public Alphanumeric();

954

955

/**

956

* Creates an Ordering instance using the given context

957

* @param context - Context for creating ordering

958

* @return This Alphanumeric instance as an Ordering

959

*/

960

public Ordering create(Context context);

961

}

962

```

963

964

**Usage Examples:**

965

966

```java

967

import org.junit.runner.JUnitCore;

968

import org.junit.runner.Request;

969

import org.junit.runner.manipulation.Alphanumeric;

970

971

public class AlphanumericExamples {

972

// Sort tests alphabetically using sortWith

973

public static void sortAlphabetically() {

974

Request request = Request.aClass(MyTest.class);

975

request = request.sortWith(new Alphanumeric());

976

new JUnitCore().run(request);

977

}

978

979

// Order tests alphabetically using orderWith

980

public static void orderAlphabetically() {

981

Request request = Request.aClass(MyTest.class);

982

Alphanumeric alphanumeric = new Alphanumeric();

983

try {

984

request = request.orderWith(

985

alphanumeric.create(null) // Context not needed for Alphanumeric

986

);

987

} catch (Exception e) {

988

e.printStackTrace();

989

}

990

new JUnitCore().run(request);

991

}

992

993

// Example test class - methods will run in alphabetical order

994

public static class MyTest {

995

@Test

996

public void testZebra() { }

997

998

@Test

999

public void testApple() { }

1000

1001

@Test

1002

public void testMango() { }

1003

1004

// Execution order with Alphanumeric:

1005

// 1. testApple

1006

// 2. testMango

1007

// 3. testZebra

1008

}

1009

}

1010

```

1011

1012

### FilterFactory

1013

1014

Interface for creating filters from command-line arguments or configuration. Filter factories enable dynamic filter creation based on string specifications, making it easy to filter tests without hardcoding filter logic.

1015

1016

```java { .api }

1017

/**

1018

* Extend this class to create a factory that creates Filter

1019

*/

1020

public interface FilterFactory {

1021

/**

1022

* Creates a Filter given a FilterFactoryParams argument

1023

* @param params - Parameters needed to create the Filter

1024

* @return Created filter

1025

* @throws FilterNotCreatedException if the Filter cannot be created

1026

*/

1027

Filter createFilter(FilterFactoryParams params) throws FilterNotCreatedException;

1028

1029

/**

1030

* Exception thrown if the Filter cannot be created

1031

*/

1032

class FilterNotCreatedException extends Exception {

1033

public FilterNotCreatedException(Exception exception);

1034

}

1035

}

1036

```

1037

1038

**Usage Examples:**

1039

1040

```java

1041

import org.junit.runner.FilterFactory;

1042

import org.junit.runner.FilterFactoryParams;

1043

import org.junit.runner.manipulation.Filter;

1044

import org.junit.runner.Description;

1045

1046

// Custom filter factory that filters by test name pattern

1047

public class NamePatternFilterFactory implements FilterFactory {

1048

@Override

1049

public Filter createFilter(FilterFactoryParams params)

1050

throws FilterNotCreatedException {

1051

final String pattern = params.getArgs();

1052

1053

if (pattern == null || pattern.isEmpty()) {

1054

throw new FilterNotCreatedException(

1055

new IllegalArgumentException("Pattern cannot be empty")

1056

);

1057

}

1058

1059

return new Filter() {

1060

@Override

1061

public boolean shouldRun(Description description) {

1062

if (!description.isTest()) {

1063

return true; // Include suites

1064

}

1065

String methodName = description.getMethodName();

1066

return methodName != null && methodName.contains(pattern);

1067

}

1068

1069

@Override

1070

public String describe() {

1071

return "tests containing '" + pattern + "'";

1072

}

1073

};

1074

}

1075

}

1076

1077

// Custom filter factory that filters by annotation

1078

public class AnnotationFilterFactory implements FilterFactory {

1079

@Override

1080

public Filter createFilter(FilterFactoryParams params)

1081

throws FilterNotCreatedException {

1082

final String annotationName = params.getArgs();

1083

1084

try {

1085

final Class<?> annotationClass = Class.forName(annotationName);

1086

1087

return new Filter() {

1088

@Override

1089

public boolean shouldRun(Description description) {

1090

if (!description.isTest()) {

1091

return true;

1092

}

1093

return description.getAnnotation(annotationClass) != null;

1094

}

1095

1096

@Override

1097

public String describe() {

1098

return "tests with @" + annotationClass.getSimpleName();

1099

}

1100

};

1101

} catch (ClassNotFoundException e) {

1102

throw new FilterNotCreatedException(e);

1103

}

1104

}

1105

}

1106

1107

// Usage: From command line or programmatically

1108

// java org.junit.runner.JUnitCore \

1109

// --filter=com.example.NamePatternFilterFactory=integration \

1110

// com.example.MyTestClass

1111

```

1112

1113

### FilterFactories

1114

1115

Utility class for creating filters from filter specifications. Supports parsing filter specs in the format `"package.FilterFactory=args"` and instantiating the appropriate filter factory. Used internally by JUnit's command-line runner but can also be used programmatically.

1116

1117

```java { .api }

1118

/**

1119

* Utility class whose methods create a FilterFactory

1120

*/

1121

class FilterFactories {

1122

/**

1123

* Creates a Filter from a filter specification

1124

*

1125

* A filter specification is of the form "package.of.FilterFactory=args-to-filter-factory"

1126

* or "package.of.FilterFactory"

1127

*

1128

* @param request - The request that will be filtered

1129

* @param filterSpec - The filter specification

1130

* @return Created filter

1131

* @throws FilterFactory.FilterNotCreatedException if filter cannot be created

1132

*/

1133

public static Filter createFilterFromFilterSpec(Request request, String filterSpec)

1134

throws FilterFactory.FilterNotCreatedException;

1135

1136

/**

1137

* Creates a Filter from a fully qualified class name

1138

* @param filterFactoryFqcn - The fully qualified class name of the FilterFactory

1139

* @param params - The arguments to the FilterFactory

1140

* @return Created filter

1141

* @throws FilterFactory.FilterNotCreatedException if filter cannot be created

1142

*/

1143

public static Filter createFilter(String filterFactoryFqcn, FilterFactoryParams params)

1144

throws FilterFactory.FilterNotCreatedException;

1145

1146

/**

1147

* Creates a Filter from a FilterFactory class

1148

* @param filterFactoryClass - The class of the FilterFactory

1149

* @param params - The arguments to the FilterFactory

1150

* @return Created filter

1151

* @throws FilterFactory.FilterNotCreatedException if filter cannot be created

1152

*/

1153

public static Filter createFilter(Class<? extends FilterFactory> filterFactoryClass,

1154

FilterFactoryParams params)

1155

throws FilterFactory.FilterNotCreatedException;

1156

}

1157

```

1158

1159

**Usage Examples:**

1160

1161

```java

1162

import org.junit.runner.Request;

1163

import org.junit.runner.FilterFactories;

1164

import org.junit.runner.FilterFactoryParams;

1165

import org.junit.runner.manipulation.Filter;

1166

import org.junit.runner.JUnitCore;

1167

1168

public class FilterFactoriesExamples {

1169

// Parse and apply a filter specification

1170

public static void useFilterSpec() {

1171

Request request = Request.aClass(MyTest.class);

1172

1173

try {

1174

// Format: "full.package.FilterFactoryClass=arguments"

1175

String filterSpec = "com.example.NamePatternFilterFactory=integration";

1176

Filter filter = FilterFactories.createFilterFromFilterSpec(request, filterSpec);

1177

1178

request = request.filterWith(filter);

1179

new JUnitCore().run(request);

1180

} catch (FilterFactory.FilterNotCreatedException e) {

1181

System.err.println("Failed to create filter: " + e.getMessage());

1182

}

1183

}

1184

1185

// Create filter from factory class directly

1186

public static void useFactoryClass() {

1187

Request request = Request.aClass(MyTest.class);

1188

1189

try {

1190

FilterFactoryParams params = new FilterFactoryParams(

1191

request.getRunner().getDescription(),

1192

"Fast" // Arguments for the factory

1193

);

1194

1195

Filter filter = FilterFactories.createFilter(

1196

AnnotationFilterFactory.class,

1197

params

1198

);

1199

1200

request = request.filterWith(filter);

1201

new JUnitCore().run(request);

1202

} catch (FilterFactory.FilterNotCreatedException e) {

1203

System.err.println("Failed to create filter: " + e.getMessage());

1204

}

1205

}

1206

1207

// Create filter without arguments

1208

public static void useFilterWithoutArgs() {

1209

Request request = Request.aClass(MyTest.class);

1210

1211

try {

1212

String filterSpec = "com.example.FastTestFilterFactory";

1213

Filter filter = FilterFactories.createFilterFromFilterSpec(request, filterSpec);

1214

1215

request = request.filterWith(filter);

1216

new JUnitCore().run(request);

1217

} catch (FilterFactory.FilterNotCreatedException e) {

1218

System.err.println("Failed to create filter: " + e.getMessage());

1219

}

1220

}

1221

}

1222

```

1223

1224

## Types

1225

1226

```java { .api }

1227

/**

1228

* Failure information

1229

*/

1230

public class Failure implements Serializable {

1231

public Failure(Description description, Throwable thrownException);

1232

1233

public Description getDescription();

1234

public Throwable getException();

1235

public String getMessage();

1236

public String getTestHeader();

1237

public String getTrace();

1238

public String getTrimmedTrace();

1239

}

1240

1241

/**

1242

* Thrown when a filter removes all tests from a runner

1243

*/

1244

public class NoTestsRemainException extends Exception {

1245

}

1246

1247

/**

1248

* Thrown when an ordering does something invalid (like remove or add children)

1249

* @since 4.13

1250

*/

1251

public class InvalidOrderingException extends Exception {

1252

public InvalidOrderingException();

1253

public InvalidOrderingException(String message);

1254

public InvalidOrderingException(String message, Throwable cause);

1255

}

1256

1257

/**

1258

* Represents an object that can describe itself

1259

*/

1260

public interface Describable {

1261

Description getDescription();

1262

}

1263

1264

/**

1265

* Strategy for computing runners and suites

1266

*/

1267

public class Computer {

1268

/**

1269

* Create a serial computer (runs tests sequentially)

1270

* @return Computer that runs tests one at a time

1271

*/

1272

public static Computer serial();

1273

1274

/**

1275

* Get runner for a test suite

1276

* @param parent - Parent runner

1277

* @param classes - Test classes

1278

* @return Runner for the suite

1279

*/

1280

public Runner getSuite(RunnerBuilder parent, Class<?>[] classes) throws InitializationError;

1281

1282

/**

1283

* Get runner for a single test class

1284

* @param testClass - Test class

1285

* @return Runner for the class

1286

*/

1287

protected Runner getRunner(RunnerBuilder builder, Class<?> testClass) throws Throwable;

1288

}

1289

1290

/**

1291

* Computer for running tests in parallel. Extends Computer to provide concurrent execution.

1292

* Part of org.junit.experimental package.

1293

*/

1294

public class ParallelComputer extends Computer {

1295

/**

1296

* Constructor for ParallelComputer

1297

* @param classes - true to parallelize classes, false otherwise

1298

* @param methods - true to parallelize methods, false otherwise

1299

*/

1300

public ParallelComputer(boolean classes, boolean methods);

1301

1302

/**

1303

* Create a computer that runs test classes in parallel

1304

* @return Computer that parallelizes classes

1305

*/

1306

public static Computer classes();

1307

1308

/**

1309

* Create a computer that runs test methods in parallel

1310

* @return Computer that parallelizes methods

1311

*/

1312

public static Computer methods();

1313

}

1314

1315

/**

1316

* Reorders tests. An Ordering can reverse the order of tests, sort the order or shuffle the order.

1317

* Generally used through Request.orderWith() rather than directly.

1318

* @since 4.13

1319

*/

1320

public abstract class Ordering {

1321

/**

1322

* Creates an Ordering that shuffles items using the given Random instance

1323

* @param random - Random instance for shuffling

1324

* @return Ordering that shuffles

1325

*/

1326

public static Ordering shuffledBy(Random random);

1327

1328

/**

1329

* Creates an Ordering from the given factory class

1330

* @param factoryClass - Factory class to create the ordering

1331

* @param annotatedTestClass - Test class annotated with @OrderWith

1332

* @return Created ordering

1333

* @throws InvalidOrderingException if the instance could not be created

1334

*/

1335

public static Ordering definedBy(

1336

Class<? extends Ordering.Factory> factoryClass,

1337

Description annotatedTestClass) throws InvalidOrderingException;

1338

1339

/**

1340

* Creates an Ordering from the given factory

1341

* @param factory - Factory to use

1342

* @param annotatedTestClass - Test class annotated with @OrderWith

1343

* @return Created ordering

1344

* @throws InvalidOrderingException if the instance could not be created

1345

*/

1346

public static Ordering definedBy(

1347

Ordering.Factory factory,

1348

Description annotatedTestClass) throws InvalidOrderingException;

1349

1350

/**

1351

* Order the tests in target using this ordering

1352

* @param target - Target to order (typically Orderable)

1353

* @throws InvalidOrderingException if ordering does something invalid

1354

*/

1355

public void apply(Object target) throws InvalidOrderingException;

1356

1357

/**

1358

* Implemented by sub-classes to order the descriptions

1359

* @param descriptions - Descriptions to order

1360

* @return descriptions in order

1361

*/

1362

protected abstract List<Description> orderItems(Collection<Description> descriptions);

1363

1364

/** Context about the ordering being applied */

1365

public static class Context {

1366

/**

1367

* Gets the description for the top-level target being ordered

1368

* @return Description of target

1369

*/

1370

public Description getTarget();

1371

}

1372

1373

/**

1374

* Factory for creating Ordering instances

1375

* For use with @OrderWith, needs public no-arg constructor

1376

*/

1377

public interface Factory {

1378

/**

1379

* Creates an Ordering instance using the given context

1380

* @param context - Context for creating ordering

1381

* @return Created ordering

1382

*/

1383

Ordering create(Context context);

1384

}

1385

}

1386

1387

/**

1388

* Orders tests. Used internally by Ordering to apply ordering logic.

1389

* @since 4.13

1390

*/

1391

public final class Orderer {

1392

/**

1393

* Orders the descriptions

1394

* @param descriptions - Descriptions to order

1395

* @return descriptions in order

1396

* @throws InvalidOrderingException if ordering is invalid

1397

*/

1398

public List<Description> order(Collection<Description> descriptions)

1399

throws InvalidOrderingException;

1400

1401

/**

1402

* Order the tests in target

1403

* @param target - Target to order

1404

* @throws InvalidOrderingException if ordering is invalid

1405

*/

1406

public void apply(Object target) throws InvalidOrderingException;

1407

}

1408

1409

/**

1410

* Parameters passed to FilterFactory for creating filters.

1411

* Contains the top-level test description and string arguments from filter specification.

1412

*/

1413

public final class FilterFactoryParams {

1414

/**

1415

* Creates filter factory parameters

1416

* @param topLevelDescription - Description of all tests being filtered

1417

* @param args - String arguments for the filter factory

1418

* @throws NullPointerException if either parameter is null

1419

*/

1420

public FilterFactoryParams(Description topLevelDescription, String args);

1421

1422

/**

1423

* Get the string arguments passed to the filter factory

1424

* @return Arguments string (may be empty, never null)

1425

*/

1426

public String getArgs();

1427

1428

/**

1429

* Get the description of all tests being filtered

1430

* @return Top-level description

1431

*/

1432

public Description getTopLevelDescription();

1433

}

1434

```

1435