Olá
Estou apanhando feio aqui para conseguir usar o relacionamento many-to-one e 2 Sessões diferentes, ou seja, na primeira sessão eu carrego um objeto e na outra sessão eu tento salvar o objeto que irá possuir o relacionamento. Montei um exemplo bem simples para ficar mais claro o que eu quero. Let´s GO:
Possuo 2 Tabelas no Banco de Dados e 2 Bean.
são eles
Cidades
public class Cidades implements Serializable {
private Integer codigo; //ID no Banco
private String nome;
//métodos gets e sets...
}
Clientes
public class Clientes implements Serializable {
private Integer codigo; //ID do Clientes
private String nome;
private Cidades cidades; //Meu Objeto Cidades
//getters e setters
}
Tanto o ID do Cidades como do Clientes serão preenchidos manualmente.
O Relacionamento está na tabela de Clientes, onde eu possuo a tag <many-to-one assim
<many-to-one
name="cidades"
class="br.com.junior.models.Cidades"
cascade="all"
outer-join="auto"
column="cidade"
/>
Supondo que eu já possuo registros cadastrados na tabela de Cidades (no meu projeto real eu irei ter), eu criei uma classe Principal para carregar o Objeto Cidades do Banco de Dados (primeira session), atribuir esse Objeto cidades ao objeto Clientes e depois salvá-lo (segunda Session).
Segue a classe
public static void main(String args[]) throws HibernateException {
Configuration configuration = new Configuration();
configuration.addClass(Cidades.class);
configuration.addClass(Clientes.class);
SessionFactory factory = configuration.buildSessionFactory();
/*Primeira sessão*/
Session session = factory.openSession();
Transaction tx = session.beginTransaction();
Cidades cidades = (Cidades) session.load(Cidades.class,Integer.valueOf("2"));
session.flush();
tx.commit();
session.close();
/*Preencher Dados*/
Clientes clientes = new Clientes();
clientes.setCodigo(Integer.valueOf("1"));
clientes.setNome("Junior");
clientes.setCidades(cidades);
/*Segunda Sessão
*/
Session session2 = factory.openSession();
Transaction tx2 = session2.beginTransaction();
session2.save(clientes);
session2.flush();
tx2.commit();
session2.close();
}
Com certeza absoluta o objeto Cidades está com dados preenchidos.
Quando eu tento gravar, da o seguinte erro (inclusive com a propriedade hibernate.show_sql = true).
[quote]Hibernate: select cidades0_.codigo as codigo0_, cidades0_.nome as nome0_ from cidades cidades0_ where cidades0_.codigo=?
Hibernate: insert into cidades (nome, codigo) values (?, ?)
12/08/2004 11:30:54 net.sf.hibernate.util.JDBCExceptionReporter logExceptions
WARNING: SQL Error: 1062, SQLState: S1009
12/08/2004 11:30:54 net.sf.hibernate.util.JDBCExceptionReporter logExceptions
SEVERE: Invalid argument value, message from server: “Duplicate entry ‘2’ for key 1”
12/08/2004 11:30:54 net.sf.hibernate.util.JDBCExceptionReporter logExceptions
WARNING: SQL Error: 1062, SQLState: S1009
12/08/2004 11:30:54 net.sf.hibernate.util.JDBCExceptionReporter logExceptions
SEVERE: Invalid argument value, message from server: “Duplicate entry ‘2’ for key 1”
12/08/2004 11:30:54 net.sf.hibernate.JDBCException
SEVERE: Could not execute JDBC batch update
java.sql.BatchUpdateException: Invalid argument value, message from server: “Duplicate entry ‘2’ for key 1”
at com.mysql.jdbc.PreparedStatement.executeBatch(PreparedStatement.java:1394)[/quote]
Note-se que primeiro ele faz um Select para preencher o objeto Cidades (primeira session) e na hora de salvar o objeto (Clientes) ele tenta primeiro salvar novamente o objeto (cidades) assim gerando uma exception de ID duplicate.
Se eu fizer tudo em uma única Session funciona normal. Mas eu estou tentando fazer assim, pois no meu projeto real, eu primeiro irei carregar o Objeto cidades, depois carregar outras telas, esperar o usuário digitar os dados do cliente para depois gravar (consequentemente irei usar mais que 1 session).
Alguem poderia me ajudar com isso fazendo favor?
Obrigado