Hi Simon, I would say your assessment is correct. If this is slow, how about caching the connection of bean-name - scope-name somewhere?
regards, Martin On 8/12/07, simon <[EMAIL PROTECTED]> wrote: > Hi, > > I've been looking at how Spring implements its custom scopes feature, > and how this interacts with JSF. > > Can someone verify that I understand this right? > > The class org.springframework.web.jsf.DelegatingVariableResolver is > configured as the var-resolver for a JSF webapp, via faces-config.xml. > > This class first delegates to the standard JSF var-resolver, which > directly looks in request, session and app scopes for the name. If it > finds the var, it just returns - this is pretty quick. If it fails, it > looks in its config for the name, and if found then it creates the bean, > adds it to the scope and returns - again fairly quick. > > If this process fails (ie bean not in request, session or app scope and > no definition in the standard JSF manner) then > DelegatingVariableResolver calls > org.springframework.beans.factory.support.AbstractBeanFactory.getBean(...). > > This code first checks its singleton cache. If it doesn't find an > already-created bean there then it looks up its bean definition. > * If the type is "singleton" then it creates a new instance, puts it in > the singleton cache then returns. > * If the type is "prototype" then it creates a new instance, and returns > it without caching it anywhere. > * If the type is a custom scope then it finds the appropriate registered > scope-handler and invokes its get method, passing an ObjectFactory > object that knows how to create an instance from the bean definition it > has already located. > > For the request and session scopes, the scope-handlers first look in the > request or session - but will never find anything, otherwise the JSF > var-resolver would have found it earlier. So they use the ObjectFactory > to create the bean and store it in the request/session. On later > attempts by JSF to look up this bean, the standard JSF var-resolver will > find it immediately in the request/session which is nice and efficient. > > For the "conversation" scope, however, things are not so efficient. The > JSF variable resolver will never find the bean in request/session. The > AbstractBeanFactory.getBean method will not find the object in the > singleton cache either. It will therefore have to locate the bean > definition, then invoke the > o.a.m.orchestra.conversation.spring.SpringConversationScope.get method. > This method locates the spring bean definition *again* in order to find > the conversation name, then retrieves the current ConversationContext, > from that the right conversation, and then from the conversation the > actual bean. When the bean already exists, it is then returned and > otherwise it is created and added to the conversation. > > This does seem a pretty slow process to go through for every EL > reference to a conversation-scoped bean. > > I don't mean to criticise, and I certainly don't have any optimisations > to suggest ATM; I would just like to know if I've understood this right, > or whether I have missed something that optimises access to > conversation-scoped beans. It seems to me that: > * access to Prototypes can't really be optimised as they are created > each time by definition > * access to Singletons is efficient as they are cached > * access to request/session vars is not very good when using Spring > alone, but because the JSF var-resolver looks into request and session > objects this allows the objects to be retrieved without passing through > spring at all. > * access to conversation vars is going to be slow because every lookup > requires a pass through Spring, resulting in quite a lot of processing - > including lookup of the bean def, which can be quite complicated. > > Regards, > > Simon > > -- http://www.irian.at Your JSF powerhouse - JSF Consulting, Development and Courses in English and German Professional Support for Apache MyFaces