Spring-Context之八:一些依賴注入的小技巧

黃博文發表於2014-03-30

Spring框架在依賴注入方面是非常靈活和強大的,多瞭解點一些注入的方式、方法,絕對能優化配置。

idref

idref屬性可以傳入一個bean的名稱,雖然它是指向一個bean的引用,但是得到的是該bean的id名。

1
2
3
4
5
6
7
8
9
10
11
<beans>

    <bean id="movieService" class="DefaultMovieService"/>

    <bean id="cinema" class=“Cinema">
        <property name="serviceRef">
            <idref bean="movieService"/>
        </property>
    </bean>

</beans>

它和直接設定serviceRef屬性的value為movieService的區別是前者是能夠保證必須有一個名movieService的bean存在於當前的spring容器中,如果沒有則Spring容器會在初始化階段就會報錯;而後者僅僅是一個字串,spring容器在初始化不會做任何檢查,很可能將異常推後到執行時丟擲。

內部bean

bean的定義是可以巢狀的。

1
2
3
4
5
6
<beans>
     <bean id=“movieService" class="DefaultMovieService"/>
     <bean id="cinema" class=“Cinema">
        <property name="movieService" ref=“movieService"/>
    </bean>
</beans>

可以改為這種方式。

1
2
3
4
5
    <bean id="cinema" class="Cinema">
        <property name="movieService">
            <bean class="DefaultMovieService"/>
        </property>
    </bean>

這樣內部bean就不需要一個名字的,當然這也意味著它無法被其他bean引用了。當然即使你給它起了名字,Spring容器也會忽略這個名字,其他bean也無法引用它。neibubean的scope始終和waibubean的scope保持一致。

對集合的注入

Java的集合框架中包含很多集合元素,比如List、Map、Set等。Spring支援對這些集合元素的注入。

1
2
3
4
5
6
7
8
    <bean id="accountService" class="AccountService">
        <property name="accounts">
            <map>
                <entry key="bowen" value="1234"/>
                <entry key="tom" value="3456"/>
            </map>
        </property>
    </bean>
1
2
3
4
5
6
7
8
9
    <bean id="cookbook" class="Cookbook">
        <property name="recipe">
            <list>
                <value>noodle</value>
                <value>rice</value>
                <value>meat</value>
            </list>
        </property>
    </bean>

還可以直接配置java的Properties。

1
2
3
4
5
6
7
8
9
    <bean id="databaseSource" class="DatabaseSource">
        <property name="source">
            <props>
                <prop key="port">2012</prop>
                <prop key="host">localhost</prop>
                <prop key="schema">db1</prop>
            </props>
        </property>
    </bean>

巢狀屬性名注入

Spring支援使用巢狀屬性注入值。

Restaurant.java
1
2
3
4
5
6
7
8
9
10
11
12
public class Restaurant {

    private Person manager;

    public Person getManager() {
        return manager;
    }

    public void setManager(Person manager) {
        this.manager = manager;
    }
}
Person.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
public class Person {

    private String name;
    private int age;

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        this.age = age;
    }
}
1
2
3
4
5
6
    <bean id="restaurant" class="huangbowen.net.service.Restaurant">
        <property name="manager">
            <bean class="huangbowen.net.PAndCNamespace.Person"/>
        </property>
        <property name="manager.age" value="20"/>
    </bean>

需注意除了最後一個屬性,其他屬性不能為空值。

使用depends-on屬性

當你初始化一個bean時,需要另一個bean先被初始化,這種情況很常見。雖然Spring在最大程度上能自動按照你期望的順序來初始化bean(比如構造器注入的bean會優先初始化),但是不保證總能符合你的心意。你可以使用depends-on屬性來顯示指定bean的初始化順序。

1
2
3
4
5
6
7
8
9
10
11
12
<beans>


   <bean id="movieService" class="DefaultMovieService"/>

    <bean id="cinema" class=“Cinema” depends-on="movieService">
        <property name="serviceRef">
            <idref bean="movieService"/>
        </property>
    </bean>

</beans>

也可以同時deppends-on多個物件。

1
2
3
4
5
    <bean id="cinema" class=“Cinema” depends-on=“movieService,accountService">
        <property name="serviceRef">
            <idref bean="movieService"/>
        </property>
    </bean>

相關文章