我正在试图抓一个网站。我有一个网站,其中有一个select
元素,因此在选择元素后,另一个选择框会动态显示,等等。
我可以使用waitForSelector
方法,但我不知道动态元素的id
,或者我可以使用wait
等待几秒钟。< / p>
但是,对于动态加载的内容,页面将发送ajax请求。我使用函数onResourceRequest
和onResourceReceived
来保持计数,这样无论何时请求资源,我都会增加计数,在事件reource.received
或onResourceError
之后,我可以减少计数计算并检查如果计数为0
,我将继续前进或者等待请求完成。
但是我使用evaluate
方法抓取页面,并且我增加和减少计数的变量在CasperJS上下文中。我应该如何从evaluate
函数访问CasperJS中声明的变量,以便检查是否所有请求都已完成。
答案 0 :(得分:2)
由于evaluate()
是沙箱,因此无法直接访问外部定义的变量。有多种方法可以将数据传递出页面上下文(控制台消息,警报,page.onCallback
,evaluate()
结果),但只有一种方法可以传入数据,直接将数据传递给evaluate()
作为论据。
问题是你如何传递它以便你的脚本有意义。
每当你在需要该变量的页面上下文中执行某些操作时,就可以将其传入。当您在使用该信息之前执行大量异步工作时,这可能无法正常工作,因为它在那时可能是陈旧的。 / p>
每当该计数发生变化时,您可以将该信息放入页面上下文中的全局范围:
// do this inside of the `reource.received` and `onResourceError` events
casper.evaluate(function(count){
window._myCount = count;
}, count);
然后,只要您需要在页面上下文中使用该信息,您只需要访问window._myCount
中已有的信息。
您可以或多或少地自由嵌套waitForSelector()
:
casper.waitForSelector(selector1, function(){
var dynamicId = this.evaluate(function(){
...
return dynId;
});
this.waitForSelector("#" + dynamicId);
});
casper.then(function(){
// this is only executed when the previous `"#" + dynamicId` was found
});