2010-10-08 5 views
2

J'ai rencontré un problème que je ne comprends pas vraiment - à moins qu'une méthode fonctionnant avec le DAO soit annotée comme @Transactional, la base de données sous-jacente n'est pas mise à jour. Mon application fonctionne sur JPA/Hibernate, Spring et Wicket. Pourquoi donc?JPA - la base de données est mise à jour uniquement lorsque la méthode est @Transactional

OAC:

@Repository(value = "userDao") 
public class UserDaoJpa implements UserDao { 
    @PersistenceContext 
    private EntityManager em; 

    public User findById(Long id) { 
     return em.find(User.class, id); 
    } 

    public List findAll() { 
     Query query = em.createQuery("select e from User e"); 
     return query.getResultList(); 
    } 

    public User create(User user) { 
     em.persist(user); 
     return user;   
    } 

    public User update(User user) { 
     return em.merge(user); 
    } 

    public void delete(User user) { 
     user = em.merge(user); 
     em.remove(user); 
    } 
} 

Service:

@Service(value = "userManager") 
public class UserManagerImpl implements UserManager { 
    @Autowired 
    UserDao dao; 

    public void setUserDao(UserDao dao) { 
     this.dao = dao; 
    } 

    public List getUsers() { 
     return dao.findAll(); 
    } 

    public User getUser(String userId) { 
     return dao.findById(Long.valueOf(userId)); 
    } 

    public void saveUser(User user) { 
     dao.update(user); 
    } 

    @Transactional 
    public void removeUser(User user) { 
     dao.delete(user); 
    } 
} 

Si je laisse de l'annotation @Transactional, la base de données ne soit pas mis à jour.

Répondre

3

Eh bien c'est normal: Chaque manipulation de base de données dans le schéma CRUD a besoin de ses limites de transaction. Sans ces limites, rien n'est écrit dans la base de données. Une transaction est une collection de manipulations DB (insertions, mises à jour) qui doivent toutes être réussies ou l'action entière est annulée par la base de données. C'est pourquoi vous devez indiquer à Hibernate quand une Transaction commence et se termine, ainsi Hibernate peut dire quelles actions doivent être considérées comme des Unités de Travail. Sans limites de transaction, la validation finale de la base de données ne se produit jamais.

espérons que cela a aidé

+0

oh, cela a du sens. Les limites de transaction sont-elles généralement marquées sur la couche au-dessus de la couche de service, où je regroupe plusieurs appels de couche de service? –

+0

Normalement, vous appliquez les limites sur la couche de service, mais si vous le souhaitez, vous pouvez également définir un @Transcational supplémentaire sur la couche ci-dessus et les méthodes transactionnelles de la couche inférieure participeront à la transaction supérieure. consultez google pour l'isolation des transactions pour quelques exemples ... – fasseg

+0

Le chapitre 11 d'Hibernate Docs est un bon point de départ pour apprendre ce genre de choses. http://docs.jboss.org/hibernate/core/3.3/reference/en/html/transactions.html – fasseg

-1

Essayez de vider et de valider.

Questions connexes