8

PhantomJS で jQuery を実行できません。この回答を見つけました。評価関数内で使用できる変数はありませんが、質問はノードモジュールに関するものであり、私の例ではconsole.log評価関数内でのみ呼び出します。この質問をGitHub にも投稿しました。

以前は、一部のページで次のevaluateコードが実行されませんでした。@b1f56gd4 がいくつかのヘルプを提供したので、メッセージを出力するようになりました。私はそれを実行することはできませんが、今ではこれを見ることができます:

https://login.yahoo.com/のページで、 http://ajax.googleapis.com/ajax/libs/jquery/1.6.1/jquery.min.jsからの安全でないコンテンツが実行されました。

別のドメインから jQuery をロードできず、--local-to-remote-url-access=trueまたは--web-security=falseオプションに違いはありません。

jQueryをローカルにロードしてみます。コードは次のとおりです。

console.log('Loading a web page');
var url = 'https://login.yahoo.com/'; 
var page = require('webpage').create();
console.log('Setting error handling');
page.onConsoleMessage = function (msg) {
    console.log(msg);
};
page.onError = function (msg, trace) {
    console.log(msg);
    trace.forEach(function(item) {
        console.log('  ', item.file, ':', item.line);
    })
    phantom.exit();
}
console.log('Error handling is set');
console.log('Opening page');
page.open(url, function (status) {
    if (status != 'success') {
        console.log('F-' + status);
    } else {
        console.log('S-' + status); 
        //-------------------------------------------------     
        var jsLoc = '';
        jsLoc = 'jquery.min.js'; // to load local
        //jsLoc = 'http://ajax.googleapis.com/ajax/libs/jquery/1.6.1/jquery.min.js'; // to load remote
        var func = function(pg){
            console.log('Function called');
            console.log('Page evaluating');
            console.log(pg);
            pg.evaluate(function() {
                console.log('Page evaluate started');               
                //---
                var loginVar = 'ih5d4hf65465fd45h6@yahoo.com.br';
                var pwdVar = 'itsmypass_445f4hd564hd56f46s'; 
                //---
                $("#login_form #username").value = loginVar;
                $("#login_form #passwd").value = pwdVar;
                //---
            });
            console.log('Rendering');
            pg.render('ystsA.png');
            console.log('Rendered');
        }
        if (typeof jQuery == 'undefined') {  
            console.log('JQuery Loading');  // <<<<==== Execute only until here
            console.log('Source:['+jsLoc+']');
            var rs = page.includeJs(jsLoc, function()  // <<<<===== Fail here, jsLoc was changed to load locally and after tried remotely, i tried use page.injectJs but fail too
            { 
                console.log('JQuery Loaded');  // <<<< ===== Never reach here, no matter if loading local or remote script in include above
                func(page); 
            });
            page.render('ystsB.png');
        } else {
            console.log('JQuery Already Loaded');
            func(page);
            page.render('ystsC.png');
        }
        //-------------------------------------------------
    }
    phantom.exit();
});

@ g4d564w56の回答を読んだ後、JQueryなしですべてを行った後、テキストボックスに入力できますが、ボタンをクリックしてログインフォームに投稿できません。
新しいコードを参照してください。

console.log('Loading a web page');
var url = 'https://login.yahoo.com/'; 
var page = require('webpage').create();
console.log('Setting error handling');
page.onConsoleMessage = function (msg) {
    console.log(msg);
};
page.onError = function (msg, trace) {
    console.log(msg);
    trace.forEach(function(item) {
        console.log('  ', item.file, ':', item.line);
    })
    phantom.exit();
}
console.log('Error handling is set');
console.log('Opening page');
page.open(url, function (status) {
    if (status != 'success') {
        console.log('F-' + status);
    } else {
        console.log('S-' + status); 
        //-------------------------------------------------     
        var jsLoc = '';
        jsLoc = 'jquery.min.js'; // to load local
        //jsLoc = 'http://ajax.googleapis.com/ajax/libs/jquery/1.6.1/jquery.min.js'; // to load remote      
        var act01 = function(pg){
            console.log('Function called');
            console.log('Page evaluating');
            console.log(pg);
            pg.evaluate(function() {
                var getElmById = function(id){
                    return document.getElementById(id);
                }           
                console.log('Page evaluate started');               
               //---
                var loginVar = 'ih5d4hf65465fd45h6@yahoo.com.br';
                var pwdVar = 'itsmypass_445f4hd564hd56f46s'; 
                //---
                getElmById("username").value = loginVar;
                getElmById("passwd").value = pwdVar;
                getElmById("login_form").submit(); /// <<<<==== now its dont work !!!
                //---
            });
            console.log('Rendering');
            pg.render('ystsA.png');
            console.log('Rendered');
        }
        act01(page);
        //-------------------------------------------------
    }
    phantom.exit();
});
4

5 に答える 5

5

この質問は約1年前にすでに回答されていることは知っていますが、回答は実際には問題に対処していませんでした. 以下のエラーの理由:

「 https://login.yahoo.com/のページは、 http://ajax.googleapis.com/ajax/libs/jquery/1.6.1/jquery.min.jsから安全でないコンテンツを実行しまし た。」

ログイン ページが https ページであり、http リソースを読み込もうとしているということですか。URL をhttps://ajax.googleapis.com/ajax/libs/jquery/1.6.1/jquery.min.jsに変更すると、このエラーはなくなります。それを理解するのにしばらく時間がかかりました。

于 2014-05-15T23:58:39.227 に答える
1

@lmeursの回答は非常に優れていますが、機能していません。
答えを使用して、機能的なものを作成しました:)。

var page = new WebPage();
var url = 'http://br.search.yahoo.com';
var stepIndex = 0;

page.onConsoleMessage = function (msg, line, source) { console.log('console> ' + msg); };

page.onAlert = function (msg) { console.log('alert!!> ' + msg); };

function takeShot(){
    console.log("TakingShot"); 
    page.render("step" + stepIndex + ".png");
    console.log("ShotTake");     
}

function step0() {
    console.log("step 00 enter");
    page.evaluate(function() {
        $("form [type='text']").val('its now sunday searching it');
        $("form [type='submit']").submit();     
    });
    console.log("step 00 exit");
}

function step1() {
    console.log("step 01 enter");
    page.evaluate(function() {
        $('#search-result a').each(function(index, link) {
            console.log($(link).attr('href'));
        })
    });
    console.log("step 01 exit");
    phantom.exit(); 
}

page.open(url, function (status) {
    console.log("[- STARTING -]");
    if (status === 'success') {
        var cmd = ""
        page.injectJs('jquery-1.6.1.min.js');
        while(true)
        {
            console.log("Step["+stepIndex+"] starting on ["+new Date()+"]");
            //cmd = "var x = step"+stepIndex+";"
            //console.log(cmd);
            //eval(cmd);
            switch(stepIndex){
                case 0:
                    step0();
                    break;
                case 1:
                    step1();
                    break;                  
            }
            takeShot();
            stepIndex++;
        }       
    }
});
于 2013-07-06T19:14:24.687 に答える
1

PhantomJS が JQuery を読み込めないというよく知られたバグがあり、一部のフォーム データをサーバーに投稿するのが難しくなりますが、この例のように querySelectorAllを使用してのみ要素を選択できます:

于 2013-04-11T03:41:40.680 に答える