简述:
了解Spring AOP的使用方式
@AspectJ支持
参考:http://ntzrj513.blog.163.com/blog/static/27945612201362232315/
需要的依赖库aspectj
pom.xml中添加
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.anialy</groupId>
<artifactId>TestProject</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>测试包</name>
<description>测试包</description>
<properties>
<!-- build -->
<project.jdk.version>1.6</project.jdk.version>
<project.source.encoding>UTF-8</project.source.encoding>
<!-- logger -->
<slf4j.version>1.7.5</slf4j.version>
<logback.version>1.0.13</logback.version>
<!-- unit test -->
<junit.version>4.11</junit.version>
<!-- common utils -->
<commons.lang3.version>3.2.1</commons.lang3.version>
<commons.beanutils.version>1.8.3</commons.beanutils.version>
<commons.io.version>2.4</commons.io.version>
<commons.collections.version>3.2.1</commons.collections.version>
<google.guava.version>15.0</google.guava.version>
<!-- http client -->
<httpcomponents.version>4.3.1</httpcomponents.version>
<!-- json -->
<jackson.version>1.9.13</jackson.version>
<!-- spring -->
<aspectj.version>1.7.4</aspectj.version>
<cglib-nodep.version>2.2.2</cglib-nodep.version>
<spring.version>4.0.0.RELEASE</spring.version>
<!-- web server -->
<jetty.version>9.1.2.v20140210</jetty.version>
<!-- templete engine -->
<freemarker.version>2.3.16</freemarker.version>
<!-- cache -->
<ehcache.version>2.6.8</ehcache.version>
<xmemcached.version>1.3.8</xmemcached.version>
<jedis.version>2.2.1</jedis.version>
<!-- mongodb -->
<mongodb.driver.version>2.11.3</mongodb.driver.version>
</properties>
<dependencies>
<!-- aspectj -->
<dependency>
<groupId>org.aspectj</groupId>
<artifactId>aspectjrt</artifactId>
<version>${aspectj.version}</version>
</dependency>
<dependency>
<groupId>org.aspectj</groupId>
<artifactId>aspectjweaver</artifactId>
<version>${aspectj.version}</version>
</dependency>
<dependency>
<groupId>org.aspectj</groupId>
<artifactId>aspectjtools</artifactId>
<version>${aspectj.version}</version>
</dependency>
<!-- spring -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-core</artifactId>
<version>${spring.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-beans</artifactId>
<version>${spring.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context</artifactId>
<version>${spring.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-aop</artifactId>
<version>${spring.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>${spring.version}</version>
</dependency>
<!-- reflect -->
<dependency>
<groupId>cglib</groupId>
<artifactId>cglib-nodep</artifactId>
<version>${cglib-nodep.version}</version>
</dependency>
<!-- j2ee -->
<dependency>
<groupId>javax.mail</groupId>
<artifactId>mail</artifactId>
<version>1.5.0-b01</version>
</dependency>
<dependency>
<groupId>org.freemarker</groupId>
<artifactId>freemarker</artifactId>
<version>${freemarker.version}</version>
</dependency>
<!-- logback -->
<dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-classic</artifactId>
<version>${logback.version}</version>
</dependency>
<!-- test -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-test</artifactId>
<version>${spring.version}</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>org.eclipse.jetty</groupId>
<artifactId>example-jetty-embedded</artifactId>
<version>${jetty.version}</version>
<scope>test</scope>
<exclusions>
<exclusion>
<groupId>org.eclipse.jetty.tests</groupId>
<artifactId>test-mock-resources</artifactId>
</exclusion>
</exclusions>
</dependency>
</dependencies>
</project>
项目结构,
applicationContext.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" xmlns:p="http://www.springframework.org/schema/p"
xmlns:c="http://www.springframework.org/schema/c" xmlns:context="http://www.springframework.org/schema/context"
xmlns:aop="http://www.springframework.org/schema/aop" xmlns:util="http://www.springframework.org/schema/util"
xsi:schemaLocation="
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.2.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.2.xsd
http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-3.2.xsd
http://www.springframework.org/schema/util http://www.springframework.org/schema/util/spring-util-3.2.xsd"
default-autowire="no" default-lazy-init="false">
<!-- 激活组件扫包功能 -->
<context:component-scan base-package="com.anialy.test.aop"/>
<!-- 激活自动代理功能 -->
<aop:aspectj-autoproxy proxy-target-class="true"/>
</beans>
1. 整个ProcessImpl类中配置切入点
ProcessImpl.java
package com.anialy.test.aop.impl;
import org.springframework.stereotype.Component;
/**
* Package: com.anialy.test.aop
*
* File: SecurityHandler.java
*
* Author: anialy Date: 2014-8-19
*
*/
@Component("processOp")
public class ProcessImpl {
public void process() throws Exception {
System.out.println("Processing !!");
throw new Exception("扔一个异常");
}
}
ProcessAspect.java
package com.anialy.test.aop.aspect;
import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.After;
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;
/**
* Package: com.anialy.test.aop.aspect
*
* File: ProcessAspect.java
*
* Author: anialy Date: 2014-8-20
*
*/
@Component("test.processAspect")
@Aspect
public class ProcessAspect {
//配置切入点,即切入的函数
@Pointcut("execution(* com.anialy.test.aop..*(..))")
public void aspect(){ }
// 配置前置通知
@Before("aspect()")
public void before(JoinPoint joinPoint){
System.out.println("before process !");
}
//配置后置通知
@After("aspect()")
public void after(JoinPoint joinPoint){
System.out.println("after process !!!");
}
@Around("aspect()")
public void around(JoinPoint joinPoint) throws Throwable {
long start = System.currentTimeMillis();
((ProceedingJoinPoint) joinPoint).proceed();
long end = System.currentTimeMillis();
System.out.println("around " + joinPoint + "\tUse time : " + (end - start) + " ms!");
}
//配置后置返回通知
@AfterReturning("aspect()")
public void afterReturn(JoinPoint joinPoint){
System.out.println("afterReturn " + joinPoint);
}
//配置抛出异常后通知
@AfterThrowing(pointcut="aspect()", throwing="ex")
public void afterThrow(JoinPoint joinPoint, Exception ex){
System.out.println("afterThrow " + joinPoint + "\t" + ex.getMessage());
}
}
Main.java spring加载
package com.anialy.test.aop;
import com.anialy.test.aop.impl.ProcessImpl;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
/**
* Package: com.anialy.test.aop
*
* File: Main.java
*
* Author: anialy Date: 2014-8-19
*
*/
public class Main {
public static void main(String[] args) throws Exception{
ApplicationContext appCtx =
new ClassPathXmlApplicationContext("classpath:applicationContext.xml");
ProcessImpl processOp = (ProcessImpl)appCtx.getBean("processOp");
processOp.process();
}
}
这是一个有异常的情况
输出:
发现afterThrow 发生, 而around没有调用
于是把在around中把异常捕获
@Around("aspect()")
public void around(JoinPoint joinPoint){
long start = System.currentTimeMillis();
try {
((ProceedingJoinPoint) joinPoint).proceed();
long end = System.currentTimeMillis();
System.out.println("around " + joinPoint + "\tUse time : " + (end - start) + " ms!");
} catch (Throwable e) {
long end = System.currentTimeMillis();
System.out.println("around " + joinPoint + "\tUse time : " + (end - start) + " ms with exception : " + e.getMessage());
}
}
2. 现在需要指定到某个类中的某个方法进行切片
就需要修改execution的正则表达式配置
在ProcessImpl中新增方法process2();
public void process2(){
System.out.println("Processing 2 !!");
}
只在process2前插入前置方法
// 配置前置通知
@Before("execution(* com.anialy.test.aop..process2(..))")
public void before(JoinPoint joinPoint){
System.out.println("before process 2 !");
}