Spring Framework 如何在两个组件之间进行选择?

问题描述 投票:0回答:2

我是Spring和依赖注入的新手,所以我会尽力而为,但这个问题可能并不完美。

简而言之,想象一个具有“奶酪”成分的“三明治”程序。瑞士奶酪和普罗沃龙奶酪都适合该接口,因此它们都可以用于我们的三明治中。我们的代码可能看起来像这样。

class Sandwich{
   @Autowired
   Meat m;
   @Autowired
   Cheese c;
}

@Component
class Ham implements Meat{
}

@Component
class Swiss implements Cheese{
}

@Component
class Provolone implements Cheese{
}

很明显Spring框架会以火腿为肉;这是唯一的肉类成分。但是Spring框架如何在Swiss和Provolone之间进行选择呢?程序员是否需要进行一些进一步的设置?如果是这样,这怎么不是紧耦合呢?

感谢您的信息!这种企业级编码对我来说是新的(并且有点吓人),因此任何意见都会受到赞赏。

spring dependency-injection loose-coupling spring-framework-beans tightly-coupled-code
2个回答
2
投票

这篇文章很好地介绍了它https://www.baeldung.com/spring-autowire#disambiguation

但简而言之,Spring 遵循以下步骤:

  1. 它将检查字段的类型,然后在
    ApplicationContext
    中按类型搜索注册的bean。如果只有一个符合条件的bean,它将注入该bean
  2. 否则,它将尝试通过查看变量名称来消除歧义,如果存在具有相同名称和类型的合格 bean,它将注入该 bean
  3. 否则,它将在字段上查找
    @Qualifier
    注释。如果有注解,它会使用其中的逻辑来确定注入哪个bean
  4. 如果仍然无法解析,Spring会抛出异常

我建议在你的例子中要么只实例化一种奶酪类型的豆。您可以通过使用

@Profile
注释对类进行注释并使用运行时配置文件值来选择要实例化的类来完成此操作。

或者,您可以声明

List<Cheese> c
,Spring 会将两种奶酪作为
List
注入到变量中。然后,您可以根据您的业务逻辑从
List
选择在运行时调用哪个奶酪。


2
投票
 In this case spring will give you the error as spring container have
 two object of type cheese that are Swiss and Provolone.
    
    class Sandwich{
       @Autowired
       Meat m;
       Cheese c;
    }
    
    @Component
    class Ham implements Meat {
    }
    
    @Component
    class Swiss implements Cheese {
    }
    
    @Component
    class Provolone implements Cheese {
    }
    
    Now if you want to provide a particular Cheese object to Sandwich you can 
  add @Qualifier("Swiss) or @Qualifier("Provolone") onto the Cheese object 
   (like to provide Spring which object you have to refer).

  // Now asking springboot to refer Swiss Cheese in Sandwich will be as follows.
    
    class Sandwich{
       @Autowired
       Meat m;
       @Qualifier("Swiss")
       Cheese c;
    }
    
    @Component
    class Ham implements Meat {
    }
    
    @Component
    class Swiss implements Cheese {
    }
    
    @Component
    class Provolone implements Cheese {
    }
© www.soinside.com 2019 - 2024. All rights reserved.