Hmerman6006
Hmerman6006

Reputation: 1913

Danger of Declaring Multiple Database Connections in Public __Constructor vs Static Variable Connection

I recently started to update my Api code on an Apache server by using more inheritance. As I was a bit careful to use it in the past due to inexperience.
The thing is I noticed that for each Model instance a new database connection is set. So I created an alternative connection on a Static variable to pass to each Model. My question is will multiple database connection on each new Model instance cause problems if I create a connection such in my example below using __construct?

     class ApiEnterprises {
        protected $db;

        private $table;
        public function __construct(){
            $this->messager = new Messager();
            $this->table = 'enterprisetable';
            $this->db = new \mysqli(DB_HOST, DB_USERRW, DB_PASSWRW, DB_DBASE);
            if ($this->db === NULL || !$this->db) {
                // set response code
                echo $this->messager->databaseFailed();
            }
        }
    }

    class ApiUsers {
        protected $db;

        private $table;
        public function __construct(){
            $this->messager = new Messager();
            $this->table = 'usertable';
            $this->db = new \mysqli(DB_HOST, DB_USERRW, DB_PASSWRW, DB_DBASE);
            if ($this->db === NULL || !$this->db) {
                // set response code
                $this->messager->databaseFailed();
            }
        }
   }

Alternatively will a Static variable be safer? As I can remove it in the Controller __destruct method.

    class Database {
        static $connect;

        protected static function conn() {
             self::$connect = new \mysqli(DB_HOST, DB_USERRW, DB_PASSWRW, DB_DBASE);
            return self::$connect;
        }
    }

    class ApiUserController extends Database {
        private $user_model;
        private $enterprise_model;
        public $connection;
        public function __construct($data){
            $this->connection =  parent::conn();
            //pass connection to models
            $this->user_model = new ApiUsers($this->connection);
            $this->enterprise_model = new ApiEnterprises($this->connection);
        }
    }

Upvotes: 0

Views: 61

Answers (1)

Dharman
Dharman

Reputation: 33238

What you need is IoC container, but before you get there you need to design your models in a such a way that they accept the database instance as a parameter in the constructor. This is called dependency injection. All dependant instances are injected into the new object at the time of instantiation.

Since your Database is useless I would not recommend to use it, but you should write some database abstraction library or use one that is already available on the web. e.g. EasyDB

Here is an example of a single dependency injection:

class ApiEnterprises {
    protected $db;
    protected $messager;

    private $table = 'enterprisetable';

    public function __construct(mysqli $db, Messager $messager) {
        $this->db = $db;
        $this->messager = $messager;
    }
}

// mysqli connection somewhere at the start of your application
mysqli_report(MYSQLI_REPORT_ERROR | MYSQLI_REPORT_STRICT);
$mysqli = new \mysqli(DB_HOST, DB_USERRW, DB_PASSWRW, DB_DBASE);
$mysqli->set_charset('utf8mb4'); // always set the charset

// instantiate the model and pass mysqli as an argument
$enterprise = new ApiEnterprises($mysqli, $messager);

Upvotes: 2

Related Questions