Передайте аргументы со страницы.оценивать
Я использую страницу PhantomJS.оцените (), чтобы сделать некоторые выскабливание. Моя проблема заключается в том, что код, который я передаю на страницу webkit, изолирован и поэтому не имеет доступа к переменным моего основного фантомного скрипта. Это делает его трудно сделать выскабливание код универсальный.
page.open(url, function() {
var foo = 42;
page.evaluate(function() {
// this code has no access to foo
console.log(foo);
});
}
Как я могу вставить аргументы на страницу?
8 ответов:
у меня была именно эта проблема. Это можно сделать с небольшим обманом, потому что
page.evaluate
также может принимать строку.есть несколько способов сделать это, но я использую обертку под названием
evaluate
, который принимает дополнительные параметры для передачи функции, которая должна быть оценена на стороне webkit. Вы бы использовали его так:page.open(url, function() { var foo = 42; evaluate(page, function(foo) { // this code has now has access to foo console.log(foo); }, foo); });
и вот это
evaluate()
функция:/* * This function wraps WebPage.evaluate, and offers the possibility to pass * parameters into the webpage function. The PhantomJS issue is here: * * http://code.google.com/p/phantomjs/issues/detail?id=132 * * This is from comment #43. */ function evaluate(page, func) { var args = [].slice.call(arguments, 2); var fn = "function() { return (" + func.toString() + ").apply(this, " + JSON.stringify(args) + ");}"; return page.evaluate(fn); }
изменение было нажато, и теперь вы можете использовать его как
page.open(url, function() { var foo = 42; page.evaluate( function(foo) { // this code has now has access to foo console.log(foo); }, foo); }
подробности толчка здесь:https://github.com/ariya/phantomjs/commit/81794f9096
другая возможность: передайте переменные с url-адресом. Например, передать объект x
// turn your object "x" into a JSON string var x_json = JSON.stringify(x); // add to existing url // you might want to check for existing "?" and add with "&" url += '?' + encodeURIComponent(x_json); page.open(url, function(status){ page.evaluate(function(){ // retrieve your var from document URL - if added with "&" this needs to change var x_json = decodeURIComponent(window.location.search.substring(1)); // evil or not - eval is handy here var x = eval('(' + x_json + ')'); )} });
есть решение, которое работает с PhantomJS 0.9.2 и 0.2.0:
page.evaluate( function (aa, bb) { document.title = aa + "/" + bb;}, //the function function (result) {}, // a callback when it's done "aaa", //attr 1 "bbb"); //attr 2
вы можете передать аргументы в функцию в качестве аргументов на страницу.оценивать.
пример:
page.evaluate(function(arg1, arg2){ console.log(arg1); //Will print "hi" console.log(arg2); //Will print "there" }, "hi", "there");
это работает для меня:
page.evaluate("function() {document.body.innerHTML = '" + size + uid + "'}");
означает поставить все как строку. Во всяком случае, позже это станет строкой. Проверьте источник библиотеки.
в то время как вы можете передать аргументы в оценить (функция, arg1, arg2,...), это часто немного громоздким. Особенно в тех случаях, когда передается несколько переменных или, что еще хуже, функций.
чтобы обойти это препятствие, можно использовать injectJs (filename) вместо.
page.open(url, function() { if ( webpage.injectJs('my_extra_functionality.js') ) { page.evaluate( function() { // this code has access to foo and also myFunction(); console.log(foo); console.log(myFunction()); }); } else { console.log("Failed to inject JS"); } }
здесь
my_extra_functionality.js
- это локальный файл в том же каталоге:var foo = 42; var myFunction = function(){ return "Hello world!"; }