西西軟件園多重安全檢測下載網站、值得信賴的軟件下載站!
軟件
軟件
文章
搜索

首頁編程開發(fā)java → spring3.0使用annotation完全代替XML

spring3.0使用annotation完全代替XML

相關軟件相關文章發(fā)表評論 來源:septem時間:2010/8/19 12:22:10字體大。A-A+

作者:佚名點擊:2598次評論:0次標簽: spring XML annotation

I wanna reach spring簡體中文硬盤版
  • 類型:ACT動作游戲大小:72.9M語言:中文 評分:10.0
  • 標簽:
立即下載

@Service與@Component有什么不同?那天被問到這個問題,一時之間卻想不起來,就利用這篇文章來紀錄spring3.0中常用的annotation。

從spring2.5開始,annotation結合BeanPostProcessor成了擴展Spring IoC容器的常用方法。Spring2.5增加了對JSR-250中@Resource, @PostConstruct, @PreDestroy的支持,Spring 3.0又增加了對JSR-330 (Dependency Injection for Java)中 @Inject,@Qualifier, @Named, @Provider的支持。將相關的jsr jar包丟到classpath,并注冊相應的BeanPostProcessor,其它的一切spring會幫你完成。spring還提供了一個簡便的方法,通過在context的XML配置文件中加入:Xml代碼
<context:annotation-config/>

<context:annotation-config/>
spring 會自動注冊AutowiredAnnotationBeanPostProcessor, CommonAnnotationBeanPostProcessor, RequiredAnnotationBeanPostProcessor,代碼中就可以使用@Autowired, @Required等annotaion了。

再回到文章開頭的問題吧。spring從2.5開始加入了classpath scanning的功能,來代替之前在xml中定義Bean。首先在context的XML配置文件中加入:Xml代碼
<context:component-scan base-package="org.example"/>

<context:component-scan base-package="org.example"/>
spring 便會在org.example以及它的子package中查找所有的類,將符合條件的Bean注冊在IoC容器當中。到3.0,spring引入了4種原型annotation(stereotype annotaion),分別為@Component, @Serivce, @Controller, @Repository。一般情況下只在將類加上@Componet,spring在掃描classpath的時候會自動檢測到,并將這個類注冊到IoC 容器中,在代碼的其它部分,便可以借助@Autowired來注入這個Bean。后面的三種原型分別是特殊的@Conponet,適用于更加特殊的場合,比如Service層,Spring MVC, DAO等。這一點從源碼上也可以看出:

Java代碼
@Target({ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Component
public @interface Service {
String value() default "";
}

@Target({ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Component
public @interface Service {
String value() default "";
}

@Service本身就是被@Componet這個元注解(meta annotaion)標注的。因此對于這三個層的Bean, spring的文檔也推薦將它們標注為@Service, @Controller與@Repository,因為這樣更方便其它工具對這些特殊Bean的處理以及為它們加上相關AOP的 aspects,spring在后續(xù)版本的升級上也可能對它們增加更多的特殊語義。至于它們到底比普通的@Componet多了哪些 aspects,spring的文檔上并沒有詳細說明,只簡單地提到了對于@Repository,spring會自動加上exception translation,用于轉化持久層拋出的異常。我google了一下,包括spring論壇的帖子,也沒能找到這方面的詳細信息,這點希望熟悉spring源代碼的朋友能夠說說。

現(xiàn)在通過classpath scanning以及@Component,@Autowired等annotation,我們已無須通過xml來定義Bean了。但還必須在application context的xml中添加<context:annotation-config/>與<context:component-scan base-package="org.example"/>。再進一步想,能不能把這個配置文件也去掉,實現(xiàn)真正的零配置?spring3.0原先Spring JavaConfig項目的功能移到了Spring Core里面,從而實現(xiàn)了利用Java代碼來代替?zhèn)鹘y(tǒng)的XML配置文件,這個功能是通過@Configuration, @Bean, @Import, @DependsOn等annotation實現(xiàn)的。

Java代碼
@Configuration
public class AppConfig {
@Bean
public GreetingDao greetingDao() {
return new GreetingDao();
}
}

public class GreetingDao {
public String getGreeting(){
return "Hi";
}
}

@Configuration
public class AppConfig {
@Bean
public GreetingDao greetingDao() {
return new GreetingDao();
}
}

public class GreetingDao {
public String getGreeting(){
return "Hi";
}
}

@configuration表明這個類包含Bean的定義,@Bean在這里就相當于原先的配置:<bean id="greetingDao" class="septem.demo.GreetingDao"/>。通過AnnotationConfigApplicationContext就可以使用這個Bean了:
Java代碼
@Test
public void test_java_config(){
AnnotationConfigApplicationContext ctx = new AnnotationConfigApplicationContext(AppConfig.class);
GreetingDao dao = ctx.getBean(GreetingDao.class);
assertEquals("Hi", dao.getGreeting());
}

@Test
public void test_java_config(){
AnnotationConfigApplicationContext ctx = new AnnotationConfigApplicationContext(AppConfig.class);
GreetingDao dao = ctx.getBean(GreetingDao.class);
assertEquals("Hi", dao.getGreeting());
}

注意AppConfig里面的greetingDao雖然是是直接new出來的,但它的默認scope仍是singleton,跟采用配置文件的情況是一樣的,如果需要prototype,則可以另外為它加上@Scope("prototype")。上面采用的方法是手工將Bean定義在 @Configuration里面,我們同樣可以讓spring自動檢測Bean,比如下面的GreetingSerivce:

Java代碼
@Service
public class GreetingService {
public String sayHello(){
return "Hello";
}
}

@Service
public class GreetingService {
public String sayHello(){
return "Hello";
}
}

將GreetingService標注為@Service,就不需要在AppConfig里面注冊了:

Java代碼
@Test
public void test_service(){
AnnotationConfigApplicationContext ctx = new AnnotationConfigApplicationContext();
ctx.scan("septem.demo");
ctx.refresh();

GreetingService service = ctx.getBean(GreetingService.class);
assertEquals("Hello", service.sayHello());
}

@Test
public void test_service(){
AnnotationConfigApplicationContext ctx = new AnnotationConfigApplicationContext();
ctx.scan("septem.demo");
ctx.refresh();

GreetingService service = ctx.getBean(GreetingService.class);
assertEquals("Hello", service.sayHello());
}

以上的ctx.scan("septem.demo")就相當于配置文件:<context:component-scan base-package="septem.demo"/>。注意因為@Configuration本身也是被@Component這個meta-annotation標注的,所以AppConfig也不需要手工在 AnnotationConfigApplicationContext里注冊,它同@Service一樣會被自動檢測到。Spring3.0還提供了 AnnotationConfigWebApplicationContext用來代替原先web項目中的 XmlWebApplicationContext,這樣在web項目中同樣可以實現(xiàn)真正的零配置了。Spring的官方文檔還提供了針對更復雜情況的處理方法,有興趣的朋友可以看看。

    相關評論

    閱讀本文后您有什么感想? 已有人給出評價!

    • 8 喜歡喜歡
    • 3 頂
    • 1 難過難過
    • 5 囧
    • 3 圍觀圍觀
    • 2 無聊無聊

    熱門評論

    最新評論

    第 1 樓 遼寧大連遼寧警官高等?茖W校 網友 客人 發(fā)表于: 2011/2/15 11:41:57
    AnnotationConfigApplicationContext 不會自動創(chuàng)建SessionFactory,零配置因此無法實現(xiàn)!

    支持( 0 ) 蓋樓(回復)

    發(fā)表評論 查看所有評論(0)

    昵稱:
    表情: 高興 可 汗 我不要 害羞 好 下下下 送花 屎 親親
    字數(shù): 0/500 (您的評論需要經過審核才能顯示)