Pessoal, estou precisando de ajuda em questão de se utilizar o criteria com entityManager com trasações controladas pelo container,
vi alguns posts aqui no forum, porém as soluções propostas não funcionaram,
segue a situação,
preciso que as transacões sejam controladas pelo container, porém, gostaria de saber se é possível usar o criteria pegando a session, desta maneira:
session = (Session) entityManager.getDelegate();
pois recebo uma exception de nullpointer ao executar meu método getUniqueResult, creio que pode algum problema na injeção
@Stateful
@TransactionManagement(TransactionManagementType.CONTAINER)
@TransactionAttribute(TransactionAttributeType.REQUIRED)
public class PersistenceInterface implements PersistenceInterfaceLocal, Serializable {
public static final Logger log = Logger.getLogger(PersistenceInterface.class);
@PersistenceContext(unitName = "persistenceUnit")
private EntityManager entityManager;
Session session;
public PersistenceInterface() {
super();
try {
session = (Session) entityManager.getDelegate();
} catch (Exception e) {
e.printStackTrace();
}
}
@Override
public void merge(AbstractEntity entity) {
try {
entityManager.merge(entity);
} catch (Exception e) {
e.printStackTrace();
}
}
@Override
public void persist(AbstractEntity entity) {
try {
entityManager.persist(entity);
} catch (HibernateException e) {
e.printStackTrace();
}
@Override
public Object getUniqueResult(Class classe, Long id) {
try {
Criteria criteria = session.createCriteria(classe);
criteria.add(Restrictions.eq("ativo", true));
criteria.add(Restrictions.eq("id", id));
criteria.setResultTransformer(Criteria.DISTINCT_ROOT_ENTITY);
return criteria.uniqueResult();
} catch (NonUniqueResultException e) {
e.printStackTrace();
} catch (HibernateException e) {
e.printStackTrace();
} catch (Exception e) {
e.printStackTrace();
}
return null;
}
@Override
public Criteria getCriteria(Class classe) {
return session.createCriteria(classe);
}
@Override
public Criteria createCriteria(Class classe) {
return getCriteria(classe);
}
}
Antes de mais nada agradeço…
Bom, só algumas informações complementares… Vamos dizer que meu projeto ja estava funcionando mas estava controlando as TRansactions na mão, e é o que não quero mais…
Então o esquema era assim,
persistence.xml
<?xml version="1.0" encoding="UTF-8"?>
<persistence version="1.0" xmlns="http://java.sun.com/xml/ns/persistence"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/persistence http://java.sun.com/xml/ns/persistence/persistence_1_0.xsd">
<persistence-unit name="persistenceUnit" transaction-type="JTA">
<provider>org.hibernate.ejb.HibernatePersistence</provider>
<jta-data-source>jdbc/***</jta-data-source>
<properties>
<property name="hibernate.dialect" value="org.hibernate.dialect.PostgreSQLDialect" />
<property name="hibernate.connection.username" value="**"/>
<property name="hibernate.connection.driver_class" value="org.postgresql.Driver"/>
<property name="hibernate.connection.password" value="**"/>
<property name="hibernate.connection.url" value="jdbc:postgresql://***"/>
<property name="hibernate.use_sql_comments" value="false" />
<property name="hibernate.show_sql" value="false" />
<property name="hibernate.transaction.factory_class" value="org.hibernate.transaction.CMTTransactionFactory"/>
<property name="hibernate.transaction.manager_lookup_class" value="org.hibernate.transaction.BESTransactionManagerLookup"/>
<property name="hibernate.hbm2ddl.auto" value="update" />
</properties>
</persistence-unit>
</persistence>
@Stateful
public class PersistenceInterface implements PersistenceInterfaceLocal, Serializable {
//Logger
public static final Logger log = Logger.getLogger(PersistenceInterface.class);
@PersistenceUnit
public static final EntityManagerFactory emFactory = Persistence.createEntityManagerFactory("persistenceUnit");
@PersistenceContext
private EntityManager entityManager = emFactory.createEntityManager();
@Resource
UserTransaction utx;
Session session;
public PersistenceInterface() {
super();
try {
session = (Session) entityManager.getDelegate();
} catch (HibernateException e) {
e.printStackTrace();
}
}
@Override
public void merge(AbstractEntity entity) {
session.clear();
Transaction tx = session.beginTransaction();
try {
entity.setUltimaModificacao();
session.merge(entity);
tx.commit();
} catch (HibernateException e) {
tx.rollback();
e.printStackTrace();
}
}
public Criteria getCriteria(Class classe) {
return session.createCriteria(classe);
}
@Override
public Criteria createCriteria(Class classe) {
return getCriteria(classe);
}
@Override
public Object getUniqueResult(Class classe, Conjunction restricoes) {
try {
Criteria criteria = getSession().createCriteria(classe);
criteria.add(Restrictions.eq("ativo", true));
if (restricoes != null) {
criteria.add(restricoes);
}
return criteria.uniqueResult();
} catch (HibernateException e) {
e.printStackTrace();
} catch (Exception ex) {
ex.printStackTrace();
}
return null;
}
/* Outros métodos**/
Agora estou tentando somente injetar o entityManager, e tirei todo aquele createEntityManagerFactory… e as linhas la no persist.xml que correspondem a factory de transações do hibernate
assim:
PersistenceContext(unitName=“persistenceUnit”)
private EntityManager entityManager;
aí tendo fazer um entityManager.getDelegate(); ele ja me traz uma exception nullPointer ou seja não consegui injetar
Obs: estou usando GlassFish,
Muito Obrigado novamente
Mais informações complementares,
estou utilizando maven, Glassfish e minha configuração de DS esta sendo feita direta no Admin do Container
Boa noite danilodesousa.
Estou tendo o mesmo problema que você, e também utilizando EJB + Maven + Glassfish e Hibernate.
Você conseguiu resolver o seu problema?
Desde já agradeço.
Abs.
Oi
Você pode colar o stacktrace?
De qualquer forma, lembre que o entityManager.getDelegate() que vai ser retornado depende do AS que você está usando (JBoss, Glassfish… ). Quando a conexão é controlada pelo AS ele te retorna a implementação da interface EntityManager, ao invés da sessão do Hibernate.
Tente recuperar assim:
@PersistenceContext
EntityManager em;
public Session getSession(){
if(em.getDelegate() instanceof EntityManagerImpl){
EntityManagerImpl manager = (EntityManagerImpl)em.getDelegate();
session = manager.getDelegate();
else{
session = em.getDelegate();
}
return session;
}