我在項目中經常用到Spring框架,雖然可以應用,可是回顧一下,我竟然都沒有好好的學習過Spring,So,打算學習一下Spring,爲了之後的項目更好的應用。
學習過程:Spring簡單應用 -> Spring 高級篇重點內容重點內容
Spring是什麼?
Spring 是開源的控制反轉和麪向切面的容器框架,它主要目的是簡化企業開發。
控制反轉:應用本身不負責依賴對象的創建及維護,依賴對象的創建及維護是由外部容器負責的,控制權的轉移即所謂的反轉
Spring的優點
1、降低模塊之間的耦合度
2、提供了很多服務,如事務管理服務、消息服務、Spring-core核心服務、持久化服務等
3、容器提供了單例模式
4、容器提供了AOP技術,可以很方便的做權限攔截、運行期監控等
5、容器對主流的應用框架提供了集成支持、
本博客重點:Spring項目搭建+Spring管理bean
Spring框架的所有jar及其作用
spring.jar 是包含有完整發布模塊的單個jar 包。但是不包括mock.jar, aspects.jar, spring-portlet.jar, and spring-hibernate2.jar。
spring-aop-3.2.4.RELEASE
spring的面向切面編程,提供AOP(面向切面編程)實現
spring-aspects-3.2.4.RELEASE Spring獨立的asm程序,Spring2.5.6的時候需要asmJar 包3.2.4開始提供他自己獨立的asmJar
spring-beans-3.2.4.RELEASE
SpringIoC(依賴注入)的基礎實現
spring-context-support-3.2.4.RELEASE
Spring-context的擴展支持,用於MVC方面
spring-context-3.2.4.RELEASE
Spring提供在基礎IoC功能上的擴展服務,此外還提供許多企業級服務的支持,如郵件服務、任務調度、JNDI定位、EJB集成、遠程訪問、緩存以及各種視圖層框架的封裝等
spring-core-3.2.4.RELEASE:
Spring3.2.4的核心工具包
spring-expression-3.2.4.RELEASE:
Spring表達式語言
spring-instrument-tomcat-3.2.4.RELEASE: Spring3.2.4對Tomcat的連接池的集成
spring-instrument-3.2.4.RELEASE :
Spring3.2.4對服務器的代理接口
spring-jdbc-3.2.4.RELEASE:
對JDBC的簡單封裝
spring-jms-3.2.4.RELEASE:
爲簡化JMS API的使用而作的簡單封裝
spring-orm-3.2.4.RELEASE:
整合第三方的ORM框架,如hibernate,ibatis,jdo,以及 spring的JPA實現
spring-oxm-3.2.4.RELEASE :
Spring 對Object/XMl的映射支持,可以讓Java與XML之間來回切換
spring-test-3.2.4.RELEASE:
對Junit等測試框架的簡單封裝
spring-tx-3.2.4.RELEASE :
爲JDBC、Hibernate、JDO、JPA等提供的一致的聲明式和編程式事務管理
spring-webmvc-portlet-3.2.4.RELEASE:
基於protlet的MVC實現
spring-webmvc-3.2.4.RELEASE :
基於servlet的MVC實現
spring-struts-3.2.4.RELEASE:
整合Struts的時候的支持
spring-web-3.2.4.RELEASE :
SpringWeb下的工具包
一、創建簡單的Spring項目
1、創建一個web(Dynamic Web Project)項目
2、引入jar
3、加入配置文件
配置文件可任意命名,如bean.xml
最簡單的bean.xml如下
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">
</beans>
4、使用Junit測試是否創建成功
@Test
public void test() {
ApplicationContext context =
new ClassPathXmlApplicationContext(new String[] {"bean.xml"});
}
Junit測試通過,說明Spring 項目創建成功
二、爲Spring 項目加入bean管理
在bean.xml文件的<beans></beans>
內部添加你要管理的bean
如:
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd">
<bean id="personBeanService" class="com.cn.service.impl.PensonBeanServiceImpl"></bean>
</beans>
<bean>
標籤的屬性id和name在此文件中均要唯一,通常情況下我們會使用id屬性,但是當你起的名稱有特殊字符時,id屬性會報錯,我們要使用name屬性。
Id或name的命名規則,駱駝命名法,我們通常使用類名(首字母小寫)命名
測試:
@Test
public void test() {
ApplicationContext context =
new ClassPathXmlApplicationContext(new String[] {"bean.xml"});
IPersonBeanService personService =
context.getBean("personBeanService", PensonBeanServiceImpl.class);
personService.save();
}
輔助類:
package com.cn.service;
public interface IPersonBeanService {
void save();
}
package com.cn.service.impl;
import com.cn.service.IPersonBeanService;
public class PensonBeanServiceImpl implements IPersonBeanService {
@Override
public void save() {
// TODO Auto-generated method stub
System.out.println("save personBean-------------");
}
}
基於XML的配置元數據的基本結構
<?xml version="1.0" encoding="UTF-8"?><beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd">
<bean id="..." class="...">
<!-- collaborators and configuration for this bean go here -->
</bean>
<bean id="..." class="...">
<!-- collaborators and configuration for this bean go here -->
</bean>
<!-- more bean definitions go here -->
</beans>
實例化spring容器方法:
ApplicationContext context =
new ClassPathXmlApplicationContext(new String[] {"xxx.xml", "yyy.xml"});
實例化spring管理的bean
Object service = context.getBean("id或name");
三、spring實例化bean的三種方法
1、採用默認的構造函數實例化,如上述示例,被9成人使用
2、靜態工廠方式創建bean
我們需要新建一個工廠類
package com.cn.factory;
import com.cn.service.impl.PensonBeanServiceImpl;
public class BeanFactory {
public static PensonBeanServiceImpl creatBean(){
PensonBeanServiceImpl pensonService = new PensonBeanServiceImpl();
return pensonService;
}
}
工廠類中有實例化某類的方法,注意此方法需是靜態方法
配置xml文件
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd">
<bean id="personBeanService" class="com.cn.factory.BeanFactory" factory-method="creatBean"></bean>
</beans>
由factory-method屬性指定創建bean的靜態方法
3、實例工廠方式創建bean
我們也需要新建一個工廠類,此工廠類中亦需一個實例化某類的方法,但是魚靜態工廠方式的區別在於,實例化某類的方法不需要是靜態的。
我們知道調用一個類中的非靜態方法,一定要先實例化該類,這種方式我們怎麼實例化工廠類呢?
答案實在bean.xml文件中實例化,通過代碼:
<bean id="beanFactory" class="com.cn.factory.BeanFactory"></bean>
實例化後我們使用工廠bena,調用實例化某類的方法,如下配置
<bean id="personBeanService" factory-bean="beanFactory" factory-method="creatBean"></bean>
Junit測試通過
Xml配置:
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd">
<bean id="beanFactory" class="com.cn.factory.BeanFactory"></bean>
<bean id="personBeanService" factory-bean="beanFactory" factory-method="creatBean"></bean>
</beans>
四、spring管理實例化的作用域
Attribute : scope
<bean id=”xxx” class=”...” scope=”prototype“>
Scope取值:
Singleton(默認值):每次getBean(“a”) 得到的對象是同一個,指向同一個引用
通常爲“singleton”(一個共享實例,將由所有調用返回getBean與給定的id),或“原型”(獨立實例從每次調用getBean產生)。默認情況下,bean將是單例,除非bean有一個父bean定義,在這種情況下它會繼承父級的作用域。 單例是最常用的,是多線程的理想選擇服務對象。
Prototype:每次getBean(“a”) 得到不同的對象,每次均創建一個新對象
Request:一次請求範圍內bean是同一個
Session:一次會員範圍內bean是同一個
五、Spring管理bean的生命週期
Spring什麼時候創建bean?
當我們使用默認構造函數創建bean的方法時候,可以在構造函數中打印一句話,用於觀察spring何時創建bean
在test類中,我們只初始化spring容器,觀察控制檯打印:
觀察得出,spring容器創建時就實例化了對象,此時我們scope作用域是默認的Singleton
若我們將scope作用域改成prototype又如何呢?
此時運行初始化spring容器並沒有實例化bean,那麼我們getBean調用一下試試
結論:
當scope=”singleton”時,bean在初始化spring容器時被初始化
當scope=”prototype”時,bean在初始化spring容器時沒有被初始化,在getbean時纔可被初始化
如何設置scope=”singleton”時,bean使用時才被初始化,不適用不被初始化。需要設置<bean>
的lazy-init懶加載屬性爲true
lazy-init值說明:
指示這個bean是否要被延遲初始化。 如果“false”,它將在啓動時由bean實例化執行單例的熱切初始化的工廠。 有效默認值爲“false”。 注意:這屬性不會被子bean定義繼承。 因此,需要根據具體情況指定bean定義。 它可以通過’bean’級別的’default-lazy-init’屬性共享
在嵌套的’beans’部分的情況下可能繼承於外部’beans’默認值
六、Spring容器的銷燬
若在<bean>
中配置destroy-method屬性,當spring容器被銷燬是則執行bean中方法
<bean id="personBeanService" class="com.cn.service.impl.PensonBeanServiceImpl"
lazy-init="true" destroy-method="destroy"></bean>
如上配置,當spring容器銷燬時執行PensonBeanServiceImpl類文件中的destroy()方法