我正在努力强化我的一些PHP代码并使用mysqli预处理语句来更好地验证用户输入并防止注入攻击。
我转离了mysqli_real_escape_string as it does not escape % and _。但是,当我将查询创建为mysqli预处理语句时,仍存在相同的缺陷。该查询根据用户名提取用户salt值。我会为密码和其他查找做类似的事情。
代码:
$db = new sitedatalayer();
if ($stmt = $db->_conn->prepare("SELECT `salt` FROM admins WHERE `username` LIKE ? LIMIT 1")) {
$stmt->bind_param('s', $username);
$stmt->execute();
$stmt->bind_result($salt);
while ($stmt->fetch()) {
printf("%s\n", $salt);
}
$stmt->close();
}
else return false;
谢谢,
答案 0 :(得分:8)
%
并非天生有害的特征。
问题是:为什么你首先使用LIKE
?是否任何情况下您不需要完全匹配用户名?
查询应该简单:
SELECT `salt` FROM admins WHERE `username` = ? LIMIT 1
在这种情况下,如果我要输入%bsmith
,我的用户名必须是(字面意思)“%bsmith”才能找到匹配项。
答案 1 :(得分:1)
您在这里混淆了两个不同级别的评估。
LIKE
运算符接受一个字符串,并将任何'%'
和'_'
评估为占位符。
查询参数的工作只是将值(例如字符串) verbatim 引入数据库引擎,因此不能将它们误认为是SQL代码。他们并不关心LIKE
运算符如何特别使用他们刚刚传输的字符串中的某些字符。一切都按照这里的设计工作。
如果您想要完全匹配,请使用=
运算符代替LIKE
。
如果您必须使用LIKE
(即使您的LIMIT 1
另有说明),请事先escape the the special characters accordingly自己。
答案 2 :(得分:-1)
使用LIKE将用户名与blame匹配,而不是转义函数。
并且,仅为您的信息:本机预处理语句不会逃避任何事情。
答案 3 :(得分:-1)
这些是未通过预准备语句%_ \
转义的字符