web-dev-qa-db-ja.com

JS正規表現を使用してHTMLからすべてのスクリプトタグを削除する

pastebinでこのHTMLからスクリプトタグを削除したい

http://Pastebin.com/mdxygM0a

以下の正規表現を使ってみました

html.replace(/<script.*>.*<\/script>/ims, " ")

ただし、html内のすべてのスクリプトタグは削除されません。インラインスクリプトのみを削除します。すべてのスクリプトタグ(インラインおよびマルチライン)を削除できる正規表現が必要です。私のサンプルでテストが実行されれば非常にありがたいです http://Pastebin.com/mdxygM0a

ありがとう

59
Kennedy

正規表現を使用してHTMLマークアップを削除しようとすると問題が発生します。スクリプトまたは属性値として何が入っているのかわかりません。 1つの方法は、divのinnerHTMLとして挿入し、スクリプト要素を削除してinnerHTMLを返すことです。

  function stripScripts(s) {
    var div = document.createElement('div');
    div.innerHTML = s;
    var scripts = div.getElementsByTagName('script');
    var i = scripts.length;
    while (i--) {
      scripts[i].parentNode.removeChild(scripts[i]);
    }
    return div.innerHTML;
  }

alert(
 stripScripts('<span><script type="text/javascript">alert(\'foo\');<\/script><\/span>')
);

現在、innerHTMLプロパティを使用して挿入された場合、ブラウザはスクリプトを実行せず、特に要素がドキュメントに追加されないため、おそらく実行されないことに注意してください。

85
RobG

jQueryは正規表現を使用してスクリプトタグを削除する場合があり、その開発者にはそうする正当な理由があると確信しています。おそらく一部のブラウザは、innerHTMLを使用してスクリプトを挿入するときにスクリプトを実行します

正規表現は次のとおりです。

/<script\b[^<]*(?:(?!<\/script>)<[^<]*)*<\/script>/gi

そして、人々が「HTMLの正規表現は悪」と叫ぶ前に: はい、そうです -しかし、スクリプトタグの場合、特別な動作のため安全です-<script>セクションは、この位置で終了しない限り、</script>を含むことはできません。したがって、正規表現と一致させることは簡単に可能です。ただし、簡単に見ると、上記の正規表現は終了タグ内の末尾の空白を考慮していないため、</script   などが引き続き機能するかどうかをテストする必要があります。

100
ThiefMaster

正規表現は打ち負かすことができますが、DOMに挿入したくないHTMLの文字列バージョンがある場合は、最良のアプローチかもしれません。次のような処理を行うためにループに入れたい場合があります。

<scr<script>Ha!</script>ipt> alert(document.cookie);</script>

上記のjquery正規表現を使用して、次のことを行いました。

var SCRIPT_REGEX = /<script\b[^<]*(?:(?!<\/script>)<[^<]*)*<\/script>/gi;
while (SCRIPT_REGEX.test(text)) {
    text = text.replace(SCRIPT_REGEX, "");
}
43
Conrad Damon

この正規表現も動作するはずです:

<script(?:(?!\/\/)(?!\/\*)[^'"]|"(?:\\.|[^"\\])*"|'(?:\\.|[^'\\])*'|\/\/.*(?:\n)|\/\*(?:(?:.|\s))*?\*\/)*?<\/script>

次のような「問題のある」変数文字列を持つこともできます。

<script type="text/javascript">
   var test1 = "</script>";
   var test2 = '\'</script>';
   var test1 = "\"</script>";
   var test1 = "<script>\"";
   var test2 = '<scr\'ipt>';
   /* </script> */
   // </script>
   /* ' */
   // var foo=" '
</script>

JQueryとPrototypeはこれらのもので失敗するようです...

17年7月31日編集: a)パフォーマンス向上のための非キャプチャグループ(および空のグループなし)、およびb)JavaScriptコメントのサポートを追加しました。

12
spaark

Regexベースのスクリプトタグクリーンアップに頼る必要があるときはいつでも。少なくとも次の形式で終了タグに空白を追加します

</script\s*>

そうでなければ

<script>alert(666)</script   >

タグ名の後に続くスペースが有効なため、残ります。

10
neongrau

なぜjQuery.parseHTML() http://api.jquery.com/jquery.parsehtml/ を使用しないのですか?

4
shao

私の場合、ページタイトルを解析する必要があり、スクリプトを実行することを除いて、jQueryのその他すべての長所が必要です。うまくいくと思われる私のソリューションは次のとおりです。

        $.get('/somepage.htm', function (data) {
            // excluded code to extract title for simplicity
            var bodySI = data.indexOf('<body>') + '<body>'.length,
                bodyEI = data.indexOf('</body>'),
                body = data.substr(bodySI, bodyEI - bodySI),
                $body;

            body = body.replace(/<script[^>]*>/gi, ' <!-- ');
            body = body.replace(/<\/script>/gi, ' --> ');

            //console.log(body);

            $body = $('<div>').html(body);
            console.log($body.html());
        });

この種類のショートカットは、スクリプトのタグとコンテンツを削除しようとしていないため、スクリプトを心配しています。代わりに、スクリプトの宣言を区切るコメントがあるため、それらをスキームをレンダリングするコメントに置き換えて役に立たないようにします。

それが私にも役立つので、それでも問題が発生するかどうかを教えてください。

1
Jason Sebring

一部のHTMLテキストからすべてのJavaScriptコードを削除する場合は、<script>タグだけでは十分ではありません。JavaScriptは「onclick」、「onerror」、「href」、およびその他の属性に引き続き存在できるからです。

このすべてを処理するこのnpmモジュールを試してください。 https://www.npmjs.com/package/strip-js

1
Shivanshu Goyal

あなたが試すことができます

$("your_div_id").remove();  

または

 $("your_div_id").html(""); 
0
Pooja Roy

さまざまな要素を取り除くために使用できるさまざまなシェルスクリプトを次に示します。

# doctype
find . -regex ".*\.\(html\|py\)$" -type f -exec sed -i "s/<\!DOCTYPE\s\+html[^>]*>/<\!DOCTYPE html>/gi" {} \;

# meta charset
find . -regex ".*\.\(html\|py\)$" -type f -exec sed -i "s/<meta[^>]*content=[\"'][^\"']*utf-8[\"'][^>]*>/<meta charset=\"utf-8\">/gi" {} \;

# script text/javascript
find . -regex ".*\.\(html\|py\)$" -type f -exec sed -i "s/\(<script[^>]*\)\(\stype=[\"']text\/javascript[\"']\)\(\s\?[^>]*>\)/\1\3/gi" {} \;

# style text/css
find . -regex ".*\.\(html\|py\)$" -type f -exec sed -i "s/\(<style[^>]*\)\(\stype=[\"']text\/css[\"']\)\(\s\?[^>]*>\)/\1\3/gi" {} \;

# html xmlns
find . -regex ".*\.\(html\|py\)$" -type f -exec sed -i "s/\(<html[^>]*\)\(\sxmlns=[\"'][^\"']*[\"']\)\(\s\?[^>]*>\)/\1\3/gi" {} \;

# html xml:lang
find . -regex ".*\.\(html\|py\)$" -type f -exec sed -i "s/\(<html[^>]*\)\(\sxml:lang=[\"'][^\"']*[\"']\)\(\s\?[^>]*>\)/\1\3/gi" {} \;
0
davidcondrey

これを試して:

var text = text.replace(/<script[^>]*>(?:(?!<\/script>)[^])*<\/script>/g, "")
0
surinder singh

/(?:(?!</ s\w)<[^ <] </ s\w */gi; -と組み合わせて任意のシーケンスを削除します

0
Blackening