in reply to Preventing MySQL Injection

In Perl (and also in PHP, btw), you don't escape the strings, you use placeholders in your query. I don't know PHP, but here's an example for Perl:

my $sth = $dbh->prepare(<<SQL); SELECT (foo,bar,baz) FROM dta WHERE (user = ? AND position < ?) SQL my $user = $q->param('user'); my $position = $q->param('position'); $sth->execute($user, $position);

Using placeholders protects you from injection attacks because the values are never interpolated into the SQL query by you but only by the driver for your SQL database which knows how to do this safely.

Blindly quoting everything is a stupid approach, because, as you already noticed, the quoting mechanism needs to know whether an element is supposed to be a number or a string. If you want to do the quoting manually, DBI->quote() is the correct approach to use, but you need to take care to validate your data and make sure that numbers look like numbers, strings look like strings and dates look like dates.

Replies are listed 'Best First'.
Re^2: Preventing MySQL Injection
by Anonymous Monk on Jan 03, 2008 at 14:54 UTC
    Guess i'll start using place holders instead.

    should this technique be used exclusively, or only where user/untrusted input is provided?
      You should use it where possible, since it greatly reduces the (error prone) task to keep track of which variables contain "trusted" data, and which doesn't.

      You should use placeholders, but there are times when placeholders aren't a suitable replacement for escaping the string ... however, those tend to be risky security wise.

      Placeholders only work with values for fields ... if you're trying to do something like allowing the user to select an arbitrary table or field, you'll have to escape the value. I don't know if it's true for all versions, but from what I recall, even setting a LIMIT couldn't be done with a placeholder in older version. In these sorts of cases, I typically abort entirely if values aren't composed of only known good characters ([a-zA-Z0-9_] for fields/tables, [0-9] for limits, etc) ... but it's best to avoid the issues as best you can.