Bonjour,
J'ai un formulaire qui permet à l'utilisateur d'entrer ses critères de filtrage pour afficher un tableau d'adresses.
Je crée une requête préparée avec une clause where construite en fonction des critères du formulaire. Je n'ai encore pas tout vérifié mais la dernière clause avec le IN (ligne 37) ne fonctionne pas comme je voudrais. Pour info, $toFilter['groups'] provient d'une liste select à sélection multiple.
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
function getFilteredAddresses(int $userId, string $language, array $toFilter): false|array
{
	$db = dbConnect();
	$wheres		= [];
	$params	= [':id_user'=>$userId];
 
	if( ! empty($toFilter['from']) )
	{
		$wheres[]			= "m.familyname>:from";
		$params[':from']	= $toFilter['from'];
	}
 
	if( !empty($toFilter['to']) )
	{
		$wheres[] 			= "m.familyname<:to";
		$params[':to']		= $toFilter['to'];
	}
 
	if( !empty($toFilter['country']) )
	{
		$wheres[] 			= "country=:country";
		$params[':country']	= $toFilter['country'];
	}
 
	if( !empty($toFilter['zipcode']) )
	{
		$wheres[] 			= "a.zipcode=:zipcode";
		$params[':zipcode']	= $toFilter['zipcode'];
	}
 
	if( !empty($toFilter['locality']) )
	{
		$wheres[] 			= "a.locality=:locality";
		$params[':locality']= $toFilter['locality'];
	}
 
	if( !empty($toFilter['groups']) )
	{
		$in = implode(',', $toFilter['groups']);
		$wheres[]			= "g.id_group IN ($in)";
		/*
		$in = implode(',', $toFilter['groups']);
		$wheres[]			= "g.id_group IN (:in)";
		$params[':in']		= $in;
		*/
	}
 
	var_dump($wheres);
	var_dump($params);
	$clause = implode(' AND ', $wheres);
	if($clause)
		$clause = " AND " . $clause;
 
	$sql = <<<SQL
SELECT DISTINCT a.id, m.familyname, m.firstname, %s_name AS country, a.zipcode, a.locality, m.email, a.homephone, m.GSM
FROM dat_addresses a
	LEFT JOIN lst_countries c
		ON a.country=c.id
	LEFT JOIN dat_members m
		ON a.id=m.id_address
	LEFT JOIN dat_groups g
		ON a.id=g.id_address
WHERE id_user=:id_user AND m.relation=0%s
ORDER BY m.familyname, m.firstname
SQL;
	$sql = sprintf($sql, $language, $clause);
	$stmt = $db->prepare($sql);
	$stmt->execute($params);
	return $stmt->fetchAll();
}
Le code de la ligne 40 n'est pas paramétré et me donne le résultat attendu avec deux adresses mais le code en commentaire est paramétré mais ne donne qu'une adresse.
En version non paramétrée, la ligne 48 donne:
array (size=2)
  0 => string 'country=:country' (length=16)
  1 => string 'g.id_group IN (1,2,3)' (length=21)
et la ligne 49:
array (size=2)
  ':id_user' => int 2
  ':country' => string 'FR' (length=2)
En version paramétrée, la ligne 48 donne:
array (size=2)
  0 => string 'country=:country' (length=16)
  1 => string 'g.id_group IN (:in)' (length=19)
et la ligne 49:
array (size=3)
  ':id_user' => int 2
  ':country' => string 'FR' (length=2)
  ':in' => string '1,2,3' (length=5)
Question: Est-ce qu'il y aurait un inconvénient à ne pas paramétrer cette clause qui ne contient que des valeurs numériques?
Sinon, comment faire pour avoir le bon résultat?