You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Jakarta EE 10序列化Person实体触发递归检查异常求助

解决Jakarta EE 10(WildFly 31)下JSON序列化递归引用异常问题

问题根源

WildFly 31默认使用Eclipse Yasson作为Jakarta JSON-B的实现,而Java EE 8通常采用MOXy(JAXB实现)处理JSON序列化。你在角色实体上标注的@XmlTransient是JAXB注解,Yasson并不会优先识别它,因此双向关联的递归引用依然会触发序列化异常。

解决方案

针对Yasson的特性,用JSON-B原生注解替代或补充JAXB注解,即可解决递归问题:

方案1:使用@JsonbTransient忽略反向关联

直接在角色实体的person属性上替换@XmlTransient为JSON-B的@JsonbTransient注解,标记该属性不参与序列化:

public class Player {
    @OneToOne(mappedBy = "player")
    @JsonbTransient // 替换原@XmlTransient
    private Person person;

    // 其他字段、getter/setter
}

// Coach、Referee类做同样修改

方案2:用@JsonbManagedReference + @JsonbBackReference处理双向关联

如果需要保留双向关联的序列化逻辑(仅避免递归),可以用这对注解明确关联方向:

  • 在Person实体的角色关联字段上标注@JsonbManagedReference(主动序列化端):
public class Person {
    @OneToOne(cascade = CascadeType.ALL)
    @JoinColumn(name = "player_id")
    @JsonbManagedReference
    private Player player;

    @OneToOne(cascade = CascadeType.ALL)
    @JoinColumn(name = "coach_id")
    @JsonbManagedReference
    private Coach coach;

    @OneToOne(cascade = CascadeType.ALL)
    @JoinColumn(name = "referee_id")
    @JsonbManagedReference
    private Referee referee;

    // 其他字段、getter/setter
}
  • 在角色实体的person属性上标注@JsonbBackReference(被动忽略端):
public class Player {
    @OneToOne(mappedBy = "player")
    @JsonbBackReference
    private Person person;

    // 其他字段、getter/setter
}

// Coach、Referee类做同样修改

方案3:配置Yasson忽略未初始化的延迟加载对象

如果关联使用了FetchType.LAZY,Yasson序列化时可能触发代理对象加载导致递归,可以通过JSON-B配置忽略未初始化的属性:
创建JsonbConfig实例并设置序列化规则,在REST端点中使用:

@Provider
public class JsonbConfigProvider implements ContextResolver<Jsonb> {
    @Override
    public Jsonb getContext(Class<?> type) {
        JsonbConfig config = new JsonbConfig()
                .withSerializationInclusion(JsonbSerializationInclusion.NON_EMPTY)
                .withPropertyVisibilityStrategy(new PropertyVisibilityStrategy() {
                    @Override
                    public boolean isVisible(Field field) {
                        return true;
                    }

                    @Override
                    public boolean isVisible(Method method) {
                        return true;
                    }
                });
        return JsonbBuilder.create(config);
    }
}

验证

修改后重新部署服务,序列化Person列表时会自动跳过角色实体中指向Person的反向引用,避免递归异常,同时保留Person的角色信息正常输出。

内容的提问来源于stack exchange,提问作者Kawu

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.29 00:26:24