如何通过CrudRepository保存包含另一个的新实体已存在于数据库中?

时间:2017-08-30 15:22:18

标签: spring entity-framework hibernate rest jpa

我正在尝试使用json将数据添加到数据库中:

{
    "id": null,
    "basicInfo": {
        "firstName": "Mistral",
        "lastName": "Castrol",
        "pesel": "45789623456",
        "startDate": "2017-02-12"
    },
    "contactInfo": {
        "id": null,
        "email": "wp@pw.pl",
        "phoneNumber": "456789123",
        "address": {
            "houseNamber": 53,
            "apartmentNumber": 25,
            "street": {
                "id": 1,
                "name": "Koszmarna",
                "city": {
                    "id": 2,
                    "name": "Radzyń Podlaski",
                    "voivodeship": {
                        "id": 2,
                        "name": "mazowieckie"
                    },
                    "zipCode": "21-307"
                }
            }
        }
    },
    "bornInfo": {
        "id": null,
        "bornDate": "2018-02-14",
        "city": {
            "id": 1,
            "name": "Siedlce",
            "voivodeship": {
                "id": 1,
                "name": "śląskie"
            },
            "zipCode": "21-307"
        }
    }
}

。我失去了耐心。经过大量的谷歌搜索和尝试,我坚持这个错误:

  

“message”:“传递给persist的分离实体:pl.dn.model.placeInfo.City;嵌套异常是org.hibernate.PersistentObjectException:传递给persist的分离实体:pl.dn.model.placeInfo.City”< / p>

问题是城市实体(分离)已经存在于数据库中但是另一个数据如firstName,second是transisent实体的一部分。我不知道我应该 修改json或模型。

模特:

主持人

@Entity
public class Moderator {

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

    @Embedded
    private BasicInfo basicInfo;

    @OneToOne(cascade = CascadeType.ALL)
    @JoinColumn(name = "contact_info_id")
    private ModeratorContactInfo contactInfo;

    @OneToOne(cascade = CascadeType.ALL)
    @JoinColumn(name = "born_info_id")
    private ModeratorBornInfo bornInfo;

}

ModeratorContactInfo

@Entity
@Table(name = "moderator_contact_info")
public class ModeratorContactInfo {

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

    private String email;

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

    @Embedded
    private Address address;

}

地址

@Embeddable
public class Address {

    @Column(name = "house_number")
    private long houseNamber;

    @Column(name = "apratment_number")
    private long apartmentNumber;

    @ManyToOne(cascade = CascadeType.ALL)
    @JoinColumn(name = "street_id")
    private Street street;

}

@Entity
public class Street {

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

    private String name;

    @ManyToOne(cascade = CascadeType.ALL, fetch = FetchType.EAGER)
    @JoinColumn(name = "city_id")
    private City city;

}

@Entity
@Table(name = "city")
public class City {

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

    private String name;

    @ManyToOne(cascade = CascadeType.ALL)
    @JoinColumn(name = "voivodeship_id")
    private Voivodeship voivodeship;

    @Column(name = "zip_code", length = 6)
    private String zipCode;
}

@Entity
public class Voivodeship {

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

    private String name;

}

最后控制器方法:

@RequestMapping(value = "add", method = RequestMethod.POST)
    public String addModerator(@RequestBody Moderator moderator) {

        return moderatorDao.save(moderator).toString();

    }

时间解决方案:

如果我从数据库加载城市并设置为用户,则可以使用,但我必须使用主持人中的所有实体。

@RequestMapping(value = "add", method = RequestMethod.POST)
    public String addModerator(@RequestBody Moderator moderator) {

        long bornCityId = moderator.getBornInfo().getCity().getId();
        long contactCityId = moderator.getContactInfo().getAddress().getStreet().getCity().getId();

        if (! (bornCityId == 0)) {
            City city = cityDao.findById(bornCityId);
            moderator.getBornInfo().setCity(city);
        }

        if (! (contactCityId == 0)) {
            City city = cityDao.findById(contactCityId);
            moderator.getContactInfo().getAddress().getStreet().setCity(city);
        }

        return moderatorDao.save(moderator).toString();

    }

1 个答案:

答案 0 :(得分:0)

我使用ModeratorService来解决这个问题:

@Service
public class ModeratorService  {

    @Autowired
    private SessionFactory sessionFactory;

    @Transactional
    public Moderator save(Moderator moderator) {

        Session session = sessionFactory.getCurrentSession();
        session.saveOrUpdate(moderator);

        return moderator;
    }

}

并更改Controller的方法:

    @RequestMapping(value = "add", method = RequestMethod.POST)
    public String add(@RequestBody Moderator moderator) {

        return moderatorService.save(moderator).toString();

    }