contextio 1.7.1 → 1.7.2

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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: c5e2dbe2586d58809974fbc1700cc773d43d6e78
4
- data.tar.gz: 216fa008cae2c54e0c195020f9405684ebabc777
3
+ metadata.gz: ee262c3eb5ba95fb430a2a2e0fc0e7398ea8d844
4
+ data.tar.gz: c9b4024b14a87f608fb61412b6a5d7dbd8e15ddf
5
5
  SHA512:
6
- metadata.gz: b4a5f33b09fd9d40bd3702df6333a422d84b259558a574265c73212950ba9eaf53f9bcbf63b432613c04c136dbdab394c219ea97766a58eed66363347c68981b
7
- data.tar.gz: 03b711445a19b70b57f57502c549e8d33acb55fd42337f29353dcd31fbdbcbfde074b848ceaf40d58e9d051d5aef18dece9bfeb83f94046f0352bbb5ed22d0b0
6
+ metadata.gz: df4b5035d406a74a45a2e4dd6a4485df9c8a5cb005c068529f148d554b08fd862dfc4e76d0897e0ca6f8c623479515a380cfae7fbd7414c6ffab60fdf35b3d34
7
+ data.tar.gz: ffd3c8568ca1d75d25492c2cd9435956add7538514c53c2f10d1a9abfe6332ee24a658b17a47703d07747d564390d1379275c9fc7dbdde2a7efd250d1372b1b5
data/CHANGES.md CHANGED
@@ -1,5 +1,9 @@
1
1
  # Changes
2
2
 
3
+ ## 1.7.2
4
+
5
+ * Improve error handling for better trouble shooting. - Ben Hamill
6
+
3
7
  ## 1.7.1
4
8
 
5
9
  * Fix bug in `ContextIO::Message#set_flags` that was failing, and also fixes the
@@ -95,30 +95,18 @@ class ContextIO
95
95
  # @raise [API::Error] if the response code isn't in the 200 or 300 range.
96
96
  def request(method, resource_path, params = {})
97
97
  response = oauth_request(method, resource_path, params, { 'Accept' => 'application/json' })
98
- body = response.body
99
- results = JSON.parse(body.to_s) unless response.body.to_s.empty?
100
98
 
101
- unless response.success?
102
- if results.is_a?(Hash) && results['type'] == 'error'
103
- message = results['value']
104
- else
105
- message = "HTTP #{response.status} Error"
106
- end
107
-
108
- raise API::Error, message
99
+ with_error_handling(response) do |response|
100
+ parse_json(response.body)
109
101
  end
110
-
111
- results
112
102
  end
113
103
 
114
104
  def raw_request(method, resource_path, params={})
115
105
  response = oauth_request(method, resource_path, params)
116
106
 
117
- unless response.success?
118
- raise API::Error, "HTTP #{response.status} Error"
107
+ with_error_handling(response) do |response|
108
+ response.body
119
109
  end
120
-
121
- response.body
122
110
  end
123
111
 
124
112
  private
@@ -186,5 +174,52 @@ class ContextIO
186
174
  faraday.adapter Faraday.default_adapter
187
175
  end
188
176
  end
177
+
178
+ # Errors can come in a few shapes and we want to detect them and extract the
179
+ # useful information. If no errors are found, it calls the provided block
180
+ # and passes the response through.
181
+ #
182
+ # @param [Faraday::Response] response A response object from making a request to the
183
+ # API with Faraday.
184
+ #
185
+ # @raise [API::Error] if the response code isn't in the 200 or 300 range.
186
+ def with_error_handling(response, &block)
187
+ return block.call(response) if response.success?
188
+
189
+ parsed_body = parse_json(response.body)
190
+ message = determine_best_error_message(parsed_body) || "HTTP #{response.status} Error"
191
+
192
+ raise API::Error, message
193
+ end
194
+
195
+ # Parses JSON if there's valid JSON passed in.
196
+ #
197
+ # @param [String] document A string you suspect may be a JSON document.
198
+ #
199
+ # @return [Hash, Array, Nil] Either a parsed version of the JSON document or
200
+ # nil, if the document wasn't valid JSON.
201
+ def parse_json(document)
202
+ return JSON.parse(document.to_s)
203
+ rescue JSON::ParserError => e
204
+ return nil
205
+ end
206
+
207
+ # Given a parsed JSON body from an error response, figures out if it can
208
+ # pull useful information therefrom.
209
+ #
210
+ # @param [Hash] parsed_body A Hash parsed from a JSON document that may
211
+ # describe an error condition.
212
+ #
213
+ # @return [String, Nil] If it can, it will return a human-readable
214
+ # error-describing String. Otherwise, nil.
215
+ def determine_best_error_message(parsed_body)
216
+ return unless parsed_body.respond_to?(:[])
217
+
218
+ if parsed_body['type'] == 'error'
219
+ return parsed_body['value']
220
+ elsif parsed_body.has_key?('success') && !parsed_body['success']
221
+ return [parsed_body['feedback_code'], parsed_body['connectionLog']].compact.join("\n")
222
+ end
223
+ end
189
224
  end
190
225
  end
@@ -1,6 +1,6 @@
1
1
  class ContextIO
2
2
  # @private
3
- VERSION = "1.7.1"
3
+ VERSION = "1.7.2"
4
4
 
5
5
  # The gem version.
6
6
  #
@@ -152,6 +152,22 @@ describe ContextIO::API do
152
152
  end
153
153
  end
154
154
 
155
+ context "with a bad response that has a different body" do
156
+ before do
157
+ WebMock.stub_request(
158
+ :get,
159
+ 'https://api.context.io/2.0/test'
160
+ ).to_return(
161
+ status: 400,
162
+ body: JSON.dump('success' => false, 'feedback_code' => 'nope')
163
+ )
164
+ end
165
+
166
+ it "raises an API error with the body message" do
167
+ expect { subject }.to raise_error(ContextIO::API::Error, 'nope')
168
+ end
169
+ end
170
+
155
171
  context "with a bad response that has no body" do
156
172
  before do
157
173
  WebMock.stub_request(
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: contextio
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.7.1
4
+ version: 1.7.2
5
5
  platform: ruby
6
6
  authors:
7
7
  - Ben Hamill
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2014-04-09 00:00:00.000000000 Z
11
+ date: 2014-04-17 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: faraday