javaspring-mvcdependency-injectionportletautowired

What exactly is Field Injection and how to avoid it?


I read in some posts about Spring MVC and Portlets that field injection is not recommended. As I understand it, field injection is when you inject a Bean with @Autowired like this:

@Component
public class MyComponent {
    @Autowired
    private Cart cart;
}

During my research I also read about constructor injection:

@Component
public class MyComponent {
    private final Cart cart;

    @Autowired
    public MyComponent(Cart cart){
       this.cart = cart;
    }
}

What are the advantages and the disadvantages of both of these types of injections?


EDIT 1: As this question is marked as duplicate of this question i checked it. Cause there aren't any code examples neither in the question nor in the answers it's not clear to me if i'm correct with my guess which injection type i'm using.


Solution

  • Injection types

    There are three options for how dependencies can be injected into a bean:

    1. Through a constructor
    2. Through setters or other methods
    3. Through reflection, directly into fields

    You are using option 3. That is what is happening when you use @Autowired directly on your field.


    Injection guidelines

    Edit: These 3 links mentioned here are for Spring 4.2., for newer version documentation as per 2023 (6.09) see list below

    A general guideline, which is recommended by Spring (see the sections on Constructor-based DI or Setter-based DI) is the following:


    Field injection drawbacks

    The reasons why field injection is frowned upon are as follows:


    Conclusion

    Depending on your needs, you should primarily use constructor injection or some mix of constructor and setter injection. Field injection has many drawbacks and should be avoided. The only advantage of field injection is that it is more convenient to write, which does not outweigh all the cons.


    Further reading

    I wrote a blog article about why field injection is usually not recommended: Field Dependency Injection Considered Harmful.


    Spring Documentation

    Spring 4.2 (from original post)

    Spring 6.0.9 (2023 Current Stable version)