如果Spring MVC控制器方法不返回值,该怎么办?


135

我正在使用jQuery $.getJSON()对我的简单Spring MVC后端进行异步调用。大多数Spring控制器方法如下所示:

@RequestMapping(value = "/someURL", method = RequestMethod.POST)
public @ResponseBody SomePOJO getSomeData(@ModelAttribute Widget widget,
    @RequestParam("type") String type) {
    return someDAO.getSomeData(widget, type);
}   

我已经进行了设置,以便每个控制器都将@ResponseBodyas作为JSON 返回,这是客户端所期望的。

但是,当请求不应该将任何内容返回给客户端时,会发生什么呢?我能有......吗:

@RequestMapping(value = "/updateSomeData" method = RequestMethod.POST)
public @ResponseBody void updateDataThatDoesntRequireClientToBeNotified(...) {
    ...
}

如果没有,在这里使用什么合适的语法?


我假设如果您不返回任何内容,将不会发送任何内容?
2012年

1
我想我仍然会返回某种POJO,即使在您的解决方案的版本1中,它只是包装了“成功”布尔值或类似内容。然后,您所有的AJAX方法中都有一个一致的模式,而且事实证明,在某些情况下更容易构建的东西确实需要返回某些东西!
米尔豪斯2012年

与建议的答案相反,第二个片段中的第一个内容非常好,并且是处理POST数据的正确方法。
Brett Ryan

在这种情况下,它将返回null。@RestController公共类RESTControllerExample {@RequestMapping(value =“ / employees”,method = RequestMethod.GET)public void getEmployeeNames(){EmployeeSource.getEmployees(); System.out.println(“我完成了”); }
spandey

Answers:


256

您可以返回void,然后必须使用@ResponseStatus(value = HttpStatus.OK)标记该方法,而无需使用@ResponseBody

@RequestMapping(value = "/updateSomeData" method = RequestMethod.POST)
@ResponseStatus(value = HttpStatus.OK)
public void updateDataThatDoesntRequireClientToBeNotified(...) {
    ...
}

只有get方法隐式地返回200状态代码,所有其他方法都可以做以下三件事之一:

  • 返回void并用标记方法 @ResponseStatus(value = HttpStatus.OK)
  • 返回一个对象并标记为 @ResponseBody
  • 返回一个HttpEntity实例

2
万一发生运行时异常,则将返回HTTP 500,而不是200。因此,如果前端处理失败,则将正确显示异常/错误消息。
Lee Chee Kiam

27
实际上,您不需要设置也不需要设置@ResponseStatus。仅仅拥有@ResponseBody一个void处理程序就足够了。
Brett Ryan

11
我认为最好返回204 No Content而不是200的void方法
raspacorp 2014年

1
@raspacorp 200对于POST是正确的,因为它并不意味着有身体。
Brett Ryan

8
@BrettRyan作为注释,至少对于REST API而言,通常的做法是使用POST来创建内容,在这种情况下,它通常会返回创建的实体的ID,完整创建的实体或链接进行读取操作。从REST API的角度来看,没有内容的200状态返回可能会造成混淆。
raspacorp 2014年

43

您可以简单地返回带有适当标头的ResponseEntity:

@RequestMapping(value = "/updateSomeData" method = RequestMethod.POST)
public ResponseEntity updateDataThatDoesntRequireClientToBeNotified(...){
....
return new ResponseEntity(HttpStatus.OK)
}

如果有人遇到我遇到的相同问题,那么这在较旧版本的spring(4.1.1)上不起作用,那么我会得到500个错误。我升级到4.2.0,效果很好
调味

那也是我返回空200的首选方式。从Spring 4.1开始,改用构建器模式:return ResponseEntity.ok()。build();
GreenTurtle

3
尽管似乎可以编译,但它发出以下警告ResponseEntity is a raw type. References to generic type ResponseEntity<T> should be parameterized
Gonzalo。

8

您可以返回“ ResponseEntity”对象。在构造响应对象(包含响应主体和HTTP状态代码)时以及从响应对象中获取信息时,使用“ ResponseEntity”对象都非常方便。

诸如getHeaders(),getBody(),getContentType(),getStatusCode()等方法使读取ResponseEntity对象的工作变得非常容易。

您应该使用带有201状态代码(无内容)的HTTP状态代码的ResponseEntity对象,该对象专门用于指定请求已正确处理并且响应正文有意为空白。使用适当的状态代码来传达正确的信息非常重要,尤其是当您要创建将由多个客户端应用程序使用的API时。


3
设置在浏览器中为我@ResponseStatus(HttpStatus.NO_CONTENT)解决XML Parsing Error: no root element found
aliopi '17

3

是的,您可以将@ResponseBody与void返回类型一起使用:

@RequestMapping(value = "/updateSomeData" method = RequestMethod.POST)
@ResponseBody
public void updateDataThatDoesntRequireClientToBeNotified(...) {
    ...
}

1
那么返回类型是什么。.它是HTTP状态代码吗?
spandey

@techBeginner在这种情况下为200(确定)。
Lakatos Gyula

2

返回void @ResponseBody并没有错,您应该POST请求。

使用HTTP状态代码来定义异常处理程序例程中的错误,而不是其他人提到成功状态。您所拥有的普通方法将返回所需的响应代码,200然后任何异常处理程序都可以返回错误对象和其他代码(即500)。


1

但是随着系统规模和功能的增长,我认为始终返回json并不是一个坏主意。更多的是建筑/“大规模设计”问题。

您可以考虑始终使用两个已知字段来重现JSON:代码和数据。其中code是一个数字代码,用于指定要完成的操作的成功,而data是与所请求的操作/服务相关的任何附加数据。

来吧,当我们使用后端服务提供商时,可以检查任何服务以查看其是否运行良好。

因此,我坚持不让spring对此进行管理,而是公开混合返回操作(有些返回数据,其他什么都没有...).. instaed确保您的服务器公开更统一的接口。一天结束时更简单。


0

这是我对异步方法所做的示例代码

@RequestMapping(value = "/import", method = RequestMethod.POST)
@ResponseStatus(value = HttpStatus.OK)
public void importDataFromFile(@RequestParam("file") MultipartFile file) 
{
    accountingSystemHandler.importData(file, assignChargeCodes);
}

您不需要从方法中返回任何东西,只需使用此批注,这样您的方法在每种情况下都应返回OK。

@ResponseStatus(value = HttpStatus.OK)
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.