2014-03-05 2 views
3

Класс MyDao имеет методы выполнения целых задач сохранения через Hibernate SessionFactory, он отлично работает.Нет сеанса Hibernate в @PostConstruct

я впрыснуть MyDao в MyService, как можно видеть выше, но когда @PostConstruct инициализации() метод вызывается после инъекции MyDao (отладки можно увидеть MyDao хорошо впрыскивается) получить следующее исключение Hibernate:

орг. hibernate.HibernateException: сеанса не найдено для текущей резьбы

Реализация моего обслуживания.

@Service("myService") 
@Transactional(readOnly = true) 
public class MyServiceImpl implements MyService { 

    @Autowired 
    private MyDao myDao; 
    private CacheList cacheList; 

    @PostConstruct 
    public void init() { 

     this.cacheList = new CacheList(); 
     this.cacheList.reloadCache(this.myDao.getAllFromServer()); 
    } 

    ... 
} 

ПУТЬ К РЕШЕНИЮ

Как @йогом рекомендовалось выше меня, я использовал TransactionTemplate, чтобы получить один действительный/активный сеанс транзакции, в этом случае я реализовал Повсеместно конструкторе отлично работает для меня.

@Service("myService") 
@Transactional(readOnly = true) 
public class MyServiceImpl implements MyService { 

    @Autowired 
    private MyDao myDao; 
    private CacheList cacheList; 

    @Autowired 
    public void MyServiceImpl(PlatformTransactionManager transactionManager) { 

     this.cacheList = (CacheList) new TransactionTemplate(transactionManager).execute(new TransactionCallback(){ 

      @Override 
      public Object doInTransaction(TransactionStatus transactionStatus) { 

       CacheList cacheList = new CacheList(); 
       cacheList.reloadCache(MyServiceImpl.this.myDao.getAllFromServer()); 

       return cacheList; 
      } 

     }); 
    } 

    ... 
} 
+0

Ваш код имеет «пустоту», где я не ожидал бы этого: 'public void MyServiceImpl'. Должен ли это быть конструктором или это метод, который вы вызываете из другого места? –

ответ

4

Я не думаю, что есть какая-либо операция позволила на @PostConstruct уровне, так @Transactional не будет делать здесь, если не mode установлен в aspectj в <tx:annotation-driven mode="aspectj" />.

Согласно this обсуждения вы можете использовать TransactionTemplate начать ручную операцию внутри init() связать session, но если вы намерены строго придерживаться декларативной транзакции вам нужно использовать ApplicationListener для регистрации событий и пользователя ContextRefreshedEvent инициировать транзакцию.

+0

Большое спасибо, TransactionTemplate отлично работает для меня. ;) – Dani

0

Убедитесь, что вы работаете по транзакции. Я вижу аннотацию транзакции, но похоже, что вы пропустили активацию управления транзакциями с помощью аннотации с использованием тега <tx:annotation-driven/> в контексте весны.

0

Это происходит из-за того, что MyServiceImpl.init() вызывается весной после MyServiceImpl связанной с ним фасонной конструкции и @Transaction аннотация не используется для управления жизненным циклом сеанса.
Решение может быть рассмотреть Spring AOP вокруг методов, которые используют кэш вместо @PostConstruct

Смежные вопросы