1

我有以下方法,每隔幾秒插入一批大量的記錄。運行之後的一段時間,我得到的錯誤如下所示:如何正確關閉並打開Hibernate會話?

ERROR: Communications link failure

The last packet successfully received from the server was 523 milliseconds ago. The last packet sent successfully to the server was 8 milliseconds ago.

May 16, 2013 9:48:30 AM com.mchange.v2.c3p0.stmt.GooGooStatementCache checkinStatement INFO: Problem with checked-in Statement, discarding.

com.mysql.jdbc.exceptions.jdbc4.MySQLNonTransientConnectionException: No operations allowed after statement closed.


我用它來打開代碼和關閉連接如下:

public DataControllerImp() { 
    session = HibernateUtil.getSessionFactory().openSession(); 
} 

@Override 
public void saveMessage(ArrayList<Message> messages) { 
    Transaction tx = session.beginTransaction(); 

    for (int i = 0; i < mesages.size(); i++) { 
     Message message = messages.get(i); 

     try { 
      session.save(message); 
      if (i % 75 == 0) { 
       // flush a batch of inserts and release memory: 
       session.flush(); 
       session.clear(); 
      } 
     } catch (Exception e) { 
      // TODO Auto-generated catch block 
      e.printStackTrace(); 
     } finally { 
      session.close(); 
     } 
    } 

    tx.commit(); 
} 


我也使用C3P0連接池。我的配置是這樣的:

<property name="connection.provider_class">org.hibernate.connection.C3P0ConnectionProvider</property>   
<property name="hibernate.c3p0.acquire_increment">1</property> 
<property name="hibernate.c3p0.idle_test_period">300</property> 
<property name="hibernate.c3p0.min_size">3</property> 
<property name="hibernate.c3p0.max_size">20</property> 
<property name="hibernate.c3p0.max_statements">50</property> 
<property name="hibernate.c3p0.timeout">300</property> 
<property name="hibernate.c3p0.acquireRetryAttempts">1</property> 
<property name="hibernate.c3p0.acquireRetryDelay">250</property> 


上午我打開和關閉不正確的連接?請讓我知道我可以改變停止接收這個錯誤並停止我的程序。

+0

作爲補充,請參閱官方[休眠參考](http://docs.jboss.org/hibernate/orm/4.3/manual/en-US/html/ch13.html#transactions-demarcation-非託管)來說明會話/事務處理習慣用法。 – informatik01

回答

2
Transaction tx = session.beginTransaction(); 
    try { 
     for (int i = 0; i < mesages.size(); i++) { 
      Message message = messages.get(i); 
      session.save(message); 
      if (i % 75 == 0) { 
       // flush a batch of inserts and release memory: 
       session.flush(); 
       session.clear(); 
      } 
     } 
     tx.commit(); 
    }catch (Exception e) { 
     // TODO Auto-generated catch block 
     e.printStackTrace(); 
     tx.rollBack(); 
    }finally{ 
     session.close(); 
    } 
} 
+0

每次調用這個方法都會關閉連接?這真的是放置結束語的正確地方嗎? – Atma

+0

您在提交之前正在關閉會話時收到了例外情況。關於要關閉會話,這取決於工作單元,理想的情景會是每個線程打開和關閉會話一次。 – Ziul

0

而是爲任何對象類型製作泛型方法並傳遞對象。也添加任何列表的邏輯。

public void save(Object obj) { 
    Session session = null; 
    Transaction transaction = null; 
    try { 
     session = sessionFactory.getCurrentSession(); 
     transaction = session.beginTransaction(); 
     session.save(obj); 
     session.flush(); 
     transaction.commit(); 
    } catch (JDBCException jde) { 
     logger.fatal("Error occured in database communication", jde); 
     transaction.rollback(); 
     throw new RuntimeException(jde); 
    } finally { 
     if (session.isOpen()) { 
      session.close(); 
     } 
    } 
} 
相關問題