《Spring实战》学习笔记Day3:高级装配
1、环境与profile
Spring为环境相关的bean所提供的解决方案与构建时的方案没有太大差别。Spring不是在构建的时候决定创建哪个bean,而是在运行时确定。这样的结果就是同一个部署单元能够适用于所有的环境,没有必要进行重新构建。在3.1版本中,Spring引入了bean profile功能。要使用profile,首先要将所有的bean定义整理到一个或多个profile中,在将应用部署到每个环境时,要确保对应的profile处于激活(active)状态。
import javax.sql.DataSource;
import org.springframework.content.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annnotation.Profile;
import org.springframework.jdbc.datasoruce.embedded.EmbeddedDatabaseBuilder;
import org.springframework.jdbc.datasoruce.embedded.EmbeddedDatabaseType;
@Configuration
@Profile("dev")
public class DevelopmentProfileConfig{
@Bean(destroyMethod="shutdown")
public DataSpurce dataSource(){
return new EmbeddedDatabaseBuilder()
.setType(EmbeddedDatabaseType.H2)
.addScript("classpath:schema.sql")
.addScript("classpath:test-data.sql")
.build();
}
}
在Spring 3.1中,只能在类级别上使用@profile注解。从Spring 3.2开始,可以在方法级别上使用@profile注解,与@bean一同使用。注意:没有指定profile的bean始终都会被创建,与激活哪个profile没有关系。
Spring在确定激活哪个profile处于激活状态时,需要依赖两个独立的属性:spring.profiles.active和spring.profiles.default。
2、条件化的bean声明
Spring 4 引入了一个@Conditional 注解,它可以用到带有@Bean注解的方法上。如果给定的条件计算结果为true,就会创建这个bean,否则的话,这个bean会被忽略。
@Bean
@Conditional(MagicExistsCondition.class)
public MagicBean magicBean(){
return new MagicBean();
}
3、自动装配的歧义性
1、标识首选(primary)的bean
在声明bean的时候,将其中一个可选的bean设置为首选bean能够避免自动装配的歧义性。设置首先bean的局限性在于@primary 无法将可选方案的范围限定到唯一一个无歧义性的选项中。它只能标示一个优先的可选方案。当首选bean的数量超过一个时,无法进一步缩小可选范围。
2、使用限定符(qualifier)限定自动装配的bean
Spring的限定符能够在所有可选的bean上进行缩小范围的操作,最终能够达到只有一个bean满足所规定的限定条件。
@Autowired
@Qualifier("iceCream")
public void setDessert(Dessert dessert){
this,dessert = dessert;
}
基于默认的bean ID作为限定符虽然简单,但由于和要注入的bean的名称是紧耦合的,对类名称的任意改动都会导致限定符失效。
4、bean的作用域
在默认情况下,Spring应用上下文中所有bean都是作为单例形式创建的。不管给定的一个bean被注入到其它bean多少次,每次所注入的都是同一个实例。
Spring定义了多种作用域,可以基于这些作用域创建bean,包括:
1、单例(singleton):在整个应用中,只创建bean的一个实例。
2、原型(Prototype):每次注入或者通过Spring应用上下文获取的时候,都会创建一个新的bean实例。
3、会话(Session):在Web应用中,为每个会话创建一个bean实例。
4、请求(Request):在Web应用中,为每个请求创建一个bean实例。
5、运行时值注入
在运行时计算要注入到bean中的值,避免硬编码。
1、属性占位符
属性占位符要放到${…}中。
2、Spring表达式语言(SpEL)
SpEL的特性有:
1)使用bean的ID来引用bean;
2)调用方法和访问对象的属性;
3)对值进行算术、关系和逻辑运算;
4)正则表达式匹配;
5)集合操作。
SpEL表达式要放到#{…}中,如
#{T(System).currentTimeMilles()}