Reputation: 23
Good afternoon. I'm starting using the PDO yesterday, and I have some problem with this. I was creating extendet class, which doesn't work and I can't find the bug.
This is code of my helper class, for work witch PDO:
class EPDO extends PDO {
/** Some identificator of connection*/
public $db;
/**
* Creating new PDO connections
*/
public function __construct($dbhost, $dbname, $dbuser = 'root', $dbpass = '', $dbtype = 'mysql') {
$db = new PDO($dbtype . ':host=' . $dbhost . ';dbname=' . $dbname, $dbuser, $dbpass);
}
/**
* Insert into database with using transaction (if operation failed the changes go before)
*/
public function insert($statement) {
$db->beginTransaction();
$status = $db->exec($statement);
if ($status) {
$db->commit();
} else {
$db->rollback();
}
}
}
And this is the unfunctional code:
$stm = $db->prepare('SELECT id FROM `startups` WHERE id = :id');
$params = array(':id' => $child->id);
$ok = $stm->execute($params);
$row = $stm->fetch(PDO::FETCH_ASSOC);
Before this code I of course call the connections following way:
require_once 'EPDO.php';
try {
$db = new EPDO('--server--', '--database--', '--user--', '--pass--');
}
catch (PDOException $err) {
echo "Chyba spojeni: " . $err->getMessage();
}
Thank you very much, and sorry for my english.
Upvotes: 2
Views: 10441
Reputation: 32290
All these long answers, when the solution is so simple:
You have to use
$this->db = new PDO(...
instead of
$db = new PDO(...
Because when you hit
$db->commit();
$db
is empty = constructor not called.
The error message should be something like undefined method commit() on non-object
.
You also have to use
$this->db->commit();
Use $this
on every member and method accessed from inside the class
and so on...
Upvotes: 1
Reputation: 589
The problem is that you're extending the PDO
class and overriding the constructor, all without calling the constructor.
Additionally, you're essentially creating two database connections every time you create a new object.
This should help resolve your issue, and reduce the connections created:
class EPDO extends PDO {
/** Some identificator of connection*/
public $db;
/**
* Creating new PDO connections
*/
public function __construct($dbhost, $dbname, $dbuser = 'root', $dbpass = '', $dbtype = 'mysql') {
parent::__construct($dbtype . ':host=' . $dbhost . ';dbname=' . $dbname, $dbuser, $dbpass);
}
/**
* Insert into database with using transaction (if operation failed the changes go before)
*/
public function insert($statement) {
$this->beginTransaction();
$status = $this->exec($statement);
if ($status) {
$this->commit();
} else {
$this->rollback();
}
}
}
Upvotes: 8
Reputation: 33511
Two problems: your design is wrong. You extend PDO, yet you create a new member object $db
of type PDO inside. That won't work as you intend it. You'll have to call its super constructor.
public function __construct($dbhost, $dbname, $dbuser = 'root', $dbpass = '', $dbtype = 'mysql') {
parent::__construct($dbtype . ':host=' . $dbhost . ';dbname=' . $dbname, $dbuser, $dbpass);
}
In fact, this constructor isn't needed at all, you are just changing the parameters, creating confusion. So you can easily remove it, together with the $db
attribute.
Second, to refer to class members and methods, use $this
in PHP:
public function insert($statement) {
$this->beginTransaction();
$status = $this->exec($statement);
if ($status) {
$this->commit();
} else {
$this->rollback();
}
}
Upvotes: 4