当前位置: 首页 > news >正文

Spring AOP表达式速查手册

📍切入点表达式常见形式速查手册


🎯execution(最常用)

语法模板

execution(修饰符?返回类型 包名.类名.方法名(参数)异常?)

可以使用通配符描述切入点

  • “ * ” :单个独立的任意符号,可以通配任意返回值、包名、类名、方法名、任意类型的一个参数,也可以通配包、类、方法名的一部分
  • … :多个连续的任意符号,可以通配任意层级的包,或任意类型、任意个数的参数

常用形式

1. 按包匹配
// 精确包匹配execution(*com.example.service.*.*(..))// service包下所有类的方法execution(*com.example.service..*.*(..))// service包及其子包下所有方法// 多级包匹配execution(*com..service.*.*(..))// 任意父包下的service包
2. 按类匹配
// 精确类匹配execution(*com.example.service.UserService.*(..))// UserService所有方法// 按类名模式匹配execution(*com.example.service.*Service.*(..))// 以Service结尾的类execution(*com.example.service.*Impl.*(..))// 以Impl结尾的类
3. 按方法名匹配
// 精确方法名execution(*com.example.service.UserService.save(..))// 特定方法// 模式匹配方法名execution(*com.example.service.*.save*(..))// 以save开头的方法execution(*com.example.service.*.*User(..))// 以User结尾的方法execution(*com.example.service.*.get*())// 无参的getter方法execution(*com.example.service.*.set*(*))// 单个参数的setter方法
4. 按参数匹配
// 精确参数execution(*com.example.service.*.*(String,int))// 参数为(String, int)// 参数模式execution(*com.example.service.*.*(*))// 单个任意参数execution(*com.example.service.*.*(*,*))// 两个任意参数execution(*com.example.service.*.*(*,String))// 第二个参数为Stringexecution(*com.example.service.*.*(..,String))// 最后一个参数为Stringexecution(*com.example.service.*.*(java.lang.String))// 明确指定类型execution(*com.example.service.*.*(com.example.User))// 自定义类型参数
5. 按返回类型匹配
execution(voidcom.example.service.*.*(..))// 返回void的方法execution(Stringcom.example.service.*.*(..))// 返回String的方法execution(List<*>com.example.service.*.*(..))// 返回List的方法execution(*com.example.service.*.*(..))// 任意返回值

🏷️@annotation(基于注解)

形式

// 匹配方法上的注解@annotation(org.springframework.transaction.annotation.Transactional)@annotation(com.example.annotation.Log)@annotation(com.example.annotation.Cacheable)// 组合使用@annotation(com.example.annotation.Log)&&execution(*com.example.service.*.*(..))

示例注解

// 自定义注解@Target(ElementType.METHOD)@Retention(RetentionPolicy.RUNTIME)public@interfaceLog{Stringvalue()default"";}// 使用@Log("用户操作")publicvoidsaveUser(){...}

📦within(按类型)

形式

// 精确类within(com.example.service.UserService)// UserService所有方法// 包级别within(com.example.service.*)// service包下所有类within(com.example.service..*)// service包及其子包下所有类// 接口/实现类within(com.example.service.BaseService+)// BaseService及其实现类

🏢@within(按类上的注解)

形式

// 匹配类上有特定注解的所有方法@within(org.springframework.stereotype.Service)// 所有@Service类@within(org.springframework.web.bind.annotation.RestController)// 所有@RestController类@within(com.example.annotation.Secured)// 所有@Secured注解类

🧾bean(Spring特有)

形式

// 按Bean名称bean(userService)// 名为userService的Beanbean(*Service)// 以Service结尾的Beanbean(user*)// 以user开头的Beanbean(*Controller)// 以Controller结尾的Beanbean(*ServiceImpl)// 以ServiceImpl结尾的Bean

🔗args(按参数类型/注解)

形式

// 按参数类型args(java.lang.String)// 第一个参数是Stringargs(java.lang.String,java.lang.Long)// 第一个String,第二个Longargs(com.example.User,..)// 第一个参数是User,后面任意// 按参数注解@args(javax.validation.Valid)// 参数有@Valid注解@args(com.example.annotation.NotEmpty)// 参数有@NotEmpty注解

🔄this/target(按代理/目标类型)

形式

// JDK代理this(com.example.service.UserService)// 代理对象是UserService类型target(com.example.service.UserService)// 目标对象是UserService类型// CGLIB代理(两者相同)this(com.example.service.UserServiceImpl)target(com.example.service.UserServiceImpl)

组合表达式

逻辑运算符

// AND (&&)execution(*com.example.service.*.*(..))&&within(com.example.service.*)execution(*com.example.service.*.*(..))&&@annotation(org.springframework.transaction.annotation.Transactional)// OR (||)execution(*com.example.service.*.save*(..))||execution(*com.example.service.*.update*(..))@annotation(com.example.annotation.Log)||@annotation(com.example.annotation.Monitor)// NOT (!)execution(*com.example.service.*.*(..))&&!execution(*com.example.service.*.get*(..))within(com.example.controller.*)&&!@annotation(com.example.annotation.SkipAuth)

实际组合示例

// 1. 监控Service层非查询方法@Pointcut("within(@org.springframework.stereotype.Service *) && "+"execution(* *.*(..)) && "+"!execution(* *.get*(..)) && "+"!execution(* *.find*(..)) && "+"!execution(* *.select*(..))")publicvoidserviceWriteOperation(){}// 2. 权限控制:Controller层需要鉴权的方法@Pointcut("within(@org.springframework.web.bind.annotation.RestController *) && "+"(@annotation(org.springframework.web.bind.annotation.PostMapping) || "+" @annotation(org.springframework.web.bind.annotation.PutMapping) || "+" @annotation(org.springframework.web.bind.annotation.DeleteMapping))")publicvoidneedAuthOperation(){}// 3. 数据库操作监控@Pointcut("execution(* com.example.repository.*.*(..)) || "+"execution(* com.example.dao.*.*(..))")publicvoiddatabaseOperation(){}// 4. 排除特定方法@Pointcut("within(com.example.service.*) && "+"!execution(* com.example.service.HealthCheckService.*(..))")publicvoidserviceExcludeHealthCheck(){}

📝命名切入点(可复用)

定义

@Aspect@ComponentpublicclassSystemArchitecture{// 1. 分层架构@Pointcut("within(@org.springframework.stereotype.Service *)")publicvoidserviceLayer(){}@Pointcut("within(@org.springframework.web.bind.annotation.RestController *)")publicvoidcontrollerLayer(){}@Pointcut("within(@org.springframework.stereotype.Repository *)")publicvoidrepositoryLayer(){}// 2. 注解定义@Pointcut("@annotation(com.example.annotation.Log)")publicvoidloggable(){}@Pointcut("@annotation(com.example.annotation.Cacheable)")publicvoidcacheable(){}@Pointcut("@annotation(org.springframework.transaction.annotation.Transactional)")publicvoidtransactional(){}// 3. 组合定义@Pointcut("serviceLayer() && loggable()")publicvoidloggableService(){}@Pointcut("controllerLayer() && transactional()")publicvoidtransactionalController(){}}// 在其他切面中使用@Before("SystemArchitecture.serviceLayer()")publicvoidbeforeService(){...}

📊实际开发常用形式总结

场景推荐形式示例
全局日志within + 注解within(@org.springframework.stereotype.Service *)
事务管理@annotation@annotation(org.springframework.transaction.annotation.Transactional)
权限控制@annotation + execution@annotation(com.example.annotation.RequireAuth)
缓存切面@annotation@annotation(com.example.annotation.Cacheable)
性能监控execution + 排除execution(* com.example.service.*.*(..)) && !execution(* *.get*(..))
参数校验argsargs(com.example.dto.*)
异常处理within + 包名within(com.example.controller..*)
特定Beanbeanbean(userService)

🎯按优先级排序

// 执行顺序:从精确到宽泛1.@annotation(com.example.CustomAnnotation)// 最精确2.execution(*com.example.service.UserService.save(..))3.execution(*com.example.service.UserService.*(..))4.within(com.example.service.UserService)5.execution(*com.example.service.*.*(..))6.within(com.example.service.*)// 最宽泛7.execution(**.*(..))

⚠️常见错误

错误示例

// ❌ 过于宽泛(影响性能)execution(**.*(..))// ❌ 缺少参数括号execution(*com.example.service.*.*)// ❌ 包路径错误execution(*com.example.*Service.*(..))// 包名中包含通配符// ✅ 正确做法execution(*com.example.service.*Service.*(..))// 类名中包含通配符

最佳实践

// 1. 优先使用注解方式@annotation(com.example.annotation.Log)// 2. 精确匹配,避免扫描过多类within(com.example.service..*)// 3. 组合使用,提高可读性@Pointcut("within(com.example.service..*) && "+"@annotation(org.springframework.transaction.annotation.Transactional)")publicvoidtransactionalService(){}

🔧调试技巧

1. 查看匹配的方法

@Aspect@ComponentpublicclassDebugAspect{@Before("yourPointcut()")publicvoiddebug(JoinPointjoinPoint){System.out.println("匹配方法: "+joinPoint.getSignature().toShortString());}}

2. 测试切入点表达式

// 使用AspectJ工具测试// 下载aspectjweaver,使用ajc编译测试

📚速查表

✅ execution - 按方法签名匹配(最灵活) ✅ @annotation - 按方法注解匹配(最常用) ✅ within - 按类型/包匹配 ✅ @within - 按类注解匹配 ✅ bean - 按Spring Bean名称匹配 ✅ args - 按参数类型/注解匹配 ✅ this/target - 按代理/目标类型匹配 ✅ 组合 - 使用&&、||、!组合多个条件

💎一句话总结

切入点表达式选择指南:

要精确 → 用@annotation 要批量 → 用within 要灵活 → 用execution 要简单 → 用bean 要组合 → 用逻辑运算符

记住:切入点越精确,性能越好,维护越容易!

http://www.cnnetsun.cn/news/19936.html

相关文章:

  • QuickAdd API实战指南:打造你的专属智能笔记工作流
  • Windows系统文件samlib.dll缺失损坏问题 下载修复
  • 鸣潮自动化工具完整使用教程:从零开始轻松掌握智能辅助
  • MethylDackel:BS-seq甲基化提取的终极利器
  • RookieAI_yolov8:2025年游戏AI自瞄技术完全指南
  • pywebview与React集成的终极指南:高效构建跨平台桌面应用
  • 大模型微调:不冻结参数 vs 冻结主干
  • 30亿参数改写AI效率范式:Qwen3-30B-A3B如何让企业AI成本降60%?
  • ppInk:Windows平台上的终极协作写作与在线文档编辑指南
  • 3步彻底解决PDFMathTranslate中文乱码:从新手到专家的终极指南
  • React Stripe.js 终极指南:快速构建安全支付系统
  • 新手专属!BurpSuite 零基础到实战全攻略 —— 渗透测试核心工具配置与精通教程
  • 基于web的农产品溯源系统选题表
  • 基于Web的企业招投标管理系统的开发中期报告
  • ABB RobotWare软件资源下载与配置完全指南
  • Unity角色移动系统终极指南:打造《原神》级流畅体验
  • 终极指南:使用APK Icon Editor轻松定制Android应用
  • 基于Java的学贷通智慧管理系统的设计与实现全方位解析:附毕设论文+源代码
  • 字节跳动开源90亿学术大模型:轻量化英文场景解决方案来了
  • 如何获取119,376个英语单词发音MP3音频资源?实用工具完整指南
  • GitHub下载加速革命:告别龟速访问的终极解决方案
  • cohesive 单元设置粘性(VISCOSITY)
  • AI 内容洞察决策系统:4 大功能让科技企业创新效率提升 50%,敏捷破局信息困局
  • DeepPCB数据集终极指南:PCB缺陷检测实战手册
  • 7-Zip ZS:六种压缩算法如何彻底改变你的文件处理体验
  • Chrome DevTools Protocol终极指南:解锁浏览器自动化的无限可能
  • ET框架客户端性能优化终极指南:从15秒到3秒的快速启动实战
  • 4种有效方法:如何将音乐从Mac传输到Android
  • LoRaWAN智慧物联应用:远距离、低功耗、广连接
  • KK-HF_Patch完整使用指南:轻松解锁游戏无限可能