ЯВЛЯЕТСЯ ли умножение на 1 безопасным способом очистки числовых значений от sql-инъекций?
Мне интересно, если у меня есть значение, которое, как я знаю, должно быть числовым, является ли умножение его на 1 безопасным способом его очистки?
function x($p1){
$p1*=1;
sql="select * from t where id ={$p1}";
//run query..
}
Хотя в моем примере используется идентификатор, он используется для многих типов числовых значений, которые у меня есть в приложении (могут быть деньги, могут быть pai и т. Д.).
6 answers
Я не понимаю, почему бы и нет. Но что плохого в использовании подготовленных заявлений? Это всегда будет безопаснее, чем использовать переменные PHP непосредственно в операторах SQL.
Вы можете использовать is_numeric()
Я уверен, что есть более "подходящий" способ, но в контексте вашего вопроса я бы сказал "да". Если передается какая-то строка, PHP будет интерпретировать ее как ноль при выполнении математической операции.
Вы также можете использовать is_int()
Хотя это, вероятно, сработает, intval
кажется лучшим решением. http://php.net/manual/en/function.intval.php . Ваше намерение, скорее всего, будет более очевидным для кого-то другого, читающего ваш код.
Если вы хотите проверить, является ли значение числовым, прежде чем преобразовывать его в int, используйте is_numeric
( http://php.net/manual/en/function.is-numeric.php ). Он будет проверять наличие строк, которые являются числовыми, а также целыми числами. Например, если номер возвращался из формы ввода текста через АЯКС, это может быть строка. В этом случае is_int
вернет значение false, но is_numeric
вернет значение true.
РЕДАКТИРОВАТЬ
Теперь, когда я знаю, что вы используете DECIMAL для типа столбца MySQL, вы можете сделать что-то вроде этого:
function getItem($pValue)
{
if (!is_numeric($pValue))
{
return false;
}
$Query = sprintf
(
'SELECT * FROM %s WHERE %s = %.2f',
'TableName',
'Price',
$pValue
);
// Do something with $Query
}
В большинстве случаев это работает, так как приводит строки к целым числам или удвоениям, но вы должны быть осторожны. Это будет правильно работать для скалярных значений. Однако, если вы сделаете это:
x(new stdClass);
Вы получите E_NOTICE
. Это не так уж и плохо, верно? Это:
x(array());
И вы получите E_ERROR
, Неподдерживаемые типы операндов, и сценарий завершается.
Возможно, вы подумаете, что это не так уж и плохо, но фатальная ошибка в неподходящий момент может оставить вашу систему в нестабильное состояние, например, из-за потери ссылочной целостности или незавершенности ряда запросов.
Только вы знаете, может ли произойти подобный случай. Но если эти данные каким-либо образом поступают от пользователя, я бы согласился с Законом Мерфи в этом вопросе и не доверял ему.