V.C.4
V.C.4

Reputation: 19

Dynamically Bind Parameter PHP

This is my first foray into the world of stack overflow, I'm new to programming and could desperately use some assistance. I'm attempting to dynamically parameterize a mysqli DB query but keep getting an error saying "Wrong parameter count for mysqli_stmt::bind_param()", even though I'm (pretty) sure my counting isn't that bad. Thanks in advance for your help, the relevant code is below.

$search = "SELECT Row1, Row2, Row3, Row4, Row5, Row6 FROM Listings WHERE (Search1 LIKE ?) AND (Search2 LIKE ?) AND (Search3 LIKE ?) AND (Status='Active')";

$params= array(&$param1, &$param2, &$param3);
$stmt = $con2->stmt_init();
        if($stmt->prepare($search)) {
            call_user_func_array(array($stmt, 'bind_param'), $params);

            if($stmt->execute()) {
                $stmt->bind_result($Row1, $Row2, $Row3, $Row4, $Row5, $Row6);
                echo 'Success';
          }
         }`

Upvotes: 2

Views: 107

Answers (1)

Elias Van Ootegem
Elias Van Ootegem

Reputation: 76413

Check the official manual. The function/method signature suggests that bind_param expects 3 arguments in your case:

bool mysqli_stmt::bind_param ( string $types , mixed &$var1 [, mixed &$... ] )

You're passing the values alright, but at no point are you passing the string that indicate the types:

$params = array(
    'sss',
    &$param1,
    &$param2,
    &$param3
);

Would make more sense. However, personally, I find code like this is pointless obfuscation of what you're actually doing, simply writing:

$stmt->bind_param('sss', $param1, $param2, $param3);

makes more sense, anyway, and you don't need to construct that array of references, call call_user_func_array, which simply invokes the bind_param method to begin with. So basically: stick to the one-liner

Slightly off-topic:
A bit of friendly advice: your query, though using prepared statements and all that is far from perfect: at no point do you seem to check for wildcards (% and _), so if these parameters are coming from the user, make sure that you don't end up performing a LIKE query that looks like this:

SELECT Row1, Row2, Row3, Row4, Row5, Row6 
FROM Listings 
WHERE Search1 LIKE '%'
  AND Search2 LIKE '%'
  AND Search3 LIKE '%'
  AND Status='Active'

Which will just return all records with Status = 'Active'. Fix this by Either using = instead of LIKE or sanitizing the input.

Upvotes: 3

Related Questions