wunderground_ruby 0.2.0 → 0.3.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/README.markdown +18 -14
- data/VERSION +1 -1
- data/lib/wunderground.rb +8 -7
- data/test/test_wunderground.rb +42 -36
- data/wunderground_ruby.gemspec +1 -1
- metadata +22 -22
data/README.markdown
CHANGED
@@ -36,13 +36,16 @@ Check out below and test file for more examples.
|
|
36
36
|
|
37
37
|
Standard request breakdown:
|
38
38
|
|
39
|
-
|
39
|
+
wrapper_instance.get_[feature]_and_[another feature]_for("location string",optional: "hash", values: "at the end")
|
40
40
|
|
41
41
|
##Optional Hash
|
42
42
|
|
43
|
-
This ugly little guy handles the nonconformists in Wunderground's API request structure
|
43
|
+
This ugly little guy handles the nonconformists in Wunderground's API request structure and the pervasive request timeout option.
|
44
|
+
Luckily there are only three of these baddies, and only if you need them. (details below)
|
44
45
|
|
45
|
-
optional_hash = {lang: "FR", geo_ip:"127.0.0.1"}
|
46
|
+
optional_hash = {lang: "FR", geo_ip:"127.0.0.1", timeout: 20}
|
47
|
+
|
48
|
+
Note: If needing to use these options, please place them as the last parameter(s) to the method call.
|
46
49
|
|
47
50
|
Can you think of a better way to handle these? Pull requests welcome.
|
48
51
|
|
@@ -72,7 +75,7 @@ Any location string that Wunderground accepts will pass straight through this wr
|
|
72
75
|
|
73
76
|
For geocoding a specific ip address as the location, just provide an IP like this:
|
74
77
|
|
75
|
-
w_api.get_alerts_for(
|
78
|
+
w_api.get_alerts_for(geo_ip: "127.0.0.1")
|
76
79
|
|
77
80
|
This was the quickest workaround to the non-conformity of the auto_ip request format.
|
78
81
|
|
@@ -81,14 +84,14 @@ This was the quickest workaround to the non-conformity of the auto_ip request fo
|
|
81
84
|
|
82
85
|
Because the Language modifier in Wunderground's request structure uses a colon, which doesn't jive with the method_missing design, adding a specific language to one request can be done like this:
|
83
86
|
|
84
|
-
w_api.get_forecast_for(
|
87
|
+
w_api.get_forecast_for("France","Paris", lang 'FR')
|
85
88
|
|
86
89
|
Also, you can set the default language in the constructor or with a setter.
|
87
90
|
|
88
|
-
w_api = Wunderground.new("apikey",
|
91
|
+
w_api = Wunderground.new("apikey",language: "FR")
|
89
92
|
w_api.language = 'FR'
|
90
93
|
w_api.get_forecast_for("France","Paris") #automatically includes /lang:FR/ in the request url, so results will be in French
|
91
|
-
w_api.get_forecast_for(
|
94
|
+
w_api.get_forecast_for("France","Paris",lang: 'DE') #this will override the French(FR) default with German(DE)
|
92
95
|
|
93
96
|
##History and Planner Helpers
|
94
97
|
|
@@ -101,21 +104,22 @@ to get the history/planner data for this date/location. You may enjoy more flexi
|
|
101
104
|
|
102
105
|
w_api.get_history_for("20101010","AL","Birmingham")
|
103
106
|
w_api.get_history_for(1.year.ago,"33909")
|
104
|
-
w_api.get_history_for(Date.now,
|
105
|
-
w_api.get_history_for(Date.now,
|
107
|
+
w_api.get_history_for(Date.now, "France/Paris",lang: "FR")
|
108
|
+
w_api.get_history_for(Date.now, geo_ip:"123.4.5.6", lang: "FR")
|
106
109
|
w_api.get_planner_for("03150323","AL","Gulf Shores")
|
107
|
-
w_api.get_planner_for(Time.now,Time.now+7.days,
|
110
|
+
w_api.get_planner_for(Time.now,Time.now+7.days, geo_ip: "10.0.0.1")
|
108
111
|
w_api.get_planner_for(Time.now,Time.now+7.days,"33030")
|
109
112
|
|
110
|
-
.get_history_for and .get_planner_for accepts a string or any Date/Time/DateTime-like object that responds to .strftime
|
113
|
+
.get_history_for and .get_planner_for accepts a preformatted string or any Date/Time/DateTime-like object that responds to .strftime to auto-format the date.
|
111
114
|
|
112
115
|
|
113
|
-
###
|
116
|
+
### Request Timeout
|
114
117
|
|
115
|
-
wunderground_ruby defaults to a 30 second timeout. You can optionally set your own timeout (in seconds) like so:
|
118
|
+
wunderground_ruby defaults to a 30 second timeout. You can optionally set your own timeout (in seconds) in three ways like so:
|
116
119
|
|
117
|
-
w_api = Wunderground.new("apikey",
|
120
|
+
w_api = Wunderground.new("apikey",timeout: 60)
|
118
121
|
w_api.timeout = 5
|
122
|
+
w_api.get_history_for(1.year.ago, geo_ip: '127.0.0.1', timeout:60)
|
119
123
|
|
120
124
|
|
121
125
|
### Error Handling
|
data/VERSION
CHANGED
@@ -1 +1 @@
|
|
1
|
-
0.
|
1
|
+
0.3.0
|
data/lib/wunderground.rb
CHANGED
@@ -36,9 +36,9 @@ class Wunderground
|
|
36
36
|
|
37
37
|
protected
|
38
38
|
|
39
|
-
def call(method,
|
39
|
+
def call(method, timeout)
|
40
40
|
raise MissingAPIKey if @api_key.nil?
|
41
|
-
response = self.class.get(base_api_url << method, :timeout => @timeout)
|
41
|
+
response = self.class.get(base_api_url << method, :timeout => (timeout || @timeout))
|
42
42
|
begin
|
43
43
|
response = JSON.parse(response.body)
|
44
44
|
rescue
|
@@ -56,12 +56,13 @@ protected
|
|
56
56
|
raise NoMethodError, "undefined method: #{method} for Wunderground" unless method.to_s.start_with?("get_") and method.to_s.end_with?("_for")
|
57
57
|
url = method.to_s.gsub("get_","").gsub("_for","").gsub("_and_","/")
|
58
58
|
url << "/lang:#{@language}" if @language
|
59
|
-
if args
|
60
|
-
|
61
|
-
|
62
|
-
args.
|
59
|
+
if args.last.instance_of? Hash
|
60
|
+
opts = args.pop
|
61
|
+
url = url.sub(/\/lang:.*/,'') and url << "/lang:#{opts[:lang]}" if opts[:lang]
|
62
|
+
ip_address = opts[:geo_ip] and args.push("autoip") if opts[:geo_ip]
|
63
|
+
timeout = opts[:timeout]
|
63
64
|
end
|
64
|
-
call(url <<'/q/'<< args.join('/') << ".json" << (ip_address
|
65
|
+
call(url <<'/q/'<< args.join('/') << ".json" << (ip_address ? "?geo_ip=#{ip_address}" : ''),timeout)
|
65
66
|
end
|
66
67
|
|
67
68
|
class << self
|
data/test/test_wunderground.rb
CHANGED
@@ -20,15 +20,11 @@ class TestWunderground < Test::Unit::TestCase
|
|
20
20
|
@wunderground = Wunderground.new(@api_key)
|
21
21
|
assert_equal(@api_key, @wunderground.api_key)
|
22
22
|
end
|
23
|
-
should 'set timeout in constructor' do
|
24
|
-
@wunderground = Wunderground.new(@api_key,
|
23
|
+
should 'set timeout and language in constructor' do
|
24
|
+
@wunderground = Wunderground.new(@api_key,timeout: 60, language: 'FR')
|
25
25
|
assert_equal(60,@wunderground.timeout)
|
26
|
-
end
|
27
|
-
should 'set language in constructor' do
|
28
|
-
@wunderground = Wunderground.new(@apikey,{language:"FR"})
|
29
26
|
assert_equal('FR',@wunderground.language)
|
30
27
|
end
|
31
|
-
|
32
28
|
should "set an API key from the 'WUNDERGROUND_API_KEY' ENV variable" do
|
33
29
|
ENV['WUNDERGROUND_API_KEY'] = @api_key
|
34
30
|
@wunderground = Wunderground.new
|
@@ -59,9 +55,8 @@ class TestWunderground < Test::Unit::TestCase
|
|
59
55
|
|
60
56
|
context "api url" do
|
61
57
|
setup do
|
62
|
-
@wunderground = Wunderground.new
|
63
|
-
@
|
64
|
-
@url = "http://api.wunderground.com/api/"
|
58
|
+
@wunderground = Wunderground.new("123")
|
59
|
+
@url = "http://api.wunderground.com/api/123/"
|
65
60
|
end
|
66
61
|
should "raise exception at empty api key" do
|
67
62
|
@wunderground.api_key=nil
|
@@ -72,83 +67,94 @@ class TestWunderground < Test::Unit::TestCase
|
|
72
67
|
end
|
73
68
|
|
74
69
|
should "contain api key" do
|
75
|
-
expect_get(@url+"
|
70
|
+
expect_get(@url+"forecast/q/ME/Portland.json",{timeout:30})
|
76
71
|
@wunderground.get_forecast_for("ME","Portland")
|
77
72
|
end
|
78
73
|
should 'contain multiple Wunderground methods from ruby method' do
|
79
|
-
expect_get(@url+"
|
74
|
+
expect_get(@url+"forecast/conditions/q/.json",{timeout: 30})
|
80
75
|
@wunderground.get_forecast_and_conditions_for()
|
81
76
|
end
|
82
77
|
should 'contain language modifier for method with {lang:"code"} hash' do
|
83
|
-
expect_get(@url+"
|
84
|
-
@wunderground.get_forecast_for(
|
78
|
+
expect_get(@url+"forecast/lang:FR/q/ME/Portland.json",{timeout: 30})
|
79
|
+
@wunderground.get_forecast_for("ME","Portland", lang: 'FR')
|
85
80
|
end
|
86
81
|
context 'location parameter' do
|
87
82
|
should 'formats query of type array' do
|
88
|
-
expect_get(@url+"
|
83
|
+
expect_get(@url+"forecast/q/ME/Portland.json",{timeout: 30})
|
89
84
|
@wunderground.get_forecast_for("ME","Portland")
|
90
85
|
end
|
91
86
|
should 'formats query of type string' do
|
92
|
-
expect_get(@url+"
|
87
|
+
expect_get(@url+"forecast/q/1234.1234,-1234.1234.json",{timeout: 30})
|
93
88
|
@wunderground.get_forecast_for("1234.1234,-1234.1234")
|
94
|
-
expect_get(@url+"
|
89
|
+
expect_get(@url+"forecast/q/pws:WHAT.json",{timeout: 30})
|
95
90
|
@wunderground.get_forecast_for("pws:WHAT")
|
96
91
|
end
|
97
92
|
should 'formats query of type geo_ip' do
|
98
|
-
expect_get(@url+"
|
99
|
-
@wunderground.get_forecast_for(
|
93
|
+
expect_get(@url+"forecast/q/autoip.json?geo_ip=127.0.0.1",{timeout: 30})
|
94
|
+
@wunderground.get_forecast_for(geo_ip: "127.0.0.1")
|
100
95
|
end
|
101
96
|
end
|
102
97
|
context 'language support' do
|
103
98
|
setup {@wunderground.language = "FR"}
|
104
99
|
should 'automatically set language for all location types' do
|
105
|
-
expect_get(@url+"
|
100
|
+
expect_get(@url+"forecast/lang:FR/q/pws:KCATAHOE2.json",{timeout: 30})
|
106
101
|
@wunderground.get_forecast_for("pws:KCATAHOE2")
|
107
102
|
end
|
108
103
|
should 'have optional language override on call' do
|
109
|
-
expect_get(@url+"
|
110
|
-
@wunderground.get_forecast_for(
|
104
|
+
expect_get(@url+"forecast/lang:DE/q/ME/Portland.json",{timeout: 30})
|
105
|
+
@wunderground.get_forecast_for("ME","Portland", lang: 'DE')
|
111
106
|
end
|
112
107
|
should 'pass language through history helper' do
|
113
|
-
expect_get(@url+"
|
114
|
-
@wunderground.get_history_for(Time.now,
|
108
|
+
expect_get(@url+"history_#{Time.now.strftime("%Y%m%d")}/lang:DE/q/ME/Portland.json",{timeout: 30})
|
109
|
+
@wunderground.get_history_for(Time.now,"ME","Portland",lang: 'DE')
|
115
110
|
end
|
116
111
|
should 'pass language through planner helper' do
|
117
|
-
expect_get(@url+"
|
118
|
-
@wunderground.get_planner_for(Time.now,(Time.now+700000),
|
112
|
+
expect_get(@url+"planner_#{Time.now.strftime("%m%d")}#{(Time.now + 700000).strftime('%m%d')}/lang:DE/q/ME/Portland.json",{timeout: 30})
|
113
|
+
@wunderground.get_planner_for(Time.now,(Time.now+700000),"ME","Portland", lang: 'DE')
|
119
114
|
end
|
120
115
|
should 'pass language through planner helper with IP' do
|
121
|
-
expect_get(@url+"
|
116
|
+
expect_get(@url+"planner_#{Time.now.strftime('%m%d')}#{(Time.now +
|
122
117
|
700000).strftime('%m%d')}/lang:DE/q/autoip.json?geo_ip=127.0.0.1",{timeout: 30})
|
123
|
-
@wunderground.get_planner_for(Time.now,(Time.now+700000),
|
118
|
+
@wunderground.get_planner_for(Time.now,(Time.now+700000),lang: "DE",geo_ip: "127.0.0.1")
|
124
119
|
end
|
125
120
|
end
|
126
121
|
context 'for get_history_for(date,location) helper' do
|
127
122
|
should 'pass string dates straight to URL' do
|
128
|
-
expect_get(@url+"
|
123
|
+
expect_get(@url+"history_20110121/q/ME/Portland.json",{timeout: 30})
|
129
124
|
@wunderground.get_history_for("20110121","ME","Portland")
|
130
125
|
end
|
131
126
|
should 'accept Time objects' do
|
132
|
-
expect_get(@url+"
|
127
|
+
expect_get(@url+"history_#{Time.now.strftime("%Y%m%d")}/q/ME/Portland.json",{timeout: 30})
|
133
128
|
@wunderground.get_history_for(Time.now,"ME","Portland")
|
134
129
|
end
|
135
130
|
should 'accept Date objects' do
|
136
|
-
expect_get(@url+"
|
131
|
+
expect_get(@url+"history_#{Time.now.strftime("%Y%m%d")}/q/ME/Portland.json",{timeout: 30})
|
137
132
|
@wunderground.get_history_for(Time.now.to_date,"ME","Portland")
|
138
133
|
end
|
139
134
|
should 'accept Date object and pass optional hash object' do
|
140
|
-
expect_get(@url+"
|
141
|
-
@wunderground.get_history_for(Time.now.to_datetime,
|
135
|
+
expect_get(@url+"history_#{Time.now.strftime("%Y%m%d")}/lang:FR/q/autoip.json?geo_ip=127.0.0.1",{timeout: 30})
|
136
|
+
@wunderground.get_history_for(Time.now.to_datetime,geo_ip: '127.0.0.1',lang: 'FR')
|
142
137
|
end
|
143
138
|
end
|
144
139
|
context 'for get_planner_for helper' do
|
145
140
|
should 'pass string date ranges through' do
|
146
|
-
expect_get(@url+"
|
141
|
+
expect_get(@url+"planner_03130323/q/ME/Portland.json",timeout: 30)
|
147
142
|
@wunderground.get_planner_for("03130323","ME","Portland")
|
148
143
|
end
|
149
144
|
should 'turn two date objects into a properly formatted string' do
|
150
|
-
expect_get(@url+"
|
151
|
-
|
145
|
+
expect_get(@url+"planner_#{Time.now.strftime('%m%d')}#{(Time.now +
|
146
|
+
700000).strftime('%m%d')}/lang:FR/q/autoip.json?geo_ip=127.0.0.1",timeout: 30)
|
147
|
+
@wunderground.get_planner_for(Time.now,(Time.now + 700000),geo_ip: '127.0.0.1',lang:'FR')
|
148
|
+
end
|
149
|
+
end
|
150
|
+
context 'timeout passed through optional hash' do
|
151
|
+
should 'work for helper' do
|
152
|
+
expect_get(@url+"planner_#{Time.now.strftime('%m%d')}#{(Time.now+700000).strftime('%m%d')}/lang:FR/q/autoip.json?geo_ip=127.0.0.1",timeout: 60)
|
153
|
+
@wunderground.get_planner_for(Time.now,(Time.now + 700000),geo_ip: '127.0.0.1',lang:'FR',timeout: 60)
|
154
|
+
end
|
155
|
+
should 'work for regular calls' do
|
156
|
+
expect_get(@url+"forecast/q/pws:WHAT.json",timeout: 60)
|
157
|
+
@wunderground.get_forecast_for("pws:WHAT", timeout: 60)
|
152
158
|
end
|
153
159
|
end
|
154
160
|
end
|
@@ -181,7 +187,7 @@ class TestWunderground < Test::Unit::TestCase
|
|
181
187
|
|
182
188
|
private
|
183
189
|
|
184
|
-
def expect_get(expected_url,expected_options)
|
190
|
+
def expect_get(expected_url,expected_options={})
|
185
191
|
Wunderground.expects(:get).with{|url, opts|
|
186
192
|
url == expected_url &&
|
187
193
|
opts[:timeout] == expected_options[:timeout]
|
data/wunderground_ruby.gemspec
CHANGED
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: wunderground_ruby
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.3.0
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -13,7 +13,7 @@ date: 2012-01-22 00:00:00.000000000Z
|
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: json
|
16
|
-
requirement: &
|
16
|
+
requirement: &70230066419980 !ruby/object:Gem::Requirement
|
17
17
|
none: false
|
18
18
|
requirements:
|
19
19
|
- - ! '>'
|
@@ -21,10 +21,10 @@ dependencies:
|
|
21
21
|
version: 1.4.0
|
22
22
|
type: :runtime
|
23
23
|
prerelease: false
|
24
|
-
version_requirements: *
|
24
|
+
version_requirements: *70230066419980
|
25
25
|
- !ruby/object:Gem::Dependency
|
26
26
|
name: httparty
|
27
|
-
requirement: &
|
27
|
+
requirement: &70230066417940 !ruby/object:Gem::Requirement
|
28
28
|
none: false
|
29
29
|
requirements:
|
30
30
|
- - ! '>'
|
@@ -32,10 +32,10 @@ dependencies:
|
|
32
32
|
version: 0.6.0
|
33
33
|
type: :runtime
|
34
34
|
prerelease: false
|
35
|
-
version_requirements: *
|
35
|
+
version_requirements: *70230066417940
|
36
36
|
- !ruby/object:Gem::Dependency
|
37
37
|
name: addressable
|
38
|
-
requirement: &
|
38
|
+
requirement: &70230066416940 !ruby/object:Gem::Requirement
|
39
39
|
none: false
|
40
40
|
requirements:
|
41
41
|
- - ! '>='
|
@@ -43,10 +43,10 @@ dependencies:
|
|
43
43
|
version: '0'
|
44
44
|
type: :runtime
|
45
45
|
prerelease: false
|
46
|
-
version_requirements: *
|
46
|
+
version_requirements: *70230066416940
|
47
47
|
- !ruby/object:Gem::Dependency
|
48
48
|
name: shoulda
|
49
|
-
requirement: &
|
49
|
+
requirement: &70230066416140 !ruby/object:Gem::Requirement
|
50
50
|
none: false
|
51
51
|
requirements:
|
52
52
|
- - ! '>='
|
@@ -54,10 +54,10 @@ dependencies:
|
|
54
54
|
version: '0'
|
55
55
|
type: :development
|
56
56
|
prerelease: false
|
57
|
-
version_requirements: *
|
57
|
+
version_requirements: *70230066416140
|
58
58
|
- !ruby/object:Gem::Dependency
|
59
59
|
name: bundler
|
60
|
-
requirement: &
|
60
|
+
requirement: &70230066415280 !ruby/object:Gem::Requirement
|
61
61
|
none: false
|
62
62
|
requirements:
|
63
63
|
- - ~>
|
@@ -65,10 +65,10 @@ dependencies:
|
|
65
65
|
version: 1.0.0
|
66
66
|
type: :development
|
67
67
|
prerelease: false
|
68
|
-
version_requirements: *
|
68
|
+
version_requirements: *70230066415280
|
69
69
|
- !ruby/object:Gem::Dependency
|
70
70
|
name: jeweler
|
71
|
-
requirement: &
|
71
|
+
requirement: &70230066414380 !ruby/object:Gem::Requirement
|
72
72
|
none: false
|
73
73
|
requirements:
|
74
74
|
- - ~>
|
@@ -76,10 +76,10 @@ dependencies:
|
|
76
76
|
version: 1.5.1
|
77
77
|
type: :development
|
78
78
|
prerelease: false
|
79
|
-
version_requirements: *
|
79
|
+
version_requirements: *70230066414380
|
80
80
|
- !ruby/object:Gem::Dependency
|
81
81
|
name: simplecov
|
82
|
-
requirement: &
|
82
|
+
requirement: &70230066413400 !ruby/object:Gem::Requirement
|
83
83
|
none: false
|
84
84
|
requirements:
|
85
85
|
- - ! '>='
|
@@ -87,10 +87,10 @@ dependencies:
|
|
87
87
|
version: '0'
|
88
88
|
type: :development
|
89
89
|
prerelease: false
|
90
|
-
version_requirements: *
|
90
|
+
version_requirements: *70230066413400
|
91
91
|
- !ruby/object:Gem::Dependency
|
92
92
|
name: mocha
|
93
|
-
requirement: &
|
93
|
+
requirement: &70230066412420 !ruby/object:Gem::Requirement
|
94
94
|
none: false
|
95
95
|
requirements:
|
96
96
|
- - ! '>'
|
@@ -98,10 +98,10 @@ dependencies:
|
|
98
98
|
version: 0.9.11
|
99
99
|
type: :development
|
100
100
|
prerelease: false
|
101
|
-
version_requirements: *
|
101
|
+
version_requirements: *70230066412420
|
102
102
|
- !ruby/object:Gem::Dependency
|
103
103
|
name: ruby-debug19
|
104
|
-
requirement: &
|
104
|
+
requirement: &70230066409800 !ruby/object:Gem::Requirement
|
105
105
|
none: false
|
106
106
|
requirements:
|
107
107
|
- - ! '>='
|
@@ -109,10 +109,10 @@ dependencies:
|
|
109
109
|
version: '0'
|
110
110
|
type: :development
|
111
111
|
prerelease: false
|
112
|
-
version_requirements: *
|
112
|
+
version_requirements: *70230066409800
|
113
113
|
- !ruby/object:Gem::Dependency
|
114
114
|
name: ruby-debug
|
115
|
-
requirement: &
|
115
|
+
requirement: &70230066409120 !ruby/object:Gem::Requirement
|
116
116
|
none: false
|
117
117
|
requirements:
|
118
118
|
- - ! '>='
|
@@ -120,7 +120,7 @@ dependencies:
|
|
120
120
|
version: '0'
|
121
121
|
type: :development
|
122
122
|
prerelease: false
|
123
|
-
version_requirements: *
|
123
|
+
version_requirements: *70230066409120
|
124
124
|
description: A simple ruby API wrapper for interacting with the Wunderground API
|
125
125
|
email: winfred.nadeau@gmail.com
|
126
126
|
executables: []
|
@@ -153,7 +153,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
153
153
|
version: '0'
|
154
154
|
segments:
|
155
155
|
- 0
|
156
|
-
hash: -
|
156
|
+
hash: -2893557894893877548
|
157
157
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
158
158
|
none: false
|
159
159
|
requirements:
|