Page 1 of 2 12 LastLast
Results 1 to 10 of 14

Thread: JSF - Spring: Cannot instantiate Spring bean

  1. #1

    Default JSF - Spring: Cannot instantiate Spring bean

    I try to use a Spring bean inside JSF. I get the following error:

    2007-01-30 16:08:43,185 DEBUG [com.sun.faces.el.ValueBindingImpl] - getValue(ref=cmdQueueInBean.name)
    2007-01-30 16:08:43,185 DEBUG [org.springframework.web.jsf.DelegatingVariableReso lver] - Attempting to resolve variable 'cmdQueueInBean' in via original VariableResolver
    Backing bean created
    2007-01-30 16:08:43,201 DEBUG [com.sun.faces.application.ApplicationImpl] - Expression cmdQueueInDAO passed syntax check
    2007-01-30 16:08:43,201 DEBUG [com.sun.faces.el.ValueBindingImpl] - getValue(ref=cmdQueueInDAO)
    2007-01-30 16:08:43,201 DEBUG [org.springframework.web.jsf.DelegatingVariableReso lver] - Attempting to resolve variable 'cmdQueueInDAO' in via original VariableResolver
    2007-01-30 16:08:43,201 DEBUG [com.sun.faces.application.ApplicationImpl] - Couldn't find a factory for cmdQueueInDAO
    2007-01-30 16:08:43,216 DEBUG [com.sun.faces.el.VariableResolverImpl] - resolveVariable: Resolved variable:null
    2007-01-30 16:08:43,216 DEBUG [org.springframework.web.jsf.DelegatingVariableReso lver] - Attempting to resolve variable 'cmdQueueInDAO' in root WebApplicationContext
    2007-01-30 16:08:43,216 DEBUG [org.springframework.web.jsf.DelegatingVariableReso lver] - Successfully resolved variable 'cmdQueueInDAO' in root WebApplicationContext
    2007-01-30 16:08:43,216 DEBUG [org.springframework.beans.factory.support.DefaultL istableBeanFactory] - Returning cached instance of singleton bean 'cmdQueueInDAO'
    2007-01-30 16:08:43,216 DEBUG [com.sun.faces.el.ValueBindingImpl] - getValue Result:com.trixpert.dao.CmdQueueInDAOImpl@174e4b3
    2007-01-30 16:08:43,216 DEBUG [com.sun.faces.el.ValueBindingImpl] - -->Returning com.trixpert.dao.CmdQueueInDAOImpl@174e4b3
    2007-01-30 16:08:43,263 ERROR [com.sun.faces.application.ApplicationImpl] - Managedbean cmdQueueInBean could not be created Can't instantiate class: 'com.trixpert.dao.CmdQueueInDAOImpl@174e4b3'.
    javax.faces.FacesException: Can't instantiate class: 'com.trixpert.dao.CmdQueueInDAOImpl@174e4b3'.
    at com.sun.faces.config.ManagedBeanFactory.getConvert edValueConsideringPrimitives(ManagedBeanFactory.ja va:869)
    at com.sun.faces.config.ManagedBeanFactory.setPropert iesIntoBean(ManagedBeanFactory.java:555)
    at com.sun.faces.config.ManagedBeanFactory.newInstanc e(ManagedBeanFactory.java:233)
    at com.sun.faces.application.ApplicationAssociate.cre ateAndMaybeStoreManagedBeans(ApplicationAssociate. java:256)
    at com.sun.faces.el.VariableResolverImpl.resolveVaria ble(VariableResolverImpl.java:78)
    at org.springframework.web.jsf.DelegatingVariableReso lver.resolveVariable(DelegatingVariableResolver.ja va:108)
    at com.sun.faces.el.impl.NamedValue.evaluate(NamedVal ue.java:125)
    at com.sun.faces.el.impl.ComplexValue.evaluate(Comple xValue.java:146)
    at com.sun.faces.el.impl.ExpressionEvaluatorImpl.eval uate(ExpressionEvaluatorImpl.java:243)
    at com.sun.faces.el.ValueBindingImpl.getValue(ValueBi ndingImpl.java:173)
    I defined in my applicationContext.xml:

    Code:
    <bean id="cmdQueueInDAO" class="com.trixpert.dao.CmdQueueInDAOImpl" />
    and in faces-config.xml:

    Code:
     <managed-bean>
      <managed-bean-name>cmdQueueInBean</managed-bean-name>
      <managed-bean-class>com.trixpert.web.CmdQueueInBean</managed-bean-class>
      <managed-bean-scope>request</managed-bean-scope>
      <managed-property>
       <property-name>name</property-name>
       <property-class>java.lang.String</property-class>
       <value/>
      </managed-property>
      <managed-property>
       <property-name>cmdQueueInDAO</property-name>
       <property-class>com.trixpert.dao.CmdQueueInDAOImpl</property-class>
       <value>#{cmdQueueInDAO}</value>
      </managed-property>
     </managed-bean>
    
     <application>
      <variable-resolver>org.springframework.web.jsf.DelegatingVariableResolver</variable-resolver>
     </application>
    My JSF Managed Bean is:

    Code:
    public class CmdQueueInBean
    {
        private java.lang.String name;
        private CmdQueueInDAOImpl cmdQueueInDAO;
    
        public CmdQueueInBean()
        {
            System.out.println("Backing bean created");
        }
    
        public java.lang.String getName()
        {
            return name;
        }
    
        public void setName(java.lang.String name)
        {
            this.name = name;
        }
    
        public CmdQueueInDAOImpl getCmdQueueInDAO()
        {
            return cmdQueueInDAO;
        }
    
        public void setCmdQueueInDAO(CmdQueueInDAOImpl cmdQueueInDAO)
        {
            this.cmdQueueInDAO = cmdQueueInDAO;
        }
        
        public List<CmdQueueIn> getCommandsForUser()
        {
            long MLUserID = Long.parseLong(name);
            return this.cmdQueueInDAO.findByMLUser(MLUserID);
        }
    }
    And the CmdQueueInDAOImpl class looks as follows (extract)


    Code:
    @Repository
    public class CmdQueueInDAOImpl implements ICmdQueueInDAO
    {
        @PersistenceContext
        private EntityManager em;
       
        /** Creates a new instance of CmdQueueInDAOImpl */
        public CmdQueueInDAOImpl() 
        {
           
        } 
        
        public List<CmdQueueIn> findByMLUser(long mLUser)
        {
            Query query = em.createNamedQuery("CmdQueueIn.findByMLUser");
            query.setParameter("mLUser", mLUser);
            return query.getResultList();
        }
    
        ......
    }
    The stacktrace shows that it is using org.springframework.web.jsf.DelegatingVariableReso lver, but it cannot be created. Does it require a special constructor? Any idea why cmdQueueInDAO cannot be instanciated?

    Tom

  2. #2
    Join Date
    Jun 2005
    Posts
    4,230

    Default

    What version of the JSF RI are you using (it might be worth trying a newer one)? It looks from the stack trace as though maybe JSF is trying to create a DaoImpl with a String valued constructor argument (this is not unlike what it often does with other object creation requirements). I think the JSF object creation model is pretty weak compared to Spring's, so you would be better off in any case with a managed bean that was a Spring bean with scope="request", rather than using faces-config at all for this.

    By the way, you really ought to code your service to the interface not the implementation of the Dao - that way it is more testable.
    Last edited by Dave Syer; Jan 31st, 2007 at 01:33 AM.

  3. #3
    Join Date
    Jan 2007
    Location
    Kuala Lumpur, Malaysia
    Posts
    138

    Default

    i think that the bean 'cmdQueueInDAO' is not a 'com.trixpert.dao.CmdQueueInDAOImpl' but a proxy of 'ICmdQueueInDAO'.
    like david_syer said, use the interface.
    i think the variable is resolved properly.'
    Code:
    2007-01-30 16:08:43,216 DEBUG [org.springframework.web.jsf.DelegatingVariableResolver] - Successfully resolved variable 'cmdQueueInDAO' in root WebApplicationContext
    i think you are using AOP and the AOP proxied the instance of the com.trixpert.dao.CmdQueueInDAOImpl.

    for a quickfix
    i suggest
    changing
    Code:
    private CmdQueueInDAOImpl cmdQueueInDAO;
    .
    .
    
        public void setCmdQueueInDAO(CmdQueueInDAOImpl cmdQueueInDAO)
        {
            this.cmdQueueInDAO = cmdQueueInDAO;
        }
    to
    Code:
    private ICmdQueueInDAO cmdQueueInDAO;
    .
    .
        public void setCmdQueueInDAO(ICmdQueueInDAO cmdQueueInDAO)
        {
            this.cmdQueueInDAO = cmdQueueInDAO;
        }
    and modify the jsf managed-bean's property-class to point to the interface.

    or.....

    you could use
    the proxyTargetClass feature
    i think it requires cglib...

  4. #4

    Default

    Quote Originally Posted by david_syer View Post
    What version of the JSF RI are you using (it might be worth trying a newer one)? It looks from the stack trace as though maybe JSF is trying to create a DaoImpl with a String valued constructor argument (this is not unlike what it often does with other object creation requirements). I think the JSF object creation model is pretty weak compared to Spring's, so you would be better off in any case with a managed bean that was a Spring bean with scope="request", rather than using faces-config at all for this.

    By the way, you really ought to code your service to the interface not the implementation of the Dao - that way it is more testable.
    Hello David,

    Thanks for that feedback. I use currently Eclipse with a Exadel Studio Test version. It is using JSF 1.1.01 RI. I think the only newer version is JSF 1.2 but thats a new spec and I don't know, if all tools I use already support 1.2 (including Spring)!

    I am definitely not so happy with the development environment. I miss a RAD tool for the GUI part. But thats a different story!

    What you say about the object creation is very interesting. I think JSF is closely bound to the web. Whatever you enter in the browser is always a string and you need to convert it then to other objects. It works for a Long or Integer or Date but is really difficult for a complex DAO!

    By suggesting NOT to use faces-config do you mean to define all managed beans as Spring beans?? Clearly: instead of:


    Code:
     <managed-bean>
      <managed-bean-name>cmdQueueInBean</managed-bean-name>
      <managed-bean-class>com.trixpert.web.CmdQueueInBean</managed-bean-class>
      <managed-bean-scope>request</managed-bean-scope>
      <managed-property>
       <property-name>name</property-name>
       <property-class>java.lang.String</property-class>
       <value/>
      </managed-property>
      <managed-property>
       <property-name>cmdQueueInDAO</property-name>
       <value>#{cmdQueueInDAO}</value>
      </managed-property>
     </managed-bean>
    in faces-config.xml I would have:

    Code:
        <bean id="cmdQueueInBean" class="com.trixpert.web.CmdQueueInBean" scope="request">
            <property name="name" value="" />
            <property name="cmdQueueInDAO" ref="cmdQueueInDAO" />
        </bean>
    in lets say applicationConext.xml?? The Java code of 'cmdQueueInBean' would be exactly the same as if it were defined in faces-config.xml? There would be NO managed bean definitions anymore in faces-config.xml? Am I getting this right???

    Regarding the Interface I agree. I will change that and see if I can get it working.

    Many thanks for your help.

    Thomas

  5. #5
    Join Date
    Jun 2005
    Posts
    4,230

    Default

    Quote Originally Posted by tbednarz View Post
    The Java code of 'cmdQueueInBean' would be exactly the same as if it were defined in faces-config.xml? There would be NO managed bean definitions anymore in faces-config.xml? Am I getting this right???
    Yes. It's much nicer to use Spring (which incidentally also has to convert from String to complex objects and just works a little harder than JSF).

  6. #6

    Default

    OK I changed my code and configuration. It brought me a bit further, but the app is still crashing!!

    First a general question:

    If I have in my backing bean (which is a Spring Bean now):

    Code:
    public class CmdQueueInBean
    {
        private java.lang.String name;
        private ICmdQueueInDAO cmdQueueInDAO;
    
        public List<CmdQueueIn> getCommandsForUser()
        {
            long MLUserID = Long.parseLong(name);
            return this.cmdQueueInDAO.findByMLUser(MLUserID);
        }
    
       ....
    
    }
    Is it possible to do the following in a JSF page:


    Code:
        <h:dataTable var="rowCmdQueueIn" border="1" rowClasses="RowOdd,RowEven"
            headerClass="Heading" value="#{cmdQueueInBean.commandsForUser}">
            <h:column>
                <f:facet name="header">
                    <f:verbatim>Command ID:</f:verbatim>
                </f:facet>
                <h:outputText value="#{rowCmdQueueIn.cmdQueueInId}" />
            </h:column>
            <h:column>
                <f:facet name="header">
                    <f:verbatim>Command</f:verbatim>
                </f:facet>
                <h:outputText value="#{rowCmdQueueIn.cmd}" />
            </h:column>
        </h:dataTable>
    The idea is, that the expression #{cmdQueueInBean.commandsForUser} calls the method getCommandForUser() of my bean.

    When I try that I always get the following exception:

    2007-01-31 14:29:11,057 DEBUG [com.sun.faces.el.ValueBindingImpl] - getValue(ref=cmdQueueInBean.commandsForUser)
    2007-01-31 14:29:11,057 DEBUG [org.springframework.web.jsf.DelegatingVariableReso lver] - Attempting to resolve variable 'cmdQueueInBean' in via original VariableResolver
    2007-01-31 14:29:11,057 DEBUG [com.sun.faces.el.VariableResolverImpl] - resolveVariable: Resolved variable:com.trixpert.web.CmdQueueInBean@124bd93
    2007-01-31 14:29:11,057 DEBUG [javax.faces.el.PropertyResolver] - Error getting property 'commandsForUser' from bean of type com.trixpert.web.CmdQueueInBean
    2007-01-31 14:29:11,088 DEBUG [com.sun.faces.el.ValueBindingImpl] - getValue Evaluation threw exception:
    javax.faces.el.PropertyNotFoundException: Error getting property 'commandsForUser' from bean of type com.trixpert.web.CmdQueueInBean
    at com.sun.faces.el.PropertyResolverImpl.getValue(Pro pertyResolverImpl.java:107)
    at com.sun.faces.el.impl.ArraySuffix.evaluate(ArraySu ffix.java:167)
    at com.sun.faces.el.impl.ComplexValue.evaluate(Comple xValue.java:151)
    at com.sun.faces.el.impl.ExpressionEvaluatorImpl.eval uate(ExpressionEvaluatorImpl.java:243)
    at com.sun.faces.el.ValueBindingImpl.getValue(ValueBi ndingImpl.java:173)
    at com.sun.faces.el.ValueBindingImpl.getValue(ValueBi ndingImpl.java:154)
    The question is:

    Is my EL wrong or does it not find it because of a Spring issue. I use JSF 1.1.01.

    Many thanks

    Tom

  7. #7
    Join Date
    Jan 2007
    Location
    Kuala Lumpur, Malaysia
    Posts
    138

    Default

    CmdQueueInBean
    getCommandForUser
    commandsForUser

    try this
    Code:
    <h:dataTable var="rowCmdQueueIn" border="1" rowClasses="RowOdd,RowEven"
            headerClass="Heading" value="#{cmdQueueInBean.commandForUser}">
    i think you made a little typo.

  8. #8

    Default

    Hello titiwangsa,

    Thanks for your feedback. I do not understand what you mean by typo. I changed my code, all managed beans are now in my applicationContext.xml as Spring beans:

    Code:
        <bean id="cmdQueueInDAO" class="com.trixpert.dao.CmdQueueInDAOImpl" />
        
        <bean id="cmdQueueInBean" class="com.trixpert.web.CmdQueueInBean" scope="request">
            <property name="userID" value="Please enter a User ID" />
            <property name="cmdQueueInDAO" ref="cmdQueueInDAO"></property>
        </bean>
    Quote Originally Posted by titiwangsa View Post
    CmdQueueInBean
    getCommandForUser
    commandsForUser

    try this
    Code:
    <h:dataTable var="rowCmdQueueIn" border="1" rowClasses="RowOdd,RowEven"
            headerClass="Heading" value="#{cmdQueueInBean.commandForUser}">
    i think you made a little typo.

    Am I wrong with:

    The backing bean com.trixpert.web.CmdQueueInBean named cmdQueueInBean in applicationContext.xml is being accessed from within the EL as #{cmdQueueInBean} and the method
    Code:
        public List<CmdQueueIn> getCommandsForUser()
        {
            long MLUserID = Long.parseLong(userID);
                    
            return cmdQueueInDAO.findByMLUser(MLUserID);
        }
    defined in CmdQueueInBean class will become commandsForUser (like a property) in Expression Language?

    I still do not know what is wrong! I debugged the code and set a breakpoint in the above method getCommandsForUser() which is also hit. I can see, that a connection to the database is successfully made to retrieve all objects:

    [TopLink Config]: 2007.02.02 06:54:17.801--ServerSession(30352443)--Connection(27193209)--Thread(Thread[http-8080-Processor24,5,main])--Connected: jdbc:odbc:dsn=mtracker_db1
    User: WebServer
    Database: Adaptive Server Anywhere Version: 9.0.2.3361
    Driver: DBODBC9.DLL Version: 09.00.0002
    [TopLink Info]: 2007.02.02 06:54:17.879--ServerSession(30352443)--Thread(Thread[http-8080-Processor24,5,main])--file:/D:/Projects/Eclipse32/.metadata/.plugins/org.eclipse.wst.server.core/tmp0/webapps/test/WEB-INF/classes/-testPU login successful


    But I cannot step inside my method 'findByMLUser(...)' inside my DAO object. There I get the following exception before it enters the function:

    2007-02-02 06:54:18,129 DEBUG [javax.faces.el.PropertyResolver] - Error getting property 'commandsForUser' from bean of type com.trixpert.web.CmdQueueInBean: java.lang.NullPointerException
    java.lang.NullPointerException
    at oracle.toplink.essentials.internal.ejb.cmp3.base.E ntityManagerImpl.getActivePersistenceContext(Entit yManagerImpl.java:533)
    at oracle.toplink.essentials.internal.ejb.cmp3.base.E ntityManagerImpl.getActiveSession(EntityManagerImp l.java:404)
    at oracle.toplink.essentials.internal.ejb.cmp3.base.E JBQueryImpl.getActiveSession(EJBQueryImpl.java:651 )
    at oracle.toplink.essentials.internal.ejb.cmp3.base.E JBQueryImpl.getDatabaseQuery(EJBQueryImpl.java:383 )
    at oracle.toplink.essentials.internal.ejb.cmp3.base.E JBQueryImpl.setParameterInternal(EJBQueryImpl.java :611)
    at oracle.toplink.essentials.internal.ejb.cmp3.EJBQue ryImpl.setParameter(EJBQueryImpl.java:161)
    at com.trixpert.dao.CmdQueueInDAOImpl.findByMLUser(Cm dQueueInDAOImpl.java:101)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Nativ e Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(Native MethodAccessorImpl.java:39)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(De legatingMethodAccessorImpl.java:25)
    When looking at the variables in the debugger I see proxy objects. I don't know if this is sort of reason for my problem. But the exception is thrown by the EL propertyResolver. So it looks to me like the method cannot be found. This is what I do not understand!

    Tom



  9. #9
    Join Date
    Jan 2007
    Location
    Kuala Lumpur, Malaysia
    Posts
    138

    Default

    i'm just guessing here..
    but could it be that there is no
    "getCommandsForUser()" function in your interface?

  10. #10

    Default

    Yes thats correct but why should I need that? getCommandsForUser() is a member of the backing bean. The interface is my DAO class.

    When I step through the code with the debugger. It first goes through getCommandsForUser() in my backing bean:


    Code:
        
    public List<CmdQueueIn> getCommandsForUser()
        {
            long MLUserID = Long.parseLong(userID);
                    
            return cmdQueueInDAO.findByMLUser(MLUserID);
        }
    I can also step through 'findByMLUser(MLUserID)' (which is defined in my interface):


    Code:
        public List<CmdQueueIn> findByMLUserAndExecutionTime(long mLUser, Date startDate, Date endDate)
        {
            Query query = em.createNamedQuery("CmdQueueIn.findByMLUserAndExecutionTime");
            query.setParameter("mLUser", mLUser);
            query.setParameter("startDate", startDate, TemporalType.TIMESTAMP);
            query.setParameter("endDate", endDate,  TemporalType.TIMESTAMP);
            return query.getResultList();
        }
    It successfully creates a Query instance from the EntityManager (em) but the call to query.setParameter(..) crashes. I need to get the source of all the libraries but it asks for AopUtils.java.

    I really do NOT understand why it does Aop when setting a query parameter. But I am new to spring and therefore do not yet see what is behind the scene.

    Tom

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •