区别与spring框架中的aop实现,jhello框架使用了类似jFinal框架的aop实现。
众所周知,spring中的aop使用的是代理模式实现,而且大家一说到aop的实现都是使用代理模式,jhello不使用代理模式的原因是我写不出来cglib这样的实现,而只使用java中的动态代理又不太过瘾,在写jhello框架初衷就是重复造轮子,学习怎么造轮子,所以能少依赖其他jar包就少依赖。偶然的机会下看到jFinal中的aop实现,感觉其实现方式很有意思,就学习了这样的方式。
aop有前置增强,后置增强,环绕增强,异常增强,引介增强,在jhello框架中只实现了前三种,而且只针对action类实现aop效果。
在jhello中要实现aop的效果,需要在配置文件中(config.properties)或配置类中添加切面类的扫描路径,在这里我就配置成:com.demo.messagebook.aspect。
首先我们实现一个记录action执行时间,其用到的是环绕增强。
编写一个切面,继承com.jhello.core.aspect.AbstractAdvice类
public class MsgAspect extends AbstractAdvice {
@Overridepublic void before(Pointcut pointcut, HttpServletRequest req,
HttpServletResponse resp) throws Exception {
}
@Overridepublic void after(Pointcut pointcut, HttpServletRequest req,
HttpServletResponse resp) throws Exception {
}
}
可以看到需要的实现方法就两个,before方法是实现前置增强,after实现后置增强,组合一起就是实现环绕增强。
光这样框架是不会扫描这个类的,我们在类上加个注解,标明这是一个切面。
@Aspect(joincutExpression = "com.demo.messagebook.controller..*#.*")
解释一下其中的joincutExpression,这就是个正则表达式,在框架内记录action的格式为“完整类名#方法命”,上面表达式的意思是匹配controller包下所有类,所有方法。如果只想要匹配save开头的方法写成
.*#save.*
就可以了
接下来我们记录一下action前的时间,记录一下执行后的时间,相减就得出执行时间了,下面是完整的实现
@Aspect(joincutExpression = "com.demo.messagebook.controller..*#.*")
public class MsgAspect extends AbstractAdvice {
private long start = 0l;
@Overridepublic void before(Pointcut pointcut, HttpServletRequest req,
HttpServletResponse resp) throws Exception {
start = System.currentTimeMillis();
}
@Overridepublic void after(Pointcut pointcut, HttpServletRequest req,
HttpServletResponse resp) throws Exception {
System.out.println("执行时间:"+(System.currentTimeMillis() - start));
}
}
实现效果:
本篇所讲到的代码会上传到oschina的git上,有兴趣的童鞋可以去拉下来运行一下
http://git.oschina.net/bigmouth/MessageBook.git