2016-02-25 46 views
1

我剛開始使用CasperJs,並且我很難調試它,因爲如此多的編碼錯誤似乎會導致腳本退出而不提供錯誤消息。當你使用詳細模式時,你會得到你應該得到的消息,直到有問題的代碼行,並且在那一刻它就會退出。CasperJS中的靜默錯誤

例如,如果我執行代碼:

var casper = require('casper').create({ 
    verbose: true, 
    logLevel: "debug" 
}); 

casper.start('https://www.google.com/#q=stackoverflow', function(){ 

}); 
casper.wait(2000, function(){ 
}); 


casper.then(function() { 
    hrefAr = this.evaluate(getLinks); 
    this.log(hrefAr.length + ' links found', 'info'); 
    this.exit(); 
}); 

casper.run(function() { 
    this.exit(); 
}); 

function getLinks() { 
    var links = document.querySelectorAll('a'); 
    return Array.prototype.map.call(links, function(e) { 
     return e.getAttribute('href'); 
    }); 
} 

我得到如下結果:

...a bunch of info & debug messages, followed by... 
[info] [phantom] Step 4/4 https://www.google.com/search?q=stackoverflow&cad=h (HTTP 200) 
[info] [phantom] 89 links found 
[debug] [phantom] Navigation requested: url=about:blank, type=Other, lock=true, isMainFrame=true 
[debug] [phantom] url changed to "about:blank" 

如果我添加日誌語句的功能getLinks ...

...code as shown above... 
function getLinks() { 
    this.log('getLinks ran', 'info'); 
    var links = document.querySelectorAll('a'); 
...code as shown above... 

...這會導致腳本失敗,如下所示:

...the same info & debug messages... 
[info] [phantom] Step 4/4 https://www.google.com/search?q=stackoverflow&cad=h (HTTP 200) 
...NO LOGS, ECHOS, OR RESULTS PAST THIS POINT, JUST THESE TWO CLOSING STATEMENTS... 
[debug] [phantom] Navigation requested: url=about:blank, type=Other, lock=true, isMainFrame=true 
[debug] [phantom] url changed to "about:blank" 

它不會告訴你任何事情都出錯了,它只是把你送回空白處並結束執行。

有沒有辦法獲得更好的錯誤報告?或者任何錯誤報告?


當我嘗試實施以下使用下面的代碼解決方法:

var casper = require('casper').create({ 
    verbose: true, 
    logLevel: "debug" 
}); 

casper.start('https://www.google.com/#q=stackoverflow', function(){ 

}); 
casper.wait(2000, function(){ 
}); 


casper.then(function() { 
    reportErrors(function() { 
     hrefAr = this.evaluate(getLinks); 
     this.log(hrefAr.length + ' links found', 'info'); 
     this.exit(); 
    }); 
}); 

casper.run(function() { 
    this.exit(); 
}); 

function getLinks() { 

     //this.log('getLinks ran', 'info'); 
     var links = document.querySelectorAll('a'); 
     return Array.prototype.map.call(links, function(e) { 
      return e.getAttribute('href'); 
     }); 

} 

function reportErrors(f) { 
    var ret = null; 
    try { 
    ret = f(); 
    } catch (e) { 
    casper.echo("ERROR: " + e); 
    casper.exit(); 
    } 
    return ret; 
} 

我得到...

...info & debug messages shown above... 
[info] [phantom] Step 4/4 https://www.google.com/search?q=stackoverflow&cad=h (HTTP 200) 
ERROR: TypeError: undefined is not a constructor (evaluating 'this.evaluate(getLinks)') 
--THIS IS WHERE MY LINK COUNT WOULD BE REPORTED 
[debug] [phantom] Navigation requested: url=about:blank, type=Other, lock=true, isMainFrame=true 
[debug] [phantom] url changed to "about:blank" 
+2

而不是'this.evaluate','this.log','this.exit'可以使用'casper.evaluate'等 – Leventix

+0

我也一直在尋找@ NiKo的方法來將console.log事件打印到屏幕上(http://stackoverflow.com/a/11957179/1542008)非常有用。對於像我這樣的新手來說,只需將casper.on聲明粘貼到頁面的底部,並從那裏開始工作。 如果您在PC上(因此沒有casper.log事件的彩色輸出(http://docs.casperjs.org/en/latest/modules/colorizer.html#index-1)),它看起來對於添加casper.on語句更加簡單(對我來說),然後對代碼中的所有日誌消息使用console.log,完全繞過casper.log。 – Rebecca

回答

3

有一個開放PhantomJS issue這一點。

您可以通過包裹每個then &具有reportErrors功能類似的,如繞過它:

function reportErrors(f) { 
    var ret = null; 
    try { 
    ret = f(); 
    } catch (e) { 
    casper.echo("ERROR: " + e); 
    casper.exit(); 
    } 
    return ret; 
} 

casper.then(function() { 
    reportErrors(function() { 
    ... 
    }); 
}); 
+0

謝謝。這對我非常有用,並且發現一行甚至對我沒有疑心的代碼導致了瘋狂的問題。 'CasperError:casper.test屬性只能使用\'casperjs測試\'命令' – Ryan

+0

其實我不得不使用你在這裏編輯的函數版本:http://stackoverflow.com/a/35638319/470749 – Ryan

2

直到PhantomJS 2.X吞嚥錯誤是固定的,你可以嘗試幾件事情:

  • 使用PhantomJS 1.9.8。到目前爲止,底層QtWebKit引擎已經有5年多的歷史了,但它大部分時間仍然運行良好。如果存在SSL/TLS問題,您可以添加命令行選項,如--ignore-ssl-errors=true。通過將PHANTOMJS_EXECUTABLE環境變量設置爲要使用的可執行文件或可執行文件的路徑,CasperJS支持根據當前終端會話的需要更改PhantomJS版本。例如,在Windows上:set PHANTOMJS_EXECUTABLE=phantomjs198(我將它們編號並放在PATH中)。

  • 如果是語法錯誤,那麼您很擔心,那麼首先在您的代碼上運行一個linter。我可以推薦eslint和jshint。

  • 使用其他事件來檢測錯誤(與PhantomJS 1.9.8):resource.errorpage.errorremote.messagecasper.page.onResourceTimeoutExample


關於你的特殊功能。thisreportErrors的回調中沒有意義。您需要綁定另一個對象:

casper.reportErrors = function (f) { 
    var ret = null; 
    try { 
    ret = f.call(this); 
    } catch (e) { 
    this.echo("ERROR: " + e); 
    this.exit(); 
    } 
    return ret; 
} 

,然後你可以使用它像以前一樣:

casper.then(function() { 
    this.reportErrors(function() { 
     hrefAr = this.evaluate(getLinks); 
     this.log(hrefAr.length + ' links found', 'info'); 
     this.exit(); 
    }); 
}); 
+0

這個版本在引入錯誤時會返回錯誤(並且在其他所有錯誤都正確的情況下運行時沒有錯誤)。但是,錯誤始終是「錯誤:TypeError:null不是對象(評估'hrefAr.length')」。當我使用「var test = notdefined;」開始getLinks時就是這種情況當我用「this.log('getLinks ran','info')」開始getLinks時。但至少它告訴我有一個錯誤! – Rebecca

+0

好吧,現在我在運行帶有「var test = notdefined」語句的腳本時,在hrefAr錯誤之前看到錯誤「Error:ReferenceError:Can not find variable:notdefined」。 – Rebecca