23

コンテンツをフェッチし、このコンテンツを次のように追加する ajax 呼び出しを行っています。

$(function(){
    var site = $('input').val();
    $.get('file.php', { site:site }, function(data){
        mas = $(data).find('a');
        mas.map(function(elem, index) {
            divs = $(this).html();
            $('#result').append('' + divs + '');
        })
    }, 'html');
});

問題は、変更abodyても何も得られないことです (エラーはなく、html だけではありません)。体は「a」と同じようにタグだと思いますか?私は何を間違っていますか?

だからこれは私のために働く:

 mas = $(data).find('a');

しかし、これはしません:

 mas = $(data).find('body');
4

5 に答える 5

13

私はこの簡単な解決策で終わった:

var body = data.substring(data.indexOf("<body>")+6,data.indexOf("</body>"));
$('body').html(body);

headやその他のタグでも機能します。

(xml 解析を使用したソリューションはより適切ですが、無効な XML 応答では、「文字列解析」を行う必要があります。)

于 2016-02-02T15:44:31.690 に答える
12

$(data)タグを取得するためにjQuery オブジェクト (つまり ) を介して返された HTML を解析することbodyは、残念ながら失敗する運命にあります。

その理由は、返さdataれるのがstring(try console.log(typeof(data))) であるためです。現在、jQuery のドキュメントによると、複雑な HTML マークアップを含む文字列から jQuery オブジェクトを作成すると、 などのタグbodyが削除される可能性があります。これは、オブジェクトを作成するために HTML マークアップが実際に DOM に挿入され、そのような追加タグを許可できないために発生します。

ドキュメントからの関連引用:

$() にパラメーターとして文字列が渡されると、jQuery はその文字列が HTML のように見えるかどうかを調べます。

[...] 上記の例のように、HTML が属性のない単一のタグよりも複雑な場合、要素の実際の作成はブラウザの innerHTML メカニズムによって処理されます。ほとんどの場合、jQuery は新しい要素を作成し、要素の innerHTML プロパティを、渡された HTML スニペットに設定します。パラメーターに単一のタグ (オプションの終了タグまたはクイック終了) がある場合 — $( "< img / >" ) または $( "< img >" )、$( "< a >< /a >" ) または $( "< a >" ) — jQuery はネイティブ JavaScript createElement() 関数を使用して要素を作成します。

複雑な HTML を渡す場合、一部のブラウザーは、提供された HTML ソースを正確に複製する DOM を生成しない場合があります。前述のように、jQuery はブラウザーの .innerHTML プロパティを使用して、渡された HTML を解析し、現在のドキュメントに挿入します。このプロセス中に、一部のブラウザーは、< html >、< title >、または < head > 要素などの特定の要素を除外します。 . 結果として、挿入された要素は、渡された元の文字列を表していない可能性があります。

于 2013-01-20T09:39:27.293 に答える
6

私は少し実験し、原因をある程度特定したので、私が興味を持っている本当の答えを待っているので、ここに問題を理解するのに役立つハックがあります

$.get('/',function(d){
    // replace the `HTML` tags with `NOTHTML` tags
    // and the `BODY` tags with `NOTBODY` tags
    d = d.replace(/(<\/?)html( .+?)?>/gi,'$1NOTHTML$2>',d)
    d = d.replace(/(<\/?)body( .+?)?>/gi,'$1NOTBODY$2>',d)
    // select the `notbody` tag and log for testing
    console.log($(d).find('notbody').html())
})

編集:さらなる実験

コンテンツをiframeにロードすると、domオブジェクト階層を介してフレームコンテンツにアクセスできるようになります...

// get a page using AJAX
$.get('/',function(d){

    // create a temporary `iframe`, make it hidden, and attach to the DOM
    var frame = $('<iframe id="frame" src="/" style="display: none;"></iframe>').appendTo('body')

    // check that the frame has loaded content
    $(frame).load(function(){

        // grab the HTML from the body, using the raw DOM node (frame[0])
        // and more specifically, it's `contentDocument` property
        var html = $('body',frame[0].contentDocument).html()

        // check the HTML
        console.log(html)

        // remove the temporary iframe
        $("#frame").remove()

    })
})

編集:より多くの研究

contentDocument はwindow.documentiFrame の要素を取得するための標準に準拠した方法のようですが、もちろん IE は標準をあまり気にしないため、これはwindow.document.bodyクロスプラットフォームの方法で iFrame のオブジェクトへの参照を取得する方法です.. .

var iframeDoc = iframe.contentDocument || iframe.contentWindow.document;
var iframeBody = iframeDoc.body;
// or for extra caution, to support even more obsolete browsers
// var iframeBody = iframeDoc.getElementsByTagName("body")[0]

参照: iframe の contentDocument

于 2013-01-20T10:00:53.310 に答える
4

私は何か素晴らしいことを考え出した(私は思う!)

html を文字列として取得しましたか?

var results = //probably an ajax response

以下は、DOM に現在アタッチされている要素とまったく同じように機能する jquery オブジェクトです。

var superConvenient = $($.parseXML(response)).children('html');

から何も削除されませんsuperConvenient! superConvenient.find('body')次のようなこともできます

superConvenient.find('head > script');

superConvenient誰もが慣れ親しんでいるjquery要素とまったく同じように機能します!!!!

ノート

この場合、文字列はJQuery のメソッドに渡されるため、有効な XMLresultsである必要があります。HTML 応答の一般的な機能は、この意味でドキュメントを無効にするタグである可能性があります。このアプローチを使用する前に、タグを削除する必要がある場合があります。また、次のような終了タグのないタグなどの機能にも注意してください。parseXML<!DOCTYPE><!DOCTYPE><!--[if IE 8]>...<![endif]-->

<ul>
    <li>content...
    <li>content...
    <li>content...
</ul>

... およびブラウザーによって寛大に解釈される HTML のその他の機能は、XML パーサーをクラッシュさせます。

于 2014-05-26T19:41:31.400 に答える