Closed ahmedhammad closed 7 years ago
Yahoo has made some changes to their API including requiring oAuth. As simpleWeather is pure JavaScript using oAuth isn't an easy option as I don't want people publishing their consumer and secret keys. I'm looking into other API options but honestly not sure when I'll have a replacement.
It has also been up and down a few times today so it's possible it could start working again.
I need use it like temporary module, please show me how to fix it with secret keys!
You can still use the rss feed, like this: http://weather.yahooapis.com/forecastrss?w=WOEID_HERE. Since it's XML, you can parse it as well with jQuery automatically (or use Yahoo to digest their own dog food)
Example code:
var woeid = "26355493";
var $url = "http://query.yahooapis.com/v1/public/yql?callback=?";
$.getJSON($url, {
q: "select * from xml where url=" +
"\"http://weather.yahooapis.com/forecastrss?w=" + woeid + "\"",
format: "json"
}, function (data) {
console.log(data.query.results.rss.channel);
}
);
Just a side node, it's possible to do something better so it'll be futureproof, using OAuth. This requires modifying a bit the code so it first fetch the access token from Yahoo's server, but it'll also imply having to modify simpleWeather instantiation so it includes the Yahoo's developer API as a mandatory parameter. For example about how to do it, see this: https://gist.github.com/hannestyden/563893
I'm not 100% sure Yahoo allow OAuth2 for its api. In all case, it's not very sexy to give the secret keys & token in the JS code from the final user, and Yahoo as some tricks that allows you to avoid this (see this post): http://derek.io/blog/2010/how-to-secure-oauth-in-javascript/
It's unlikely I'll update simpleWeather to work with OAuth. It is not recommended to have secret keys or tokens in client side code as it's not really secret anymore. The initial option would be to provide a PHP proxy but that complicates simpleWeather more than I would like at the moment.
The XML feed is also limited by woeid only so location names and geolocation wouldn't work which I believe is the majority of the simpleWeather use cases.
I have been looking at other options for the data. One might be to use weather.gov but it will be a complete change in data returned and how location works; http://forecast.weather.gov/MapClick.php?lat=38.4247341&lon=-86.9624086&FcstType=json is an option but uses coordinates vs location name. forecast.io API would also require a proxy due to OAuth but it also only gives 1,000 free API calls a day before charging. I'm not sure when I'll have the time to really work on it or whether the weather.gov data will be the best option.
If anybody has recommendations for those wanting an alternate solution to simpleWeather please share. Thanks!
fleeting, can use http://openweathermap.org/ ?
Broke 13 of my apps. Dammit!
The XML RSS looks promising. We can still make it work with geolocation by retrieving woeid from geo.places in a separate call.
The XML solution is working in my case. Thanks for that.
I'm glad the XML feed is a workable solution for some. The geo.places
call will continue to work for getting the woeid until Yahoo rolls out OAuth to it as well.
@fleeting Please read my second comment and the derek's blog, as it's a method to avoid distributing your Yahoo's API key. Basically you'll store the keys/token on Yahoo's servers directly, only referencing them in your request.
Sorry guys, I've tried the XML feed option but can't quite make it work. Can anyone advise as to where exactly the above XML code should go? This is what I'm currently using in my header.php file of my Wordpress install and up until yesterday it worked perfectly:
` $(function() {
$.simpleWeather({
location: '43.623432, -79.386583',
unit: 'c',
success: function(weather) {
html = '<div align="center">' + weather.temp + '°' + weather.units.temp + '<br />' + weather.wind.direction + ' ' + Math.round(weather.wind.speed * 0.540) + 'kts</div>';
$("#weather2").html(html);
},
error: function(error) {
$("#weather2").html('<p>'+error+'</p>');
}
});
});`
Thanks for any help with this,
T
This broke ~150 sites. I really hate that Yahoo isn't more proactive with warnings.
If somebody is interested, this is how I my code looks like now after change to XML/RSS. I'm not using geo.places, so it was a quick fix.
`function getWeatherData() {
var woeid = '2375129';
var weatherURL = 'http://weather.yahooapis.com/forecastrss?w=' + woeid;
$.ajax({
url: "http://query.yahooapis.com/v1/public/yql",
async: true,
data: {
q: "select * from xml where url='" + weatherURL + "'",
format: "json"
},
success: function (data) {
var weather = data.query.results.rss.channel.item;
// Today
$('#condition').find('.weather').addClass('icon-' + weather.condition.code);
$('#conditionText').text(weather.condition.text);
$('#todayHighText').find('span').html(weather.forecast[0].high + '<i class="degree">°</i>');
$('#todayLowText').find('span').html(weather.forecast[0].low + '<i class="degree">°</i>');
$('#todayCurrentText').find('.value').html(weather.condition.temp + '<i class="degree">°</i>');
$('#todayCurrentText').find('.unit').text('F');
// Forecast
$('#day1 .weather').addClass('icon-' + weather.forecast[1].code);
$('#day1 .weekdayHigh').html(weather.forecast[1].high + '<i class="degree">°</i>');
$('#day1 .weekdayLow').html(weather.forecast[1].low + '<i class="degree">°</i>');
$('#day2 .weather').addClass('icon-' + weather.forecast[2].code);
$('#day2 .weekdayHigh').html(weather.forecast[2].high + '<i class="degree">°</i>');
$('#day2 .weekdayLow').html(weather.forecast[2].low + '<i class="degree">°</i>');
$('#day3 .weather').addClass('icon-' + weather.forecast[3].code);
$('#day3 .weekdayHigh').html(weather.forecast[3].high + '<i class="degree">°</i>');
$('#day3 .weekdayLow').html(weather.forecast[3].low + '<i class="degree">°</i>');
$('#weatherContainer').addClass('fadeInDown');
},
error: function () {
$('#weatherContainer').html('No weather data available').addClass('fadeInDown');
}
});
}`
For my needs I'm switching to the weather underground API
Using the XML method proposed by @X-Ryl669 this is a simplified version of the code I used just in case it helps anyone: http://plnkr.co/edit/dClPDtnToMhHqvKpfCzj?p=preview
var zipCode = 90210;
$.ajax({
dataType: "json",
headers: { "Accept": "application/json; odata=verbose" },
url: "https://query.yahooapis.com/v1/public/yql?q=select%20*%20from%20geo.places%20where%20text%3D"+zipCode+"%20limit%201&format=json&env=store%3A%2F%2Fdatatables.org%2Falltableswithkeys",
beforeSend: function(xhr){xhr.setRequestHeader('Accept', 'application/json; odata=verbose');},
success: function(data){
$.getJSON("https://query.yahooapis.com/v1/public/yql?callback=?", {
q: "select * from xml where url=\"https://weather.yahooapis.com/forecastrss?w="+data.query.results.place.locality1.woeid+"\"",
format: "json"
},function (data) {
var weather = data.query.results.rss.channel;
var html = '<div><span class="temperature">'+weather.item.condition.temp+'<span class="degree">°</span><sup>'+weather.units.temperature+'</sup></span><br><span class="wind-chill">Feels like: '+weather.wind.chill+'<span class="degree">°</span></span></div></a>';
$("#weather").html(html);
});
},
});
Was also able to work with XML using code below (thanks X-Ryl669). You will now have a weather object with all the data you need.
My only concern is how often these XML/RSS get updated. Anyone know this?
var woeid = "12772140";
var $url = "http://query.yahooapis.com/v1/public/yql?callback=?";
$.getJSON($url, {
q: "select * from xml where url=" +
"\"http://weather.yahooapis.com/forecastrss?w=" + woeid + "\"",
format: "json"
}, function (data) {
var weather = {
code: data.query.results.rss.channel.item.condition.code,
temp: data.query.results.rss.channel.item.condition.temp,
phrase: data.query.results.rss.channel.item.condition.text
};
weather.temp_alt = Math.round( (weather.temp - 32) * 5 / 9 );
}
);
I have modified Simple Weather to use the new rss and xml solution provided by @X-Ryl669 and @mattferderer. It should work as before, just swap the old script for this one.
EDIT : This no longer works!
(function($) {
"use strict";
function getAltTemp(unit, temp) {
if(unit === 'f') {
return Math.round((5.0/9.0)*(temp-32.0));
} else {
return Math.round((9.0/5.0)*temp+32.0);
}
}
$.extend({
simpleWeather: function(options){
options = $.extend({
location: '',
woeid: '',
unit: 'f',
success: function(weather){},
error: function(message){}
}, options);
if(options.location !== '') {
$.ajax({
dataType: "json",
headers: {"Accept": "application/json; odata=verbose"},
url: "https://query.yahooapis.com/v1/public/yql?format=json&q=select%20woeid%20from%20geo.places(1)%20where%20text%3D%22" + options.location + "%22&format=json&diagnostics=true&env=store%3A%2F%2Fdatatables.org%2Falltableswithkeys&callback=",
beforeSend: function (xhr) {
xhr.setRequestHeader('Accept', 'application/json; odata=verbose');
},
success: function (data) {
if (data !== null && data.query !== null && data.query.results !== null && data.query.results.place !== null && data.query.results.place.woeid !== null) {
var woeid = data.query.results.place.woeid;
getWeatherData(woeid);
} else {
options.error({message: "There was an error retrieving the latest weather information. Please try again.", error: null});
}
}
});
} else if(options.woeid !== '') {
getWeatherData(options.woeid);
} else {
options.error({message: "Could not retrieve weather due to an invalid location."});
return false;
}
function getWeatherData (woeid) {
var now = new Date();
$.getJSON('https://query.yahooapis.com/v1/public/yql?callback=?&rnd='+now.getFullYear()+now.getMonth()+now.getDay()+now.getHours(), {
q: 'select * from xml where url="https://weather.yahooapis.com/forecastrss?w='+woeid+'&u='+options.unit+'"',
format: "json"
},function (data) {
if(data !== null && data.query !== null && data.query.results !== null && data.query.results.rss !== null && data.query.results.rss.channel.description !== 'Yahoo! Weather Error') {
var result = data.query.results.rss.channel,
weather = {},
forecast,
compass = ['N', 'NNE', 'NE', 'ENE', 'E', 'ESE', 'SE', 'SSE', 'S', 'SSW', 'SW', 'WSW', 'W', 'WNW', 'NW', 'NNW', 'N'],
image404 = "https://s.yimg.com/os/mit/media/m/weather/images/icons/l/44d-100567.png";
weather.title = result.item.title;
weather.temp = result.item.condition.temp;
weather.code = result.item.condition.code;
weather.todayCode = result.item.forecast[0].code;
weather.currently = result.item.condition.text;
weather.high = result.item.forecast[0].high;
weather.low = result.item.forecast[0].low;
weather.text = result.item.forecast[0].text;
weather.humidity = result.atmosphere.humidity;
weather.pressure = result.atmosphere.pressure;
weather.rising = result.atmosphere.rising;
weather.visibility = result.atmosphere.visibility;
weather.sunrise = result.astronomy.sunrise;
weather.sunset = result.astronomy.sunset;
weather.description = result.item.description;
weather.city = result.location.city;
weather.country = result.location.country;
weather.region = result.location.region;
weather.updated = result.item.pubDate;
weather.link = result.item.link;
weather.units = {temp: result.units.temperature, distance: result.units.distance, pressure: result.units.pressure, speed: result.units.speed};
weather.wind = {chill: result.wind.chill, direction: compass[Math.round(result.wind.direction / 22.5)], speed: result.wind.speed};
if(result.item.condition.temp < 80 && result.atmosphere.humidity < 40) {
weather.heatindex = -42.379+2.04901523*result.item.condition.temp+10.14333127*result.atmosphere.humidity-0.22475541*result.item.condition.temp*result.atmosphere.humidity-6.83783*(Math.pow(10, -3))*(Math.pow(result.item.condition.temp, 2))-5.481717*(Math.pow(10, -2))*(Math.pow(result.atmosphere.humidity, 2))+1.22874*(Math.pow(10, -3))*(Math.pow(result.item.condition.temp, 2))*result.atmosphere.humidity+8.5282*(Math.pow(10, -4))*result.item.condition.temp*(Math.pow(result.atmosphere.humidity, 2))-1.99*(Math.pow(10, -6))*(Math.pow(result.item.condition.temp, 2))*(Math.pow(result.atmosphere.humidity,2));
} else {
weather.heatindex = result.item.condition.temp;
}
if(result.item.condition.code == "3200") {
weather.thumbnail = image404;
weather.image = image404;
} else {
weather.thumbnail = "https://s.yimg.com/zz/combo?a/i/us/nws/weather/gr/"+result.item.condition.code+"ds.png";
weather.image = "https://s.yimg.com/zz/combo?a/i/us/nws/weather/gr/"+result.item.condition.code+"d.png";
}
weather.alt = {temp: getAltTemp(options.unit, result.item.condition.temp), high: getAltTemp(options.unit, result.item.forecast[0].high), low: getAltTemp(options.unit, result.item.forecast[0].low)};
if(options.unit === 'f') {
weather.alt.unit = 'c';
} else {
weather.alt.unit = 'f';
}
weather.forecast = [];
for(var i=0;i<result.item.forecast.length;i++) {
forecast = result.item.forecast[i];
forecast.alt = {high: getAltTemp(options.unit, result.item.forecast[i].high), low: getAltTemp(options.unit, result.item.forecast[i].low)};
if(result.item.forecast[i].code == "3200") {
forecast.thumbnail = image404;
forecast.image = image404;
} else {
forecast.thumbnail = "https://s.yimg.com/zz/combo?a/i/us/nws/weather/gr/"+result.item.forecast[i].code+"ds.png";
forecast.image = "https://s.yimg.com/zz/combo?a/i/us/nws/weather/gr/"+result.item.forecast[i].code+"d.png";
}
weather.forecast.push(forecast);
}
options.success(weather);
} else {
options.error({message: "There was an error retrieving the latest weather information. Please try again.", error: data.query.results.rss.channel.item.title});
}
});
}
return this;
}
});
})(jQuery);
@rhyshalsey +1, worked immediately for me
One note, it appears to be reporting the wrong weather status. It's 54 degrees and raining here, but shows snowing. Could be an issue with the icons I'm using.
@rhyshalsey, thank you!
@rhyshalsey Thanks from me as well, I was neck deep in other options for my applications. Glad you got this figured out!
@rhyshalsey thanks!! This worked for me as well. I just made the code change and its now working.
@rhyshalsey, you should move the line var now = new Date();
into the function just below, else it's undefined in the function itself where you're using it.
Just a comment, guys: This is only a temporary workaround. As soon as more people will use this, Yahoo is going to protect with oAuth either their RSS feed, either their XML to JSON converter. I still think we need to figure out how to use their weather api with oAuth in pure JS without having to give our reader our own dev API tokens.
Good catch @X-Ryl669, updated the code. I also agree that this should not be considered a long term solution.
I have been trying to get a consumer key for the YDN all day, but I'm being been hit with a "An internal error occurred" when trying to access the YDN apps section. Anyone else getting this error?
@X-Ryl669 Send me a link and I'll try.
I've been getting a "Server Connection Closed" error all day when trying to go to https://developer.yahoo.com/apps/
Trying to create an app gives me some server connection error on submit.
Same error here.
Same for me. I guess their weather API change is currently overloading their "processing" buffers.
With talks of Yahoo trying to sell the majority of their internet business & staff, plus large shareholders trying to remove their entire board, the best path forward may be to find a different weather api. Unfortunately I can't find any that are free, utilize zip codes or city/state/country, and have a high request per hour/day limit.
@mattferderer I'm probably going to fork this and hook this up with weatherunderground's API. 500 calls a day @ 10 a minute max suits my needs. edited, I said "an hour" previously, not by minute.
@webdevbrian +1
@webdevbrian Are you going to cache the response from Weather Underground or do you get less than 10 visitors per hour on your site or am I mistaken in how I read that?
@webdevbrian Where I live, there's only 24 hours a day. So the best I could expect with only 10 call per hour would be 240 calls per day. Did I miss something ?
@X-Ryl669 Whoops, meant to say minute. Here are their limits for their free account. Feel free to dig into it if it'll work for you (and their other packages if you need more and what you'll be paying) See here
Just started my fork, I'm out on vacation next week but I need this working again so probably expect it to be done in a few weeks. I'll ping @fleeting to see what he wants to do? Holler at me buddy. Also, I might be in Boston soon, we should meet up for some :beers: .
@mattferderer I'll probably set a rate limit. I'll need more than 500 a day for my needs, but at least people will be able to throttle it so it doesn't get canned. I'll have to think it over a few margaritas on the beach next week :)
:boat: :sunrise: :sunny: :sunglasses:
I think the difference is the application. I only use it for a digital signage (updates every 5 mins) whereas someone else may use it on a website and may load it 1000's of times a day.
@kgiszewski Correct -- I'll probably just rate limit it which people can define whatever they'd like in the options depending how crazy they want to get, haven't thought to that point yet. Currently mapping the response from wunderground to what @fleeting has, there are a bunch of things to change.
@rhyshalsey Looks like we are starting to get an error on your work around. Was working great until 2 minutes ago. "Unhandled exception at line 53, column 21, 0x800a138f - JavaScript runtime error: Unable to get property 'channel' of undefined or null reference" anyone else seeing this? Doug
@dmcrock, same here
Looks like they're requiring OAuth on the XML feed now. Glad to see Yahoo took the time to implement that fix but still haven't fixed their Developer App section so you can login & create an app to connect through OAuth.
So what? When hundreds of people enter my website, I can not show the weather? This is so absurd. Is there another weather app I can use?
Long time SimpleWeather user, first time commentor. Not sure if others are experiencing this, but it seems like it is only displaying Fahrenheit. Sorry to be a pain, but in Canada we use Celsius.
Otherwise, thanks for all the updating you have been doing to this plugin.
@dmcrock, same here. The workaround provided by @rhyshalsey (by the way, thanks for trying) worked for a few hours until around 5pm'ish EST today (3/24/16).
I am now getting the following console error: Uncaught TypeError: Cannot read property 'channel' of undefined
Yahoo claims the site to create an app works now. I can't verify though.
Yes, it is working now - but their example code doesn't reference the API keys so I'm not sure where we're supposed to pass them.
@rhyshalsey don't work
I think openweathermap.org is only one replacement for the Yahoo API, because it has the best limits (Calls per minute 60). I don't see any other way to make this plugin work again, because as I know there are no public weather APIs without limitations. Even in this way we have to expose keys.
Ok, for those interested, I've started my port with weatherunderground and it's working for my need.
You'll need to register an api key from the Weatherunderground website, and add a apiKey
member to the options of simpleWeather. The woeid does not exist in weather underground, but I've used the "id" they are using. Either you use the location
member of options to specify the location (but it'll make 2 request to WU, one to figure out the id, and the second for the forecast), either you capture the output of the former request on the console, and use that as woeid
. If location
is set to auto
then it takes the IP address of the client for the weather query.
Not everything is ported (feel free to adjust to your need), but for those using metrics system, it works quite well.
(function($) {
"use strict";
function getAltTemp(unit, temp) {
if(unit === 'f') {
return Math.round((5.0/9.0)*(temp-32.0));
} else {
return Math.round((9.0/5.0)*temp+32.0);
}
}
$.extend({
simpleWeather: function(options){
options = $.extend({
location: '',
woeid: '',
unit: 'f',
apiKey: '',
success: function(weather){},
error: function(message){}
}, options);
if(options.location !== '') {
if (options.location == 'auto')
{
$.ajax({
dataType: "json",
headers: {"Accept": "application/json; odata=verbose"},
url: "http://api.wunderground.com/api/"+options.apiKey+"/geolookup/q/autoip.json",
beforeSend: function (xhr) {
xhr.setRequestHeader('Accept', 'application/json; odata=verbose');
},
success: function (data) {
if (data !== null && data.location !== null && data.location.l !== null) {
var query = data.location.l;
console.log("Fetching weather forecast for :" + query);
getWeatherData(query);
} else {
options.error({message: "There was an error retrieving the latest weather information. Please try again.", error: null});
}
}
});
}
else
{
$.ajax({
dataType: "json",
headers: {"Accept": "application/json; odata=verbose"},
url: "http://api.wunderground.com/api/"+options.apiKey+"/geolookup/q/" + options.location + ".json",
beforeSend: function (xhr) {
xhr.setRequestHeader('Accept', 'application/json; odata=verbose');
},
success: function (data) {
if (data !== null && data.location !== null && data.location.l !== null) {
var query = data.location.l;
console.log("Fetching weather forecast for :" + query);
getWeatherData(query);
} else {
options.error({message: "There was an error retrieving the latest weather information. Please try again.", error: null});
}
}
});
}
} else if(options.woeid !== '') {
getWeatherData(options.woeid);
} else {
options.error({message: "Could not retrieve weather due to an invalid location."});
return false;
}
function iconToCode(icon) {
var night = /^nt_/.test(icon);
var i = icon.replace("nt_", "");
switch(i) {
case "chanceflurries": // Chance of Flurries
return 13;
case "chancerain": // Chance of Rain
return 40;
case "chancesleet": // Chance of Freezing Rain
return 10;
case "chancesnow": // Chance of Snow
return 42;
case "chancetstorms": // Chance of Thunderstorms
return 38;
case "clear": // Clear
return night ? 31 : 32;
case "flurries": // Flurries
return 13;
case "fog": // Fog
return 20;
case "hazy": // Haze
return 21;
case "mostlycloudy": // Mostly Cloudy
return night ? 27 : 28;
case "mostlysunny": // Mostly Sunny
return night ? 33 : 34;
case "partlycloudy": // Partly Cloudy
return night ? 29 : 30;
case "partlysunny": // Partly Sunny
return night ? 33 : 34;
case "rain": // Rain
return 11;
case "sleet": // Sleet
return 18;
case "snow": // Snow
return 16;
case "sunny": // Sunny
return 32;
case "tstorms": // Thunderstorms
return 4;
case "cloudy": // Overcast
return 26;
default:
case "unknown": // Unknown
return 3200;
}
}
function padToTwo(number) {
if (number<=99) { number = ("0"+number).slice(-2); }
return number;
}
function getWeatherData (woeid) {
$.getJSON('http://api.wunderground.com/api/' + options.apiKey + '/conditions/astronomy/forecast10day' + woeid + '.json', { format: 'json' }, function(data) {
if(data !== null && data.current_observation !== null && data.sun_phase !== null && data.forecast !== null && data.forecast.simpleforecast !== null && data.forecast.simpleforecast.forecastday !== null) {
var current = data.current_observation,
weather = {},
forecast,
compass = ['N', 'NNE', 'NE', 'ENE', 'E', 'ESE', 'SE', 'SSE', 'S', 'SSW', 'SW', 'WSW', 'W', 'WNW', 'NW', 'NNW', 'N'],
image404 = "https://s.yimg.com/os/mit/media/m/weather/images/icons/l/44d-100567.png";
weather.title = 'Conditions for ' + current.display_location.city;
weather.city = current.display_location.city;
weather.temp = options.unit == 'f' ? current.temp_f : current.temp_c;
weather.humidity = current.relative_humidity.replace("%", "");
weather.pressure = current.pressure_mb;
weather.currently = current.weather;
weather.code = iconToCode(current.icon);
weather.sunrise = data.sun_phase.sunrise.hour + ':' + padToTwo(data.sun_phase.sunrise.minute);
weather.sunset = data.sun_phase.sunset.hour + ':' + padToTwo(data.sun_phase.sunset.minute);
var result = data.forecast.simpleforecast.forecastday;
weather.forecast = [];
for(var i=0;i<Math.min(result.length, 5);i++) {
var forecast = {};
forecast.day = result[i].date.weekday;
forecast.low = result[i].low[options.unit == 'c' ? "celsius" : "fahrenheit"];
forecast.high = result[i].high[options.unit == 'c' ? "celsius" : "fahrenheit"];
forecast.code = iconToCode(result[i].icon);
forecast.text = result[i].conditions;
weather.forecast.push(forecast);
}
weather.todayCode = weather.code;
weather.high = weather.forecast[0].high;
weather.low = weather.forecast[0].low;
weather.text = weather.forecast[0].text;
/* Everything below should be adapted to WU format, but I'm not interested into them.
Refer to https://www.wunderground.com/weather/api/d/docs?d=data/forecast10day for documentation
weather.rising = result.atmosphere.rising;
weather.visibility = result.atmosphere.visibility;
weather.description = result.item.description;
weather.country = result.location.country;
weather.region = result.location.region;
weather.updated = result.item.pubDate;
weather.link = result.item.link;
weather.units = {temp: result.units.temperature, distance: result.units.distance, pressure: result.units.pressure, speed: result.units.speed};
weather.wind = {chill: result.wind.chill, direction: compass[Math.round(result.wind.direction / 22.5)], speed: result.wind.speed};
if(result.item.condition.temp < 80 && result.atmosphere.humidity < 40) {
weather.heatindex = -42.379+2.04901523*result.item.condition.temp+10.14333127*result.atmosphere.humidity-0.22475541*result.item.condition.temp*result.atmosphere.humidity-6.83783*(Math.pow(10, -3))*(Math.pow(result.item.condition.temp, 2))-5.481717*(Math.pow(10, -2))*(Math.pow(result.atmosphere.humidity, 2))+1.22874*(Math.pow(10, -3))*(Math.pow(result.item.condition.temp, 2))*result.atmosphere.humidity+8.5282*(Math.pow(10, -4))*result.item.condition.temp*(Math.pow(result.atmosphere.humidity, 2))-1.99*(Math.pow(10, -6))*(Math.pow(result.item.condition.temp, 2))*(Math.pow(result.atmosphere.humidity,2));
} else {
weather.heatindex = result.item.condition.temp;
}
if(result.item.condition.code == "3200") {
weather.thumbnail = image404;
weather.image = image404;
} else {
weather.thumbnail = "https://s.yimg.com/zz/combo?a/i/us/nws/weather/gr/"+result.item.condition.code+"ds.png";
weather.image = "https://s.yimg.com/zz/combo?a/i/us/nws/weather/gr/"+result.item.condition.code+"d.png";
}
weather.alt = {temp: getAltTemp(options.unit, result.item.condition.temp), high: getAltTemp(options.unit, result.item.forecast[0].high), low: getAltTemp(options.unit, result.item.forecast[0].low)};
if(options.unit === 'f') {
weather.alt.unit = 'c';
} else {
weather.alt.unit = 'f';
}
*/
options.success(weather);
} else {
options.error({message: "There was an error retrieving the latest weather information. Please try again.", error: data.query.results.rss.channel.item.title});
}
});
}
return this;
}
});
})(jQuery);
X-Ryl669 Thank you for posting this! I went to WeatherUnderground and got an API key, but I'm getting this in the console:
XMLHttpRequest cannot load http://api.wunderground.com/api//geolookup/q/Solana%20Beach,%20CA,%20United%20States.json. The 'Access-Control-Allow-Origin' header has a value 'http://www.wunderground.com' that is not equal to the supplied origin. Origin 'http://mydomain.com' is therefore not allowed access.
Am I missing something obvious here?
Simple Weather Gives me the following error: THERE WAS A PROBLEM RETRIEVING THE LATEST WEATHER INFORMATION. Also, I tried the plugin in the website http://simpleweatherjs.com/ and the same result is happen. Please help me to find a solution for it