Hi
I'm using Hibernate version:3.2.5 and I'm using the discriminator tag in hbm.xml file to specify some object's properties. This is my hbm:
Code:
<hibernate-mapping>
<class name="it.aams.contenzioso.persistentObjects.CAnaRicorrenti" table="C_ANA_RICORRENTI">
<cache usage="read-only" />
<id name="idk" type="long">
<column name="IDK" precision="22" scale="0" />
<generator class="sequence">
<param name="sequence">SEQ_ANA_RICORRENTI</param>
</generator>
</id>
<discriminator column="TIPO_PERSONA" type="string" insert="false" />
<many-to-one name="CSTipoPersona" class="it.aams.contenzioso.persistentObjects.CSTipoPersona" fetch="select" lazy="false">
<column name="TIPO_PERSONA" precision="22" scale="0" />
</many-to-one>
<property name="comune" type="string">
<column name="COMUNE" length="50" />
</property>
<property name="provincia" type="string">
<column name="PROVINCIA" length="2" />
</property>
<property name="isRicorrenteProvvCU" type="integer">
<column name="IS_RICORRENTE_PROVV_CU" precision="22" scale="0" length="1" />
</property>
<subclass name="it.aams.contenzioso.persistentObjects.CAnaRicorrentiFisica" discriminator-value="1">
<property name="nome" type="string">
<column name="NOME" length="50" />
</property>
<property name="cognome" type="string">
<column name="COGNOME_DENOMINAZIONE" length="50" />
</property>
<property name="codiceFiscale" type="string">
<column name="CF_IVA" length="16" />
</property>
<property name="dtNascita" type="timestamp">
<column name="DT_NASCITA" length="7" />
</property>
<property name="domComune" type="string">
<column name="DOM_COMUNE" length="60" />
</property>
<property name="domProvincia" type="string">
<column name="DOM_PROVINCIA" length="2" />
</property>
<property name="domIndirizzo" type="string">
<column name="DOM_INDIRIZZO" length="100" />
</property>
</subclass>
<subclass name="it.aams.contenzioso.persistentObjects.CAnaRicorrentiGiuridica" discriminator-value="2">
<property name="denominazione" type="string">
<column name="COGNOME_DENOMINAZIONE" length="50" />
</property>
<property name="partitaIva" type="string">
<column name="CF_IVA" length="16" />
</property>
</subclass>
</class>
</hibernate-mapping>
As you can see I need a general Object containing the main property and 2 subclass extending the main object and having more specific features (properties) basing on the dicriminator column.
These are the persisting objects involved in the mapping:
This is the general object
Code:
public class CAnaRicorrenti implements Serializable
{
public CAnaRicorrenti(){}
public CAnaRicorrenti(long idk){
this.setIdk(idk);
}
// primary key
private long idk;
// fields
private java.lang.String nome;
private java.lang.String cognomeDenominazione;
private java.lang.String cfIva;
private java.lang.String comune;
private java.lang.String provincia;
private java.util.Date dtNascita;
private java.lang.String domComune;
private java.lang.String domProvincia;
private java.lang.String domIndirizzo;
private java.lang.Integer isRicorrenteProvvCU;
// many to one
private it.aams.contenzioso.persistentObjects.CSTipoPersona cSTipoPersona;
public long getIdk(){
return idk;
}
public void setIdk(long idk){
this.idk = idk;
}
protected java.lang.String getNome(){
return nome;
}
protected void setNome(java.lang.String nome){
this.nome = nome;
}
protected java.lang.String getCognomeDenominazione(){
return cognomeDenominazione;
}
protected void setCognomeDenominazione(java.lang.String cognomeDenominazione){
this.cognomeDenominazione = cognomeDenominazione;
}
protected java.lang.String getCfIva(){
return cfIva;
}
protected void setCfIva(java.lang.String cfIva){
this.cfIva = cfIva;
}
public java.lang.String getComune(){
return comune;
}
public void setComune(java.lang.String comune){
this.comune = comune;
}
public java.lang.String getProvincia(){
return provincia;
}
public void setProvincia(java.lang.String provincia){
this.provincia = provincia;
}
protected java.util.Date getDtNascita(){
return dtNascita;
}
protected void setDtNascita(java.util.Date dtNascita){
this.dtNascita = dtNascita;
}
protected java.lang.String getDomComune(){
return domComune;
}
protected void setDomComune(java.lang.String domComune){
this.domComune = domComune;
}
protected java.lang.String getDomProvincia(){
return domProvincia;
}
protected void setDomProvincia(java.lang.String domProvincia){
this.domProvincia = domProvincia;
}
protected java.lang.String getDomIndirizzo(){
return domIndirizzo;
}
protected void setDomIndirizzo(java.lang.String domIndirizzo){
this.domIndirizzo = domIndirizzo;
}
public it.aams.contenzioso.persistentObjects.CSTipoPersona getCSTipoPersona(){
return cSTipoPersona;
}
public void setCSTipoPersona(it.aams.contenzioso.persistentObjects.CSTipoPersona cSTipoPersona){
this.cSTipoPersona = cSTipoPersona;
}
}
These are the subclasses:
Code:
public class CAnaRicorrentiFisica extends CAnaRicorrenti{
public CAnaRicorrentiFisica(){
super();
}
public CAnaRicorrentiFisica(long idk)
{
super(idk);
}
public java.lang.String getCodiceFiscale()
{
return super.getCfIva();
}
public void setCodiceFiscale(java.lang.String codiceFiscale)
{
super.setCfIva(codiceFiscale);
}
public java.lang.String getCognome(){
return super.getCognomeDenominazione();
}
public void setCognome(java.lang.String cognome){
super.setCognomeDenominazione(cognome);
}
public java.lang.String getDomComune(){
return super.getDomComune();
}
public void setDomComune(java.lang.String domComune){
super.setDomComune(domComune);
}
public java.lang.String getDomIndirizzo(){
return super.getDomIndirizzo();
}
public void setDomIndirizzo(java.lang.String domIndirizzo){
super.setDomIndirizzo(domIndirizzo);
}
public java.lang.String getDomProvincia(){
return super.getDomProvincia();
}
public void setDomProvincia(java.lang.String domProvincia){
super.setDomProvincia(domProvincia);
}
public java.util.Date getDtNascita(){
return super.getDtNascita();
}
public void setDtNascita(java.util.Date dtNascita){
super.setDtNascita(dtNascita);
}
public java.lang.String getNome(){
return super.getNome();
}
public void setNome(java.lang.String nome){
super.setNome(nome);
}
}
Code:
public class CAnaRicorrentiGiuridica extends CAnaRicorrenti{
public CAnaRicorrentiGiuridica(){
super();
}
public CAnaRicorrentiGiuridica(long idk){
super(idk);
}
public java.lang.String getDenominazione(){
return super.getCognomeDenominazione();
}
public void setDenominazione(java.lang.String denominazione){
super.setCognomeDenominazione(denominazione);
}
public java.lang.String getPartitaIva(){
return super.getCfIva();
}
public void setPartitaIva(java.lang.String partitaIva){
super.setCfIva(partitaIva);
}
}
This is the junit code where I use this mapping:
Code:
CAnaRicorrenti cAnaRicorrentiResult = cAnaRicorrentiDAO.getCAnaRicorrenti(new Long("644"));
System.out.println("Idk: "+cAnaRicorrentiResult.getIdk());
System.out.println("CSTipoPersona: "+cAnaRicorrentiResult.getCSTipoPersona().getIdk());
System.out.println("Comune: "+cAnaRicorrentiResult.getComune());
System.out.println("Provincia: "+cAnaRicorrentiResult.getProvincia());
System.out.println("IsRicorrenteProvvCU: "+cAnaRicorrentiResult.getIsRicorrenteProvvCU());
System.out.println("CSTipoRicorrenti: "+cAnaRicorrentiResult.getCSTipoRicorrenti().getIdk());
System.out.println("CRicorsi: "+cAnaRicorrentiResult.getCRicorsi().getIdk());
As you can see I'm getting the properties of the general object, no problem until here.
But now I want to access the specific properties of the subclasses basing on the discriminator and here comes the problem.
Basing on the hbm.xml above, when calling a findbyPrimaryKey method, I supposed Hibernate would return a specific object (i.e. CAnaRicorrentiFisica) basing on TIPO_PERSONA value, so I could cast from the abstract supertype to the concrete child and easily access the specific properties, but when I execute the following code I get a ClassCastException:
Code:
if (cAnaRicorrentiResult.getCSTipoPersona().getIdk() == 2)
{
cAnaRicorrentiGiuridicaResult = (CAnaRicorrentiGiuridica)cAnaRicorrentiResult;
}
I run the junit in debug mode and this is the detail of what Hibernate returned:
As you can see, the returned object belongs to the supertype CAnaRicorrenti while CAnaRicorrentiGiuridica with its properties is included deep inside.
So here comes the question:
How can I access the specific properties of the specific objects?
Thanks in advance.
Feel free to ask more details if you need.