Reputation: 3298
I have an application that reads in one of its classes:
public function __construct()
{
global $config;
//Establish a connection to the database and get results set
$this->db = new Database("localhost",$config["dbuser"],$config["dbpass"],"student");
$this->records = $this->db->query("SELECT * FROM major") or die("ERROR: ".$this->db->error);
echo "<pre>".var_dump($this->records)."</pre>";
}
My problem is that var_dump shows
that $this->records
is a boolean. I've read the documentation and see that the SELECT query should return a result set. This is the only query used by the application.
The DB Class:
class Database
{
private $con;
public function __construct($server,$user,$password,$database)
{
$this->con = new mysqli($server,$user,$password,$database) or die ("FATAL ERR: ".mysqli_error());
}
public function query($qry)
{
if(!isset($this->con)) die("ERROR: YOU ARE TRYING TO QUERY BEFORE THE CONNECTION IS ESTABLISHED!");
return $this->con->query($qry) or die("FATAL ERROR:".$this->con->error);
}
}
Any ideas where I am going wrong?
Upvotes: 0
Views: 1984
Reputation: 157870
The issue in this question is not related to mysqli_query()
function, but to the operator precedence.
There, the =
operator has a higher precedence over OR
operator, means assignment will be executed before OR
(I explained this behavior in detail in the other answer, mysqli or die, does it have to die? )
The problem line is
return $this->con->query($qry) or die("FATAL ERROR:".$this->con->error);
Here, return
operator has (for the obvious reason) the lowest precedence possible. Means that first PHP will execute the logical operator and then return its result - a boolean value!
But why doesn't the script actually die due to the logical operator execution?
Because of that logical operator execution optimization explained in the answer by the link above. PHP doesn't bother to actually execute the rightmost operator. It's enough that the leftmost one is already evaluates to true
, means the whole expression will return true
either way.
To solve this problem, the code of the function have to be changed this way:
public function query($qry)
{
$ret = $this->con->query($qry) or trigger_error($this->con->error);
return $ret;
}
while the calling code should be changed to simple
$this->records = $this->db->query("SELECT * FROM major");
echo "<pre>".var_dump($this->records)."</pre>";
call, as checking for the error for the second time makes no sense - this function will never return a false
-like value.
Upvotes: 0
Reputation: 660
The answer would be in what is called Magic Methods. One of PHP's magic methods is called __debugInfo(). If this Magic Method is defined, when you call var_dumb(obj), it will output whatever the function says to output. This is normally done to hide the private and protected functions of a parent class.
Upvotes: -1
Reputation: 346
That is incorrect. The assignment operator (=
) has a higher precedence than the literal "or" operator. (Not to be confused with the "||
" operator, which has a higher precedence than "=
".)
There seems to be a bug in mysqli::query()
, that causes it to return the boolean "true" in rare cases on a select statement. (Legal return values would be the boolean "false" or a mysqli_result
object.)
You don't have to believe me on that assertion, you can easily try it yourself in a PHP shell:
$a = false or true;
var_dump($a);
Result:
bool (false)
That is because the above assignment is equivalent to:
($a = false) or true;
Upvotes: 3