or run

npx @tessl/cli init
Log in

Version

Tile

Overview

Evals

Files

Files

docs

annotations.mdargument-capturing.mdbdd-testing.mdindex.mdjunit-integration.mdmatchers.mdmock-creation.mdstubbing.mdverification.md

junit-integration.mddocs/

0

# JUnit Integration

1

2

Mockito provides seamless integration with JUnit testing framework through runners and rules, enabling automatic mock initialization and enhanced debugging capabilities.

3

4

## JUnit Runners

5

6

### MockitoJUnitRunner

7

8

Automatically initializes mocks without requiring explicit setup:

9

10

```java { .api }

11

public class MockitoJUnitRunner extends Runner { }

12

```

13

14

**Usage:**

15

16

```java

17

import org.junit.runner.RunWith;

18

import org.mockito.runners.MockitoJUnitRunner;

19

20

@RunWith(MockitoJUnitRunner.class)

21

public class UserServiceTest {

22

23

@Mock

24

private UserRepository userRepository;

25

26

@Mock

27

private EmailService emailService;

28

29

@InjectMocks

30

private UserService userService;

31

32

// No need for MockitoAnnotations.initMocks(this)

33

34

@Test

35

public void testUserCreation() {

36

when(userRepository.save(any(User.class))).thenReturn(user);

37

38

User result = userService.createUser("John", "john@example.com");

39

40

verify(emailService).sendWelcomeEmail(user);

41

assertEquals("John", result.getName());

42

}

43

}

44

```

45

46

### VerboseMockitoJUnitRunner

47

48

Enhanced debugging with detailed output:

49

50

```java { .api }

51

public class VerboseMockitoJUnitRunner extends MockitoJUnitRunner { }

52

```

53

54

**Usage:**

55

56

```java

57

@RunWith(VerboseMockitoJUnitRunner.class)

58

public class UserServiceTest {

59

@Mock private UserRepository userRepository;

60

@InjectMocks private UserService userService;

61

62

@Test

63

public void testWithVerboseOutput() {

64

// Test implementation

65

// Runner will provide detailed output for debugging

66

}

67

}

68

```

69

70

**Benefits of Verbose Runner:**

71

- Detailed mock interaction logging

72

- Enhanced error messages with stack traces

73

- Better debugging information for test failures

74

- Helps identify unused stubs and interactions

75

76

### ConsoleSpammingMockitoJUnitRunner

77

78

Prints warnings and hints to console:

79

80

```java { .api }

81

public class ConsoleSpammingMockitoJUnitRunner extends MockitoJUnitRunner { }

82

```

83

84

**Usage:**

85

86

```java

87

@RunWith(ConsoleSpammingMockitoJUnitRunner.class)

88

public class UserServiceTest {

89

// Prints warnings about unused stubs, potential issues, etc.

90

}

91

```

92

93

## JUnit Rules

94

95

### MockitoRule

96

97

Alternative to runners when you can't use `@RunWith`:

98

99

```java { .api }

100

public interface MockitoRule extends TestRule { }

101

102

public class MockitoJUnit {

103

public static MockitoRule rule();

104

}

105

```

106

107

**Basic Usage:**

108

109

```java

110

import org.junit.Rule;

111

import org.mockito.junit.MockitoJUnit;

112

import org.mockito.junit.MockitoRule;

113

114

public class UserServiceTest {

115

116

@Rule

117

public MockitoRule mockitoRule = MockitoJUnit.rule();

118

119

@Mock

120

private UserRepository userRepository;

121

122

@InjectMocks

123

private UserService userService;

124

125

@Test

126

public void testUserService() {

127

// Mocks are automatically initialized

128

when(userRepository.findById(1)).thenReturn(user);

129

130

User result = userService.getUser(1);

131

132

assertEquals(user, result);

133

}

134

}

135

```

136

137

### Rule with Custom Configuration

138

139

```java

140

public class UserServiceTest {

141

142

@Rule

143

public MockitoRule mockitoRule = MockitoJUnit.rule().strictness(Strictness.STRICT_STUBS);

144

145

// Strict mode helps catch unused stubs and other issues

146

}

147

```

148

149

## Integration Patterns

150

151

### Combining with Other Runners

152

153

When you need multiple runners, use rules instead:

154

155

```java

156

@RunWith(SpringJUnit4ClassRunner.class)

157

@ContextConfiguration(classes = TestConfig.class)

158

public class IntegrationTest {

159

160

@Rule

161

public MockitoRule mockitoRule = MockitoJUnit.rule();

162

163

@Autowired

164

private ApplicationService applicationService;

165

166

@Mock

167

private ExternalService externalService;

168

169

@Test

170

public void testIntegration() {

171

// Mix Spring integration with Mockito mocks

172

}

173

}

174

```

175

176

### JUnit 5 Integration

177

178

For JUnit 5, use the MockitoExtension:

179

180

```java

181

import org.junit.jupiter.api.extension.ExtendWith;

182

import org.mockito.junit.jupiter.MockitoExtension;

183

184

@ExtendWith(MockitoExtension.class)

185

class UserServiceTest {

186

187

@Mock

188

private UserRepository userRepository;

189

190

@InjectMocks

191

private UserService userService;

192

193

@Test

194

void testUserCreation() {

195

// Test implementation

196

}

197

}

198

```

199

200

## Test Lifecycle Integration

201

202

### Manual Initialization

203

204

When you can't use runners or rules:

205

206

```java

207

public class UserServiceTest {

208

209

@Mock private UserRepository userRepository;

210

@InjectMocks private UserService userService;

211

212

@Before

213

public void setUp() {

214

MockitoAnnotations.initMocks(this);

215

}

216

217

@After

218

public void tearDown() {

219

// Optional cleanup

220

validateMockitoUsage();

221

}

222

223

@Test

224

public void testUser() {

225

// Test implementation

226

}

227

}

228

```

229

230

### Base Test Class Pattern

231

232

```java

233

public abstract class BaseMockitoTest {

234

235

@Before

236

public void setUpMocks() {

237

MockitoAnnotations.initMocks(this);

238

}

239

240

@After

241

public void validateMocks() {

242

validateMockitoUsage();

243

}

244

}

245

246

public class UserServiceTest extends BaseMockitoTest {

247

248

@Mock private UserRepository userRepository;

249

@InjectMocks private UserService userService;

250

251

@Test

252

public void testUser() {

253

// Test implementation inherits mock setup

254

}

255

}

256

```

257

258

## Debugging and Troubleshooting

259

260

### Validation

261

262

Enable automatic validation of Mockito usage:

263

264

```java

265

@After

266

public void validateMockitoUsage() {

267

Mockito.validateMockitoUsage();

268

}

269

```

270

271

**What it catches:**

272

- Unfinished stubbing

273

- Unused stubs

274

- Unnecessary stubs

275

- Invalid use of matchers

276

277

### Verbose Output Example

278

279

```java

280

@RunWith(VerboseMockitoJUnitRunner.class)

281

public class DebuggingTest {

282

283

@Mock private Service service;

284

285

@Test

286

public void testWithDebugging() {

287

when(service.process("input")).thenReturn("output");

288

when(service.process("unused")).thenReturn("never_used"); // Unused stub

289

290

String result = service.process("input");

291

292

// VerboseMockitoJUnitRunner will report:

293

// - Used stubs

294

// - Unused stubs (potential issues)

295

// - All interactions

296

}

297

}

298

```

299

300

### Console Output Configuration

301

302

```java

303

@RunWith(ConsoleSpammingMockitoJUnitRunner.class)

304

public class ConsoleOutputTest {

305

306

@Mock private Service service;

307

308

@Test

309

public void testWithConsoleOutput() {

310

// Console will show:

311

// [MockitoHint] You have unused stubbings in this test...

312

// [MockitoHint] Consider removing unnecessary stubbings...

313

}

314

}

315

```

316

317

## Best Practices

318

319

### Choose the Right Integration Method

320

321

```java

322

// Use MockitoJUnitRunner for simple cases

323

@RunWith(MockitoJUnitRunner.class)

324

public class SimpleTest { }

325

326

// Use MockitoRule when combining with other runners

327

@RunWith(SpringRunner.class)

328

public class SpringIntegrationTest {

329

@Rule public MockitoRule mockitoRule = MockitoJUnit.rule();

330

}

331

332

// Use manual initialization for maximum control

333

public class ComplexTest {

334

@Before public void setUp() { MockitoAnnotations.initMocks(this); }

335

}

336

```

337

338

### Test Organization

339

340

```java

341

@RunWith(MockitoJUnitRunner.class)

342

public class UserServiceTest {

343

344

// Group related mocks

345

@Mock private UserRepository userRepository;

346

@Mock private UserValidator userValidator;

347

@Mock private UserNotificationService notificationService;

348

349

// Service under test

350

@InjectMocks private UserService userService;

351

352

// Test data setup

353

private User testUser;

354

355

@Before

356

public void setUp() {

357

testUser = new User("John", "john@example.com");

358

}

359

360

@Test

361

public void shouldCreateValidUser() {

362

// Given

363

when(userValidator.isValid(testUser)).thenReturn(true);

364

when(userRepository.save(testUser)).thenReturn(testUser);

365

366

// When

367

User result = userService.createUser(testUser);

368

369

// Then

370

assertEquals(testUser, result);

371

verify(notificationService).sendWelcomeEmail(testUser);

372

}

373

}

374

```

375

376

### Error Handling

377

378

```java

379

@RunWith(VerboseMockitoJUnitRunner.class)

380

public class ErrorHandlingTest {

381

382

@Mock private ErrorProneService service;

383

384

@Test

385

public void testErrorScenarios() {

386

// Setup error conditions

387

when(service.process(anyString())).thenThrow(ProcessingException.class);

388

389

// Test error handling

390

assertThrows(ProcessingException.class, () -> {

391

service.process("test");

392

});

393

394

// VerboseMockitoJUnitRunner helps debug any issues

395

}

396

}

397

```

398

399

### Integration Testing

400

401

```java

402

@RunWith(SpringRunner.class)

403

@SpringBootTest

404

public class IntegrationTest {

405

406

@Rule

407

public MockitoRule mockitoRule = MockitoJUnit.rule();

408

409

@Autowired

410

private UserController userController;

411

412

@MockBean // Spring Boot's mock annotation

413

private UserService userService;

414

415

@Mock // Mockito's mock annotation

416

private ExternalApiClient apiClient;

417

418

@Test

419

public void testControllerIntegration() {

420

// Mix Spring integration testing with Mockito mocks

421

when(userService.findUser(1)).thenReturn(user);

422

423

ResponseEntity<User> response = userController.getUser(1);

424

425

assertEquals(HttpStatus.OK, response.getStatusCode());

426

assertEquals(user, response.getBody());

427

}

428

}

429

```

430

431

## Common Integration Issues

432

433

### Runner Conflicts

434

435

```java

436

// PROBLEM: Can't use multiple runners

437

@RunWith(MockitoJUnitRunner.class)

438

@RunWith(SpringRunner.class) // Compilation error

439

public class ConflictTest { }

440

441

// SOLUTION: Use rule instead

442

@RunWith(SpringRunner.class)

443

public class SolutionTest {

444

@Rule public MockitoRule mockitoRule = MockitoJUnit.rule();

445

}

446

```

447

448

### Initialization Order

449

450

```java

451

// PROBLEM: Wrong initialization order

452

public class InitializationProblem extends BaseTest {

453

public InitializationProblem() {

454

MockitoAnnotations.initMocks(this); // Too early!

455

}

456

}

457

458

// SOLUTION: Use @Before or runner

459

@RunWith(MockitoJUnitRunner.class)

460

public class InitializationSolution extends BaseTest {

461

// Automatic initialization at right time

462

}

463

```

464

465

### Forgotten Initialization

466

467

```java

468

// PROBLEM: Mocks not initialized

469

public class ForgottenInitTest {

470

@Mock private Service service; // Will be null!

471

472

@Test

473

public void test() {

474

service.doSomething(); // NullPointerException

475

}

476

}

477

478

// SOLUTION: Add initialization

479

@RunWith(MockitoJUnitRunner.class)

480

public class ProperInitTest {

481

@Mock private Service service; // Properly initialized

482

}

483

```