Spring Dependency Injection Revealed: The Differences and Applications of @Autowired, @Qualifier and @Resource

Preface

In the world of programming, just like in the Magic Kingdom, sometimes we need to get different components to communicate and collaborate with each other to create amazing applications. And here, dependency injection is our magic spell, and @Autowired, @Qualifierand @Resourceare our wands.

In this fantasy-filled story, we will unveil the mystery of these three magical annotations in the Spring framework. Like a magician mastering different spells, we will learn when to use to @Autowiredmake magic happen automatically, when to use @Qualifierto indicate the target of magic, and when to use to @Resourceawaken specific magical creatures.

Whether you are an experienced developer or are venturing into this magical field for the first time, this blog will help you explore the power of these annotations, allowing you to become a true wizard in the Spring world.

Now, let's travel to this magical world and start our dependency injection adventure!

@AutowiredIt is important to understand the annotations related to these three dependency injections @Qualifierand @Resourcethe differences between them. Their differences, usage scenarios, and their respective advantages and disadvantages are explained in detail below:

1. @AutowiredNotes:

  • Function : @AutowiredUsed to automatically assemble dependencies, which finds and injects matching beans by type (class).

  • Usage scenarios : Usually used on constructors, methods, fields or setter methods for automatic dependency injection.

  • Advantages :

    • Automation: Simplifies the dependency injection process, eliminating the need to explicitly specify the name of the bean to be injected.
    • Type safety: Dependency injection is based on type matching, so it is safer and reduces the possibility of type errors.
  • Disadvantages :

    • When there are multiple matching beans, ambiguity may arise and require further processing.

2. @QualifierNotes:

  • Function : @QualifierUsually @Autowiredused in combination with to specify the name of the specific bean to be injected.

  • Usage scenario : When there are multiple beans of the same type available for injection, it is used to eliminate ambiguity and clarify the bean to be injected.

  • Advantages :

    • Provides more fine-grained control and can inject based on bean name.
  • Disadvantages :

    • It is necessary to specify the name of the bean explicitly, which is not automatic enough.
    • If the bean name is misspelled or changed, the injection may fail.

3. @ResourceNotes:

  • Role : @ResourceIt is part of Java EE and is used for dependency injection. It can be injected based on name or type.

  • Usage scenario : Typically used in Java EE environments, beans can be injected based on name or type.

  • Advantages :

    • Injection can be done based on name or type, providing more injection flexibility.
    • No additional imports are required as it is part of Java EE.
  • Disadvantages :

    • Platform specific: @ResourceNot part of the Spring framework, so additional configuration may be required in non-Java EE environments.
    • Not @Autowiredas type safe as can be injected by name.

Sample code

When it comes to @Autowired, @Qualifierand @Resource, sample code will help to understand their usage and differences more clearly. Here is sample code with detailed comments:

Use @Autowiredand @Qualifier:

Suppose we have a simple Spring Boot application with two UserServicebeans that implement the interface: UserServiceAand UserServiceB. We want to inject one of these beans in another class.

public interface UserService {
    
    
    void getUserInfo();
}

@Service("userServiceA")
public class UserServiceA implements UserService {
    
    
    @Override
    public void getUserInfo() {
    
    
        System.out.println("User Service A");
    }
}

@Service("userServiceB")
public class UserServiceB implements UserService {
    
    
    @Override
    public void getUserInfo() {
    
    
        System.out.println("User Service B");
    }
}

@Service
public class MyService {
    
    
    private final UserService userService;

    // 使用构造函数注入,@Autowired注解会自动找到UserService的实现类并注入
    @Autowired
    public MyService(@Qualifier("userServiceA") UserService userService) {
    
    
        this.userService = userService;
    }

    public void displayUserInfo() {
    
    
        userService.getUserInfo();
    }
}

In the above example:

  • We define two UserServicebeans that implement the interface: UserServiceAand UserServiceB, and @Servicespecify their names using annotations.
  • In MyServicethe class, we use the constructor to inject UserServicean instance of the interface and @Qualifierspecify the name of the specific bean to be injected through the annotation (here "userServiceA").

In this way, the class will inject one of "userServiceA" or "userServiceB" MyServicebased on the annotation specified in the constructor .@Qualifier

Use @Resource:

Here is @Resourcean example of using dependency injection:

@Service("userServiceA")
public class UserServiceA implements UserService {
    
    
    @Override
    public void getUserInfo() {
    
    
        System.out.println("User Service A");
    }
}

@Service("userServiceB")
public class UserServiceB implements UserService {
    
    
    @Override
    public void getUserInfo() {
    
    
        System.out.println("User Service B");
    }
}

@Service
public class MyService {
    
    
    // 使用@Resource注解根据bean的名称注入
    @Resource(name = "userServiceA")
    private UserService userService;

    public void displayUserInfo() {
    
    
        userService.getUserInfo();
    }
}

In this example, we MyServiceuse the annotation on the field of the class @Resourceto specify the name of the specific bean to be injected (here "userServiceA"). Therefore, userServicethe field will be injected into "userServiceA".

Choice of usage scenarios:

  • This can be used if you are developing in a Spring environment and want to automatically inject beans and don't care about ambiguities @Autowired.

  • If there are multiple beans of the same type available for injection and you need to know which bean to inject, you can combine @Autowiredand @Qualifieruse them.

  • This can be used if you are developing in a Java EE environment and want to inject beans based on name or type @Resource.

Summarize:

  • @AutowiredUsed for automatic assembly, injection by type, suitable for simple injection scenarios, no need to explicitly specify the bean name.

  • @QualifierUsually @Autowiredused in conjunction with to disambiguate the bean name to be injected.

  • @ResourceIt is part of Java EE and provides a way to inject beans based on name or type. It is suitable for use in a Java EE environment, but is not as @Autowiredtype safe as

Depending on your specific project needs and Spring environment, choose the appropriate annotations to manage dependency injection.

Guess you like

Origin blog.csdn.net/Mrxiao_bo/article/details/133136428