2015-08-08 206 views
2

我試圖在我的spring mvc控制器中自動編寫org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping以獲取所有url映射並將它們顯示在UI上,但不成功。有錯誤豆丟失:Spring mvc autowire RequestMappingHandlerMapping

org.springframework.beans.factory.BeanCreationException: Could not autowire field: org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping web.controller.WorkController.handlerMapping; nested exception is org.springframework.beans.factory.NoSuchBeanDefinitionException: No qualifying bean of type [org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping] found for dependency: expected at least 1 bean which qualifies as autowire candidate for this dependency. Dependency annotations: {@org.springframework.beans.factory.annotation.Autowired(required=true)} 

我的web.xml:

<display-name>Spring MVC Application</display-name> 

<servlet> 
    <servlet-name>mvc-dispatcher</servlet-name> 
    <servlet-class> 
     org.springframework.web.servlet.DispatcherServlet 
    </servlet-class> 
    <init-param> 
     <param-name>contextConfigLocation</param-name> 
     <param-value>WEB-INF/mvc-dispatcher-servlet.xml</param-value> 
    </init-param> 
    <load-on-startup>1</load-on-startup> 
</servlet> 

<servlet-mapping> 
    <servlet-name>mvc-dispatcher</servlet-name> 
    <url-pattern>/</url-pattern> 
</servlet-mapping> 


<context-param> 
    <param-name>contextConfigLocation</param-name> 
    <param-value>/WEB-INF/root-context.xml</param-value> 
</context-param> 

<listener> 
    <listener-class> 
     org.springframework.web.context.ContextLoaderListener 
    </listener-class> 
</listener> 

我的MVC-調度-servlet.xml中:

<context:annotation-config/> 
    <context:component-scan base-package="web.controller"/> 
      <bean class="org.springframework.web.servlet.view.InternalResourceViewResolver"> 
     <property name="prefix"> 
      <value>/WEB-INF/views/</value> 
     </property> 
     <property name="suffix"> 
      <value>.jsp</value> 
     </property> 
    </bean> 
</beans> 

我的根-context.xml:

<bean id="helloBean" class="web.beans.HelloBean"/> 

的java的控制器:

package web.controller; 

import org.springframework.beans.factory.annotation.Autowired; 
import org.springframework.context.ApplicationContext; 
import org.springframework.stereotype.Controller; 
import org.springframework.web.bind.annotation.RequestMapping; 
import org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping; 
import web.beans.HelloBean; 

import java.util.List; 

@Controller 
public class WorkController { 

    @Autowired RequestMappingHandlerMapping handlerMapping; 
    @Autowired private HelloBean helloBean; 
    @Autowired private ApplicationContext applicationContext; 

    @RequestMapping(value = "/index") 
    public String index() { 
     return "index"; 
    } 
} 

回答

1

嘗試讓所有的請求urls,下面的代碼可能是對您有用。

ServletContext servletContext = request.getSession().getServletContext(); 
WebApplicationContext appContext = WebApplicationContextUtils.getWebApplicationContext(servletContext); 
Map<String, HandlerMapping> allRequestMappings = BeanFactoryUtils.beansOfTypeIncludingAncestors(appContext, HandlerMapping.class, true, false); 
for (HandlerMapping handlerMapping : allRequestMappings.values()) { 
    if (handlerMapping instanceof RequestMappingHandlerMapping) { 
      RequestMappingHandlerMapping requestMappingHandlerMapping = (RequestMappingHandlerMapping) handlerMapping; 
      Map<RequestMappingInfo, HandlerMethod> handlerMethods = requestMappingHandlerMapping.getHandlerMethods(); 
      for (Map.Entry<RequestMappingInfo, HandlerMethod> requestMappingInfoHandlerMethodEntry : handlerMethods.entrySet()) { 
      RequestMappingInfo requestMappingInfo = requestMappingInfoHandlerMethodEntry.getKey(); 
      PatternsRequestCondition patternsCondition = requestMappingInfo.getPatternsCondition(); 
      String requestUrl = SetUtils.first(patternsCondition.getPatterns()); 
      System.out.println(requestUrl); 
      } 
    } 
} 

老實說,java reflect是一個關鍵點,以讓所有的請求urls。如果你看看春天MVC源深,你會發現HandlerMapping接口的implementation classes,如

AbstractControllerUrlHandlerMapping, AbstractDetectingUrlHandlerMapping, 
AbstractHandlerMapping, AbstractHandlerMethodMapping, 
AbstractUrlHandlerMapping, BeanNameUrlHandlerMapping, 
ControllerBeanNameHandlerMapping, ControllerClassNameHandlerMapping, 
DefaultAnnotationHandlerMapping, RequestMappingHandlerMapping, 
RequestMappingInfoHandlerMapping, SimpleUrlHandlerMapping 
+0

什麼是SetUtils.first()? – NickJ

+0

@NickJ認爲它爲 'final Set patterns = patternsCondition.getPatterns(); String requestUrl = patterns.stream()。findFirst()。orElse(StringUtils.EMPTY);' – Scolytus

3

你應該啓動RequestMappingHandlerMapping bean之前自動裝配它。 它有兩個方式:

  1. 在springxml配置諸如問候豆
<bean name="handlerMapping" class="org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping"> 
<!-- add your properties here property name="..." value="..."></property--> 
</bean> 
  • 或者用

    @Configuration

    @Configuration 
    @ComponentScan("your.package") 
    @EnableWebMvc 
    public class AppConfig { 
    ... 
        @Bean 
        public RequestMappingHandlerMapping requestMappingHandlerMapping() { 
         RequestMappingHandlerMapping mapping = new RequestMappingHandlerMapping(); 
         // add properties here 
         return mapping; 
        } 
    ... 
    }