lib/barometer/weather_services/wunderground.rb in barometer-0.5.0 vs lib/barometer/weather_services/wunderground.rb in barometer-0.6.1
- old
+ new
@@ -44,76 +44,67 @@
# = Wunderground terms of use
# Unable to locate.
#
class WeatherService::Wunderground < WeatherService
- def self.source_name; :wunderground; end
- def self.accepted_formats
+ #########################################################################
+ # PRIVATE
+ # If class methods could be private, the remaining methods would be.
+ #
+
+ def self._source_name; :wunderground; end
+ def self._accepted_formats
[:zipcode, :postalcode, :icao, :coordinates, :geocode]
end
# these are the icon codes that indicate "wet", used by wet? function
- def self.wet_icon_codes
+ def self._wet_icon_codes
%w(flurries rain sleet snow tstorms nt_flurries nt_rain nt_sleet nt_snow nt_tstorms chancerain chancetstorms)
end
# these are the icon codes that indicate "sun", used by sunny? function
- def self.sunny_icon_codes
+ def self._sunny_icon_codes
%w(clear mostlysunny partlysunny sunny partlycloudy)
end
- def self._measure(measurement, query, metric=true)
- raise ArgumentError unless measurement.is_a?(Data::Measurement)
- raise ArgumentError unless query.is_a?(Barometer::Query)
- measurement.source = self.source_name
-
- begin
- current_result = self.get_current(query.q)
- measurement.current = self.build_current(current_result, metric)
- rescue Timeout::Error => e
- return measurement
- end
-
- begin
- forecast_result = self.get_forecast(query.q)
- measurement.forecast = self.build_forecast(forecast_result, metric)
- rescue Timeout::Error => e
- return measurement
- end
-
- measurement.location = self.build_location(current_result)
- measurement.station = self.build_station(current_result)
- measurement.timezone = self.build_timezone(forecast_result)
-
- if current_result["credit"] && current_result["credit_URL"]
- measurement.links[current_result["credit"]] = current_result["credit_URL"]
- end
-
- sun = nil
- if measurement.current
- sun = self.build_sun(forecast_result, measurement.timezone)
- measurement.current.sun = sun
- end
+ def self._build_extra(measurement, result, metric=true)
+ #raise ArgumentError unless measurement.is_a?(Data::Measurement)
+ #raise ArgumentError unless query.is_a?(Barometer::Query)
+
# use todays sun data for all future days
- if measurement.forecast && sun
+ if measurement.forecast && measurement.current.sun
measurement.forecast.each do |forecast|
- forecast.sun = sun
+ forecast.sun = measurement.current.sun
end
end
- local_time = measurement.timezone ? Data::LocalTime.parse(
- measurement.timezone.utc_to_local(Time.now.utc)
- ) : nil
- measurement.measured_at = local_time
- measurement.current.current_at = local_time
-
measurement
end
+
+ def self._parse_full_timezone(data)
+ raise ArgumentError unless data.is_a?(Hash)
+ if data && data['simpleforecast'] &&
+ data['simpleforecast']['forecastday'] &&
+ data['simpleforecast']['forecastday'].first &&
+ data['simpleforecast']['forecastday'].first['date']
+ Data::Zone.new(
+ data['simpleforecast']['forecastday'].first['date']['tz_long']
+ )
+ end
+ end
- def self.build_current(data, metric=true)
+ def self._build_links(data)
+ links = {}
+ if data["credit"] && data["credit_URL"]
+ links[data["credit"]] = data["credit_URL"]
+ end
+ links
+ end
+
+ def self._build_current(data, metric=true)
raise ArgumentError unless data.is_a?(Hash)
- current = Data::CurrentMeasurement.new
+ current = Measurement::Current.new
current.updated_at = Data::LocalDateTime.parse(data['observation_time']) if data['observation_time']
current.humidity = data['relative_humidity'].to_i
current.icon = data['icon'] if data['icon']
current.temperature = Data::Temperature.new(metric)
@@ -140,19 +131,19 @@
current.visibility << [data['visibility_km'], data['visibility_mi']]
current
end
- def self.build_forecast(data, metric=true)
+ def self._build_forecast(data, metric=true)
raise ArgumentError unless data.is_a?(Hash)
- forecasts = []
+ forecasts = Measurement::ForecastArray.new
# go through each forecast and create an instance
if data && data['simpleforecast'] &&
data['simpleforecast']['forecastday']
data['simpleforecast']['forecastday'].each do |forecast|
- forecast_measurement = Data::ForecastMeasurement.new
+ forecast_measurement = Measurement::Forecast.new
forecast_measurement.icon = forecast['icon']
forecast_measurement.date = Date.parse(forecast['date']['pretty'])
forecast_measurement.pop = forecast['pop'].to_i
forecast_measurement.high = Data::Temperature.new(metric)
@@ -164,12 +155,12 @@
forecasts << forecast_measurement
end
end
forecasts
end
-
- def self.build_location(data)
+
+ def self._build_location(data, geo=nil)
raise ArgumentError unless data.is_a?(Hash)
location = Data::Location.new
if data['display_location']
location.name = data['display_location']['full']
location.city = data['display_location']['city']
@@ -181,11 +172,11 @@
location.longitude = data['display_location']['longitude']
end
location
end
- def self.build_station(data)
+ def self._build_station(data)
raise ArgumentError unless data.is_a?(Hash)
station = Data::Location.new
station.id = data['station_id']
if data['observation_location']
station.name = data['observation_location']['full']
@@ -198,71 +189,74 @@
station.longitude = data['observation_location']['longitude']
end
station
end
- def self.build_timezone(data)
+ def self._build_sun(data)
raise ArgumentError unless data.is_a?(Hash)
- timezone = nil
- if data && data['simpleforecast'] &&
- data['simpleforecast']['forecastday'] &&
- data['simpleforecast']['forecastday'].first &&
- data['simpleforecast']['forecastday'].first['date']
- timezone = Data::Zone.new(
- data['simpleforecast']['forecastday'].first['date']['tz_long']
- )
- end
- timezone || Data::Zone.new(nil)
- end
-
- def self.build_sun(data, timezone)
- raise ArgumentError unless data.is_a?(Hash)
- raise ArgumentError unless timezone.is_a?(Data::Zone)
sun = nil
if data
if data['moon_phase']
- if data['moon_phase']['sunrise']
- rise = Data::LocalTime.new(
- data['moon_phase']['sunrise']['hour'].to_i,
- data['moon_phase']['sunrise']['minute'].to_i
- )
- end
- if data['moon_phase']['sunset']
- set = Data::LocalTime.new(
- data['moon_phase']['sunset']['hour'].to_i,
- data['moon_phase']['sunset']['minute'].to_i
- )
- end
-
- sun = Data::Sun.new(
- rise,
- set
- )
+ rise = Data::LocalTime.new(
+ data['moon_phase']['sunrise']['hour'].to_i,
+ data['moon_phase']['sunrise']['minute'].to_i
+ ) if data['moon_phase']['sunrise']
+ set = Data::LocalTime.new(
+ data['moon_phase']['sunset']['hour'].to_i,
+ data['moon_phase']['sunset']['minute'].to_i
+ ) if data['moon_phase']['sunset']
+ sun = Data::Sun.new(rise,set)
end
end
sun || Data::Sun.new
end
+ # override default _fetch behavior
+ # this service requires TWO seperate http requests (one for current
+ # and one for forecasted weather) ... combine the results
+ #
+ def self._fetch(query, metric=true)
+ result = []
+ result << _fetch_current(query)
+ result << _fetch_forecast(query)
+ result
+ end
+
# use HTTParty to get the current weather
- def self.get_current(query)
+ #
+ def self._fetch_current(query)
return unless query
+ puts "fetch wunderground current: #{query.q}" if Barometer::debug?
self.get(
"http://api.wunderground.com/auto/wui/geo/WXCurrentObXML/index.xml",
- :query => {:query => query},
+ :query => {:query => query.q},
:format => :xml,
:timeout => Barometer.timeout
)['current_observation']
end
# use HTTParty to get the forecasted weather
- def self.get_forecast(query)
+ #
+ def self._fetch_forecast(query)
return unless query
+ puts "fetch wunderground forecast: #{query.q}" if Barometer::debug?
self.get(
"http://api.wunderground.com/auto/wui/geo/ForecastXML/index.xml",
- :query => {:query => query},
+ :query => {:query => query.q},
:format => :xml,
:timeout => Barometer.timeout
)['forecast']
end
+
+ # since we have two sets of data, override these calls to choose the
+ # right set of data
+ #
+ def self._current_result(data); data[0]; end
+ def self._forecast_result(data=nil); data[1]; end
+ def self._location_result(data=nil); data[0]; end
+ def self._station_result(data=nil); data[0]; end
+ def self._links_result(data=nil); data[0]; end
+ def self._sun_result(data=nil); data[1]; end
+ def self._timezone_result(data=nil); data[1]; end
end
end
\ No newline at end of file