checkout_ru 0.5.0 → 0.5.1

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: e0a282cdafe5a22eec40082c3a726a2f07dff009
4
- data.tar.gz: f34819469e964ef1fbb497bd696ced3f7fd78bab
3
+ metadata.gz: 67ba1776758aff93812e8db9601160ee5a095719
4
+ data.tar.gz: 6b6c449d9ca9aabb1ed0edf0ca63872f1a934922
5
5
  SHA512:
6
- metadata.gz: ce436024add082677decc45b29a184cbc6e654352f3341b78815161ffce4ffcda4072242ca41e97c6e9311a43972c3c28709931dc60cad29473ccff24d075c14
7
- data.tar.gz: f1db0972f18d62420b22662d0ff148af31df5ec01fa38c32cfb9f8962d74d9a878d64cb31176def6f5863635d98b2c7ec92e7eba6991deeb866c0896ee32f57e
6
+ metadata.gz: 442d13b106ee8ab3ab8a2375e99ade2b04eb699e412b8185452c8c88ee975065fc25219c038cd7a4f0a53b18232b16b5b9c841f28c37d81da12fe7a65e5b1466
7
+ data.tar.gz: 05d23e0922f1765dfffcb77c26dc5e74faef7f9103a27eb0f1f090b028a95a797ad78e29016cd13e7abf6a9b43dcd7e2bdbfd06b7c3603d047c56baae10aed8d
@@ -1,3 +1,10 @@
1
+ ## 0.5.1
2
+
3
+ - Support for first specialized error: CheckoutRu::NoDeliveryFoundError.
4
+ It's descendant from CheckoutRu::Error so doesn't break existing rescue code.
5
+ It's raised when checkout.ru has no delivery for certain settlement id.
6
+ - All CheckoutRu::Error exceptions now have `code` attribute
7
+
1
8
  ## 0.5.0
2
9
 
3
10
  - Support new JSON errors (includes support for JSON expired-ticket response)
@@ -11,7 +11,6 @@ require 'checkout_ru/order'
11
11
 
12
12
  module CheckoutRu
13
13
  SERVICE_URL = 'http://platform.checkout.ru'.freeze
14
- Error = Class.new(RuntimeError)
15
14
 
16
15
  class << self
17
16
  attr_accessor \
@@ -0,0 +1,34 @@
1
+ module CheckoutRu
2
+ class Error < RuntimeError
3
+ class << self
4
+ def construct(response)
5
+ code, message = parse_error_response(response)
6
+ error_message = "#{message} (checkout.ru error, code #{code})"
7
+
8
+ case code
9
+ when 4 then NoDeliveryFoundError.new(error_message, code)
10
+ when nil then new(response.inspect)
11
+ else new(error_message, code)
12
+ end
13
+ end
14
+
15
+ def parse_error_response(response)
16
+ if response.respond_to?(:[]) &&
17
+ response[:error_code] &&
18
+ response[:error_message]
19
+
20
+ [response[:error_code], response[:error_message]]
21
+ end
22
+ end
23
+ end
24
+
25
+ attr_reader :code
26
+
27
+ def initialize(message, code = nil)
28
+ @code = code
29
+ super(message)
30
+ end
31
+ end
32
+
33
+ NoDeliveryFoundError = Class.new(Error)
34
+ end
@@ -0,0 +1,37 @@
1
+ module CheckoutRu
2
+ class ExpiredTicketResponse
3
+ attr_reader :response
4
+
5
+ def initialize(response)
6
+ @response = response || {}
7
+ end
8
+
9
+ def match?
10
+ # Checkout.ru changed (broke) invalid ticket responses a few times. These
11
+ # predicates reflect various ways we've seen that tickets can expire.
12
+ json_style_error_after_jan_2015? ||
13
+ old_style_error_before_jan_2015? ||
14
+ broken_error_as_of_oct_06_2014?
15
+ end
16
+
17
+ def json_style_error_after_jan_2015?
18
+ error && error_code == 3 && error_message =~ /is\s+expired\s+or\s+invalid/
19
+ end
20
+
21
+ def old_style_error_before_jan_2015?
22
+ [400, 500].include?(status) && body =~ /is\s+expired\s+or\s+invalid/
23
+ end
24
+
25
+ def broken_error_as_of_oct_06_2014?
26
+ status == 500 && body =~ /Сервис\s+временно\s+не\s+доступен/
27
+ end
28
+
29
+ private
30
+
31
+ def error; response[:error] end
32
+ def error_code; response[:error_code] end
33
+ def error_message; response[:error_message] end
34
+ def body; response[:body] end
35
+ def status; response[:status] end
36
+ end
37
+ end
@@ -1,27 +1,8 @@
1
+ require 'checkout_ru/expired_ticket_response'
2
+ require 'checkout_ru/error'
3
+
1
4
  module CheckoutRu
2
5
  class Session
3
- # Checkout.ru changed (broke) invalid ticket responses a few times. These
4
- # hashes reflect various ways we've seen up to date that ticket can expire.
5
- EXPIRED_TICKET_MATCHERS = [
6
- # the new JSON errors
7
- lambda { |r|
8
- r[:error] &&
9
- r[:error_code] == 3 &&
10
- r[:error_message] =~ /is\s+expired\s+or\s+invalid/
11
- },
12
-
13
- # before JSON errors were introduced
14
- lambda { |r|
15
- [400, 500].include?(r[:status]) &&
16
- r[:body] =~ /is\s+expired\s+or\s+invalid/
17
- },
18
-
19
- # broken style as of 10-06-14
20
- lambda { |r|
21
- r[:status] == 500 && r[:body] =~ /Сервис\s+временно\s+не\s+доступен/
22
- }
23
- ].freeze
24
-
25
6
  class << self
26
7
  def initiate
27
8
  ticket = CheckoutRu.get_ticket
@@ -81,10 +62,7 @@ module CheckoutRu
81
62
  end
82
63
 
83
64
  if parsed_response[:error]
84
- msg = "Error code: #{parsed_response[:error_code]}. "\
85
- "Error message: #{parsed_response[:error_message]}"
86
-
87
- raise Error, msg
65
+ raise Error.construct(parsed_response)
88
66
  end
89
67
 
90
68
  parsed_response
@@ -95,9 +73,7 @@ module CheckoutRu
95
73
  end
96
74
 
97
75
  def expired_ticket?(parsed_response)
98
- parsed_response && EXPIRED_TICKET_MATCHERS.any? do |matcher|
99
- matcher.call(parsed_response)
100
- end
76
+ ExpiredTicketResponse.new(parsed_response).match?
101
77
  end
102
78
  end
103
79
  end
@@ -1,3 +1,3 @@
1
1
  module CheckoutRu
2
- VERSION = "0.5.0"
2
+ VERSION = "0.5.1"
3
3
  end
@@ -0,0 +1,24 @@
1
+ require 'test_helper'
2
+
3
+ class ExpiredTicketResponseTest < MiniTest::Test
4
+ def test_json_style_error_after_jan_2015_is_recognized
5
+ response = {
6
+ error: true, error_code: 3, error_message: "Ticket is expired or invalid"
7
+ }
8
+
9
+ assert CheckoutRu::ExpiredTicketResponse.new(response).match?
10
+ end
11
+
12
+ def test_old_style_error_before_jan_2015_is_recognized
13
+ response1 = { status: 400, body: "Ticket is expired or invalid" }
14
+ response2 = { status: 500, body: "Ticket is expired or invalid" }
15
+
16
+ assert CheckoutRu::ExpiredTicketResponse.new(response1).match?
17
+ assert CheckoutRu::ExpiredTicketResponse.new(response2).match?
18
+ end
19
+
20
+ def test_broken_error_as_of_oct_06_2014_is_recognzied
21
+ response = { status: 500, body: "Сервис временно не доступен" }
22
+ assert CheckoutRu::ExpiredTicketResponse.new(response).match?
23
+ end
24
+ end
@@ -85,4 +85,22 @@ class CheckoutRu::SessionTest < MiniTest::Test
85
85
  assert_equal 'г. Москва', place.full_name
86
86
  end
87
87
  end
88
+
89
+ def test_get_no_delivery_found_error
90
+ VCR.use_cassette('get_no_delivery_found_error') do
91
+ error = assert_raises(CheckoutRu::NoDeliveryFoundError) do
92
+ @session.calculation(
93
+ :place_id => 'b0122c31-eb1c-40ae-b998-08f9e99a0fa1',
94
+ :total_sum => 1500,
95
+ :assessed_sum => 2000,
96
+ :items_count => 2,
97
+ :total_weight => 1
98
+ )
99
+ end
100
+
101
+ assert_equal 4, error.code
102
+ assert_match /no delivery found/, error.message
103
+ assert_match /code 4/, error.message
104
+ end
105
+ end
88
106
  end
@@ -71,8 +71,6 @@ class CheckoutRuTest < MiniTest::Test
71
71
  end
72
72
  end
73
73
 
74
- # Test is broken. Request on update returns error status without description.
75
- # Must be discussed in skype with support.
76
74
  def test_update_order
77
75
  VCR.use_cassette('update_order') do
78
76
  id = create_order
@@ -0,0 +1,103 @@
1
+ ---
2
+ http_interactions:
3
+ - request:
4
+ method: get
5
+ uri: http://platform.checkout.ru/service/checkout/calculation?placeId=b0122c31-eb1c-40ae-b998-08f9e99a0fa1&totalSum=1500&assessedSum=2000&itemsCount=2&totalWeight=1&ticket=tests-will-autorequest-a-valid-ticket
6
+ body:
7
+ encoding: US-ASCII
8
+ string: ''
9
+ headers:
10
+ User-Agent:
11
+ - Faraday v0.8.9
12
+ Accept:
13
+ - application/json
14
+ response:
15
+ status:
16
+ code: 200
17
+ message:
18
+ headers:
19
+ server:
20
+ - nginx/1.7.7
21
+ date:
22
+ - Wed, 28 Jan 2015 00:46:24 GMT
23
+ content-type:
24
+ - application/json;charset=UTF-8
25
+ transfer-encoding:
26
+ - chunked
27
+ connection:
28
+ - close
29
+ set-cookie:
30
+ - JSESSIONID=B7124F28808555872014EE6D7E9BAF26.srv100; Path=/; HttpOnly
31
+ body:
32
+ encoding: UTF-8
33
+ string: '{"error":true,"errorCode":3,"errorMessage":"ticket: ticket is expired
34
+ or invalid; "}'
35
+ http_version:
36
+ recorded_at: Wed, 28 Jan 2015 00:46:24 GMT
37
+ - request:
38
+ method: get
39
+ uri: http://platform.checkout.ru/service/login/ticket/valid-api-key
40
+ body:
41
+ encoding: US-ASCII
42
+ string: ''
43
+ headers:
44
+ User-Agent:
45
+ - Faraday v0.8.9
46
+ Accept:
47
+ - application/json
48
+ response:
49
+ status:
50
+ code: 200
51
+ message:
52
+ headers:
53
+ server:
54
+ - nginx/1.7.7
55
+ date:
56
+ - Wed, 28 Jan 2015 00:46:24 GMT
57
+ content-type:
58
+ - application/json;charset=UTF-8
59
+ content-length:
60
+ - '113'
61
+ connection:
62
+ - close
63
+ body:
64
+ encoding: UTF-8
65
+ string: '{"ticket":"211e40247d084107eedfcf4ebc5fffb8", "receiverEmailNotRequired":"false",
66
+ "isCashOnDeliveryOnly":"false"}'
67
+ http_version:
68
+ recorded_at: Wed, 28 Jan 2015 00:46:25 GMT
69
+ - request:
70
+ method: get
71
+ uri: http://platform.checkout.ru/service/checkout/calculation?placeId=b0122c31-eb1c-40ae-b998-08f9e99a0fa1&totalSum=1500&assessedSum=2000&itemsCount=2&totalWeight=1&ticket=211e40247d084107eedfcf4ebc5fffb8
72
+ body:
73
+ encoding: US-ASCII
74
+ string: ''
75
+ headers:
76
+ User-Agent:
77
+ - Faraday v0.8.9
78
+ Accept:
79
+ - application/json
80
+ response:
81
+ status:
82
+ code: 200
83
+ message:
84
+ headers:
85
+ server:
86
+ - nginx/1.7.7
87
+ date:
88
+ - Wed, 28 Jan 2015 00:46:25 GMT
89
+ content-type:
90
+ - application/json;charset=UTF-8
91
+ transfer-encoding:
92
+ - chunked
93
+ connection:
94
+ - close
95
+ set-cookie:
96
+ - JSESSIONID=0367069015CE5D427494A3220B42CE5D.srv100; Path=/; HttpOnly
97
+ body:
98
+ encoding: UTF-8
99
+ string: '{"error":true,"errorCode":4,"errorMessage":"no delivery found for place
100
+ specified"}'
101
+ http_version:
102
+ recorded_at: Wed, 28 Jan 2015 00:46:25 GMT
103
+ recorded_with: VCR 2.9.0
@@ -5,7 +5,9 @@ require 'vcr'
5
5
  require 'cgi'
6
6
 
7
7
  REAL_API_KEY = ENV['CHECKOUT_RU_API_KEY']
8
- CheckoutRu.api_key = ENV['CHECKOUT_RU_API_KEY'] || 'valid-api-key'
8
+ FAKE_API_KEY = 'valid-api-key'
9
+
10
+ CheckoutRu.api_key = REAL_API_KEY || FAKE_API_KEY
9
11
  CheckoutRu.auto_renew_session = true
10
12
 
11
13
  VCR.configure do |c|
@@ -13,7 +15,7 @@ VCR.configure do |c|
13
15
  c.hook_into :faraday
14
16
 
15
17
  if REAL_API_KEY
16
- c.filter_sensitive_data('valid-api-key') { CheckoutRu.api_key }
18
+ c.filter_sensitive_data(FAKE_API_KEY) { REAL_API_KEY }
17
19
  end
18
20
 
19
21
  c.before_record do |i|
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: checkout_ru
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.5.0
4
+ version: 0.5.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Maxim Chernyak
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2015-01-21 00:00:00.000000000 Z
11
+ date: 2015-01-28 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: faraday
@@ -182,15 +182,19 @@ files:
182
182
  - lib/checkout_ru/address.rb
183
183
  - lib/checkout_ru/delivery.rb
184
184
  - lib/checkout_ru/entity.rb
185
+ - lib/checkout_ru/error.rb
186
+ - lib/checkout_ru/expired_ticket_response.rb
185
187
  - lib/checkout_ru/item.rb
186
188
  - lib/checkout_ru/order.rb
187
189
  - lib/checkout_ru/session.rb
188
190
  - lib/checkout_ru/user.rb
189
191
  - lib/checkout_ru/version.rb
192
+ - test/checkout_ru/expired_ticket_response_test.rb
190
193
  - test/checkout_ru/session_test.rb
191
194
  - test/checkout_ru_test.rb
192
195
  - test/fixtures/calculation.yml
193
196
  - test/fixtures/create_order.yml
197
+ - test/fixtures/get_no_delivery_found_error.yml
194
198
  - test/fixtures/get_place_by_postal_code.yml
195
199
  - test/fixtures/get_places_by_query.yml
196
200
  - test/fixtures/get_postal_code_by_address.yml
@@ -227,10 +231,12 @@ signing_key:
227
231
  specification_version: 4
228
232
  summary: Ruby client for checkout.ru
229
233
  test_files:
234
+ - test/checkout_ru/expired_ticket_response_test.rb
230
235
  - test/checkout_ru/session_test.rb
231
236
  - test/checkout_ru_test.rb
232
237
  - test/fixtures/calculation.yml
233
238
  - test/fixtures/create_order.yml
239
+ - test/fixtures/get_no_delivery_found_error.yml
234
240
  - test/fixtures/get_place_by_postal_code.yml
235
241
  - test/fixtures/get_places_by_query.yml
236
242
  - test/fixtures/get_postal_code_by_address.yml