2

My limited PHP knowledge is rather old. When I used to create websites I always had a config.php file which contained some defines and a $_DB global variable. Then in every function_xyz.php file I included this config file.

Now I want to finally move on and use classes. But I can't figure out a proper way to have access to mysql in functions of my classes without inclusion of the so called config.php file on top of each file.

Imagine I have a class called User.php:

class User {

private $firstName;
private $familyName;
private $emailAddress;


public function __construct($username, $password) {
    //check if user with name and pass exist in DB
    // stuff....


    //If user exist, populate member variables
    $this->emailAddress = ...

}

public function getEmail(){
    return $this->emailAddress;
}
}

I know it is not the best example or practice...but how can I have a global MySQL access in all my classes without being required to have the config file included.

What is the best practice nowadays?

3
  • 10
    Best practice is dependency injection Commented Apr 16, 2015 at 20:19
  • If you're trying to go without a framework, you should make a Database class that you can call to to make connections with different users: $db = new Database('myuser'); or $this->db = Database::connect('myuser'); which can return a connection for you to use. You can make it part of the constructor: new User(Database::connect('myuser')) and that, as I understand, would be dependency injection such as Machavity indicated. Commented Apr 16, 2015 at 20:20
  • @ceejayoz Why is that the best practice then? .. Commented Apr 16, 2015 at 20:21

2 Answers 2

1

Make a global Instance:

//db.php include once 
class DB {
  #bind connenction in it
}
#make instance
$db = new DB($config);#use for User Instances

and then:

class User {

private $db;
private $firstName;
private $familyName;
private $emailAddress;

public function __construct($db) {
    $this->db=$db;
}

public function validate($username, $password,$db) {
    //check if user with name and pass exist in DB

    //If user exist, populate member variables
    $this->emailAddress = ...

}

public function getEmail(){
    return $this->emailAddress;
}
}
$user = new User($db);

Is one way. But you telling to less about how you want to use the classes.

Sign up to request clarification or add additional context in comments.

5 Comments

this is not really prettier than having require("../config.php")
It's the way to go though.. Another option would be to use a singleton pattern to retrieve the connection instead of DI
'telling to less about how you want to use the classes' does he use only inde.php since he use classes? autoloader? auto.prepend? include what where ?
What has autoloading to do with passing around an instance/connection?
'without being required to have the config file included' *autoloader maybe include DB class and if A auto.prepend is used and does $_DB, there will be an include of config.php once(if there and array is create....) - simple question - simple commment ;) what was the best way to rome ...
1

I would go with PHPAcademy's login/register tutorial. He have DB class that handles almost anything you need. Here is sample of his code, slightly modified by me, but all credits to Alex Garrett.

<?php

class DB {
    private static $_instance = null;
    private $_pdo,
            $_query, 
            $_error = false,
            $_results,
            $_count = 0;

    private function __construct() {
        try {
            $this->_pdo = new PDO('mysql:host=' . Config::get('mysql/host') . ';dbname=' . Config::get('mysql/db'), Config::get('mysql/username'), Config::get('mysql/password'));
        } catch(PDOException $e) {
            die($e->getMessage());
        }
    }

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

    public function query($sql, $params = array()) {
        $this->_error = false;
        if($this->_query = $this->_pdo->prepare($sql)) {
            $x = 1;
            if(count($params)) {
                foreach($params as $param) {
                    if (is_int($param)) {
                        $this->_query->bindValue($x, $param, PDO::PARAM_INT);
                    } else {
                        $this->_query->bindValue($x, $param);
                    }

                    $x++;
                }
            }



            if($this->_query->execute()) {
                $this->_results = $this->_query->fetchAll(PDO::FETCH_OBJ);
                $this->_count = $this->_query->rowCount();
            }
            else {
                $this->_error = true;
                print_r($this->_query->errorInfo());
            }
        }

        return $this;
    }

    public function action($action, $table, $where = array()) {
        if(count($where) === 3){
            $operators = array('=', '>', '<', '>=', '<=', '!=');

            $field    = $where[0];
            $operator = $where[1];
            $value    = $where[2];

            if(in_array($operator, $operators)) {
                $sql = "{$action} FROM {$table} WHERE {$field} {$operator} ?";

                if(!$this->query($sql, array($value))->error()) {
                    return $this;
                }
            }
        } else if (count($where) === 0) {

            $sql       = "{$action} FROM {$table}";

            if(!$this->query($sql)->error()) {
                    return $this;
                }

        }



        return false;
    }

    public function get($table, $where) {
        return $this->action('SELECT *', $table, $where);
    }

    public function delete($table, $where) {
        return $this->action('DELETE', $table, $where);
    }

    public function getAll($table) {
        return $this->action('SELECT *', $table);
    }

    public function first() {
        return $this->results()[0];
    }

    public function last() {
        $i = count($this->results()) - 1;

        return $this->results()[$i];
    }

    public function insert($table, $fields = array()) {
        if(count($fields)) {
            $keys = array_keys($fields);
            $values = '';
            $x = 1;

            foreach ($fields as $field) {
                $values .= '?';
                if($x < count($fields)) {
                    $values .= ', ';
                }
                $x++;
            }

            $sql = "INSERT INTO {$table} (`"  . implode('` , `', $keys) . "`) VALUES({$values})";

            if (!$this->query($sql, $fields)->error()) {
                return true;
            }
        }

        return false;
    }

    public function update($table, $where, $parametar, $fields) {
        $set = '';
        $x = 1;

        foreach ($fields as $name => $value) {
            $set .= "{$name} = ?";
            if ($x < count($fields)) {
                $set .= ', ';
            }

            $x++;
        }
        if (is_int($parametar)) {
            $sql = "UPDATE {$table} SET {$set} WHERE {$where} = {$parametar}";
        } else {
            $sql = "UPDATE {$table} SET {$set} WHERE {$where} = '{$parametar}'";
        }

        if (!$this->query($sql, $fields)->error()) {
                return true;
            }

        return false;

    }

    public function results() {
        return $this->_results;
    }

    public function error() {
        return $this->_error;
    }

    public function count() {
        return $this->_count;
    }

}

Then you can query database like DB::getInstance()->getAll('tableName')->results();. Change DB credentials in __construct, or watch his videos (which I recomend).

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.