Spring核心技術(shù)(十)——JSR-330標(biāo)準(zhǔn)注解

從Spring 3.0開始,Spring開始支持JSR-330標(biāo)準(zhǔn)的注解(依賴注入)。這些注解和Spring注解掃描的方式是一直的,開發(fā)者只需要在classpath中配置相關(guān)的jar包即可。

如果開發(fā)者使用Maven來管理項目的話,javax.injectartifact在Maven倉庫中是可用的(http://repo1.maven.org/maven2/javax/inject/javax.inject/1/)。開發(fā)者只需要在pom中引用這個依賴即可。

<dependency>
<groupId>javax.inject</groupId>
<artifactId>javax.inject</artifactId>
<version>1</version>
</dependency>

通過@Inject@Named進(jìn)行依賴注入

JSR-330中,@javax.inject.Inject和Spring中的@Autowired的職責(zé)相同:

import javax.inject.Inject;

public class SimpleMovieLister {

    private MovieFinder movieFinder;

    @Inject
    public void setMovieFinder(MovieFinder movieFinder) {
        this.movieFinder = movieFinder;
    }

    public void listMovies() {
        this.movieFinder.findMovies(...);
        ...
    }
}

@Autowired一致的是,開發(fā)者可以使用@Inject在實例變量,方法以及構(gòu)造參數(shù)級別來使用依賴注入。而且,開發(fā)者可以將注入聲明為Provider,通過Provider.get()來請求那些短作用域或者延遲初始化的Bean。比如如下的例子:

import javax.inject.Inject;
import javax.inject.Provider;

public class SimpleMovieLister {

    private Provider<MovieFinder> movieFinder;

    public void listMovies() {
        this.movieFinder.get().findMovies(...);
        ...
    }
}

如果開發(fā)者希望來通過名字來限定注入的Bean,可以使用@Named注解:

import javax.inject.Inject;
import javax.inject.Named;

public class SimpleMovieLister {

    private MovieFinder movieFinder;

    @Inject
    public void setMovieFinder(@Named("main") MovieFinder movieFinder) {
        this.movieFinder = movieFinder;
    }

    // ...
}

@Named:等同于@Component注解

JSR-330中,@javax.inject.Named和Spring中的@Component的職責(zé)類似:

import javax.inject.Inject;
import javax.inject.Named;

@Named("movieListener")
public class SimpleMovieLister {

    private MovieFinder movieFinder;

    @Inject
    public void setMovieFinder(MovieFinder movieFinder) {
        this.movieFinder = movieFinder;
    }

    // ...
}

@Component的使用中經(jīng)常是不需要指定名字的,@Named注解也是如此:

import javax.inject.Inject;
import javax.inject.Named;

@Named
public class SimpleMovieLister {

    private MovieFinder movieFinder;

    @Inject
    public void setMovieFinder(MovieFinder movieFinder) {
        this.movieFinder = movieFinder;
    }

    // ...
}

在使用@Named注解的時候,也同樣可以使用組件掃描:

@Configuration
@ComponentScan(basePackages = "org.example")
public class AppConfig  {
    ...
}

和Spring的@Component組件不同的是,JSR-330的Named注解不可以組合來使用,如果希望自定義組件注解的話,還請使用Spring的組件注解。

JSR-330標(biāo)準(zhǔn)注解的限制

當(dāng)使用JSR-330標(biāo)準(zhǔn)的注解時,了解其和Spring注解的不同點也是十分必要的,參考如下表:

Spring javax.inject.* javax.inject 限制
@Autowired @Inject @Inject注解沒有required屬性,但是可以通過Java 8的Optional取代
@Component @Named JSR_330標(biāo)準(zhǔn)并沒有提供復(fù)合的模型,只有一種方式來識別組件
@Scope("singleton") @Singleton JSR-330默認(rèn)的作用域類似Spring的prototype,然而,為何和Spring的默認(rèn)保持一致,JSR-330標(biāo)準(zhǔn)中的Bean在Spring中默認(rèn)也是單例的。如果要使用非單例的作用域,開發(fā)者應(yīng)該使用Spring的@Scope注解。java.inject也提供一個@Scope注解,然而,這個注解僅僅可以用來創(chuàng)建自定義的作用域時才能使用。
@Qualifier @Qualifier/@Named javax.inject.Qualifier僅僅是一個元注解,用來構(gòu)建自定義限定符的。而String的限定符(比如Spring中的@Qualifier)可以通過javax.inject.Named來實現(xiàn)
@Value - 不等價
@Required - 不等價
@Lazy - 不等價
ObjectFactory Provider javax.inject.Provider是SpringObjectFactory的另一個選擇,通過get()方法來代理,Provider可以和Spring的@Autowired組合使用
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容