2009-10-23 95 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 2009-10-23 14:00:36

+0

就打印*查詢*對象,看看你是否得到預期的查詢''endDateChecker'' – 2009-10-23 14:20:26

+0

我越來越期待查詢 – ant 2009-10-23 14:33:30

回答

5

對於第二個錯誤(「無法執行查詢」),我不知道,我真的很疑惑會議的樣子。在Quarted Jobs中,持久化上下文對於爲它們建立一個Hibernate Session沒有任何幫助(Quartz在Servlets的上下文之外運行,而view view中的開放式會話在這裏不適用),在這個契約中,AFAIK沒有提供持久化上下文。 。這就是爲什麼你得到第一個錯誤(「沒有hibernate會話綁定到線程」)。

對此的一種解決方案在AOP – Spring – Hibernate Sessions for background threads/jobs中描述。在這篇文章中,作者展示了如何使用Spring AOP代理連接一個hibernate攔截器,該攔截器允許您訪問持久化上下文,並且需要關閉並打開您的會話

雖然沒有自己測試,但它應該工作。

+0

謝謝m8,這不是解決方案,但它使我成爲一個,因此它有資格成爲正確的答案。 gr8 – ant 2009-10-26 13:39:05

+0

我很高興能提供幫助。但是,您能否詳細說明「這不是解決方案」,以便我可以更新此答案?提前致謝。 – 2009-10-26 14:18:10

3

我也正面臨着同樣的「HibernateException的:沒有Hibernate的Session綁定到線程」異常

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 ; 
    } 
} 

相關bean中的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 2014-03-25 07:12:25