open-weather-ruby-client 0.2.0 → 0.3.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 1d3916328b6401b21690d359dab0aa1f893282b9456f7d9960fcb8a3024fc625
4
- data.tar.gz: 66657fdd5b0cbad2889b5467cdf9e009b4b8e32cd997c0d86c7ddbf19b14e644
3
+ metadata.gz: 3b61381c999fcbbcefa63521936ee96cc28eb7648a9b2b13cc9d01a608d8b12f
4
+ data.tar.gz: aaa00190d52e86a471f2dca1e52c5c4f5fbf67cdfdf5639fe9302d793d1326e2
5
5
  SHA512:
6
- metadata.gz: 75c4b1f7baafa1a3a61d5b8ba3223a8ac3eeabc2a6a1ccec506e8f718608088b1289487e562a3061d74ba517c09de8bcd4150e3cbad381e893fb9db1b71976ee
7
- data.tar.gz: 6e769293fc354dd3af19780e4cba5a92a0730d2ded3db7976f44d25e8518b49b58bd62bfd7e033ab2ca2d7194db01df03e91a834a67b55824443f45465a9b59e
6
+ metadata.gz: 890ef7edc806545a9b83f99a87133d7ff83900593f17e5aadcf76f7389cfa7c6a3249d0f4911d6d257d493a00dd572880f8848ee68a6ba0cd5ffd9561c53c75f
7
+ data.tar.gz: 3094f7b9d058070590db2ddfabc99d9f799f00b3b185fb9efd93b348d9abd8f124ec8d2f0552f7430850bf08dc7cb698e802c648a32aa9dbaf333b343c0521b4
data/CHANGELOG.md CHANGED
@@ -1,3 +1,10 @@
1
+ ### 0.3.0 (2023/03/25)
2
+
3
+ * [#30](https://github.com/dblock/open-weather-ruby-client/pull/30): Added support for Ruby 3.2 - [@petergoldstein](https://github.com/petergoldstein).
4
+ * [#27](https://github.com/dblock/open-weather-ruby-client/pull/27): Removed default values for Faraday’s SSL settings ca_file and ca_path - [@sunny](https://github.com/sunny).
5
+ * [#21](https://github.com/dblock/open-weather-ruby-client/pull/21), [#20](https://github.com/dblock/open-weather-ruby-client/pull/20), [#19](https://github.com/dblock/open-weather-ruby-client/pull/19), [#18](https://github.com/dblock/open-weather-ruby-client/pull/18): Added support for Stations API - [@wasabigeek](https://github.com/wasabigeek).
6
+ * [#22](https://github.com/dblock/open-weather-ruby-client/pull/23): Removed API version from `Config#endpoint` - [@dblock](https://github.com/dblock).
7
+
1
8
  ### 0.2.0 (2020/05/17)
2
9
 
3
10
  * [#14](https://github.com/dblock/open-weather-ruby-client/pull/14): Added support for One Call API - [@dblock](https://github.com/dblock).
data/README.md CHANGED
@@ -2,9 +2,9 @@ OpenWeather Ruby Client
2
2
  =======================
3
3
 
4
4
  [![Gem Version](https://badge.fury.io/rb/open-weather-ruby-client.svg)](https://badge.fury.io/rb/open-weather-ruby-client)
5
- [![Build Status](https://travis-ci.org/dblock/open-weather-ruby-client.svg?branch=master)](https://travis-ci.org/dblock/open-weather-ruby-client)
5
+ [![Tests Status](https://github.com/dblock/open-weather-ruby-client/actions/workflows/test.yml/badge.svg)](https://github.com/dblock/open-weather-ruby-client/actions)
6
6
 
7
- A Ruby client for the [OpenWeather API v2.5](https://openweathermap.org/api).
7
+ A Ruby client for the [OpenWeather API v2.5 and v3.0](https://openweathermap.org/api).
8
8
 
9
9
  Unlike other clients, including [open-weather](https://github.com/coderhs/ruby_open_weather_map), provides a rich first class interface to OpenWeather models, structured timestamps, built-in metrics conversion for temperature and wind speed, offers more consistent error handling, and is implemented with thorough test coverage using actual OpenWeather data.
10
10
 
@@ -20,6 +20,14 @@ Unlike other clients, including [open-weather](https://github.com/coderhs/ruby_o
20
20
  - [One Call](#one-call)
21
21
  - [Current and Forecast Weather](#current-and-forecast-weather)
22
22
  - [Historical Weather](#historical-weather)
23
+ - [Stations](#stations)
24
+ - [Register a Station](#register-a-station)
25
+ - [List Stations](#list-stations)
26
+ - [Get Station](#get-station)
27
+ - [Update Station](#update-station)
28
+ - [Delete Station](#delete-station)
29
+ - [Create Measurements](#create-measurements)
30
+ - [Get Measurements](#get-measurements)
23
31
  - [Configuration](#configuration)
24
32
  - [Units](#units)
25
33
  - [Converting Temperature](#converting-temperature)
@@ -193,6 +201,96 @@ data.current # => OpenWeather::Models::OneCall::CurrentWeather
193
201
  data.hourly # => Array[OpenWeather::Models::OneCall::HourlyWeather]
194
202
  ```
195
203
 
204
+ ### Stations
205
+
206
+ The [Stations API](https://openweathermap.org/stations) lets your manage personal weather stations and measurements.
207
+
208
+ #### Register a Station
209
+
210
+ To register a station, you can call the client method:
211
+ ```ruby
212
+ data = client.register_station(external_id: 'SF_TEST001', ...) # => OpenWeather::Models::Station
213
+ data.id # => '5ed2118acca8ce0001f1aeg1'
214
+ data.external_id # => 'SF_TEST001'
215
+ ```
216
+ Alternatively, call `register!` on an instance of `Station`:
217
+ ```ruby
218
+ model = OpenWeather::Models::Station.new(external_id: 'SF_TEST001', ...)
219
+ model.register!
220
+ model.id # => '5ed2118acca8ce0001f1aeg1'
221
+ ```
222
+
223
+ #### List Stations
224
+
225
+ To list all stations, call the client method:
226
+ ```ruby
227
+ client.list_stations # => Array[OpenWeather::Models::Station]
228
+ ```
229
+
230
+ #### Get Station
231
+
232
+ To get a station, call the client method:
233
+ ```ruby
234
+ client.get_station('5ed2118acca8ce0001f1aeg1') # => OpenWeather::Models::Station
235
+ ```
236
+
237
+ #### Update Station
238
+
239
+ To update a station, call the client method:
240
+ ```ruby
241
+ client.update_station('5ed2118acca8ce0001f1aeg1', external_id: 'SF_TEST002') # => OpenWeather::Models::Station
242
+ ```
243
+ Alternatively, call `update!` on an instance of `Station`:
244
+ ```ruby
245
+ model = OpenWeather::Models::Station.new(external_id: 'SF_TEST001', ...)
246
+ model.register!
247
+ model.update!(external_id: 'SF_TEST002')
248
+ model.external_id # => 'SF_TEST002'
249
+ ```
250
+
251
+ #### Delete Station
252
+
253
+ To delete a station, call the client method:
254
+ ```ruby
255
+ data = client.delete_station('5ed2118acca8ce0001f1aeg1') # => nil
256
+ ```
257
+
258
+ #### Create Measurements
259
+
260
+ To create measurements, call the client method:
261
+ ```ruby
262
+ client.create_measurements([
263
+ {
264
+ "station_id": -1,
265
+ "dt": 1479817340,
266
+ "temperature": 18.7,
267
+ "wind_speed": 1.2,
268
+ "wind_gust": 3.4,
269
+ "pressure": 1021,
270
+ "humidity": 87,
271
+ "rain_1h": 2,
272
+ "clouds": [
273
+ {
274
+ "condition": 'NSC'
275
+ }
276
+ ]
277
+ }
278
+ ]) # => nil
279
+ ```
280
+
281
+ #### Get Measurements
282
+
283
+ To get measurements, call the client method with the required parameters:
284
+ ```ruby
285
+ client.get_measurements(
286
+ station_id: '5ed21a12cca8ce0001f1aef1',
287
+ type: 'd',
288
+ limit: 100,
289
+ from: 1469817340,
290
+ to: 1591620047
291
+ ) # => Array[OpenWeather::Models::Stations::Measurement]
292
+ ```
293
+
196
294
  ## Configuration
197
295
 
198
296
  You can configure client options, globally.
@@ -211,7 +309,7 @@ setting | description
211
309
  api_key | Required API key.
212
310
  lang | Default language in API responses.
213
311
  units | Default units in API responses.
214
- endpoint | Defaults to `https://api.openweathermap.org/data/2.5/`.
312
+ endpoint | Defaults to `https://api.openweathermap.org/data`.
215
313
  user_agent | User-agent, defaults to _OpenWeather Ruby Client/version_.
216
314
  proxy | Optional HTTP proxy.
217
315
  ca_path | Optional SSL certificates path.
@@ -6,6 +6,7 @@ module OpenWeather
6
6
  include Request
7
7
  include Endpoints::Current
8
8
  include Endpoints::OneCall
9
+ include Endpoints::Stations
9
10
 
10
11
  attr_accessor(*Config::ATTRIBUTES)
11
12
 
@@ -21,11 +21,11 @@ module OpenWeather
21
21
  attr_accessor(*Config::ATTRIBUTES)
22
22
 
23
23
  def reset
24
- self.endpoint = 'https://api.openweathermap.org/data/2.5'
24
+ self.endpoint = 'https://api.openweathermap.org/data'
25
25
  self.api_key = nil
26
26
  self.user_agent = "OpenWeather Ruby Client/#{OpenWeather::VERSION}"
27
- self.ca_path = defined?(OpenSSL) ? OpenSSL::X509::DEFAULT_CERT_DIR : nil
28
- self.ca_file = defined?(OpenSSL) ? OpenSSL::X509::DEFAULT_CERT_FILE : nil
27
+ self.ca_path = nil
28
+ self.ca_file = nil
29
29
  self.proxy = nil
30
30
  self.logger = nil
31
31
  self.timeout = nil
@@ -11,7 +11,10 @@ module OpenWeather
11
11
  def connection
12
12
  @connection ||= begin
13
13
  options = {
14
- headers: headers.merge('Accept' => 'application/json; charset=utf-8')
14
+ headers: headers.merge(
15
+ 'Accept' => 'application/json; charset=utf-8',
16
+ 'Content-Type' => 'application/json'
17
+ )
15
18
  }
16
19
 
17
20
  options[:headers]['User-Agent'] = user_agent if user_agent
@@ -38,7 +38,7 @@ module OpenWeather
38
38
  options.delete(:country)
39
39
  ].compact.join(',')
40
40
  end
41
- OpenWeather::Models::City::Weather.new(get('weather', options), options)
41
+ OpenWeather::Models::City::Weather.new(get('2.5/weather', options), options)
42
42
  end
43
43
 
44
44
  def current_cities_geo_box(*args)
@@ -51,7 +51,7 @@ module OpenWeather
51
51
  options.delete(:lat_top),
52
52
  options.delete(:zoom)
53
53
  ].join(',')
54
- OpenWeather::Models::List.new(get('box/city', options), options)
54
+ OpenWeather::Models::List.new(get('2.5/box/city', options), options)
55
55
  end
56
56
 
57
57
  def current_cities_geo_circle(*args)
@@ -63,7 +63,7 @@ module OpenWeather
63
63
  options[:cnt] = args.shift || 1
64
64
  end
65
65
 
66
- OpenWeather::Models::List.new(get('find', options), options)
66
+ OpenWeather::Models::List.new(get('2.5/find', options), options)
67
67
  end
68
68
 
69
69
  def current_cities_id(*args)
@@ -71,7 +71,7 @@ module OpenWeather
71
71
  options[:id] = args.join(',') if args.any?
72
72
  options[:id] = options.delete(:ids) if options.key?(:ids)
73
73
  options[:id] = options[:id].join(',') if options[:id].is_a?(Array)
74
- OpenWeather::Models::List.new(get('group', options), options)
74
+ OpenWeather::Models::List.new(get('2.5/group', options), options)
75
75
  end
76
76
  end
77
77
  end
@@ -7,7 +7,7 @@ module OpenWeather
7
7
  options = lat.is_a?(Hash) ? options.merge(lat) : options.merge(lat: lat, lon: lon)
8
8
  options[:exclude] = options[:exclude].join(',') if options[:exclude].is_a?(Array)
9
9
  options[:dt] = options[:dt].to_i if options[:dt].is_a?(Time)
10
- path = options.key?(:dt) ? 'onecall/timemachine' : 'onecall'
10
+ path = options.key?(:dt) ? '2.5/onecall/timemachine' : '2.5/onecall'
11
11
  OpenWeather::Models::OneCall::Weather.new(get(path, options), options)
12
12
  end
13
13
  end
@@ -0,0 +1,53 @@
1
+ # frozen_string_literal: true
2
+
3
+ module OpenWeather
4
+ module Endpoints
5
+ module Stations
6
+ def register_station(options = {})
7
+ OpenWeather::Models::Station.new(post('3.0/stations', options))
8
+ end
9
+
10
+ def list_stations
11
+ get('3.0/stations').map { |data| OpenWeather::Models::Station.new(data) }
12
+ end
13
+
14
+ def get_station(id)
15
+ validate_id(id)
16
+
17
+ OpenWeather::Models::Station.new(get("3.0/stations/#{id}"))
18
+ end
19
+
20
+ def update_station(id, options = {})
21
+ validate_id(id)
22
+
23
+ OpenWeather::Models::Station.new(put("3.0/stations/#{id}", options))
24
+ end
25
+
26
+ def delete_station(id)
27
+ validate_id(id)
28
+
29
+ delete("3.0/stations/#{id}")
30
+ nil
31
+ end
32
+
33
+ def create_measurements(measurements, options = {})
34
+ post('3.0/measurements', options.merge(body: measurements))
35
+ nil
36
+ end
37
+
38
+ def get_measurements(options)
39
+ required_keys = %i[station_id type limit from to]
40
+ missing_keys = required_keys - options.keys
41
+ raise ArgumentError, "Missing params: #{missing_keys.join(', ')}" if missing_keys.any?
42
+
43
+ get('3.0/measurements', options).map { |m| OpenWeather::Models::Stations::Measurement.new(m) }
44
+ end
45
+
46
+ private
47
+
48
+ def validate_id(id)
49
+ raise ArgumentError, 'Invalid ID' unless id&.is_a?(String)
50
+ end
51
+ end
52
+ end
53
+ end
@@ -2,3 +2,4 @@
2
2
 
3
3
  require_relative 'endpoints/current'
4
4
  require_relative 'endpoints/one_call'
5
+ require_relative 'endpoints/stations'
@@ -10,7 +10,8 @@ module OpenWeather
10
10
  attr_reader :options
11
11
 
12
12
  def initialize(args = nil, options = {})
13
- super args
13
+ transformed_args = args.respond_to?(:transform_keys) ? args.transform_keys(&:to_s) : args
14
+ super transformed_args
14
15
  @options = { units: OpenWeather.config.units }.merge(options || {})
15
16
  end
16
17
 
@@ -0,0 +1,35 @@
1
+ # frozen_string_literal: true
2
+
3
+ module OpenWeather
4
+ module Models
5
+ class Station < Model
6
+ property 'id', from: 'ID' # internal identifier for the station
7
+ property 'external_id' # external identifier for the station
8
+ property 'name' # name of the station
9
+ property 'latitude' # geographical coordinates of the location (latitude)
10
+ property 'longitude' # geographical coordinates of the location (longitude)
11
+ property 'altitude' # height of station above sea level
12
+ property 'created_at' # timestamp when station was created
13
+ property 'updated_at' # timestamp when station was updated
14
+ property 'rank' # rank of station
15
+
16
+ def register!
17
+ data = OpenWeather::Client.new.register_station(to_h)
18
+ update_attributes!(data)
19
+
20
+ self
21
+ end
22
+
23
+ def update!(attributes)
24
+ data = OpenWeather::Client.new.update_station(id, attributes)
25
+ update_attributes!(data)
26
+
27
+ self
28
+ end
29
+
30
+ def delete!
31
+ OpenWeather::Client.new.delete_station(id)
32
+ end
33
+ end
34
+ end
35
+ end
@@ -0,0 +1,12 @@
1
+ # frozen_string_literal: true
2
+
3
+ module OpenWeather
4
+ module Models
5
+ module Stations
6
+ class Humidity < Model
7
+ property 'average'
8
+ property 'weight'
9
+ end
10
+ end
11
+ end
12
+ end
@@ -0,0 +1,27 @@
1
+ # frozen_string_literal: true
2
+
3
+ module OpenWeather
4
+ module Models
5
+ module Stations
6
+ class Measurement < Model
7
+ property 'station_id' # The internal ID of the station
8
+ property 'type' # Type of the aggregated data - minute, hour or day. Specifies the letters m, h or d respectively
9
+ property 'date' # Time of measurement
10
+ property 'temp'
11
+ property 'humidity'
12
+ property 'wind'
13
+ property 'precipitation'
14
+ property 'pressure'
15
+
16
+ def initialize(args = nil, options = {})
17
+ super args, options
18
+
19
+ self.temp = OpenWeather::Models::Stations::Temp.new(temp, options) if temp
20
+ self.humidity = OpenWeather::Models::Stations::Humidity.new(humidity, options) if humidity
21
+ self.pressure = OpenWeather::Models::Stations::Pressure.new(pressure, options) if pressure
22
+ self.precipitation = OpenWeather::Models::Stations::Precipitation.new(precipitation, options) if precipitation
23
+ end
24
+ end
25
+ end
26
+ end
27
+ end
@@ -0,0 +1,11 @@
1
+ # frozen_string_literal: true
2
+
3
+ module OpenWeather
4
+ module Models
5
+ module Stations
6
+ class Precipitation < Model
7
+ property 'rain'
8
+ end
9
+ end
10
+ end
11
+ end
@@ -0,0 +1,14 @@
1
+ # frozen_string_literal: true
2
+
3
+ module OpenWeather
4
+ module Models
5
+ module Stations
6
+ class Pressure < Model
7
+ property 'min'
8
+ property 'max'
9
+ property 'average'
10
+ property 'weight'
11
+ end
12
+ end
13
+ end
14
+ end
@@ -0,0 +1,14 @@
1
+ # frozen_string_literal: true
2
+
3
+ module OpenWeather
4
+ module Models
5
+ module Stations
6
+ class Temp < Model
7
+ temperature_property 'min'
8
+ temperature_property 'max'
9
+ temperature_property 'average'
10
+ property 'weight'
11
+ end
12
+ end
13
+ end
14
+ end
@@ -13,3 +13,9 @@ require_relative 'models/snow'
13
13
  require_relative 'models/list'
14
14
  require_relative 'models/city'
15
15
  require_relative 'models/one_call'
16
+ require_relative 'models/station'
17
+ require_relative 'models/stations/measurement'
18
+ require_relative 'models/stations/temp'
19
+ require_relative 'models/stations/humidity'
20
+ require_relative 'models/stations/pressure'
21
+ require_relative 'models/stations/precipitation'
@@ -20,6 +20,14 @@ module OpenWeather
20
20
 
21
21
  private
22
22
 
23
+ #
24
+ # @param [Symbol] method - Faraday HTTP method.
25
+ # @param [String] path - URL to send.
26
+ # @param [Hash] options - :appid, :lang, :units, :endpoint, :body keys will configure the request.
27
+ # The rest will be converted to query params for GET/DELETE, or jsonified for POST/PUT.
28
+ #
29
+ # @return [Object] - the Faraday::Response#body.
30
+ #
23
31
  def request(method, path, options)
24
32
  options = options.dup
25
33
  options[:appid] ||= api_key if api_key.present?
@@ -33,7 +41,12 @@ module OpenWeather
33
41
  request.url(path, options)
34
42
  when :post, :put
35
43
  request.path = path
36
- request.body = options unless options.empty?
44
+ request.params = { appid: options.delete(:appid) }
45
+ if options.key?(:body)
46
+ request.body = options.delete(:body).to_json
47
+ elsif !options.empty?
48
+ request.body = options.to_json
49
+ end
37
50
  end
38
51
  request.options.merge!(options.delete(:request)) if options.key?(:request)
39
52
  end
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module OpenWeather
4
- VERSION = '0.2.0'
4
+ VERSION = '0.3.0'
5
5
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: open-weather-ruby-client
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.2.0
4
+ version: 0.3.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Daniel Doubrovkine
8
- autorequire:
8
+ autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2020-05-17 00:00:00.000000000 Z
11
+ date: 2023-03-25 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: activesupport
@@ -66,7 +66,7 @@ dependencies:
66
66
  - - ">="
67
67
  - !ruby/object:Gem::Version
68
68
  version: '0'
69
- description:
69
+ description:
70
70
  email: dblock@dblock.org
71
71
  executables: []
72
72
  extensions: []
@@ -82,6 +82,7 @@ files:
82
82
  - lib/open_weather/endpoints.rb
83
83
  - lib/open_weather/endpoints/current.rb
84
84
  - lib/open_weather/endpoints/one_call.rb
85
+ - lib/open_weather/endpoints/stations.rb
85
86
  - lib/open_weather/errors.rb
86
87
  - lib/open_weather/errors/fault.rb
87
88
  - lib/open_weather/logger.rb
@@ -106,6 +107,12 @@ files:
106
107
  - lib/open_weather/models/one_call/weather.rb
107
108
  - lib/open_weather/models/rain.rb
108
109
  - lib/open_weather/models/snow.rb
110
+ - lib/open_weather/models/station.rb
111
+ - lib/open_weather/models/stations/humidity.rb
112
+ - lib/open_weather/models/stations/measurement.rb
113
+ - lib/open_weather/models/stations/precipitation.rb
114
+ - lib/open_weather/models/stations/pressure.rb
115
+ - lib/open_weather/models/stations/temp.rb
109
116
  - lib/open_weather/models/sys.rb
110
117
  - lib/open_weather/models/weather.rb
111
118
  - lib/open_weather/models/wind.rb
@@ -116,7 +123,7 @@ homepage: http://github.com/dblock/open-weather-ruby-client
116
123
  licenses:
117
124
  - MIT
118
125
  metadata: {}
119
- post_install_message:
126
+ post_install_message:
120
127
  rdoc_options: []
121
128
  require_paths:
122
129
  - lib
@@ -132,7 +139,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
132
139
  version: 1.3.6
133
140
  requirements: []
134
141
  rubygems_version: 3.1.3
135
- signing_key:
142
+ signing_key:
136
143
  specification_version: 4
137
144
  summary: OpenWeather API Ruby client.
138
145
  test_files: []