Closed
Description
Mischa Neumann opened SPR-14692 and commented
if you use @EnableAspectJAutoProxy
and e.g. @EnableScheduling
you might accidentally create a ScheduledMethodRunnable
with an unproxied bean.
this is caused by AnnotationAwareAspectJAutoProxyCreator
and ScheduledAnnotationBeanPostProcessor
both having a default order of Ordered.LOWEST_PRECEDENCE.
as the developer usually has no insight in which post processor is applied in which order and the ordering might be critical for the application to function properly, I would suggest:
- log all post processors and their ordering at INFO level on startup
- force all post processors to have a unique order (there is enough space between Ordered.LOWEST_PRECEDENCE and HIGHEST_PRECEDENCE)
- review the existing spring framework post processors for having a reasonable default order
Affects: 4.2.7
Issue Links:
- Ordered interface not respected on non-singleton aspects [SPR-14959] #19526 Ordered interface not respected on non-singleton aspects
- SchedulingConfigurer's ScheduledTaskRegistrar should reliably shut down before TaskScheduler [SPR-15067] #19633 SchedulingConfigurer's ScheduledTaskRegistrar should reliably shut down before TaskScheduler
Metadata
Metadata
Assignees
Type
Projects
Relationships
Development
No branches or pull requests
Activity
spring-projects-issues commentedon Dec 29, 2016
Juergen Hoeller commented
From my perspective,
AnnotationAwareAspectJAutoProxyCreator
's default order is alright; our general AOP post-processors are all ordered that way, leaving a custom order open to the user but also allowing for declaration order to be significant (with the same order values). Post-processor ordering is a rather subtle affair overall since the order effectively only applies to each callback: i.e. first allpostProcessBeforeInitialization
callbacks, then allpostProcessAfterInitialization
callbacks. I'd rather not make this more complex through implementation-specific default order values that would subtly affect existing declaration-order scenarios.Solving your scenario in a different way, it's rather
ScheduledAnnotationBeanPostProcessor
(and its siblingJmsAnnotationBeanPostProcessor
) which should always come in a final phase (after the AOP phase) since they're dispatching to the bean. The easiest way to enforce this is for them to declareMergedBeanDefinitionPostProcessor
, a marker for internal post-processors which insist on seeing the final runtime bean definition. This rule was introduced in #10734 and has been applied toAutowiredAnnotationBeanPostProcessor
and co already but unfortunately not toScheduledAnnotationBeanPostProcessor
yet. I've closed that gap for 4.3.6 now.As a final note, as far as I could reproduce,
@EnableAspectJAutoProxy
doesn't actually reveal the problem since the internal auto-proxy creator behind@EnableAspectJAutoProxy
will be set up withOrdered.HIGHEST_PRECEDENCE
, even if theAnnotationAwareAspectJAutoProxyCreator
classLOWEST_PRECEDENCE
as a default (like all other AOP post-processor classes). As a consequence, it always comes first, withScheduledAnnotationBeanPostProcessor
reliably seeing the properly proxied instance. However, with a manualAnnotationAwareAspectJAutoProxyCreator
bean definition, the problem does show and is being addressed by the fix above now.