Mysqli database connection issue - php

I am currently using mysqli to crate a connection to my database. My host server doesnt support PDO connections so that is why I am using mysqli. When making the connection I am getting this error:
Fatal error: Call to undefined method mysqli_result::fetchAll()
Is fetchAll() not part of mysqli?
PHP Connect to DB
$mysqli = new mysqli('localhost', 'user', 'password', 'database');
if (mysqli_connect_error()) {
die('Connect Error (' . mysqli_connect_errno() . ') '
. mysqli_connect_error());
}
else {
echo ('Success... ');
}
$sql = "SELECT *
FROM `categories`
WHERE `master` = 0";
$statement = $mysqli->query($sql);
$list = $statement->fetchAll();

No: it's fetch_all(), not fetchAll().

When you call $mysqli->query($sql), this can return a mysqli_result object, or the value false in case of an error. I think that your query is not successful, and returns the value false, and of course if you ask for false->fetchAll() this will give an error message.
So you have to check first, if the query was successful (use the === operator and check for false), and afterwards you can work with the result of the query.
P.S. That's why i never write functions myself, with mixed typed return values...

According to the documentation it is only available with the mysqlnd However the first comment on the mysql fetch all page describes how you can create a function that does the same thing.
http://php.net/manual/en/mysqli-result.fetch-all.php
Also it's fetch_all not fetchAll

You probably want fetch_all(), instead of fetchAll().
mysqli_result::fetch_all();
PDO::fetchAll();
Manual Entry

Related

sqlsrv_fetch_array() expects parameter 1 to be resource, boolean given in

im trying print records from my db (IIS, MSSQL PHP) but i have this error...
Warning: sqlsrv_fetch_array() expects parameter 1 to be resource, boolean given in
<?php
$serverName ="name\SQLEXPRESS";
$usr="sa";
$pwd="pasw";
$db="dbname";
$connectionInfo = array("UID" => $usr, "PWD" => $pwd, "Database" => $db);
$conn = sqlsrv_connect($serverName, $connectionInfo);
$sql = "SELECT first_col, s_col, t_col, FROM names ";
$res = sqlsrv_query($conn,$sql);
while ($row = sqlsrv_fetch_array($res)) {
print(
$row['first_col'].",".$row['s_col'].",".$row['t_col'].");
}
sqlsrv_close( $conn);
?>
Your query failed. This causes sqlsrv_query() to return false.
Your error in your query is an errant comma:
$sql = "SELECT first_col, s_col, t_col, FROM names ";
^^^^
HERE
Remove it and your query should work.
FYI, you don't check for errors in your code. You should always check to see if something failed, and if so, get the error message. You would have caught this quickly if you did.
The accepted answer is too localized and of no help for most users coming from Google, who need rather a generic answer, what to do when one gets such error in general.
This error message doesn't have any particular meaning, it's just a symptom telling us that the query execution failed. While we need to get the actual error message from SQL server. Hence every query should be executed in PHP like this:
$sql = "SELECT first_col, s_col, t_col, FROM names";
$stmt = sqlsrv_query($conn, $sql);
if($stmt === false) {
trigger_error(print_r(sqlsrv_errors(), true), E_USER_ERROR);
}
What is going on here?
first, we are checking the query result, if case it's equal to false, which means the query failed
if so, we are calling sqlsrv_errors() which returns an array with all errors returned by SQL server
then we are converting this array to string using print_r()
and finally, throwing a conventional PHP error that could be handled the same way as any other error
In the end, a failed query will throw a PHP error that explains the reason, so one can read the SQL server error message and then fix it right away or Google this message to get the explanation/practical suggestions for their particular error
If you use Stored Procedure with SQL SERVE, you must use EXEC, in your code you used CALL
$check = sqlsrv_query($conn, "{CALL Mem_Users_Accede (?,?,?,?)}", $data);

PDO::exec() blocking further query from working

I'm trying to implement pagination using PHP. I found that calling exec to the connected database prevents the further query calls from working.
The piece of code at hand:
<?php
// Pagination logic
//Here we count the number of results
$query = "SELECT COUNT(*) as num FROM gig";
$total_pages = $db->exec($query);
$total_pages = $total_pages[num];
?>
After it if I try to use a query such as:
<?php>
foreach ($db->query("SELECT sname, start, venue FROM gig WHERE start = '0000-00-00 00:00:00'") as $a) {
$row="<tr><td>$a[sname]</td><td>To be announced</td><td>$a[venue]</td></tr>\n";
print $row;
}
?>
it returns
Warning: Invalid argument supplied for foreach()
As soon as the first code block is removed, the query works fine. When I check the value of $total_pages, it's 0, so something must be going wrong along the way. As far as I know, I use it in the same way as the query(which works on its own), so is there any reason why it doesn't work?
The PDO is initialized in the following way:
try {
$db = new PDO("mysql:dbname=$db_name;host=$db_server", $db_user, $db_pw);
} catch (PDOException $e) {
die('Connection failed: ' . $e->getMessage());
}
session_start();
From Manual
PDO::exec() does not return results from a SELECT statement. For a
SELECT statement that you only need to issue once during your program,
consider issuing PDO::query(). For a statement that you need to issue
multiple times, prepare a PDOStatement object with PDO::prepare() and
issue the statement with PDOStatement::execute().
Used a function of the STATEMENT object had after using querying to count the rows instead of exec:
$dbq = $db->query("SELECT * FROM gig");
$rows = $dbq->rowCount();
About the latter code block not working because of the exec failing - it seems to just be the way php queries work, if one fails, all fail. The foreach() error is for the object it's provided is not an array, for it failed.

Do unbuffered queries for one request

I'm looking to do unbuffered queries only on some requests.
In MySQL I was doing this:
$req = mysql_unbuffered_query('SELECT * FROM forum_topics
ORDER BY (topic_id/topic_stick) DESC, topic_last_post DESC');
while($data = mysql_fetch_assoc($req)) {
// display results...
}
I looked at PHP doc, and according to it in pdo we must proceed this way to do queries unbuffered:
$pdo = new PDO("mysql:host=localhost;dbname=world", 'my_user', 'my_pass');
$pdo->setAttribute(PDO::MYSQL_ATTR_USE_BUFFERED_QUERY, false);
$uresult = $pdo->query("SELECT Name FROM City");
if ($uresult) {
while ($row = $uresult->fetch(PDO::FETCH_ASSOC)) {
echo $row['Name'] . PHP_EOL;
}
}
But is it possible to do it unbuffered only for the "forum_topics" table results without setting all pdo instance to unbuffered?
Re, this doesn't work, I obtain an error while using your method:
SQLSTATE[IM001]: Driver does not support this function: This driver doesn't support setting attributes
What's wrong?
Edit : I found the solution on php.net doc.
If you use this:
$sth->setAttribute(PDO::MYSQL_ATTR_USE_BUFFERED_QUERY, false);
It doesn't work.
But if you set it in an array in prepare(), it works fine.
$sth = $pdo->prepare('SELECT * FROM my_table',
array(PDO::MYSQL_ATTR_USE_BUFFERED_QUERY => false));
I hope this will help people who haven't found a way for this problem.
You can set the attribute on the PDO connection:
$pdo->setAttribute(PDO::MYSQL_ATTR_USE_BUFFERED_QUERY, false);
then run this particular query which result needs to be unbuffered,
$uresult = $pdo->query("SELECT Name FROM City");
while ($row = $uresult->fetch(PDO::FETCH_ASSOC)) {
echo $row['Name'] . PHP_EOL;
}
and then set the attribute back
$pdo->setAttribute(PDO::MYSQL_ATTR_USE_BUFFERED_QUERY, true);
The answers on here are all trying to use MYSQL_ATTR_USE_BUFFERED_QUERY on the statment. and MYSQL_ATTR_USE_BUFFERED_QUERY only operates on the entire connection, as you seem to have sussed out.
MYSQL_ATTR_USE_BUFFERED_QUERY also only works if you're using the mysqlnd library - which odds are good you are if you're using PHP 7 or higher.
Your original method of setting the connection as unbuffered was the correct and only actually functional method.
$pdo->setAttribute(PDO::MYSQL_ATTR_USE_BUFFERED_QUERY, false);
But is it possible to do it unbuffered only for the "forum_topics" table results without setting all pdo instance to unbuffered?
Not all instances are set to unbuffered, only that "instance" of that connection. You can either simply immediately turn buffering back on ala:
$pdo->setAttribute(PDO::MYSQL_ATTR_USE_BUFFERED_QUERY, true);
The problem is that you can only iterate a single query per connection when in unbuffered mode, so you cannot run a second query until you have retrieved all data from the first set.
Normally you only want to use unbuffered queries for very large datasets. I would recommend to use a second PDO connection to the database specifically for unbuffered queries that you open only when you need to run an unbuffered query, aka:
$pdo2 = new PDO("mysql:host=localhost;dbname=world", 'my_user', 'my_pass');
$pdo2->setAttribute(PDO::MYSQL_ATTR_USE_BUFFERED_QUERY, true);
MySQL does not implement statement-level attribute setting.
Source:
Here is your error message:
https://github.com/php/php-src/blob/master/ext/pdo/pdo_stmt.c#L1630
pdo_raise_impl_error(stmt->dbh, stmt, "IM001", "This driver doesn't support setting attributes");
And the condition above is checked on the stmt->methods->set_attribute above.
The stmt->methods is defined above and the type is declared at:
https://github.com/php/php-src/blob/5d6e923d46a89fe9cd8fb6c3a6da675aa67197b4/ext/pdo/php_pdo_driver.h#L417
struct pdo_stmt_methods
The set_attribute parameter is the 10th struct entry.
Here is the MySQL PDO implementation. And the statements methods are defined here:
https://github.com/php/php-src/blob/2ba4fb126391c578d20d859c841c4d31cd14adef/ext/pdo_mysql/mysql_statement.c#L935
NULL, /* set_attr */
This shows that the MySQL PDO module does implement that feature.
Discussion:
I have reviewed other extensions. And only the Firebird PDO database module supports that feature.
As an workaround if my query is a SELECT, I don't call the fetchAll function.
$query = 'SELECT ...... ';
$arr = explode(' ', $query);
$query_type = strtolower($arr[0]);
if ($query_type == 'select') {
$query_response = $query_prepare->fetchAll(PDO::FETCH_ASSOC);
} else {
$query_response = '';
}
Also you must treat the exception when you accidentaly put a space at the begining of the query.
Hope this is helpful.

Why is $rs->RowCount not returning a value?

I'm using a basic SQL query with ADO and PHP but the row count always returns -1. What am I missing?
Here is my code:
include 'constants.php';
// Create an instance of the ADO connection object
$conn = new COM ("ADODB.Connection")
or die("Cannot start ADO");
// Open the connection to the database
$conn->open(DB_CONN_STR);
$query = "select * from table_name";
$rs = $conn->execute($query);
if (!$rs) {
return;
}
else {
return $rs->RecordCount();
}
I know this table has values...what am I missing?
The manual says why.
http://phplens.com/lens/adodb/docs-adodb.htm#recordcount
seems you have set
$ADODB_COUNTRECS = false
I had a similar problem using Adodb with PHP, with a PDO mssql driver.
I executed a SQL query with GetOne or LimitQuery in a try / catch block
the query resulted in an error
i caught the exception and went on to execute a valid query with Execute
the resulting calls to RecordCount would wrongly return -1 (but i could iterate on the rows).
I found out that some Adodb functions set that $ADODB_COUNTRECS flag to false before executing their query. In case of an error the flag was not set back to true, and that is why RecordCount returned -1.
I set the global variable to true in my exception constructor and that solved the problem.

PDO query problem

I am updating some code from the old mysql_* functions to PDO. It connects without a problem, runs the query without a problem, but the resultset is empty. PDO::query() is supposed to return a PDOStatement object, yet I am getting true in return. No errors are reported.
Here is my code:
try
{
$DB = new PDO("mysql:host=localhost;dbname=dbname", "user", "pass");
$stmt = $DB->prepare("SELECT * FROM report_clientinfo");
$stmt->execute();
}catch(PDOException $e)
{
echo $e->getMessage() . "\n";
}
echo gettype($stmt) . "\n";
if ($stmt) echo "true\n";
else echo "false\n";
$resultset = $stmt->fetchAll();
if(empty($resultset))
{
exit("ERROR: getClientInfo query failed.");
}
$DB = null;
print_r($resultset);
The output I am seeing is:
object
true
ERROR: getClientInfo query failed.
Any ideas why it is not returning any results?
object
true
ERROR: getClientInfo query failed.
It looks to me like your PDOStatement $stmt variable is in fact reported to be an object, not "true". The code then prints "true" when it sees that $stmt is non-null, which it is, because it's an object.
I recommend that you check the return value from $stmt->execute(). You might have an SQL error. For example, if you misspelled the table name, or the table doesn't exist in the database "dbname" that you connected to, or the user you login as doesn't have privilege to query that table.
Also check $stmt->errorInfo() to get more details on any error that occurred.
I'm a little embarrassed to report back that I was pointing to the wrong DSN. I guess that's what I get for trying to learn something new on just a few hours of sleep after going out for New Year's Eve. Thanks for the tip on the PDOStatement::errorInfo() method, I had not noticed it before.

Categories