hibernate无限递归问题
项目异常如下:
2018-01-26 17:12:38.162 WARN 3128 --- [nio-8080-exec-6] .w.s.m.s.DefaultHandlerExceptionResolver : Failed to write HTTP message: org.springframework.http.converter.HttpMessageNotWritableException: Could not write JSON: Infinite recursion (StackOverflowError); nested exception is com.fasterxml.jackson.databind.JsonMappingException: Infinite recursion (StackOverflowError) (through reference chain: demo.server.core.domain.User["userAddresses"]->
org.hibernate.collection.internal.PersistentBag[0]->
demo.server.core.domain.UserAddress["user"]->
demo.server.core.domain.User["userAddresses"]->
org.hibernate.collection.internal.PersistentBag[0]->
demo.server.core.domain.UserAddress["user"]->
......//无限递归
java.lang.StackOverflowError: null
at java.lang.ClassLoader.defineClass1(Native Method) ~[na:1.8.0_111]
at java.lang.ClassLoader.defineClass(Unknown Source) ~[na:1.8.0_111]
at java.security.SecureClassLoader.defineClass(Unknown Source) ~[na:1.8.0_111]
at java.net.URLClassLoader.defineClass(Unknown Source) ~[na:1.8.0_111]
at java.net.URLClassLoader.access$100(Unknown Source) ~[na:1.8.0_111]
at java.net.URLClassLoader$1.run(Unknown Source) ~[na:1.8.0_111]
at java.net.URLClassLoader$1.run(Unknown Source) ~[na:1.8.0_111]
at java.security.AccessController.doPrivileged(Native Method) ~[na:1.8.0_111]
at java.net.URLClassLoader.findClass(Unknown Source) ~[na:1.8.0_111]
at java.lang.ClassLoader.loadClass(Unknown Source) ~[na:1.8.0_111]
at sun.misc.Launcher$AppClassLoader.loadClass(Unknown Source) ~[na:1.8.0_111]
at java.lang.ClassLoader.loadClass(Unknown Source) ~[na:1.8.0_111]
at com.fasterxml.jackson.databind.ser.std.BeanSerializerBase.serializeFields(BeanSerializerBase.java:709) ~[jackson-databind-2.8.1.jar:2.8.1]
at com.fasterxml.jackson.databind.ser.BeanSerializer.serialize(BeanSerializer.java:155) ~[jackson-databind-2.8.1.jar:2.8.1]
at com.fasterxml.jackson.databind.ser.std.CollectionSerializer.serializeContents(CollectionSerializer.java:149) ~[jackson-databind-2.8.1.jar:2.8.1]
at
...
看异常的名字会发现是栈溢出,而且第一处后面出现大量的递归的提示,这边的原因是因为使用了jpa的实体类注解@ManyToMany,@ManyToOne,@OneToOne并且是双向表关联
举个例子:
@Entity
@Table(name = "t_student")
public class Student{
@Id
@GeneratedValue
private Integer sId;
@Column(length = 20)
private String sName;
//学生所修课程
@ManyToMany(mappedBy = "students")
private List<Course> courses;
//get、set 方法省略
}
@Entity
@Table(name = "t_course")
public class Course{
@Id
@GeneratedValue
private Integer cId;
@Column(length = 20)
private String cName;
//上课的学生
@ManyToMany(cascade = CascadeType.ALL)
private List<Student> students;
//get、set 方法省略
}
一个student类和一个course类分别对应 t_student 表和 t_course表,它们是多对多的关系,一个学生可以修多个课程,一个课程可以有多个学生修
省略仓储层代码…
控制层代码
@RestController
public class TestController{
@Autowired
private StudentRepository studentRep;
@RequestMapping("/test")
public int test(){
List<Student> students = stntRep.findAll();
students.forEach(data->{
System.out.println(data);
});
return 1;
}
}
此时,程序运行便会报 java.lang.StackOverflowError: null 异常
java.lang.StackOverflowError: null
at java.util.AbstractCollection.toString(Unknown Source) ~[na:1.8.0_111]
at org.hibernate.collection.internal.PersistentBag.toString(PersistentBag.java:510) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
at java.lang.String.valueOf(Unknown Source) ~[na:1.8.0_111]
at java.lang.StringBuilder.append(Unknown Source) ~[na:1.8.0_111]
at com.demo.domain.Course.toString(Course.java:38) ~[classes/:na]
at java.lang.String.valueOf(Unknown Source) ~[na:1.8.0_111]
at java.lang.StringBuilder.append(Unknown Source) ~[na:1.8.0_111]
at java.util.AbstractCollection.toString(Unknown Source) ~[na:1.8.0_111]
at org.hibernate.collection.internal.PersistentBag.toString(PersistentBag.java:510) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
at java.lang.String.valueOf(Unknown Source) ~[na:1.8.0_111]
at java.lang.StringBuilder.append(Unknown Source) ~[na:1.8.0_111]
at com.demo.domain.Student.toString(Student.java:40) ~[classes/:na]
....
Student类中有一个字段List<Course> courses,在遍历集合中,输出一个student实例的时候,List<Course> courses 字段也将输出,因为是双向多对多的关联查询,每一个Course实例也会输出List<Student> students 字段值,因此一直递归下去直到栈溢出报错,若是单向多对多就不会发生这样地递归
其实一开始报这个错完全是因为对spring-data-jpa不熟悉,了解之后一想就通了。
解决办法:
方法一:
此处,若不需要查看关联表中的字段信息时,可以在遍历List<Student> students集合时先将关联对象设置为null,即:
students.forEach(data->{
data.setCourses(null);
System.out.println(data);
});
这样才能打印出Student 实例中除了courses 字段之外地所有数据
方法二:
取消使用双向多对多关联,改为使用单向多对多,这样也可以同时将关联表中所对应的数据查询出来使用
原文地址:https://blog.csdn.net/pbhLOVEpp/article/details/77945651
hibernate无限递归问题的更多相关文章
- -java转json hibernate懒加载造成的无限递归问题
1.在判断到底是谁维护关联关系时,可以通过查看外键,哪个实体类定义了外键,哪个类就负责维护关联关系. JoinColumn(name="pid") 2. 在保存数据时,总是先保存的 ...
- jackson java转json hibernate懒加载造成的无限递归问题
@JsonIgnore @JsonFilter @JsonBackReference @JsonManagedReference @JsonIgnoreProperties jackson中的@Jso ...
- JPA一对多循环引用的解决&&JackSon无限递归问题
说是解决,其实不是很完美的解决的,写出来只是想记录一下这个问题或者看一下有没有哪位仁兄会的,能否知道一二. 下面说说出现问题: 问题是这样的,当我查询一个一对多的实体的时候,工具直接就爆了,差不多我就 ...
- 无限递归的构造器和javap使用指南
无限递归的构造器和javap使用指南 public class ConstructorRecursion { ConstructorRecursion rc; { rc = newConstructo ...
- 无限“递归”的python程序
如果一个函数直接或者间接调用了自己,那么就形成了递归(recursion),比如斐波那契数列的一个实现 def fib(n): if n <= 2: return 1 else: return ...
- 【整理】iview Tree数据格式问题,无限递归树处理数据
iview Tree数据格式问题,无限递归树处理数据 https://juejin.im/post/5b51a8a4e51d455d6825be20
- C# .NetCore简单实现无限递归的功能
1:在实际开发中,我们会经常使用到无限递归的情况,如菜单,父子级等的情况 2:Code 1 using System; 2 using System.Collections.Generic; 3 us ...
- vue 无限递归级联组件实现方案
最终组件效果图: 无限级联组件实现思想: 在这里有一个很重要的地方就是前端组件如何与后端匹配方法协调好,无限级联很好实现,但是如何让服务器端可以成功的匹配到条件是一个问题,在这里我借鉴了html元素的 ...
- SqlServer与Linq 无限递归目录树且输出层级
ALTER VIEW [dbo].[view_TreeLevel] AS WITH cte AS ( SELECT a.ModuleID , a.Module_Name , a.Module_Desc ...
随机推荐
- 拦截导弹 (最长上升子序列LIS)
#include <iostream> #include <stdio.h> #include <algorithm> using namespace std; ] ...
- 使用Gradle构建项目
使用gradle构建项目之前,咱们先聊聊maven,使用maven构建项目和配置主要 接下来正式使用gradle来构建项目的和步骤: 1.下载源码 2.下载gradle 1.下载地址:https:// ...
- 并发模式与 RPS 模式之争,性能压测领域的星球大战
本文是<如何做好性能压测>系列专题分享的第四期,该专题将从性能压测的设计.实现.执行.监控.问题定位和分析.应用场景等多个纬度对性能压测的全过程进行拆解,以帮助大家构建完整的性能压测的理论 ...
- maven与sbt修改国内镜像
一.idea中的maven 1.打开IntelliJ IDEA->Settings ->Build, Execution, Deployment -> Build Tools > ...
- 如何写JavaScript中的callback回调函数
如何写回调函数? 如果自己在写一个方法或函数,你有可能会遇到需要一个回调函数.下面就是一个简单的常见回调函数例子: function mySandwich(param1, param2, callba ...
- SWF在线绘本批量制作高质量PDF的新方法(重点在批量制作)
SWF在线绘本批量制作高质量PDF的新方法(重点在批量制作) 2012-12-21 未来决定... http://www.ebama.net/thread-107643-1-1.html ...
- Map容器案例
案例讲解 --统计字符串出现的次数 package com.date; import java.util.HashMap; import java.util.Map; import java.uti ...
- (五)IO流之ByteArrayInput/OutputStream
ByteArrayInputStream:是把字节数组当成源的输入流 String string="hello shanghai"; ByteArrayInputStream bi ...
- Unicode与FFFE(记一个蛋疼的项目)
好久没更新博客了. 近期忙着一个项目, 还要应付各种考试就顾不上博客了. 今天遇到了一个蛋疼的问题, 通过BLE4.0与蓝牙外设通信. 按照客户给的协议文档发送的数据, 可是外设不能正确识别.折腾了一 ...
- @bzoj - 4298@ [ONTAK2015]Bajtocja
目录 @description@ @solution@ @accepted code@ @details@ @description@ 给定d张无向图,每张图都有n个点.一开始,在任何一张图中都没有任 ...