从Spring3.0,@Configuration用于定义配置类,可替换xml配置文件,被注解的类内部包含有一个或多个被@Bean注解的方法,这些方法将会被AnnotationConfigApplicationContext或AnnotationConfigWebApplicationContext类进行扫描,并用于构建bean定义,初始化Spring容器。
使用@Configuration注解的配置类有如下要求:
@Bean注解告诉Spring,一个带有@Bean注解的方法将返回一个对象,该对象应该被注册为在 Spring 应用程序上下文中的 bean。
@Bean是一个方法级别上的注解,主要用在@Configuration注解的类里,也可以用在@Component注解的类里。
@ConfigurationProperties注解,主要是用来把properties或者yml配置文件转化为bean来使用的,而@EnableConfigurationProperties注解的作用是@ConfigurationProperties注解生效。
如果只配置@ConfigurationProperties注解,在IOC容器中是获取不到properties配置文件转化的bean的,当然在@ConfigurationProperties加入注解的类上加@Component也可以使交于springboot管理。
@AutoConfigureAfter(DataSourceAutoConfiguration.class) //在加载配置的类之后再加载当前类
PostConstruct 注释用于在依赖关系注入完成之后需要执行的方法上,以执行任何初始化。
注意:该方法不得有任何参数;该方法的返回类型必须为 void;该方法不得抛出已检查异常;
所谓元注解就是可以注解到别的注解上的注解,以下介绍4个基本元注解的作用
1、@Retention: 定义注解的保留策略
@Retention(RetentionPolicy.SOURCE) //注解仅存在于源码中,在class字节码文件中不包含 @Retention(RetentionPolicy.CLASS) // 默认的保留策略,注解会在class字节码文件中存在,但运行时无法获得, @Retention(RetentionPolicy.RUNTIME) // 注解会在class字节码文件中存在,在运行时可以通过反射获取到
2、@Target:定义注解的作用目标
@Target(ElementType.TYPE) //接口、类、枚举、注解 @Target(ElementType.FIELD) //字段、枚举的常量 @Target(ElementType.METHOD) //方法 @Target(ElementType.PARAMETER) //方法参数 @Target(ElementType.CONSTRUCTOR) //构造函数 @Target(ElementType.LOCAL_VARIABLE)//局部变量 @Target(ElementType.ANNOTATION_TYPE)//注解 @Target(ElementType.PACKAGE) ///包
3、@Document:说明该注解将被包含在javadoc中
4、@Inherited:说明子类可以继承父类中的该注解
一、声明一个Configuration配置类
@org.springframework.context.annotation.Configuration @ConditionalOnClass({ SqlSessionFactory.class, SqlSessionFactoryBean.class }) @ConditionalOnBean(DataSource.class) @EnableConfigurationProperties(MybatisProperties.class) @AutoConfigureAfter(DataSourceAutoConfiguration.class) //在加载配置的类之后再加载当前类 public class MybatisAutoConfiguration { private static final Logger logger = LoggerFactory.getLogger(MybatisAutoConfiguration.class); private final MybatisProperties properties; private final Interceptor[] interceptors; private final ResourceLoader resourceLoader; private final DatabaseIdProvider databaseIdProvider; private final List<ConfigurationCustomizer> configurationCustomizers; //会自动注入参数中已经被实例化的bean public MybatisAutoConfiguration(MybatisProperties properties, ObjectProvider<Interceptor[]> interceptorsProvider, ResourceLoader resourceLoader, ObjectProvider<DatabaseIdProvider> databaseIdProvider, ObjectProvider<List<ConfigurationCustomizer>> configurationCustomizersProvider) { this.properties = properties; this.interceptors = interceptorsProvider.getIfAvailable(); this.resourceLoader = resourceLoader; this.databaseIdProvider = databaseIdProvider.getIfAvailable(); this.configurationCustomizers = configurationCustomizersProvider.getIfAvailable(); } @PostConstruct //配置加载完后执行此方法 public void checkConfigFileExists() { //检查配置的configLocation是否加载到资源 if (this.properties.isCheckConfigLocation() && StringUtils.hasText(this.properties.getConfigLocation())) { Resource resource = this.resourceLoader.getResource(this.properties.getConfigLocation()); Assert.state(resource.exists(), "Cannot find config location: " + resource + " (please add config file or check your Mybatis configuration)"); } } @Bean @Primary //当spring实例化了多个DataSource的bean,自动注入时默认注入这个 @ConfigurationProperties(prefix = "spring.datasource.druid.oracle") public DataSource dataSource() { return DruidDataSourceBuilder.create().build(); } //配合@Qualifier使用注入特定bean @Bean(name="transactionManager") //**声明返回的bean名,默认为方法名tmOracle** DataSourceTransactionManager tmOracle(@Qualifier("dataSource") DataSource dataSource) { DataSourceTransactionManager tm = new DataSourceTransactionManager(dataSource); return tm; } @Bean @ConditionalOnMissingBean public SqlSessionFactory sqlSessionFactory(DataSource dataSource) throws Exception { //以下省略sqlSessionFactory的初始化操作 } @Bean @ConditionalOnMissingBean public SqlSessionTemplate sqlSessionTemplate(SqlSessionFactory sqlSessionFactory) { //... }
二、配置文件信息加载到Properties类
@ConfigurationProperties(prefix = "mybatis") public class MybatisProperties { private String configLocation; //对应配置 mybatis.configLocation= ... //set和get方法 }