Расшифровка mysql_real_escape_string() для вывода HTML

Я пытаюсь защитить себя от инъекций SQL и использую:

mysql_real_escape_string($string);

При публикации HTML это выглядит примерно так:

<span class="\&quot;className\&quot;">
<p class="\&quot;pClass\&quot;" id="\&quot;pId\&quot;"></p>
</span>

Я не уверен, сколько других вариаций добавляет real_escape_string, поэтому не хочу просто заменять несколько и пропускать другие... Как мне "декодировать" это обратно в правильно отформатированный HTML, с чем-то вроде:

html_entity_decode(stripslashes($string));

9 ответов

Страница руководства http://php.net/mysql_real_escape_string сообщает вам, какие символы экранированы:

mysql_real_escape_string() вызывает библиотечную функцию MySQL mysql_real_escape_string, которая добавляет обратную косую черту к следующим символам: \x00, \n, \r, \, ', "и \x1a.

Вы можете успешно отменить экранирование, заменив эти экранированные символы их неэкранированными формами.

mysql_real_escape_string() не следует использовать для очистки HTML, хотя... нет причин использовать его перед выводом данных веб-страницы. Он должен использоваться только для данных, которые вы собираетесь поместить в базу данных. Ваш процесс очистки должен выглядеть примерно так:

вход

  1. Принимать ввод пользователя из формы или HTTP-запроса
  2. Создать запрос к базе данных, используя mysql_real_escape_string()

Выход

  1. Извлекать данные из базы данных
  2. Выполнить любые пользовательские данные через htmlspecialchars() перед печатью

Использование другого драйвера базы данных, такого как MySQLi или PDO, позволит вам использовать подготовленные операторы, которые позаботятся о том, чтобы избежать большинства входных данных для вас. Однако, если вы не можете переключиться или воспользоваться этим, то обязательно используйте mysql_real_escape_string()... просто используйте его только перед вставкой данных.

Вы все испортили.

mysql_real_escape_string не требует никакого декодирования.

если вы вернете свои данные с косой чертой, это означает, что они были экранированы дважды. И вместо того, чтобы удалять лишние косые черты, вы должны просто не добавлять их.

Не говоря уже о том, что все спасения устарели, и вы должны

использовать подготовленные заявления

вместо какой-либо escape-строки.

Так что никогда не убегай, никогда не декодируй.
Проблема решена.

mysql_real_escape_string используется для предотвращения внедрения SQL при сохранении данных, предоставленных пользователем, в базу данных, но лучшим способом будет использование привязки данных с использованием PDO (например). Я всегда рекомендую использовать это вместо того, чтобы возиться с побегом.

При этом, что касается вашего вопроса о том, как отображать его впоследствии - после того, как данные сохранены, когда вы извлекаете их, данные полны и действительны без какой-либо необходимости "уходить". Если вы не добавили свои собственные экранирующие последовательности, пожалуйста, не делайте этого.

Используйте следующую функцию для удаления слешей при отображении на HTML-странице:

stripslashes ();

например. $ HTML =stripslashes($ HTML); ИЛИ $html=stripslashes($row["fieldname"]);

Не уверен, что происходит с форматированием, как я вижу, но ваша HTML-форма

<span class="\&quot;className\&quot;">
<p class="\&quot;pClass\&quot;" id="\&quot;pId\&quot;"></p>
</span>

должно быть просто;

<span class="className">
<p class="pClass" id="pId"></p>
</span>

Когда вы получите его обратно, прежде чем поместить его в базу данных, вы избежите его, используя mysql_real_escape_string(), чтобы убедиться, что вы не подвергнетесь атаке SQL-инъекций.

Следовательно, вы избегаете значений, готовых к тому месту, куда идет следующий текст.

Когда вы выводите его из базы данных (или выводите ЛЮБОЕ из него пользователям в виде html), вы снова экранируете его, готовый к тому месту, куда он пойдет следующим (html), с помощью htmlentities() и т. Д., Чтобы защитить ваших пользователей от XSS-атак.

Это формирует часть EO мантры FIEO, Filter Input, Escape Output, которую вы должны татуировать на внутренней стороне своих век.

Ну, я попробовал это по старинке и пока не вижу ничего плохого в моем подходе. Очевидно, это немного грубо, но это делает работу:

function mysql_unreal_escape_string($string) {
    $characters = array('x00', 'n', 'r', '\\', '\'', '"','x1a');
    $o_chars = array("\x00", "\n", "\r", "\\", "'", "\"", "\x1a");
    for ($i = 0; $i < strlen($string); $i++) {
        if (substr($string, $i, 1) == '\\') {
            foreach ($characters as $index => $char) {
                if ($i <= strlen($string) - strlen($char) && substr($string, $i + 1, strlen($char)) == $char) {
                    $string = substr_replace($string, $o_chars[$index], $i, strlen($char) + 1);
                    break;
                }
            }
        }
    }
    return $string;
}

Это должно охватывать большинство случаев.

Мне было интересно, почему эта процедура не имеет сопутствующей процедуры декодера. Он, вероятно, интерпретируется MySQL точно так же, как если бы он не был экранирован. Вы получаете неперекрытые результаты, когда вы делаете $row=mysql_fetch_array($res, MYSQL_ASSOC)';

Даже если это старый вопрос... У меня была та же проблема, что и у Питера Крейга. На самом деле я имею дело со старой CMS. Чтобы предотвратить SQL-инъекцию, все значения $_POST и $_GET являются "sql-escape-экранированными". К сожалению, это делается в центральной точке, поэтому все ваши модули получают все данные sql-escape-escape! В некоторых случаях вы хотите напрямую отобразить эти данные, чтобы вы столкнулись с проблемой: как отобразить строку с экранированием sql, не получая ее из БД? Ответ: используйте стрип-слэш (НЕ стрип-слэш!!)

http://php.net/manual/en/function.stripcslashes.php

Я думаю, что ряд других ответов пропустили очевидную проблему...

Вы используете mysql_real_escape_string для введенного содержимого (как следует, если не используете подготовленные операторы).

Ваша проблема с выходом.

В настоящее время проблема заключается в том, что вы вызываете html_entity_decode. Просто полоски - это все, что вам нужно для восстановления исходного текста. html_entity_decode - это то, что портит ваши цитаты и т. д., так как они меняют их. Вы действительно хотите выводить html, а не просто текст (когда вы используете html_entities и т. Д.). Вы декодируете то, что хотите закодировать.

Если вы хотите, чтобы отображалась только текстовая версия, вы можете использовать объекты. Если вас беспокоят плохие теги, используйте стрип-теги и разрешите только те теги, которые вам нужны (например, b, i и т. Д.).

Наконец, не забудьте кодировать и декодировать в правильном порядке. если вы запустили mysql_real_escape_String(htmlentities($str)), то вам нужно запустить html_entity_decode(stripslashes($str)). Порядок действий имеет значение.

ОБНОВЛЕНИЕ: я не понял, что html_entity_decode также удаляет косые черты. Это не было четко задокументировано на этой странице, и я просто никогда не замечал этого. Я все равно буду автоматически запускать его, так как большинство HTML, которые я представляю, я хочу оставить как сущности, и даже когда я этого не сделаю, я предпочитаю принимать это решение за пределами моего класса БД, в каждом конкретном случае. Таким образом, я знаю, что косые черты исчезли.

Похоже, что на оригинальном плакате работает htmlentities (или его программа ввода, как это делает tinymce), и он хочет вернуть его обратно к содержанию. Итак, html_entity_decode($Str) должен быть всем, что требуется.

Другие вопросы по тегам