Java 如何在 Tomcat 上的 JAX-RS (Jersey) 中返回 HTTP 404 JSON/XML 响应?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/23858488/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
How I return HTTP 404 JSON/XML response in JAX-RS (Jersey) on Tomcat?
提问by IJR
I have the following code:
我有以下代码:
@Path("/users/{id}")
public class UserResource {
@Autowired
private UserDao userDao;
@GET
@Produces({MediaType.APPLICATION_XML, MediaType.APPLICATION_JSON})
public User getUser(@PathParam("id") int id) {
User user = userDao.getUserById(id);
if (user == null) {
throw new NotFoundException();
}
return user;
}
If I request for a user that doesn't exists, like /users/1234
, with "Accept: application/json
", this code returns an HTTP 404
response like one would expect, but returns Content-Type
sets to text/html
and a body message of html. Annotation @Produces
is ignored.
如果我请求一个不存在的用户,例如/users/1234
带有“ Accept: application/json
”的用户,则此代码将返回一个符合HTTP 404
预期的响应,但返回Content-Type
设置为text/html
和 html 的正文消息。注释@Produces
被忽略。
Is it a problem of code or a problem of configuration?
是代码问题还是配置问题?
采纳答案by Svetlin Zarev
Your @Produces
annotation is ignored because uncaught exceptions are processed by the jax-rs runtime using a predefined (default) ExceptionMapper
If you want to customize the returned message in case of a specific exception you can create your own ExceptionMapper
to handle it. In your case you need one to handle the NotFoundException
exception and query the "accept" header for the requested type of the response:
你@Produces
因未捕获的异常是由JAX-RS处理注释被忽略使用预定义(默认)运行时ExceptionMapper
如果您希望自定义返回的消息在一个特定的异常的情况下,你可以创建自己ExceptionMapper
来处理它。在您的情况下,您需要一个来处理NotFoundException
异常并查询请求类型的响应的“接受”标头:
@Provider
public class NotFoundExceptionHandler implements ExceptionMapper<NotFoundException>{
@Context
private HttpHeaders headers;
public Response toResponse(NotFoundException ex){
return Response.status(404).entity(yourMessage).type( getAcceptType()).build();
}
private String getAcceptType(){
List<MediaType> accepts = headers.getAcceptableMediaTypes();
if (accepts!=null && accepts.size() > 0) {
//choose one
}else {
//return a default one like Application/json
}
}
}
回答by dev2d
that 404 is returned by your server as it is expected that you will pass things in following form
404 由您的服务器返回,因为预计您将以以下形式传递内容
/users/{id}
but you are passing it as
但你把它作为
/users/user/{id}
which resource is not existing at all
哪个资源根本不存在
try accessing resource as /users/1234
尝试访问资源 /users/1234
EDIT:
编辑:
create a class like
创建一个类
class RestResponse<T>{
private String status;
private String message;
private List<T> objectList;
//gettrs and setters
}
now in case you want response for User
you can create it as following
现在,如果您想要响应,User
可以按如下方式创建它
RestResponse<User> resp = new RestResponse<User>();
resp.setStatus("400");
resp.setMessage("User does not exist");
and signature of your rest method would be like following
你的rest方法的签名如下
public RestResponse<User> getUser(@PathParam("id") int id)
while in case successful response you can set things like
如果成功响应,您可以设置诸如
RestResponse<User> resp = new RestResponse<User>();
List<User> userList = new ArrayList<User>();
userList.add(user);//the user object you want to return
resp.setStatus("200");
resp.setMessage("User exist");
resp.setObjectList(userList);
回答by Tiago
You can use the Response return. Example below:
您可以使用 Response 返回。下面的例子:
@GET
@Path("{id}")
@Produces(MediaType.APPLICATION_JSON)
public Response get(@PathParam("id") Long id) {
ExampleEntity exampleEntity = getExampleEntityById(id);
if (exampleEntity != null) {
return Response.ok(exampleEntity).build();
}
return Response.status(Status.NOT_FOUND).build();
}