In the code below, I try to return arr with details in it, but I think it's empty, because of the request. What can I do to make this work?
module.exports = function getWeather(country) {
var arr = [];
var pageToVisit = "https://www.timeanddate.com/weather/" + country;
console.log("Visiting page " + pageToVisit);
request(pageToVisit, function(error, response, body) {
if (error) {
console.log("Error: " + error);
}
// Check status code (200 is HTTP OK)
console.log("Status code: " + response.statusCode);
if (response.statusCode === 200) {
// Parse the document body
var $ = cheerio.load(body);
console.log("Page title: " + $('title').text());
$('div.bk-focus__qlook').each(function(index) {
var title = $(this).find('div.h2').text().trim();
//var link = $(this).find('div.h1').attr('href');
console.log('title: ' + title);
//console.log(link);
arr.push(title)
});
}
});
return arr;
}
The arr is always empty, and I can't add the title to the arr. How can I wait for it?
I would write a function :
function pagetovisit( parameters if necessary) {
// logic whatever you want to do
}
async function asyncCall() {
/// stock the return value in a var
const result = await pagetovisit();
console.log(result);
// expected output: "resolved"
}
It does not look like that website uses a public-facing weather API. Looks like an pre-rendered HTML page that loads from the server.
The API information does even include weather: https://www.timeanddate.com/services/api/
If you were to return a list of scraped text, you would need to make your function a asynchronous and return the Promise like so:
const parseHTML = (htmlText) =>
new DOMParser().parseFromString(html, 'text/html');
const getWeather = async (country, city) {
var pageToVisit = `https://www.timeanddate.com/weather/${country}/${city}`
console.log(`Visiting page: ${pageToVisit}`);
return fetch(pageToVisit, {
method: 'GET',
headers: {
'Content-Type': 'text/html',
}
})
.then(response => response.text())
.then(parseHTML)
.then(doc =>
[...doc.querySelectorAll('div.bk-focus__qlook')].map(qlook =>
qlook.querySelector('div.h2').textContent.trim()));
};
module.exports = getWeather;
// https://www.timeanddate.com/weather/usa/chicago
const weather = await getWeather('usa', 'chicago'); // Should not be empty
I would ditch this website, because:
thank you all, I use callback fun and it work.
var cheerio = require('cheerio');
var URL = require('url-parse');
var express = require('express');
var country="canada";
module.exports= function getWeather(country,callback){
var arr=[];
arr.push(country)
var pageToVisit = "https://www.timeanddate.com/weather/"+country;
console.log("Visiting page " + pageToVisit);
request(pageToVisit, function(error, response, body) {
if(error) {
callback(error);
}
// Check status code (200 is HTTP OK)
console.log("Status code: " + response.statusCode);
if(response.statusCode === 200) {
// Parse the document body
var $ = cheerio.load(body);
console.log("Page title: " + $('title').text());
$('div.bk-focus__qlook').each(function( index ) {
var temp = $(this).find('div.h2').text().trim();
var wind = $(this).find('p').text().trim();
var index=wind.search("Wind")
wind=wind.substring(index);
arr.push(temp)
arr.push(wind)
});
}
callback(null, arr);
});
}
getWeather(country, function(err, result){
if(err) {console.log(err); }
else {
console.log(result);
}
});