|
ServiceIntegration
Integration with different services
Applies to: PhantomJS 1.5. Important: read first some basic examples, API reference, and test framework integration (Jasmine, QUnit, etc) All of the examples given here are available in the code repository under the sub-directory examples/. External LibraryExternal hosted JavaScript library can be used by PhantomJS easily. See the following code snippet for an example: page.includeJs("http://ajax.googleapis.com/ajax/libs/jquery/1.6.1/jquery.min.js", function() {
// jQuery is loaded, now manipulate the DOM
});The function includeJs behaves just like the usual dynamic script tag loading technique. File UploadThis imagebin.js script uploads an image to imagebin.org, the popular image hosting service. var page = new WebPage(), fname;
if (phantom.args.length !== 1) {
console.log('Usage: imagebin.js filename');
phantom.exit();
} else {
fname = phantom.args[0];
page.open("http://imagebin.org/index.php?page=add", function () {
page.uploadFile('input[name=image]', fname);
page.evaluate(function () {
document.querySelector('input[name=nickname]').value = 'phantom';
document.querySelector('input[name=disclaimer_agree]').click()
document.querySelector('form').submit();
});
window.setTimeout(function () {
phantom.exit();
}, 3000);
});
}JSONPJSONP is easy to do, following the usual loading technique via the src attribute of the script tag. This ipgeocode.js script shows the approximated location based on the network IP address, using freegeoip JSONP API. var cb = function (data) {
var loc = data.city;
if (data.region_name.length > 0)
loc = loc + ', ' + data.region_name;
console.log('IP address: ' + data.ip);
console.log('Estimated location: ' + loc);
phantom.exit();
};
var el = document.createElement('script');
el.src = 'http://freegeoip.net/json/?callback=cb';
document.body.appendChild(el);Example output: IP address: 75.25.137.196 Estimated location: Palo Alto, California YQLIntegration with YQL system can be achieved via the same JSONP approach. The example movies.js here using the query to pull the listed movies from kids-in-mind.com: var cbfunc = function (data) {
globaldata= data;
var list = data.query.results.movie;
list.forEach(function (item) {
console.log(item.title + ' [' + item.rating.MPAA.content + ']');
});
phantom.exit();
};
var el = document.createElement('script');
el.src = 'http://query.yahooapis.com/v1/public/yql?q=select%20*%20from%20movies.kids-in-mind&format=json&env=store%3A%2F%2Fdatatables.org%2Falltableswithkeys&callback=cbfunc';
document.body.appendChild(el);which will give: Chronicles of Narnia: Voyage of the Dawn Treader [PG] The Tourist [PG-13] Black Swan [R] Little Fockers [PG-13] True Grit [PG-13] Somewhere [R] TRON: Legacy [PG] As another example, the following seasonfood.js displays the list of seasonal food from BBC GoodFood query. var cbfunc = function (data) {
var list = data.query.results.results.result,
names = ['January', 'February', 'March',
'April', 'May', 'June',
'July', 'August', 'September',
'October', 'November', 'December'];
list.forEach(function (item) {
console.log([item.name.replace(/\s/ig, ' '), ':',
names[item.atItsBestUntil], 'to',
names[item.atItsBestFrom]].join(' '));
});
phantom.exit();
};
var el = document.createElement('script');
el.src = 'http://query.yahooapis.com/v1/public/yql?q=SELECT%20*%20FROM%20bbc.goodfood.seasonal%3B&format=json&diagnostics=true&env=store%3A%2F%2Fdatatables.org%2Falltableswithkeys&callback=cbfunc';
document.body.appendChild(el);such as: Apricot : September to May Blackberry : September to September Blackcurrant : August to July Blueberry : August to July Bramley apple : December to October Broad beans : September to July XMLInstead of asynchronous XML HTTP request, often it is simpler to load the XML directly into the web page and then use standard DOM scripting and CSS selectors. The following weather.js script displays the weather data and forecast information for a specified location, obtained via Google Gadget Weather. var page = new WebPage(),
address = "Mountain View";
page.onConsoleMessage = function(msg) {
console.log(msg);
};
page.open(encodeURI('http://www.google.com/ig/api?weather=' + address), function (status) {
if (status !== "success") {
console.log("Unable to access network");
} else {
page.evaluate(function() {
if (document.querySelectorAll('problem_cause').length > 0) {
console.log('No data available for ' + address);
} else {
function data (s, e) {
var el;
e = e || document;
el = e.querySelector(s);
return el ? el.attributes.data.value : undefined;
};
console.log('City: ' + data('weather > forecast_information > city'));
console.log('Current condition: ' + data('weather > current_conditions > condition'));
console.log('Temperature: ' + data('weather > current_conditions > temp_f') + ' F');
console.log(data('weather > current_conditions > humidity'));
console.log(data('weather > current_conditions > wind_condition'));
console.log('');
var forecasts = document.querySelectorAll('weather > forecast_conditions');
for (var i = 0; i < forecasts.length; ++i) {
var f = forecasts[i];
console.log(data('day_of_week', f) + ': ' +
data('low', f) + '-' + data('high', f) + ' F ' +
data('condition', f));
}
}
});
}
phantom.exit();
});When it is invoked: phantomjs weather.js The output looks like: City: Mountain View, CA Current condition: Clear Temperature: 50 F Humidity: 80% Wind: N at 0 mph Mon: 47-57 F Partly Cloudy Tue: 49-58 F Showers Wed: 40-53 F Windy Thu: 40-54 F Partly Cloudy Another example herebelow, direction.js, gets driving direction between two locations using Google Directions API. var page = new WebPage(),
origin, dest, steps;
if (phantom.args.length < 2) {
console.log('Usage: direction.js origin destination');
console.log('Example: direction.js "San Diego" "Palo Alto"');
phantom.exit(1);
} else {
origin = phantom.args[0];
dest = phantom.args[1];
page.open(encodeURI('http://maps.googleapis.com/maps/api/directions/xml?origin=' + origin +
'&destination=' + dest + '&units=imperial&mode=driving&sensor=false'), function (status) {
if (status !== 'success') {
console.log('Unable to access network');
} else {
steps = page.content.match(/<html_instructions>(.*)<\/html_instructions>/ig);
if (steps == null) {
console.log('No data available for ' + origin + ' to ' + dest);
} else {
steps.forEach(function (ins) {
ins = ins.replace(/\</ig, '<').replace(/\>/ig, '>');
ins = ins.replace(/\<div/ig, '\n<div');
ins = ins.replace(/<.*?>/g, '');
console.log(ins);
});
console.log('');
console.log(page.content.match(/<copyrights>.*<\/copyrights>/ig).join('').replace(/<.*?>/g, ''));
}
}
phantom.exit();
});
}
When it runs as follows: phantomjs direction.js 'San Diego' 'Palo Alto' it gives the following result: Head south on 8th Ave toward E St Take the 1st left onto E St Turn left at the 3rd cross street onto 11th Ave Continue onto CA-163 N Take exit 7A to merge onto I-805 N toward Los Angeles Merge onto I-5 N Take exit 403B to merge onto CA-152 W/CA-33 N toward Gilroy/Hollister/San Jose Continue to follow CA-152 W Slight right at CA-152 W/Pacheco Pass Hwy Turn left at CA-152 W/Pacheco Pass Rd Merge onto US-101 N via the ramp to San Jose Take exit 402 for Embarcadero Rd toward Oregon Expy Keep right at the fork and merge onto Oregon Expy Turn right at Middlefield Rd Destination will be on the left |
Found that in the Jasmine driver the selector for .finished_at needs to be finished-at, that might have changed in some past release...
I think you might have your fruity months the wrong way round in the YQL example.
@tushar: phantomjs does not have that feature (yet). There is a feature request for it.