1 pièce(s) jointe(s)
Hibernate Erreur Many to Many persistance
Code:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161
| package main.webapp.bean;
import java.sql.Timestamp;
import java.util.ArrayList;
import java.util.Collection;
import java.util.HashSet;
import java.util.Set;
import javax.persistence.CascadeType;
import javax.persistence.Column;
import javax.persistence.ElementCollection;
import javax.persistence.JoinColumn;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.JoinTable;
import javax.persistence.ManyToMany;
import javax.persistence.OneToOne;
import javax.persistence.Table;
import javax.persistence.ElementCollection;
@Entity
@Table(name = "tb_user")
public class User {
@Id
@GeneratedValue
@Column(name = "D_US_CODE")
private int code;
@Column(name = "V_US_NOM")
private String nom;
@Column(name = "V_US_PRENOM")
private String prenom;
@Column(name = "V_US_MDP")
private String mdp;
@Column(name = "V_US_EMAIL")
private String email;
@Column(name = "V_US_TELEPHONE")
private String telephone;
@Column(name = "DT_US_DEBUT")
private Timestamp date_debut;
@Column(name = "DT_US_FIN")
private Timestamp date_fin;
@OneToOne(mappedBy = "visiteur")
private Reservation reservation;
@ManyToMany(cascade = {CascadeType.MERGE, CascadeType.PERSIST}) // DESACTIVER PERSIST SECOND PASSAGE
@JoinTable(name = "tb_user_role", joinColumns = @JoinColumn(name = "tb_user_D_US_CODE") , inverseJoinColumns = @JoinColumn(name = "tb_role_D_RO_CODE") )
private Set<Role> roles = new HashSet<Role>();
public void setRoles(Set<Role> roles) {
this.roles = roles;
}
public User() {
}
public User(String pNom, String pPrenom, String pMdp, String pEmail) {
this.setNom(pNom);
this.setPrenom(pPrenom);
this.setMdp(pMdp);
this.setEmail(pEmail);
}
@Override
public String toString() {
return "User code=" + code + ", Nom=" + nom + ", prenom=" + prenom + ", email=" + email + ", telephone="
+ telephone + ", debut=" + date_debut + ", fin=" + date_fin + "]";
}
public int getCode() {
return code;
}
public void setCode(int code) {
this.code = code;
}
public String getNom() {
return nom;
}
public void setNom(String nom) {
this.nom = nom;
}
public String getPrenom() {
return prenom;
}
public void setPrenom(String prenom) {
this.prenom = prenom;
}
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
public String getTelephone() {
return telephone;
}
public void setTelephone(String telephone) {
this.telephone = telephone;
}
public Timestamp getDate_debut() {
return date_debut;
}
public void setDate_debut(Timestamp date_debut) {
this.date_debut = date_debut;
}
public Timestamp getDate_fin() {
return date_fin;
}
public void setDate_fin(Timestamp date_fin) {
this.date_fin = date_fin;
}
public Set<Role> getRoles() {
return roles;
}
public void addRole(Role pRole){
roles.add(pRole);
}
public Reservation getReservation() {
return reservation;
}
public void setReservation(Reservation reservation) {
this.reservation = reservation;
}
public String getMdp() {
return mdp;
}
public void setMdp(String mdp) {
this.mdp = mdp;
}
} |
Code:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66
| package main.webapp.bean;
import java.util.HashSet;
import java.util.Set;
import javax.persistence.CascadeType;
import javax.persistence.Column;
import javax.persistence.ElementCollection;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.ManyToMany;
import javax.persistence.Table;
@Entity
@Table(name = "tb_role")
public class Role {
@Id
@GeneratedValue // A DESACTIVER APRES PASSAGE
@Column(name = "D_RO_CODE")
private int code;
@Column(name = "V_RO_LIBELLE")
private String name;
@ManyToMany(
/*cascade = {CascadeType.PERSIST, CascadeType.MERGE},*/
mappedBy = "roles",
targetEntity = User.class
)
private Set<User> users = new HashSet<User>();
public Set<User> getUsers() {
return users;
}
public void setUsers(Set<User> users) {
this.users = users;
}
public Role() {
}
public Role(String pName) {
this.name = pName;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getCode() {
return code;
}
public void setCode(int code) {
this.code = code;
}
} |
Code:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30
|
package main.webapp.test;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.HashSet;
import java.util.Set;
import main.webapp.bean.Role;
import main.webapp.bean.User;
import main.webapp.dao.RoleDAO;
import main.webapp.dao.UserDAO;
public class AdminConnexion {
public static void main(String[] args) {
connexionAdmin();
}
public static void connexionAdmin() {
System.out.println("###debut###");
UserDAO userDAO = new UserDAO();
User us = new User("nom", "prenom", "toto", "email");
//Role r = new Role();
us.addRole(new Role("admin"));
//us.addRole(new RoleDAO().findbyId(26)); // second passage
userDAO.create(us);
System.out.println("###fin###");
}
} |
javax.persistence.PersistenceException: org.hibernate.HibernateException: Illegal attempt to associate a collection with two open sessions. Collection : [main.webapp.bean.Role.users#32]
Collection contents: [<uninitialized>]
Bonjour voici mon problème. Lorsque j' initialise un nouveau role avec un nouveau User tous ce passe bien mais lors du deuxième passage lorsque je veux affecté ce nouveau role à un User erreur que vous pouvez voir précédemment.
Mon test se fait uniquement par le biais de ma classe java donc peut de chance d'avoir une double session pouvant poser problème et ma classe manager vient la clôturé après échange.
Code:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93
|
package main.webapp.dao;
import javax.persistence.EntityManager;
import javax.persistence.EntityTransaction;
import javax.persistence.NoResultException;
import org.springframework.stereotype.Service;
import main.webapp.persistance.util.HibernateUtil;
@Service
public abstract class ManagerDAO<T> {
private EntityManager em = HibernateUtil.getEntityManager();
private EntityTransaction tx = em.getTransaction();
private Class<T> classT;
public ManagerDAO(Class<T> pClass) {
this.classT = pClass;
}
public T create(T obj) {
getTx().begin();
try {
getEm().persist(obj);
getTx().commit();
} catch (Exception e) {
getEm().clear();
if(getTx() != null){
//getTx().rollback();
}
new ExceptionDAO(e);
}
finally {
if (HibernateUtil.getEntityManager() != null) {
HibernateUtil.getEntityManager().close();
}
}
return obj;
}
public T findbyId(int id) {
T objet = null;
try {
objet = getEm().find(classT, id);
} catch (NoResultException e) {
return null;
} catch (Exception e) {
new ExceptionDAO(e);
}
return objet;
}
public abstract T update(T obj);
public boolean delete(T obj) {
getTx().begin();
try {
getEm().remove(obj);
getTx().commit();
return true;
} catch (Exception e) {
new ExceptionDAO("Probleme de suppression", e);
return false;
}
}
@Override
protected void finalize() throws Throwable {
em.close();
super.finalize();
}
public EntityTransaction getTx() {
return tx;
}
public EntityManager getEm() {
return em;
}
public void setEm(EntityManager em) {
this.em = em;
}
public void setTx(EntityTransaction tx) {
this.tx = tx;
}
} |
Si vous avez une idée du pourquoi du comment. Sachant qu'en commentant les lignes indiqués par des commentaires majuscules le fonctionnement marche au deuxième passage minimum. C'est à dire si un élément existe déjà. J'ai également tenté par un merge plutôt que le persistance mais pas de réel intérêt ici étant donné qu'il s'agit bien d'une création d'un user (et de l'ajout d'un élément dans la table tb_user_role).