Java 如何在Spring Boot@ResponseBody中返回404响应状态-方法返回类型为response?

Java 如何在Spring Boot@ResponseBody中返回404响应状态-方法返回类型为response?,java,spring,http-status-code-404,retrofit,Java,Spring,Http Status Code 404,Retrofit,我使用基于@ResponseBody的Spring Boot方法,如下所示: @RequestMapping(value = VIDEO_DATA_PATH, method = RequestMethod.GET) public @ResponseBody Response getData(@PathVariable(ID_PARAMETER) long id, HttpServletResponse res) { Video video = null; Response res

我使用基于@ResponseBody的Spring Boot方法,如下所示:

@RequestMapping(value = VIDEO_DATA_PATH, method = RequestMethod.GET)
public @ResponseBody Response getData(@PathVariable(ID_PARAMETER) long id, HttpServletResponse res) {
    Video video = null;
    Response response = null;
    video = videos.get(id - 1);
    if (video == null) {
      // TODO how to return 404 status
    }
    serveSomeVideo(video, res);
    VideoSvcApi client =  new RestAdapter.Builder()
            .setEndpoint("http://localhost:8080").build().create(VideoSvcApi.class);
    response = client.getData(video.getId());
    return response;
}

public void serveSomeVideo(Video v, HttpServletResponse response) throws IOException  {
    if (videoDataMgr == null) {
        videoDataMgr = VideoFileManager.get();
    }
    response.addHeader("Content-Type", v.getContentType());
    videoDataMgr.copyVideoData(v, response.getOutputStream());
    response.setStatus(200);
    response.addHeader("Content-Type", v.getContentType());
}
return new ResponseEntity(HttpStatus.NOT_FOUND);
我尝试了一些典型的方法,如:

res.setStatus(HttpStatus.NOT_FOUND.value())
新响应(HttpStatus.BAD_请求)

但是我需要回来


如果视频为空,如何在此处返回404状态代码?

创建一个带有
@ResponseStatus(HttpStatus.NOT\u FOUND)
注释的
NotFoundException
类,并将其从控制器中抛出

@ResponseStatus(code = HttpStatus.NOT_FOUND, reason = "video not found")
public class VideoNotFoundException extends RuntimeException {
}

您的原始方法可以返回
响应属性
(不会更改您的方法行为):

并返回以下内容:

@RequestMapping(value = VIDEO_DATA_PATH, method = RequestMethod.GET)
public @ResponseBody Response getData(@PathVariable(ID_PARAMETER) long id, HttpServletResponse res) {
    Video video = null;
    Response response = null;
    video = videos.get(id - 1);
    if (video == null) {
      // TODO how to return 404 status
    }
    serveSomeVideo(video, res);
    VideoSvcApi client =  new RestAdapter.Builder()
            .setEndpoint("http://localhost:8080").build().create(VideoSvcApi.class);
    response = client.getData(video.getId());
    return response;
}

public void serveSomeVideo(Video v, HttpServletResponse response) throws IOException  {
    if (videoDataMgr == null) {
        videoDataMgr = VideoFileManager.get();
    }
    response.addHeader("Content-Type", v.getContentType());
    videoDataMgr.copyVideoData(v, response.getOutputStream());
    response.setStatus(200);
    response.addHeader("Content-Type", v.getContentType());
}
return new ResponseEntity(HttpStatus.NOT_FOUND);

您可以在res上设置responseStatus,如下所示:

@RequestMapping(value = VIDEO_DATA_PATH, method = RequestMethod.GET)
public ResponseEntity getData(@PathVariable(ID_PARAMETER) long id,
                                            HttpServletResponse res) {
...
    res.setStatus(HttpServletResponse.SC_NOT_FOUND); 
    // or res.setStatus(404)
    return null; // or build some response entity
 ...
}

这非常简单,只需抛出org.springframework.web.server.ResponseStatusException:

throw new ResponseStatusException(
  HttpStatus.NOT_FOUND, "entity not found"
);

它与
@ResponseBody
和任何返回值兼容。需要Spring 5+

准确地说,您应该返回ResponseEntity,其中T是例如Response(第一个有问题的案例)。当响应正确时,您将返回新的ResponseEntity(myResponse,HttpStatus.OK)。这种方式允许您设置标题,ResponseStatus不会,woot!另一个好处是它不会导致日志中出现警告,而抛出ResponseStatusException会导致警告。但是,随后您会丢失响应上的类型,这对Swagger生成的文档不起作用。需要标准导入方法:导入org.springframework.http.HttpStatus@andrej有时候这是一个很好的解决方案,但是(1)直到春季5日才添加了
ResponseStatusException
;(2)
NotFoundException
对于被捕获或对于带有
@ExceptionHandler
的双堆栈HTML UI都很有用。此解决方案将异常与REST控制器层紧密耦合。我想避免的事情。我会在
@AroundAdvice
组件中使用
@ExceptionHandler
而不是如果有人想使用Spring附带的预先存在的异常,
org.springframework.data.rest.webmvc.ResourceNotFoundException
已经用
@ResponseStatus(HttpStatus.NOT\u FOUND)注释了
是否有办法在不引起Springboot发出警告的情况下执行此操作?我得到'WARN 27604---[nio-8081-exec-9].w.s.m.a.ResponseStatusExceptionResolver:Resolved[org.springframework.web.server.ResponseStatusException:404 NOT_FOUND',它不合理地进入警报等:这不是问题。@GreenAsJade我不确定这个警告记录在哪里(我在日志中没有看到这个警告)但也许您可以使用log4j设置或与警报系统对话来避免这种情况。这不是最好的,您的访问者将看到错误堆栈信息。@buff这是针对web服务的(与机器对话)