Author:LuJianyu 2007-6-28
一、基本概念
Spring的核心是轻量级(Lightweight)的容器(Container),它实现了IoC容器、非侵入性(No intrusive)的框架,并提供AOP概念的实现方式,提供对持久层(Persistence)、事务(Transaction)的支持,提供MVC Web框架的实现,并对一些常用的企业服务API(Application Interface)提供一致的模型封装,是一个全方位的应用程序框架(Application framework),另外,Spring也提供了对现有框架(Struts、JSF、Hibernate等)的整合方案。
Spring旨在分离体系结构的层次,因此每一层都可以修改而不会影响到其它层。每一层都不知道其上层的关注点;就其可能而言,只对所紧挨的下一层有依赖。层与层之间的依赖通常是以接口的形式表现,以确保其耦合尽可能松散。
容器管理事务,容器,贯穿始终:1、对象生命周期的管理。 2、容器本身具备功能,加在自己的类中。需要自己调用则为显示调用。 而尽量用容器隐式调用,Spring即为隐式调用、声明式编程。
Spring轻量级容器体现在:只需设置一个Jar文件到CLASSPATH,不用去调用它,但又可以拥有其强大的功能。组件的极大程度的复用。
让层与层中耦合度低——Loosely-Coupled 工厂类创建DAO对象。
声明式编程。在xml文件中声明。 基于POJO类,支持事务,事务是根本;而EJB事务由Container管理。
Spring将 View层与持久层,比如与Hibernate 联系起来。Spring简化Hibernate 的使用,还可以帮助管理Hibernate。Spring本身没有O-R_mapping,因为有Hibernate,她已经做得很好了。
Spring将编译时异常(checked)转化为运行时异常(runtime)。比如,JDBC 则为编译时异常,即必须写try…catch;而Hibernate程序为运行时异常。
在spring-framework-2.0.5dist 目录下 有jar文件、 dtd文件、 tld文件。
总之,Spring是一个轻型容器(light-weight container),其核心是Bean工厂(Bean Factory),用以构造我们所需要的M(Model)。在此基础之上,Spring提供了AOP(Aspect-Oriented Programming, 面向层面的编程)的实现,用它来提供非管理环境下申明方式的事务、安全等服务;对Bean工厂的扩展ApplicationContext更加方便我们实现Java EE的应用;DAO/ORM的实现方便我们进行数据库的开发;Web MVC和Spring Web提供了Java Web应用的框架或与其它流行的Web框架进行集成。
二、IoC(Inversion of Control)
1
控制权由对象本身转向容器;由容器根据配置文件去创建实例并创建各个实例之间的依赖关系。
、定义:组件之间的依赖关系由容器在运行时决定。
例如:B对象所依赖的A对象是由 Spring创建好并且通过Set方法传递注入过来的。
最基本的优点体现在:若A为接口,让B依赖于接口。只看接口不管实现类。 可把工厂类全部替换掉。对象均为容器创建。到时还能把容器的功能融入到其中。
●IoC要求:容器尽量不要侵入到应用程序中去,应用程序本身可以依赖于抽象的接口,容器根据这些接口所需要的资源注入到应用程序中,也就是说应用程序不会主动向容器请求资源;容器会自动把这些对象给应用程序。
●IoC有基于Set方式的注入(property)、 基于构造方法的注入。
●IoC核心:bean工厂。在Spring中,bean工厂创建的各个实例称作bean。业务组件间的依赖是容器(Bean工厂)解决的。BeanFactory负责读取Bean定义文件,管理对象的加载、生成,维护Bean对象与Bean对象的依赖关系,负责Bean的生命周期,对于简单的应用程序来说,使用BeanFactory就已经足够来管理Bean,在对象的管理上就可以获得许多的便利性。
●Spring中有两个包里的类都可以做IoC:
beans包:org.springframework.beans包;
context包:org.springframework.context包 其类功能更加强大。
2、bean工厂创建bean的三种方式:
●通过构造方法直接创建:
<bean id=” ” class=”bean class name”>
●通过静态工厂方法创建:
<bean id=” ” class=”factory class name” factory-method=””>
●通过非静态工厂方法创建:
<bean id=”factory” class=”factory class name”>
<bean id=”” factory-bean=” factory” factory-method=””>
3、Spring中实现IoC的方式:依赖注入(Dependency Injection)
Spring中依赖注入的两种方式:
●通过setter方法注入:
<property name=” ”> </property>
其中,name属性的取值依setter方法名而定。Spring推荐使用setter方法注入
●通过构造方法注入:
<constructor-arg index=”0”></ constructor-arg>
<constructor-arg type=”int”></ constructor-arg>
其中,index表示构造方法中的参数索引(第一个参数索引为0),type表示构造方法中参数的类型。
●两种注入方式的区别:
●Constructor: 可以在构建对象的同时,把依赖关系也构建好。对象创建后好就已经准备好了所有的资源,安全性高。
●Setter: 创建完对象之后再通过set()方法进行属性的设定。
4、设置属性时可选的标签:
value:基本类型(包装类型)或String类型
ref:引用工厂中其它的bean
list:List或数组类型
set:Set类型。用法与list类似。
map:Map类型
props:Properties类型,键值为String类型的,所以直接写值。
举例:
List Set
Map Properties
如果key依赖其它对象 用key-ref, 如果还是一个Map,可再嵌套。
●abstract 属性
如果在配置文件中把某个方法设置成为abstract=“true”的(缺省false ),那么不能通过beanFactory 获得bean 的实例。
●lazy-init属性
如果使用的是XmlBeanFactory来获得beanFactory : 缺省的是延迟加载,如果不想延迟加载,则需要把工厂bean实例的lazy-init设置为false,例如:
<bean id=“carFactory" lazy-init="false" class="spring. ioc.CarFactory">
</bean>
5、自动装配:自动将某个bean 注入到另一个bean的属性当中。
(bean标签的autowire属性)其分类如下表: (大型应用不推荐使用,因为可读性太差)
模式 | 说明 |
---|---|
no | 不使用自动装配。必须通过ref元素指定依赖,这是默认设置。由于显式指定协作者可以使配置更灵活、更清晰,因此对于较大的部署配置,推荐采用该设置。而且在某种程度上,它也是系统架构的一种文档形式。 |
byName | 根据属性名自动装配。此选项将检查容器并根据名字查找与属性完全一致的bean,并将其与属性自动装配。例如,在bean定义中将autowire设置为by name,而该bean包含master属性(同时提供setMaster(..)方法),Spring就会查找名为master的bean定义,并用它来装配给master属性。 |
byType | 如果容器中存在一个与指定属性类型相同的bean,那么将与该属性自动装配。如果存在多个该类型的bean,那么将会抛出异常,并指出不能使用byType方式进行自动装配。若没有找到相匹配的bean,则什么事都不发生,属性也不会被设置。如果你不希望这样,那么可以通过设置dependency-check="objects"让Spring抛出异常。 |
constructor | 与byType的方式类似,不同之处在于它应用于构造器参数。如果在容器中没有找到与构造器参数类型一致的bean,那么将会抛出异常。 |
autodetect | 通过bean类的自省机制(introspection)来决定是使用constructor还是byType方式进行自动装配。如果发现默认的构造器,那么将使用byType方式。 |
6、依赖检查:检查bean的属性是否完成依赖关系的注入
(bean标签的dependency-check属性)
●作用:检查bean的属性是否完成依赖关系的注入
●分类:
.simple : 只查看简单的类型是否完成依赖注入(基本类型和字符串)
.objects: 检查对象类型是否完成依赖注入
.all: 检查全部的类型是否完成依赖注入。
.none: 默认的设置,表示不检查依赖性。
7、生命周期方法:
init-method(也可实现接口org.springframework.beans.factory.InitializingBean)
destroy-method(也可实现接口DisposableBean)
<
bean name="view" class="ioc.beanfactory.CommanLineView" autowire="byType" init-method="init" scope="prototype">
8、单例bean:默认情况下,从bean工厂所取得的实例为Singleton(bean的singleton属性)
<bean id="dateFactory" class="ioc.beanfactory.DateFactory" singleton="false"/>
9、Aware相关接口:可以通过实现Aware接口来获得Spring所提供的资源或使用某些功能。
●org.springframework.beans.factory.BeanNameAware 此接口用得不多
实
现BeanNameAware接口的Bean类,在依赖关系设定完成后、初始化方法之前,会将Bean在定义文件中的名称通过setBeanFactory()方法设定给Bean。
●org.springframework.beans.factory.BeanFactoryAware 要重视
实现BeanFactoryAware接口的类,在依赖关系设定完成后、初始化方法之前,Spring容器将会注入BeanFactory的实例。
放弃一些反向控制,在需要B对象时再根据需要
●org.springframework.context.ApplicationContextAware
10、ApplicationContext的功能扩展:
org.springframework.context.ApplicationContext,其基本功能与BeanFactory很相似,还提供一个应用程序所需的更完整的框架功能。例如:提供取得资源文件更方便的方法、提高文字消息解析方法、支持国际化消息等。
.BeanPostProcessor:若想在Spring对bean完成依赖注入之后,再补充一些后续操作,则可以定义一个bean类来实现接口:org.springframework.beans.factory.config.BeanPostProcessor,然后在配置文件中定义该bean类;从而Spring容器会在每一个bean被初始化之前、之后分别执行实现了该接口的bean类的postProcessBeforeInitialization()方法和postProcessAfterInitialization()方法;
.BeanFactoryPostProcessor:对Bean工厂修改其它支持。
●CustomEditorConfigurer:可借助实现了接口java.beans.PropertyEditor的类,并依据当中的实现,将字符串类型转换为指定类型的对象;
●PropertyPlaceholderConfigurer:可将配置文件中属性值用“${key}”形式表示,则会将其值替换成指定的属性文件中key所对应的value;
●PropertyOverrideConfigurer:可借助该类在指定的属性文件中设定一些优先的属性(将忽略配置文件中对应属性的设定值);
(注意:属性文件中设定属性值的格式为:beanName.propertyName=value)
.
国际化消息的支持:可通过ApplicationContext(继承于MessageSource)的getMessage()方法获得指定资源文件中的消息;配置如下:
.事件的支持:
可发布的事件:ApplicationEvent
发布事件的方法:publishEvent(ApplicationEvent)
事件监听接口:ApplicationListener
11、ApplicationContext管理bean的执行阶段:(他回预先实例化所有的singleton bean)
●创建bean;
●属性注入(依赖关系的注入);
●BeanNameAware接口实现类的setBeanName()方法;
●BeanFactoryAware接口实现类的setBeanFactory()方法;
●ApplicationContextAware接口实现类的setApplicationContext()方法;
●BeanPostProcessor接口实现类中的postProcessBeforeInitialization()方法; (init方法调用前要做的后续操作)
●InitializingBean接口实现类的afterPropertiesSet()方法;
●Bean定义文件中init-method属性所指定的方法;
●BeanPostProcessor接口实现类中的postProcessAfterInitialization()方法;
12、FactoryBean:用来创建bean
(注意:通过bean工厂的getBean(“myObject”)得到的是FactoryBean所生产的产品;getBean(“&myObject”)得到的是FactoryBean实例本身)
三、AOP(Aspect-orented programming)面向层面编程 重点、难点
1、AOP学习目标:
使所需要的功能能够加在任何类中,而不需要调用。
借助于Spring编写一个自己的切面,加到任何一个Java中;
Spring本身也提供了编写好的切面功能。
切面有最大程度的复用性,耦合度趋于零。在事务方面,AOP用得较成功。
2、代理的两种方式:
●静态代理:
○针对每个具体类分别编写代理类;
○针对一个接口编写一个代理类;
●动态代理:
○针对一个方面编写一个InvocationHandler,然后借用JDK反射包中的Proxy类为各种接口动态生成相应的代理类
AOP的主要原理:动态代理 研究一下动态代理的写法。
3、AOP中思想和名词术语:
LogHandler
根据
SecurityHandler
具体设计为Advices
Weave
Logging
Jointpoint
Jointpoint
Jointpoint
Aspects
被辨认为
Cross-cuting concerns
业务流程1
业务流程2
业务流程3
●Aspect:方面,层面
●Joinpoint:结合点、联结点;加入业务流程的点或时机
●Pointcut:切入点、作用点;指定某个方面在哪些联结点织入到应用程序中
●Advice:通知、行为;某个方面的具体实现,代表了一个动作.
●Advisor:由Pointcut和Advice共同构成
●Pointcut:Spring根据类名称及方法名称定义Pointcut,表示Advice织入至应用程序的时机;org.springframework.aop.Pointcut
●P
roxyFactoryBean:用来创建代理对象
<list>
<value>Advice/Advisor bean</value>
</list>
</property>
</bean>
创建代理对象需指定的三要素:
target:设定目标对象(只能是一个);
proxyInterfaces:设定代理接口(目标对象所实现的接口);
interceptorNames:设定拦截器的名字(各个advice或advisor bean的列表)
Advice:五种(根据织入的时机不同而划分)
●Before Advice:在目标对象的方法执行之前加入行为;
要实现的接口:org.springframework.aop.MethodBeforeAdvice
●After Advice:在目标对象的方法执行之后加入行为;
要实现的接口:org.springframework.aop.AfterReturningAdvice
●Throw Advice:在目标对象的方法发生异常时加入行为;
要实现的接口:org.springframework.aop.ThrowsAdvice
●Around Advice:在目标对象的方法执行前后加入行为;
要实现的接口:org.aopalliance.intercept.MethodInterceptor
●Introduction Advice:引入的行为(增加了可操作的方法)。
■声明要添加的功能接口;
■创建引入Advice;
(继承org.springframework.aop.support.DelegatingIntroductionInterceptor,并实现添加的功能接口)
■在配置文件中定义一个DefaultIntroductionAdvisor的bean。
(需要两个构造方法的参数:Advice和添加的功能接口)
●PointcutAdvisor:Pointcut定义了Advice的应用时机;在Spring中,使用PointcutAdvisor将Pointcut和Advice结合为一个对象。
●NameMatchMethodPointcutAdvisor:可用来指定Advice所要应用的目标对象上的方法名称
●RegexpMethodPointcutAdvisor:可使用Regular expression定义Pointcut,在符合Regular expression的情况下应用Advice,其pattern属性用来指定所要符合的完整类名(包括 package名称)及方法名;定义该属性时可使用的符号包括:
符号 | 描述 |
---|---|
. | 符合任意一个字符 |
| 符合前一个字符一次或多次 |
* | 符合前一个字符零次或多次 |
转义字符,用来转义正则表达式中使用到的字符 |
●
●AutoProxy:自动代理
○B
eanNameAutoProxyCreator:根据bean的名字为其自动创建代理对象,bean工厂自动返回其代理对象:
○D
efaultAdvisorAutoProxyCreator:自动将Advisor应用到符合Pointcut的目标对象上
四、Spring的Web MVC:
1、DispatcherServlet:作为前端控制器,负责分发客户的请求到Controller;
在web.xml中的配置如下:
2、Controller:负责处理客户请求,并返回ModelAndView实例;
Controller必须实现接口org.springframework.web.servlet.mvc.Controller,实现该接口中的方法handleRequest(),在该方法中处理请求,并返回ModelAndView实例
3、HandlerMapping:DispatcherServlet根据它来决定请求由哪一个Controller处理;
○默认情况下,DispatcherServlet将使用org.springframework.web.servlet.handler. BeanNameUrlHandlerMapping,即使用和客户请求的URL名称一致的Controller的bean实例来处理请求;
○另外一种常用的HandlerMapping为org.springframework.web.servlet.handler. SimpleUrlHandlerMapping,配置如下:
在以上“mappings”属性设置中,“key”为请求的URL,而“value”为处理请求的Controller的bean名称
4、ModelAndView:用来封装View与呈现在View中的Model对象;
DispatcherServlet根据它来解析View名称,并处理呈现在View中的Model对象
5、ViewResolver:DispatcherServlet委托ViewResolver来解析View名称;
常用的ViewResolver实例配置如下:
Cglig库作用1、Spring通过调用cglib在客户端的类之上修改二进制码。
2、能够给某一个类生成子类(Hibernate中也要用到,用来生成子类)。
CGLIB用来生成动态代理类(dynamic proxy classes),供核心DI和AOP实现之用,所以大量Spring功能都要用到CGLIB。
五、Spring Data Access
1、Template
2、Dao Support
3、Transaction Manager
4、Transaction Proxy
Spring对Hibernate的集成:
Spring与Struts的集成
如下3种方式:
、使用Spring的ActionSupport类整合Struts。
、使用Spring的DelegatingRequestProcessor覆盖Struts的RequestProcessor。
、将Struts Action管理委托给Spring框架。
SSH编程示例图:
附,行业的一些名词术语:
CRM ERP OSS BSS BOSS OA Pre-Sale
CRM 客户关系管理 Customer Relationship Management
ERP 企业资源规划 Enterprise Resource Planning
OSS 运营支撑系统 Operation Support System
BSS 业务支撑系统 Business Support System
BOSS 业务运营支撑系统 Business Operation Support System
OA 办公自动化 Office Automatization
Pre-Sale 售前(基本上什么都要会)
1