fetch() on a non-object - php

I keep getting the same error message...
Fatal error: Call to a member function fetch() on a non-object
I've tried:
- removing quotes from ':user' and ':pass'
- changing fetch() to fetchAll()
- using PDO::FETCH_ASSOC
I can't seem to find a question that solves this, they all are solid SQL statements, there's no variables inside them.
$q = $dbh->prepare("SELECT * FROM users WHERE username= ':user' AND password= ':pass' ");
$q -> bindParam(':user', $username);
$q -> bindParam(':pass', $password);
$result = $q -> execute();
$numrows = count($result);
echo $numrows;
if($numrows == 1){
while($row = $result->fetch(PDO::FETCH_OBJ)){
$row["id"] = $_SESSION["id"];
$row["username"] = $_SESSION["username"];
$row["password"] = $_SESSION["password"];
$row["email"] = $_SESSION["email"];
}
} else {
header("location: index.php?p=5");
}

Fetch should be used on the PDOstatement object.
According to the PDO manual:
PDOStatement::fetch — Fetches the next row from a result set
The fetch function is a member function of the PDOStatement object.
Example from the manual:
$sth = $dbh->prepare("SELECT name, colour FROM fruit");
$sth->execute(); //no need in another variable, like: $r = $sth->
/* Exercise PDOStatement::fetch styles */
$result = $sth->fetch(PDO::FETCH_ASSOC); //$sth, not "$r"
Another note:
Regarding your usage of execute, according to the manual it returns a boolean value (true/false) and not an array of values.
I believe you've used mySQL so the "migration" to PDO is a bit strange for you, look at the manual and follow some tutorials.

Remove quote from user and pass
$q = $dbh->prepare(" SELECT * FROM users WHERE username= :user AND password= :pass");

Related

PHP statement with mysqli_fetch_assoc not working [duplicate]

I'm currently working on a login script, and I got this code:
$selectUser = $db->prepare("SELECT `id`,`password`,`salt` FROM `users` WHERE `username`=?");
$selectUser->bind_param('s', $username);
$selectUser->execute();
if ($selectUser->num_rows() < 0)
echo "no_user";
else
{
$user = $selectUser->fetch_assoc();
echo $user['id'];
}
Here's the error I get:
Fatal error: Uncaught Error: Call to undefined method
mysqli_stmt::fetch_assoc()
I tried all sorts of variations, like:
$result = $selectUser->execute();
$user = $result->fetch_assoc();
and more... nothing worked.
That's because fetch_assoc is not part of a mysqli_stmt object. fetch_assoc belongs to the mysqli_result class. You can use mysqli_stmt::get_result to first get a result object and then call fetch_assoc:
$selectUser = $db->prepare("SELECT `id`,`password`,`salt` FROM `users` WHERE `username`=?");
$selectUser->bind_param('s', $username);
$selectUser->execute();
$result = $selectUser->get_result();
$assoc = $result->fetch_assoc();
Alternatively, you can use bind_result to bind the query's columns to variables and use fetch() instead:
$selectUser = $db->prepare("SELECT `id`,`password`,`salt` FROM `users` WHERE `username`=?");
$selectUser->bind_param('s', $username);
$selectUser->bind_result($id, $password, $salt);
$selectUser->execute();
while($selectUser->fetch())
{
//$id, $password and $salt contain the values you're looking for
}
1) you need the mysqlInd driver.
The variable $db is of type mysqli_stmt, not mysqli_result. The mysqli_stmt class doesn't have a method fetch_assoc() defined for it.
You can get a mysqli_result object from your mysqli_stmt object by calling its get_result() method. For this you need the mysqlInd driver installed!
Alternative try this
$selectUser = $db->prepare("SELECT `id`,`password`,`salt` FROM `users` WHERE `username`=?");
$selectUser->bind_param('s', $username);
$selectUser->execute();
$selectUser->bind_result($id, $password,$salt);
while ($selectUser->fetch()) {
printf("%s %s %s\n", $id, $password,$salt);
}
for more info about this Reference link
Now talk of alternatives.
PDO, unlike mysqli, never have a problem like this. It can fetch you an array out of a prepared statement without the need of installing any additional modules.
$stmt = $db->prepare("SELECT `id`,`password`,`salt` FROM `users` WHERE `username`=?");
$stmt->execute([$username]);
$user = $stmt->fetch();
if (!$user) {
echo "no_user";
} else {
echo $user['id'];
}
See, it works exactly the way you would expect and require two times less code to write. Not to mention other wonderful features.

Mysqli prepared statement get multiple rows from multiple columns on Count condition [duplicate]

I'm currently working on a login script, and I got this code:
$selectUser = $db->prepare("SELECT `id`,`password`,`salt` FROM `users` WHERE `username`=?");
$selectUser->bind_param('s', $username);
$selectUser->execute();
if ($selectUser->num_rows() < 0)
echo "no_user";
else
{
$user = $selectUser->fetch_assoc();
echo $user['id'];
}
Here's the error I get:
Fatal error: Uncaught Error: Call to undefined method
mysqli_stmt::fetch_assoc()
I tried all sorts of variations, like:
$result = $selectUser->execute();
$user = $result->fetch_assoc();
and more... nothing worked.
That's because fetch_assoc is not part of a mysqli_stmt object. fetch_assoc belongs to the mysqli_result class. You can use mysqli_stmt::get_result to first get a result object and then call fetch_assoc:
$selectUser = $db->prepare("SELECT `id`,`password`,`salt` FROM `users` WHERE `username`=?");
$selectUser->bind_param('s', $username);
$selectUser->execute();
$result = $selectUser->get_result();
$assoc = $result->fetch_assoc();
Alternatively, you can use bind_result to bind the query's columns to variables and use fetch() instead:
$selectUser = $db->prepare("SELECT `id`,`password`,`salt` FROM `users` WHERE `username`=?");
$selectUser->bind_param('s', $username);
$selectUser->bind_result($id, $password, $salt);
$selectUser->execute();
while($selectUser->fetch())
{
//$id, $password and $salt contain the values you're looking for
}
1) you need the mysqlInd driver.
The variable $db is of type mysqli_stmt, not mysqli_result. The mysqli_stmt class doesn't have a method fetch_assoc() defined for it.
You can get a mysqli_result object from your mysqli_stmt object by calling its get_result() method. For this you need the mysqlInd driver installed!
Alternative try this
$selectUser = $db->prepare("SELECT `id`,`password`,`salt` FROM `users` WHERE `username`=?");
$selectUser->bind_param('s', $username);
$selectUser->execute();
$selectUser->bind_result($id, $password,$salt);
while ($selectUser->fetch()) {
printf("%s %s %s\n", $id, $password,$salt);
}
for more info about this Reference link
Now talk of alternatives.
PDO, unlike mysqli, never have a problem like this. It can fetch you an array out of a prepared statement without the need of installing any additional modules.
$stmt = $db->prepare("SELECT `id`,`password`,`salt` FROM `users` WHERE `username`=?");
$stmt->execute([$username]);
$user = $stmt->fetch();
if (!$user) {
echo "no_user";
} else {
echo $user['id'];
}
See, it works exactly the way you would expect and require two times less code to write. Not to mention other wonderful features.

PDO method for mysql_fetch_assoc()?

I used to do :
$resource = mysql_query("SELECT * FROM table WHERE id = " . $id);
$user = mysql_fetch_assoc($resource);
echo "Hello User, your number is" . $user['number'];
I read that mysql statements are all deprecated and should not be used.
How can i do this with PDO?
The first line would be :
$stmt = $db->prepare("SELECT * FROM table WHERE id = " . $id); // there was an aditional double quote in here.
$stmt->execute(array(':id' => $id));
What about the mysql_fetch_assoc() function?
I am using php
You can use (PDO::FETCH_ASSOC) constant
Usage will be
while ($res = $stmt->fetch(PDO::FETCH_ASSOC)){
....
}
Here's the reference (documentation precisely) : http://www.php.net/manual/en/pdostatement.fetch.php
All well documentned in the manual: http://php.net/manual/en/pdostatement.fetchall.php
As example:
<?php
$sth = $dbh->prepare("SELECT name, colour FROM fruit");
$sth->execute();
/* Fetch all of the remaining rows in the result set */
print("Fetch all of the remaining rows in the result set:\n");
$result = $sth->fetchAll();
print_r($result);
?>
There is a nice manual right here.
From which you can learn what you don't need to set fetch mode explicitly with every fetch.
...and even what with PDO you don't need no arrays at all to echo a number:
$stmt = $db->prepare("SELECT number FROM table WHERE id = ?");
$stmt->execute(array($id));
echo "Hello User, your number is".$stmt->fetchColumn();
This is a nice tutorial:
http://wiki.hashphp.org/PDO_Tutorial_for_MySQL_Developers
<?php
$db = new PDO('mysql:host=localhost;dbname=testdb;charset=utf8', 'username', 'password');
$stmt = $db->query("SELECT * FROM table");
$results = $stmt->fetchAll(PDO::FETCH_ASSOC);
var_dump($results);
?>
You can use PDO::FETCH_ASSOC for the same.
$stmt = $db->prepare("SELECT * FROM table WHERE id = :id");
$stmt->execute(array(':id' => $id));
$stmt->setFetchMode(PDO::FETCH_ASSOC);
$stmt->execute();
while($record = $stmt->fetch()) {
//do something
}
You can find a good tutorial here

PHP PDO how do i include fetch assoc and numrows

trying to convert all my old mysql_* operations into new and, from what i've heard, improved PDO, but this query wont seem to run successfully, I am trying to select all from the table PEOPLE where the username = $username (which has previously been declared $username = $_SESSION['username'];)
$query = "SELECT * FROM people WHERE username=?";
$stmt = $conn->prepare($query);
$stmt->bindParam(1, $username);
$stmt->execute();
$num_rows = $stmt->fetchColumn();
if ($num_rows == 1) {
// ...
}
THE WORKING CODE IS:
$query = "SELECT * FROM people
WHERE username=?";
$stmt = $conn->prepare($query);
$stmt->bindParam(1, $username);
$stmt->execute();
$num_rows = $stmt->fetchColumn();
$user = $stmt->fetchObject();
if ($user) {
//do something
}
$stmt->fetchColumn does not fetch the number of rows; in this case it will fetch the first column from the first row of the result set. Since that will not be equal to 1 generally your test will fail.
In this case there is also no real need to count the number of returned rows because you are expecting either one or zero (if the username does not exist). So you can simply do:
$stmt->execute();
$user = $stmt->fetchObject();
if (!$user) {
// not found
}
else {
echo "User $user->username found!";
}
The if(!$user) test works because if there is no row to fetch $user will be false (see the documentation for fetchObject).
$query = "SELECT * FROM people WHERE username = :username";
$stmt = $conn->prepare($query);
$stmt->bindParam(':username', $username);
$stmt->execute();
while ($row = $stmt->fetchObject()) {
// do stuff
}
Use PDOStatement::rowCount as the num_rows and PDOStatement::fetch(PDO::FETCH_ASSOC) as fetch_assoc equivalent.
You want
if ($stmt->num_rows == 1) {
instead.

How to remove the fatal error when fetching an assoc array

I am receiving a fatal error in my php/mysqli code which states that on line 46:
Fatal error: Call to undefined method mysqli_stmt::fetch_assoc() in ...
I just want to know how can I remove this fatal error?
The line of code it is pointing at is here:
$row = $stmt->fetch_assoc();
ORIGINAL CODE:
$query = "SELECT Username, Email FROM User WHERE User = ?";
// prepare query
$stmt=$mysqli->prepare($query);
// You only need to call bind_param once
$stmt->bind_param("s",$user);
// execute query
$stmt->execute();
// get result and assign variables (prefix with db)
$stmt->bind_result($dbUser, $dbEmail);
//get number of rows
$stmt->store_result();
$numrows = $stmt->num_rows();
if ($numrows == 1){
$row = $stmt->fetch_assoc();
$dbemail = $row['Email'];
}
UPDATED CODE:
$query = "SELECT Username, Email FROM User WHERE User = ?";
// prepare query
$stmt=$mysqli->prepare($query);
// You only need to call bind_param once
$stmt->bind_param("s",$user);
// execute query
$stmt->execute();
// get result and assign variables (prefix with db)
$stmt->bind_result($dbUser, $dbEmail);
//get number of rows
$stmt->store_result();
$numrows = $stmt->num_rows();
if ($numrows == 1){
$row = $stmt->fetch_assoc();
$dbemail = $row['Email'];
}
The variable $stmt is of type mysqli_stmt, not mysqli_result. The mysqli_stmt class doesn't have a method "fetch_assoc()" defined for it.
You can get a mysqli_result object from your mysqli_stmt object by calling its get_result() method. For this you need the mysqlInd driver installed!
$result = $stmt->get_result();
row = $result->fetch_assoc();
If you don't have the driver installed you can fetch your results like this:
$stmt->bind_result($dbUser, $dbEmail);
while ($stmt->fetch()) {
printf("%s %s\n", $dbUser, $dbEmail);
}
So your code should become:
$query = "SELECT Username, Email FROM User WHERE User = ?";
// prepare query
$stmt=$mysqli->prepare($query);
// You only need to call bind_param once
$stmt->bind_param("s",$user);
// execute query
$stmt->execute();
// bind variables to result
$stmt->bind_result($dbUser, $dbEmail);
//fetch the first result row, this pumps the result values in the bound variables
if($stmt->fetch()){
echo 'result is ' . dbEmail;
}
Change,
$stmt->store_result();
to
$result = $stmt->store_result();
And
Change,
$row = $stmt->fetch_assoc();
to
$row = $result->fetch_assoc();
You have missed this step
$stmt = $mysqli->prepare("SELECT id, label FROM test WHERE id = 1");
$stmt->execute();
$res = $stmt->get_result(); // you have missed this step
$row = $res->fetch_assoc();
I realized that this code was provided as an answer somewhere on stackoverflow:
//get number of rows
$stmt->store_result();
$numrows = $stmt->num_rows();
I tried it to get the number of rows but realized that i didnt need the line $stmt->store_result();, and it didn't get me my number. I used this:
$result = $stmt->get_result();
$num_of_rows = $result->num_rows;
......
$row = $result->fetch_assoc();
$sample = $row['sample'];
It's best to use mysqlnd as Asciiom pointed out. But if you're in a weird situation where you are not allowed to install mysqlnd, it is still possible to get your data into an associative array without it. Try using the code in this answer
Mysqli - Bind results to an Array

Categories