Take the 2-minute tour ×
Stack Overflow is a question and answer site for professional and enthusiast programmers. It's 100% free, no registration required.

Given an array of ids $galleries = array(1,2,5) I want to have a SQL query that uses the values of the array in its WHERE clause like:

SELECT *
FROM galleries
WHERE id = /* values of array $galleries... eg. (1 || 2 || 5) */

How can I generate this query string to use with MySQL?

share|improve this question
    
3  
@trante this one is the oldest (2009). –  Fabián Sep 13 '13 at 17:33
    
Is there any similar solution for problem like SELECT * FROM TABLE WHERE NAME LIKE ( 'ABC%' or 'ABD%' OR .. ) –  Eugine Joseph Jun 12 '14 at 7:11
    
I'd recommend Laravel –  Michael Calkins Jun 22 '14 at 3:56

9 Answers 9

up vote 228 down vote accepted

BEWARE! This answer contains a severe SQL Injection vulnerability. Do NOT use the code samples presented here, unless you are really really sure about the incoming ids as "safe". This answer is only preserved to prevent breaking links and for reference value.

$ids = join(',',$galleries);  
$sql = "SELECT * FROM galleries WHERE id IN ($ids)";
share|improve this answer
1  
The identifiers are still a quoted list, so it comes out as "WHERE id IN ( '1,2,3,4' )", for example. You need to quote each identifier separately, or else ditch the quotes inside the parentheses. –  Rob May 25 '09 at 20:05
9  
I just add the warning that $galleries should be input validated before this statement! Prepared statements can't handle arrays AFAIK, so if you are used to bound variables, you could easily make SQL injection possible here. –  leemes Mar 27 '12 at 11:07
4  
This answer should be edited to make it less harmful to anyone who copy/pastes it. @FlaviusStef, do you think you could edit to address the blatant SQL injection risks here? –  Chris Baker May 15 '14 at 2:34
7  
PLEASE DON'T USE THIS ANSWER!!! Use the CW by "Your Common Sense". –  Hans Jun 5 '14 at 23:23
3  
Dangerous answer is dangerous. As mentioned, SQL injection vulnerabilities are potentially rampant here. –  Dan Lugg Aug 28 '14 at 16:03
select id from galleries where id in (1, 2, 5);

Simple for each loop will work.

EDIT: Flavius/AvatarKava's way is better, but make sure that none of the array values contain commas.

share|improve this answer

Assuming you properly sanitize your inputs beforehand...

$matches = implode(',', $galleries);

Then just adjust your query:

SELECT *
FROM galleries
WHERE id IN ( $matches )

Quote values appropriately depending on your dataset.

share|improve this answer
    
Yea, yours is better than mine was :P –  Aiden Bell May 25 '09 at 19:39

Because the original question relates to an array of numbers and I am using an array of strings I couldnt make the given examples work.

I found that each string needed to be encapsulated in single quotes to work with the IN() function.

Here is my solution

foreach($status as $status_a) {
        $status_sql[] = '\''.$status_a.'\'';
    }
    $status = implode(',',$status_sql);

$sql = mysql_query("SELECT * FROM table WHERE id IN ($status)");

As you can see the first function wraps each array variable in single quotes (\') and then implodes the array.

NOTE: $status does not have single quotes in the SQL statement.

There is probably a nicer way to add the quotes but this works.

share|improve this answer

You may have table texts (T_ID (int), T_TEXT (text)) and table test (id (int), var (varchar(255)))

in insert into test values (1, '1,2,3') ;

the following will output rows from table texts where T_ID IN (1,2,3)

SELECT * FROM `texts` WHERE (SELECT FIND_IN_SET( T_ID, ( SELECT var FROM test WHERE id =1 ) ) AS tm) >0

this way you can manage a simple n2m db relation without extra table and using only SQL without need to us PHP or other programming lang.

share|improve this answer

ints:

$query = "SELECT * FROM `$table` WHERE `$column` IN(".implode(',',$array).")";

strings:

$query = "SELECT * FROM `$table` WHERE `$column` IN('".implode("','",$array)."')";
share|improve this answer
1  
Why '\' ??Please tell me –  zloctb Sep 20 '13 at 11:42

How can I create a prepared statement for IN () operator?

Prepared statement can represent complete data literal only. Not a part of literal, nor a complex expression, nor identifier. But either string or number only. So, a very common pitfall is a query like this:

$ids = array(1,2,3);
$stm = $pdo->prepare("SELECT * FROM t WHERE id IN (?)");
$stm->execute(array($ids));

it will actually bind a word 'Array' and raise a warning.

One have to create a query with placeholders representing every array member, and then bind this array values for execution:

$ids = array(1,2,3);
$stm = $pdo->prepare("SELECT * FROM t WHERE id IN (?,?,?)");
$stm->execute($ids);

To make this query more flexible, it's better to create a string with ?s dynamically:

$ids = array(1,2,3);
$in  = str_repeat('?,', count($arr) - 1) . '?';
$sql = "SELECT * FROM table WHERE column IN ($in)";
$stm = $db->prepare($sql);
$stm->execute($ids);
$data = $stm->fetchAll();

Of course, if we have other variables to be bound, we need to add them to values array:

$ids = array(1,2,3);
$in  = str_repeat('?,', count($arr) - 1) . '?';
$sql = "SELECT * FROM table WHERE column IN ($in) AND category=?";
$stm = $db->prepare($sql);
$ids[] = $category; //adding another member to array
$stm->execute($ids);
$data = $stm->fetchAll();

the code become quite bloated but that's all PDO can offer to handle such complex cases. As a further improvement one can invent their own placeholders to support such complex data types.

share|improve this answer
    
You also have to handle the case of an empty array separately as MySQL doesn't allow the empty list as in field IN (). How about writing a function for this which applies PDO::quote to each value in the set? –  Adder May 14 '13 at 14:46
    
Yup, you are right. However, I have a better idea already and I hope I will come up with neat solution pretty soon :) –  Your Common Sense May 14 '13 at 14:59
    
Isn't this better? join(',', array_fill(0, count($arr), '?')) :) –  deceze Jun 12 '13 at 8:44
$ids = "(".implode(',',$galleries).")";  // you can remplace "implode" with "join"  
$sql = "SELECT * FROM galleries WHERE id IN $ids";
share|improve this answer

In SQL the IN() operator is used to check if a value exists in an array.

The code below uses prepared statements for MySQLi or PDO to help mitigate SQL injection attacks. The variable $ids is assumed to contain at least one value. Error checking is omitted for brevity; you need to check for the usual errors for each database method (or set your DB driver to throw exceptions).

$in = join(',', array_fill(0, count($ids), '?'));

$select = <<<SQL
    SELECT *
    FROM galleries
    WHERE id IN ($in);
SQL;


// if using MySQLi (PHP 5.6):
$statement = $mysqli->prepare($select);
$statement->bind_param(str_repeat('i', count($ids)), ...$ids);
$statement->execute();
$result = $statement->get_result();

// if using PDO (or don't have PHP 5.6):
$statement = $pdo->prepare($select);
$statement->execute($ids);

Using the IN() operator with strings.

It is easy to change between strings and integers because of the bound parameters. For PDO there is no change required; for MySQLi change str_repeat('i', to str_repeat('s', if you need to check strings.

share|improve this answer
    
What does ...$ids do? I get "syntax error, unexpected '.'". –  Marcel Sep 18 '14 at 0:43
    
@Marcel Read the comments in the code. –  Levi Morrison Sep 18 '14 at 14:03
    
I see them, I am using MySQLi and I have php 5.6 –  Marcel Sep 18 '14 at 15:52

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.