2009-10-23 3 views
3

Я пытаюсь вызвать метод, основанный на некоторый интервал времени, вот некоторые бобы внутри applicationContext.xmlПроблемы с пружинным кварцем

<bean id="MngtTarget" 
    class="com.management.engine.Implementation" 
    abstract="false" lazy-init="true" autowire="default" dependency-check="default"> 

    <bean id="jobDetail" class="org.springframework.scheduling.quartz.MethodInvokingJobDetailFactoryBean"> 
     <property name="targetObject" ref="MngtTarget" /> 
     <property name="targetMethod" value="findItemByPIdEndDate"/> 
    </bean> 


    <bean id="simpleTrigger" class="org.springframework.scheduling.quartz.SimpleTriggerBean"> 

     <property name="jobDetail" ref="jobDetail" /> 
     <!-- 10 seconds --> 
     <property name="startDelay" value="10000" /> 
     <!-- repeat every 50 seconds --> 
     <property name="repeatInterval" value="20000" /> 
    </bean> 


    <bean class="org.springframework.scheduling.quartz.SchedulerFactoryBean"> 
     <property name="triggers"> 
      <list> 
       <ref bean="simpleTrigger" /> 
      </list> 
     </property> 
    </bean> 

Вот метод, который я пытаюсь вызвать:

public List<Long> I need findItemByPIdEndDate() throws Exception { 

       List<Long> list = null; 

       try{ 
         Session session = sessionFactory.getCurrentSession(); 

         Query query = session.getNamedQuery("endDateChecker"); 
         list = query.list(); 

         for(int i=0; i<list.size(); i++) 
         { 
           System.out.println(list.get(i)); 
         } 

         System.out.println("Total " + list.size()); 

       }catch (HibernateException e){ 
         throw new DataAccessException(e.getMessage()); 
       } 

       return list; 
     } 

Вот сообщение исключения, которое я получаю:

Invocation of method 'findItemByPIdEndDate' on target class [class com.management.engine.Implementation] failed; nested exception is No Hibernate Session bound to thread, and configuration does not allow creation of non-transactional one here 

Я провел время много прибегая к помощи до сих пор я также имею синтаксическое дерево d, чтобы изменить мой метод, как это:

public List<Long> I need findItemByPIdEndDate() throws Exception { 

        List<Long> list = null; 

        try{ 
          Session session = sessionFactory.openSession(); 

          Query query = session.getNamedQuery("endDateChecker"); 
          list = query.list(); 

          for(int i=0; i<list.size(); i++) 
          { 
            System.out.println(list.get(i)); 
          } 

          System.out.println("Total " + list.size()); 
          session.close(); 
        }catch (HibernateException e){ 
          throw new DataAccessException(e.getMessage()); 
        } 

        return list; 
      } 

И я получаю другую Сообщ ошибки, я получаю: Invocation of method 'findItemByPIdEndDate' on target class [class com.management.engine.Implementation] failed; nested exception is could not execute query], кто знает, что это все о, какие-либо предложения? спасибо

Кроме того, мой queries.hbm.xml

<hibernate-mapping> 

<sql-query name="endDateChecker"> 
<return-scalar column="PId" type="java.lang.Long"/> 
     <![CDATA[select 
    item_pid as PId 
    from 
     item 
     where 
     end_date < trunc(sysdate)]]>  
</sql-query> 
</hibernate-mapping> 
+0

Пожалуйста, добавьте конфигурацию Hibernate – sfussenegger

+0

Просто распечатайте * запрос * объект и посмотреть, если вы получаете ожидаемый запрос ' 'endDateChecker'' –

+0

Я получаю ожидается query – ant

ответ

5

Для второй ошибки («не может выполнить запрос»), я не знаю, и я действительно интересно, что сессия выглядит ,

В действии, AFAIK, постоянный контекст недоступен для Quartz Jobs, поскольку ничто не заботится о создании сеанса Hibernate для них (Quartz работает вне контекста Servlets и шаблон открытого сеанса в представлении не применяется здесь) , Вот почему вы получаете первую ошибку («Нет сеанса спящего режима, связанного с потоком»).

Одно решение для этого описано в AOP – Spring – Hibernate Sessions for background threads/jobs. В этом сообщении автор показывает , как вы можете использовать прокси-серверы Spring AOP для подключения перехватчика спящего режима, который дает вам доступ к контексту персистентности, и он заботится о закрытии и открытии сеансов для вас.

Не испытал это сам, но он должен работать.

+0

Спасибо m8, это было не решение, но оно привело меня к одному, поэтому он квалифицируется как правильный ответ. gr8 – ant

+0

Счастлив, что я могу помочь. Однако вы можете немного уточнить, «это было не решение», чтобы я мог обновить этот ответ? Заранее спасибо. –

3

Я тоже сталкиваются с той же "HibernateException: Нет Hibernate Session обязан нить" Exception

2012-01-13 13:16:15.005 DEBUG MyQuartzJob Caught an exception 
org.hibernate.HibernateException: No Hibernate Session bound to thread, and configuration does not allow creation of non-transactional one here 
at org.springframework.orm.hibernate3.SpringSessionContext.currentSession(SpringSessionContext.java:63) 
at org.hibernate.impl.SessionFactoryImpl.getCurrentSession(SessionFactoryImpl.java:687) 
at com.company.somemodule.dao.hibernate.AbstractHibernateDaoImpl.getSession(AbstractHibernateDaoImpl.java:107) 
at com.company.somemodule.dao.hibernate.SomeDataDaoImpl.retrieveSomeData(SomeDataDaoImpl.java:264) 

, и я решил ее, следуя примеру here.

Соответствующий код

import org.hibernate.Session; 
import org.hibernate.SessionFactory; 
import org.quartz.JobExecutionContext; 
import org.quartz.JobExecutionException; 
import org.slf4j.Logger; 
import org.slf4j.LoggerFactory; 
import org.springframework.orm.hibernate3.SessionFactoryUtils; 
import org.springframework.orm.hibernate3.SessionHolder; 
import org.springframework.scheduling.quartz.QuartzJobBean; 
import org.springframework.transaction.support.TransactionSynchronizationManager; 

import com.company.somemodule.dao.SomeDataDao; 
import com.company.somemodule.SomeData; 

public class MyQuartzJob extends QuartzJobBean implements Runnable { 

    private boolean existingTransaction; 
    private JobExecutionContext jobExecCtx; 
    private static Logger logger = LoggerFactory.getLogger(MyQuartzJob.class); 
    private SomeDataDao someDataDao; //set by Spring 
    private Session session; 
    private SessionFactory hibernateSessionFactory; //set by Spring 

    protected void executeInternal(JobExecutionContext ctx) throws JobExecutionException 
    this.jobExecCtx = ctx; 
    run(); 
    } 

    private void handleHibernateTransactionIntricacies() { 
    session = SessionFactoryUtils.getSession(hibernateSessionFactory, true); 
    existingTransaction = SessionFactoryUtils.isSessionTransactional(session, hibernateSessionFactory); 
    if (existingTransaction) { 
     logger.debug("Found thread-bound Session for Quartz job"); 
    } else { 
     TransactionSynchronizationManager.bindResource(hibernateSessionFactory, new SessionHolder(session)); 
    } 
    } 


    private void releaseHibernateSessionConditionally() { 
    if (existingTransaction) { 
     logger.debug("Not closing pre-bound Hibernate Session after TransactionalQuartzTask"); 
    } else { 
     TransactionSynchronizationManager.unbindResource(hibernateSessionFactory); 
     SessionFactoryUtils.releaseSession(session, hibernateSessionFactory); 
    } 
    } 

    @Override 
    public void run() { 
    // .. 

    // Do the required to avoid HibernateException: No Hibernate Session bound to thread 
    handleHibernateTransactionIntricacies(); 

    // Do the transactional operations 
    try { 

     // Do DAO related operations .. 

    } finally { 
     releaseHibernateSessionConditionally(); 
    } 
    } 

    public void setHibernateSessionFactory(SessionFactory hibernateSessionFactory) { 
    this.hibernateSessionFactory = hibernateSessionFactory; 
    } 

    public void setSomeDataDao(SomeDataDao someDataDao) { 
    this.someDataDao = someDataDao ; 
    } 
} 

конфигурации Соответствующая боб внутри applicationContext.xml

<bean name="myJob" class="org.springframework.scheduling.quartz.JobDetailBean"> 
    <property name="jobClass" value="com.somecompany.worker.MyQuartzJob" /> 
    <property name="jobDataAsMap"> 
    <map> 
     <entry key="hibernateSessionFactory" value-ref="sessionFactory" /> 
     <entry key="someDataDao" value-ref="someDataDao" /> 
    </map> 
    </property> 
</bean> 
+0

Ты спас мой день !!! – Reusable

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