一、decorator 模式
从毛胚房的装修说起
每个人拿到属于自己的毛胚房时都兴奋不已,左看看右量量,筹划着装修的桩桩件件,憧憬着未来的幸福家园。每个人都希望装修完全按照自己的设想走,无论风格还是造价预算。可是装修这个活并不好干,同样的毛胚房有很多种装修方案,装修过程中也不可避免发生计划不如变化快的情形,往往最终的效果和最初的设想并不一致,这就是生活的实际。
软件开发的某个阶段和装修房子像极了!系统的基本功能实现后(原型跑起来),相当于毛胚房建造完成,界面不美观,功能也不够完善,毛胚嘛!在接下来的软件“装修”过程中,Decorator 模式将发挥重大的作用。众所周知,我们实施房屋装修工程有两个基本条件和约束:第一,必须有个毛胚房,否则还装修什么啊!第二,不能拆除承重结构。软件的装修也是如此,基本功能和流程框架不会做大的改动,否则还不如推倒重来了。Decorator 设计模式正如房屋的装修,是在毛胚房的基础上层层 wrapper(包装),先刷刷墙面漆,再铺铺木地板,再购置家具布置一下等等。这一道道的装修工序,可以看作是对毛胚房层层包装,最后的装修效果,甚至让你忘记了毛胚房的样子!因此,Decorator 设计模式也被称为 Wrapper 设计模式。
Decorator 设计模式的特点
Decorator 设计模式正如毛胚房的装修,不会改变原毛胚房的基本框架,只是增加新的外观、功能等,且随着时间的推移,可以不断的实施装修工程:增加新的家具、根据心情换换新鲜的墙纸等等。在面向对象的程序设计中,扩展系统的原有功能也可以采用继承、组合的方式。继承也不会改变毛胚房(父类),但是由于装修工程的复杂和很多不可预测的改变,比如不同墙纸和地板样式的组合数量简直无法想想,难道我们要为每一种组合都定义一个子类吗?显然这是不现实的,即通过继承的方式来应对未来的功能和外观改变通常是吃力不讨好的事情。组合的方式也不可取,因为这要求不断的修改父类的结构,相当于对毛胚房大动干戈,房屋的可维护性和可靠性就大大降低了。
让我们回顾一下设计模式的重要原则:Classes should be open for extenstion, but closed for modification。Decorator 设计模式很好的诠释了这个原则。
Decorator 设计模式的 Java 实例
以房屋装修为例,依据 Decorator 设计模式的原则设计类图如下:
图 1.Decorator 模式类图
二、intercepter拦截器
1.拦截器综述
拦截器的功能是定义在Java拦截器规范。
拦截器规范定义了三种拦截点:
- 业务方法拦截,
- 生命周期回调侦听,
- 超时拦截(EJB)方法。
在容器的生命周期中进行拦截
-
public class DependencyInjectionInterceptor {
-
@PostConstruct
-
public void injectDependencies(InvocationContext ctx) { ... }
-
}
EJB超时时使用的拦截器
-
public class TimeoutInterceptor {
-
@AroundTimeout
-
public Object manageTransaction(InvocationContext ctx) throws Exception { ... }
-
}
在业务上,对某一个Bean的方法进行拦截
-
public class TransactionInterceptor {
-
@AroundInvoke
-
public Object manageTransaction(InvocationContext ctx) throws Exception { ... }
-
}
-
@AroundInvoke注释指定了要用作拦截器的方法,拦截器方法与被拦截的业务方法执行同一个java调用堆栈、同一个事务和安全上下文中。用@AroundInvoke注释指定的方法必须遵守以下格式:public Object XXX(javax.interceptor.InvocationContext ctx) throws Exception