【问题标题】:Spring boot injection of inherited class继承类的spring boot注入
【发布时间】:2017-10-10 04:37:18
【问题描述】:

我正在开发一个 java 核心库,将更改保持在最低限度,它包含一个类 Foo,其中 Foo 由 spring rest 接口使用并自动装配到 rest 接口中。

我必须扩展 Foo 以覆盖它在 Foo.init() 上调用的方法之一,以稍微改变启动。

我的 FooExtend 是从我项目中的另一个类自动装配的,我希望让这两个引用同一个对象,即 FooExtend 对象,但目前我得到一个 Foo 对象和一个 FooExtend。我应该如何解决这个问题?下面的例子

@Component
public class Foo{
  @PostConstruct
  private void init() {
    startStuff();
  }

  protected void startStuff(){
    //Stuff done here
  }
}

@Component
public class FooExtend extends Foo{
  @PostConstruct
  private void init() {
    //Nothing is done here
  }

  @Override
  protected void startStuff(){
    //Different altered stuff is done here
  }
}

【问题讨论】:

  • 我不确定我是否理解您的问题。您有两个 bean,一个名为“foo”的 bean 和一个名为“fooExtend”的 bean。在我看来,您应该能够在对 Foo 的引用之上使用 @Qualifier("fooExtend") 或 @Qualifier("foo") 以及 @Autowired 来自动装配一个或另一个。

标签: java spring inheritance spring-boot inject


【解决方案1】:

尝试从扫描中排除 Foo 类

@ComponentScan(value = {'your.package.here'}, excludeFilters = {
  @ComponentScan.Filter(classes = { Foo.class })
})

【讨论】:

  • 我不能对 Foo 进行这样的更改,因为它位于 Core 包中,因此不应更改为根据核心破坏其他项目。还是我应该把它放在我自己的包裹里?
  • 你应该在你的 spring-boot 中添加这个(而不是在核心包中)。因此,当您的应用启动时,不会创建 Foo.class 的 bean。
  • 不能让它工作,我可能在我的类定义中很友好,但这样做时我得到这个错误:java.lang.IllegalArgumentException: An error occurred while processing a @ComponentScan ANNOTATION type filter: class com.companyname.projectname.core.Foo is not assignable to interface java.lang.annotation.Annotation
  • 这个解决方案的一个问题是核心有它自己的@ComponentScan,包括Foo。所以这个排除可能只会中断,因为它没有找到任何东西。
  • 如果您不想在 Spring 上下文中注册 Foo ,那么这是一个正确的解决方案。尝试指定过滤器类型:@ComponentScan.Filter(type=FilterType.ASSIGNABLE_TYPE, value=Foo.class)。但是,Foo 和 FooExtend 需要在不同的包中,以便 FooExtend 在您的 Spring 上下文中注册。
【解决方案2】:

根据您的要求,有 2 个可能的答案:

1) 您希望在 Spring 上下文中同时注册 Foo 和 FooExtend。 在这种情况下,您可以使用@Qualifier 注解注入一个或另一个实例:

@Autowired
@Qualifier("fooExtend")
Foo foo;

2) 您只想在 Spring 上下文中注册 FooExtend。

@ComponentScan(value = {'your.package.here'}, excludeFilters = {
 @ComponentScan.Filter(type=FilterType.ASSIGNABLE_TYPE, value=Foo.class))
}

但是要求 Foo 和 FooExtend 位于不同的包中,以便 FooExtend 不会被上述过滤器排除。

【讨论】:

  • 解决方案 2 会更可取,但 Foo 在 Core 的 Spring 上下文中,导致它仍然被加载
  • 这取决于您如何从核心库中扫描/注册 bean。如果是@ComponentScan,那么你可以通过Filter来排除它。
  • 我无法让它工作。它给了我以下错误:java.lang.IllegalArgumentException: An error occurred while processing a @ComponentScan ANNOTATION type filter: class com.companyname.projectname.core.Foo is not assignable to interface java.lang.annotation.Annotation
猜你喜欢
  • 1970-01-01
  • 2019-03-27
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-11-08
  • 1970-01-01
  • 2021-11-05
  • 2020-06-08
相关资源
最近更新 更多