|
View:
New views
5 Messages
—
Rating Filter:
Alert me
|
|
|
Problems with ManyToOne and OneToManyHi,
I'm using eclipselink to do some persistence. I'm having the following classes/tables:
@Entity
public class Team{ @OneToMany(mappedBy="team") public Set<Player> players; } @Entity public class Player{ @ManyToOne public Team team; } In my database there is a table team and a table player (with a foreign-key-relationship to a team-ID).
This works as far as I'm not deleting anything. But when calling em.remove(myPlayer) the "players"-Set in "Team" is not automatically updated. When closing my application and restarting it, everything works fine. But without this restart the "players"-array seems to get cached somewhere.
Any idea on how to solve this? From time to time I'm getting errors that there are unpersistet instances after such a remove operation. For hibernate, I've read something about an "inverse"-annotation which could (if I understood it right) solve such a problem.
Any help would be highly appreciated,
best regards
-Johannes
_______________________________________________ eclipselink-users mailing list eclipselink-users@... https://dev.eclipse.org/mailman/listinfo/eclipselink-users |
|
|
Re: Problems with ManyToOne and OneToManyHi,
you have to tell JPA to cascade the persistence operations on the relations. See for example: http://wiki.eclipse.org/Introduction_to_EclipseLink_JPA_(ELUG)#.40OneToMany @OneToMany(mappedBy="team", cascade = {CascadeType.REMOVE}) if you want, that only remove operations will be cascaded. I hope that helps! McJoe
|
|
|
|
|
|
Re: Problems with ManyToOne and OneToManyHi,
@Chris: Yes this is what was my solution so far, to update the collections on add and remove manually. But this is quite ugly :-( Using @PostRemove or @PreRemove also didn't really help and caused ugly problems from time to time. For hibernate there is a special non-jpa-standard annotation (I think it could be "inverse", but I'm not quite sure and I couldn't find the site I read about this again) to handle this. If I understood you right, there is no such thing for EclipseLink :-( @Joe: I think the Cascade.Remove doesn't really help. As mentioned, my database get's updated the right way. I couldn't see any effect on my issue when using the @cascade annotation unfortunately. Any way, thanks for your help. I fear I'll have to do the updates of the collections manually :-( -Johannes 2009/7/13 <christopher.delahunt@...>
_______________________________________________ eclipselink-users mailing list eclipselink-users@... https://dev.eclipse.org/mailman/listinfo/eclipselink-users |
|
|
Re: Problems with ManyToOne and OneToManyThis revelation has been a little disappointing.
I have also run into this problem with JPA (Eclipselink) and I am wondering about a couple of things I have seen. Using the same scenario of a parent -> child table relationship as Mr Johannes except using Collection - @Entity public class Team{ @OneToMany(mappedBy="team") public Collection<Player> players; ...getter and setters for Team attributes } @Entity public class Player{ @JoinColumn(name = "team_id", referencedColumnName = "team_id") @ManyToOne public Team team; ...getter and setters for Player attributes } I can get the Player record's foreign key: team_id to populate automatically during a create operation by doing - ... aTeam is a new instance of the Team class that has not yet been created in the database ... playerList is a collection of Player objects that have not yet been created in the datase em.persist(aTeam); for (Iterator it=playerList.iterator(); it.hasNext(); ) { Player player = (Player) it.next(); em.persist(player); player.setTeam(aTeam); } The result of that is a new Team record in the Team table and however many Player records in the Player table with foreign key values set to the parent Team record. However, if I change the code to be like this - em.persist(aTeam); for (Iterator it=playerList.iterator(); it.hasNext(); ) { Player player = (Player) it.next(); em.persist(player); aTeam.getPlayers().add(player); } The new Team record gets created and so do the new Player records except none of the Player record foreign key values are set to the parent Team record. The Player record team_id values are NULL. Is that just a flaw with the current JPA implementation? I have found that Many-to-Many relationships using a mapping table don't have this problem. For instance if the Team entity class had another reference to something like Sponsers where a Sponser could sponser many teams and teams could have many sponsers you might have this - @Entity public class Team{ @OneToMany(mappedBy="team") public Collection<Player> players; @JoinTable(name = "TEAM_SPONSER_MAP", joinColumns = {@JoinColumn(name = "TEAM_ID",referencedColumnName = "TEAM_ID")}, inverseJoinColumns = {@JoinColumn(name = "SPONSER_ID", referencedColumnName = "SPONSER_ID")}) @ManyToMany private Collection<SPONSER> sponsers; ...getter and setters for Team attributes } @Entity public class Sponser{ @ManyToMany(mappedBy = "sponsers", fetch = FetchType.LAZY) public Collection<Team> teams; ...getter and setters for Sponser attributes } @Entity public class Player{ @JoinColumn(name = "team_id", referencedColumnName = "team_id") @ManyToOne public Team team; ...getter and setters for Player attributes } In this case doing an operation like this - ....sponserList is a Collection<Sponser> that has been populated with Sponser objects to be linked to a Team object .....aTeam is a Team entity that has just been created em.persist(aTeam); for ( Iterator it = sponserList.iterator(); it.hasNext(); ) { Sponser sponser = (Sponser)it.next(); aTeam.getSponsers().add(sponser); } The result is the TEAM_SPONSER_MAP table gets automatically populated with the linked Team and Sponser records. One last example of a problem involving the first case of the ManyToOne mapping - In the case of an update where a Team entity is retrieved from the database and includes a populated collection of team Players. If an edit operation removes a player (or more than one player) from the Team object "players" collection and an entity manager is used to update the Team using a merge: em.merge(aTeam); ....where aTeam is the entity object the edit operation manipulated The merge process will not handle the players collection properly and the players removed from the aTeam object do not get deleted. The remove has to be done manually in the code without using the "merge" method. In the case of the ManyToMany Team - Sponsers relationship however, the mapping table entries are handled nicely by a "merge" operation. It seems to be the ManyToOne and OneToMany relationships that developers have to handle manually. OneToOne relationships seem to work fine. -sonavor
|
| Free embeddable forum powered by Nabble | Forum Help |