3
I have a m:n relationship between Column and Element. The entity that owns the relationship is Column. but when I’m saving a map of Columns, the following scenario happens:
1) In the first iteration, Hibernate:
1.1) saves the first element Column
1.2) inserts the two elements in the column element table
island following:
Hibernate: select nextval ('hibernate_sequence')
Hibernate: insert into coluna (COLUNA_ALIAS_OPERACAO, COLUNA_CLAUSULA, COLUNA_DATA_DOIS, COLUNA_DATA_UM, COLUNA_EXIBE_FILTRO, COLUNA_EXIBE_NO_RELATORIO, COLUNA_EXIBE_TOTALIZADOR, COLUNA_INDEX, COLUNA_LABEL, COLUNA_NOME, COLUNA_OPERACAO, COLUNA_OPERACAO_REFERNCIANDO_ALIAS, RELATORIO_ID, COLUNA_TEMPO_DOIS, COLUNA_TEMPO_UM, COLUNA_TIPO_CLAUSULA_TEXTO, COLUNA_TIPO_EXIBICAO, COLUNA_TIPO_FILTRO, COLUNA_ID) values (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)
Hibernate: insert into coluna_elemento (COLUNA_ID, ELEMENTO_DOMINIO_ID) values (?, ?)
Hibernate: insert into coluna_elemento (COLUNA_ID, ELEMENTO_DOMINIO_ID) values (?, ?)
Right now the column table of my bank is like this:
coluna_id | elemento_id
988 860
988 861
So far everything is happening as expected.
2) In the second iteration, Hibernate:
2.1) saves the second column element
2.2) delete the previously saved element from the column
2.3)inserts the two elements in the column element table
How it shows the console output below:
Hibernate: select nextval ('hibernate_sequence')
Hibernate: insert into coluna (COLUNA_ALIAS_OPERACAO, COLUNA_CLAUSULA, COLUNA_DATA_DOIS, COLUNA_DATA_UM, COLUNA_EXIBE_FILTRO, COLUNA_EXIBE_NO_RELATORIO, COLUNA_EXIBE_TOTALIZADOR, COLUNA_INDEX, COLUNA_LABEL, COLUNA_NOME, COLUNA_OPERACAO, COLUNA_OPERACAO_REFERNCIANDO_ALIAS, RELATORIO_ID, COLUNA_TEMPO_DOIS, COLUNA_TEMPO_UM, COLUNA_TIPO_CLAUSULA_TEXTO, COLUNA_TIPO_EXIBICAO, COLUNA_TIPO_FILTRO, COLUNA_ID) values (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)
Hibernate: delete from coluna_elemento where COLUNA_ID=?
Hibernate: insert into coluna_elemento (COLUNA_ID, ELEMENTO_DOMINIO_ID) values (?, ?)
Hibernate: insert into coluna_elemento (COLUNA_ID, ELEMENTO_DOMINIO_ID) values (?, ?)
And then, the column table in the database looks like this:
coluna_id | elemento_id
989 860
989 861
When what I expected was this:
coluna_id | elemento_id
988 860
988 861
989 860
989 861
What am I doing wrong?
The code where I save the column map is as follows:
private void salvaColunas() {
for (Map.Entry<Integer, Coluna> entry : mapaColunas.entrySet()){
Coluna coluna = entry.getValue();
coluna.setRelatorio(relatorio);
colunaDao.saveOrUpdate(coluna);
}
}
The saveOrUpdate method of my Dao class is as follows::
public void saveOrUpdate(T obj) {
Session session;
Transaction tx = null;
try {
session = HibernateUtil.getSessionFactory().getCurrentSession();
}catch (HibernateException ex) {
session = HibernateUtil.getSessionFactory().openSession();
}
try{
tx = session.beginTransaction();
session.saveOrUpdate(obj);
tx.commit();
} catch (RuntimeException e) {
e.printStackTrace();
} finally {
if(session.isOpen()) {
session.close();
}
}
}
The mapping in the column class (already with the equals and hashcode methods implemented) is thus :
@ManyToMany(fetch= FetchType.LAZY, cascade= {CascadeType.PERSIST, CascadeType.REFRESH, CascadeType.MERGE})
@JoinTable(name="coluna_elemento", joinColumns={
@JoinColumn(name="COLUNA_ID", nullable=false, updatable=false )},
inverseJoinColumns = {@JoinColumn(name = "ELEMENTO_DOMINIO_ID", nullable=false, updatable = false) })
private Set<ElementoDominio> elementosDoDominio;
public int hashCode() {
final int prime = 31;
int result = 1;
result = prime * result + ((id == null) ? 0 : id.hashCode());
result = prime * result + ((label == null) ? 0 : label.hashCode());
result = prime * result + ((nome == null) ? 0 : nome.hashCode());
return result;
}
@Override
public boolean equals(Object obj) {
if (this == obj)
return true;
if (obj == null)
return false;
if (getClass() != obj.getClass())
return false;
Coluna other = (Coluna) obj;
if (id == null) {
if (other.id != null)
return false;
} else if (!id.equals(other.id))
return false;
if (label == null) {
if (other.label != null)
return false;
} else if (!label.equals(other.label))
return false;
if (nome == null) {
if (other.nome != null)
return false;
} else if (!nome.equals(other.nome))
return false;
return true;
}
And my Element class (which also has the equals and hashcode methods implemented) is like this:
@ManyToMany(fetch = FetchType.LAZY, mappedBy = "elementosDoDominio")
private Set<Coluna> colunas;
@Override
public int hashCode() {
final int prime = 31;
int result = 1;
result = prime * result + ((id == null) ? 0 : id.hashCode());
result = prime * result + ((label == null) ? 0 : label.hashCode());
return result;
}
@Override
public boolean equals(Object obj) {
if (this == obj)
return true;
if (obj == null)
return false;
if (getClass() != obj.getClass())
return false;
ElementoDominio other = (ElementoDominio) obj;
if (id == null) {
if (other.id != null)
return false;
} else if (!id.equals(other.id))
return false;
if (label == null) {
if (other.label != null)
return false;
} else if (!label.equals(other.label))
return false;
return true;
}
Both Column and Element classes have more attributes, including the id that is generated by Hibernate. All with getters and setters.
Can someone help me? Thank you
Do the following, put the updatable to true in the DoDominio. I think he might be trying to update the object instead of inserting a new one. Just a hunch..
– Giuliana Bezerra
I tried to insert the columns in a hashMap before saving in each interaction and saw that instead of the hash containing the two columns, it is containing only one. Which leads me to believe that my equals method is returning that the two columns are equal. but are not equal!!!
– oitathi
Hmm, but when it’s in the hash you have to implement the hashcode, it doesn’t use the equals. How is it implemented?
– Giuliana Bezerra
generated by the eclipse
– oitathi
Put the method here.
– Giuliana Bezerra
ready, put on!
– oitathi
You can’t imagine just by looking at this, I suggest you debug, put a breakpoint in the hashcode method and see if it is actually returning true in the second interaction and so it replaces the previous object.
– Giuliana Bezerra
I already did that. It returns false... therefore, they are not equal
– oitathi
Let’s go continue this discussion in chat.
– Giuliana Bezerra
I use a set and not a list.. I don’t need @Ordercolumn
– oitathi