我正在使用ManyToOne,OneToMany并且获取数据时有无限循环 [英] I am using ManyToOne , OneToMany and have endless loop when getting data

查看:510
本文介绍了我正在使用ManyToOne,OneToMany并且获取数据时有无限循环的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我在休眠状态下使用ManyToOne和OneToMany.我想创建一个具有位置的用户. 当我在邮递员中获取数据时,我会无休止地循环,因为当我获取用户时,它会显示用户的位置,而在位置中则显示用户,依此类推.这是代码:

位置信息类:

 @ManyToOne(fetch = FetchType.LAZY,cascade = CascadeType.ALL)
    @JoinColumn(name=FLD_LOC, nullable=false)
    private Consumer consumers;

    public Consumption(String location, float consumpiton,Consumer consumer) {
        this.location = location;
        this.consumpiton = consumpiton;
        this.consumers=consumer;

    }

用户类别:

@OneToMany(mappedBy = Consumption.FLD_LOC,orphanRemoval = true)
private List<Consumption> locations ;


public Consumer(String clientId, String name,String location, float pwConsumption, String email, String password, String roles) {
    super(clientId, name, email, password, roles);
    this.locations=new ArrayList<>();
    this.location=location;
    this.pwcons=pwConsumption;

}

但是在数据库中,它是在用户表中存储位置名称,在位置表中存储用户ID

这是问题的模样:

"id": 2,
        "version": 1,
        "updated": "2020-06-28T15:41:49.082",
        "clientId": "admin",
        "name": "admin",
        "email": "admin123@gmail.com",
        "password": "$2a$10$hgcTSHjGpxEPg6WNb0U7ouHR5J5YYR5l1XVAejdK8JsG9w2Bko00a",
        "active": true,
        "roles": "ROLE_ADMIN",
        "locations": [
            {
                "locationsid": 1,
                "location": "Pecs",
                "consumpiton": 0.0,
                "consumers": {
                    "id": 2,
                    "version": 1,
                    "updated": "2020-06-28T15:41:49.082",
                    "clientId": "admin",
                    "name": "admin",
                    "email": "admin123@gmail.com",
                    "password": "$2a$10$hgcTSHjGpxEPg6WNb0U7ouHR5J5YYR5l1XVAejdK8JsG9w2Bko00a",
                    "active": true,
                    "roles": "ROLE_ADMIN",
                    "locations": [
                        {
                            "locationsid": 1,
                            "location": "Pecs",
                            "consumpiton": 0.0,
                            "consumers": {
                                "id": 2,
                                "version": 1,
                                "updated": "2020-06-28T15:41:49.082",
                                "clientId": "admin",
                                "name": "admin",
                                "email": "admin123@gmail.com",
                                "password": "$2a$10$hgcTSHjGpxEPg6WNb0U7ouHR5J5YYR5l1XVAejdK8JsG9w2Bko00a",
                                "active": true,
                                "roles": "ROLE_ADMIN",
                                "locations": [
                                    {
                                        "locationsid": 1,
                                        "location": "Pecs",

如何使其仅在JSON位置部分中显示位置名称或ID?

解决方案

问题

当您必须序列化具有双向关系的对象时,这是一个普遍的问题.

解决方案

向串行器发出信号,当遇到双向关系时在何处停止

  1. 第一种方法是创建自定义DTO,然后从其余控制器返回它们.在DTO中,将用locationDto填充customerDtolocation字段,但是设置locationDtocustomer字段,该字段将为空. /p>

  2. 第二种方法次之.但是我们可以通过添加@JsonManagedReference@JsonBackReference来告诉Jackson库不要递归序列化它.

  • 替换

   @OneToMany(mappedBy = Consumption.FLD_LOC,orphanRemoval = true)
   private List<Consumption> locations ;

        with

    @OneToMany(mappedBy = Consumption.FLD_LOC,orphanRemoval = true)
    @JsonManagedReference
    private List<Consumption> locations ;

  • 替换

    @ManyToOne(fetch = FetchType.LAZY,cascade = CascadeType.ALL)
    @JoinColumn(name=FLD_LOC, nullable=false)
    private Consumer consumers;

       with

    @ManyToOne(fetch = FetchType.LAZY,cascade = CascadeType.ALL)
    @JoinColumn(name=FLD_LOC, nullable=false)
    @JsonBackReference
    private Consumer consumers;

注意:

在生产系统中,我们不会公开域对象的所有字段,因为它可以具有许多不应暴露给外部的内部字段.这是原因,首选第一种方法

I am using ManyToOne and OneToMany in hibernate .I want to create a user who has locations. When I get data in postman I have endless loop because when I get user it's showing a user's location and in location showing user and so on. Here is code:

Locations class :

 @ManyToOne(fetch = FetchType.LAZY,cascade = CascadeType.ALL)
    @JoinColumn(name=FLD_LOC, nullable=false)
    private Consumer consumers;

    public Consumption(String location, float consumpiton,Consumer consumer) {
        this.location = location;
        this.consumpiton = consumpiton;
        this.consumers=consumer;

    }

User class :

@OneToMany(mappedBy = Consumption.FLD_LOC,orphanRemoval = true)
private List<Consumption> locations ;


public Consumer(String clientId, String name,String location, float pwConsumption, String email, String password, String roles) {
    super(clientId, name, email, password, roles);
    this.locations=new ArrayList<>();
    this.location=location;
    this.pwcons=pwConsumption;

}

But in database it's storing name of location in users table and id of user in locations table

Here is problem looks like :

"id": 2,
        "version": 1,
        "updated": "2020-06-28T15:41:49.082",
        "clientId": "admin",
        "name": "admin",
        "email": "admin123@gmail.com",
        "password": "$2a$10$hgcTSHjGpxEPg6WNb0U7ouHR5J5YYR5l1XVAejdK8JsG9w2Bko00a",
        "active": true,
        "roles": "ROLE_ADMIN",
        "locations": [
            {
                "locationsid": 1,
                "location": "Pecs",
                "consumpiton": 0.0,
                "consumers": {
                    "id": 2,
                    "version": 1,
                    "updated": "2020-06-28T15:41:49.082",
                    "clientId": "admin",
                    "name": "admin",
                    "email": "admin123@gmail.com",
                    "password": "$2a$10$hgcTSHjGpxEPg6WNb0U7ouHR5J5YYR5l1XVAejdK8JsG9w2Bko00a",
                    "active": true,
                    "roles": "ROLE_ADMIN",
                    "locations": [
                        {
                            "locationsid": 1,
                            "location": "Pecs",
                            "consumpiton": 0.0,
                            "consumers": {
                                "id": 2,
                                "version": 1,
                                "updated": "2020-06-28T15:41:49.082",
                                "clientId": "admin",
                                "name": "admin",
                                "email": "admin123@gmail.com",
                                "password": "$2a$10$hgcTSHjGpxEPg6WNb0U7ouHR5J5YYR5l1XVAejdK8JsG9w2Bko00a",
                                "active": true,
                                "roles": "ROLE_ADMIN",
                                "locations": [
                                    {
                                        "locationsid": 1,
                                        "location": "Pecs",

How to let it show in JSON Locations part only name of location or id?

解决方案

Problem

This is generic issue when you have to serialise objects with bidirectional relationship.

Solution

Signal the serialiser where to stop when facing bidirectional relationship

  1. First approach is to create custom DTOs and return them from your rest controller. In the DTOs, you will populate the location field of the customerDto with locationDtos but you will NOT set the customer field of locationDto and it will be null.

  2. Second approach is less preferred. But we can tell the Jackson library to not to serialise it recursively by adding @JsonManagedReference and @JsonBackReference.

  • Replace

   @OneToMany(mappedBy = Consumption.FLD_LOC,orphanRemoval = true)
   private List<Consumption> locations ;

        with

    @OneToMany(mappedBy = Consumption.FLD_LOC,orphanRemoval = true)
    @JsonManagedReference
    private List<Consumption> locations ;

  • Replace

    @ManyToOne(fetch = FetchType.LAZY,cascade = CascadeType.ALL)
    @JoinColumn(name=FLD_LOC, nullable=false)
    private Consumer consumers;

       with

    @ManyToOne(fetch = FetchType.LAZY,cascade = CascadeType.ALL)
    @JoinColumn(name=FLD_LOC, nullable=false)
    @JsonBackReference
    private Consumer consumers;

Note:

In production systems, we don't expose all the fields of domain objects as it can have many internal fields which should not be exposed to outside. It is the reason, first approach is preferred

这篇关于我正在使用ManyToOne,OneToMany并且获取数据时有无限循环的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆