当前位置:  开发笔记 > 编程语言 > 正文

org.codehaus.jackson.map.JsonMappingException:无限递归(StackOverflowError)

如何解决《org.codehaus.jackson.map.JsonMappingException:无限递归(StackOverflowError)》经验,为你挑选了1个好方法。

我正在尝试一些非常基本的Web服务.每当我尝试返回Prtnr对象时,我都会收到此异常.

Uncaught exception thrown in one of the service methods of the servlet: spitter. Exception thrown : 
org.codehaus.jackson.map.JsonMappingException: Infinite recursion (StackOverflowError) 
(through reference chain: org.hibernate.collection.PersistentSet[0]->org.abc.dvo.PrtnrGeoInfo["id"]->org.abc.dvo.PrtnrGeoInfoId["partner"]->
org.abc.dvo.Prtnr["prtnrGeoInfos"]->org.hibernate.collection.PersistentSet[0]->org.abc.dvo.PrtnrGeoInfo["id"]->org.abc.dvo.PrtnrGeoInfoId["partner"]->
org.abc.dvo.Prtnr["prtnrGeoInfos"]->org.hibernate.collection.PersistentSet[0]->org.abc.dvo.PrtnrGeoInfo["id"]->org.abc.dvo.PrtnrGeoInfoId["partner"]->
org.abc.dvo.Prtnr["prtnrGeoInfos"]->org.hibernate.collection.PersistentSet[0]->org.abc.dvo.PrtnrGeoInfo["id"]->org.abc.dvo.PrtnrGeoInfoId["partner"]->
...
    at org.codehaus.jackson.map.ser.std.BeanSerializerBase.serializeFields(BeanSerializerBase.java:164)
    at org.codehaus.jackson.map.ser.BeanSerializer.serialize(BeanSerializer.java:112)
    at org.codehaus.jackson.map.ser.BeanPropertyWriter.serializeAsField(BeanPropertyWriter.java:446)
    at org.codehaus.jackson.map.ser.std.BeanSerializerBase.serializeFields(BeanSerializerBase.java:150)
    ...

Prtnr课程是:

public class Prtnr implements Cloneable, java.io.Serializable {

    private static final long serialVersionUID = 201207021420600052L;
    private Integer prtnrId;
    private String creatUserId;
    private Date creatTs;
    private String updtUserId;
    private Date updtTs;
    private String prtnrNm;
    private Integer cncilNum;
    private Character prtnrTypCd;
    private Set prtnrGeoInfos = new HashSet(0);
    private Set prtnrDtls = new HashSet(0);
    private Set suplyDtls = new HashSet(0);
    private Set trnsprtDtls = new HashSet(0);
    private Set prtnrFacils = new HashSet(0);
    private Set prtnrHumanResrcs = new HashSet(0);
    .....
    .....
    Getters and setters for these properties
    ...
}

PrtnrGeoInfo类是:

public class PrtnrGeoInfo implements java.io.Serializable {
    private PrtnrGeoInfoId id = new PrtnrGeoInfoId();
    private String creatUserId;
    private Date creatTs;
    private String updtUserId;
    private Date updtTs;

    Getters and setters for these properties

}

PrtnrGeoInfoId类是:

public class PrtnrGeoInfoId implements java.io.Serializable {   
    private Prtnr partner;
    private GeoSegment geoSegment;
    private static final long serialVersionUID = 201207060857580050L;

    Getters and setters for these properties
}

我相信这是因为课堂相互融合.但是如何解决这个问题呢.在Struts 2和Spring的应用程序中,这个对象传递得很好.

控制器类如下:

@Controller
@RequestMapping("/partners")
public class PartnerController {
    @RequestMapping(value="/{id}", method=RequestMethod.GET, headers ={"Accept=text/xml,application/json"})
    @ResponseBody
    public Prtnr getPartner(@PathVariable("id") String id) throws Exception{
        Prtnr partner = null;
        try{
            partner = partnerService.getPartnerById(Integer.valueOf(id));
                System.out.println("******* Test message " );
        }catch(Exception ex){
            System.out.println("******* Exception thrown ... " + ex.getMessage());
        }

        return partner;
    }
}

调用类是公共类TestTemplate {

    private static final long serialVersionUID = 1130201273334264152L;
    public static void main(String[] args){
        Prtnr partner = (Prtnr)new RestTemplate().getForObject("http://localhost:9080/respondersApp/testWs/partners/{id}", Prtnr.class, "1");
        System.out.println("partner name is : " + partner.getPrtnrNm());
    }
}

madx.. 6

在此链接中,您可以找到如何解决此问题.

但是下面我会在实践中粘贴解决方案.

这很简单.假设您的数据库查询已经在没有JSON的情况下工作,您所要做的就是:

添加@JsonManagedReference在关系的前面部分(即User.java类):

@Entity
public class User implements java.io.Serializable{

 @Id
 @GeneratedValue(strategy=GenerationType.IDENTITY)
 private long id;

 @Column(name="name")
 private String name;

 @ManyToMany
 @JoinTable(name="users_roles",joinColumns=@JoinColumn(name = "user_fk"),
 inverseJoinColumns=@JoinColumn(name = "role_fk"))
 @JsonManagedReference
 private Set roles = new HashSet();

...

添加@JsonBackReference在关系的后面部分(即Role.java类):

@Entity
public class Role implements java.io.Serializable {

 @Id 
 @GeneratedValue(strategy=GenerationType.IDENTITY)
 private int id;

 @ManyToMany(mappedBy="roles")
 @JsonBackReference
 private Set users = new HashSet();

...

工作完成了.如果你看一下你的firebug日志,你会发现无限递归循环已经消失了.



1> madx..:

在此链接中,您可以找到如何解决此问题.

但是下面我会在实践中粘贴解决方案.

这很简单.假设您的数据库查询已经在没有JSON的情况下工作,您所要做的就是:

添加@JsonManagedReference在关系的前面部分(即User.java类):

@Entity
public class User implements java.io.Serializable{

 @Id
 @GeneratedValue(strategy=GenerationType.IDENTITY)
 private long id;

 @Column(name="name")
 private String name;

 @ManyToMany
 @JoinTable(name="users_roles",joinColumns=@JoinColumn(name = "user_fk"),
 inverseJoinColumns=@JoinColumn(name = "role_fk"))
 @JsonManagedReference
 private Set roles = new HashSet();

...

添加@JsonBackReference在关系的后面部分(即Role.java类):

@Entity
public class Role implements java.io.Serializable {

 @Id 
 @GeneratedValue(strategy=GenerationType.IDENTITY)
 private int id;

 @ManyToMany(mappedBy="roles")
 @JsonBackReference
 private Set users = new HashSet();

...

工作完成了.如果你看一下你的firebug日志,你会发现无限递归循环已经消失了.

推荐阅读
放ch养奶牛
这个屌丝很懒,什么也没留下!
DevBox开发工具箱 | 专业的在线开发工具网站    京公网安备 11010802040832号  |  京ICP备19059560号-6
Copyright © 1998 - 2020 DevBox.CN. All Rights Reserved devBox.cn 开发工具箱 版权所有