{"id":"d031b96b4d4fe1b5","repo":"spring-projects/spring-framework","slug":"found-candidate-annotation-binding-variables-bu","errorCode":null,"errorMessage":"Found {} candidate annotation binding variables but only one potential argument binding slot","messagePattern":"Found (.+?) candidate annotation binding variables but only one potential argument binding slot","errorType":"exception","errorClass":"IllegalArgumentException","httpStatus":null,"severity":"error","filePath":"spring-aop/src/main/java/org/springframework/aop/aspectj/AspectJAdviceParameterNameDiscoverer.java","lineNumber":438,"sourceCode":"\t * Match the given list of extracted variable names to argument slots.\n\t */\n\tprivate void bindAnnotationsFromVarNames(List<String> varNames) {\n\t\tif (!varNames.isEmpty()) {\n\t\t\t// we have work to do...\n\t\t\tint numAnnotationSlots = countNumberOfUnboundAnnotationArguments();\n\t\t\tif (numAnnotationSlots > 1) {\n\t\t\t\tthrow new AmbiguousBindingException(\"Found \" + varNames.size() +\n\t\t\t\t\t\t\" potential annotation variable(s) and \" +\n\t\t\t\t\t\tnumAnnotationSlots + \" potential argument slots\");\n\t\t\t}\n\t\t\telse if (numAnnotationSlots == 1) {\n\t\t\t\tif (varNames.size() == 1) {\n\t\t\t\t\t// it's a match\n\t\t\t\t\tfindAndBind(Annotation.class, varNames.get(0));\n\t\t\t\t}\n\t\t\t\telse {\n\t\t\t\t\t// multiple candidate vars, but only one slot\n\t\t\t\t\tthrow new IllegalArgumentException(\"Found \" + varNames.size() +\n\t\t\t\t\t\t\t\" candidate annotation binding variables\" +\n\t\t\t\t\t\t\t\" but only one potential argument binding slot\");\n\t\t\t\t}\n\t\t\t}\n\t\t\telse {\n\t\t\t\t// no slots so presume those candidate vars were actually type names\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * If the token starts meets Java identifier conventions, it's in.\n\t */\n\tprivate @Nullable String maybeExtractVariableName(@Nullable String candidateToken) {\n\t\tif (AspectJProxyUtils.isVariableName(candidateToken)) {\n\t\t\treturn candidateToken;\n\t\t}\n\t\treturn null;","sourceCodeStart":420,"sourceCodeEnd":456,"githubUrl":"https://github.com/spring-projects/spring-framework/blob/e8729d043887bf0d0baf91e062e909b56eb2b708/spring-aop/src/main/java/org/springframework/aop/aspectj/AspectJAdviceParameterNameDiscoverer.java#L420-L456","documentation":"Thrown as IllegalArgumentException when the pointcut expression produces multiple candidate annotation-binding variable names but there is exactly one unbound Annotation-typed slot. Spring cannot pick which name maps to the single slot. Only surfaces when raiseExceptions=true.","triggerScenarios":"A pointcut with two or more annotation-binding expressions (e.g. @annotation(a) @annotation(b)) but only one Annotation-typed parameter in the advice method.","commonSituations":"Refactoring a pointcut to add a second @annotation binding while forgetting to add the matching parameter; copy-paste errors in pointcut expressions.","solutions":["Make the number of annotation-binding expressions match the number of Annotation-typed parameters.","Remove the extra annotation-binding expression from the pointcut.","Compile with -parameters and bind each annotation explicitly."],"exampleFix":"// before\n@Before(\"@annotation(a) && @annotation(b)\")\npublic void before(MyAnnotation a) { ... }\n\n// after\n@Before(\"@annotation(a) && @annotation(b)\")\npublic void before(MyAnnotation a, OtherAnnotation b) { ... }","handlingStrategy":"validation","validationCode":"// Count annotation-binding expressions and Annotation params and assert equality:\nint bindingClauses = countAnnotationBindingClauses(pointcutExpression);\nint annotationParams = countAnnotationParams(adviceMethod);\nassert bindingClauses == annotationParams;","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Pair every @annotation/@args/@this/etc. binding with exactly one Annotation parameter.","Compile with -parameters.","Review pointcut strings after refactoring advice signatures."],"tags":["spring-aop","aspectj","advice-binding","annotation"],"analyzedSha":"e8729d043887bf0d0baf91e062e909b56eb2b708","analyzedAt":"2026-08-04T19:07:39.725Z","schemaVersion":2}