从Spring自动装配中排除子包?


82

在Spring 3.1中,有没有一种简单的方法可以将程序包/子程序包排除在自动装配之外?

例如,如果我想在的基本软件包中包括组件扫描,com.example是否有一种简单的方法可以排除com.example.ignore

(为什么?我想从集成测试中排除一些组件)

Answers:


84

我不确定您是否可以使用<exclude-filter>明确排除软件包,但是我敢打赌,使用正则表达式过滤器可以有效地使您到达此处:

 <context:component-scan base-package="com.example">
    <context:exclude-filter type="regex" expression="com\.example\.ignore\..*"/>
 </context:component-scan>

为了使其基于注释,您可以使用@ com.example.annotation.ExcludedFromITests注释要为集成测试排除的每个类。然后,组件扫描将如下所示:

 <context:component-scan base-package="com.example">
    <context:exclude-filter type="annotation" expression="com.example.annotation.ExcludedFromITests"/>
 </context:component-scan>

这很清楚,因为现在您已经在源代码本身中记录了该类不打算包含在集成测试的应用程序上下文中。


使用exclude-filter可以,但是我不必转义“。”
阿敏(Amin)

2
@Amin那可能是因为“。” 包含任何字符,包括文字“。”。
aksh1618

54

@ComponentScan对于相同的用例,我将使用以下方法。这与BenSchro10的XML答案相同,但是使用了注释。两者都使用过滤器type=AspectJ

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration;
import org.springframework.boot.autoconfigure.jersey.JerseyAutoConfiguration;
import org.springframework.boot.autoconfigure.jms.JmsAutoConfiguration;
import org.springframework.boot.autoconfigure.jmx.JmxAutoConfiguration;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.context.annotation.FilterType;
import org.springframework.context.annotation.ImportResource;

@SpringBootApplication
@EnableAutoConfiguration
@ComponentScan(basePackages = { "com.example" },
    excludeFilters = @ComponentScan.Filter(type = FilterType.ASPECTJ, pattern = "com.example.ignore.*"))
public class Application {
    public static void main(String[] args) {
        SpringApplication.run(Application.class, args);
    }
}

也许纯粹是怀旧之情,但我实际上仍然更喜欢XML
Kirby

10
可能是我,但是在Spring 4.2中,我必须使用FilterType.REGEX这种方法
ThankForAllTheFish

这是我想要的,但是我也不得不使用FilterType.REGEX。也许答案可以更新以反映这一点?
亚当

1
随时提出新的答案
Kirby

37

对于Spring 4,我使用以下命令
(我在发帖是因为问题已经4岁了,并且使用Spring 4的人多于Spring 3.1)。

@Configuration
@ComponentScan(basePackages = "com.example", 
  excludeFilters = @Filter(type=FilterType.REGEX,pattern="com\\.example\\.ignore\\..*")) 
public class RootConfig {
    // ...
}

13

看来您已经通过XML做到了这一点,但是如果您以新的Spring最佳实践进行工作,则您的配置将使用Java,因此可以将它们排除在外:

@Configuration
@EnableWebMvc
@ComponentScan(basePackages = "net.example.tool",
  excludeFilters = {@ComponentScan.Filter(
    type = FilterType.ASSIGNABLE_TYPE,
    value = {JPAConfiguration.class, SecurityConfig.class})
  })

9
@JonathanW但是,对于从谷歌搜索访问此页面的人来说,这是一个非常有用的答案
Stewart

12

这在Spring 3.0.5中有效。因此,我认为它将在3.1中工作

<context:component-scan base-package="com.example">  
    <context:exclude-filter type="aspectj" expression="com.example.dontscanme.*" />  
</context:component-scan> 

1
注意,如果在类路径中没有Aspectj,它会默默地忽略排除。
Vadzim

7

我认为您应该在更方便的层次结构中重构软件包,因此它们不在基本软件包之列。

但是,如果您不能这样做,请尝试:

<context:component-scan base-package="com.example">
    ...
    <context:exclude-filter type="regex" expression="com\.example\.ignore.*"/>
</context:component-scan>

在这里您可以找到更多示例:使用过滤器自定义扫描


谢谢,原则上我同意重构的想法-这是我的第一个想法。不幸的是,对于我的特定情况,这并不是一个很好的选择。
HolySamosa 2012年

好的包装设计可以避免这种情况,但是如果您不能...您就不能哈哈哈,:)
richarbernal 2012年

4

似乎对我有用的一件事是:

@ComponentScan(basePackageClasses = {SomeTypeInYourPackage.class}, resourcePattern = "*.class")

或使用XML:

<context:component-scan base-package="com.example" resource-pattern="*.class"/>

这将覆盖默认resourcePattern"**/*.class"

这似乎是仅包含基础包的最类型安全的方法,因为resourcePattern始终是相同的,并且相对于基础包而言。


2

您还可以使用@SpringBootApplication,根据Spring文档它执行相同的功能为以下三个注解: @Configuration@EnableAutoConfiguration @ComponentScan 在一个注解。

@SpringBootApplication(exclude= {Foo.class})
public class MySpringConfiguration {}

根据Javadoc,这exclude是要排除特定的自动配置类,而不是组件扫描中的所有类。如果尝试这样做,将收到错误消息“无法排除以下类,因为它们不是自动配置类”。
Abhijit Sarkar

0

您还可以包括特定的软件包,并排除它们,例如:

包含和排除(两者)

 @SpringBootApplication
        (
                scanBasePackages = {
                        "com.package1",
                        "com.package2"
                },
                exclude = {org.springframework.boot.sample.class}
        )

只是排除

@SpringBootApplication(exclude= {com.package1.class})
public class MySpringConfiguration {}

根据Javadoc,这exclude是要排除特定的自动配置类,而不是组件扫描中的所有类。如果尝试这样做,将收到错误消息“无法排除以下类,因为它们不是自动配置类”。
Abhijit Sarkar
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.