2012-02-17 25 views
5

返回陳舊的數據我一直在尋找#1的答案,但似乎無法找到一個不涉及休眠或一些其他數據庫的包裝。MYSQL的Java/JDBC查詢是從緩存的連接

我通過在Tomcat 6的Java EE應用程序的MYSQL 5.18 JDBC驅動程序直接使用JDBC。我正在緩存Connection對象,但沒有緩存Statement對象。查詢的結果集正確返回第一次運行的最新數據。當我通過PHPMyAdmin或其他外部工具更改了幾行時,重新運行查詢,我得到過時的數據。

我使用正常的語句,而不是PreparedStatements。我試過ResultSet.TYPE_SCROLL_SENSITIVE,ResultSet.CONCUR_UPDATABLE。我也關閉了結果集。這些都不能解決問題。我也試過ResultSet.refreshRows(),但是這會導致錯誤,因爲查詢有一個JOIN子句。

,明確解決的問題是關閉連接,並重新連接到數據庫,從而導致每個查詢嘗試了沉重的代價的唯一的事情。

有沒有辦法重用連接而不返回陳舊的數據?

編輯:我目前沒有使用交易進行查詢。

這裏是一般的代碼。

Connection conn; //created elsewhere and reused 
... 

String query = "SELECT p.ID as oid,rid,handle,summary,city,state,zip,t.name AS category  
       FROM profiles AS p 
       JOIN (terms AS t) ON (p.tid = t.ID) 
       WHERE p.ID = 1"; 

ResultSet resultSet; 
Statement s; 
synchronized (conn) 
{        
    s = conn.createStatement(ResultSet.TYPE_SCROLL_SENSITIVE, 
          ResultSet.CONCUR_UPDATABLE);       
    resultSet = s.executeQuery(query); 
} 

//Iterate over the results using .next() and copy data to another data structure 
List retval = getResults(resultSet); 
s.close(); 

感謝您的幫助!

+2

您使用的是交易嗎?如果是的話隔離級別是什麼?它看起來有點像REPEATABLE READ行爲。 – 2012-02-17 04:25:37

+0

好問題。沒有這些查詢的交易。我一般使用事務處理更新/插入,但在這種情況下,我現在不在應用程序本身中執行任何操作。我正在通過一個外部工具來完成更新,這個工具可能會拋出一些東西。如果您推薦交易作爲防止髒讀的解決方案,請分享答案。另外,我沒有在連接上設置任何隔離級別。那會是問題嗎? – ricosrealm 2012-02-17 05:05:50

回答

9

原來這是未提交查詢的問題。感謝Brent Worden提出的有關交易的問題,這些問題導致我四處查看,並注意到我禁用了自動提交,並且在查詢後未提交。

所以,對我工作的解決方案:

conn.setAutoCommit(true); 

statement.executeQuery(query); 
conn.commit(); 

這使得查詢進行沖洗,防止過期數據。

+0

您能否將此標記爲答案?這樣,人們可以找到這篇文章,並閱讀你的問題和解決方案:)。 – 2012-02-17 05:58:06

+0

我會在2天內。我現在不能,因爲該網站不會讓我。 – ricosrealm 2012-02-17 06:13:51

+0

你的意思是'conn.commit();'對嗎? – 2012-05-29 10:40:52

0

爲什麼不使用使用Apache DBUtils的JDBC池?它允許您使用相同的連接並控制連接大小。這個鏈接是http://commons.apache.org/dbutils

+0

感謝您的指針。我可以試着看看這段代碼。不過,我正試圖在沒有更大代碼包裝的情況下做一些非常簡單的事情。 – ricosrealm 2012-02-17 04:15:00

3

設置事務隔離級別如下。

connection.setTransactionIsolation(Connection.TRANSACTION_READ_COMMITTED);

1

我的MySQL安裝:ENGINE = InnoDB的,默認TX_ISOLATION = REPEATABLE_READ

spring.xml

<tx:method name="find*" propagation="SUPPORTS" read-only="true" timeout="600" /> 

如果使用池連接,這將始終返回相同的結果!

變化的MySQL TX_ISOLATION = READ_COMMITTED解決我的問題。