Reputation: 447
Newbie to Hibernate here. I'm building a simple app to play around with Hibernate and I'm getting the hang of most of the annotations but the mappings are really confusing me.
I have a Person
class and I have a Note
's class. A person can have many notes associated with them but a single note will only ever correspond to a specific person.
I'm trying to set it up so that the note
table has a column called person_id
such that I won't need an extra person_note
table in the database for the associations.
How would I go about setting up the annotations such that an extra table is not created in the database and I can associate multiple notes to a single person via an extra column in the note
's table?
I've tried a few options after searching on Google such as using annotations like this but with no luck:
@JoinColumn(name="id_person", nullable=false)
Person Class
@Entity
@Table(name = "person")
public class Person {
@OneToMany()
private Set<Note> notes;
public Set<Note> getNotes() {
return notes;
}
public void setNotes(Set<Note> notes) {
this.notes = notes;
}
...
}
Note Class
@Entity
@Table (name = "note")
public class Note {
@ManyToOne
private Person person;
public Person getPerson() {
return person;
}
public void setPerson(Person person) {
this.person = person;
}
...
}
Any help would be appreciated. Thank you.
For the benefit of anyone looking in the future, I now don't have a separate table for mapping note
objects to people
objects. The final code (with extra lines removed) now looks like this:
Person Class
@Entity
@Table(name = "person")
public class Person {
@OneToMany(fetch = FetchType.EAGER, mappedBy = "person", cascade = CascadeType.ALL)
private Set<Note> notes;
...
}
Note Class
@Entity
@Table (name = "note")
public class Note {
@ManyToOne(fetch = FetchType.EAGER)
@JoinColumn(name = "id_person", nullable = false)
private Person person;
...
}
Misc Points
cascade = CascadeType.ALL
in the Person
class to ensure that when I saved a Person
object that all the Note
objects inside were saved. Upvotes: 2
Views: 2967
Reputation: 1374
I agree with you. One can implement what you're asking with only the two tables you already have.
Here is what I would do:
Database wise:
Table Person, with: PK column: person_id
Table Note, with:
Purpose:
person_id - reference to the PK of the Person table. That will define the [Person : Note] relationship, where 1 person can have multiple notes.
assigned_person_id - reference to the person assigned to the note. However to guarantee your requirement that only one person can be assigned to a note - add an unique index by that column. That will guarantee that the same person_id was on used for another note record.
Hibernate wise:
Note that the code snippet is not complete! It is just pointing the important moments. You can look at one of the many complete examples, for instance: http://www.mkyong.com/hibernate/hibernate-one-to-many-relationship-example-annotation/
public class Person {
@OneToMany(fetch = FetchType.LAZY, mappedBy = "person")
public setNotes(Set<Note> notes) {
this.notes=notes;
}
...
}
@Table(name = "note", catalog = "schema_name",
uniqueConstraints = @UniqueConstraint(columnNames = "assigned_person_id"))
public class Note {
private Person person;
private Person assignedPerson;
@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name = "person_id", nullable = false)
public Person getPerson() {
return person;
}
public Person getAssignedPerson() {
return assignedPerson;
}
...
}
Upvotes: 0
Reputation: 32145
In your mapping annotations you should map the entities with a mappedBy
property in the @OneToMany
annotation and specify a joinColumn under the @ManyToOne
annotation using the @JoinColumn
annotation, Change your code like this:
Person class:
@OneToMany(mappedBy = "person") // "person" here refers to the person property in the notes class
private Set<Note> notes;
Notes class:
@ManyToOne
@JoinColumn(name = "id_person", nullable = false)
private Person person;
Take a look at Hibernate Collection mapping for further information.
Upvotes: 2
Reputation: 7042
Edit Person
@OneToMany(fetch = FetchType.EAGER , mappedBy = "person")
private Set<Note> notes;
And Note
@ManyToOne(fetch = FetchType.EAGER)
@JoinColumn(name = "person_id", nullable = false)
private Person person;
Upvotes: 1