gmaps_geocoding 1.1.4 → 1.2.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
  SHA1:
3
- metadata.gz: 3b5e8f1bc785e0ddee97bdc381830b4a6b3d728c
4
- data.tar.gz: b29c97b2bf0aec977373e9e32edf55603daf49b6
3
+ metadata.gz: c4212e76443665512914a3a67effa5079cb5776c
4
+ data.tar.gz: 96483f4316b0b456d2821a14e652bf1f53834ba9
5
5
  SHA512:
6
- metadata.gz: 34b7bb966efb1ee1d27d35a50a00bb027844a183cf8de821c4299de00cae085df59f8ef905b4bbe4dc21593a48bd189e92b78b6d0fdb867a041197a71e43b700
7
- data.tar.gz: c23de144517af7aca69d6d2aa787dc7cecb81905dbabd60c62643e888a607a9ed6203208ae955565e8d812af7eabae0effab5abc6368efb19890b3a281ec541c
6
+ metadata.gz: a34e7caf36cf100d2db5992b98f312021f13c8696737b7c5830ca123a07b25bdd6a496a7f6f79f99f45b023ac3f75f2786354186fe4819acf3604d36e555c629
7
+ data.tar.gz: 8ba65838f3c20d70bc6f0e5fa692540b88d603df43d815b16368fa6fe62f87d846205f9141653ee93b5f7d4630a727962397797358221593601f39894671220c
data/.rubocop.yml CHANGED
@@ -1,7 +1,7 @@
1
1
  # Reference here: https://github.com/bbatsov/rubocop/blob/master/config/enabled.yml
2
2
 
3
3
  Metrics/LineLength:
4
- Description: 'Limit lines to 310 characters.'
4
+ Description: 'Limit lines to 120 characters.'
5
5
  Enabled: false
6
6
  Max: 120
7
7
 
data/README.md CHANGED
@@ -1,4 +1,4 @@
1
- # GmapsGeocoding
1
+ # GmapsGeocoding [![Gem Version](https://badge.fury.io/rb/gmaps_geocoding.svg)](http://badge.fury.io/rb/gmaps_geocoding) [![Build Status](https://travis-ci.org/fenicks/gmaps_geocoding.svg?branch=master)](https://travis-ci.org/fenicks/gmaps_geocoding) [![Coverage Status](https://coveralls.io/repos/fenicks/gmaps_geocoding/badge.svg?branch=master&service=github)](https://coveralls.io/github/fenicks/gmaps_geocoding?branch=master)
2
2
 
3
3
  A simple Ruby gem for Google Maps Geocoding API.
4
4
  This gem return a Ruby Hash object of the result.
@@ -75,176 +75,62 @@ _Return a location array_
75
75
 
76
76
  **Ruby Hash object from json output**
77
77
 
78
- {"results"=>
79
- [{"address_components"=>
80
- [{"long_name"=>"Eiffel Tower",
81
- "short_name"=>"Eiffel Tower",
82
- "types"=>["point_of_interest", "establishment"]},
83
- {"long_name"=>"Champ de Mars",
84
- "short_name"=>"Champ de Mars",
85
- "types"=>["premise"]},
86
- {"long_name"=>"5", "short_name"=>"5", "types"=>["street_number"]},
87
- {"long_name"=>"Avenue Anatole France",
88
- "short_name"=>"Av. Anatole France",
89
- "types"=>["route"]},
90
- {"long_name"=>"Paris",
91
- "short_name"=>"Paris",
92
- "types"=>["locality", "political"]},
93
- {"long_name"=>"Paris",
94
- "short_name"=>"75",
95
- "types"=>["administrative_area_level_2", "political"]},
96
- {"long_name"=>"Île-de-France",
97
- "short_name"=>"IdF",
98
- "types"=>["administrative_area_level_1", "political"]},
99
- {"long_name"=>"France",
100
- "short_name"=>"FR",
101
- "types"=>["country", "political"]},
102
- {"long_name"=>"75007", "short_name"=>"75007", "types"=>["postal_code"]}],
103
- "formatted_address"=>
104
- "Eiffel Tower, Champ de Mars, 5 Avenue Anatole France, 75007 Paris, France",
105
- "geometry"=>
106
- {"location"=>{"lat"=>48.858278, "lng"=>2.294254},
107
- "location_type"=>"APPROXIMATE",
108
- "viewport"=>
109
- {"northeast"=>{"lat"=>48.8656186, "lng"=>2.3102614},
110
- "southwest"=>{"lat"=>48.8509364, "lng"=>2.2782466}}},
111
- "types"=>["point_of_interest", "establishment"]},
112
- {"address_components"=>
113
- [{"long_name"=>"Eiffel Tower", "short_name"=>"Eiffel Tower", "types"=>[]},
114
- {"long_name"=>"Paris",
115
- "short_name"=>"Paris",
116
- "types"=>["locality", "political"]},
117
- {"long_name"=>"Paris",
118
- "short_name"=>"75",
119
- "types"=>["administrative_area_level_2", "political"]},
120
- {"long_name"=>"Île-de-France",
121
- "short_name"=>"IdF",
122
- "types"=>["administrative_area_level_1", "political"]},
123
- {"long_name"=>"France",
124
- "short_name"=>"FR",
125
- "types"=>["country", "political"]},
126
- {"long_name"=>"75007", "short_name"=>"75007", "types"=>["postal_code"]}],
127
- "formatted_address"=>"Eiffel Tower, 75007 Paris, France",
128
- "geometry"=>
129
- {"bounds"=>
130
- {"northeast"=>{"lat"=>48.858872, "lng"=>2.2952731},
131
- "southwest"=>{"lat"=>48.8578587, "lng"=>2.2937331}},
132
- "location"=>{"lat"=>48.8582222, "lng"=>2.2945},
133
- "location_type"=>"APPROXIMATE",
134
- "viewport"=>
135
- {"northeast"=>{"lat"=>48.8597143302915, "lng"=>2.295852080291502},
136
- "southwest"=>{"lat"=>48.8570163697085, "lng"=>2.293154119708498}}},
137
- "types"=>[]},
138
- {"address_components"=>
139
- [{"long_name"=>"Tour Eiffel", "short_name"=>"Tour Eiffel", "types"=>[]},
140
- {"long_name"=>"Paris",
141
- "short_name"=>"Paris",
142
- "types"=>["locality", "political"]},
143
- {"long_name"=>"Paris",
144
- "short_name"=>"75",
145
- "types"=>["administrative_area_level_2", "political"]},
146
- {"long_name"=>"Île-de-France",
147
- "short_name"=>"IdF",
148
- "types"=>["administrative_area_level_1", "political"]},
149
- {"long_name"=>"France",
150
- "short_name"=>"FR",
151
- "types"=>["country", "political"]},
152
- {"long_name"=>"75015", "short_name"=>"75015", "types"=>["postal_code"]}],
153
- "formatted_address"=>"Tour Eiffel, 75015 Paris, France",
154
- "geometry"=>
155
- {"location"=>{"lat"=>48.857269, "lng"=>2.291018},
156
- "location_type"=>"APPROXIMATE",
157
- "viewport"=>
158
- {"northeast"=>{"lat"=>48.8586179802915, "lng"=>2.292366980291502},
159
- "southwest"=>{"lat"=>48.8559200197085, "lng"=>2.289669019708498}}},
160
- "types"=>[]}],
161
- "status"=>"OK"}
78
+ ```ruby
79
+ {
80
+ "results"=>[{
81
+ "address_components"=>[
82
+ {"long_name"=>"Eiffel Tower", "short_name"=>"Eiffel Tower", "types"=>["point_of_interest", "establishment"]},
83
+ {"long_name"=>"5", "short_name"=>"5", "types"=>["street_number"]},
84
+ {"long_name"=>"Avenue Anatole France", "short_name"=>"Avenue Anatole France", "types"=>["route"]},
85
+ {"long_name"=>"Paris", "short_name"=>"Paris", "types"=>["locality", "political"]},
86
+ {"long_name"=>"Paris", "short_name"=>"75", "types"=>["administrative_area_level_2", "political"]},
87
+ {"long_name"=>"Île-de-France", "short_name"=>"IDF", "types"=>["administrative_area_level_1", "political"]},
88
+ {"long_name"=>"France", "short_name"=>"FR", "types"=>["country", "political"]},
89
+ {"long_name"=>"75007", "short_name"=>"75007", "types"=>["postal_code"]}
90
+ ],
91
+ "formatted_address"=>"Eiffel Tower, Champ de Mars, 5 Avenue Anatole France, 75007 Paris, France",
92
+ "geometry"=>{
93
+ "location"=>{"lat"=>48.85837009999999, "lng"=>2.2944813},
94
+ "location_type"=>"APPROXIMATE",
95
+ "viewport"=>{
96
+ "northeast"=>{"lat"=>48.8597190802915, "lng"=>2.295830280291502},
97
+ "southwest"=>{"lat"=>48.8570211197085, "lng"=>2.293132319708498}
98
+ }
99
+ },
100
+ "place_id"=>"ChIJLU7jZClu5kcR4PcOOO6p3I0",
101
+ "types"=>["premise", "point_of_interest", "establishment"]
102
+ }],
103
+ "status"=>"OK"
104
+ }
105
+ ```
162
106
 
163
107
  **Ruby Hash object from xml output**
164
108
 
165
- {"status"=>"OK",
166
- "result"=>
167
- [{"type"=>["point_of_interest", "establishment"],
168
- "formatted_address"=>
169
- "Eiffel Tower, Champ de Mars, 5 Avenue Anatole France, 75007 Paris, France",
170
- "address_component"=>
171
- [{"long_name"=>"Eiffel Tower",
172
- "short_name"=>"Eiffel Tower",
173
- "type"=>["point_of_interest", "establishment"]},
174
- {"long_name"=>"Champ de Mars",
175
- "short_name"=>"Champ de Mars",
176
- "type"=>"premise"},
177
- {"long_name"=>"5", "short_name"=>"5", "type"=>"street_number"},
178
- {"long_name"=>"Avenue Anatole France",
179
- "short_name"=>"Av. Anatole France",
180
- "type"=>"route"},
181
- {"long_name"=>"Paris",
182
- "short_name"=>"Paris",
183
- "type"=>["locality", "political"]},
184
- {"long_name"=>"Paris",
185
- "short_name"=>"75",
186
- "type"=>["administrative_area_level_2", "political"]},
187
- {"long_name"=>"Île-de-France",
188
- "short_name"=>"IdF",
189
- "type"=>["administrative_area_level_1", "political"]},
190
- {"long_name"=>"France",
191
- "short_name"=>"FR",
192
- "type"=>["country", "political"]},
193
- {"long_name"=>"75007", "short_name"=>"75007", "type"=>"postal_code"}],
194
- "geometry"=>
195
- {"location"=>{"lat"=>"48.8582780", "lng"=>"2.2942540"},
196
- "location_type"=>"APPROXIMATE",
197
- "viewport"=>
198
- {"southwest"=>{"lat"=>"48.8509364", "lng"=>"2.2782466"},
199
- "northeast"=>{"lat"=>"48.8656186", "lng"=>"2.3102614"}}}},
200
- {"formatted_address"=>"Eiffel Tower, 75007 Paris, France",
201
- "address_component"=>
202
- [{"long_name"=>"Eiffel Tower", "short_name"=>"Eiffel Tower"},
203
- {"long_name"=>"Paris",
204
- "short_name"=>"Paris",
205
- "type"=>["locality", "political"]},
206
- {"long_name"=>"Paris",
207
- "short_name"=>"75",
208
- "type"=>["administrative_area_level_2", "political"]},
209
- {"long_name"=>"Île-de-France",
210
- "short_name"=>"IdF",
211
- "type"=>["administrative_area_level_1", "political"]},
212
- {"long_name"=>"France",
213
- "short_name"=>"FR",
214
- "type"=>["country", "political"]},
215
- {"long_name"=>"75007", "short_name"=>"75007", "type"=>"postal_code"}],
216
- "geometry"=>
217
- {"location"=>{"lat"=>"48.8582222", "lng"=>"2.2945000"},
218
- "location_type"=>"APPROXIMATE",
219
- "viewport"=>
220
- {"southwest"=>{"lat"=>"48.8570164", "lng"=>"2.2931541"},
221
- "northeast"=>{"lat"=>"48.8597143", "lng"=>"2.2958521"}},
222
- "bounds"=>
223
- {"southwest"=>{"lat"=>"48.8578587", "lng"=>"2.2937331"},
224
- "northeast"=>{"lat"=>"48.8588720", "lng"=>"2.2952731"}}}},
225
- {"formatted_address"=>"Tour Eiffel, 75015 Paris, France",
226
- "address_component"=>
227
- [{"long_name"=>"Tour Eiffel", "short_name"=>"Tour Eiffel"},
228
- {"long_name"=>"Paris",
229
- "short_name"=>"Paris",
230
- "type"=>["locality", "political"]},
231
- {"long_name"=>"Paris",
232
- "short_name"=>"75",
233
- "type"=>["administrative_area_level_2", "political"]},
234
- {"long_name"=>"Île-de-France",
235
- "short_name"=>"IdF",
236
- "type"=>["administrative_area_level_1", "political"]},
237
- {"long_name"=>"France",
238
- "short_name"=>"FR",
239
- "type"=>["country", "political"]},
240
- {"long_name"=>"75015", "short_name"=>"75015", "type"=>"postal_code"}],
241
- "geometry"=>
242
- {"location"=>{"lat"=>"48.8572690", "lng"=>"2.2910180"},
243
- "location_type"=>"APPROXIMATE",
244
- "viewport"=>
245
- {"southwest"=>{"lat"=>"48.8559200", "lng"=>"2.2896690"},
246
- "northeast"=>{"lat"=>"48.8586180", "lng"=>"2.2923670"}}}}]}
247
-
109
+ ```ruby
110
+ {
111
+ "status"=>"OK",
112
+ "result"=>{
113
+ "type"=>["premise", "point_of_interest", "establishment"],
114
+ "formatted_address"=>"Eiffel Tower, Champ de Mars, 5 Avenue Anatole France, 75007 Paris, France",
115
+ "address_component"=>[
116
+ {"long_name"=>"Eiffel Tower", "short_name"=>"Eiffel Tower", "type"=>["point_of_interest", "establishment"]},
117
+ {"long_name"=>"5", "short_name"=>"5", "type"=>"street_number"},
118
+ {"long_name"=>"Avenue Anatole France", "short_name"=>"Avenue Anatole France", "type"=>"route"},
119
+ {"long_name"=>"Paris", "short_name"=>"Paris", "type"=>["locality", "political"]},
120
+ {"long_name"=>"Paris", "short_name"=>"75", "type"=>["administrative_area_level_2", "political"]},
121
+ {"long_name"=>"Île-de-France", "short_name"=>"IDF", "type"=>["administrative_area_level_1", "political"]},
122
+ {"long_name"=>"France", "short_name"=>"FR", "type"=>["country", "political"]},
123
+ {"long_name"=>"75007", "short_name"=>"75007", "type"=>"postal_code"}
124
+ ],
125
+ "geometry"=>{
126
+ "location"=>{"lat"=>"48.8583701", "lng"=>"2.2944813"},
127
+ "location_type"=>"APPROXIMATE",
128
+ "viewport"=>{"southwest"=>{"lat"=>"48.8570211", "lng"=>"2.2931323"}, "northeast"=>{"lat"=>"48.8597191", "lng"=>"2.2958303"}}
129
+ },
130
+ "place_id"=>"ChIJLU7jZClu5kcR4PcOOO6p3I0"
131
+ }
132
+ }
133
+ ```
248
134
 
249
135
  ## Contributing
250
136
 
@@ -24,13 +24,14 @@ Gem::Specification.new do |s|
24
24
  s.require_paths = ['lib']
25
25
 
26
26
  s.add_runtime_dependency 'rest-client', '~> 1.8'
27
- s.add_runtime_dependency 'yajl-ruby', '~> 1.2'
28
- s.add_runtime_dependency 'nori', '~> 2.5'
29
- s.add_runtime_dependency 'nokogiri', '~> 1.6'
27
+ s.add_runtime_dependency 'oj', '>= 2.12.13'
28
+ s.add_runtime_dependency 'oj_mimic_json'
29
+ s.add_runtime_dependency 'ox', '>= 2.2.1'
30
30
  s.add_development_dependency 'bundler', '~> 1.7', '>= 1.7.0'
31
31
  s.add_development_dependency 'rake', '~> 0'
32
32
  s.add_development_dependency 'yard', '~> 0'
33
33
  s.add_development_dependency 'simplecov', '~> 0'
34
34
  s.add_development_dependency 'test-unit', '~> 3.0'
35
35
  s.add_development_dependency 'rubocop', '~> 0'
36
+ s.add_development_dependency 'coveralls', '~> 0'
36
37
  end
@@ -1,7 +1,7 @@
1
1
  require 'logger'
2
+ require 'ox'
3
+ require 'oj'
2
4
  require 'rest-client'
3
- require 'yajl/json_gem'
4
- require 'nori'
5
5
 
6
6
  # Gmaps geocoding module
7
7
  module GmapsGeocoding
@@ -23,6 +23,7 @@ module GmapsGeocoding
23
23
  end
24
24
  end
25
25
  @config = GmapsGeocoding::Config.new(opts)
26
+ Oj.default_options = Oj.default_options.merge(bigdecimal_load: :float, float_precision: 7)
26
27
  end
27
28
 
28
29
  # Return a Ruby Hash object of the Google Maps Geocoding Service response
@@ -40,25 +41,19 @@ module GmapsGeocoding
40
41
  # result = api.location
41
42
  #
42
43
  def location
43
- begin
44
- if @config.valid?
45
- rest_client = retrieve_geocoding_data
46
- result = case @config.json_format?
47
- when true
48
- Yajl::Parser.parse(rest_client)
49
- else
50
- r = Nori.new.parse(rest_client)
51
- if r.include?('GeocodeResponse'.freeze)
52
- r['GeocodeResponse']
53
- else
54
- { status: 'UNKNOWN_ERROR'.freeze }
55
- end
56
- end
57
- return result
44
+ if @config.valid?
45
+ rest_client = retrieve_geocoding_data
46
+ case @config.json_format?
47
+ when true
48
+ json_to_hash(rest_client)
49
+ else
50
+ xml_to_hash(rest_client)
58
51
  end
59
- rescue => e
60
- @logger.error e
52
+ else
53
+ fail 'Invalid configuration parameters check the Google Geocoding API documentation'.freeze
61
54
  end
55
+ rescue => e
56
+ @logger.error e
62
57
  nil
63
58
  end
64
59
 
@@ -119,5 +114,53 @@ module GmapsGeocoding
119
114
  data = build_url_query
120
115
  RestClient.get data[:url], params: data[:params]
121
116
  end
117
+
118
+ def json_to_hash(json_str)
119
+ Oj.load(json_str)
120
+ end
121
+
122
+ def xml_to_hash(xml_str)
123
+ xml = Ox.parse(xml_str)
124
+ r = xml_node_to_ruby(xml)
125
+ if r.include?('GeocodeResponse'.freeze)
126
+ r['GeocodeResponse']
127
+ else
128
+ { status: 'UNKNOWN_ERROR'.freeze }
129
+ end
130
+ end
131
+
132
+ # rubocop:disable Metrics/AbcSize
133
+ # rubocop:disable Metrics/PerceivedComplexity
134
+ # rubocop:disable Metrics/CyclomaticComplexity
135
+ def xml_node_to_ruby(ox)
136
+ return unless ox.respond_to?(:nodes)
137
+ result = {}
138
+ ox.nodes.each do |d|
139
+ next unless d.respond_to?(:nodes)
140
+ if d.nodes[0].is_a?(Ox::Element)
141
+ if result.include?(d.value)
142
+ unless result[d.value].is_a?(Array)
143
+ result[d.value] = [result[d.value]]
144
+ end
145
+ result[d.value] << xml_node_to_ruby(d)
146
+ else
147
+ result[d.value] = xml_node_to_ruby(d)
148
+ end
149
+ else
150
+ if result.include?(d.value)
151
+ unless result[d.value].is_a?(Array)
152
+ result[d.value] = [result[d.value]]
153
+ end
154
+ result[d.value] << d.nodes[0]
155
+ else
156
+ result[d.value] = d.nodes[0]
157
+ end
158
+ end
159
+ end
160
+ result
161
+ end
162
+ # rubocop:enable Metrics/AbcSize
163
+ # rubocop:enable Metrics/PerceivedComplexity
164
+ # rubocop:enable Metrics/CyclomaticComplexity
122
165
  end
123
166
  end
@@ -1,3 +1,3 @@
1
1
  module GmapsGeocoding
2
- VERSION = '1.1.4'.freeze
2
+ VERSION = '1.2.0'.freeze
3
3
  end
data/test/test_helper.rb CHANGED
@@ -1,4 +1,8 @@
1
1
  require 'simplecov'
2
+ require 'coveralls'
3
+
4
+ SimpleCov.formatter = SimpleCov::Formatter::MultiFormatter[SimpleCov::Formatter::HTMLFormatter,
5
+ Coveralls::SimpleCov::Formatter]
2
6
  SimpleCov.start
3
7
 
4
8
  require 'test/unit'
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: gmaps_geocoding
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.1.4
4
+ version: 1.2.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Christian Kakesa
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2015-09-06 00:00:00.000000000 Z
11
+ date: 2015-09-08 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rest-client
@@ -25,47 +25,47 @@ dependencies:
25
25
  - !ruby/object:Gem::Version
26
26
  version: '1.8'
27
27
  - !ruby/object:Gem::Dependency
28
- name: yajl-ruby
28
+ name: oj
29
29
  requirement: !ruby/object:Gem::Requirement
30
30
  requirements:
31
- - - "~>"
31
+ - - ">="
32
32
  - !ruby/object:Gem::Version
33
- version: '1.2'
33
+ version: 2.12.13
34
34
  type: :runtime
35
35
  prerelease: false
36
36
  version_requirements: !ruby/object:Gem::Requirement
37
37
  requirements:
38
- - - "~>"
38
+ - - ">="
39
39
  - !ruby/object:Gem::Version
40
- version: '1.2'
40
+ version: 2.12.13
41
41
  - !ruby/object:Gem::Dependency
42
- name: nori
42
+ name: oj_mimic_json
43
43
  requirement: !ruby/object:Gem::Requirement
44
44
  requirements:
45
- - - "~>"
45
+ - - ">="
46
46
  - !ruby/object:Gem::Version
47
- version: '2.5'
47
+ version: '0'
48
48
  type: :runtime
49
49
  prerelease: false
50
50
  version_requirements: !ruby/object:Gem::Requirement
51
51
  requirements:
52
- - - "~>"
52
+ - - ">="
53
53
  - !ruby/object:Gem::Version
54
- version: '2.5'
54
+ version: '0'
55
55
  - !ruby/object:Gem::Dependency
56
- name: nokogiri
56
+ name: ox
57
57
  requirement: !ruby/object:Gem::Requirement
58
58
  requirements:
59
- - - "~>"
59
+ - - ">="
60
60
  - !ruby/object:Gem::Version
61
- version: '1.6'
61
+ version: 2.2.1
62
62
  type: :runtime
63
63
  prerelease: false
64
64
  version_requirements: !ruby/object:Gem::Requirement
65
65
  requirements:
66
- - - "~>"
66
+ - - ">="
67
67
  - !ruby/object:Gem::Version
68
- version: '1.6'
68
+ version: 2.2.1
69
69
  - !ruby/object:Gem::Dependency
70
70
  name: bundler
71
71
  requirement: !ruby/object:Gem::Requirement
@@ -156,6 +156,20 @@ dependencies:
156
156
  - - "~>"
157
157
  - !ruby/object:Gem::Version
158
158
  version: '0'
159
+ - !ruby/object:Gem::Dependency
160
+ name: coveralls
161
+ requirement: !ruby/object:Gem::Requirement
162
+ requirements:
163
+ - - "~>"
164
+ - !ruby/object:Gem::Version
165
+ version: '0'
166
+ type: :development
167
+ prerelease: false
168
+ version_requirements: !ruby/object:Gem::Requirement
169
+ requirements:
170
+ - - "~>"
171
+ - !ruby/object:Gem::Version
172
+ version: '0'
159
173
  description: |2
160
174
  A simple Ruby gem for Google Maps Geocoding API.
161
175
  This gem return a Ruby Hash object of the result.