{"record":{"id":"e68c23b408c9af62","repo":"spring-projects/spring-framework","slug":"unexpected-aop-exception","errorCode":null,"errorMessage":"Unexpected AOP exception","messagePattern":"Unexpected AOP exception","errorType":"exception","errorClass":"AopConfigException","httpStatus":null,"severity":"error","filePath":"spring-aop/src/main/java/org/springframework/aop/framework/CglibAopProxy.java","lineNumber":242,"sourceCode":"\t\t\t// Generate the proxy class and create a proxy instance.\n\t\t\t// ProxyCallbackFilter has method introspection capability with Advisor access.\n\t\t\ttry {\n\t\t\t\treturn (classOnly ? createProxyClass(enhancer) : createProxyClassAndInstance(enhancer, callbacks));\n\t\t\t}\n\t\t\tfinally {\n\t\t\t\t// Reduce ProxyCallbackFilter to key-only state for its class cache role\n\t\t\t\t// in the CGLIB$CALLBACK_FILTER field, not leaking any Advisor state...\n\t\t\t\tfilter.advised.reduceToAdvisorKey();\n\t\t\t}\n\t\t}\n\t\tcatch (CodeGenerationException | IllegalArgumentException ex) {\n\t\t\tthrow new AopConfigException(\"Could not generate CGLIB subclass of \" + this.advised.getTargetClass() +\n\t\t\t\t\t\": Common causes of this problem include using a final class or a non-visible class\",\n\t\t\t\t\tex);\n\t\t}\n\t\tcatch (Throwable ex) {\n\t\t\t// TargetSource.getTarget() failed\n\t\t\tthrow new AopConfigException(\"Unexpected AOP exception\", ex);\n\t\t}\n\t}\n\n\tprotected Class<?> createProxyClass(Enhancer enhancer) {\n\t\tenhancer.setInterceptDuringConstruction(false);\n\t\treturn enhancer.createClass();\n\t}\n\n\tprotected Object createProxyClassAndInstance(Enhancer enhancer, Callback[] callbacks) {\n\t\tenhancer.setInterceptDuringConstruction(false);\n\t\tenhancer.setCallbacks(callbacks);\n\t\treturn (this.constructorArgs != null && this.constructorArgTypes != null ?\n\t\t\t\tenhancer.create(this.constructorArgTypes, this.constructorArgs) :\n\t\t\t\tenhancer.create());\n\t}\n\n\t/**\n\t * Creates the CGLIB {@link Enhancer}. Subclasses may wish to override this to return a custom","sourceCodeStart":224,"sourceCodeEnd":260,"githubUrl":"https://github.com/spring-projects/spring-framework/blob/69bf83ad716d0cfc4b0520a19b4d8b24c79d1538/spring-aop/src/main/java/org/springframework/aop/framework/CglibAopProxy.java#L224-L260","documentation":"buildProxy() has a final catch (Throwable) at line 240 that wraps anything not already covered by the CodeGeneration/IllegalArgumentException branch. The most documented source is TargetSource.getTarget() failing (the comment at line 241), but any unexpected error during callback retrieval or enhancer setup lands here as a generic 'Unexpected AOP exception'.","triggerScenarios":"A TargetSource whose getTarget() throws (custom TargetSource, pooling source exhausting, prototype bean creation failure); an unexpected runtime error inside getCallbacks()/Enhancer.create() not already classified.","commonSituations":"Custom TargetSource throwing on getTarget(); a pooled TargetSource (CommonsPool2TargetSource) that cannot obtain an instance; prototype target bean failing construction; classloader errors surfacing during proxy creation.","solutions":["Inspect the wrapped cause (ex.getCause()) - it is the real failure; fix that root issue","If using a custom TargetSource, make getTarget() robust and check the underlying resource (pool, factory)","For prototype/scoped targets, verify the target bean can actually be instantiated standalone"],"exampleFix":"// before\nclass MyTargetSource extends AbstractPoolingTargetSource { ... }\n// pool exhausted -> 'Unexpected AOP exception' wrapping NoSuchElementException\n\n// after\n// increase pool size / fix target bean creation; inspect getCause() in logs","handlingStrategy":"try-catch","validationCode":"// If using a custom TargetSource, validate getTarget() behavior in isolation:\nObject t = targetSource.getTarget();\nif (t == null) throw new IllegalStateException(\"TargetSource.getTarget() returned null\");","typeGuard":null,"tryCatchPattern":"try {\n  Object proxy = proxyFactory.getProxy();\n} catch (AopConfigException ex) {\n  Throwable cause = ex.getCause();\n  // inspect cause - often the real TargetSource / pool / bean-creation failure\n  throw new RuntimeException(\"Proxy creation failed: \" + cause, ex);\n}","preventionTips":["Always log ex.getCause() - the wrapped throwable is the actionable detail","Test custom TargetSource implementations for getTarget() failures independently"],"tags":["spring-aop","cglib","target-source","proxy"],"backgroundTag":null,"analyzedSha":"69bf83ad716d0cfc4b0520a19b4d8b24c79d1538","analyzedAt":"2026-08-09T15:32:58.770Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}