Есть ли более простой способ безопасного извлечения представленных переменных, кроме следующих?
if(isset($_REQUEST['kkld'])) $kkld=mysql_real_escape_string($_REQUEST['kkld']); if(isset($_REQUEST['info'])) $info=mysql_real_escape_string($_REQUEST['info']); if(isset($_REQUEST['freq'])) $freq=mysql_real_escape_string($_REQUEST['freq']);
(И: вы бы использовали isset()
в этом контексте?)
Чтобы избежать всех переменных за один раз:
$escapedGet = array_map('mysql_real_escape_string', $_GET);
Чтобы извлечь все переменные в текущее пространство имен (например, $foo = $_GET['foo']
):
extract($escapedGet);
Однако не делайте этого последнего шага. Нет необходимости, просто оставьте значения в массиве. Извлечение переменных может привести к конфликтам имен и перезаписи существующих переменных, что является не только хлопот и источником ошибок, но и угрозой безопасности. Кроме того, как говорит @BoltClock, придерживайтесь $_GET
или $_POST
. Также2, как указывает @zerkms, нет смысла в переменных mysql_real_escaping
, которые не должны использоваться в запросе базы данных, это может даже привести к дальнейшим проблемам.
Обратите внимание, что на самом деле ничто из этого не является особенно хорошей идеей, вы просто перевоплощаетесь magic_quotes и global_vars, которые были ужасающими методами PHP из прошлого. Используйте подготовленные операторы с связанными параметрами через mysqli или PDO и используйте значения через $_GET
или filter_input
. См. http://www.phptherightway.com .
Вы также можете использовать такую рекурсивную функцию, чтобы выполнить это
function sanitate($array) { foreach($array as $key=>$value) { if(is_array($value)) { sanitate($value); } else { $array[$key] = mysql_real_escape_string($value); } } return $array; } sanitate($_POST);
Насколько я знаю, Starx 'и ответ Райана от 19 ноября '10 – лучшее решение здесь, поскольку я просто нуждался в этом.
Когда у вас есть несколько полей ввода с одним именем (например, имена []), то есть они будут сохранены в массив в массиве $ _POST, вы должны использовать рекурсивную функцию, так как mysql_real_escape_string не работает для массивов.
Таким образом, это единственное решение избежать такой переменной $ _POST.
function sanitate($array) { foreach($array as $key=>$value) { if(is_array($value)) { sanitate($value); } else { $array[$key] = mysql_real_escape_string($value); } } return $array; } sanitate($_POST);
Для дезинфекции или проверки любых INPUT_GET
, INPUT_POST
, INPUT_COOKIE
, INPUT_SERVER
или INPUT_ENV
вы можете использовать
filter_input_array
– получает внешние переменные и, возможно, фильтрует их Фильтрация может быть выполнена с помощью обратного вызова, поэтому вы можете предоставить mysql_real_escape_string
.
Этот метод не позволяет фильтровать $_REQUEST
, потому что вы не должны работать с $_REQUEST
когда данные доступны в любом из других суперглобалов. Это потенциально небезопасно.
Метод также требует, чтобы вы написали ключи ввода, поэтому это не общая фильтрация пакетов. Если вам нужна общая пакетная фильтрация, используйте array_map
или array_walk
или array_filter
как показано в другом месте на этой странице.
Кроме того, почему вы используете старое расширение mysql вместо расширения mysqli (i для улучшения). Расширение mysqli даст вам поддержку транзакций , мультивизоров и подготовленных операторов (что исключает необходимость экранирования). Все функции, которые могут сделать ваш код DB более надежным и безопасным.
В качестве альтернативы я могу посоветовать вам использовать входные фильтры PHP7 , которые предоставляют ярлык для sql-экранирования. Я бы не рекомендовал его сам по себе, но он предлагает создавать локализованные переменные:
$_REQUEST->sql['kkld']
Который может использоваться inline в строках SQL-запросов и дает дополнительное предупреждение, если вы его забудете:
mysql_query("SELECT x FROM y WHERE z = '{$_REQUEST->sql['kkld']}'");
Это синтаксически сомнительно, но позволяет избегать только тех переменных, которые действительно нуждаются в этом. Или, чтобы подражать тому, что вы просили, используйте $_REQUEST->sql->always();