Каков наилучший способ обработки созданного пользователем HTML-контента, который будет просматриваться публикой? - PullRequest
10 голосов
/ 22 октября 2009

В моем веб-приложении я разрешаю публиковать пользовательский контент для общего пользования, аналогично Stackoverflow.

Какая лучшая практика для передачи этого?

Мои текущие шаги для обработки пользовательского контента:

  1. Я использую MarkItUp , чтобы разрешить пользователям простой способ форматировать их HTML.

  2. После того, как пользователь отправил их изменения, которые я запускаю через HTML Дезинфицирующее средство (выделите bottem) , который использует белый список подход.

  3. Если в процессе санации удалил любой созданный пользователем контент, который я не сохраняйте контент. После, я Вернуть туда измененный контент с предупреждающее сообщение, "Некоторые незаконные теги содержимого, где обнаружены и удалите дважды проверить свою работу и попробуйте еще раз. "

  4. Если контент проходит через Процесс санации чисто, я экономлю сырое содержание HTML в базы данных.

  5. При рендеринге клиенту я просто передать сырой HTML из БД страницы.

Ответы [ 2 ]

2 голосов
/ 22 октября 2009

Это вполне разумный подход. Для типичных приложений этого будет вполне достаточно.

Самая хитрая часть белого HTML-списка - это атрибут style и embed / object. Существуют законные причины, по которым кто-то может захотеть поместить стили CSS в ненадежный блок форматированного текста или, скажем, встроенное видео YouTube. Эта проблема чаще всего встречается в каналах. Вы не можете доверять произвольному блоку текста, содержащемуся в записи фида, но вы не хотите удалять, например, подсветку синтаксиса CSS или флэш-видео, потому что это в корне изменит контент и может привести в замешательство любого, кто его читает. Поскольку CSS может содержать опасные вещи, такие как поведение в IE, вам, возможно, придется анализировать CSS, если вы решите оставить атрибут style. А с embed / object вам может понадобиться внести в белый список имена хостов.

Addenda:

В наихудших сценариях HTML, который скрывает все, что видно, может привести к очень плохому восприятию пользователя. Гораздо лучше использовать что-то вроде одного из HTML5-парсеров, чтобы пройти через DOM с вашим белым списком. Это намного более гибко с точки зрения того, как вы представляете очищенный вывод своим пользователям. Вы даже можете делать такие вещи, как:

<code><div class="sanitized">
  <div class="notice">
    This was sanitized for security reasons.
  </div>
  <div class="raw"><pre>
    &lt;script&gt;alert("XSS!");&lt;/script&gt;
  

Затем скройте содержимое .raw с помощью CSS и используйте jQuery для привязки обработчика щелчка к .sanitized div, который переключается между .raw и .notice:

CSS:

.raw {
  display: none;
}

JQuery:

$('.sanitized').click(function() {
  $(this).find('.notice').toggle();
  $(this).find('.sanitized').toggle();
});
1 голос
/ 22 октября 2009

Белый список - хороший ход. Любое решение из черного списка может пропустить больше, чем должно, потому что вы не можете думать обо всем. Я видел некоторые попытки использования черных списков (например, The Code Project), и, если им удается поймать все, как правило, они по-прежнему вызывают дополнительные проблемы, такие как замена символов в коде, так что его нельзя использовать без предварительного восстановления вручную .

Самый безопасный метод будет:

  1. HTML кодирует весь текст.

  2. Соответствует набору разрешенных тегов и атрибутов и декодирует их.

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

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

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...