= Dependency Injection for Constructors and Methods

In JUnit Jupiter, both test constructors and methods are permitted to have parameters.
This allows for greater flexibility and enables _Dependency Injection_ for constructors
and methods.

`{ParameterResolver}` defines the API for test extensions that wish to _dynamically_
resolve parameters at runtime. If a _test class_ constructor, a _test method_, or a
_lifecycle method_ (see xref:writing-tests/definitions.adoc[]) accepts a parameter, the parameter
must be resolved at runtime by a registered `ParameterResolver`.

[[built-in-parameter-resolvers]]
== Built-In Parameter Resolvers

There are currently three built-in resolvers that are registered automatically.

[[test-info]]
=== TestInfo

If a constructor or method parameter is of type `{TestInfo}`, the
`{TestInfoParameterResolver}` will supply an instance of `TestInfo` corresponding to the
current container or test as the value for the parameter. The `TestInfo` can then be used
to retrieve information about the current container or test such as the display name, the
test class, the test method, and associated tags. The display name is either a technical
name, such as the name of the test class or test method, or a custom name configured via
`@DisplayName`.

`{TestInfo}` acts as a drop-in replacement for the `TestName` rule from JUnit 4. The
following demonstrates how to have `TestInfo` injected into a `@BeforeAll` method, test
class constructor, `@BeforeEach` method, and `@Test` method.

[tabs]
====
Java::
+
--
[source,java,indent=0]
----
include::example$java/example/TestInfoDemo.java[tags=user_guide]
----
--

Kotlin::
+
--
[source,kotlin,indent=0]
----
include::example$kotlin/example/kotlin/TestInfoDemo.kt[tags=user_guide]
----
--
====

[[repetition-info]]
=== RepetitionInfo

If a method parameter in a `@RepeatedTest`, `@BeforeEach`, or `@AfterEach` method is of
type `{RepetitionInfo}`, the `{RepetitionExtension}` will supply an instance of
`RepetitionInfo`. `RepetitionInfo` can then be used to retrieve information about the
current repetition, the total number of repetitions, the number of repetitions that have
failed, and the failure threshold for the corresponding `@RepeatedTest`. Note, however,
that `RepetitionExtension` is not registered outside the context of a `@RepeatedTest`. See
xref:writing-tests/repeated-tests.adoc#examples[Repeated Test Examples].

[[test-reporter]]
=== TestReporter

If a constructor or method parameter is of type `{TestReporter}`, the
`{TestReporterParameterResolver}` will supply an instance of `TestReporter`. The
`TestReporter` can be used to publish additional data about the current test run or attach
files to it. The data can be consumed in a `{TestExecutionListener}` via the
`reportingEntryPublished()` or `fileEntryPublished()` method, respectively. This allows
them to be viewed in IDEs or included in reports.

In JUnit Jupiter you should use `TestReporter` where you used to print information to
`stdout` or `stderr` in JUnit 4. Some IDEs print report entries to `stdout` or display
them in the user interface for test results.

[tabs]
====
Java::
+
--
[source,java,indent=0]
----
include::example$java/example/TestReporterDemo.java[tags=user_guide]
----
--

Kotlin::
+
--
[source,kotlin,indent=0]
----
include::example$kotlin/example/kotlin/TestReporterDemo.kt[tags=user_guide]
----
--
====

[[custom-parameter-resolvers]]
== Custom Parameter Resolvers

NOTE: Custom parameter resolvers must be explicitly enabled by
xref:extensions/registering-extensions.adoc[registering] appropriate
xref:extensions/overview.adoc[extensions].

Check out the `xref:extensions/registering-extensions.adoc#RandomNumberExtension[RandomNumberExtension]`
for an example of a custom `{ParameterResolver}`. While not intended to be production-ready,
it demonstrates the simplicity and expressiveness of both the extension model and the
parameter resolution process. `MyRandomParametersTest` demonstrates how to inject random
values into a constructor and a `@Test` method.

[tabs]
====
Java::
+
--
[source,java,indent=0]
----
include::example$java/example/MyRandomParametersTest.java[tags=user_guide]
----
--

Kotlin::
+
--
[source,kotlin,indent=0]
----
include::example$kotlin/example/kotlin/MyRandomParametersTest.kt[tags=user_guide]
----
--
====

For real-world use cases, check out the source code for the `{MockitoExtension}` and the
`{SpringExtension}`.

When the type of the parameter to inject is the only condition for your
`{ParameterResolver}`, you can use the generic `{TypeBasedParameterResolver}` base class.
The `supportsParameters` method is implemented behind the scenes and supports
parameterized types.
