接口的自定义jax-rs实体提供程序?

时间:2011-11-16 21:56:59

标签: java jax-rs resteasy

我如何告诉RESTEasy(jax-rs实现),“嘿,当你被问到IFoo时,请继续制作一个Foo对象?”

我当前(错误的)尝试

我有一个api接入点,我想使用ReportPieceDAO个对象。 ReportPieceDAOList<StandardScoreReport>个成员。 StandardScoreReport是一个界面,由StandardScoreReportImpl实现。

@Path("pieces")
@PUT
@Produces("application/json")
@Consumes("application/json")
public Iterable<Long> putReportPiece( List<ReportPieceDAO> reportPieces) {
    return getDataCoordinator().updateReportPieces(getAuthenticatedUser(), reportPieces);
}

在我添加List<StandardScoreReport>成员之前,此入口点运作良好。因为StandardScoreReport是一个抽象接口,所以RESTEasy不能自动构造一个 - 它抱怨StandardScoreReport没有默认构造函数。

所以,在需要StandardScoreReportImpl的情况下,我想制作某种构造StandardScoreReport的适配器或提供程序:

@Provider
@Consumes("application/json")
public class StandardScoreReportProvider implements MessageBodyReader<StandardScoreReport>{

    @Override
    public boolean isReadable(Class<?> arg0, Type arg1, Annotation[] arg2,
            MediaType arg3) {
        return true;
    }

    @Override
    public StandardScoreReport readFrom(Class<StandardScoreReport> arg0,
            Type arg1, Annotation[] arg2, MediaType arg3,
            MultivaluedMap<String, String> arg4, InputStream arg5)
            throws IOException, WebApplicationException {

            //I'm hoping I can just call some "default" code that 
            //would run if StandardScoreReportImpl were naturally 
            //encountered, and not have to write my own unmarshalling code.

        return new StandardScoreReportImpl();
    }

}

但是这些代码都没有执行过。这是我的申请说明:

public class RESTEasyApplicationDescription extends Application
{
    HashSet<Class<?>> classes = new HashSet<Class<?>>();

    public RESTEasyApplicationDescription()
    {
        classes.add(APIRoot.class);
        classes.add(ReportsRoot.class);
        classes.add(StandardScoreReportProvider.class);
        classes.add(StandardScoreReport.class);
        classes.add(ReportPiece.class);
    }

    @Override
    public Set<Class<?>> getClasses() {
        return classes;
    }

    @Override
    public Set<Object> getSingletons() {
        return null;
    }
}

1 个答案:

答案 0 :(得分:2)

在将应用程序部署到服务器时会注册提供程序。服务器自动知道如何接收/传递某个对象。 您必须创建一个具有@Provider的类,然后创建一个

  

从POST中创建一个java对象,您可以使用:@Consumes
  通过您可能使用的Web服务调用将一个java对象发送到Response:@Produces

并指定类型。
示例: 我有一个服务,当我打电话给我一个PDF,它没有消耗任何东西,它只给我一个PDF文件:
MyService.java

@GET
@Path("/report.{format}")
@Produces({ MediaType.TEXT_HTML, "application/pdf" })
public Response recuperarReporte(){
    private ByteArrayOutputStream responseEntity = ....;
    Response
            .ok()
            .entity(responseEntity)
            .type("application/pdf").build();
}

<强> MyPDFProvider.java

@Produces("application/pdf")
@Provider
public class MyPDFProvider implements MessageBodyWriter<ByteArrayOutputStream>
{

    @Override
    public long getSize(ByteArrayOutputStream stream, Class<?> type,
            Type genericType, Annotation[] annotations, MediaType mediaType)
    {
        return stream.size();
    }

    @Override
    public boolean isWriteable(Class<?> type, Type genericType,
            Annotation[] annotations, MediaType mediaType)
    {
        return ByteArrayOutputStream.class.isAssignableFrom(type);
    }

    @Override
    public void writeTo(ByteArrayOutputStream t, Class<?> type,
            Type genericType, Annotation[] annotations, MediaType mediaType,
            MultivaluedMap<String, Object> httpHeaders,
            OutputStream entityStream) throws IOException,
            WebApplicationException
    {
        entityStream.write(t.toByteArray());
    }
}