JAX-RS& CXF映射请求到基于XML的方法

时间:2011-02-02 14:36:10

标签: cxf jax-rs superclass

希望我的标题是正确的,但我正在尝试使用JAX-RS @Path注释将请求映射到基于实体参数的不同方法。

我认为示例代码会更容易:

超级课程

public class Geothing {
    private int thingId;
    private String status;

    // Ctor, getters and setters
}

PolygonGeothing扩展了Geothing:

@XmlRootElement
public class PolygonGeothing extends Geothing {
    private Coordinates coordinates;

    // Ctor, getters and setters
}

CircleGeothing扩展了Geothing:

@XmlRootElement
public class CircleGeothing extends Geothing {
    private Coordinate center;
    private int radius;

    // Ctor, getters and setters
}

服务界面:

@Path("/geothing/{id}")
public interface GeothingService extends CoService {
    @POST
    Response createGeothing(@PathParam("{id}") Long id, PolygonGeothing geothing);

    @POST
    Response createGeothing(@PathParam("{id}") Long id, CircleGeothing geothing);
}

我的期望是,如果我为PolygonGeothing或CircleGeothing发布XML,那么它会起作用。但是,它只有在我发布PolygonGeothing XML并且如果我POST CircleGeothing XML然后我得到一个JAXBException时才有效:
JAXBException occurred : unexpected element (uri:"", local:"circleGeothing"). Expected elements are <{}polygonGeothing>.

是否可以正确映射,而无需为CircleGeothing和PolygonGeothing指定单独的URI路径?此外,是否可以使用以下界面,我可以使用超类作为参数?我测试了返回类型Geothing,如果我创建一个PolygonGeothing或CircleGeothing并返回它然后它工作正常...但是如果我尝试将PolygonGeothing或CircleGeothing作为参数传递,其中param类型是Geothing。

@Path("/geothing/{id}")
public interface GeothingService extends CoService {
    @POST
    Response createGeothing(@PathParam("{id}") Long id, Geothing geothing);
}

1 个答案:

答案 0 :(得分:1)

这样做是不可能的。原因很简单:CXF(与任何其他JAX-RS框架一样)基于REST定义而不是基于面向对象的主体来路由响应。 我的意思是它选择基于URL的方法,生成的内容类型和消费的内容类型。 (这是简化的描述,请参阅JSR311以获取精确算法)。但它与您期望的对象无关。只有在选择了方法后,对象才会被序列化。这是您获得异常的原因:createGeothing(@PathParam("{id}") Long id, PolygonGeothing geothing)已被选中,因此它会尝试序列化错误的类。

您可以执行以下操作:

Response createGeothing(@PathParam("{id}") Long id, Geothing geothing)

而不是演员并打电话给相关方法 当然,您需要确保JAXB上下文已知Geothing。