This post builds on the auto-mocking and @TestBean basics features. Make sure you're familiar with those first.
1. Producer Bean Replacements
When a single @Alternative class should provide
multiple bean types, use beanProducer to activate a
class with @Produces methods:
@Alternative
@ApplicationScoped
public class TestProducers {
@Produces
public AuditService audit() {
return action -> { /* no-op */ };
}
@Produces
public MetricsService metrics() {
return Mockito.mock(MetricsService.class);
}
}
@EnableTestBeans
@TestBean(beanProducer = TestProducers.class)
class MyTest {
// AuditService and MetricsService from TestProducers
// Everything else auto-mocked
}
bean and beanProducer can be combined:
@EnableTestBeans
@TestBean(bean = CustomGreeting.class)
@TestBean(beanProducer = TestProducers.class)
class MyTest { ... }
2. Whitelist Mode
limitToTestBeans = true vetoes all
application beans except those explicitly declared via
@TestBean. CDI internals (Weld, OWB, DeltaSpike) are
preserved. No auto-mocking occurs.
@EnableTestBeans(limitToTestBeans = true)
@TestBean(bean = CustomGreeting.class)
class MyTest {
// Only CustomGreeting is active.
// All other application beans are vetoed.
// No Mockito mocks are created.
}
This is useful for true unit tests where you want complete control
over which beans exist. If a @TestBean references a class
that has no @TestBean on this test, the injection point
is unsatisfied — the container tells you exactly what's missing.
3. Composable Meta-Annotations
Bundle @TestBean declarations into reusable annotations.
Meta-annotations can nest to any depth, and duplicate bean references
across levels are deduplicated automatically.
Level 1: single concern
@TestBean(bean = CustomGreeting.class)
@Retention(RUNTIME)
@Target({TYPE, ANNOTATION_TYPE})
public @interface GreetingMocks {}
Level 2: compose level-1 annotations
@GreetingMocks
@NotificationMocks
@Retention(RUNTIME)
@Target({TYPE, ANNOTATION_TYPE})
public @interface StandardMocks {}
Level 3: compose level-2 + add more
@StandardMocks
@TestBean(beanProducer = AuditProducers.class)
@TestBean(bean = CustomGreeting.class) // redundant — already in @GreetingMocks
@Retention(RUNTIME)
@Target({TYPE, ANNOTATION_TYPE})
public @interface FullTestSetup {}
Usage
@EnableTestBeans
@FullTestSetup
class MyTest {
// Gets: CustomGreeting + CustomNotificationSender + AuditProducers
// Duplicate CustomGreeting is silently deduplicated
}
@TestBean annotations across any number of
meta-annotation levels. The extension collects them into a
Set — duplicates are a no-op, not an error.
Feature Summary
| Feature | Annotation | Default |
|---|---|---|
Activate @Alternative producer bean |
@TestBean(beanProducer = ...) |
— |
| Whitelist mode (veto all others) | @EnableTestBeans(limitToTestBeans = true) |
Off |
| Composable meta-annotations | @TestBean on custom annotations |
Recursive, deduplicated |
| Manual container management | @EnableTestBeans(manageContainer = false) |
Off (auto-managed by default) |
| Disable test class injection | @EnableTestBeans(addTestClass = false) |
Off (injected by default) |