You are viewing a plain text version of this content. The canonical link for it is here.
Posted to users@wicket.apache.org by leok <le...@gmail.com> on 2008/12/11 22:33:52 UTC

SpringBeanLocator and @SpringBean performance issue

Hello,

Our Wicket app makes use of the @SpringBean annotation thorughout our code,
which is a pretty cool feature. While checking some thread stack traces
during load testing, we found lots of threads bottlenecking in the
SpringBeanLocator class:

Object blocked: 145.133 ms, Object wait: 0 ms, CPU wait: 2.118 ms, I/O wait:
9.017 ms, CPU: 73.847 ms

    *
org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton
(DefaultSingletonBeanRegistry.java:180, bci=22, server compiler)
          o blocked on java.util.concurrent.ConcurrentHashMap
(0x000000cd67f9d170)
    *
org.springframework.beans.factory.support.AbstractBeanFactory.isTypeMatch
(AbstractBeanFactory.java:415, bci=41, server compiler)
    *
org.springframework.beans.factory.support.DefaultListableBeanFactory.getBeanNamesForType
(DefaultListableBeanFactory.java:223, bci=142, server compiler)
    *
org.springframework.beans.factory.support.DefaultListableBeanFactory.getBeanNamesForType
(DefaultListableBeanFactory.java:202, bci=4, server compiler)
    *
org.springframework.context.support.AbstractApplicationContext.getBeanNamesForType
(AbstractApplicationContext.java:933, bci=5, server compiler)
    *
org.springframework.beans.factory.BeanFactoryUtils.beanNamesForTypeIncludingAncestors
(BeanFactoryUtils.java:143, bci=8, server compiler)
    * org.apache.wicket.spring.SpringBeanLocator.getBeanNameOfClass
(SpringBeanLocator.java:104, bci=2, server compiler)
    * org.apache.wicket.spring.SpringBeanLocator.getBeanName
(SpringBeanLocator.java:192, bci=29, server compiler)
    * org.apache.wicket.spring.SpringBeanLocator.isSingletonBean
(SpringBeanLocator.java:133, bci=13, server compiler)
    *
org.apache.wicket.spring.injection.annot.AnnotProxyFieldValueFactory.getFieldValue
(AnnotProxyFieldValueFactory.java:90, bci=46, server compiler)
    * org.apache.wicket.injection.Injector.inject (Injector.java:108,
bci=87, server compiler)
    * org.apache.wicket.injection.ConfigurableInjector.inject
(ConfigurableInjector.java:39, bci=6, server compiler)
    * org.apache.wicket.injection.ComponentInjector.onInstantiation
(ComponentInjector.java:52, bci=5, server compiler)
    * org.apache.wicket.Application.notifyComponentInstantiationListeners
(Application.java:974, bci=20, server compiler)
    * org.apache.wicket.Component.<init> (Component.java:873, bci=35, server
compiler)
    * org.apache.wicket.MarkupContainer.<init> (MarkupContainer.java:105,
bci=2, server compiler)
    * org.apache.wicket.markup.html.WebMarkupContainer.<init>
(WebMarkupContainer.java:39, bci=2, server compiler)
    *
org.apache.wicket.markup.html.WebMarkupContainerWithAssociatedMarkup.<init>
(WebMarkupContainerWithAssociatedMarkup.java:42, bci=2, server compiler)
    * org.apache.wicket.markup.html.panel.Panel.<init> (Panel.java:76,
bci=2, server compiler)
[...snip...]

I found that if we specified a name in @SpringBean (e.g. @SpringBean(name =
"foo")), then we would avoid this bottlenecking and our requests per second
improved 50-75%. It appears that the SpringBeanLocator.isSingletonBean()
call will do an expensive lookup of the bean name against
BeanFactoryUtils.beanNamesForTypeIncludingAncestors() if the name isn't
specified, even if the bean is already cached. By specifying the @SpringBean
name parameter, you avoid the lookup.

This feels like a bug, though I don't know who to should address it, Wicket
or Spring. Specifying a name in @SpringBean is optional, and the performance
gain of a cache lookup of already-injected beans is consequently defeated by
the isSingletonBean() call, which is called every single time a SpringBean
is injected. This implies Wicket should be addressing it. OTOH, Spring
BeanFactoryUtils.beanNamesForTypeIncludingAncestors() is clearly a
bottleneck if called too frequently, though when I've found performance
issues in Spring code (e.g. http://jira.springframework.org/browse/SPR-4505)
they've implied that Wicket should have better bean caching (though they've
fixed them anyway).

So.. how would one go about addressing this problem? It's a big performance
issue for those deploying a Wicket app using @SpringBean on multi-core
systems. I'm able to hack around it in our app, but not knowing much about
how Spring and Wicket should be interacting I'm not sure I can give an
educated guess.

Thanks,
leo
-- 
View this message in context: http://www.nabble.com/SpringBeanLocator-and-%40SpringBean-performance-issue-tp20964687p20964687.html
Sent from the Wicket - User mailing list archive at Nabble.com.


---------------------------------------------------------------------
To unsubscribe, e-mail: users-unsubscribe@wicket.apache.org
For additional commands, e-mail: users-help@wicket.apache.org


Re: SpringBeanLocator and @SpringBean performance issue

Posted by Igor Vaynberg <ig...@gmail.com>.
thanks for keeping us informed. like i said, if it takes too long we
can build a temp cache into wicket.

-igor

On Fri, Dec 12, 2008 at 4:21 PM, leok <le...@gmail.com> wrote:
>
> I went ahead and filed a bug with the Spring people:
> http://jira.springframework.org/browse/SPR-5360
>
>
> igor.vaynberg wrote:
>>
>> as far as i can see the problem is "on the other side of the fence".
>> applicationcontext has much better metadata about its beans then we do
>> so it should be cached there as it can be done so properly.
>>
>> if this is urgent we can build a temporary cache into
>> springbeanlocator, but its not the proper thing to do imho. if we
>> follow this logic then we can actually start caching bean references
>> as well and essentially build our own applicationcontext....
>>
>>
>> -igor
>>
>> On Thu, Dec 11, 2008 at 1:33 PM, leok <le...@gmail.com> wrote:
>>>
>>> Hello,
>>>
>>> Our Wicket app makes use of the @SpringBean annotation thorughout our
>>> code,
>>> which is a pretty cool feature. While checking some thread stack traces
>>> during load testing, we found lots of threads bottlenecking in the
>>> SpringBeanLocator class:
>>>
>>> Object blocked: 145.133 ms, Object wait: 0 ms, CPU wait: 2.118 ms, I/O
>>> wait:
>>> 9.017 ms, CPU: 73.847 ms
>>>
>>>    *
>>> org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton
>>> (DefaultSingletonBeanRegistry.java:180, bci=22, server compiler)
>>>          o blocked on java.util.concurrent.ConcurrentHashMap
>>> (0x000000cd67f9d170)
>>>    *
>>> org.springframework.beans.factory.support.AbstractBeanFactory.isTypeMatch
>>> (AbstractBeanFactory.java:415, bci=41, server compiler)
>>>    *
>>> org.springframework.beans.factory.support.DefaultListableBeanFactory.getBeanNamesForType
>>> (DefaultListableBeanFactory.java:223, bci=142, server compiler)
>>>    *
>>> org.springframework.beans.factory.support.DefaultListableBeanFactory.getBeanNamesForType
>>> (DefaultListableBeanFactory.java:202, bci=4, server compiler)
>>>    *
>>> org.springframework.context.support.AbstractApplicationContext.getBeanNamesForType
>>> (AbstractApplicationContext.java:933, bci=5, server compiler)
>>>    *
>>> org.springframework.beans.factory.BeanFactoryUtils.beanNamesForTypeIncludingAncestors
>>> (BeanFactoryUtils.java:143, bci=8, server compiler)
>>>    * org.apache.wicket.spring.SpringBeanLocator.getBeanNameOfClass
>>> (SpringBeanLocator.java:104, bci=2, server compiler)
>>>    * org.apache.wicket.spring.SpringBeanLocator.getBeanName
>>> (SpringBeanLocator.java:192, bci=29, server compiler)
>>>    * org.apache.wicket.spring.SpringBeanLocator.isSingletonBean
>>> (SpringBeanLocator.java:133, bci=13, server compiler)
>>>    *
>>> org.apache.wicket.spring.injection.annot.AnnotProxyFieldValueFactory.getFieldValue
>>> (AnnotProxyFieldValueFactory.java:90, bci=46, server compiler)
>>>    * org.apache.wicket.injection.Injector.inject (Injector.java:108,
>>> bci=87, server compiler)
>>>    * org.apache.wicket.injection.ConfigurableInjector.inject
>>> (ConfigurableInjector.java:39, bci=6, server compiler)
>>>    * org.apache.wicket.injection.ComponentInjector.onInstantiation
>>> (ComponentInjector.java:52, bci=5, server compiler)
>>>    * org.apache.wicket.Application.notifyComponentInstantiationListeners
>>> (Application.java:974, bci=20, server compiler)
>>>    * org.apache.wicket.Component.<init> (Component.java:873, bci=35,
>>> server
>>> compiler)
>>>    * org.apache.wicket.MarkupContainer.<init> (MarkupContainer.java:105,
>>> bci=2, server compiler)
>>>    * org.apache.wicket.markup.html.WebMarkupContainer.<init>
>>> (WebMarkupContainer.java:39, bci=2, server compiler)
>>>    *
>>> org.apache.wicket.markup.html.WebMarkupContainerWithAssociatedMarkup.<init>
>>> (WebMarkupContainerWithAssociatedMarkup.java:42, bci=2, server compiler)
>>>    * org.apache.wicket.markup.html.panel.Panel.<init> (Panel.java:76,
>>> bci=2, server compiler)
>>> [...snip...]
>>>
>>> I found that if we specified a name in @SpringBean (e.g. @SpringBean(name
>>> =
>>> "foo")), then we would avoid this bottlenecking and our requests per
>>> second
>>> improved 50-75%. It appears that the SpringBeanLocator.isSingletonBean()
>>> call will do an expensive lookup of the bean name against
>>> BeanFactoryUtils.beanNamesForTypeIncludingAncestors() if the name isn't
>>> specified, even if the bean is already cached. By specifying the
>>> @SpringBean
>>> name parameter, you avoid the lookup.
>>>
>>> This feels like a bug, though I don't know who to should address it,
>>> Wicket
>>> or Spring. Specifying a name in @SpringBean is optional, and the
>>> performance
>>> gain of a cache lookup of already-injected beans is consequently defeated
>>> by
>>> the isSingletonBean() call, which is called every single time a
>>> SpringBean
>>> is injected. This implies Wicket should be addressing it. OTOH, Spring
>>> BeanFactoryUtils.beanNamesForTypeIncludingAncestors() is clearly a
>>> bottleneck if called too frequently, though when I've found performance
>>> issues in Spring code (e.g.
>>> http://jira.springframework.org/browse/SPR-4505)
>>> they've implied that Wicket should have better bean caching (though
>>> they've
>>> fixed them anyway).
>>>
>>> So.. how would one go about addressing this problem? It's a big
>>> performance
>>> issue for those deploying a Wicket app using @SpringBean on multi-core
>>> systems. I'm able to hack around it in our app, but not knowing much
>>> about
>>> how Spring and Wicket should be interacting I'm not sure I can give an
>>> educated guess.
>>>
>>> Thanks,
>>> leo
>>> --
>>> View this message in context:
>>> http://www.nabble.com/SpringBeanLocator-and-%40SpringBean-performance-issue-tp20964687p20964687.html
>>> Sent from the Wicket - User mailing list archive at Nabble.com.
>>>
>>>
>>> ---------------------------------------------------------------------
>>> To unsubscribe, e-mail: users-unsubscribe@wicket.apache.org
>>> For additional commands, e-mail: users-help@wicket.apache.org
>>>
>>>
>>
>> ---------------------------------------------------------------------
>> To unsubscribe, e-mail: users-unsubscribe@wicket.apache.org
>> For additional commands, e-mail: users-help@wicket.apache.org
>>
>>
>>
>
> --
> View this message in context: http://www.nabble.com/SpringBeanLocator-and-%40SpringBean-performance-issue-tp20964687p20985895.html
> Sent from the Wicket - User mailing list archive at Nabble.com.
>
>
> ---------------------------------------------------------------------
> To unsubscribe, e-mail: users-unsubscribe@wicket.apache.org
> For additional commands, e-mail: users-help@wicket.apache.org
>
>

---------------------------------------------------------------------
To unsubscribe, e-mail: users-unsubscribe@wicket.apache.org
For additional commands, e-mail: users-help@wicket.apache.org


Re: SpringBeanLocator and @SpringBean performance issue

Posted by leok <le...@gmail.com>.
I went ahead and filed a bug with the Spring people:
http://jira.springframework.org/browse/SPR-5360


igor.vaynberg wrote:
> 
> as far as i can see the problem is "on the other side of the fence".
> applicationcontext has much better metadata about its beans then we do
> so it should be cached there as it can be done so properly.
> 
> if this is urgent we can build a temporary cache into
> springbeanlocator, but its not the proper thing to do imho. if we
> follow this logic then we can actually start caching bean references
> as well and essentially build our own applicationcontext....
> 
> 
> -igor
> 
> On Thu, Dec 11, 2008 at 1:33 PM, leok <le...@gmail.com> wrote:
>>
>> Hello,
>>
>> Our Wicket app makes use of the @SpringBean annotation thorughout our
>> code,
>> which is a pretty cool feature. While checking some thread stack traces
>> during load testing, we found lots of threads bottlenecking in the
>> SpringBeanLocator class:
>>
>> Object blocked: 145.133 ms, Object wait: 0 ms, CPU wait: 2.118 ms, I/O
>> wait:
>> 9.017 ms, CPU: 73.847 ms
>>
>>    *
>> org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton
>> (DefaultSingletonBeanRegistry.java:180, bci=22, server compiler)
>>          o blocked on java.util.concurrent.ConcurrentHashMap
>> (0x000000cd67f9d170)
>>    *
>> org.springframework.beans.factory.support.AbstractBeanFactory.isTypeMatch
>> (AbstractBeanFactory.java:415, bci=41, server compiler)
>>    *
>> org.springframework.beans.factory.support.DefaultListableBeanFactory.getBeanNamesForType
>> (DefaultListableBeanFactory.java:223, bci=142, server compiler)
>>    *
>> org.springframework.beans.factory.support.DefaultListableBeanFactory.getBeanNamesForType
>> (DefaultListableBeanFactory.java:202, bci=4, server compiler)
>>    *
>> org.springframework.context.support.AbstractApplicationContext.getBeanNamesForType
>> (AbstractApplicationContext.java:933, bci=5, server compiler)
>>    *
>> org.springframework.beans.factory.BeanFactoryUtils.beanNamesForTypeIncludingAncestors
>> (BeanFactoryUtils.java:143, bci=8, server compiler)
>>    * org.apache.wicket.spring.SpringBeanLocator.getBeanNameOfClass
>> (SpringBeanLocator.java:104, bci=2, server compiler)
>>    * org.apache.wicket.spring.SpringBeanLocator.getBeanName
>> (SpringBeanLocator.java:192, bci=29, server compiler)
>>    * org.apache.wicket.spring.SpringBeanLocator.isSingletonBean
>> (SpringBeanLocator.java:133, bci=13, server compiler)
>>    *
>> org.apache.wicket.spring.injection.annot.AnnotProxyFieldValueFactory.getFieldValue
>> (AnnotProxyFieldValueFactory.java:90, bci=46, server compiler)
>>    * org.apache.wicket.injection.Injector.inject (Injector.java:108,
>> bci=87, server compiler)
>>    * org.apache.wicket.injection.ConfigurableInjector.inject
>> (ConfigurableInjector.java:39, bci=6, server compiler)
>>    * org.apache.wicket.injection.ComponentInjector.onInstantiation
>> (ComponentInjector.java:52, bci=5, server compiler)
>>    * org.apache.wicket.Application.notifyComponentInstantiationListeners
>> (Application.java:974, bci=20, server compiler)
>>    * org.apache.wicket.Component.<init> (Component.java:873, bci=35,
>> server
>> compiler)
>>    * org.apache.wicket.MarkupContainer.<init> (MarkupContainer.java:105,
>> bci=2, server compiler)
>>    * org.apache.wicket.markup.html.WebMarkupContainer.<init>
>> (WebMarkupContainer.java:39, bci=2, server compiler)
>>    *
>> org.apache.wicket.markup.html.WebMarkupContainerWithAssociatedMarkup.<init>
>> (WebMarkupContainerWithAssociatedMarkup.java:42, bci=2, server compiler)
>>    * org.apache.wicket.markup.html.panel.Panel.<init> (Panel.java:76,
>> bci=2, server compiler)
>> [...snip...]
>>
>> I found that if we specified a name in @SpringBean (e.g. @SpringBean(name
>> =
>> "foo")), then we would avoid this bottlenecking and our requests per
>> second
>> improved 50-75%. It appears that the SpringBeanLocator.isSingletonBean()
>> call will do an expensive lookup of the bean name against
>> BeanFactoryUtils.beanNamesForTypeIncludingAncestors() if the name isn't
>> specified, even if the bean is already cached. By specifying the
>> @SpringBean
>> name parameter, you avoid the lookup.
>>
>> This feels like a bug, though I don't know who to should address it,
>> Wicket
>> or Spring. Specifying a name in @SpringBean is optional, and the
>> performance
>> gain of a cache lookup of already-injected beans is consequently defeated
>> by
>> the isSingletonBean() call, which is called every single time a
>> SpringBean
>> is injected. This implies Wicket should be addressing it. OTOH, Spring
>> BeanFactoryUtils.beanNamesForTypeIncludingAncestors() is clearly a
>> bottleneck if called too frequently, though when I've found performance
>> issues in Spring code (e.g.
>> http://jira.springframework.org/browse/SPR-4505)
>> they've implied that Wicket should have better bean caching (though
>> they've
>> fixed them anyway).
>>
>> So.. how would one go about addressing this problem? It's a big
>> performance
>> issue for those deploying a Wicket app using @SpringBean on multi-core
>> systems. I'm able to hack around it in our app, but not knowing much
>> about
>> how Spring and Wicket should be interacting I'm not sure I can give an
>> educated guess.
>>
>> Thanks,
>> leo
>> --
>> View this message in context:
>> http://www.nabble.com/SpringBeanLocator-and-%40SpringBean-performance-issue-tp20964687p20964687.html
>> Sent from the Wicket - User mailing list archive at Nabble.com.
>>
>>
>> ---------------------------------------------------------------------
>> To unsubscribe, e-mail: users-unsubscribe@wicket.apache.org
>> For additional commands, e-mail: users-help@wicket.apache.org
>>
>>
> 
> ---------------------------------------------------------------------
> To unsubscribe, e-mail: users-unsubscribe@wicket.apache.org
> For additional commands, e-mail: users-help@wicket.apache.org
> 
> 
> 

-- 
View this message in context: http://www.nabble.com/SpringBeanLocator-and-%40SpringBean-performance-issue-tp20964687p20985895.html
Sent from the Wicket - User mailing list archive at Nabble.com.


---------------------------------------------------------------------
To unsubscribe, e-mail: users-unsubscribe@wicket.apache.org
For additional commands, e-mail: users-help@wicket.apache.org


Re: SpringBeanLocator and @SpringBean performance issue

Posted by leok <le...@gmail.com>.
No, there's no rush here. We're able to hack around the problem effectively
in our own code. Thanks for your response!

leo


igor.vaynberg wrote:
> 
> as far as i can see the problem is "on the other side of the fence".
> applicationcontext has much better metadata about its beans then we do
> so it should be cached there as it can be done so properly.
> 
> if this is urgent we can build a temporary cache into
> springbeanlocator, but its not the proper thing to do imho. if we
> follow this logic then we can actually start caching bean references
> as well and essentially build our own applicationcontext....
> 
> 
> -igor
> 
> On Thu, Dec 11, 2008 at 1:33 PM, leok <le...@gmail.com> wrote:
>>
>> Hello,
>>
>> Our Wicket app makes use of the @SpringBean annotation thorughout our
>> code,
>> which is a pretty cool feature. While checking some thread stack traces
>> during load testing, we found lots of threads bottlenecking in the
>> SpringBeanLocator class:
>>
>> Object blocked: 145.133 ms, Object wait: 0 ms, CPU wait: 2.118 ms, I/O
>> wait:
>> 9.017 ms, CPU: 73.847 ms
>>
>>    *
>> org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton
>> (DefaultSingletonBeanRegistry.java:180, bci=22, server compiler)
>>          o blocked on java.util.concurrent.ConcurrentHashMap
>> (0x000000cd67f9d170)
>>    *
>> org.springframework.beans.factory.support.AbstractBeanFactory.isTypeMatch
>> (AbstractBeanFactory.java:415, bci=41, server compiler)
>>    *
>> org.springframework.beans.factory.support.DefaultListableBeanFactory.getBeanNamesForType
>> (DefaultListableBeanFactory.java:223, bci=142, server compiler)
>>    *
>> org.springframework.beans.factory.support.DefaultListableBeanFactory.getBeanNamesForType
>> (DefaultListableBeanFactory.java:202, bci=4, server compiler)
>>    *
>> org.springframework.context.support.AbstractApplicationContext.getBeanNamesForType
>> (AbstractApplicationContext.java:933, bci=5, server compiler)
>>    *
>> org.springframework.beans.factory.BeanFactoryUtils.beanNamesForTypeIncludingAncestors
>> (BeanFactoryUtils.java:143, bci=8, server compiler)
>>    * org.apache.wicket.spring.SpringBeanLocator.getBeanNameOfClass
>> (SpringBeanLocator.java:104, bci=2, server compiler)
>>    * org.apache.wicket.spring.SpringBeanLocator.getBeanName
>> (SpringBeanLocator.java:192, bci=29, server compiler)
>>    * org.apache.wicket.spring.SpringBeanLocator.isSingletonBean
>> (SpringBeanLocator.java:133, bci=13, server compiler)
>>    *
>> org.apache.wicket.spring.injection.annot.AnnotProxyFieldValueFactory.getFieldValue
>> (AnnotProxyFieldValueFactory.java:90, bci=46, server compiler)
>>    * org.apache.wicket.injection.Injector.inject (Injector.java:108,
>> bci=87, server compiler)
>>    * org.apache.wicket.injection.ConfigurableInjector.inject
>> (ConfigurableInjector.java:39, bci=6, server compiler)
>>    * org.apache.wicket.injection.ComponentInjector.onInstantiation
>> (ComponentInjector.java:52, bci=5, server compiler)
>>    * org.apache.wicket.Application.notifyComponentInstantiationListeners
>> (Application.java:974, bci=20, server compiler)
>>    * org.apache.wicket.Component.<init> (Component.java:873, bci=35,
>> server
>> compiler)
>>    * org.apache.wicket.MarkupContainer.<init> (MarkupContainer.java:105,
>> bci=2, server compiler)
>>    * org.apache.wicket.markup.html.WebMarkupContainer.<init>
>> (WebMarkupContainer.java:39, bci=2, server compiler)
>>    *
>> org.apache.wicket.markup.html.WebMarkupContainerWithAssociatedMarkup.<init>
>> (WebMarkupContainerWithAssociatedMarkup.java:42, bci=2, server compiler)
>>    * org.apache.wicket.markup.html.panel.Panel.<init> (Panel.java:76,
>> bci=2, server compiler)
>> [...snip...]
>>
>> I found that if we specified a name in @SpringBean (e.g. @SpringBean(name
>> =
>> "foo")), then we would avoid this bottlenecking and our requests per
>> second
>> improved 50-75%. It appears that the SpringBeanLocator.isSingletonBean()
>> call will do an expensive lookup of the bean name against
>> BeanFactoryUtils.beanNamesForTypeIncludingAncestors() if the name isn't
>> specified, even if the bean is already cached. By specifying the
>> @SpringBean
>> name parameter, you avoid the lookup.
>>
>> This feels like a bug, though I don't know who to should address it,
>> Wicket
>> or Spring. Specifying a name in @SpringBean is optional, and the
>> performance
>> gain of a cache lookup of already-injected beans is consequently defeated
>> by
>> the isSingletonBean() call, which is called every single time a
>> SpringBean
>> is injected. This implies Wicket should be addressing it. OTOH, Spring
>> BeanFactoryUtils.beanNamesForTypeIncludingAncestors() is clearly a
>> bottleneck if called too frequently, though when I've found performance
>> issues in Spring code (e.g.
>> http://jira.springframework.org/browse/SPR-4505)
>> they've implied that Wicket should have better bean caching (though
>> they've
>> fixed them anyway).
>>
>> So.. how would one go about addressing this problem? It's a big
>> performance
>> issue for those deploying a Wicket app using @SpringBean on multi-core
>> systems. I'm able to hack around it in our app, but not knowing much
>> about
>> how Spring and Wicket should be interacting I'm not sure I can give an
>> educated guess.
>>
>> Thanks,
>> leo
>> --
>> View this message in context:
>> http://www.nabble.com/SpringBeanLocator-and-%40SpringBean-performance-issue-tp20964687p20964687.html
>> Sent from the Wicket - User mailing list archive at Nabble.com.
>>
>>
>> ---------------------------------------------------------------------
>> To unsubscribe, e-mail: users-unsubscribe@wicket.apache.org
>> For additional commands, e-mail: users-help@wicket.apache.org
>>
>>
> 
> ---------------------------------------------------------------------
> To unsubscribe, e-mail: users-unsubscribe@wicket.apache.org
> For additional commands, e-mail: users-help@wicket.apache.org
> 
> 
> 

-- 
View this message in context: http://www.nabble.com/SpringBeanLocator-and-%40SpringBean-performance-issue-tp20964687p20979661.html
Sent from the Wicket - User mailing list archive at Nabble.com.


---------------------------------------------------------------------
To unsubscribe, e-mail: users-unsubscribe@wicket.apache.org
For additional commands, e-mail: users-help@wicket.apache.org


Re: SpringBeanLocator and @SpringBean performance issue

Posted by Igor Vaynberg <ig...@gmail.com>.
as far as i can see the problem is "on the other side of the fence".
applicationcontext has much better metadata about its beans then we do
so it should be cached there as it can be done so properly.

if this is urgent we can build a temporary cache into
springbeanlocator, but its not the proper thing to do imho. if we
follow this logic then we can actually start caching bean references
as well and essentially build our own applicationcontext....


-igor

On Thu, Dec 11, 2008 at 1:33 PM, leok <le...@gmail.com> wrote:
>
> Hello,
>
> Our Wicket app makes use of the @SpringBean annotation thorughout our code,
> which is a pretty cool feature. While checking some thread stack traces
> during load testing, we found lots of threads bottlenecking in the
> SpringBeanLocator class:
>
> Object blocked: 145.133 ms, Object wait: 0 ms, CPU wait: 2.118 ms, I/O wait:
> 9.017 ms, CPU: 73.847 ms
>
>    *
> org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton
> (DefaultSingletonBeanRegistry.java:180, bci=22, server compiler)
>          o blocked on java.util.concurrent.ConcurrentHashMap
> (0x000000cd67f9d170)
>    *
> org.springframework.beans.factory.support.AbstractBeanFactory.isTypeMatch
> (AbstractBeanFactory.java:415, bci=41, server compiler)
>    *
> org.springframework.beans.factory.support.DefaultListableBeanFactory.getBeanNamesForType
> (DefaultListableBeanFactory.java:223, bci=142, server compiler)
>    *
> org.springframework.beans.factory.support.DefaultListableBeanFactory.getBeanNamesForType
> (DefaultListableBeanFactory.java:202, bci=4, server compiler)
>    *
> org.springframework.context.support.AbstractApplicationContext.getBeanNamesForType
> (AbstractApplicationContext.java:933, bci=5, server compiler)
>    *
> org.springframework.beans.factory.BeanFactoryUtils.beanNamesForTypeIncludingAncestors
> (BeanFactoryUtils.java:143, bci=8, server compiler)
>    * org.apache.wicket.spring.SpringBeanLocator.getBeanNameOfClass
> (SpringBeanLocator.java:104, bci=2, server compiler)
>    * org.apache.wicket.spring.SpringBeanLocator.getBeanName
> (SpringBeanLocator.java:192, bci=29, server compiler)
>    * org.apache.wicket.spring.SpringBeanLocator.isSingletonBean
> (SpringBeanLocator.java:133, bci=13, server compiler)
>    *
> org.apache.wicket.spring.injection.annot.AnnotProxyFieldValueFactory.getFieldValue
> (AnnotProxyFieldValueFactory.java:90, bci=46, server compiler)
>    * org.apache.wicket.injection.Injector.inject (Injector.java:108,
> bci=87, server compiler)
>    * org.apache.wicket.injection.ConfigurableInjector.inject
> (ConfigurableInjector.java:39, bci=6, server compiler)
>    * org.apache.wicket.injection.ComponentInjector.onInstantiation
> (ComponentInjector.java:52, bci=5, server compiler)
>    * org.apache.wicket.Application.notifyComponentInstantiationListeners
> (Application.java:974, bci=20, server compiler)
>    * org.apache.wicket.Component.<init> (Component.java:873, bci=35, server
> compiler)
>    * org.apache.wicket.MarkupContainer.<init> (MarkupContainer.java:105,
> bci=2, server compiler)
>    * org.apache.wicket.markup.html.WebMarkupContainer.<init>
> (WebMarkupContainer.java:39, bci=2, server compiler)
>    *
> org.apache.wicket.markup.html.WebMarkupContainerWithAssociatedMarkup.<init>
> (WebMarkupContainerWithAssociatedMarkup.java:42, bci=2, server compiler)
>    * org.apache.wicket.markup.html.panel.Panel.<init> (Panel.java:76,
> bci=2, server compiler)
> [...snip...]
>
> I found that if we specified a name in @SpringBean (e.g. @SpringBean(name =
> "foo")), then we would avoid this bottlenecking and our requests per second
> improved 50-75%. It appears that the SpringBeanLocator.isSingletonBean()
> call will do an expensive lookup of the bean name against
> BeanFactoryUtils.beanNamesForTypeIncludingAncestors() if the name isn't
> specified, even if the bean is already cached. By specifying the @SpringBean
> name parameter, you avoid the lookup.
>
> This feels like a bug, though I don't know who to should address it, Wicket
> or Spring. Specifying a name in @SpringBean is optional, and the performance
> gain of a cache lookup of already-injected beans is consequently defeated by
> the isSingletonBean() call, which is called every single time a SpringBean
> is injected. This implies Wicket should be addressing it. OTOH, Spring
> BeanFactoryUtils.beanNamesForTypeIncludingAncestors() is clearly a
> bottleneck if called too frequently, though when I've found performance
> issues in Spring code (e.g. http://jira.springframework.org/browse/SPR-4505)
> they've implied that Wicket should have better bean caching (though they've
> fixed them anyway).
>
> So.. how would one go about addressing this problem? It's a big performance
> issue for those deploying a Wicket app using @SpringBean on multi-core
> systems. I'm able to hack around it in our app, but not knowing much about
> how Spring and Wicket should be interacting I'm not sure I can give an
> educated guess.
>
> Thanks,
> leo
> --
> View this message in context: http://www.nabble.com/SpringBeanLocator-and-%40SpringBean-performance-issue-tp20964687p20964687.html
> Sent from the Wicket - User mailing list archive at Nabble.com.
>
>
> ---------------------------------------------------------------------
> To unsubscribe, e-mail: users-unsubscribe@wicket.apache.org
> For additional commands, e-mail: users-help@wicket.apache.org
>
>

---------------------------------------------------------------------
To unsubscribe, e-mail: users-unsubscribe@wicket.apache.org
For additional commands, e-mail: users-help@wicket.apache.org