使用 @XmlIDREF 避免 JAXB 循环引用

发布于 2024-09-10 10:00:49 字数 1040 浏览 6 评论 0原文

我在 Web 服务中使用 JAXB 和一些稍微复杂的对象。其中一个对象 Sensor 有一个可以与之通信的其他对象的列表,这些对象必然可以包含其自身(无法更改的行为),从而导致在编组到 XML 期间出现循环引用。

@XmlAccessorType(XmlAccessType.FIELD)
public class Sensor extends BaseObject {
    private ArrayList<SensorCommLink> sensorCommLinks;
}

@XmlAccessorType(XmlAccessType.FIELD)
public class SensorCommLink {

    @XmlIDREF
    private BaseObject receiver;
    @XmlIDREF
    private Sensor cueingSensor;
}

@XmlAccessorType(XmlAccessType.FIELD)
public abstract class BaseObject {

    @XmlElement 
    @XmlID
    private String id;
}

如上所示,我使用 @XmlIDREF 和 @XmlID 解决了这个问题,并且效果非常好。

通过 wsimport 生成的客户端代码将对象编组为 XML,并且服务器能够完美地解组它们。

我遇到的问题是,由于某种原因,当我尝试封送传感器对象时,在服务器端出现循环引用异常。令人抓狂的部分是,服务器端代码包含 wsimport 用于创建客户端代码的 JAXB 注释,效果很好,但由于循环原因,我无法编组服务器端传感器。

我尝试将 JAXB 添加到客户端代码的所有额外注释复制到服务器端类上,认为 JAXB 中可能存在运行时错误,导致它无法正确应用 @XmlIDREF 注释。那里没有运气。

也许我在这里遗漏了一些非常基本的东西,但这个问题让我有点抓狂,当我试图弄清楚它时,我陷入了僵局。

我确实注意到我正在调查的一件事是,生成的客户端对象上的一些名称空间不是我所期望的,尽管代码可以工作。我很好奇服务器上的名称空间问题是否会导致 IDREF 编组崩溃。

I'm using JAXB in a web service with some slightly complex objects. One of the objects, Sensor, has a list of other objects it can communicate with, which necessarily can include itself (behavior that cannot be changed), leading to a cyclic reference during marshalling to XML.

@XmlAccessorType(XmlAccessType.FIELD)
public class Sensor extends BaseObject {
    private ArrayList<SensorCommLink> sensorCommLinks;
}

@XmlAccessorType(XmlAccessType.FIELD)
public class SensorCommLink {

    @XmlIDREF
    private BaseObject receiver;
    @XmlIDREF
    private Sensor cueingSensor;
}

@XmlAccessorType(XmlAccessType.FIELD)
public abstract class BaseObject {

    @XmlElement 
    @XmlID
    private String id;
}

As shown above I solved this using @XmlIDREF and @XmlID and it works very nicely.

The client-side code generated via wsimport marshals the objects to XML and the server is able to unmarshal them perfectly.

The problem I'm experiencing is that for some reason on the server side I am getting a cyclic reference exception when I try to marshal a Sensor object. The maddening part is that the server-side code contains the JAXB annotations that are used by wsimport to create the client-side code, which works great, yet I can't marshal server-side Sensors due to the cycle.

I tried copying all of the extra annotations JAXB adds to the client-side code onto the server-side classes thinking perhaps there was a runtime bug in JAXB that was preventing it from properly applying the @XmlIDREF annotation. No luck there.

Perhaps there's something very basic I'm missing here but this issue is driving me a little batty and I'm at a dead stop while I try to figure it out.

One thing I did notice that I'm investigating is that some of the namespaces on the generated client-side objects aren't what I expected, though the code works. I'm curious to see if somehow a namespace issue on the server is causing the IDREF marshalling to bomb.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

烦人精 2024-09-17 10:00:49

在服务器端,它有可能处理属性(获取/设置)而不是字段(实例变量)。您可以通过以下方式强制执行字段访问:

@XmlAccessorType(XmlAccessType.FIELD)
public class SensorCommLink {

@XmlIDREF 
private BaseObject receiver; 
@XmlIDREF 
private Sensor cueingSensor; 

}

或者您可以注释 get 方法。

Any chance on the server side it is processing properties (get/set) instead of fields (instance variables). You can enforce field access in the following way:

@XmlAccessorType(XmlAccessType.FIELD)
public class SensorCommLink {

@XmlIDREF 
private BaseObject receiver; 
@XmlIDREF 
private Sensor cueingSensor; 

}

Or you could annotate the get methods.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文