2016-12-01 16 views
9

Próbuję użyć CasperJS jako skrobaczki internetowej, a istnieje strona z przyciskami, które będą ładować dane po kliknięciu. Chciałbym najpierw kliknąć wszystkie te przyciski i poczekać, zanim faktycznie wykonam zapytanie, aby pobrać wszystkie niezbędne dane.CasperJS: Jak klikasz na wszystkie wybrane przyciski?

Problem polega na tym, że w przypadku Caspera, casper.thenClick(selector) klika pierwszy element. Ale jak iterować i klikać każdy element na podstawie selektora?

Pamiętaj, że te przyciski nie mają identyfikatorów. Wszystkie mają generyczne selektory klasy.

Przykł.

<h3> 
    <span>Text 1</span> 
    <span> 
     <button class="load-btn">show</button> 
    </span> 
</h3> 
<h3> 
    <span>Text 2</span> 
    <span> 
     <button class="load-btn">show</button> 
    </span> 
</h3> 
<h3> 
    <span>Text 3</span> 
    <span> 
     <button class="load-btn">show</button> 
    </span> 
</h3> 

I z jakiegoś powodu casper.thenClick("h3:contains('text 1') .load-btn") nie działa.

Odpowiedz

4

stworzyłem nową funkcję 'click', można kliknąć na każdy element za pomocą for cyklu:

function click(sel){var event=document.createEvent('MouseEvents');event.initMouseEvent('click',1,1,window,1,0,0,0,0,0,0,0,0,0,null);sel.dispatchEvent(event);} 
var casper = require('casper').create({ 
    verbose: true, 
    logLevel: 'debug', 
    waitTimeout: 5000, 
    userAgent: 'Mozilla/5.0 (X11; Linux x86_64; rv:49.0) Gecko/20100101 Firefox/49.0', 
    viewportSize:{width: 1600, height: 900} 
}); 
casper 
.on("error", function(msg){ this.echo("error: " + msg, "ERROR") }) 
.on("page.error", function(msg, trace){ this.echo("Page Error: " + msg, "ERROR") }) 
.on("remote.message", function(msg){ this.echo("Info: " + msg, "INFO") }) 

.start("http://domu-test-2/node/12", function(){ 
    this.evaluate(function(click){ 
     var i, x = document.querySelectorAll("button.load-btn"); 
     for(i = 0; i < x.length; i++) { 
      click(x[i]); 
     } //'click' for each element 
    }, click); 
}) 
.run(); 

Dzięki tej HTML:

<h3> 
    <span>Text 1</span> 
    <span> 
     <button class="load-btn" onclick='console.log("1")'>show</button> 
    </span> 
</h3> 
<h3> 
    <span>Text 2</span> 
    <span> 
     <button class="load-btn" onclick='console.log("2")'>show</button> 
    </span> 
</h3> 
<h3> 
    <span>Text 3</span> 
    <span> 
     <button class="load-btn" onclick='console.log("3")'>show</button> 
    </span> 
</h3> 

wypisze:

Info: 1 
Info: 2 
Info: 3 

W kolorze zielonym.

+2

jesteś przejazdem w 'funkcję click' od zewnętrznego kontekstu do kontekstu strony. To nie działało z PhantomJS 1.x. Czy to się zmieniło? Byłbym bardzo zaskoczony, jeśli to naprawdę działa tak, jak go opisujesz. –

+1

Przetestowałem to ponownie, wszystko działa dobrze, wersja PhantomJS: 2.1.1 –

2

Możesz spróbować wpaść do DOM za pomocą ewaluacji (zakładam, że strona zawiera jquery).

casper.thenEvaluate(function() { 
    $('button.load-btn').click(); 
}); 

Pamiętaj, że trzeba będzie WAIT za coś pojawiać się później.

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

lub przy użyciu jednego z waitFor function

Powiązane problemy