Spring AOP 在项目中的使用示例
网站首页 文章专栏 Spring AOP 在项目中的使用示例
Spring AOP 在项目中的使用示例
编辑时间:2019-05-06 18:03 作者:毛毛小妖 浏览量:70 评论数:0

一、AOP概念 

AOP(Aspect Oriented Programming),即面向切面编程。其主要作用是,在不修改源代码的情况下给某个或者一组操作添加额外的功能。像日志记录,事务处理,权限控制等功能,都可以用AOP来“优雅”地实现,使这些额外功能和真正的业务逻辑分离开来,软件的结构将会更加清晰。AOP是OOP的一个强有力的补充。Spring AOP是基于代理机制的,通过JDK Proxy和CGLIB Proxy两种方法实现代理。

二、AOP使用

1、新建maven项目,并修改pom.xml文件,主要是引入spring AOP的相关依赖

<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>cn.outofmemory</groupId>
	<artifactId>spring-aop-aspect</artifactId>
	<version>0.0.1-SNAPSHOT</version>
	<packaging>jar</packaging>

	<name>spring-aop-aspect</name>
	<url>http://maven.apache.org</url>
	<properties>
		<spring.version>3.1.1.RELEASE</spring.version>
	</properties>
	<dependencies>
		<dependency>
			<groupId>org.springframework</groupId>
			<artifactId>spring-core</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.aspectj</groupId>
			<artifactId>aspectjrt</artifactId>
			<version>1.6.12</version>
		</dependency>
		<dependency>
			<groupId>org.aspectj</groupId>
			<artifactId>aspectjweaver</artifactId>
			<version>1.6.12</version>
		</dependency>
		<dependency>
			<groupId>cglib</groupId>
			<artifactId>cglib</artifactId>
			<version>2.2</version>
		</dependency>
	</dependencies>
</project>

2、新建service类,它是业务代码,是我们AOP注入的目标类

PersonService类中定义了三个方法,addPerson方法无返回值,而deletePerson方法有返回值,而editPerson方法抛出运行时的异常。

package com.aspectJ.SpringAop;

import org.springframework.stereotype.Service;

@Service
public class PersonService {

	public void addPerson(String personName) {
		System.out.println("add person " + personName);
	}
	
	public boolean deletePerson(String personName) {
		System.out.println("delete person " + personName) ;
		return true;
	}
	
	public void editPerson(String personName) {
		System.out.println("edit person " + personName);
		throw new RuntimeException("edit person throw exception");
	}
}

3、定义Aspect类

SimpleAspect类中的第一个方法是pointCut()方法,此方法无任何执行内容,只有一个@Pointcut的注解,其他方法都会引用这个注解中指定的pointcut表达式。其他几个方法是各种Advice类型的方法实现,在这些方法中都可以通过JoinPoint实例来获得方法执行的上下文信息,参数信息。

package com.aspectJ.SpringAop;

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;

@Component
@Aspect
public class SampleAspect {
	@Pointcut("execution(* com.aspectJ.SpringAop.*Service*.add*(..))")
	public void pointCut() {
	}

	@After("pointCut()")
	public void after(JoinPoint joinPoint) {
		System.out.println("after aspect executed");
	}

	@Before("pointCut()")
	public void before(JoinPoint joinPoint) {
		System.out.println("before aspect executing");
	}

	@AfterReturning(pointcut = "pointCut()", returning = "returnVal")
	public void afterReturning(JoinPoint joinPoint, Object returnVal) {
		System.out.println("afterReturning executed, return result is " + returnVal);
	}

	@Around("pointCut()")
	public void around(ProceedingJoinPoint pjp) throws Throwable {
		System.out.println("around start..");
		try {
			pjp.proceed();
		} catch (Throwable ex) {
			System.out.println("error in around");
			throw ex;
		}
		System.out.println("around end");
	}

	@AfterThrowing(pointcut = "pointCut()", throwing = "error")
	public void afterThrowing(JoinPoint jp, Throwable error) {
		System.out.println("error:" + error);
	}
}

4、配置spring aop

新建spring.xml,内容如下。

注意:在beans节点中需要指定aop命名空间,以及chemaLocation地址,启用aop只需要添加<aop:aspectj-autoproxy/>就可以了。<context:component-scan/>节点用来指定自动扫描bean的命名空间。

<?xml version="1.0" encoding="UTF-8" ?>
<beans xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns="http://www.springframework.org/schema/beans"
       xmlns:aop="http://www.springframework.org/schema/aop"
       xmlns:context="http://www.springframework.org/schema/context"
       xsi:schemaLocation="http://www.springframework.org/schema/beans
       					   http://www.springframework.org/schema/beans/spring-beans.xsd
						   http://www.springframework.org/schema/aop
						   http://www.springframework.org/schema/aop/spring-aop-3.0.xsd
						   http://www.springframework.org/schema/context
						   http://www.springframework.org/schema/context/spring-context-3.1.xsd">
    <aop:aspectj-autoproxy />
    <context:component-scan base-package="com.aspectJ.SpringAop" />
</beans>

5、测试aop

新建测试类,代码如下:

package com.aspectJ.SpringAop;

import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;

/**
 * Main Method
 */
public class App {
	public static void main( String[] args ) {
		ApplicationContext appContext = new ClassPathXmlApplicationContext("spring.xml");
		PersonService personService = appContext.getBean(PersonService.class);
		String personName = "Jim";
		personService.addPerson(personName);
		personService.deletePerson(personName);
		personService.editPerson(personName);
		((ClassPathXmlApplicationContext)appContext).close();
	}
}

三、代码附件

获取完整代码地址:https://gitee.com/shengyu4/springAopDemo

来说两句吧
最新评论
    还没有人评论哦,快来坐沙发吧!