2018年7月23日09:50:01
【1、背景】
1)aop切面编程,spring框架提供的招牌菜之一(另一个是ioc,依赖注入),用于提供对模块化程序的切面处理;
2)需求:一个是使用dataTable的服务器模式,通过物理分页,获取数据;二是对于某些数据,我们想让最新的Mysql数据显示在dataTable的最前面,(可以理解为id最大的数据排序最前面)
【2、构思】
1)使用aop:导入jar包和使用可参考《开发日常小结(19):Spring AOP 最佳入门试验 + 游戏禁言的应用实例小结》,或《PageHelper分页插件源码及原理剖析》
2) PageHelper 物理分页的机制:执行sql查询之前,对sql语句进行拦截,然后对SQL补充多个字段;
如上:可以加多个参数;
【3、实现】
下面是功能代码,对某些Dao层的方法进行增强,进而修改sql,实现了物理分页和排序,jar包环境的搭建不作赘述;
PageHelperAop.java:
package ***.***.aop;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.AfterReturning;
import org.aspectj.lang.annotation.AfterThrowing;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Before;
import org.aspectj.lang.annotation.Pointcut;
import org.springframework.stereotype.Component;
import com.github.pagehelper.PageHelper;
/**
* 对现有的一些查询做pageHelper分页的织入()
* @author mym
*
*/
@Aspect
@Component
public class PageHelperAop {
private int pageNo; //页号
private int pageSize; //每页大小
private String orderBy; //排序字段
//声明切点:getPageMethod只是一个引用名称
@Pointcut("execution (* com.xs.fun.admin.sql.service.*.getPage*(..))")
private void getPageMethod() {}
//声明切点:getSortPageMethod 引用方法名称
@Pointcut("execution (* com.xs.fun.admin.sql.service.*.getSortPage*(..))")
private void getSortPageMethod(){}
//======================通知方法=======================//
//前置通知
// @Before("getPageMethod()")
// public void before() {
// System.out.println("查询前。。。");
// }
//后置通知:方法返回后
// @AfterReturning("getPageMethod()")
// public void afterReturning() {
// System.out.println("方法返回后。。。");
// }
//后置通知:方法抛出异常后
// @AfterThrowing("getPageMethod()")
// public void afterThrow() {
// System.out.println("方法抛出异常后。。。");
// }
/*环绕通知说明:
* (1)环绕通知是所有通知类型中功能最为强大的, 能够全面地控制连接点. 甚至可以控制是否执行连接点.
(2)对于环绕通知来说, 连接点的参数类型必须是 ProceedingJoinPoint . 它是 JoinPoint 的
子接口, 允许控制何时执行, 是否执行连接点.
(3)在环绕通知中需要明确调用 ProceedingJoinPoint 的 proceed() 方法来执行被代理的方法.
如果忘记这样做就会导致通知被执行了, 但目标方法没有被执行.
(4)环绕通知的方法需要返回目标方法执行之后的结果, 即调用 joinPoint.proceed(); 的返回值, 否则会出现空指针异常
* */
/**
* @function 只做物理分页,不做逆序处理,table主键不为id
* */
@Around("getPageMethod()")
public Object around(ProceedingJoinPoint joinpoint) {
Object proceed = null;
try {
PageHelper.startPage(pageNo, pageSize);
proceed = joinpoint.proceed();//执行目标方法
} catch (Throwable e) {
e.printStackTrace();
} finally {}
return proceed;
}
/**
* @function 物理分页+逆序处理,table主键为id(
* */
@Around("getSortPageMethod()")
public Object around2(ProceedingJoinPoint joinpoint) {
Object proceed = null;
try {
// String orderBy = 排序字段+" desc";
String orderBy="id desc";
PageHelper.startPage(pageNo, pageSize,orderBy);
proceed = joinpoint.proceed();//执行目标方法
} catch (Throwable e) {
e.printStackTrace();
} finally {}
return proceed;
}
public int getPageNo() {
return pageNo;
}
public void setPageNo(int pageNo) {
this.pageNo = pageNo;
}
public int getPageSize() {
return pageSize;
}
public void setPageSize(int pageSize) {
this.pageSize = pageSize;
}
public String getOrderBy() {
return orderBy;
}
public void setOrderBy(String orderBy) {
this.orderBy = orderBy;
}
}
------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
画外音:
2004年欧洲杯,初进大赛的C罗惊艳四方,花哨的过人,凌厉的脚法,惊人的速度无不昭示着他今后的成功。决赛输给希腊后,C罗流泪的样子让人心碎。那一年C罗19岁,葡萄牙黄金一代就此谢幕。如今,33岁的C罗离开了皇家马德里,开始了意甲征途;谁又知道这个决定昭示着今后的哪些结果呢?岁月如歌,精神永存。