I have a problem with mapping hibernate Inheritance, an example
I have a portal with more section and this section could be a page or another section, a page could have more visualizations.
My web app calculates from the portal all page with more visualization, the app work with the mock object but not work with hibernate, the portal and the section root load ok but all children no.
I’m learning Hibernate and I’m trying the @Inheritance(strategy = InheritanceType.JOINED)
for the first time
I committed an error with mapping hibernate with InheritanceType.JOINED?
This is a class diagram with UML and all code for mapping
The code of the class
/*
* To change this license header, choose License Headers in Project Properties.
* To change this template file, choose Tools | Templates
* and open the template in the editor.
*/
package it.unibas.webanalytics.modello;
import java.util.ArrayList;
import java.util.List;
import javax.persistence.CascadeType;
import javax.persistence.Column;
import javax.persistence.DiscriminatorColumn;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.Inheritance;
import javax.persistence.InheritanceType;
import javax.persistence.ManyToOne;
import javax.persistence.OneToMany;
import javax.persistence.OneToOne;
/**
*
* @author Vincenzo Palazzo
*/
@Entity(name = "sezioniastratte")
@Inheritance(strategy = InheritanceType.JOINED)
public abstract class AbstractSezione implements ISezione {
private Long id;
protected String identificativo;
private PortaleWeb root;
private List<AbstractSezione> sezioniList = new ArrayList<>();
private AbstractSezione padre;
public AbstractSezione(String identificativo) {
this.identificativo = identificativo;
}
public AbstractSezione() {
}
@Id
@GeneratedValue(strategy = GenerationType.TABLE)
public Long getId() {
return id;
}
public void setId(Long id) {
this.id = id;
}
@Column(length = 150)
public String getIdentificativo() {
return identificativo;
}
public void setIdentificativo(String identificativo) {
this.identificativo = identificativo;
}
@OneToOne(mappedBy = "sezione", cascade = {CascadeType.ALL}, fetch = FetchType.EAGER)
public PortaleWeb getRoot() {
return root;
}
public void setRoot(PortaleWeb root) {
this.root = root;
}
public void addSezione(AbstractSezione sezione) {
sezioniList.add(sezione);
}
@OneToMany(mappedBy = "padre", orphanRemoval = true, cascade = {CascadeType.ALL}, fetch = FetchType.EAGER)
public List<AbstractSezione> getSezioniList() {
return sezioniList;
}
public void setSezioniList(List<AbstractSezione> sezioniList) {
this.sezioniList = sezioniList;
}
public void setPadre(AbstractSezione padre) {
this.padre = padre;
}
@ManyToOne(cascade = {CascadeType.ALL}, fetch = FetchType.EAGER)
public AbstractSezione getPadre() {
return padre;
}
}
/*
* To change this license header, choose License Headers in Project Properties.
* To change this template file, choose Tools | Templates
* and open the template in the editor.
*/
package it.unibas.webanalytics.modello;
import it.unibas.webanalytics.modello.visite.IVisitor;
import java.util.ArrayList;
import java.util.List;
import java.util.Objects;
import java.util.UUID;
import javax.persistence.CascadeType;
import javax.persistence.DiscriminatorValue;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.OneToMany;
import javax.persistence.Transient;
/**
*
* @author Vincenzo Palazzo
*/
@Entity(name = "pagine")
public class Pagina extends AbstractSezione{
@Deprecated
private String uuid;
private List<Visualizzazione> visualizzazioni = new ArrayList<>();
public Pagina(String identificativo) {
super(identificativo);
uuid = UUID.randomUUID().toString();
}
public Pagina() {
}
@OneToMany(mappedBy = "pagina", orphanRemoval = true, cascade = {CascadeType.ALL}, fetch = FetchType.EAGER)
public List<Visualizzazione> getVisualizzazioni() {
return visualizzazioni;
}
public void addVisualizzazione(Visualizzazione visualizzazione){
visualizzazioni.add(visualizzazione);
}
@Override
@Transient
public boolean isPage(){
return true;
}
@Override
public void accept(IVisitor visitor) {
visitor.visitaPagina(this);
}
@Transient
public String getUuid() {
return uuid;
}
public void setUuid(String uuid) {
this.uuid = uuid;
}
public void setVisualizzazioni(List<Visualizzazione> visualizzazioni) {
this.visualizzazioni = visualizzazioni;
}
public int dimensione(){
return this.visualizzazioni.size();
}
@Override
public int hashCode() {
int hash = 5;
hash = 67 * hash + Objects.hashCode(super.identificativo);
hash = 67 * hash + Objects.hashCode(this.uuid);
return hash;
}
@Override
public boolean equals(Object obj) {
if (this == obj) {
return true;
}
if (obj == null) {
return false;
}
if (getClass() != obj.getClass()) {
return false;
}
final Pagina other = (Pagina) obj;
if (!Objects.equals(super.identificativo, other.identificativo)) {
return false;
}
if (!Objects.equals(this.uuid, other.uuid)) {
return false;
}
return true;
}
}
/*
* To change this license header, choose License Headers in Project Properties.
* To change this template file, choose Tools | Templates
* and open the template in the editor.
*/
package it.unibas.webanalytics.modello;
import it.unibas.webanalytics.modello.visite.IVisitor;
import javax.persistence.DiscriminatorValue;
import javax.persistence.Entity;
import javax.persistence.PrimaryKeyJoinColumn;
import javax.persistence.Transient;
/**
*
* @author Vincenzo Palazzo
*/
@Entity(name = "sezioni")
public class Sezione extends AbstractSezione {
public Sezione() {
}
public Sezione(String identificativo) {
super(identificativo);
}
@Override
@Transient
public boolean isPage() {
return false;
}
@Override
public void accept(IVisitor visitor) {
//Non riesco ad applicare la correzione che ha detto il prof. (fix)
/*for(ISezione sezione : sezioni){
sezione.accept(visitor);
}*/
visitor.visitaSezione(this);
}
}
/*
* To change this license header, choose License Headers in Project Properties.
* To change this template file, choose Tools | Templates
* and open the template in the editor.
*/
package it.unibas.webanalytics.modello;
import javax.persistence.CascadeType;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.ManyToOne;
/**
*
* @author Vincenzo Palazzo
*/
@Entity(name = "visualizzazioni")
public class Visualizzazione {
private long id;
private String nazioneDiProvenienza;
private String urlProvenienza;
private String urlDestinazione;
private String browser;
private int daQuanto;
private Pagina pagina;
public Visualizzazione() {
}
public Visualizzazione(String nazioneDiProvenienza, String urlProvenienza, String urlDestinazione, String browser, int daQuanto) {
this.nazioneDiProvenienza = nazioneDiProvenienza;
this.urlProvenienza = urlProvenienza;
this.urlDestinazione = urlDestinazione;
this.browser = browser;
this.daQuanto = daQuanto;
}
@Column(length = 50)
public String getNazioneDiProvenienza() {
return nazioneDiProvenienza;
}
@Column(length = 250)
public String getUrlProvenienza() {
return urlProvenienza;
}
@Column(length = 250)
public String getUrlDestinazione() {
return urlDestinazione;
}
@Column(length = 50)
public String getBrowser() {
return browser;
}
public int getDaQuanto() {
return daQuanto;
}
@Id
@GeneratedValue(strategy = GenerationType.TABLE)
public long getId() {
return id;
}
public void setId(long id) {
this.id = id;
}
@ManyToOne(cascade = {CascadeType.ALL})
public Pagina getPagina() {
return pagina;
}
public void setPagina(Pagina pagina) {
this.pagina = pagina;
}
public void setNazioneDiProvenienza(String nazioneDiProvenienza) {
this.nazioneDiProvenienza = nazioneDiProvenienza;
}
public void setUrlProvenienza(String urlProvenienza) {
this.urlProvenienza = urlProvenienza;
}
public void setUrlDestinazione(String urlDestinazione) {
this.urlDestinazione = urlDestinazione;
}
public void setBrowser(String browser) {
this.browser = browser;
}
public void setDaQuanto(int daQuanto) {
this.daQuanto = daQuanto;
}
}
My generic DAO for executing all operation with hibernate
package it.unibas.webanalytics.persistenza.hibernate;
import it.unibas.webanalytics.eccezioni.DAOException;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.hibernate.HibernateException;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.cfg.Configuration;
import org.hibernate.service.ServiceRegistry;
import org.hibernate.boot.registry.StandardServiceRegistryBuilder;
public class DAOUtilHibernate {
private static Log logger = LogFactory.getLog(DAOUtilHibernate.class);
private static SessionFactory sessionFactory;
private static ServiceRegistry serviceRegistry;
static {
try {
Configuration conf = new Configuration().configure();
ServiceRegistry sr = new StandardServiceRegistryBuilder().applySettings(conf.getProperties()).build();
sessionFactory = conf.buildSessionFactory(sr);
} catch (Throwable ex) {
logger.error("Building SessionFactory failed.", ex);
throw new ExceptionInInitializerError(ex);
}
}
public static SessionFactory getSessionFactory() {
return sessionFactory;
}
public static Session getCurrentSession() throws DAOException {
try {
return sessionFactory.getCurrentSession();
} catch (HibernateException ex) {
logger.error(ex);
throw new DAOException(ex);
}
}
public static void beginTransaction() throws DAOException {
try {
sessionFactory.getCurrentSession().beginTransaction();
} catch (HibernateException ex) {
logger.error(ex);
throw new DAOException(ex);
}
}
public static void commit() throws DAOException {
try {
sessionFactory.getCurrentSession().getTransaction().commit();
} catch (HibernateException ex) {
logger.error(ex);
throw new DAOException(ex);
}
}
public static void rollback() {
try {
sessionFactory.getCurrentSession().getTransaction().rollback();
} catch (HibernateException ex) {
logger.error(ex);
}
}
}
an example of the use case
I have a web portal that contains a composition of sections, a section is a page or another section with a list of pages, my use case is represented by I select a portal (I can load the portals) and on a subsequent page I visit the composite layer and I get all the visualizations that I see in a table, when I do this use case the not views are loaded.
I load all the web portals with a findAll () that applies them criteria and from there you will have all the structure loaded by the db, that is I expect portal, sections, pages and views this is wrong?
This is the reference for the StackOverflow post