{"id":"cc035866de8e80ed","repo":"spring-projects/spring-framework","slug":"failed-to-bind-all-argument-names-argument-s","errorCode":null,"errorMessage":"Failed to bind all argument names: {} argument(s) could not be bound","messagePattern":"Failed to bind all argument names: (.+?) argument\\(s\\) could not be bound","errorType":"exception","errorClass":"IllegalStateException","httpStatus":null,"severity":"error","filePath":"spring-aop/src/main/java/org/springframework/aop/aspectj/AspectJAdviceParameterNameDiscoverer.java","lineNumber":271,"sourceCode":"\t\t\t\t\tdefault -> throw new IllegalStateException(\"Unknown algorithmic step: \" + (algorithmicStep - 1));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tcatch (AmbiguousBindingException | IllegalArgumentException ex) {\n\t\t\tif (this.raiseExceptions) {\n\t\t\t\tthrow ex;\n\t\t\t}\n\t\t\telse {\n\t\t\t\treturn null;\n\t\t\t}\n\t\t}\n\n\t\tif (this.numberOfRemainingUnboundArguments == 0) {\n\t\t\treturn this.parameterNameBindings;\n\t\t}\n\t\telse {\n\t\t\tif (this.raiseExceptions) {\n\t\t\t\tthrow new IllegalStateException(\"Failed to bind all argument names: \" +\n\t\t\t\t\t\tthis.numberOfRemainingUnboundArguments + \" argument(s) could not be bound\");\n\t\t\t}\n\t\t\telse {\n\t\t\t\t// convention for failing is to return null, allowing participation in a chain of responsibility\n\t\t\t\treturn null;\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * An advice method can never be a constructor in Spring.\n\t * @return {@code null}\n\t * @throws UnsupportedOperationException if\n\t * {@link #setRaiseExceptions(boolean) raiseExceptions} has been set to {@code true}\n\t */\n\t@Override\n\tpublic String @Nullable [] getParameterNames(Constructor<?> ctor) {\n\t\tif (this.raiseExceptions) {","sourceCodeStart":253,"sourceCodeEnd":289,"githubUrl":"https://github.com/spring-projects/spring-framework/blob/e8729d043887bf0d0baf91e062e909b56eb2b708/spring-aop/src/main/java/org/springframework/aop/aspectj/AspectJAdviceParameterNameDiscoverer.java#L253-L289","documentation":"Thrown by AspectJAdviceParameterNameDiscoverer.getParameterNames (line 270-273) when raiseExceptions is true and after running the full binding algorithm some parameters remain unbound. This is a catch-all failure: the heuristic chain (join-point, throwing, annotation, returning, primitive, this/target/args, reference pointcut) could not account for every parameter.","triggerScenarios":"An advice method has parameters that none of the binding heuristics can match to the pointcut expression: extra parameters with no corresponding pointcut binding form; complex pointcuts with multiple ambiguous candidates; parameters whose names can't be discovered and aren't implied by the expression.","commonSituations":"Advice method declares more parameters than the pointcut binds; pointcut uses binding forms the heuristic doesn't recognize; raising exceptions is enabled (the discoverer is last in the chain) and a genuinely unresolvable parameter exists; relying on discovery instead of explicit arg-names.","solutions":["Provide explicit arg-names matching every parameter so discovery is not needed.","Compile with -parameters so reflection-based discovery (DefaultParameterNameDiscoverer) can supply names earlier in the chain.","Ensure every non-join-point parameter has a corresponding binding form in the pointcut (args/this/target/@annotation) or is a returning/throwing param.","Remove surplus parameters from the advice method."],"exampleFix":"// before: extra 'ctx' param has no binding source\n@After(value = \"execution(* svc.*(..)) && args(id)\")\npublic void after(Long id, String ctx) { ... }\n// after\n@After(value = \"execution(* svc.*(..)) && args(id,ctx)\")\npublic void after(Long id, String ctx) { ... }","handlingStrategy":"validation","validationCode":"// Before relying on discovery, ensure every non-join-point param has a binding source.\nint jpOffset = (firstParamIsJoinPointLike(adviceMethod) ? 1 : 0);\nint bindableFromExpr = countBindingForms(pointcutExpression); // args/this/target/@annotation etc.\nint returningThrowing = (returningName != null ? 1 : 0) + (throwingName != null ? 1 : 0);\nint needed = adviceMethod.getParameterCount() - jpOffset - returningThrowing;\nif (bindableFromExpr < needed) {\n    throw new IllegalStateException(\"Pointcut binds \" + bindableFromExpr\n        + \" but advice needs \" + needed + \" named parameters; add arg-names or fix the pointcut\");\n}","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Compile aspects with -parameters so DefaultParameterNameDiscoverer can supply names earlier in the chain.","Provide explicit arg-names for advice whose parameters cannot be discovered.","Ensure each non-join-point parameter maps to a binding form (args/this/target/@annotation) or returning/throwing.","Remove surplus parameters from advice methods."],"tags":["spring-aop","aspectj","argument-binding","parameters-flag","configuration"],"analyzedSha":"e8729d043887bf0d0baf91e062e909b56eb2b708","analyzedAt":"2026-08-04T19:07:39.725Z","schemaVersion":2}