Pessoal, é o seguinte, precisamos de opiniões sobre a seguinte situação.
Estamos desenvolvendo um pequeno sistema e usando na camada de persistência o hibernate. A nossa dúvida é referente a delegar controle sobre a transação e a sessão no hibernate.
Existem duas situações, e precisamos saber qual usar.
A primeira hipótese (implementada como teste nas listagens abaixo) é que deve-se criar a sessão e a transação fora dos DAOs, passar a sessao para os DAOs e no final na utilização dos mesmos dar um commit na transação e fechar a sessão.
A outra hipótese é deixar que o controle da sessão e da transação fique totalmente por responsabilidade do DAO.
Eu defendo a primeira hipótese, pois assim podemos ter maior controle.
O que vocês acham?
Dêem uma olhada nas listagens.
package usandohibernate.entity;
import javax.persistence.*;
/**
*
* @author David Buzatto
*/
@Entity
public class Cliente {
@Id
@GeneratedValue
private Long id;
@Column(
length = 30,
nullable = false
)
private String nome;
@Column(
length = 50,
nullable = false
)
private String sobrenome;
public Long getId() {
return id;
}
public void setId(Long id) {
this.id = id;
}
public String getNome() {
return nome;
}
public void setNome(String nome) {
this.nome = nome;
}
public String getSobrenome() {
return sobrenome;
}
public void setSobrenome(String sobrenome) {
this.sobrenome = sobrenome;
}
}
package usandohibernate.entity;
import javax.persistence.*;
/**
*
* @author David Buzatto
*/
@Entity
public class Produto {
@Id
@GeneratedValue
private Long id;
@Column(
length = 30,
nullable = false
)
private String nome;
@Column(
length = 50,
nullable = false
)
private String descricao;
private Double preco;
public Long getId() {
return id;
}
public void setId(Long id) {
this.id = id;
}
public String getNome() {
return nome;
}
public void setNome(String nome) {
this.nome = nome;
}
public String getDescricao() {
return descricao;
}
public void setDescricao(String descricao) {
this.descricao = descricao;
}
public Double getPreco() {
return preco;
}
public void setPreco(Double preco) {
this.preco = preco;
}
}
package usandohibernate.entity;
/**
* Enumeração das entidades.
*
* @author David Buzatto
*/
public enum EntityEnum {
// entidades
/**
* Cliente.
*/
CLIENTE( Cliente.class ),
/**
* Produto.
*/
PRODUTO( Produto.class );
private Class entity;
EntityEnum( Class entity ) {
setEntity( entity );
}
private void setEntity( Class entity ) {
this.entity = entity;
}
public Class getEntity() {
return entity;
}
}
package usandohibernate.hibernate;
import org.hibernate.*;
import org.hibernate.cfg.*;
import usandohibernate.entity.*;
/**
* Fábrica de sessões do hibernate.
*
* Utiliza uma enumeração de classes anotadas para popular a configuração.
*
* @author David Buzatto
*/
public class HibernateFactory {
// fábrica de sessões
private static final SessionFactory factory;
/*
* AnnotationConfiguration, responsável em armazenar as configurações
* das classes anotadas.
*/
private static final AnnotationConfiguration config;
/*
* Permite que as sessions associadas sejam locais a thread que a está executando.
*/
private static final ThreadLocal< Session > threadLocal =
new ThreadLocal< Session >();
// bloco de inicialização estático (executado apenas UMA vez)
static {
// cria a AnnotationConfiguration, evitando uso do arquivo hibernate.cfg.xml
config = new AnnotationConfiguration();
// adiciona as classes anotadas
EntityEnum[] entities = EntityEnum.values();
for ( int i = 0; i < entities.length; i++ ) {
config.addAnnotatedClass( entities[ i ].getEntity() );
}
// cria a factory
factory = config.buildSessionFactory();
}
public SessionFactory getFactory() {
return factory;
}
public AnnotationConfiguration getConfig() {
return config;
}
public Session getSession() {
Session session = factory.openSession();
threadLocal.set( session );
return factory.openSession();
}
}
package usandohibernate.dao;
import java.util.*;
import org.hibernate.*;
import usandohibernate.entity.*;
/**
*
* @author David Buzatto
*/
public class ClienteDAO< T extends Cliente > {
private Session session;
private Class classe = Cliente.class;
public ClienteDAO( Session session ) {
this.session = session;
}
public void adiciona( T obj ) throws HibernateException {
this.session.save( obj );
}
public void remove( T obj ) throws HibernateException {
this.session.delete( obj );
}
public void atualiza( T obj ) throws HibernateException {
this.session.update( obj );
}
public T procuraPorId( Long id ) throws HibernateException {
return ( T ) this.session.load( classe, id );
}
public List< T > procuraPorNome( String nome ) throws HibernateException {
Query query = this.session.createQuery(
"FROM usandohibernate.entity.Cliente " +
"WHERE nome LIKE ? "
);
query.setString( 0, nome );
return query.list();
}
public List< T > procuraPorSobrenome( String sobrenome ) throws HibernateException {
Query query = this.session.createQuery(
"FROM usandohibernate.entity.Cliente " +
"WHERE sobrenome LIKE ? "
);
query.setString( 0, sobrenome );
return query.list();
}
public List< T > listaTudo() throws HibernateException {
return this.session.createCriteria( classe ).list();
}
public List< T > listaPagina( int inicio, int quantia )
throws HibernateException {
return this.session.createCriteria( classe ).
setMaxResults( quantia ).setFirstResult( inicio ).list();
}
}
package usandohibernate.dao;
import java.util.*;
import org.hibernate.*;
import usandohibernate.entity.*;
/**
*
* @author David Buzatto
*/
public class ProdutoDAO< T extends Produto > {
private Session session;
private Class classe = Produto.class;
public ProdutoDAO( Session session ) {
this.session = session;
}
public void adiciona( T obj ) throws HibernateException {
this.session.save( obj );
}
public void remove( T obj ) throws HibernateException {
this.session.delete( obj );
}
public void atualiza( T obj ) throws HibernateException {
this.session.update( obj );
}
public T procuraPorId( Long id ) throws HibernateException {
return ( T ) this.session.load( classe, id );
}
public List< T > procuraPorNome( String nome ) throws HibernateException {
Query query = this.session.createQuery(
"FROM usandohibernate.entity.Produto " +
"WHERE nome LIKE ? "
);
query.setString( 0, nome );
return query.list();
}
public List< T > procuraPorDescricao( String descricao ) throws HibernateException {
Query query = this.session.createQuery(
"FROM usandohibernate.entity.Produto " +
"WHERE descricao LIKE ? "
);
query.setString( 0, descricao );
return query.list();
}
public List< T > procuraPorPreco( Double preco ) throws HibernateException {
Query query = this.session.createQuery(
"FROM usandohibernate.entity.Produto " +
"WHERE preco = ? "
);
query.setDouble( 0, preco );
return query.list();
}
public List< T > listaTudo() throws HibernateException {
return this.session.createCriteria( classe ).list();
}
public List< T > listaPagina( int inicio, int quantia )
throws HibernateException {
return this.session.createCriteria( classe ).
setMaxResults( quantia ).setFirstResult( inicio ).list();
}
}
package usandohibernate;
import org.hibernate.*;
import usandohibernate.dao.*;
import usandohibernate.entity.*;
import usandohibernate.hibernate.*;
/**
*
* @author David Buzatto
*/
public class Testes {
public static void main( String[] args ) {
Produto p = new Produto();
p.setNome( "arroz" );
p.setDescricao( "comida..." );
p.setPreco( 3.5 );
Cliente c = new Cliente();
c.setNome( "david" );
c.setSobrenome( "buzatto" );
Session session = null;
Transaction t = null;
try {
session = new HibernateFactory().getSession();
t = session.beginTransaction();
new ProdutoDAO( session ).adiciona( p );
new ClienteDAO( session ).adiciona( c );
t.commit();
} catch ( HibernateException exc ) {
// tratar excessões específicas aqui
if ( t != null )
t.rollback();
} finally {
if ( session != null )
session.close();
}
}
}
Aguardo resposta!