I am trying to pass an array into a SELECT * FROM table WHERE IN()
statement. I am expecting 3 result. but I got 2 result instead.
I am aware same question in the below 2 posts
Can I bind an array to an IN() condition?
and
MySQL WHERE IN () + AND , PDO returns only one row
However I am still learning php pdo, thus I dont understand the code enough to figure out how to repurpose their code to my code.
I hope someone can point out where I did wrong. because I get partial results from the select in statement. I suspect I did not pass array into the IN() correctly.
below is php code of my controler page
$customer_ids = array(1,2,3,4,5,6,7);
//in actual case I get array from another query.
$customer_id = implode(',',$customer_ids);
//add comma to the array
$template->orders = $rephome->getOrder($customer_id);
//passing the imploded array into my Model page with class named rephome,
//call on the method of getOrder, which is the select query
below is my model page.
public function getOrder($customer_id){
$this->db->query("SELECT * FROM orders WHERE customer_id_fk IN(.$customer_id.)");
$results = $this->db->resultset();
return $results;
Below is what is in my database class
public function query($query) {
$this->stmt = $this->dbh->prepare($query);
}
public function bind($param, $value, $type = null) {
if (is_null ( $type )) {
switch (true) {
case is_int ( $value ) :
$type = PDO::PARAM_INT;
break;
case is_bool ( $value ) :
$type = PDO::PARAM_BOOL;
break;
case is_null ( $value ) :
$type = PDO::PARAM_NULL;
break;
default :
$type = PDO::PARAM_STR;
}
}
$this->stmt->bindValue ( $param, $value, $type );
}
public function execute(){
return $this->stmt->execute();
}
public function resultset(){
$this->execute();
return $this->stmt->fetchAll(PDO::FETCH_OBJ);
}
You're not binding an array. You're converting your array into a string, and then binding that string. Bound parameters can represent only SINGLE values, not lists-of-values, so your implode/bind version is functionally identical to
SELECT ... foo IN ('1,2,3')
which executes exactly the same as
SELECT ... foo = '1,2,3'
instead of
SELECT ... IN (1,2,3)
^-^-^--- three separate values
What you want is simply not possible with a single placeholder. You need to build your query dynamically (one placeholder per value), and then you pass your array in to the query call, eg
$temp = array_fill(1, count($customer_ids), '?');
$in_arg = implode(',', $temp);
$sql = "SELECT ... IN ($in_arg)";
$stmt = $db->prepare(sql);
$res = $stmt->execute($customer_ids);
This would produce a query string like
SELECT ... IN (?,?,?,....)
with a placeholder for every value you want to bind.
You can modify the bottom of your switch statement to something like this, what it will do is identify if you have an array
and implode
it with the ,
seperator, and then flow into your default type of PDO::PARAM_STR
... which it now is.
case is_array ( $value ) :
$value = implode(',', $value);
default :
$type = PDO::PARAM_STR;
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.