簡體   English   中英

播放框架:關閉JDBC連接

[英]Play framework: closing JDBC connection

是否需要在Play中手動關閉數據庫連接(JDBC)! 框架(2.3.0)后的每個請求?

此處的示例僅執行DB.getConnection(),而未說明關閉連接的方法: http ://www.playframework.com/documentation/2.3.x/JavaDatabase

所以我假設對每個GET / POST請求執行一個DB.getConnection()是可以接受的,並且我不需要關閉任何東西。 sql語句呢?

conn = ds.getConnection();
stmt = conn.createStatement();
stmt.execute("SOME SQL QUERY");
stmt.close();

這可能是一個非常糟糕的假設,具體取決於您的數據庫供應商。

連接是客戶端和數據庫服務器組件的稀缺資源。 客戶端上的垃圾收集器當然可以清理Connection對象,但這不會通知服務器連接已關閉。 您很快就會用完服務器端的連接,因為它們是有限的資源。 StatementResultSet相同(服務器端的光標)。

更好的解決方案是使用JDBC連接池來分攤創建連接的成本,並在完成連接后管理關閉它們。

您還應該在finally塊中關閉SQL資源,該塊包含在單獨的try / catch塊中:

public class DatabaseUtils {

    private DatabaseUtils() {}

    // Similar for Statement and ResultSet
    public static void close(Connection c) {
        try {
            if (c != null) {
                c.close();
            }
        } catch { Exception e) {
            log.error(e);
        }
    }
}

在您的代碼中:

Connection c = null;
try {
    c = ds.getConnection();    
    // Do something with the connection
} finally {
    DatabaseUtils.close(c);  // same for Statement and ResultSet
}

如果仔細閱讀文檔,您會發現它們確實回答了您的第一個問題:

重要的是要注意,結果連接不會在請求周期結束時自動處理。 換句話說,您有責任在代碼中的某個位置調用它們的close()方法,以便可以將它們立即返回到池中。

關於SQL語句,我想您不必顯式關閉它。 在Javadoc中的Connection.close()中,他們說:

立即釋放此Connection對象的數據庫和JDBC資源,而不是等待它們自動釋放。

如果我正確理解這一點,Connection.close()也應該釋放Statement資源。

Scala有一種更優雅的方式(已通過Play 2.6測試):

但是,當然,您需要在打開的連接上的某個時刻調用close(),以將其返回到連接池。 另一種方法是讓Play管理為您關閉連接:

// access "default" database
db.withConnection { conn =>
  // do whatever you need with the connection
}

請參閱文檔

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM