【问题标题】:Spring: get all Beans of certain interface AND typeSpring:获取特定接口和类型的所有 Bean
【发布时间】:2017-03-10 05:20:48
【问题描述】:

在我的 Spring Boot 应用程序中,假设我有 Java 接口:

public interface MyFilter<E extends SomeDataInterface> 

(一个很好的例子是Spring的公共接口ApplicationListener

我有几个实现,例如:

@Component
public class DesignatedFilter1 implements MyFilter<SpecificDataInterface>{...}

@Component
public class DesignatedFilter2 implements MyFilter<SpecificDataInterface>{...}

@Component
public class DesignatedFilter3 implements MyFilter<AnotherSpecificDataInterface>{...}

然后,在某些对象中,我有兴趣使用实现 MyFilter但不是 MyFilter所有过滤器

这个的语法是什么?

【问题讨论】:

  • 如果我可以添加到问题中,如果我想要所有过滤器的列表,即 DesignatedFilter1、DesignatedFilter2、DesignatedFilter3 怎么办?如果我自动装配 List> ,我会得到空列表。我正在使用 Kotlin,所以不能使用 List 谢谢。

标签: java spring spring-boot autowired


【解决方案1】:

你可以简单地使用

@Autowired
private List<MyFilter<SpecificDataInterface>> filters;

编辑 2020 年 7 月 28 日:

由于不再推荐现场注入Constructor injection should be used instead of field injection

使用构造函数注入:

class MyComponent {

  private final List<MyFilter<SpecificDataInterface>> filters;

  public MyComponent(List<MyFilter<SpecificDataInterface>> filters) {
    this.filters = filters;
  }
  ...
}

【讨论】:

    【解决方案2】:

    如果您想要Map&lt;String, MyFilter&gt;,其中key (String) 代表bean 名称:

    private final Map<String, MyFilter> services;
    
    public Foo(Map<String, MyFilter> services) {
      this.services = services;
    }
    

    这是recommended 的替代品:

    @Autowired
    private Map<String, MyFilter> services;
    

    【讨论】:

      【解决方案3】:

      如果你想要一张地图,下面的代码可以工作。关键是你定义的方法

      private Map<String, MyFilter> factory = new HashMap<>();
      
      @Autowired
      public ReportFactory(ListableBeanFactory beanFactory) {
        Collection<MyFilter> interfaces = beanFactory.getBeansOfType(MyFilter.class).values();
        interfaces.forEach(filter -> factory.put(filter.getId(), filter));
      }
      

      【讨论】:

        【解决方案4】:

        以下内容会将具有扩展 SpecificDataInterface 的类型的每个 MyFilter 实例作为泛型参数注入到列表中。

        @Autowired
        private List<MyFilter<? extends SpecificDataInterface>> list;
        

        【讨论】:

        • 我不认为你打算把“= new ArrayList();”最后:)
        • 你说得对,我删除了它:)。额外信息:它仍然可以使用。
        • Spring 实现是否读取类字节码以提取确切的泛型类型?由于类型擦除,无法直接从对象中获得此信息...我讨厌这种 Spring 魔法,如果它发生的话。
        • 我相信执行此操作的类是github.com/spring-projects/spring-framework/blob/master/…,据我所知,没有字节码魔术。这只是反思。
        • 考虑到没有具体化,你确定这能按预期工作吗?
        猜你喜欢
        • 1970-01-01
        • 2016-05-13
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2014-02-21
        • 2010-09-06
        • 1970-01-01
        相关资源
        最近更新 更多