楊瑞東,王云峰,張海英
(1. 中國科學院微電子研究所 新一代通信射頻芯片技術北京市重點實驗室,北京 100029; 2. 中國科學院大學,北京 100049)
Spring新特性之Java Config在Web開發(fā)中的應用
楊瑞東1,2,王云峰1,張海英1
(1. 中國科學院微電子研究所 新一代通信射頻芯片技術北京市重點實驗室,北京 100029; 2. 中國科學院大學,北京 100049)
為提高項目開發(fā)的效率,對Spring新特性Java Config在Web開發(fā)中的應用作了深入研究。以傳統(tǒng)的使用XML配置Spring的方式為對比,對新特性Java Config的使用方法和其優(yōu)勢作了介紹。以實際案例的形式具體描述了Spring中XML配置方式和Java Config配置的方式。結果表明,Java Config在Web項目開發(fā)中具有操作簡單、編譯器錯誤檢查、更符合程序員編程規(guī)范等優(yōu)勢。使用Java Config的方式還可以配合Servlet3.0完全去掉傳統(tǒng)Web項目中固有的web.xml文件。Java Config將成為Web開發(fā)的流行趨勢。
Spring;Java Config;容器;注解
Abstract: In order to improve the efficiency of project development, intensive study of the application of Spring’s new feature Java Config in Web development is made. By contrasting with the conventional way of configuring Spring with XML, the usage method and advantage of Spring’s new feature Java Config are introduced. In the form of actual cases, Spring’s XML config and Java Config are described. As a result, Java Config in Web development has some advantages such as simple operation, compiler error checking, programming specification. The way of Java Config combined with Servlet3.0 can get rid of conventional file web.xml. Java Config will be the main trend of the Web development in the future.
Key words:Spring; Java Config; container; annotation
Spring是目前Web開發(fā)中非常流行的一個容器框架,是進行對象管理、對象關聯(lián)、解耦的一個中間層框架[1]。它的主要功能是創(chuàng)建Java bean并維護bean與bean之間的關系。在傳統(tǒng)的使用Spring的項目中都是采用外部XML文件的方式進行配置,利用XML文件來管理bean之間的依賴關系[2]。由于XML文件和程序是分離的,而且XML文件沒有集成工具語法檢查,隨著項目不斷增大,對XML的管理就越來越復雜,特別容易出錯。
Spring在新的版本中引入了使用Java Config進行配置的方式,這種配置方式使用Java類的形式來代替?zhèn)鹘y(tǒng)使用的XML文件,使用Java類進行配置編譯器可以在編譯期間檢查錯誤,這大大提高了程序開發(fā)的效率,而且使用Java編程的方式進行Spring配置更符合程序員的編程風格。利用Java Config進行Spring項目的配置是目前使用Spring的一個新的思路,相對于使用XML進行配置,使用Java Config的方式更加簡化,程序員不需要頻繁地在Java代碼和XML文件之間進行切換,而且也可以在一定程度上減少語法錯誤的可能性。
在Web項目中使用Spring框架時,不需要手動去創(chuàng)建Spring容器,而是通過外部配置文件聲明式地創(chuàng)建Spring容器,可以在web.xml文件中進行Spring容器的配置[3]。
Spring容器需要隨著Web應用的啟動而啟動,這可以利用ServletContextListener來實現(xiàn)。Spring為開發(fā)者提供了ServletContextListener的一個實現(xiàn)類ContextLoaderListener,這個類作為Listener會在創(chuàng)建時默認自動去查找WEB-INF/applicationContext.xml文件。所以如果Spring的配置文件只有一個而且名字命名為applicationContext.xml,只需要在web.xml中進行如下配置:
如果Spring的配置文件命名為其他的名字或者配置文件不止一個,則需要用
/WEB-INF/serviceContext.xml,/WEB-INF/actionContext.xml,/WEB-INF/daoContext.xml
在項目的web.xml文件中,如果開發(fā)者沒有通過contextConfigLocation指定配置文件,則Spring會自動在類路徑下查找applicationContext.xml文件,如果有contextConfigLocation,則Spring利用該參數(shù)確定配置文件;如果無法找到合適的配置文件,則Spring將無法正常初始化。
Spring初始化完成并且正常啟動后,定義在Spring配置文件中的bean就會被實例化[4]。這里以單個配置文件applicationContext.xml為例來介紹在Spring容器中如何定義并初始化bean。
定義三個類,分別是Person類、Car類、Company類。Person類具有Car類和Company類的引用,類定義如下:
public class Car{
private String name;
//省略get/set方法
}
public class Company{
private String name;
//省略get/set方法
}
public class Person{
private Car car;
private Company company;
//省略get/set方法
}
要在Spring容器中初始化這三個類,需要在applicationContext.xml中進行配置。以下代碼說明了上面三個類在上下文XML中bean的定義。
這樣Spring容器在啟動的時候,容器內就會實例化Person、Car、Company這三個類,并且三個類中的屬性也會自動地注入進去。在Person類中使用屬性car和company時就不用單獨去創(chuàng)建對象,Spring已經自動進行了實例的創(chuàng)建,而且默認情況下Spring創(chuàng)建的實例都是單例的[5]。如果需要將實例修改為非單例模式,開發(fā)者可以在Spring的配置文件applicationContext.xml中進行設置。
相對傳統(tǒng)使用XML進行配置的方式,Spring新推出了一種基于Java Config進行配置的方式[6]。在這種配置方式里丟棄了傳統(tǒng)的Spring配置文件applicationContext.xml,甚至加上Servlet3.0的支持,連Web項目中的web.xml都可以省略。
2.1在Web項目中去掉web.xml
首先來討論如何去掉傳統(tǒng)Web項目中的web.xml文件。對于一個傳統(tǒng)的Web應用,其部署在Web容器中的時候,Web容器提供其一個全局的上下文環(huán)境,這個上下文就是ServletContext,其為后面的Spring 容器提供了宿主環(huán)境。其次,在web.xml文件中會提供有contextLoaderListener。在Web容器啟動時,會觸發(fā)容器初始化事件,此時contextLoaderListener會監(jiān)聽到這個事件,Spring框架會初始化一個啟動上下文,這個啟動上下文就稱為根上下文,也就是WebApplicationContext,這是一個接口類,確切地說,其實際的實現(xiàn)類是XmlWebApplicationContext。這個就是Spring的IoC容器,其對應的bean定義的配置文件由web.xml中的context-param標簽指定。
具有Servlet3.0支持的服務器在啟動一個Web項目的時候,服務器會自動在項目代碼中掃描實現(xiàn)了WebApplicationInitializer接口的類,該類屬于Spring,在WebApplicationInitializer接口中有onStartup方法,Spring會自動執(zhí)行這個方法啟動Web應用。下面的代碼是一個實現(xiàn)了WebApplicationInitializer接口的類。
public class WebAppInitializer implements
WebApplicationInitializer{
@Override
public void onStartup(ServletContext container)
throws ServletException {
AnnotationConfigWebApplicationContext rootContext=new AnnotationConfigWebApplicationContext();
rootContext.register(AppContext.class);
container.addListener(new ContextLoaderListener(rootContext));
}
}
2.2 Java Config配置Spring
在傳統(tǒng)的使用XML文件配置的方法中,使用ClassPathXmlApplicationContext 類來加載外部 XML上下文文件。但在使用基于Java Config的方法配置Spring進行開發(fā)的時候,可以使用一個基于注解配置的AnnotationConfigApplicationContext類。在2.1節(jié)的代碼中,WebAppInitializer類的onStartup方法被執(zhí)行時,AnnotationConfigApplicationContext實例馬上被創(chuàng)建。AnnotationConfigApplicationContext類其實是 ApplicationContext 接口的一個實現(xiàn),能夠注冊所注解的配置類。在下面的代碼中,使用AppContext類來代替?zhèn)鹘y(tǒng)的XML文件作為配置類來實現(xiàn)相同的配置效果,這個類現(xiàn)在用作bean配置的平臺。以下是AppContext類的代碼。
@Configuration
public class AppContext {
@Bean
public Car car() {
Car car = new Car();
return car;
}
@Bean
public Company company() {
Company company = new Company();
return company;
}
@Bean
public Person person() {
Person person = new Person();
person.setCar(car());
person.setCompany(company());
return person;
}
}
在上面的代碼中,以編程的方式將bean定義為基于Java配置的一部分。AppContext類現(xiàn)在就像applicationContext.xml文件一樣充當著配置類的作用,這是通過@Configuration這個注解來實現(xiàn)的。@Configuration注解位于類的頂端,通過這個注解Spring會獲知這個類是一個擁有bean定義和依賴項的配置類。@Bean注解用于定義一個bean,位于定義bean并實例化依賴項的方法頂端。bean的ID就是方法的名字,bean的類型就是方法返回類型。bean的依賴項可以通過bean中的setter方法進行設置。
創(chuàng)建bean還可以采用annotation(注解)的方式。采用annotation方式進行bean的創(chuàng)建就不再需要@Bean注解方式創(chuàng)建bean,Spring會自動搜索指定路徑下面的Java類并將這些Java類注冊成為Spring容器中的bean。這些Java類采用注解的方式進行標記,方便Spring框架進行識別。Spring目前主要提供了@Component、@Controller、@Service、@Repository這四種注解來定義一個bean。目前通過這四種方式定義bean之后所實現(xiàn)的效果是一樣的。為了使得Spring能夠正確地找到定義之后的這些bean,需要在AnnotationConfigWebApplicationContext的注冊類AppContext中說明掃描的路徑,需要通過注解@ComponentScan("com.spring")來定義掃描路徑,如下面代碼所示:
@Configuration
@ComponentScan("com.spring.test")
public class AppContext {
}
和以前的AppContext類相比,在這個新的AppContext類中少了那些以@Bean注解開頭的定義bean的方法?,F(xiàn)在如果需要定義一個新的bean,只需要在com.spring.test包下面定義一個Java類并用@Component、@Controller、@Service、@Repository四個中的任意一個注解即可。
使用注解的方式創(chuàng)建bean時,bean之間的依賴關系也是用注解的方式實現(xiàn)。有兩個注解用來實現(xiàn)依賴注入,即@Autowired和@Resource,它們既可以寫在字段上,也可以寫在setter方法上。兩者的不同在于@Autowired默認使用byType的方式進行注入,而@Resource默認使用byName的方式進行注入。以下代碼是使用以注解@Autowired為例子的方式創(chuàng)建Car、Company、Person三個bean。
@Component
public class Car{
private String name = “myCar”;
//省略get/set方法
}
@Component
public class Company{
private String name = “myCompany”;
//省略get/set方法
}
@Component
public class Person{
@Autowired
private Car car;
@Autowired
private Company company;
//省略get/set方法
}
通過上面的方法創(chuàng)建bean并進行注入后,Spring容器中就有了Car、Company、Person三個實例,并且Person中的屬性car和company也被注入了Car和Company的實例,整個Spring容器容納了所需的所有bean,并且形成一個bean之間的關系網(wǎng)。需要說明的是,使用annotation創(chuàng)建bean并不是Java Config的特權,使用XML配置Spring的方式同樣也可以使用annotation的方式創(chuàng)建bean,只不過需要在配置文件applicationContext.xml中開啟使用注解,同樣也需要聲明掃描包的范圍。
使用基于Java Config的方式配置Spring框架具有比較大的優(yōu)勢,主要體現(xiàn)在以下三個方面:
(1)基于Java Config的配置定義bean是定義在Java類中,這種定義方式符合程序員一貫的編程方式,相對于使用XML定義bean的方式,使用Java Config的方式能夠減少編程思維的跳躍性,程序員不需要在Java類和XML文件中來回切換。
(2)使用Java類進行Spring配置可以在編譯期間檢查錯誤,這樣在開發(fā)項目的時候能夠隨時發(fā)現(xiàn)錯誤并修改錯誤。而使用XML配置,只有在運行時才能發(fā)現(xiàn)各種配置及語法的錯誤,降低了開發(fā)效率。
(3)使用Java Config操作簡單。只需要用@Configuration注解JavaConfig類,用每個方法來表示Bean并使用@Bean注解方法,每個方法名代表XML配置文件中的name。而在XML的配置中,創(chuàng)建bean以及bean之間的依賴關系需要通過大量的標簽來實現(xiàn)。
Spring在目前的Java Web開發(fā)中具有非常廣泛的應用,通過對比傳統(tǒng)的使用XML配置的方式,對Spring新特性Java Config在Web項目開發(fā)中的應用進行了詳細的研究。基于XML的配置方式是較為傳統(tǒng)的配置方式,其靈活性好,項目部署后修改也方便[7]。而基于Java Config的配置方式配合使用annotation開發(fā)效率高,不容易出錯,而且Java Config方式更符合程序員編程的風格,是以后Web項目開發(fā)的一種趨勢。
[1] 李洋,孫永維,許冰,等.基于Ajax,Struts,Hibernate和Spring的J2EE架構[J]. 吉林大學學報(信息科學版),2011,29(6):576-584.
[2] 胡啟敏,薛錦云,鐘林輝. 基于Spring框架的輕量級J2EE架構與應用[J]. 計算機工程與應用,2008,44(5):115-118,133.
[3] 趙佳. 支持XML配置的IoC微容器設計[D]. 天津:天津大學,2007.
[4] 翟劍錕. Spring框架技術分析及應用研究[D].北京:中國科學院大學,2013.
[5] JOHNSON R,田佳偉. Spring framework 2.5介紹(上)[J]. 程序員,2008(1):90-95.
[6] JOHNSON R,田佳偉. Spring framework 2.5介紹(中)[J]. 程序員, 2008(2):101-106.
[7] MAK G, LONG J, RUBIO D. Spring Recipes[M]. Springer Apress, 2010.
Application of Spring′s new feature Java Config in Web development
Yang Ruidong1,2, Wang Yunfeng1, Zhang Haiying1
(1. Beijing Key Laboratory of Radio Frequency IC Technology for Next Generation Communications, Institute of Microelectronics of Chinese Academy of Sciences, Beijing 100029, China; 2. University of Chinese Academy of Sciences, Beijing 100049, China)
TP311
A
10.19358/j.issn.1674- 7720.2017.18.008
楊瑞東,王云峰,張海英.Spring新特性之Java Config在Web開發(fā)中的應用[J].微型機與應用,2017,36(18):26-29.
2017-03-28)
楊瑞東(1991-),男,碩士,學生,主要研究方向:Java Web開發(fā)、移動醫(yī)療。
王云峰(1981-),男,博士,副研究員,主要研究方向:便攜式醫(yī)療電子設計。
張海英(1964-),女,博士,研究員,主要研究方向:健康電子醫(yī)療、射頻集成電路。