Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

M:N relationship in JPA (wrapping given tables)

I have a m:n relationship book - borrow - user, the borrow is the join table.

The tables are given (can not be changed):

  • on one side they are used by jdbc app as well.
  • on the other side i would like to use them via jpa

book(book_id) - borrow(book_id,used_id) - user(user_id)

 used jpa annotations:
 User:
 @OneToMany(targetEntity=BorrowEntity.class, mappedBy="user")
 @JoinColumn(name="USER_ID", referencedColumnName="USER_ID")    
 private List<BorrowEntity>borrowings;

 Book: 
 @OneToMany(targetEntity=BorrowEntity.class, mappedBy="book")
 @JoinColumn(name="BOOK_ID", referencedColumnName="BOOK_ID")
 private List<BorrowEntity>borrowings;

My problem is that by the settings above it adds some extra (undesired) fields to the borrow table:

'user_USER_ID' and 'book_BOOK_ID'

How can I configure the jpa annotations to keep just Borrow:user_id,book_id which is enough the many to one ?

Take a look at the picture which tells more:

book borrowing

like image 235
cscsaba Avatar asked Jul 21 '12 21:07

cscsaba


People also ask

How do you model a many to many relationship in JPA?

Implementation in JPA Modeling a many-to-many relationship with POJOs is easy. We should include a Collection in both classes, which contains the elements of the others. After that, we need to mark the class with @Entity and the primary key with @Id to make them proper JPA entities.

What is one-to-one relationship mapping in JPA?

Now that we've set up the foundations of relationship mapping in JPA through One-to-Many/Many-to-One relationships and their settings, we can move on to One-to-One relationships. This time, instead of having a relationship between one entity on one side and a bunch of entities on the other, we'll have a maximum of one entity on each side.

What is entity relationships in JPA?

JPA - Entity Relationships. This chapter takes you through the relationships between Entities. Generally the relations are more effective between tables in the database. Here the entity classes are treated as relational tables (concept of JPA), therefore the relationships between Entity classes are as follows:

What is a join table in JPA?

Such a table is called a join table. In a join table, the combination of the foreign keys will be its composite primary key. 2.2. Implementation in JPA Modeling a many-to-many relationship with POJOs is easy. We should include a Collection in both classes, which contains the elements of the others.


1 Answers

First of all, since the borrow table is a pure join table, you don't need to map it at all. All you need is a ManyToMany association using this borrow table as JoinTable.

@ManyToMany
@JoinTable(name = "borrow",
           joinColumns = @JoinColumn(name = "USER_ID"),
           inverseJoinColumns = @JoinColumn(name = "BOOK_ID"))
private List<Book> borrowedBooks;
...

@ManyToMany(mappedBy = "borrowedBooks")
private List<User> borrowingUsers;

If you really want to map the join table as an entity, then it should contain two ManyToOne associations (one for each foreign key). So the following is wrong:

@OneToMany(targetEntity=BorrowEntity.class, mappedBy="user")
@JoinColumn(name="USER_ID", referencedColumnName="USER_ID")    
private List<BorrowEntity>borrowings;

Indeed, mappedBy means: this association is the inverse side of the bidirectional OneToMany/ManyToOne association, which is already mapped by the field user in the BorrowEntity entity. Please see the annotations on this field to know how to map the association.

So the @JoinColumn doesn't make sense. It's in contradiction with mappedBy. You just need the following:

@OneToMany(mappedBy="user")
private List<BorrowEntity>borrowings;

The targetEntity is also superfluous, since it's a List<BorrowEntity>: JPA can infer the target entity from the generic type of the list.

like image 73
JB Nizet Avatar answered Dec 21 '22 00:12

JB Nizet