Perl DBI:转义 LIKE 准备好的语句

问题描述 投票:0回答:1

我有一个将参数绑定到 LIKE 语句的查询,如下所示:

my $sth = $dbh->prepare('SELECT foo FROM bar WHERE baz LIKE ?');
$sth->execute("%$like%");

但是,

$like
是用户输入的值。因此,如果该值包含
LIKE
子句(
%
_
\
)识别的任何特殊字符,这些字符将不转义传递到数据库并解析为通配符或转义字符。例如,如果用户输入
%value
,则将提交的查询是:
SELECT foo FROM bar WHERE baz LIKE '%%value'
,而不是我所期望的
LIKE '%\%value

目前我正在使用正则表达式手动转义该字段:

# Escape LIKE wildcard characters
$like =~ s!\\!\\\\!g;
$like =~ s!%!\\%!g;
$like =~ s!_!\\_!g;

my $sth = $dbh->prepare('SELECT foo FROM bar WHERE baz LIKE ?');
$sth->execute("%$like%");

但感觉转义是 DBI 应该能够处理的。我使用了

DBI::quote
,但这是为引用整个字段而设计的,因此在这种情况下,它还会引用我添加的
%
符号,并且
DBI::quote
的文档特别指出:

quote() 方法不应与“Placeholders 和 Bind 价值观”。

是否有更好的方法将用户提供的输入绑定到 LIKE 子句,同时转义输入并添加相关通配符,而不需要手动转义输入?

sql perl dbi
1个回答
-3
投票

尽管

DBI::quote
的文档有说明,
LIKE
参数有点特殊。您想要做的几乎就是您的示例中已经拥有的内容:首先通过将
quote
应用于用户提供的字符串(您在示例中使用正则表达式执行此操作)来确保没有用户提供的元字符,然后添加您的自己的元字符(在本例中为百分号),然后将其用作绑定参数的食物。

© www.soinside.com 2019 - 2024. All rights reserved.