[[spring-testing-annotation-beanoverriding-testbean]]
= `@TestBean`

`@TestBean` is used on a non-static field in a test class to override a specific bean in
the test's `ApplicationContext` with an instance provided by a factory method.

The associated factory method name is derived from the annotated field's name, or the
bean name if specified. The factory method must be `static`, accept no arguments, and
have a return type compatible with the type of the bean to override. To make things more
explicit, or if you'd rather use a different name, the annotation allows for a specific
method name to be provided.

By default, the annotated field's type is used to search for candidate beans to override.
If multiple candidates match, `@Qualifier` can be provided to narrow the candidate to
override. Alternatively, a candidate whose bean name matches the name of the field will
match.

A bean will be created if a corresponding bean does not exist. However, if you would like
for the test to fail when a corresponding bean does not exist, you can set the
`enforceOverride` attribute to `true` – for example, `@TestBean(enforceOverride = true)`.

To use a by-name override rather than a by-type override, specify the `name` attribute
of the annotation.

[WARNING]
====
Qualifiers, including the name of the field, are used to determine if a separate
`ApplicationContext` needs to be created. If you are using this feature to override the
same bean in several tests, make sure to name the field consistently to avoid creating
unnecessary contexts.
====

[NOTE]
====
There are no restrictions on the visibility of `@TestBean` fields or factory methods.

Such fields and methods can therefore be `public`, `protected`, package-private (default
visibility), or `private` depending on the needs or coding practices of the project.
====

The following example shows how to use the default behavior of the `@TestBean` annotation:

[tabs]
======
Java::
+
[source,java,indent=0,subs="verbatim,quotes"]
----
	class OverrideBeanTests {
		@TestBean // <1>
		CustomService customService;

		// test case body...

		static CustomService customService() { // <2>
			return new MyFakeCustomService();
		}
	}
----
<1> Mark a field for overriding the bean with type `CustomService`.
<2> The result of this static method will be used as the instance and injected into the field.
======

In the example above, we are overriding the bean with type `CustomService`. If more than
one bean of that type exists, the bean named `customService` is considered. Otherwise,
the test will fail, and you will need to provide a qualifier of some sort to identify
which of the `CustomService` beans you want to override.

The following example uses a by-name lookup, rather than a by-type lookup:

[tabs]
======
Java::
+
[source,java,indent=0,subs="verbatim,quotes"]
----
	class OverrideBeanTests {
		@TestBean(name = "service", methodName = "createCustomService") // <1>
		CustomService customService;

		// test case body...

		static CustomService createCustomService() { // <2>
			return new MyFakeCustomService();
		}
	}
----
<1> Mark a field for overriding the bean with name `service`, and specify that the
    factory method is named `createCustomService`.
<2> The result of this static method will be used as the instance and injected into the field.
======

[TIP]
====
To locate the factory method to invoke, Spring searches in the class in which the
`@TestBean` field is declared, in one of its superclasses, or in any implemented
interfaces. If the `@TestBean` field is declared in a `@Nested` test class, the enclosing
class hierarchy will also be searched.

Alternatively, a factory method in an external class can be referenced via its
fully-qualified method name following the syntax `<fully-qualified class name>#<method name>`
– for example, `methodName = "org.example.TestUtils#createCustomService"`.
====

[TIP]
====
Only _singleton_ beans can be overridden. Any attempt to override a non-singleton bean
will result in an exception.

When overriding a bean created by a `FactoryBean`, the `FactoryBean` will be replaced
with a singleton bean corresponding to the value returned from the `@TestBean` factory
method.
====
