This article has participated in the Denver Nuggets Creators Camp 3 “More Productive writing” track, see details: Digg project | creators Camp 3 ongoing, “write” personal impact.

Spring’s container configuration can be done in two ways, one based on XML files and one based on annotations. Annotation injection is performed before XML injection. Therefore, when both are used together, the XML configuration overrides the annotation-injected properties.

This article will focus on @required, @AutoWired, @postConstruct, @Predestroy, and @Resource annotations.

These annotations are introduced by context:annotation-config/. Essentially the introduction of this configuration would implicitly registered AutoWiredAnnotationBeanPostProcessor, which offers the @autowired CommonAnnotationBeanPostProcessor (provide @ PostConstruct, @ PreDestroy, @ the Resource). RequiredAnnotationBeanPostProcessor provide @ (Required), thus provides the function of each annotation.

We will describe the functionality of each annotation below.

@Required

@required is usually used for methods, indicating that the parameters of the method must be configurable or loaded automatically. Usually we use this annotation if an attribute is required.

However, starting with Spring Framework 5.1, the @required annotation is officially deprecated in favor of constructor injection for Required properties, Or use InitializingBean. AfterPropertiesSet () the custom of implementation and the bean property setter method.

Example code is as follows:

public class RequiredBean {

    private BeanA  beanA;

    @Required
    public void setBeanA(BeanA beanA){
        this.beanA=beanA; }}Copy the code

@Autowired

@autoWired is the automatic injection of required fields, parameters, etc. JSR 330’s @Inject annotation can replace Spring’s @Autowired annotation.

You can annotate @Autowired to the constructor as follows:

public class AutowiredBean {

    private BeanA beanA;

    @Autowired
    public AutowiredBean(BeanA beanA){
        this.beanA=beanA; }}Copy the code

Starting with SpringFramework4.3, if the target bean defines only one constructor, the @autowired annotation is no longer required on such a constructor. However, if multiple constructors are available, at least one of them must be annotated to tell the container which one to use.

Autowired can also be annotated to a traditional setter method, as shown in the following example:

public class AutowiredBean {

    private BeanB beanB;

    @Autowired
    public void setBeanB(BeanB beanB){
        this.beanB=beanB; }}Copy the code

Annotations can also be applied to any name and multiple parameters, as follows:

    @Autowired
    public void configAB(BeanA beanA , BeanB beanB){
        this.beanA=beanA;
        this.beanB=beanB;
        
    }
Copy the code

@autowired can also be used on fields, as follows:

    @Autowired
    private BeanC beanC;
Copy the code

You can also get all beans of that particular type from ApplicationContext by adding annotations to fields or methods that require an array of that type, as shown in the following example:

    @Autowired
    private BeanC[] beanCList;
Copy the code

If you want an array or a list of items in a particular Order, target bean can realize org, springframework. Core. Ordered interface, or you can use @ the @ the Priority of the Order or standard annotations. Otherwise, their order follows the registration order defined by the corresponding target bean in the container.

Map instances can also be injected as long as the key is of type String. The Map value contains all beans that match the type, and keys is the name of the Bean. As follows:

    @Autowired
    public void configMapA(Map<String,BeanA> mapA){
    this.mapA=mapA;
    }
Copy the code

@autoWired has a required attribute. If it is possible that the bean to be injected does not exist, it can look like this:

    @Autowired(required = false)
    public void setBeanC(BeanC beanC){}Copy the code

It is recommended to use the ‘required’ attribute of @Autowired rather than the @required annotation on setter methods. The “required” attribute indicates that this attribute is required for automatic loading, or ignored if it cannot be. For @required, an exception is raised if no value is defined.

You can also indicate the non-essential nature of a particular dependency through Java 8’s java.util.Optional, as shown in the following example:

    @Autowired
    public void setMovieFinder(Optional<BeanC> BeanC) {}Copy the code

In Spring Framework 5.0, you can also use @nullable annotations:

    @Autowired
    public void setMovieFinderC(@Nullable BeanC beanC) {}Copy the code

Spring can use @autoWired to automatically parse some beans that exist by default, such as: The BeanFactory, ApplicationContext, Environment, ResourceLoader, ApplicationEventPublisher and MessageSource. These interfaces and its extension interface (e.g., ConfigurableApplicationContext or ResourcePatternResolver). Automatically inject ApplicationContext as shown below:

    @Autowired
    private ApplicationContext context;
Copy the code

Note: @Autowired, @Inject, @Value, and @Resource annotations are handled in Spring’s BeanPostProcessor, which means you can’t use these annotations in your own BeanPostProcessor, Spring BeanFactoryPostProcessor type.

@primary

When injected by type, there may be multiple candidates, and the preferred object can be indicated by the @primary annotation. As follows:

@Configuration
public class ConfigBean {

    @Bean
    @Primary
    public BeanA firstBeanA(a) { return new BeanA(); }

    @Bean
    public BeanA secondBeanA(a) {  return new BeanA();}

}
Copy the code

@Qualifier

@primary is an effective way to use auto-load by type in multiple instances, but you can use @Qualifier if you want more fine-grained control over injected beans. As follows:

    @Bean
    @Qualifier("main")
    public BeanC beanC(a) {  return newBeanC(); }Copy the code
    @Autowired
    @Qualifier("main")
    private BeanA beanA;

    @Autowired
    public void setBeanA(@Qualifier("main") BeanA beanA){}Copy the code

The value of a qualifier is not unique, it is just a filter criterion.

@autoWired is typically used to match by type, while @resource is used to match by name.

You can also create custom annotations:

@Target({ElementType.FIELD, ElementType.PARAMETER})
@Retention(RetentionPolicy.RUNTIME)
@Qualifier
public @interface Genre {

        String value(a);
}
Copy the code

The generic

In addition to the @qualifier annotation, you can use Java generic types as implicitly qualified forms. For example, suppose you have the following configuration:

public class StringStore implements Store<String> {}public class IntegerStore implements Store<Integer> {}Copy the code
    @Bean
    public StringStore stringStore(a) {
        return new StringStore();
    }

    @Bean
    public IntegerStore integerStore(a) {
        return new IntegerStore();
    }
Copy the code
public class GenericBean {

    @Autowired
    private Store<String> s1; // <String> qualifier, injects the stringStore bean

    @Autowired
    private Store<Integer> s2; // <Integer> qualifier, injects the integerStore bean

    // Inject all Store beans as long as they have an <Integer> generic
    // Store<String> beans will not appear in this list
    @Autowired
    private List<Store<Integer>> s;

}
Copy the code

@Resource

@Resource is used on fields or Setter methods, and by default @Resource is injected by name.

public class ResourceBean {
    
    @Resource(name = "beanA")
    private BeanA BeanA;
}
Copy the code

If the name is not explicitly specified, the default name is derived from the field name or setter method.

In the @Resource usage, if no explicit name is specified, and similar to @Autowired, @Resource finds a main type match instead of the specified bean, and resolves known resolvable dependencies: The BeanFactory, ApplicationContext, ResourceLoader, ApplicationEventPublisher and MessageSource interface.

@ PostConstruct and @ PreDestroy

These two annotations are primarily used for lifecycle callbacks. As follows:

public class ConstructBean   {

    @PostConstruct
    public void populateMovieCache(a) {
        // populates the movie cache upon initialization...
    }

    @PreDestroy
    public void clearMovieCache(a) {
        // clears the movie cache upon destruction...}}Copy the code

Like @Resource, the @PostConstruct and @Predestroy annotation types are part of the standard Java libraries in JDK 6 through 8. However, the entire Javax. Annotation package was separated from the core Java modules in JDK 9 and was eventually removed in JDK 11. If needed, the Javax.annotation-API artifacts are now available through Maven Central and can be added to the application’s classpath just like any other library.

The code for this article can be referenced as annotation-config

See flydean’s blog for more tutorials