Bug 393318 - Cannot pass middle argument to pointcut
Summary: Cannot pass middle argument to pointcut
Status: RESOLVED WONTFIX
Alias: None
Product: AspectJ
Classification: Tools
Component: Compiler (show other bugs)
Version: 1.6.11   Edit
Hardware: PC All
: P3 normal (vote)
Target Milestone: ---   Edit
Assignee: aspectj inbox CLA
QA Contact:
URL:
Whiteboard:
Keywords:
Depends on:
Blocks:
 
Reported: 2012-11-01 07:59 EDT by z z CLA
Modified: 2016-10-28 12:21 EDT (History)
2 users (show)

See Also:


Attachments

Note You need to log in before you can comment on or make changes to this bug.
Description z z CLA 2012-11-01 07:59:41 EDT
This code fails to start:

@Pointcut (value = "args(.., object, ..)", argNames = "object")  
private void pointcut(Object object)    {} 

The exception is:

Caused by: java.lang.IllegalArgumentException: error at ::0 uses more than one .. in args (compiler limitation)
	at org.aspectj.weaver.tools.PointcutParser.parsePointcutExpression(PointcutParser.java:301) ~[aspectjweaver-1.6.11.jar:1.6.11]
Comment 1 Andrew Clement CLA 2012-11-01 11:47:49 EDT
We don't support multiple '..' in args. So typically you use '*' to stand in for an argument:

args(*,object,..) - the 2nd argument
args(*,*,object,..) - the 3rd argument

will that work for you?
Comment 2 z z CLA 2012-11-02 05:35:20 EDT
This is obviously not suitable. I want to pass argument that is anywhere among parameters. It can be 1st,2nd, 3rd.
How can I do it ? Create pointcuts for any number of parameters from 1 to 1000 ?
Comment 3 z z CLA 2012-11-02 05:45:09 EDT
Here is how my pointcut looks now:
args(..,criteria) || args(criteria,..) || args(*,criteria,..) || args(..,criteria,*)

Do you really suppose this to be quite elegantly (besides it handles just 4 cases) ?

(In reply to comment #2)
> This is obviously not suitable. I want to pass argument that is anywhere
> among parameters. It can be 1st,2nd, 3rd.
> How can I do it ? Create pointcuts for any number of parameters from 1 to
> 1000 ?
Comment 4 Andrew Clement CLA 2012-11-02 14:36:51 EDT
I completely agree that it is not elegant. We have an open enhancement request to handle this situation which comes up a lot with parameter annotations (@NotNull being a prime example).  Unfortunately the design and implementation of supporting this is quite tricky to get right, and whilst a workaround exists we tend to focus more on the problems which have no workaround.

> Create pointcuts for any number of parameters from 1 to 1000 ?

I haven't really seen methods with more than 10 parameters - but yes you would have to create a variant pointcut or pointcut comopnent for each you want to match.  I'm not 100% sure it will behave if you merge them all into one clause:

 args(..,criteria) || args(criteria,..) || args(*,criteria,..) || args(..,criteria,*)

because if your criteria matches two of them at one call location, what would it bind?  This is the pattern I've seen:

before(Object arg): somepcd() && args(arg,..) { callsomething(); }
before(Object arg): somepcd() && args(*,arg,..) { callsomething(); }
before(Object arg): somepcd() && args(*,*,arg,..) { callsomething(); }
before(Object arg): somepcd() && args(*,*,*,arg,..) { callsomething(); }
before(Object arg): somepcd() && args(*,*,*,*,arg,..) { callsomething(); }
...
Comment 5 Andrew Clement CLA 2016-10-28 12:21:11 EDT
Closing as known limitation for now.  Periodically raised as something to look into but it is a lot of work to implement nicely when there exists a crude workaround.