Repository navigation
Improve performance of #getBeanNamesForType() while the BeanFactory configuration is not yet frozen [SPR-13610] #18188
Copy link
Copy link
Closed
Labels
in: coreIssues in core modules (aop, beans, core, context, expression)Issues in core modules (aop, beans, core, context, expression)status: duplicateA duplicate of another issueA duplicate of another issuetype: enhancementA general enhancementA general enhancement
Description
Activity
spring-projects-issues commented
on Oct 26, 2015 CollaboratorAuthorMore actionsSteffen Ryll commented
Here are the details, which calls to
getBeanNamesForTypeduringrefresh()take how long:- getBeanNamesForType() (frozen=false) for Type
BeanDefinitionRegistryPostProcessortook: 14452 ms - getBeanNamesForType() (frozen=false) for Type
BeanDefinitionRegistryPostProcessortook: 7452 ms - getBeanNamesForType() (frozen=false) for Type
BeanDefinitionRegistryPostProcessortook: 11886 ms - getBeanNamesForType() (frozen=false) for Type
BeanFactoryPostProcessordauerte took: 13819 ms - getBeanNamesForType() (frozen=false) for Type
BeanPostProcessortook: 7335 ms - getBeanNamesForType() (frozen=false) for Type
Advisortook: 9153 ms - getBeanNamesForType() (frozen=false) for Type
ApplicationListenertook: 7328 took - getBeanNamesForType() (frozen=false) for Type
LoadTimeWeaverAwaretook: 10496 ms
- getBeanNamesForType() (frozen=false) for Type
spring-projects-issues commented
on Oct 26, 2015 CollaboratorAuthorMore actionsJuergen Hoeller commented
Fair enough, with that size of context, those calls may take painfully long. We'll revisit this for 4.3, trying to optimize based on the metadata that we have at each given point... but also exploring options for explicit hints in the application's configuration, allowing us to bypass entire steps (e.g. if we know that there is nothing to find for this particular application anyway). We may even go as far as using pre-computed indexes for certain steps, which has been suggested in other cases before; not sure whether that part can happen for 4.3 though.
Juergen
- addedtype: enhancementA general enhancementA general enhancementin: coreIssues in core modules (aop, beans, core, context, expression)Issues in core modules (aop, beans, core, context, expression)
on Jan 11, 2019 - addedstatus: duplicateA duplicate of another issueA duplicate of another issue
on Feb 26, 2024
Metadata
Metadata
Assignees
Labels
in: coreIssues in core modules (aop, beans, core, context, expression)Issues in core modules (aop, beans, core, context, expression)status: duplicateA duplicate of another issueA duplicate of another issuetype: enhancementA general enhancementA general enhancement
Steffen Ryll opened SPR-13610 and commented
We have a pretty large ApplicationContext with about 7600 Beans and startup times have become an issue, now at 5.5 min just for the ApplicationContext. We observed that all the steps in
AbstractApplicationContext#refreshbefore#preInstantiateSingletons()is called take about 90 seconds (excluding the time it takes to load all bean definition XML files). About 81 seconds of that time seems to be spent in the methodDefaultListableBeanFactory#getBeanNamesForType.In order to better understand where time is spent, we've build a wrapper around
DefaultListableBeanFactorythat measures the execution time of calls to#createBean,#getBeanNamesForTypeand#applyBeanPostProcessors*Initialization/Instantiation. This is the tooling we used to get the numbers mentioned above.Closer inspection shows that runtime performance of
#getBeanNamesForTypedepends heavily on the flag#isConfigurationFrozen- as long as it is set tofalseduring AppCtx refresh, each call takes about 10 seconds, when it is set totrue, calls typically take only ~100 ms.A particular issue seems to me, that
#getBeanNamesForTypeis called at least three times for the typeBeanDefinitionRegistryPostProcessor, so that's more than 30 seconds in our scenario. I found that this has been implemented as part of #15258, and comments in the code ofPostProcessorRegistrationDelegateindicate that calling it three times is "by design". But that seems like a waste of time to me, given that these calls take rather long.Please let's discuss which optimizations would be feasible here within the boundaries of the involved interface contracts.
Affects: 4.0.7, 4.2.1
Issue Links:
@Autowired/@Injectget much slower than with@Resourceas the number of classes increases4 votes, 10 watchers