Skip to main content

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [List Home]
Re: [aspectj-users] Fwd: Round advice on constructor?

Hello again, Leon.

The Object[] returned by jp.getArgs() will not be passed on to jp.proceed(). You need to bind the parameter(s) you want to modify via args(), e.g. like this (untested, I hope I got the Scala syntax right):

@Around("execution (com.leon.aop.MyObject.new(String, ..)) && args(text)")
def constructCP(jp: ProceedingJoinPoint, String text): Object = {
    try {
        println("Start...")
        jp.proceed(text..toUpperCase)
    } finally {
        println("End...")
    }
}

CAVEAT: If you manipulate parameters in subclass constructors this way, they will not be passed on to base class constructors via super() calls due to the execution order of
  - preinitialization(*.new())
  - initialization(*.new())
  - execution(*.new()).

If you really want to catch the former two as well, you need and around() advice on
  - call(*.new())

For background information see my answer and its sample output on http://stackoverflow.com/a/15571384/1082681.

Regards
-- 
Alexander Kriegisch
http://scrum-master.de


Leon Ma schrieb am 10.06.2014 10:10:

> I've successfully used round advice to intercept input parameter for a method.
> 
> 
> However, it seems constructor does not work for me. Here're my test: (It's in scala, but should be easy to understand)
> 
> 
> class MyObjectTest extends FlatSpecLike with Matchers {
> 
> 
>   "MyObjectAspect" should "work" in {
> 
>     val t = new MyObject("leon")
> 
>     val result = t.talk()
> 
>     println(result)
> 
>     result should be("LEON")
> 
>   }
> 
> }
> 
> 
> class MyObject(text: String) {
> 
> 
>   def talk(): String = {
> 
>     println("MyObject " + text)
> 
>     text
> 
>   }
> 
> }
> 
> 
> @Aspect
> 
> class MyObjectAspect {
> 
> 
>   @Around(value = "execution (com.leon.aop.MyObject.new(..))")
> 
>   def constructCP(jp: ProceedingJoinPoint): Object = {
> 
> 
>     try {
> 
>       println("Start...")
> 
>       val args = jp.getArgs
> 
>       args(0) = args(0).toString.toUpperCase
> 
>       jp.proceed(args)
> 
>     } finally {
> 
>       println("End...")
> 
>     }
> 
> 
>   }
> 
> 
> }
> 
> 
> output:
> 
> 
> Start...
> 
> End...
> 
> MyObject leon
> 
> leon
> 
> 
> "[leon]" was not equal to "[LEON]"
> 
> org.scalatest.exceptions.TestFailedException: "[leon]" was not equal to "[LEON]"
> 
> at org.scalatest.MatchersHelper$.newTestFailedException(MatchersHelper.scala:160)
> 
> at org.scalatest.Matchers$ShouldMethodHelper$.shouldMatcher(Matchers.scala:6141)
> 
> at org.scalatest.Matchers$AnyShouldWrapper.should(Matchers.scala:6175)
> 
> at com.leon.aop.MyObjectTest$$anonfun$1.apply$mcV$sp(ConstructorTest.scala:18)
> 
> 
> Anything wrong?
> 
> 
> Thanks
> 
> 
> Leon
> 
>


Back to the top