Announcement Announcement Module
Collapse
No announcement yet.
org.springframework.beans.BeanInstantiationExcepti on Page Title Module
Move Remove Collapse
X
Conversation Detail Module
Collapse
  • Filter
  • Time
  • Show
Clear All
new posts

  • org.springframework.beans.BeanInstantiationExcepti on

    Hi,

    I am trying to use "spring mobile" but I am having little success so far.

    I have made the following changes to my exisiting Spring 3.0 MVC project.

    POM - move

    spring-orm
    spring-context
    spring-beans
    spring-core
    spring-webmvc
    spring-web
    spring-jdbc
    spring-context-support

    org.springframework dependancies to 3.1.0.M1.


    change:

    Code:
    <?xml version="1.0" encoding="UTF-8" ?>
    <beans xmlns="http://www.springframework.org/schema/beans" 
           xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
           xmlns:mvc="http://www.springframework.org/schema/mvc" 
           xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.0.xsd http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc-3.0.xsd">
           
    <!--  Configures the @Controller programming model 
      --> 
      <mvc:annotation-driven />
        
    </beans>
    to

    Code:
    <?xml version="1.0" encoding="UTF-8" ?>
    <beans xmlns="http://www.springframework.org/schema/beans" 
           xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
           xmlns:mvc="http://www.springframework.org/schema/mvc" 
           xmlns:device="http://www.springframework.org/schema/mobile/device"  
           xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.1.xsd http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc-3.1.xsd http://www.springframework.org/schema/mobile/device http://www.springframework.org/schema/mobile/device/spring-mobile-device-1.0.xsd">
           <!--  When went to Spring 3.1 change line above to 3.1 -->
           
    <!--  Configures the @Controller programming model --> 
      <mvc:annotation-driven>
         <mvc:argument-resolvers>
            <bean class="org.springframework.mobile.device.DeviceWebArgumentResolver" />
         </mvc:argument-resolvers>
       </mvc:annotation-driven>
       
      <mvc:interceptors>
         <!-- On pre-handle, resolve the device that originated the web request -->
         <bean class="org.springframework.mobile.device.DeviceResolverHandlerInterceptor" />
      </mvc:interceptors>
     		
    </beans>
    In my controller I am trying to bind 'Device'

    Code:
     public String showUserPage(Principal principal,
    		@RequestParam(value="userid") Long userid,
                                 ModelMap model,
                                 Device device){

    but I am getting the following exception.

    org.springframework.beans.BeanInstantiationExcepti on: Could not instantiate bean class [org.springframework.mobile.device.Device]: Specified class is an interface


    Any help greatly appreciated.

  • #2
    Hmm. for some reason it seems the DeviceWebArgumentResolver is not getting picked up. Make sure you don't have any other AnnotationMethodHandlerAdapter beans floating around from your existing app. You might want to set a breakpoint on setCustomWebArgumentResolvers method of that class and see what gets injected there. Also I'd recommend referring to the lite-showcase sample app.

    Comment


    • #3
      Thanks again,

      I have used the sample but as you correct pointed out I also had.

      Code:
      <bean class="org.springframework.web.servlet.mvc.annotation.DefaultAnnotationHandlerMapping" /> 
         
      
         <bean class="org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter" >
            <property name="messageConverters">
               <list>
                  <bean class="org.springframework.http.converter.json.MappingJacksonHttpMessageConverter" />
               </list>
            </property> 
         </bean

      I have removed AnnotationMethodHandlerAdapter

      and used

      Code:
      <mvc:annotation-driven>
           <mvc:argument-resolvers>
              <bean class="org.springframework.mobile.device.DeviceWebArgumentResolver" />
           </mvc:argument-resolvers>
           <mvc:message-converters>
              <bean class="org.springframework.http.converter.json.MappingJacksonHttpMessageConverter" />
           </mvc:message-converters>
         </mvc:annotation-driven>
      This seems to work.

      I assume I can/should leave DefaultAnnotationHandlerMapping ?

      Comment


      • #4
        Also another question - does LiteDeviceResolver find the IPad as 'mobile' ?

        Comment


        • #5
          Realising the answer to my own question about IPADs (ie. will not be seen a 'mobile').

          I decided to move to WURFL.

          So I changed to:

          Code:
            <mvc:interceptors>
                  <!-- On pre-handle, use WURFL to detect the device that originated the web request -->
                  <bean class="org.springframework.mobile.device.DeviceResolverHandlerInterceptor">
                      <constructor-arg>
                      	<!-- Inject a WurflDeviceResolver that populates its device repository from the specified file locations -->
                          <device:wurfl-device-resolver root-location="/WEB-INF/wurfl/wurfl-2.0.30.zip" patch-locations="/WEB-INF/wurfl/web_browsers_patch.xml" />
                      </constructor-arg>		
                  </bean>
              </mvc:interceptors>
          Having set up the zip and xml files.

          Changed:

          Code:
          public String showUserPage(Principal principal,
          		        @RequestParam(value="userid") Long userid,
                                              ModelMap model,
                                              Device device){
          file to

          import net.sourceforge.wurfl.core.Device;

          but I am now getting:

          org.springframework.beans.BeanInstantiationExcepti on: Could not instantiate bean class [net.sourceforge.wurfl.core.Device]: Specified class is an interface


          My mvc:annotation-driven is:

          Code:
          <mvc:annotation-driven>
               <mvc:argument-resolvers>
                  <bean class="org.springframework.mobile.device.DeviceWebArgumentResolver" />
               </mvc:argument-resolvers>
               <mvc:message-converters>
                  <bean class="org.springframework.http.converter.json.MappingJacksonHttpMessageConverter" />
               </mvc:message-converters>
             </mvc:annotation-driven>
          I appear to have a binding issue.

          Again any help appreciated.

          Comment


          • #6
            If you're using mvc:annotation-driven, you should not have DefaultAnnotationHandlerMapping or AnnotationMethodHandlerAdapter registered manually: this element registers them for you. Please refer to the wurfl-showcase sample and test it out and see how it's different then yours.

            Keith

            Comment


            • #7
              Thanks again.

              Moving forward but still a problem.

              What I am confused about - and the WURFL showcase does not cover this - is for the WURFL case how do you "inject the Device into your @Controller".

              I have this working for the non-WURFL case but cannot seem to get it to work when I move to the WURFL case.

              Comment


              • #8
                Well, the WURFL showcase shows injection of a SitePreference, which is done using the same WebArgumentResolver machinery that the DeviceWebArgumentResolver uses. Something has to be wrong with your configuration. Fundamentally, a DeviceWebArgumentResolver MUST be registered with the AnnotationMethodHandlerAdapter that is used to invoke @Controllers dispatched by the DispatcherServlet. Having a duplicate AnnotationMethodHandlerAdapter floating around in your context that is not configured properly can definitely cause this problem.

                You might want to try the following test:
                - Take wurfl-showcase and try injecting a Device into a @Controller method. It should fail.
                - Add DeviceWebArgumentResolver to the set of web-argument-resolvers, alongside SitePreferenceWebArgumentResolver, and try your @Controller test again. It should work.

                Something has to be wrong with your configuration somewhere.
                Last edited by Keith Donald; May 14th, 2011, 01:27 PM.

                Comment


                • #9
                  Found the issue - thanks for all the help - I had not noticed that I needed to change.

                  Code:
                  public String showUserPage(Principal principal,
                  		        @RequestParam(value="userid") Long userid,
                                                      ModelMap model,
                                                      Device device){
                  to

                  Code:
                  public String showUserPage(Principal principal,
                  		        @RequestParam(value="userid") Long userid,
                                                      ModelMap model,
                                                      WurflDevice device){
                  Note: An update to the 'spring mobile' documentation might be useful ?

                  Comment


                  • #10
                    WurflDevice is not required there, a org.springframework.mobile.Device reference will work fine as long as the DeviceWebArgumentResolver is registered properly. You can review the code of DeviceWebArgumentResolver to see this for yourself. Of course, if you need a WurflDevice, you can inject it as well.

                    Keith

                    Comment


                    • #11
                      Looking back at this thread, it looks like you were trying to import net.sourceforge.wurf.core.Device. This will definitely NOT work, as this is part of the WURFL library. You can only import implementations of the Spring Mobile Device abstraction: org.springframework.mobile.Device, which includes the interface itself as well as the specific WurflDevice implementation, which is a Spring Mobile wrapper around net.sourceforge.wurfl.core.Device.

                      Keith

                      Comment


                      • #12
                        Just out of curiosity, did you actually test out the LiteDeviceResolver from a iPad User Agent and you ended up with a non-mobile version of your site? If so, that would be a defect in the LiteDeviceResolver implementation. If you could open a JIRA reporting the problem, that would be helpful.

                        Keith

                        Comment


                        • #13
                          Thanks again,

                          I have ended up needing to test for 'touchscreen' so I did need pointing_method in WURFL.

                          I imported the following

                          import org.springframework.mobile.device.wurfl.WurflDevic e;

                          and had

                          Code:
                          public String showUserPage(Principal principal,
                          		       @RequestParam(value="userid") Long userid,
                                                              ModelMap model,
                                                              WurflDevice device)
                          This seems to work ok so far.

                          I believe I did test an IPAD user-agent (simulated with Firefox user-agent addon) on the LiteDeviceResolver and it did not pick it up as 'mobile'.

                          I will retest and try and raise a JIRA.

                          Comment

                          Working...
                          X