Java:Spring AOP &重构 [英] Java: Spring AOP & Refactoring

查看:27
本文介绍了Java:Spring AOP &重构的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

所以我开始使用 Spring AOP,并且发生了一些事情.配置aspect时,注解都使用String作为参数,而不是Class对象.

So I'm starting to get into Spring AOP, and something occurred to me. When configuring an aspect, the annotations all use Strings as parameters, rather than Class objects.

我提出这个问题是因为这意味着 IDE(我使用 Eclipse,所以我只在这里引用它)将无法正确重构方面.因此,如果我有一个 MyClass 类,其方法是 public void foo(),则 Spring AOP 注释的示例如下:

I bring this up because this means that an IDE (I use Eclipse, so I'll just refer to it here) won't be able to refactor the aspect properly. So if I have a class MyClass, with a method public void foo(), an example of a Spring AOP annotation would be this:

@Before ("execution(public void package.MyClass.foo())")

因为注解中的param是String,如果我把方法名重构为public void foo2(),会破坏这方面的绑定.

Because the param in the annotation is a String, if I refactored the method name to public void foo2(), it would break the binding of this aspect.

我一直在搜索各种论坛和教程,但无论我看哪里,我都只看到字符串参数,这表明这是这里唯一的选择.我想你可以通过在声明绑定的方式上更通用一些来解决这个问题:

I've been scouring various forums and tutorials, but everywhere I look I just see String parameters, which suggests that's the only option here. I guess you could work around this by being a bit more generic in how you declare the binding:

@Before ("exeuction(public void package.MyClass.set*(..))")

这个新方法适用于 MyClass 中的任何 setter 方法,具有任意数量的参数(或没有参数).当然,像这样含糊其辞可能不会一直奏效.

This new one will work for any setter method in MyClass, with any number of parameters (or no params). Of course, being vague like this might not work all the time.

无论如何,我在这里咆哮一下,已经很晚了,我有点累了,我的大脑因寻找答案而疲惫不堪.但我的最后一个问题是:有没有办法设置 Spring AOP 注释,以便重构会影响它们?

Anyway, I'm ranting a little bit here, it's late and I'm kind of tired and my brain is all worn out from hunting for an answer to this. But my final question is this: is there any way to set up Spring AOP annotations so that refactoring will affect them?

谢谢.

推荐答案

嗯,AOP 的全部意义在于以模块化方式实现横切行为,并将其应用于理想情况下不知道任何方面的应用程序代码.因此,您在两者之间没有固定的联系.重要的是要记住,在维护和重构应用程序代码的同时,还应该使用它重构方面,以确保切入点不会中断.

Well, the whole point of AOP is to implement cross-cutting behaviour in a modular way and apply it to application code which ideally is unaware of any aspects. Thus, you have no fixed connection between the two. It is just important to remember that as much as you maintain and refactor your application code, you should also refactor your aspects with it in oder to make sure that pointcuts do not break.

话虽如此,如果您安装 AJDT(AspectJ 开发工具),Eclipse 和其他 IDE 仍然会提示您将哪些方面应用于何处.我主要使用完整的 AspectJ,而不是称为 Spring AOP 的基于代理的AOP lite"变体,所以我不知道 AJDT 对 Spring AOP 是否有用.不过,它将通过 LTW(加载时编织)将 AspectJ 应用于 Spring.

Having said that, Eclipse and other IDEs still give you hints about which aspects are applied where if you install AJDT (AspectJ Development Tools). I mainly use full AspectJ, not the proxy-based "AOP lite" variant called Spring AOP, so I do not know if AJDT is any useful with Spring AOP. It will be with AspectJ applied to Spring via LTW (load-time weaving), though.

这是方面可视化"视角的屏幕截图:

它以图形方式显示了哪些方面适用于代码的哪些部分.如果您双击任何虚线,代码编辑器将引导您到应用方面的确切位置.

It graphically shows which aspects apply to which parts of the code. If you double-click any of the dotted lines, a code editor will lead you to the exact place where an aspect is applied.

还有交叉引用视图,在方面代码和纯 Java 代码中几乎没有指标:

There also is the cross-reference view with little indicators within aspect code as well as plain Java code:

右侧是交叉参考视图,列出了适用于当前所选方法的所有方面.左侧有一些小图标,指示适用于每种方法的建议类型.

On the right hand side there is the cross-reference view listing all aspects applying to the currently selected method. On the left hand side there are little icons indicating which types of advice apply to each method.

顺便说一句,交叉引用视图也适用于各个方面.当您将光标置于建议内时,外部参照视图会列出代码中应用建议的所有位置:

BTW, the cross-reference view also works from aspects. When you place the cursor to within an advice, the xref view lists all places in the code where the advice applies:

还有更多:AspectJ 编译器 可以这样配置,以便列出方面代码建议的所有连接点.您可以手动或什至在自动烟雾测试中检查输出的变化.例如,如果由于您更改了某些包、类或方法名称而导致建议不再适用,则会出现 Xlint 警告 "adviceDidNotMatch" 和/或有时也会 无效的绝对类型名称".此外,相关建议的交叉引用视图将为空:

There is more: The AspectJ compiler can be configured in such a way so as to list all joinpoints advised by aspect code. You can check the output for changes manually or even in an automated smoke test. For instance, if an advice does not apply anymore because you changed some package, class or method names, there will be an Xlint warning "adviceDidNotMatch" and/or sometimes also "invalidAbsoluteTypeName". Furthermore, the cross-reference view for the advice in question will be empty:

正如您刚刚看到的,在重构应用程序或方面代码时,AJDT 中有很多指标和帮助程序.

As you have just seen, there are plenty indicators and helpers within AJDT when refactoring application or aspect code.

另外一件事:如果您使用 AspectJ 而不是 Spring AOP,您可以选择使用更简洁和富有表现力的原生 AspectJ 语法,而不是注释样式的语法.我绝对喜欢前者而不是后者.然后,您的代码编辑器中不仅有字符串,还有更好的语法突出显示以及代码完成和重构.

One more thing: If you use AspectJ instead of Spring AOP you have an option to use the more concise and expressive native AspectJ syntax instead of the annotation-style syntax. I definitely prefer the former to the latter. Then you have more than just strings in your code editor, better syntax highlighting and code completion and refactoring.

最后但并非最不重要的一点:您还应该为方面代码编写单元测试和集成测试,以便注意方面是否中断.手动检查很好,但在即时反馈方面,自动回归测试是无与伦比的.;-)

Last, but not least: You should also write unit and maybe integration tests for your aspect code so as to notice if aspects break. Manual checks are nice, but automated regression tests are unbeatable when it comes to immediate feedback. ;-)

这篇关于Java:Spring AOP &重构的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆