This question already has an answer here:
$stmt->num_rows returning 0 even after calling store_result
(1 answer)
Closed 9 years ago.
i am just trying to learn prepared statement and i am following the PHP manual to guide me through, i have checked the answers regarding this problem on stackoverflow but, i can't find any solutions, the $stmt->num_rows always ( Return 0 )
there is a post on stackoverflow discussed the problem and they advised to use
$stmt->store_result() just before the $stmt-num_rows, but the $stmt->num_rows return 0
some one please can tell me what i am doing wrong here.... i am just sick of the procedural style coding and i want to enhance my skills with prepared statement
here is the function down below
function get_all()
{
// ** Initializing the Connection
$mysqli = Connect();
$sql = ( ' SELECT * FROM `users` ' );
$stmt = $mysqli->prepare($sql);
$stmt->execute();
$res = $stmt->get_result();
echo $num_count = $stmt->num_rows();
$user = array();
for ($counter = 0; $row = $res->fetch_assoc(); $counter++)
{
$user[$counter] = $row;
}
return $user;
}
// This is the second update
function get_all()
{
// ** Initializing the Connection
$mysqli = Connect();
$sql = ( ' SELECT * FROM `users` ' );
$stmt = $mysqli->prepare($sql);
$stmt->execute();
$res = $stmt->get_result();
echo $num_count = $stmt->num_rows;
$user = array();
while($row = $res->fetch_assoc())
{
$user[] = $row;
}
return $user;
}
// third update
function get_alll()
{
// ** Initializing the Connection
$mysqli = Connect();
// no need to use * character,
// need to write query this way
$sql = ( ' SELECT `id`,`fname`,`lname`,`uname`,`email` FROM `users` ' );
$stmt = $mysqli->prepare($sql);
// here need to use bind param
$stmt->bind_result( $id, $fname, $lname, $uname, $email);
$stmt->execute();
// it's important to store the result
// before using num rows
$res = $stmt->store_result();
echo $num_count = $stmt->num_rows;
//
while($stmt->fetch())
{
echo $fname;
}
}
num_rows is a property, not a method, try with $stmt->num_rows without brackets
Related
I have been converting a small login script i did to PDO trying to give it a try.
Code mysqli
$stmt = $conn->prepare('SELECT id, name FROM users WHERE id = ?');
$stmt->bind_param('i', $id);
$stmt->execute();
$stmt->store_result();
$stmt->bind_result($id, $name);
if ($stmt->fetch()) {
$_SESSION['id'] = $id;
$_SESSION['name'] = $name;
$is_valid = true;
} else {
$is_valid = false;
self::logout();
}
I changed to PDO
$sql = "SELECT id, name FROM users WHERE id = :id";
$stmt = $conn->prepare($sql);
$stmt->bindParam(':id', $id);
$stmt->bindParam(':name', $name);
$stmt->execute();
if ($stmt->fetch())
{
$_SESSION['id'] = $id;
$_SESSION['name'] = $name;
$is_valid = true;
} else {
$is_valid = false;
self::logout();
}
in mysqli i was able to bind and store $id and $name but read those were not available in PDO
$stmt->store_result();
$stmt->bind_result($id, $name);
There's no equivalent of bind_result in PDO because you don't really need it. Just read the data from the row:
if ($row = $stmt->fetch(PDO::FETCH_ASSOC))
{
$_SESSION['id'] = $row["id"];
$_SESSION['name'] = $row["name"];
$is_valid = true;
}
You also don't need the $stmt->bindParam(':name', $name); line because there is no :name input parameter in your SQL.
More examples are available in the manual and elsewhere.
See also Is it possible to use store_result() and bind_result() with PHP PDO? for more useful background info.
The equivalent method is called bindColumn(). You can bind a variable to one column in the result set.
/* Bind by column number */
$stmt->bindColumn(1, $id);
$stmt->bindColumn(2, $name);
while ($stmt->fetch(PDO::FETCH_BOUND)) {
print $name . "\t" . $id. "\n";
}
However, I would recommend writing simpler code. PDO is designed to be easier to use.
If you want to make the code simpler, use arrays. The method fetch() returns an array with the current row. They are better when you need to fetch more than one column from the result. If you only need to fetch one column, use fetchColumn().
$sql = "SELECT id, name FROM users WHERE id = :id";
$stmt = $conn->prepare($sql);
$stmt->execute([
'id' => $id,
'name' => $name,
]);
if ($row = $stmt->fetch()) {
$_SESSION['id'] = $row['id'];
$_SESSION['name'] = $row['name'];
$is_valid = true;
} else {
$is_valid = false;
self::logout();
}
This question already has an answer here:
MySQL/PHP output array repeats the query and then shows result, how can I remove the query? [duplicate]
(1 answer)
Closed 3 years ago.
I am trying to let to check the a table if there exists a value and if there exists a value it should output as JSON "one" and if it doesn't exist it should output "two". My thought is that With my SELECT EXIST Statement it should only return a row if there exists the value in the table but for some reason it always outputs a row.
Here is the code:
// Create connection
$conn = new mysqli($servername, $username, $password, $dbname);
// Check connection
if ($conn->connect_error) {
die("Connection failed: " . $conn->connect_error);
}
if ($result = mysqli_query($conn, $query)) {
$newArr = array();
$value = mysqli_fetch_object($result);
$newArr[] = (bool) $value->item_exists;
echo json_encode($newArr); // get all products in json format.
}
*/
/* part where output is just 1 or 0*/
$query = "SELECT EXISTS(SELECT * FROM wp_woocommerce_order_items WHERE order_id = $sdata)";
$myArray = array();
if ($result = mysqli_query($conn, $query)) {
while($row = $result->fetch_row()) {
$myArray[] = $row;
}
// 2nd operation checkif order available
if ($conn->affected_rows == 1) {
echo json_encode($one);
} else {
//Success and return new id
echo json_encode($two);
}
//end 2nd operation
echo json_encode($myArray);
}$result->close();
echo json_encode($newArr); // get all products in json format.
}
$conn->close();
?>
Could you not simply try something like the following? Assign an alias to the result of the query so you can access it like you would for a regular column name, run the query and extract that pseudo-columnname from the recordset. This does, of course, ignore the sql vulnerability ( or potential vulnerability ) in the sql statement - a prepared statement would be a safer method to employ.
$query = "select exists( select * from `wp_woocommerce_order_items` where `order_id` = $sdata ) as `exists`";
$exists = false;
if( $result = mysqli_query( $conn, $query ) ) {
$row = $result->fetch_assoc();
$exists = intval( $row['exists'] );
}
$myArray = array( $exists ? 1 : 2 );
echo json_encode($myArray);
To do similar using a prepared statement you might consider something like this:
$exists = false;
$sql='select exists( select * from `wp_woocommerce_order_items` where `order_id` = ? ) as `exists`';
$stmt=$conn->prepare($sql);
if( $stmt ){
$stmt->bind_param( 'i', $sdata );
$res=$stmt->execute();
if( $res ){
$stmt->store_result();
$stmt->bind_result( $exists );
$stmt->fetch();
$stmt->free_result();
$stmt->close();
}
}
$myArray = array( $exists ? 1 : 2 );
echo json_encode( $myArray );
Please always use PDO or Prepared MySQLI to avoid SQL injections.
Someone could drop your tables or do other dangerous things that will ruin your data.
Refer to this example:
<?php
$conn = new PDO("mysql:host=$servername;dbname=$dbname", $username, $dbpassword);
$conn->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
$stmt = $conn->prepare("SELECT 1 FROM `wp_woocommerce_order_items WHERE order_id = :sdata");
$stmt->execute(['sdata' => $sdata]);
$result = $stmt->fetchColumn();
$exists = $result ? "one" : "two";
print_r($exists);
This method is part of a larger class, and am trying to get it to return an array of objects containing the same classes. However, it doesn't seem to be entering the while loop, and I can't figure out why. Any suggestions?
The expected result would be an array of objects containing this data http://sqlfiddle.com/#!9/b6e23/1.
public static function getAllFacts($groupID)
{
$factTable = array();
$conn = new mysqli($GLOBALS['hostName'], $GLOBALS['userName'], $GLOBALS['password'], $GLOBALS['database']);
if ($conn->connect_error)
{
echo "Database connection error (source table)<br>";
}
$query = "SELECT factID, sourceID, factTXT, citationID, noteGroupID, factCreated, factsGroupID FROM facts WHERE factsGroupID = ?";
$stmt = $conn->prepare($query);
if ($stmt)
{
$stmt->bind_param("i", $groupID);
$stmt->execute();
$stmt->store_result();
$stmt->bind_result(
$factID,
$sourceID,
$factTXT,
$citaitionID,
$noteGroupID,
$factCreated,
$factsGroupID
);
$row = 0;
while ($stmt->fetch())
{
$numRows = $stmt->num_rows;
echo "numRows: " . $numRows . "<br>";
$factTable[$row] = new self($factID, $sourceID, $factTxt, $citationTxt, $noteGroupID, $factCreated, $factsGroupID, $numRows);
$row++;
}
$stmt->close();
}
else
{
echo "Statement failed. (source table) <br>";
}
return $factTable;
}
I have this PHP function :
function userParent($Username)
{
global $con;
$Result = mysqli_query($con, "SELECT Username FROM Family WHERE Parent = '$Username' LIMIT 10");
$row = mysqli_fetch_assoc($Result);
return $row;
}
that function should give me 10 rows in array, but why I just have a value in array? I tried to test that codes outside function bracket and try to add WHILE loop like this :
while ($row = mysqli_fetch_assoc($Result)){
print_r($row);
}
and it works. I got my 10 rows in array format. but it prints the result to the screen. how to make it as variable so it can be returned in function?
thanks.
UPDATE : according to Phil's answer, now here's my complete code :
<?php
function userParent(mysqli $con, $username) {
$stmt = $con->prepare('SELECT Username FROM Family WHERE Parent = ? LIMIT 10');
$stmt->bind_param('s', $username);
$stmt->execute();
$res = $stmt->get_result();
return $res->fetch_all(MYSQLI_ASSOC);
}
$DbServer = 'localhost';
$DbUser = 'username';
$DbPassword = 'password';
$DbName = 'dbname';
$mysqli = new mysqli($DbServer, $DbUser, $DbPassword, $DbName);
$arrayParent = userParent($mysqli, 'root');
print_r($arrayParent);
?>
but I got this error message :
Fatal error: Call to undefined method mysqli_stmt::get_result() in /home/myhome/public_html/test.php on line 6
Use return:
function userParent(mysqli &$dbms, $username){
// You need to "escape" strings, which you would use in direct queries.
// OR BETTER: use mysqli prepared statements with parameter binding.
$username = mysqli_real_escape_string($dbms, $username);
$result = mysqli_query($dbms, "SELECT Username FROM Family WHERE Parent = '$username' LIMIT 10");
// Create temporary array for resultset:
$buffer = array();
// Fetch data to temporary buffer:
while ($row = mysqli_fetch_assoc($result)){
$buffer[] = $row;
}
// Free result set:
$result->free();
// Return buffer to global scope:
return $buffer;
}
$users = userParent($con, 'John');
var_dump($users);
Try mysqli_result::fetch_all instead
function userParent(mysqli $con, $username) {
$stmt = $con->prepare('SELECT Username FROM Family WHERE Parent = ? LIMIT 10');
if ($stmt === false) {
throw new Exception($con->error, $con->errno);
}
$stmt->bind_param('s', $username);
$stmt->execute();
$res = $stmt->get_result();
return $res->fetch_all(MYSQLI_ASSOC);
}
Then call it like this
$parents = userParent($mysqli, 'some username');
Read these in case you're not aware of prepared statements and parameter binding
http://www.php.net/manual/en/mysqli.prepare.php
http://www.php.net/manual/en/mysqli-stmt.bind-param.php
Update
Apparently (undocumented), the mysqli_stmt::get_result() method is only available when using the mysqlnd driver. If you cannot use this driver, try this alternative
function userParent(mysqli $con, $username) {
$stmt = $con->prepare('SELECT Username FROM Family WHERE Parent = ? LIMIT 10');
if ($stmt === false) {
throw new Exception($con->error, $con->errno);
}
$stmt->bind_param('s', $username);
$stmt->execute();
$parent = null;
$parents = array();
$stmt->bind_result($parent);
while($stmt->fetch()) {
$parents[] = $parent;
}
return $parents;
}
This question already has answers here:
Call to undefined method mysqli_stmt::get_result
(10 answers)
Closed 11 months ago.
I'm quite new to prepared statements and am not sure I am doing this right.
Here is what I try:
$currgame = 310791;
$sql = "SELECT fk_player_id, player_tiles, player_draws, player_turn, player_passes, swapped FROM ".$prefix."_gameplayer WHERE fk_game_id = ?";
$stmt = $mysqli->stmt_init();
$data = array();
if($stmt->prepare($sql)){
$stmt->bind_param('i', $currgame);
$stmt->execute();
$fk_player_id = null; $player_tiles = null; $player_draws = null; $player_turn = null; $player_passes = null; $swapped = null;
$stmt->bind_result($fk_player_id, $player_tiles, $player_draws, $player_turn, $player_passes, $swapped);
$res = $stmt->get_result();
while ($row = $res->fetch_assoc()){
$data[] = $row;
}
$stmt->close();
}
// to display own games
foreach ($data as $row) {
if ($row['fk_player_id'] == $playerid) {
$udraws = $row['player_draws']+1;
$upass = $row['player_passes'];
$uswaps = $row['swapped'];
echo 'uDraws: '.$udraws.'<br>';
echo 'uPass: '.$upass.'<br>';
echo 'uSwaps: '.$uswaps.'<br><br>';
}
}
// to display other games
foreach ($data as $row) {
if ($row['fk_player_id'] != $playerid) {
$opponent = $row['fk_player_id'];
$oppTiles = $row['player_tiles'];
$odraws = $row['player_draws']+1;
$opass = $row['player_passes'];
$oswaps = $row['swapped'];
echo 'oID: '.$opponent.'<br>';
echo 'oTiles: '.$oppTiles.'<br>';
echo 'oDraws: '.$odraws.'<br>';
echo 'oPass: '.$opass.'<br>';
echo 'oSwaps: '.$oswaps.'<br><br>';
}
}
I get an "ServerError" when trying to run this: It is the $res = $stmt->get_result(); that makes the error, but not sure why.
PHP Fatal error: Call to undefined method mysqli_stmt::get_result() in /home/mypage/public_html/TEST/preparedstatement.php on line 61
Depending on your PHP/MySQL setup you may not be able to use get_result().
The way to get around this is to bind the results.
For example:
$stmt->execute();
$fk_player_id = null; $player_tiles = null; $player_draws = null; $player_turn = null; $player_passes = null; $swapped = null;
$stmt->bind_result($fk_player_id, $player_tiles, $player_draws, $player_turn, $player_passes, $swapped);
while ($stmt->fetch()) { // For each row
/* You can then use the variables declared above, which will have the
new values from the query every time $stmt->execute() is ran.*/
}
For more information click here
Since I don't see it in your code, make sure you're instantiating the mysqli object before trying to query on it:
$mysqli = new mysqli("127.0.0.1", "user", "password", "mydb");
if($mysqli->connect_error){
die("$mysqli->connect_errno: $mysqli->connect_error");
}
Also, a ServerError would certainly show up in your logs and point you in the right direction.
while (mysqli_stmt_fetch($stmt)) {
printf ("%s (%s)\n", $name, $code);
}
This might help you:
http://php.net/manual/en/mysqli-stmt.fetch.php