为什么要为JAX-RS实现声明一个接口? [英] Why should an Interface be declared for JAX-RS implementation?

查看:70
本文介绍了为什么要为JAX-RS实现声明一个接口?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我已经看过一些教程,在其中可以看到创建了一个带有JAX-RS批注的接口.然后完成相同的实现.

I have gone through couple of tutorials, where I could see that an Interface which JAX-RS annotation is created. And later an implementation of the same is done.

为什么会这样?我不能将具体类直接作为RESTful服务公开吗?这是不好的做法吗?以下是我在问题中遇到的示例之一.

Why is so? Can't I expose a concrete class directly as a RESTful Service? Is that a bad practice? Below is one of the samples which I came across in this question.

public interface ICRUD {

    @POST
    @Consumes("application/json")
    @Produces("application/json")
    @Path("create")
    public String createREST(String transferObject);

    @GET
    @Consumes("application/json")
    @Produces("application/json")
    @Path("retreive/{id}")
    public String retreiveREST(@PathParam("id") String id);

    @POST
    @Consumes("application/json")
    @Produces("application/json")
    @Path("update")
    public void updateREST(@Suspended final AsyncResponse asyncResponse, 
                          final String transferObject) ;

    @DELETE
    @Consumes("application/json")
    @Produces("application/json")
    @Path("delete/{id}")
    public String deleteREST(@PathParam("id") String id); 
}

推荐答案

我不能将具体类直接作为RESTful服务公开吗?

Can't I expose a concrete class directly as a RESTful Service?

您绝对可以.你试过了吗?它应该可以正常工作.

You definitely can. Have you tried it? It should work just fine.

这是不好的做法吗?

Is that a bad practice?

就个人而言(这只是我的偏爱),我认为使用接口是一种不好的做法.有人可能会争辩说它可以清理您的代码,但是使用接口会带来一些问题,例如注释继承可以有时会给那些不了解问题的人造成问题.真的很难发现.

Personally (and this is just my preference), I think it's bad practice to use interfaces. Some people may argue that it cleans up your code, but there are problems that come with using interfaces, for instance annotation inheritance can sometimes cause a problem for those who don't understand what the problem is. It can be really hard to spot.

如果您的论点是接口可以使代码更整洁,那么我有几个论点.

If your argument is that interfaces make code cleaner, I have a couple arguments.

(1)您的代码难以理解.您需要继续返回接口以查看参数的含义(例如,检查方法参数注释).当所有注释都在您实际编写的代码中时,会更容易.

(1) Your code is less understandable. You need to keep referring back to the interface to see what arguments are for (e.g. inspecting the method parameter annotations). It's easier when all the annotations are in the code your actually writing.

(2)接口没有实现,因此您仍然需要实现每个类.我个人使用一个抽象的基类,它将实现所有基本操作.例如

(2) Interfaces have no implementation, so you would still need to implement every class. I personally go with an abstract base class that will implement all the basic operations. For example

public abstract class AbstractResource<T extends BaseEntity> {

    private final Repository<T> repository;

    public AbstractResource(Repository<T> repository) {
        this.repository = repository;
    }

    @GET
    public List<T> getAll() {
        return this.repository.findAll();
    }

    @GET
    @Path("{id}")
    public T getOne(@PathParam("id") long id) {
        T result = this.repository.findOne(id);
        if (result == null) {
             throw new NotFoundException();
        }
        return result;
    }

    @POST
    public Response create(T entity, @Context UriInfo uriInfo) {
        T saved = this.repository.save(entity);
        // BaseEntity should have an id property
        long id = saved.getId();
        URI createdUri = uriInfo.getAbsoluteUriBuilder()
            .path(id).build();
        return Response.created(createdUri).build();
    }
}

您可以对@PUT@DELET执行相同的操作.所有资源集合的核心功能都是相同的.唯一需要更改的是Repository类型.您所有的实现都可以像这样扩展它

You could do the same for @PUT and @DELET. The core functionality is the same for all resource collections. The only thing that would need to change is the Repository type. All your implementations could just extend it like

@Path("pets")
public class PetsResource extends AbstractResource<Pet> {

    @Inject
    public PetsResource(PetsRepository repository) {
         super(repository);
    }
}

这更干净.您不需要为您的具体资源实施相同的基本CRUD操作.如果您想在具体的资源类中提供其他资源方法,则可以这样做.

This is much cleaner. You don't need to implement the same basic CRUD operations for your concrete resources. If you want to provide other resource methods in your concrete resource class, you can do so.

这篇关于为什么要为JAX-RS实现声明一个接口?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆