سؤال

هل من الممكن الاحتفاظ بجميع التكوينات المتعلقة بقاعدة البيانات الخاصة بي (أسماء المضيفين وأسماء المستخدمين وكلمات المرور وقواعد البيانات) بالإضافة إلى وظيفة الاتصال بقاعدة البيانات الصحيحة وتحديدها في فئة منفصلة؟

لقد حاولت شيئًا مثل هذا:

class Database
{
    var $config = array(
        'username' => 'someuser',
        'password' => 'somepassword',
        'hostname' => 'some_remote_host',
        'database' => 'a_database'
    );
    function __construct() {
        $this->connect();
    }
    function connect() {
        $db = $this->config;
        $conn = mysql_connect($db['hostname'], $db['username'], $db['password']);
        if(!$conn) {
            die("Cannot connect to database server"); 
        }
        if(!mysql_select_db($db['database'])) {
            die("Cannot select database");
        }
    }
}

وبعد ذلك في فئة أخرى سأستخدمها في وظيفة __construct للفئات:

require_once('database.php');
var $db_conn = new Database();

لكن هذا لا يحفظ الاتصال، بل ينتهي به الأمر إلى الاتصال الافتراضي بقاعدة البيانات المحلية للخادم.أم هل يجب علي تنفيذ أوامر قاعدة البيانات في كل مرة قبل تنفيذ بعض أوامر قاعدة البيانات؟

هل كانت مفيدة؟

المحلول

لقد قمت بتعديل فصلك للعمل كما يبدو أنك تتوقعه:

<?php
class Database
{
    var $conn = null;
    var $config = array(
        'username' => 'someuser',
        'password' => 'somepassword',
        'hostname' => 'some_remote_host',
        'database' => 'a_database'
    );

    function __construct() {
        $this->connect();
    }

    function connect() {
        if (is_null($this->conn)) {
            $db = $this->config;
            $this->conn = mysql_connect($db['hostname'], $db['username'], $db['password']);
            if(!$this->conn) {
                die("Cannot connect to database server"); 
            }
            if(!mysql_select_db($db['database'])) {
                die("Cannot select database");
            }
        }
        return $this->conn;
    }
}

الاستخدام:

$db = new Database();
$conn = $db->connect();

لاحظ أنه يمكنك الاتصال بـconnect() عدة مرات كما تريد وسوف يستخدم الاتصال الحالي، أو ينشئ واحدًا إذا لم يكن موجودًا.هذا ال شيء جيد.

لاحظ أيضًا أنه في كل مرة تقوم فيها إنشاء مثيل كائن قاعدة البيانات (باستخدام جديد) سوف تقوم بإنشاء اتصال جديد بقاعدة البيانات.أقترح عليك النظر في تنفيذ فئة قاعدة البيانات الخاصة بك باعتبارها سينجلتون أو تخزينها في التسجيل للوصول العالمي.

يمكنك أيضًا القيام بذلك بالطريقة القذرة ودفعه في $GLOBALS.

يحرر

لقد أخذت الحرية في تعديل صفك لتنفيذ نمط Singleton، واتباع اصطلاحات PHP5 OOP.

<?php
class Database
{
    protected static $_instance = null;

    protected $_conn = null;

    protected $_config = array(
        'username' => 'someuser',
        'password' => 'somepassword',
        'hostname' => 'some_remote_host',
        'database' => 'a_database'
    );

    protected function __construct() {
    }

    public static function getInstance()
    {
        if (null === self::$_instance) {
            self::$_instance = new self();
        }
        return self::$_instance;
    }

    public function getConnection() {
        if (is_null($this->_conn)) {
            $db = $this->_config;
            $this->_conn = mysql_connect($db['hostname'], $db['username'], $db['password']);
            if(!$this->_conn) {
                die("Cannot connect to database server"); 
            }
            if(!mysql_select_db($db['database'])) {
                die("Cannot select database");
            }
        }
        return $this->_conn;
    }

    public function query($query) {
        $conn = $this->getConnection();
        return mysql_query($query, $conn);
    }
}

الاستخدام:

$res = Database::getInstance()->query("SELECT * FROM foo;");

أو

$db = Database::getInstance();
$db->query("UPDATE foo");
$db->query("DELETE FROM foo");

نصائح أخرى

ويمكنك بالتأكيد حفاظ على معلومات الاتصال في ملف منفصل.

وحفظ فقط كائن الاتصال الخاص بك - $ كون في الدالة ربط () - في متغير الصف. عليك أن تكون قادرا على إعادة استخدامها عبر استدعاءات ذلك الحين.

في طريقتك اتصال () $ كون ليست سوى متغير محلي موجود فقط في نطاق هذا الأسلوب. في أقرب وقت إرجاع الأسلوب لن يكون هناك إشارة (أخرى) إلى المورد الاتصال وسيتم جمعها / التخلص منها. ستحتاج على الأقل

$this->conn = mysql_connect(...)

وهنا يأتي المفرد مع شركة تنمية نفط عمان سبيل المثال. بفضلhodobave

<?php 

/**
 * DB Connection class
 * Singleton pattern
 * An single instance of DB connection is created
**/

class Db{

    protected static $_instance = null;
    protected $_conn;

    protected $_config = [
        'username' => 'root',
        'password' => '',
        'hostname' => 'localhost',
        'database' => 'news',
    ];
    protected function __construct(){

    }

    public function getInstance(){
        if(null === self::$_instance){
            self::$_instance = new self();
        }
        return self::$_instance;
    }

    public function getConnection(){
        if(is_null($this->_conn)){
            //connect here
            $db = $this->_config;
            $dsn = "mysql:host={$db['hostname']};dbname={$db['database']}";
            $this->_conn = new PDO($dsn, $db['username'], $db['password']);
        }
        return $this->_conn;
    }

    public function query($sql){
        $args = func_get_args();
        array_shift($args);
        $statement = $this->getConnection()->prepare($sql);
        $statement->execute($args);
        return $statement->fetchAll(PDO::FETCH_OBJ);
    }
}



$res = Db::getInstance();
$users = $res->query("SELECT * FROM `user` WHERE id=?",1);
print_r($users);
?> 
مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top