使用spring通过aop获取方法参数和参数值
作者:Insist_on_progress 发布时间:2022-06-04 16:28:33
标签:spring,aop获取方法参数,参数值
spring通过aop获取方法参数和参数值
自定义注解
package com.xiaolc.aspect;
import java.lang.annotation.*;
/**
* @author lc
* @date 2019/9/10
*/
@Documented
@Target({ElementType.TYPE, ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
public @interface LiCheng {
}
切面
package com.xiaolc.aspect;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.springframework.core.DefaultParameterNameDiscoverer;
import org.springframework.core.ParameterNameDiscoverer;
import org.springframework.stereotype.Component;
import java.lang.reflect.Method;
import java.util.HashMap;
import java.util.Map;
/**
* 获取方法上的注解值
*/
@Component
@Aspect
public class AuditAnnotationAspect {
@Around("@annotation(liCheng))")
private static Map getFieldsName(ProceedingJoinPoint joinPoint,LiCheng liCheng) throws ClassNotFoundException, NoSuchMethodException {
String classType = joinPoint.getTarget().getClass().getName();
String methodName = joinPoint.getSignature().getName();
// 参数值
Object[] args = joinPoint.getArgs();
Class<?>[] classes = new Class[args.length];
for (int k = 0; k < args.length; k++) {
if (!args[k].getClass().isPrimitive()) {
// 获取的是封装类型而不是基础类型
String result = args[k].getClass().getName();
Class s = map.get(result);
classes[k] = s == null ? args[k].getClass() : s;
}
}
ParameterNameDiscoverer pnd = new DefaultParameterNameDiscoverer();
// 获取指定的方法,第二个参数可以不传,但是为了防止有重载的现象,还是需要传入参数的类型
Method method = Class.forName(classType).getMethod(methodName, classes);
// 参数名
String[] parameterNames = pnd.getParameterNames(method);
// 通过map封装参数和参数值
HashMap<String, Object> paramMap = new HashMap();
for (int i = 0; i < parameterNames.length; i++) {
paramMap.put(parameterNames[i], args[i]);
System.out.println("参数名:"+parameterNames[i]+"\n参数值"+args[i]);
}
return paramMap;
}
private static HashMap<String, Class> map = new HashMap<String, Class>() {
{
put("java.lang.Integer", int.class);
put("java.lang.Double", double.class);
put("java.lang.Float", float.class);
put("java.lang.Long", Long.class);
put("java.lang.Short", short.class);
put("java.lang.Boolean", boolean.class);
put("java.lang.Char", char.class);
}
};
}
aop切面 注解、参数获取
在工作中会经常使用aop,这里将aop使用基本方法,获取在切点中使用的获取参数、注解做一个样例。
1、定义需要切面的注解
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface AnnDemo {
String value();
boolean isAop() default true;
}
2、在需要进行切面的方法标注注解
@RestController
@RequestMapping("/order")
public class OrderController {
@Autowired
private OrderService orderService;
@RequestMapping("/all")
@AnnDemo(value = "all",isAop = false)
public List<TbOrder> findAll() {
List<TbOrder> list = orderService.getOrderList();
return list;
}
@RequestMapping("/page")
@AnnDemo(value = "page")
public List<TbOrder> findPage(@RequestParam("username") String username) {
List<TbOrder> listPage = orderService.getOrdersListPage();
return listPage;
}
}
3、定义切面
在切面中获取切点注解,方法,参数的获取
@Aspect
@Component
public class AspectDemo {
@Pointcut(value = "execution(* com.yin.freemakeradd.controller..*(..))")
public void excetionMethod() {}
@Pointcut(value = "execution(* com.yin.freemakeradd.controller..*(..)) && @annotation(AnnDemo)")
public void excetionNote() { }
@Before("excetionMethod()")
public void testBefore(JoinPoint joinPoint) {
System.out.println("----------------------------前置通知---");
Object[] args = joinPoint.getArgs();
for (Object arg : args) {
System.out.println(arg);
}
}
@Around(value = "execution(* com.yin.freemakeradd.controller..*(..)) && @annotation(AnnDemo)")
public Object testBeforeNote(ProceedingJoinPoint joinPoint) throws Throwable {
//用的最多通知的签名
Signature signature = joinPoint.getSignature();
MethodSignature msg=(MethodSignature) signature;
Object target = joinPoint.getTarget();
//获取注解标注的方法
Method method = target.getClass().getMethod(msg.getName(), msg.getParameterTypes());
//通过方法获取注解
AnnDemo annotation = method.getAnnotation(AnnDemo.class);
Object proceed;
//获取参数
Object[] args = joinPoint.getArgs();
System.out.println(annotation.value());
System.out.println(annotation.isAop());
for (Object arg : args) {
System.out.println(arg);
}
if (Objects.isNull(annotation) || !annotation.isAop()) {
System.out.println("无需处理");
proceed = joinPoint.proceed();
}else {
System.out.println("进入aop判断");
proceed = joinPoint.proceed();
if(proceed instanceof List){
List proceedLst = (List) proceed;
if(!CollectionUtils.isEmpty(proceedLst)){
TbOrder tbOrder = new TbOrder();
tbOrder.setPaymentType("fffffffffffffffffff");
ArrayList<TbOrder> tbOrderLst = new ArrayList<>();
tbOrderLst.add(tbOrder);
return tbOrderLst;
}
}
System.out.println(proceed);
}
return proceed;
}
}
来源:https://blog.csdn.net/qq_41988504/article/details/100726527
0
投稿
猜你喜欢
- Java类库及其组织结构(Java API)Java 官方为开发者提供了很多功能强大的类,这些类被分别放在各个包中,随JDK一起发布,称为J
- 我们在代码中经常使用using保障非托管资源的释放 static void Main(string[] args){
- package dao;import java.sql.*;public class BaseDao { //oracle//&n
- Java.io 包几乎包含了所有操作输入、输出需要的类。所有这些流类代表了输入源和输出目标。Java.io 包中的流支持很多种格式,比如:基
- 第1部分 ArrayList介绍ArrayList 是一个数组队列,相当于 动态数组。与Java中的数组相比,它的容量能动态增长。它继承于A
- 从接触springboot开始,便深深的被它的简洁性深深的折服了,精简的配置,方便的集成,使我再也不想用传统的ssm框架来搭建项目,一大堆的
- 本文实例为大家分享了Java实现发送邮件并携带附件的具体代码,供大家参考,具体内容如下一、 邮件服务器与传输协议要在网络上实现邮件功能,必须
- Java常用类包装类由于Java语言中的基本类型不是面向对象,并不具备对象的性质,实际使用存在很多不便。Java在java.lang包中提供
- 在 Windows 有一些字符是不能作为文件名,尝试重命名一个文件,输入/ 就可以看到windows 提示的不能作为文件名的字符那么具体是包
- (注意:本文基于JDK1.8)前言元素在存储到内存中,当我们需要使用在内存中存储的元素,这就涉及到在内存中查找元素,今天一起学习Vector
- RabbitMQ主要有六种种工作模式,本文整合SpringBoot分别介绍工作模式的实现。前提概念生产者消息生产者或者发送者,使用P表示:队
- 问题描述:在windows系统下,idea中,操作terminal控制台,使用git log查看日志时,出现如下乱码为什么参考网上很多的gi
- 编写程序,事先将所有观众姓名输入数组,然后获得数组元素的总数量,最后在数组元素中随机抽取元素的下标,根据抽取的下标获得幸运观众的姓名。思路如
- 通过JDK的Proxy代理实现对业务类做简单的AOP实现接口:UserService 包含的方法为切入点,会被代理拦截类:UserServi
- 前言:使用 interrupt 来通知线程停止运行,而不是强制停止!普通情况停止线程public class Right
- 序言:使用MyBatis3提供的注解可以逐步取代XML,例如使用@Select注解直接编写SQL完成数据查询,使用@SelectProvid
- Java读取properties文件中文乱码初用properties,读取java properties文件的时候如果value是中文,会出
- 本文实例为大家分享了Java使用MulticastSocket实现群聊应用程序的具体代码,供大家参考,具体内容如下在这篇文章中,讨论了一个使
- 本文实例讲述了java采用中文方式显示时间的方法。分享给大家供大家参考。具体如下:其中t为秒,比如有时候需要计算两个任务相差多久,或者该任务
- 在使用Java web开发的后端工程师们大多会使用Maven作为项目构建以及编译的工具,微服务和大中台当道的今天,更加关注maven的细节是