This question already has answers here:
Use an array in a mysqli prepared statement: `WHERE .. IN(..)` query [duplicate]
(8 answers)
How can I bind an array of strings with a mysqli prepared statement?
(7 answers)
Closed 11 months ago.
I have a select where I need to scan a table to get results:
where (p.user in (select f from fl where user =? and block=0))
This table is a big table with more than 1 million rows. And it is taking a while to read. I need to read it all the time, so I was thinking I could read it once and then just use:
where (p.user in ($variable_with_all_results))
I tried:
$stmt = $mysqli->prepare("select f from f1 where user = '1' and block = 0");
$stmt->execute();
$stmt->bind_result($variable_with_all_results);
But I cannot use this variable on the select, the mysql is not recognizing it. Any ideas?
You should be able to do what you want like this:
$stmt = $mysqli->prepare("select GROUP_CONCAT(f) from f1 where user = '1' and block = 0");
$stmt->execute();
$stmt->bind_result($variable_with_all_results);
$stmt->fetch();
Note you need to add a GROUP_CONCAT aggregation function around f in the query, this will give you a list like 1,5,6. Also you need to do a fetch on the statement to get the result into your variable.
Then you should be able to make a new query like this:
$sql = "SELECT ...
WHERE p.user in ($variable_with_all_results)";
bind_result wont work in that way, you should use bind_param().
But using IN (?) won`t do.
You will need to bind each id separately, some think like this:
$stmt->bind_param("select f from f1 where (p.user in (select f from fl where user = IN (?,?,?,?,?) and block=0))", $id1, $id2,$id3, $id4, $id5);
This answer https://stackoverflow.com/a/17228326/2271198 explain better who bind_param works
Related
This question already has answers here:
How do I create a PDO parameterized query with a LIKE statement?
(9 answers)
Closed 1 year ago.
I have the following statement set up. I have replaces a long list of columns with * to make this more readable. FYI - I already know that there are questions similar to this. They use SINGLE select statements with a SINGLE parameter. Somehow this is different.
$sql = <<<EOM
SELECT *
FROM table1
WHERE StreetName like '%:StreetName_Coml%'
UNION
SELECT *
FROM table2
WHERE StreetName like '%:StreetName_Coms%'
UNION
SELECT *
FROM table3
WHERE StreetName like '%:StreetName_Farm%'
UNION
SELECT *
FROM table4
WHERE StreetName like '%:StreetName_Land%';
EOM;
$p = $db->prepare($sql);
$StreetName = 'tree'
$p->bindValue(':StreetName_Coml', $StreetName);
$p->bindValue(':StreetName_Coms', $StreetName);
$p->bindValue(':StreetName_Farm', $StreetName);
$p->bindValue(':StreetName_Land', $StreetName);
$p->execute();
$data = $p->fetchAll(PDO::FETCH_ASSOC);
The query runs, with no PHP errors. But I am getting no results back. I should be getting back 100's of rows. When I run the same query in my database browser I get 100's of rows. There is something in how the parameters are being bound that is not working.
I have tried the following:
bindParam instead of bindValue
moving the '%' from the SQL statement and into $StreetName. So instead of 'tree' it is '%tree%'
using a CONCAT statement like "WHERE StreetName like CONCAT('%',:StreetName_Land,'%')
and various mix and matching of the above.
What am I missing?
Put the percent signs in the bind, so your SQL is like this, unqouted:
WHERE StreetName like :StreetName
And then your binds are like this:
$p->bindValue(':StreetName', '%' . $StreetName . '%');
This question already has answers here:
PHP - Using PDO with IN clause array
(9 answers)
MySQLi prepared statements with IN operator [duplicate]
(1 answer)
Closed 3 years ago.
So I have this sql preparted statment:
SELECT carName, modelName
FROM cars
INNER JOIN model ON cars.idCar = model.idCar
WHERE carName IN (?)`
$input = " 'toyota','honda' "
I am trying to put this into the sql statment, but it gives zero rows out. I have tried the query in phpMyAdmin and there it works all fine. Anyone know the problem?
You need one parameter per value in the IN list. If you pass a single parameter, it is interpreted as a unique string that contains a comma, which is not what you want (and you end up with no match, since none of the names in the table matches this value).
So for two parameters:
SELECT carName, modelName
FROM cars
INNER JOIN model ON cars.idCar = model.idCar WHERE carName IN (?, ?);
The IN clause takes multiple arguments and each parameter can only take on one value. So to automate the process of inserting multiple parameters in this statement you could use something like the following:
/* Execute a prepared statement using an array of values for an IN clause */
$params = ['toyota', 'honda'];
/* Create a string for the parameter placeholders filled to the number of params */
$place_holders = implode(',', array_fill(0, count($params), '?'));
/*
This prepares the statement with enough unnamed placeholders for every value
in our $params array. The values of the $params array are then bound to the
placeholders in the prepared statement when the statement is executed.
This is not the same thing as using PDOStatement::bindParam() since this
requires a reference to the variable. PDOStatement::execute() only binds
by value instead.
*/
$st = $db->prepare("SELECT carName, modelName FROM cars WHERE carName IN ($place_holders)");
$st->execute($params);
This question already has answers here:
Using SQlite3 in PHP how to count the number of rows in a result set?
(6 answers)
Closed 5 years ago.
I need to make a query in my SQLite3 database using PHP and this is my code and it's working:
# Set access to data base...
$db = new SQLite3('./Data/myDB.sqlite');
# Set the query ...
$q="SELECT * FROM my_table WHERE key = '123'";
# Prepare for the query ...
$stmt = $db->prepare($q);
# Execute the query ...
$results = $stmt->execute();
Now, how to count how many records there are in my result? Suggestions / examples?
You could either do it in SQL or in PHP:
Change your SQL request to
SELECT COUNT(*) FROM my_table WHERE key = 123
Or count rows in PHP (taken from here) :
$nrows = 0;
$result->reset();
while ($result->fetchArray())
$nrows++;
$result->reset();
return $nrows;
This question already has answers here:
Can PHP PDO Statements accept the table or column name as parameter?
(8 answers)
Closed 8 years ago.
I'm having trouble figuring out what I'm doing wrong. If i use this set of code I get the result I intend:
$x = $db->prepare('SELECT * FROM table LIMIT 2');
$x->execute();
print_r($x->fetchALL());
When I use this set of code I don't get anything in return:
$a = "table";
$b = "2";
$x = $db->prepare('SELECT * FROM ? LIMIT ?');
$x->execute(array($a,$b));
print_r($x->fetchALL());
Is there something I'm missing? Thanks in advance.
Parameter placeholders can only be used to replace column values; not table names, column names, or other syntax elements (including LIMIT values).
In order to make your query dynamic with respect to things that can't be parameterized, you have to build it yourself, without PDO's help. However, you should still build it so that the values that can be parameterized, are paramerized.
This question already has answers here:
How can I bind an array of strings with a mysqli prepared statement?
(7 answers)
Closed 3 years ago.
I’m moving some old code over to the new msqli interface using prepared statements, I’m having trouble with SQL statements containing the IN clause. I would just normally do this:
$ids = '123,535,345,567,878'
$sql = "SELECT * FROM table WHERE id IN ($ids)";
$res = mysql_query($sql);
Converting this to mysqli and prepared statements I have tried a number of solutions:
$ids = '123,535,345,567,878'
$ids = implode($ids,',');
$result = $msqli->prepare("SELECT foo,blar FROM table WHERE id IN (?));
$result->bind_param("i", $ids);
$result->execute();
The above fails and calculating the number of elements in the array and altering number of question marks in the SQL string and calling bind_parm for each element in the array also fails. Just using the comma separated string also fails.
I can find no good documentation in Google on this, so how have you solved the problem?
It's not possible to bind a list of variable length to a single bound variable.
Similarly, if you were to bind the string $ids you'll actually end up with:
SELECT foo,blar FROM table WHERE id IN ('123,535,345,567,878')
(Note the quotes around the list of IDs).
Creating your own query with the right number of question marks and bound parameters should have actually worked - you may need to try that again and report on the actual error.
Alternatively, this may be one of those occasions where it's unfortunately necessary to hand-craft your own SQL and not use bound parameters.
Look at the answer to a similar question that has been asked here before (second code sample):
I have an array of integers, how do I use each one in a mysql query (in php)?
It boils down to:
create the SQL string with the right amount of question marks
use call_user_func_array() to bind your array to the query string
I thought the point of prepared statements was so in this situation you could just do:
$stmt = $this->mysqli->prepare("UPDATE radcheck SET attribute = ?, value = ? WHERE username = ? AND attribute LIKE 'CS-Total-Octets%'");
foreach ($usernames as $username)
{
$stmt->bind_param('sss', $bandwidth_types[$bandwidth_type], $bandwidth_bytes, $username);
$stmt->execute();
}
$stmt->close();