Aspect(切面):是切入点和通知(引介)的结合
compile "org.springframework:spring-aspects:4.3.9.RELEASE"
compile "org.springframework:spring-aop:4.3.9.RELEASE"
compile "aspectj:aspectjweaver:1.5.4"
compile "aopalliance:aopalliance:1.0"
"http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:aop="http://www.springframework.org/schema/aop"
xmlns:p="http://www.springframework.org/schema/p"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context.xsd
http://www.springframework.org/schema/aop
http://www.springframework.org/schema/aop/spring-aop.xsd">
@Bean
data class User(var name: String, var age: Int)
{
fun add()
{
println("user add")
}
}
@Bean
data class Advice(var content: String)
{
fun before()
{
println("前置通知")
}
}
execution(public * *(..))
execution(* com.kotlin.*(..))
(一个点表示不包含子包)execution(* com.kotlin.. *(..))
(两个点表示包含子包)execution(* com.kotlin.xxinterface+.*(..))
execution(* add*(..))
execution(* *.*(..))
<bean id="user" class="com.kotlin.Bean.User">bean>
<bean id="advice" class="com.kotlin.Bean.Advice">bean>
<aop:config>
<aop:pointcut id="pointcut" expression="execution(* com.kotlin.Bean.User.*(..))"/>
<aop:aspect ref="advice">
<aop:before method="before" pointcut-ref="pointcut"/>
aop:aspect>
aop:config>
class main
{
@Test
fun test()
{
//加载Spring配置文件,创建对象
val context = FileSystemXmlApplicationContext("src/main/webapp/WEB-INF/applicationContext.xml")
val user = context.getBean("user") as User
user.add()
}
}
@Bean
data class User(var name: String, var age: Int)
{
fun add(): String
{
println("user add")
return "你好"
}
}
@Bean
data class Advice(var content: String)
{
fun before()
{
println("前置通知")
}
//后置通知需要传入一个参数,这个参数就是需要增强方法的返回值,没有可以不写
fun afterResult(result: Any)
{
println("后置通知 "+result)
}
//最终通知无论该方法有没有出异常有没有返回值,最终都会被执行
fun after()
{
println("最终通知")
}
/* 环绕通知需要一个ProceedingJoinPoint参数,这相当于需要增强的函数的方法体,需要的调用它的proceed方法执行,如果该函数有返回值,那么环绕通知也需要返回一个proceed方法的返回值 */
fun around(pro: ProceedingJoinPoint): Any
{
//方法之前
println("环绕通知 方法之前")
//被增强的方法
val any = pro.proceed()
//方法之后
println("环绕通知 方法之后")
return any
}
//异常通知需要一个异常参数,当出现异常时该方法将会被调用
fun exception(ex : Exception)
{
println("异常通知 "+ex)
}
}
<bean id="user" class="com.kotlin.Bean.User">bean>
<bean id="advice" class="com.kotlin.Bean.Advice">bean>
<aop:config>
<aop:pointcut id="pointcut" expression="execution(* com.kotlin.Bean.User.*(..))"/>
<aop:aspect ref="advice">
<aop:before method="before" pointcut-ref="pointcut"/>
<aop:after-returning method="afterResult" pointcut-ref="pointcut" returning="result"/>
<aop:after method="after" pointcut-ref="pointcut" />
<aop:around method="around" pointcut-ref="pointcut" />
<aop:after-throwing method="exception" pointcut-ref="pointcut" throwing="ex"/>
aop:aspect>
aop:config>
try
{
// 前置通知
// 环绕通知(前)
// 目标方法
// 环绕通知(后)
// 后置通知(也有人称为返回通知)
}
catche(Exception e)
{
// 异常通知
}
finally
{
// 最终通知
}
<aop:aspectj-autoproxy>aop:aspectj-autoproxy>
@Bean
@Component(value = "user")
data class User(var name: String, var age: Int)
{
fun add(): String
{
println("user add")
// var s = 4 / 0
return "你好"
}
}
@Aspect
@Bean
@Component(value = "advice")
data class Advice(var content: String)
{
@Before(value = "execution(* com.kotlin.Bean.User.*(..))")
fun before()
{
println("前置通知")
}
@AfterReturning(value = "execution(* com.kotlin.Bean.User.*(..))", returning = "result")
fun afterResult(result: Any)
{
println("后置通知 " + result)
}
@After(value = "execution(* com.kotlin.Bean.User.*(..))")
fun after()
{
println("最终通知")
}
@Around(value = "execution(* com.kotlin.Bean.User.*(..))")
fun around(pro: ProceedingJoinPoint): Any
{
//方法之前
println("环绕通知 方法之前")
//被增强的方法
val any = pro.proceed()
//方法之后
println("环绕通知 方法之后")
return any
}
@AfterThrowing(value = "execution(* com.kotlin.Bean.User.*(..))", throwing = "ex")
fun exception(ex: Exception)
{
println("异常通知 " + ex)
}
}