[
Date Prev][
Date Next][
Thread Prev][
Thread Next][
Date Index][
Thread Index]
[
List Home]
Re: [aspectj-users] joinpoint in interface
|
Hi ,
Thanks Adrian, the pointcuts worked fine but not exactly in the way I need
them to work. I'll try to explain my situation:
We're using Hibernate (and Spring) and Hibernate transactions start in the
facade layer. One part of our errorhandling involves "translating" any
exceptions into internal ones (with a sweet looking message code,
configurable via the annotation TranslateExceptionToInternal, e.g
TranslateExceptionToInternal(defaultMess="error.db.unavailable") ).
For some peculiar reason Hibernate exceptions (thanks to Spring?) does not
propagate up the chain of method calls to the start of the transaction (so I
cannot write an 'after throwing' advice pointcutting the execution of a
facade method), but rather quite miraculously appears at the method call
just before the start of the transaction, in my example in the client
package.
Since I prefer not to redesign the entire error handling I need a pointcut
that, in the client package, triggers on method calls to annotated facade
methods. AND I need access to the annotation (in one way or the other,
through reflection if I cannot bind it via a pointcut).
package com.salestool.client;
public class MyController {
private UserServiceFacade userFacade;
public void myMethodA() {
UserServiceFacadeImpl userFacadeImpl = new UserServiceFacadeImpl();
userFacadeImpl.saveUpdateUser(user); //should be adviced, and I need
access to the annotation on the saveUpdateUser method in the
UserServiceFacadeImpl class
}
public void myMethodB() {
userFacade.saveUpdateUser(user); //should be adviced, and I need access
to the annotation on the saveUpdateUser method in the UserServiceFacadeImpl
class
}
}
package com.salestool.facade;
public class UserServiceFacadeImpl implements UserServiceFacade {
@TranslateExceptionToInternal(
ConstraintViolationException="error.db.duplicate.user",
NullpointerException="error.user.not.available",
DefaultMess="error.db.generic")
@Transactional(readOnly = false, propagation = Propagation.REQUIRED,
isolation = Isolation.DEFAULT)
public StatusResult saveUpdateUser(user) { //should NOT be adviced since
I'm looking for exceptions thrown
}
}
regards
Martin
Adrian Colyer-2 wrote:
>
> In your pointcut expression:
>
>> pointcut annotatedFacadeCall(TranslateExceptionToInternal
>> translateExceptionToInternal) :
>> @annotation(translateExceptionToInternal)
>> && within(com.salestool.client..*)
>> && call(@TranslateExceptionToInternal StatusResult+
>> com.salestool.facade.*.*(..));
>
> Annotation matching in both @annotation and in call is based on the
> static type of the receiver - the "subject" of the join point as the
> aspectj docs call it. When you change to declare the variable to have
> the interface type, the subject of the join point changes (it becomes
> the interface operation).
>
> Changing to use the execution join point is probably what you want
> here - this will match annotations based on the thing that actually
> gets to execute (the implementation method). It would read something
> like this:
>
> pointcut inClientControlFlow() :
> cflow(execution(* com.salestool.client..*(..));
>
> pointcut annotatedFacadeCall(TranslateExceptionToInternal
> translateExceptionToInternal) :
> @annotation(translateExceptionToInternal) &&
> execution(StatusResult+ com.salestool.facade.*.*(..)) &&
> inClientControlFlow();
>
> Regards, Adrian.
>
> On Mon, Feb 12, 2007 at 04:24:47AM -0800, aXXa wrote:
>>
>> All!
>> My question:
>> In the following example, how do I write my pointcut to trigger on any
>> implementing classes annotation, i.e. so BOTH A) and B) are adviced
>> (without
>> having to annotate the interface)
>>
>> I have the following pointcut defined:
>> /**
>> any method call to facade package returning a subclass of StatusResult
>> and
>> annotated with TranslateExceptionToInternal
>> from within the client package
>> */
>> pointcut annotatedFacadeCall(TranslateExceptionToInternal
>> translateExceptionToInternal) :
>> @annotation(translateExceptionToInternal)
>> && within(com.salestool.client..*)
>> && call(@TranslateExceptionToInternal StatusResult+
>> com.salestool.facade.*.*(..));
>>
>>
>> a method of a class in facade package is annotated...
>> public class UserServiceFacadeImpl implements UserServiceFacade {
>>
>> @TranslateExceptionToInternal()
>> public StatusResult saveUpdateUser(user) {
>> }
>> }
>>
>> ...but NOT its corresponding method in the interface
>> public interface UserServiceFacade {
>> public StatusResult saveUpdateUser(user);
>> }
>>
>> The following works fine, A):
>>
>> package com.salestool.client;
>> public class MyController {
>> public void myMethod() {
>> UserServiceFacadeImpl userFacadeImpl = new UserServiceFacadeImpl();
>> userFacadeImpl.saveUpdateUser(user); //is adviced
>> }
>>
>> BUT since programming against interfaces is good manners I changed the
>> code
>> to, B)
>>
>> public void myMethod2() {
>> UserServiceFacade userFacade = new UserServiceFacadeImpl();
>> userFacade.saveUpdateUser(user); //is NOT adviced
>> }
>> }
>>
>>
>
> --
> Adrian Colyer
> CTO
> Interface21 Limited
> http://www.interface21.com
>
> Registered in England and Wales: No. 5187766 Registered Office: Summit
> House, 2-2A Highfield Road, Dartford, Kent, DA1 2JY, UK
>
> E-mails should be checked by the recipient to ensure that there are no
> viruses and Interface21 does not accept any responsibility if this is
> not done. Any views or opinions presented are solely those of the
> author and do not necessarily represent those of Interface21.
>
>
>
>
> _______________________________________________
> aspectj-users mailing list
> aspectj-users@xxxxxxxxxxx
> https://dev.eclipse.org/mailman/listinfo/aspectj-users
>
>
--
View this message in context: http://www.nabble.com/joinpoint-in-interface-tf3213307.html#a8940273
Sent from the AspectJ - users mailing list archive at Nabble.com.