我正在尝试访问我编写的RESTful Web服务:
http://localhost:8080/dukegen/ws/family/1
但是使用浏览器中的地址栏获取404并且不知道原因。我想恢复JSON。我把Jackson 2放在了我的课堂上:
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-databind</artifactId>
<version>2.3.1</version>
</dependency>
这是服务器输出:
Jan 14, 2014 8:29:55 PM org.springframework.web.servlet.handler.AbstractUrlHandlerMapping registerHandler
INFO: Mapped URL path [/ws/family/{familyId}] onto handler 'familyResource'
Jan 14, 2014 8:29:55 PM org.springframework.web.servlet.handler.AbstractUrlHandlerMapping registerHandler
INFO: Mapped URL path [/ws/family/{familyId}.*] onto handler 'familyResource'
Jan 14, 2014 8:29:55 PM org.springframework.web.servlet.handler.AbstractUrlHandlerMapping registerHandler
INFO: Mapped URL path [/ws/family/{familyId}/] onto handler 'familyResource'
Jan 14, 2014 8:29:55 PM org.springframework.web.servlet.FrameworkServlet initServletBean
INFO: FrameworkServlet 'dispatcher': initialization completed in 360 ms
Jan 14, 2014 8:29:55 PM org.springframework.web.servlet.DispatcherServlet noHandlerFound
WARNING: No mapping found for HTTP request with URI [/dukegen/ws/family/1] in DispatcherServlet with name 'dispatcher'
这是我的控制器:
@Controller
@RequestMapping("ws")
public class FamilyResource {
@RequestMapping(value="family/{familyId}", method = RequestMethod.GET, produces="application/json")
public @ResponseBody Family getFamily(@PathVariable long familyId) {
.... builds Family object ....
return family;
}
}
这是我在web.xml中设置的调度程序:
<servlet>
<servlet-name>dispatcher</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath:/mvcContext.xml</param-value>
</init-param>
</servlet>
<servlet-mapping>
<servlet-name>dispatcher</servlet-name>
<url-pattern>/ws/*</url-pattern>
</servlet-mapping>
我的mvcContext.xml:
<?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:p="http://www.springframework.org/schema/p"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="
http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context.xsd">
<context:component-scan base-package="ws.hamacher.dukegen.resource"/>
</beans>
任何帮助都会受到赞赏。
答案 0 :(得分:17)
这里的一些事情都不正确。
首先,在您的请求映射中,映射应该是一致的。
您的类应映射到"/ws"
,产生结果的方法应为"/family/{familyId}"
在您的web.xml中,您已配置servlet以响应/ws/*
,并且您的控制器再次请求映射到ws
。这不起作用。
servlet拦截"/ws/*"
后,不应在请求映射中重复它。 Controller仅响应其上下文中的URL模式。在您的URL中"/ws"
之后的任何内容仅在控制器的上下文中。
我通常更喜欢将servlet映射到"/"
以及在控制器内编码的所有其他分辨率。不过只是我的偏好。
所以正确的配置是
web.xml
<servlet>
<servlet-name>dispatcher</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath:/mvcContext.xml</param-value>
</init-param>
</servlet>
<servlet-mapping>
<servlet-name>dispatcher</servlet-name>
<url-pattern>/</url-pattern>
</servlet-mapping>
和控制器
@Controller
@RequestMapping("/ws")
public class FamilyResource {
@RequestMapping(value="/family/{familyId}", method = RequestMethod.GET, produces="application/json")
public @ResponseBody Family getFamily(@PathVariable long familyId) {
.... builds Family object ....
return family;
}
}
答案 1 :(得分:0)
在stackoverflow中搜索了几篇文章之后,没有找到决定性的答案,下面就是我验证的内容:
1)如果您通过以下方式在请求映射中进行设置:“ / rest / *”,web.xml或“ AbstractAnnotationConfigDispatcherServletInitializer”类的“ getServletMappings”方法中,请不要在RestController的RequestMapping。
MySpringMvcDispatcherServletInitializer.java
import org.springframework.web.servlet.support.AbstractAnnotationConfigDispatcherServletInitializer;
public class MySpringMvcDispatcherServletInitializer extends AbstractAnnotationConfigDispatcherServletInitializer {
@Override
protected Class<?>[] getRootConfigClasses() {
// TODO Auto-generated method stub
return null;
}
@Override
protected Class<?>[] getServletConfigClasses() {
return new Class[] { DemoAppConfig.class };
}
@Override
protected String[] getServletMappings() {
return new String[] { "/rest/*" };
}
}
DemoRestController.java
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
@RestController
@RequestMapping(value="/rest")
public class DemoRestController {
// add code for the "/hello" endpoint
@GetMapping(value="/hello")
public String sayHello() {
return "Hello World!";
}
}
如果您在RestController类的RequestMapping中重复“ / rest”,它将不起作用。尝试访问以下网址时,您会收到404错误:http://localhost:9091/your-context-app/rest/hello
2)当我们在请求映射中定义“ / rest / *”时,我们正在向Servlet Dispatcher指示从该上下文“ / rest”将处理所有内容。因此,通过删除“ / rest”来更改RestController的映射。输入另一个映射,例如“ / test”:
DemoRestController.java
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
@RestController
@RequestMapping(value="/test")
public class DemoRestController {
// add code for the "/hello" endpoint
@GetMapping(value="/hello")
public String sayHello() {
return "Hello World!";
}
}
3)现在,使用URL http://localhost:9091/your-context-app/rest/test/hello
访问rest服务。这应该很好!
希望这会有所帮助。