2011-11-07 2 views
1

У меня возникли проблемы с удалением всего javascript с HTML-страницы с C#. У меня есть три выражения регулярных выражений, которые удаляют много, но также пропускают слишком много. Разбор javascript с помощью анализатора MSHTML DOM заставляет javascript фактически запускаться, чего я пытаюсь избежать, используя регулярное выражение.Удалить JavaScript с помощью Regex

"<script.*/>" 

    "<script[^>]*>.*</script>" 

    "<script.*?>[\\s\\S]*?</.*?script>" 

Кто-нибудь знает, что мне не хватает, что приводит к тому, что эти три выражения регулярного выражения пропускают блоки JavaScript?

Пример того, что я пытаюсь удалить:

<script src="do_files/page.js" type="text/javascript"></script> 
<script src="do_files/page.js" type="text/javascript" /> 
    <script type="text/javascript"> 
    <!-- 
     var Time=new Application('Time') 
    //--> 
    </script> 
    <script type="text/javascript"> 
     if(window['com.actions']) { 
      window['com.actions'].approvalStatement = "", 
      window['com.actions'].hasApprovalStatement = false 
     } 
    </script> 
+2

Не могли бы вы привести пример пропущенного блока? – Whetstone

+1

Используйте парсер HTML (например [Nokogiri] (http://nokogiri.org)) и измените DOM; [не использовать регулярное выражение] (http://stackoverflow.com/questions/1732348/regex-match-open-tags-except-xhtml-self-contained-tags/1732454#1732454) на необработанном HTML. Вы пытаетесь сделать это на клиенте веб-браузера или на сервере? Если сервер, какой язык программирования? – Phrogz

+0

Во всяком случае, похоже, что ваши регулярные выражения будут соответствовать * больше *, чем вы хотите. Ваш # 2 делает жадный '. *', Поэтому он будет соответствовать всем, начиная с первого '', возможно включая содержимое * между * тегами сценария, которые вы не хотели удалить. –

ответ

4

Я предполагаю, что вы пытаясь просто дезинформировать ввод JavaScript. Честно говоря, я беспокоюсь, что это слишком простое решение, потому что это кажется невероятно простым. Ниже приведено рассуждение после выражения (в строке C#):

@"(?s)<script.*?(/>|</script>)" 

Все, что я хочу, надеюсь! (Это, безусловно, работает для ваших примеров!)

Мое рассуждение об простоте состоит в том, что основной проблемой при анализе HTML с регулярным выражением является возможность вложенных тегов - это не столько вложенность DIFFERENT-тегов, сколько вложенность синонимичных теги

Например,

<b> bold <i> AND italic </i></b> 

... это не так уж плохо, но

<span class='BoldText'> bold <span class='ItalicText'> AND italic </span></span> 

будет гораздо труднее разобрать, потому что конечные теги IDENTICAL.

Однако, поскольку он является недействительным в гнездо script тегов, следующий экземпляр /> (< -эт это действует?) Или </script> конец этого блока сценария.

В тексте сценария всегда есть комментарии HTML или теги CDATA, но они должны быть в порядке, если они не содержат </script>. ОДНАКО: если они это сделают, то определенно будет возможно получить некоторый «код». Я не думаю, что страница будет отображаться, но некоторые парсеры HTML удивительно гибкие, поэтому я никогда не знаю. обрабатывать немногих дополнительные возможные пробела, вы можете использовать:

@"(?s)<\s?script.*?(/\s?>|<\s?/\s?script\s?>)" 

Пожалуйста, дайте мне знать, если вы можете выяснить способ сломать его, что позволит через ДЕЙСТВИТЕЛЬНО HTML код с вводным состоянием JavaScript (я знаю есть несколько способов получить , но он должен быть разбит одним из самых разных способов, если он пройдет, и не должен быть запущенным кодом JavaScript.)

+0

Конечно, это должно обрабатывать полное удаление любых допустимых блоков сценариев, а допустимый HTML-код должен быть действительным HTML out (минус блоки скриптов). –

+0

Отлично! Огромное спасибо. – tcables

3

Общепризнано, что при попытке разобрать HTML с регулярным выражением является плохой идеей, и даст плохие результаты. Вместо этого вы должны использовать парсер DOM. jQuery отлично обходит вокруг DOM браузера и позволит вам легко удалить все теги <script>.

+5

Хех. Мне нравится ирония использования jQuery для удаления JavaScript. –

+0

В настоящее время я использую C# – tcables

+0

. [HTML Agility Pack] (http://htmlagilitypack.codeplex.com/), по-видимому, является стандартным решением для C#. –

0

Создание собственного анализатора или скриптового детектора HTML - особенно плохая идея, если это делается для предотвращения межсайтового скриптинга. Выполнение этого вручную - это очень плохая идея, потому что существует множество угловых случаев и трюков, которые можно использовать для победы над такой попыткой. Это называется «черным списком», поскольку он пытается удалить небезопасные элементы из HTML, и это в значительной степени обречено на провал.

Гораздо безопаснее использовать процессор белого списка (например, AntiSamy), который разрешает только одобренные элементы путем автоматического выхода из всего остального.

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

Edit:

Теперь, когда мы знаем, что вы используете C#, попробуйте HTMLAgilityPack, как предложено here.

+0

У меня были проблемы с ошибками в пакете гибкости в прошлом, поэтому я стараюсь держаться подальше от него ... но спасибо за предложение. – tcables

+1

Вот еще один: http://www.codeproject.com/KB/cs/ZetaHtmlTidy.aspx –

0

Какой язык вы используете? В качестве общего утверждения регулярные выражения не подходят для синтаксического анализа HTML.

Если вы находитесь на платформе .net, HTML Agility Pack предлагает гораздо лучший парсер.

0

Вы должны использовать настоящий html-парсер для работы. Тем не менее, для простого снятия
блоков скриптов вы можете использовать рудиментарное регулярное выражение, как показано ниже.

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

Однако это не заменит html-процессор. Удачи!

Поиск Regex: (модификаторы - расширены, глобальные, включают в себя новые строки в точке, обратного вызова функ)

(?: 
    <script (?:\s+(?:".*?"|\'.*?\'|[^>]*?)+)? \s*> .*? </script\s*> 
    | </?script (?:\s+(?:".*?"|\'.*?\'|[^>]*?)+)? \s*/?> 
) 
| 
    ( # Capture group 1 
    <!(?:DOCTYPE.*?|--.*?--)> # things that hide html, add more constructs here ... 
) 

Замена код FUNC псевдо:

string callback() { 
    if capture buffer 1 matched 
    return capt buffer 1 
    else return '' 

}

+0

не работает. – tcables

0

ok Я столкнулся с проблемой аналогичный случай, когда мне нужно очистить «богатый текст» (текст с форматированием HTML) из любого возможного javascript-ing.

Есть несколько способов, чтобы добавить JavaScript в HTML:

  • , используя в < сценарий > тег с JavaScript внутри него или путем загрузки файла JavaScript с помощью «SRC» Attribué. ex: <script> maliciousCode(); </скрипт >

  • , используя событие на HTML элемент, такой как "OnLoad" или "OnMouseOver" например: < IMG SRC = "a.jpg" OnLoad = "maliciousCode()" >

  • пути создания гиперссылки, вызывающий яваскрипт код Ex: < A HREF = "JavaScript: maliciousCode()" > ...

Это все, что я могу думать сейчас.

Таким образом, представленный HTML-код необходимо удалить из этих трех случаев. Простым решением было бы искать эти шаблоны с использованием Regex и заменять их на «" или делать все, что захотите.

Это простой код, чтобы сделать это:

public static string CleanHTMLFromScript(string str) 
{ 
    Regex re = new Regex("<script[^>]*>", RegexOptions.IgnoreCase); 
    str = re.Replace(str, ""); 
    re = new Regex("<[a-z][^>]*on[a-z]+=\"?[^\"]*\"?[^>]*>", RegexOptions.IgnoreCase); 
    str = re.Replace(str, ""); 
    re = new Regex("<a\\s+href\\s*=\\s*\"?\\s*javascript:[^\"]*\"[^>]*>", RegexOptions.IgnoreCase); 
    str = re.Replace(str, ""); 
    return(str); 
} 

Этот код берет на себя каких-либо пробелов и кавычек, которые могут или не могут быть добавлены. Кажется, он работает отлично, но не идеально, но он делает трюк. Любые улучшения приветствуются.

Смежные вопросы