Junit
如果代码想用Junit测试框架来测试,则Spring提供了对Junit支持,还可以使用注解的方式:
@RunWith(SpringJUnit4ClassRunner.class)//让测试运行于spring测试环境
@ContextConfiguration(locations="classpath:xxx.xml")//指定 Spring 配置文件所在的位置
//@ContextConfiguration("classpath:xxx.xml")
public class TestSpring {
@Resource
private A a;
@Test
public void test() {
}
}
---------------------------------
classpath*: 和 classpath:的区别
spring可以通过指定classpath*:与classpath:前缀加路径的方式从classpath加载文件,如bean的定义文件.classpath*:的出现是为了从多个jar文件中加载相同的文件.classpath:只能加载找到的第一个文件.
比如 resource1.jar中的package 'com.test.rs' 有一个 'jarAppcontext.xml' 文件,内容如下:
<bean name="ProcessorImplA" class="com.test.spring.di.ProcessorImplA" />
resource2.jar中的package 'com.test.rs' 也有一个 'jarAppcontext.xml' 文件,内容如下:
<bean id="ProcessorImplB" class="com.test.spring.di.ProcessorImplB" />
通过使用下面的代码则可以将两个jar包中的文件都加载进来
ApplicationContext ctx = new ClassPathXmlApplicationContext( "classpath*:com/test/rs/jarAppcontext.xml");
而如果写成下面的代码,就只能找到其中的一个xml文件(顺序取决于jar包的加载顺序)
ApplicationContext ctx = new ClassPathXmlApplicationContext( "classpath:com/test/rs/jarAppcontext.xml");
classpath*:的使用是为了多个component(最终发布成不同的jar包)并行开发,各自的bean定义文件按照一定的规则:package+filename,而使用这些component的调用者可以把这些文件都加载进来.
------------------------------------------------------------
spring管理属性配置文件properties——使用PropertiesFactoryBean
<!-- config file path -->
<bean id="prop" class="org.springframework.beans.factory.config.PropertiesFactoryBean">
<property name="locations">
<array>
<value>classpath:app-context-filepath.properties</value>
</array>
</property>
</bean>
app-context-filepath.properties文件(一般以键值对的形式存储)
usageFolderPath=D:\\RatingEngineFile\\usage\\input\\
private String productFolderPath;
private String productFileName;
public String getProductFolderPath() {
return productFolderPath;
}
@Value("#{prop.usageFolderPath}")//这样就把usageFolderPath的值赋给了productFolderPath属性
public void setProductFolderPath(String productFolderPath) {
this.productFolderPath = productFolderPath;
}
--------------------------------------------------------
@Configuration注解该类,等价与XML中配置beans;用@Bean标注方法等价于XML中配置bean。
代码如下:
package SpringStudy;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import SpringStudy.Model.Counter;
import SpringStudy.Model.Piano;
@Configuration
public class SpringConfig {
/** piano(方法名)相当于bean的id,SpringStudy.Model.Piano相当于
bean的class 方法里的参数就相当于注入的属性如:
@Bean
public JdbcTemplate jdbcTemplate(DataSource dataSource) {
return new JdbcTemplate(dataSource);
}
*/
@Bean
public Piano piano(){
return new Piano();
}
@Bean(name = "counter")
public Counter counter(){
return new Counter(12,"Shake it Off",piano());
}
}
----------------------------
Spring batch 的@stepscope 一般注释在Itemreader itemprocessor itemwriter的实现类
Marking a @Bean as @StepScope is equivalent to marking it as
@Scope(value="step", proxyMode=TARGET_CLASS)、
@Bean
@StepScope
public ItemReader<Product> productReader(@Value("#{jobParameters[filePath]}")String filePath) {
this.filePath=filePath;
logger.info("productFilePath:"+filePath);
if(filePath == null){
logger.error("The product reader file is null");
return null;
}
FlatFileItemReader<Product> reader = new FlatFileItemReader<Product>();
reader.setResource(new FileSystemResource(filePath));
reader.setLineMapper(new DefaultLineMapper<Product>() {{
setLineTokenizer(new DelimitedLineTokenizer() {{
setNames(new String[]{"id","name","description","quantity"});
}});
setFieldSetMapper(new BeanWrapperFieldSetMapper<Product>() {{
setTargetType(Product.class);
}});
}});
reader.open(new ExecutionContext());
return reader;
}
注意需要设置Bean的scope属性为step,这是SpringBatch的一个后绑定技术,就是在生成Step的时候,才去创建bean,因为这个时候jobparameter才传过来。如果加载配置信息的时候就创建bean,这个时候jobparameter的值还没有产生,会抛出异常。