cannot get results from prepared statement's fetch() - php

This is my code
I tried replacing SELECT * with SELECT booktitle. If I do fetch(PDO::FETCH_BOTH) , that is the default, I get Warning: mysqli_stmt::fetch() expects exactly 0 parameters, 1 given in C:\Apache24\htdocs\phpprepared.php on line 89. I guess I dont have to bind_param, since there are no params here.
$query3 = 'SELECT * FROM books';
$stmt = $db->prepare($query3);
$stmt->execute();
while ($row = $stmt->fetch()) {
echo 'booktitle: '.$row['booktitle'].'<br>';
}
The problem
I get the booktitle string echoed 9 times, but no actual data. I am confused on how to use the fetch, the results and/or the associative (?) array so I can get the data. Thanks
Edit
Wondering if there is a way to simply get everything from a table without having to use bind_result or the combination get_result - fetch_assoc.
Thanks

Related

PHP bind_param not binding parameter [duplicate]

This question already has answers here:
MySQLI Prepared Statement: num_rows & fetch_assoc
(5 answers)
Closed 5 years ago.
I am trying to search a table for specific items using a prepared statement in PHP. I am getting no errors, but also getting no record. Here is my code:
$items = [];
$search = "john";
if ($stmt = $this->con->prepare("SELECT * FROM phptest WHERE search = ?")) { //'john'";
$stmt->bind_param("s",$search);
$stmt->execute();
while ($row = mysqli_fetch_array($stmt)) {
$item = [];
$item['id'] = $row['id'];
$item['first'] = $row['search'];
$item['last'] = $row['data'];
array_push($items, $item);
}
}
return $items;
Now, when I don't use a prepared statement, and just SELECT * FROM phptest I get all the results in the table (including the item where search = 'john'). Furthermore, if I use the query SELECT * FROM phptest WHERE search = 'john' I get the one record where search = 'john'
But as soon as I turn it into the prepared statement, I get zero errors but zero records. I do get a warning:
mysqli_fetch_array() expects parameter 1 to be mysqli_result, boolean given
Which made me think my bind_param or execute() was returning FALSE, but when I check, it does not appear to be returning false.
I started off my adventure working through the tutorial https://www.simplifiedcoding.net/android-mysql-tutorial-to-perform-basic-crud-operation/, which I thought I understood fully but ran into my error when trying to make my own PHP API.
I then went to the manual http://php.net/manual/fr/mysqli.prepare.php, but still cannot find my error.
Though it has been closed as "off-topic," I have reviewed PHP bind_param not working and found nothing applicable to my situation.
Likewise, I am not finding the error in PHP bind_param not defined nor php bind_param is not working.
You're very close. mysqli_fetch_array() expects to be passed a result object, not the statement object itself:
$stmt = $conn->prepare(...);
$stmt->bind_param(...);
$stmt->execute();
$result = $stmt->get_result();
while ($row = mysqli_fetch_array($result)) {
Or, in the fully OO manner:
while ($row = $result->fetch_array()) {

Getting elements of the array MySQLi + PHP

Trying to get array from using MySQLi and PHP, so that I could work with each element of the array (like $array[0], array[1])
$titlesquery = $db->prepare("SELECT title FROM books WHERE id = ?");
$titlesquery->bind_param('i', $id);
$titlesquery->execute();
$titlesquery->bind_result($returned_title);
$json = $titlesquery->fetch($returned_title, MYSQLI_ASSOC);
echo json_encode($json);
This doesn't work. I get such warning:
mysqli_stmt::fetch() expects exactly 0 parameters, 2 given
If it helps, just $titlesquery->fetch(); works fine but I get not a kind of array(?) structure, just single element for that column. What is my mistake?
Like what exactly says on the error message, it needs no parameters:
http://php.net/manual/en/mysqli-stmt.fetch.php
bool mysqli_stmt::fetch ( void )
$titlesquery->bind_result($returned_title);
$titlesquery->fetch();
$json = array('title' => $returned_title);
After you have invoked ->bind_result(), this already binds results from your prepared statement.
If you want an array row fetching and this is available to you (needs mysqlnd), use ->get_result() instead.
$titlesquery = $db->prepare("SELECT title FROM books WHERE id = ?");
$titlesquery->bind_param('i', $id);
$titlesquery->execute();
$result = $titlesquery->get_result();
$json = $result->fetch_assoc();
echo json_encode($json);

PHP PDO Select Query Results

This seems like it should be a very easy task, but I'm not sure it is.
I would like to use PDO to do a SELECT query, and then immediately after find out if there are any results (rows), and if so how many.
I'd like to fetch the result as an object not an array, as I like the $obj->col_name syntax, and it just feels a bit wrong to return an array just to find the above out.
$qryh = $conn->query("SELECT ...");
Then use $qryh to first find out if there are any rows, and if so how many.
Can this be done without falling back to using arrays..?
UPDATE:
I know about rowCount(), but I think it only works on UPDATE, INSERT and DELETE - my question relates to SELECT.
UPDATE 2:
I'm using SQL Server and MS Access, not MySQL, and rocount() does not work.
SOLUTION FOUND
The accepted answer lead to the solution. Here is what I found:
I was setting the PDO::ATTR_CURSOR option to PDO::CURSOR_SCROLL when creating the PDO object (new PDO(...), which returned -1 on a rowCount(). However if I set the cursor within ->prepare(... using an array (array(PDO::ATTR_CURSOR => PDO::CURSOR_SCROLL)) it works and returns the row count.
http://technet.microsoft.com/en-us/library/ff628154(v=sql.105).aspx
So, the example on the above link works, setting the cursor when you create the PDO object doesn't work. Also note that in the 'remarks' section on the above link, it mentions PDO::CURSOR_SCROLLABLE which doesn't for me (I get Undefined class constant 'CURSOR_SCROLLABLE').
Try this way:
$query = "select * from ...";
$stmt = $conn->prepare( $query, array(PDO::ATTR_CURSOR => PDO::CURSOR_SCROLL));
$stmt->execute();
print $stmt->rowCount()
Should work
$stmt = $conn->query('SELECT ...');
// number of rows:
$rows = $stmt->rowCount();
// get an array with objects:
$objects = $stmt->fetchAll();
// another way to count the results:
$rows = count($objects);
This is what I do in my database class:
$stmt = $conn->prepare('SELECT ...');
$stmt->execute();
$arrayOfObjects = $stmt->fetchALL(PDO::FETCH_OBJ);
$numberOfRows = count($arrayOfObjects);
print $numberOfRows;
By passing PDO::FETCH_OBJ each object is an stdClass meaning you can use the -> syntax.
I believe this is what you are looking for, and it just uses the PHP count() function instead of mySQL rowCount().
If you want more context, here is the DB class I use in all of my projects: https://gist.github.com/pxlsqre/9f6471220ef187343f54
You're right, PDO::rowCount does not work properly with SELECT
One workaround is to Add the count to your query
$qryh = $conn->query("SELECT COUNT(*) as numRows FROM Table");
$result = $qryh->(PDO::FETCH_OBJ);;
$count = $result->numRows;
$qryh->fetchColumn()
Returns the number of rows selected through a SELECT query

Prepared statements result in an error

I am very new to prepared statements.
This is my code:
<?php
$getImages=$db->prepare("SELECT * FROM header_image_arabic");
$getImages->bind_param('s', '$images');
$getImages->execute();
$getImages->bind_result($returned_images);
while($img=$returned_images->fetch_object()){
?>
This is the error:
Fatal error: Cannot pass parameter 2 by reference in C:\wamp\www\arabia\admin\includes\pan\imageHeader.php on line 22`
What does this error mean?
There are number of things wrong here.
'$images' is a string containing 7 characters. You want to pass the variable to bind_param, not a string.
$getImages->bind_param('s', $images);
Also, what exactly are you trying to bind to here? There are no placeholders (question marks) in your query. You can just use $db->query() here. You only need to "prepare" a query when you are filling in data.
$getImages = $db->query('SELECT * FROM header_image_arabic');
if($getImages === FALSE){
die($db->error);
}
while($img = $getImages->fetch_object()){
}
Another thing is the line: $getImages->bind_result($returned_images);. bind_result is used to bind to the fields in the query. You can't use that here, since you are doing SELECT *. (Also, fetch_object and bind_result cannot be used together. You need to use get_result (which only works with the mysqlnd driver) to be able to use fetch_object.)
So, if you wanted to use "prepared statements", it would look something like this:
$getImages = $db->prepare("SELECT image_id FROM header_image_arabic WHERE name = ?");
$getImages->bind_param('s', $images);
$getImages->execute();
$getImages->bind_result($returned_images);
while($getImages->fetch()){
// This will get updated each iteration
echo $returned_images;
}
Or like this (requires mysqlnd driver):
$getImages = $db->prepare("SELECT * FROM header_image_arabic WHERE name = ?");
$getImages->bind_param('s', $images);
$getImages->execute();
$result = $getImages->get_result();
while($img = $result->fetch_object()){
echo $img->image_id;
}

Why doesn't this prepare statement work in MYSQLI?

I created this code:
$statement = $db->prepare("SELECT * FROM phptech_contact");
$statement->execute();
$result = $statement->result_metadata();
$object = $result->fetch_object();
print_r( $object );
When I run it, it doesn't work. Can anybody tell me why it doesn't work?
I have 20 rows in this table so data should be returned.
From http://ch.php.net/manual/en/mysqli-stmt.result-metadata.php
Note: The result set returned by mysqli_stmt_result_metadata() contains only metadata. It does not contain any row results. The rows are obtained by using the statement handle with mysqli_stmt_fetch().
As long as you don't need this meta data you don't need to call this method.
$statement = $db->prepare("SELECT fld1, fld2 FROM phptech_contact");
$statement->execute();
$stmt->bind_result($fld1, $fld2);
while ($stmt->fetch()) {
echo "$fld1 and $fld2<br />";
}
But I really dislike the mysqli extension. PDO is much cooler ... ;-)
$db = new PDO('...');
$stmt = $db->prepare("SELECT fld1, fld2 FROM phptech_contact");
$stmt->execute();
while ($obj = $stmt->fetchObject()) {
// ...
}
or
$objs = stmt->fetchAll(PDO::FETCH_OBJ);
if you're trying to get the rows from the database, the function you need is mysqli_stmt::fetch(), not mysqli_stmt::fetch_metadata()
You're also missing a few steps. When using prepared statements, you must specify the fields you would like to return instead of using the star wildcard, and then use mysqli_stmt::bind_result() to specify which variables the database fields should be placed in.
If you're more familiar with the original MySQL extension, prepared statements have a different process to use. If your select statement has a parameter (eg., "WHERE value=?") prepared statements are definitely recommended, but for your simple query, mysqli:query() would be sufficient, and not very different from the process of mysql_query()
I believe the problem is that mysqli_stmt::result_metadata() returns a mysqli_result object without any of the actual results — it only holds metadata.
So what you want to do is use $result = $statement->bind_result(...) and then call $result->fetch() repeatedly to get the results.
One of the comments under the bind-result() article shows how to do this for a query like yours, where you don't necessarily know all of the columns being returned.

Categories