簡體   English   中英

數據庫連接模式

[英]Database connection pattern

我使用mysql-native 該驅動程序支持vibed的連接池。 在dlang新聞組上, mysql-native開發人員Nick Sabalausky寫道:

“如果您使用的是連接池,則不必擔心關閉連接。整個問題是,連接將保持打開狀態,直到您需要再次使用它為止。當程序結束時,連接將自行關閉。 “。

“您只需創建池一次(無論何時何地)。然后,每次您要使用數據庫時,都可以通過調用MySqlPool.lockConnection獲得連接。”

“調用'close'總是會關閉連接。如果您從池中獲得連接,那么當您不再使用它時,它將自動返回到池中。無需為此做任何特殊的事情。”

關於應該如何做游泳池的問題? 我已經閱讀了有關單例模式的信息,不能理解這種情況。

我寫了下一個代碼:

database class:
import std.stdio;
import std.string;
import mysql;
import vibe.d;

import config;
import user;

class Database
{
    Config config;
    MySqlPool mydb;
    Connection connection;

    this(Config config)
    {
        this.config = config;
        mydb = new MySqlPool(config.dbhost, config.dbuser, config.dbpassword, config.dbname, config.dbport);    
    }

    void connect()
    {
        if(connection is null)
        {
            connection = mydb.lockConnection();
        }
        scope(exit) connection.close();
    }

}

用戶類/結構:

module user;

import mysql;
import vibe.d;

struct User
{
    int id;
    string login;
    string password;
    string usergroup;
}
    void getUserByName(string login)
    {
        User user;
        Prepared prepared = prepare(connection, `SELECT id, login, password, usergroup from users WHERE login=?`); // need to get connection accessible here to make request to DB
        prepared.setArgs(login);
        ResultRange result = prepared.query();
        if (result.empty) 
            logWarn(`user: "%s" do not exists`, login);
        else
        {
                Row row = result.front;
                user.id = row[0].coerce!(int);
                user.login = row[1].coerce!string;
                user.password = row[2].coerce!string;
                user.usergroup = row[3].coerce!string;

        logInfo(`user: "%s" is exists`, login);
        }

    }

我不明白什么是訪問connection實例的正確方法的問題。 users結構內創建每個新的數據庫連接類似乎是非常愚蠢的想法。 但是如何以更好的方式做到這一點? 要使Connection connection全局Connection connection 好嗎 還是有更正確的方法?

一種實現方法是將連接傳遞給需要它的函數。 因此,您將重構getUserByName()以將連接作為參數。

另一種選擇是使用DAO模式 DAO類的構造方法會將連接作為主要參數之一,並且所有方法都將使用該連接來執行數據庫操作。

scope(exit) connection.close();

刪除該行。 connect函數返回之前,它將關閉您剛剛從池中收到的connect 您在此處所做的所有操作只是打開連接以立即再次將其關閉。

更改getUserByName以將連接作為參數(通常作為第一個參數)。 通常,需要調用getUserByName任何代碼getUserByName應該打開一個連接,或者通過lockConnection從池中獲取連接,然后將該連接傳遞給getUserByName以及需要使用的任何其他與數據庫相關的功能。 然后,在代碼完成調用getUserByName (以及需要調用的任何其他數據庫函數)之后,您就不必擔心連接了,而讓光纖連接完成(如果您使用的是vibed並從池)或close連接(如果您未從虛擬池中獲得連接)。

暫無
暫無

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

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