How to solve circular reference in json serializer caused by many many many many types of bidirectional display hibernation?

I am trying to serialize a POJO for JSON but am stuck with a circular reference problem. I know how to handle one of many and inverse relationships using @JsonBackReference and @JsonManagedReference .

My problem is with the bi-directional many-to-many relationship (for example, a student can have many courses, and there can be many students in each course), parent links to child and child links back to parent, and here my serializer dies. In my understanding, I cannot use @JsonBackReference here, since the value type of the property must be bean: it cannot be Collection, Map, Array or an enumeration.

Can someone please tell me how I can handle this scenario?

+8
json spring hibernate circular-reference many-to-many
source share
5 answers

You can use @JsonIgnoreProperties("someField") on one side of the relationship (annotation is a class). Or @JsonIgnore

+8
source share

As @Bozho answered using @JsonIgnoreProperties, try this, it worked for me.

Below are my models with @JsonIgnoreProperties:

 @Entity public class Employee implements Serializable{ @ManyToMany(fetch=`enter code here`FetchType.LAZY) @JoinTable(name="edm_emp_dept_mappg", joinColumns={@JoinColumn(name="emp_id", referencedColumnName="id")}, inverseJoinColumns={@JoinColumn(name="dept_id", referencedColumnName="id")}) @JsonIgnoreProperties(value="employee") Set<Department> department = new HashSet<Department>(); } @Entity public class Department implements Serializable { @ManyToMany(fetch=FetchType.LAZY, mappedBy="department") @JsonIgnoreProperties(value="department") Set<Employee> employee = new HashSet<Employee>(); } 

In the value @JsonIgnoreProperties attribute, we need to provide a collection type property for the counted (bound) model.

+1
source share

You can also use Dozer mapping to convert POJOs to Map and exclude fields. For example, if we have two classes PojoA and PojoB having bidirectional relationships, we define a mapping like this

 <mapping map-id="mapA" map-null="false"> <class-a>com.example.PojoA</class-a> <class-b>java.util.Map</class-b> <field> <a>fieldA</a> <b>this</b> </field> <field map-id="mapB"> <a>pojoB</a> <b>this</b> <b-hint>java.util.Map</b-hint> </field> </mapping> <mapping map-id="mapB" map-null="false"> <class-a>com.example.PojoB</class-a> <class-b>java.util.Map</class-b> <field-exclude> <a>pojoA</a> <b>this</b> </field-exclude> </mapping> 

Then you define the bean parameter for the specified bulldozer file mapping file as a property.

 <bean id="mapper" class="org.dozer.DozerBeanMapper"> <property name="mappingFiles"> <list> <value>dozerMapping.xml</value> </list> </property> </bean> 

Then in the class where you serialize

 public class TestClass { @Autowired DozerBeanMapper mapper; public Map<String,Object> serializeObject(PojoA pojoA) { return ((Map<String, Object>) mapper.map(pojoA, Map.class, "mapA")); } } 

Bulldozer instruction manual is here .

0
source share

Outlining what @Bozho already mentioned ...

I'm stuck with Jackson 1 right now because I'm using Google Cloud Endpoints, so it can still help some people, although Jackson 2 hasn't been working for a long time. Although I do not need the entire deserialized object, the link is still very necessary.

I put @JsonIgnore in the fields that call the circular link, but then create a new getter for each of them so that the flat link still returns in my APIs.

 @JsonIgnore private FooClass foo; public String getFooKey() ... 

With cloud endpoints, this results in a flat "fooKey" returning to the GET payload, and "foo" to "foo".

0
source share

if you have a let it collection object

 collection<object> listobj var jsonObj = from c in listobj select new { Prop1 = c.Prop1 ... } 

This should work, and the object you get can now be serialized by json and its clean

-one
source share

All Articles