相当于泽西的Spring MVC @ResponseStatus(HttpStatus.CREATED)?

时间:2015-02-20 03:41:44

标签: java spring-mvc jersey jax-rs

这个Spring MVC代码的Jersey相当于什么?在成功发布POST之后,我需要响应以返回201和资源URL:

@RequestMapping(method = RequestMethod.POST)
@ResponseStatus(HttpStatus.CREATED)
Widget create(@RequestBody @Valid Widget wid) {
  return service.create(wid);
}

这是我在泽西岛发现的最短的例子。是否需要手动为POST / 201成功构建响应?

@POST @Path("widget")
Response create(@RequestBody @Valid Widget wid) {
   return Response
             .status(Response.Status.CREATED)
             .entity("new widget created")
             .header("Location","http://localhost:7001/widget"+wid)
             .build();
  }

2 个答案:

答案 0 :(得分:2)

我不认为泽西有这样的注释。您可以使用Name Binding创建一个。

基本上,您创建一个注释并添加@NameBinding元注释:

@NameBinding
@Target({ElementType.TYPE, ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
public @interface ResponseStatusCreated {}

接下来,您将创建一个覆盖状态的过滤器。

@ResponseStatusCreated
@Provider
class StatusCreatedFilter implements ContainerResponseFilter {

    @Override
    public void filter(ContainerRequestContext requestContext, 
                       ContainerResponseContext responseContext) throws IOException {
        responseContext.setStatusInfo(Response.Status.CREATED)

        String location = "..."; // set based on responseContext.getEntity() 
                                 // or any other properties
        responseContext.getHeaders().putSingle("Location", location);
    }
}

然后在资源方法上使用相同的注释。

@POST
@Path("widget")
@ResponseStatusCreated
Object create(@RequestBody @Valid Widget wid) {
    return ... // return whatever you need to build the
               // correct header fields in the filter
}

您还可以通过创建一个将状态作为参数接受的注释来使其更通用,即@ResponseStatus(Status.CREATED)并使用responseContext.getAnnotations()在过滤器中获取状态。

答案 1 :(得分:2)

评论示例,根据OP的要求:

  

我认为没有相应的,但就个人而言,我喜欢创建自己的回复。我有更多的控制权。还有Response.created(...),这将自动设置状态。它接受URI或String作为参数,并使用该参数设置位置标头。您也可以UriInfo使用getAbsolutePathBuilder(),然后只需附加创建的ID即可。这通常是我的方式。

@Path("/widgets")
public class WidgetResource {

    @Inject
    WidgetService widgetService;

    @POST
    @Consumes(...)
    public Response createWidget(@Context UriInfo uriInfo, Widget widget) {
        Widget created = widgetService.createWidget(widget);

        UriBuilder builder = uriInfo.getAbsolutePathBuilder();
        URI uri = builder.path(created.getId()).build();

        return Response.created(uri).build();
    }
}

这是我用于创建方法的一般模式。收集路径将是从uriInfo.getAbsolutePath(Builder)获得的绝对路径,然后您只需将创建的id附加到路径。因此,如果收集路径为http://blah.com/widgets,且ID为someId,则位置标头将为Location: http://blah.com/widgets/someId(这是新资源的位置),状态将设置为到201 Created

Response.created(..)返回Response.ResponseBuilder,就像Response.status一样,因此您可以执行通常的方法链接。 Response上有许多静态方法具有默认设置,例如oknoContent。只需通过API。他们的名字几乎与状态名称相匹配。