2017-04-26 11 views
0

これは、PHP 5.4およびMariaDB 5.5を実行するCentOS 7サーバを参照しています。PHPの他のオブジェクトからの永続的なデータベースオブジェクト接続の使用

私はPHPでOOPをやや新しくしています。 MySQLiをすると手続きデータベース機能からOOPへのMySQLからのスクリプトの束を変換するには、私はこの基本的なデータベースのクラスを設定しますmysql_ *を使用し、元の手続きデータベース機能付き

class Database 
{ 
    private $host = "localhost"; 
    private $username; 
    private $password; 
    private $database; 
    private $dbconnect; 

    function __construct() 
    { 
     // Load config file for database connection info 
     $ini = parse_ini_file("config.ini"); 

     $this->username = $ini['db.user']; 
     $this->password = $ini['db.pword']; 
     $this->database = $ini['db']; 
    } 

    public function connect() 
    { 
     // Only make a new connection if one not already established. 
     if (empty($this->dbconnect)) { 

      $mysql = new mysqli($this->host, $this->username, $this->password, $this->database); 

      if ($mysql->connect_errno) { 
       throw new appError($mysql->connect_error); 
      } 

      $this->dbconnect = $mysql; 
     } 

     return $this->dbconnect; 
    } 

    public function query($query) 
    { 
     $db = $this->connect(); 
     $result = $db->query($query); 

     if ($db->errno) return false; 
     return $result; 
    } 

    public function select($query) 
    { 
     $rows = array(); 
     $result = $this->query($query); 

     if ($result === false) return false; 

     // Create array with results 
     while ($row = $result->fetch_assoc()) { 
      $rows[] = $row; 
     } 

     return $rows; 
    } 
} 

、持続的なデータベース接続が行われましたスクリプトの開始付近で、リソースIDがグローバル変数に保管されていた場合、グローバル・リソース変数にアクセスすることによって、すべての照会がその1つのデータベース接続を介して実行されました。重要なことに、これは他の関数やオブジェクトの中からうまく機能しました。 ...だから各スクリプトの開始時に、私は...

db_connect(); 

これを行うと思います。そして、このように私のクエリを実行し

function db_connect() { 

    if (!empty($GLOBALS['DBCONNECT']) && is_resource($GLOBALS['DBCONNECT'])) { 
     return $GLOBALS['DBCONNECT']; 
    } else {  
     $result = mysql_connect("localhost", DB_USER, DB_PASSWORD); 
     $GLOBALS['DBCONNECT'] = $result; 
     return $result; 
    } 
} 

$result = mysql_query($query, db_connect()); 
:ここではその機能が働いていた方法です

これにより、1つのデータベース接続が確立され、すべてのクエリがその接続を介して実行されることが確認されました。

の上に新しいデータベースクラスでは、私は私のスクリプトの開始時に、それをインスタンス化...

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

しかし、私は実行する必要がある他のオブジェクトにそのデータベース・オブジェクトにアクセスできるようにする方法を理解していません同じデータベース接続がスクリプト全体で使用されるように、データベースクエリを実行します。私が今やっていることは、これは、データベースへの新規および追加の接続を作成している上記のクラス内の新しいデータベースオブジェクトをインスタンス化し

class MyClass 
{ 
    public function myFunction() 
    { 
     $db = new Database; 
     $data = $db->select("SELECT * FROM mydata WHERE id = 888"); 
     ... 
    } 
} 

...基本的にこれでは、データベース$dbオブジェクトにアクセスすることはできませんので、 (私が知っている)親呼び出しスクリプトで作成されます。

永続的なMySLQiデータベース接続を開くためにオブジェクトを使用する方法はありますか?そのスクリプトによって読み込まれたすべての関数とオブジェクトは使用できますか?それとも、クラスやオブジェクトではなく、手続き型の関数でうまくいくのですか?このソリューションは、データベースのプロパティとそのメソッドを作成することにありますかstatic?これを行うと、connect()関数が必要とするconfig.iniファイルからデータベースのユーザー名とパスワードをどのようにロードするのか不明で、Databaseオブジェクトのインスタンス化時にのみ実行されます。

ここで基本的な質問は、インスタンス化されたオブジェクトのプロパティまたはメソッドに別のオブジェクトからアクセスする方法ですか?あるいは、それは疑問ではないし、私は何か他のものを完全に欠いている。ありがとう!

答えて

0

データベースクラスの静的ファクトリメソッドを使用して、以前に初期化されたデータベースクラスのインスタンスを返す単純な方法が1つあります。

class Database 
{ 
    //static instance of the class 
    private static $instance; 

    public static function getDB() 
    { 
     //if the instance is not set, set it 
     if(is_null(self::$instance)) 
     { 
      self::$instance = new Database(); 
      self::$instance->connect(); 
     } 
     return self::$instance; 
    } 

    //rest of your class below 
} 

この静的メソッドは、任意のコンテキストのどこからでも呼び出すことができ、データベースの同じ接続インスタンスを取得できるようになります。必要な場所で$db = Database::getDB()に電話するだけです。たとえば:

function TestFunction() 
{ 
    //get an instance to the database 
    $dbInstance = Database::getDB(); 

    //then use the database object like you normally would. 
    $dbInstance->query("SELECT * FROM `someTable`"); 
} 

class TestClass 
{ 
    public function doSomething() 
    { 
     //get an instance to the database 
     $dbInstance = Database::getDB(); 

     //then use the database object like you normally would. 
     $dbInstance->query("SELECT * FROM `someTable`"); 
    } 
} 

$tc = new TestClass(); 
$tc->doSomething(); 

別のオプション、と私は簡単にするために使用するものは、どこでもクエリのデータベースクラスでとなるように、あなたの接続は、静的および参照宣言です。これにより、どこでも$db = new Database()を作成することができ、同じ接続を使用します。私はこれがグローバルと同じであるかのように悩まされました。なぜなら、実際には1つのデータベースにしか接続できないからです(後続の接続は接続変数を上書きします)。しかし、それは私のために働きました。また、そのインスタンスで実行されたクエリが何であっても記憶しておき、クエリのプライベートカウントを実行することができます。

+0

ドゥそのコメントの背後にある理由を確認するには、静的なものを使用しないでください。 – getl0st

+1

@ getl0stあなたがそれを正しく使用しているならば、静的でないことはありません。ファクトリーメソッドは、よく受け入れられた習慣で、かなり必要です。また、私はあなたの代替ソリューションが表示されません。あなたはグローバルを好むでしょうか? –

+0

データベースクエリを実行する必要がある別のオブジェクト内からgetDB()メソッドにアクセスするにはどうすればいいですか? – Monty

3

あなただけの単一のトーン

<?php 
    /* 
    * Mysql database class - only one connection alowed 
    */ 
    class Database { 
     private $_connection; 
     private static $_instance; //The single instance 
     private $_host = "HOSTt"; 
     private $_username = "USERNAME"; 
     private $_password = "PASSWORd"; 
     private $_database = "DATABASE"; 
     /* 
     Get an instance of the Database 
     @return Instance 
     */ 
     public static function getInstance() { 
      if(!self::$_instance) { // If no instance then make one 
       self::$_instance = new self(); 
      } 
      return self::$_instance; 
     } 
     // Constructor 
     private function __construct() { 
      $this->_connection = new mysqli($this->_host, $this->_username, 
       $this->_password, $this->_database); 

      // Error handling 
      if(mysqli_connect_error()) { 
       trigger_error("Failed to conencto to MySQL: " . mysql_connect_error(), 
        E_USER_ERROR); 
      } 
     } 
     // Magic method clone is empty to prevent duplication of connection 
     private function __clone() { } 
     // Get mysqli connection 
     public function getConnection() { 
      return $this->_connection; 
     } 
    } 

とデータベースへの接続を作成し、クエリ簡単な使用をするラインで静的メソッドそのような何かを行うことができます。

$db = Database::getInstance(); 
$mysqli = $db->getConnection(); 
$sql_query = "SELECT foo FROM ....."; 
$result = $mysqli->query($sql_query); 
関連する問題