0

I faced the problem when I need to partially udate data in BD.

What I have: I have three linked entities:

Profile --(1-m)--> Person --(1-1)--> Address

Where Person -> Address is lazy relationship. It was achieved via optional=false option (that allow hibernate to use proxy).

What the problem:

I need to update Profile in such way, that I needn't pull all Addresses that linked with this profile.

When I update Profile (don't work):

profile.setPersons(persons);
session.saveOrUpdate(profile);

throws: org.springframework.dao.DataIntegrityViolationException: not null property references a null or transient value

It happens because Person->Address relationship has optional=false option

I need to do:

//for each person
Address address = requestAddressFromDB();
person.setAddress(address);
persons.add(person)
//and only then
profile.setPersons(persons);
session.saveOrUpdate(profile);
profile.setPerson(person)

But I don't want to pull all address each time I update Profile name.

What is the question:

How can I avoid obligatory Person->(not null)Address constraint to save my profile without pulling all addresses?

ADDITION:

@Entity
public class Person{

  @Id
  @SequenceGenerator(name = "person_sequence", sequenceName = "sq_person")
  @GeneratedValue(strategy = GenerationType.SEQUENCE, generator = "person_sequence")
  @Column(name = "id")
  private long personID;

  @OneToOne(mappedBy="person", cascade=CascadeType.ALL, optional = false, fetch = FetchType.LAZY)
  private Address address;
  //.. getters, setters
}

@Entity
public class Address {

  @Id
  @Column(name="id", unique=true, nullable=false)
  @GeneratedValue(generator="gen")
  @GenericGenerator(name="gen", strategy="foreign", parameters=@Parameter(name="property", value="person"))
  private long personID;

  @PrimaryKeyJoinColumn
  @OneToOne
  private FileInfo person;
}
buræquete
  • 14,226
  • 4
  • 44
  • 89
VB_
  • 45,112
  • 42
  • 145
  • 293

1 Answers1

1

Modify the cascade element on the @OneToOne annotation so that the PERSIST operation is not cascaded. This may require you to manually persist updates to Address in certain areas of your code. If the cascade is not really used however no change is needed.

@OneToOne(mappedBy="person", cascade={CascadeType.MERGE, CascadeType.REMOVE, CascadeType.REFRESH}, optional = false, fetch = FetchType.LAZY)
private Adress address;  //Do you know that Address is missing a 'd'?
buræquete
  • 14,226
  • 4
  • 44
  • 89
Kevin Bowersox
  • 93,289
  • 19
  • 159
  • 189