ruby_psigate 0.7

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.
Files changed (47) hide show
  1. data/CHANGELOG +2 -0
  2. data/Gemfile +12 -0
  3. data/LICENSE +0 -0
  4. data/Manifest +45 -0
  5. data/README.markdown +99 -0
  6. data/Rakefile +28 -0
  7. data/lib/certs/cacert.pem +2633 -0
  8. data/lib/ruby_psigate/account.rb +152 -0
  9. data/lib/ruby_psigate/account_manager_api.rb +137 -0
  10. data/lib/ruby_psigate/account_methods.rb +5 -0
  11. data/lib/ruby_psigate/address.rb +54 -0
  12. data/lib/ruby_psigate/connection.rb +96 -0
  13. data/lib/ruby_psigate/credit_card.rb +104 -0
  14. data/lib/ruby_psigate/credit_card_methods.rb +12 -0
  15. data/lib/ruby_psigate/error.rb +33 -0
  16. data/lib/ruby_psigate/gateway.rb +126 -0
  17. data/lib/ruby_psigate/hash_variables.rb +58 -0
  18. data/lib/ruby_psigate/item.rb +65 -0
  19. data/lib/ruby_psigate/item_option.rb +10 -0
  20. data/lib/ruby_psigate/number_validation_methods.rb +12 -0
  21. data/lib/ruby_psigate/order.rb +120 -0
  22. data/lib/ruby_psigate/recurring_charge.rb +53 -0
  23. data/lib/ruby_psigate/recurring_item.rb +26 -0
  24. data/lib/ruby_psigate/response.rb +109 -0
  25. data/lib/ruby_psigate/serializer.rb +59 -0
  26. data/lib/ruby_psigate/transaction_methods.rb +21 -0
  27. data/lib/ruby_psigate/utils.rb +18 -0
  28. data/lib/ruby_psigate.rb +57 -0
  29. data/ruby_psigate.gemspec +31 -0
  30. data/test/remote/remote_account_test.rb +33 -0
  31. data/test/remote/remote_gateway_test.rb +32 -0
  32. data/test/test_helper.rb +144 -0
  33. data/test/unit/account_manager_api_test.rb +96 -0
  34. data/test/unit/account_test.rb +388 -0
  35. data/test/unit/address_test.rb +99 -0
  36. data/test/unit/connection_test.rb +153 -0
  37. data/test/unit/credit_card_test.rb +152 -0
  38. data/test/unit/gateway_test.rb +112 -0
  39. data/test/unit/item_option_test.rb +19 -0
  40. data/test/unit/item_test.rb +106 -0
  41. data/test/unit/order_test.rb +491 -0
  42. data/test/unit/recurring_charge_test.rb +89 -0
  43. data/test/unit/recurring_item_test.rb +62 -0
  44. data/test/unit/response_test.rb +110 -0
  45. data/test/unit/serializer_test.rb +89 -0
  46. data/test/unit/xml_api_test.rb +25 -0
  47. metadata +154 -0
@@ -0,0 +1,388 @@
1
+ require 'test_helper'
2
+
3
+ module RubyPsigate
4
+
5
+ # This class needs to perform a few functions:
6
+ # 1) Retrieve summary level information (account, charge, invoice, template, email report)
7
+ # 2) Perform body level functions
8
+ # 3) Perform detail level functions
9
+ class AccountTest < Test::Unit::TestCase
10
+
11
+ def setup
12
+ @account = Account.new
13
+ end
14
+
15
+ should "have a getter/setter for account_id" do
16
+ assert @account.respond_to?(:account_id)
17
+ assert @account.respond_to?(:account_id=)
18
+ end
19
+
20
+ context "actions" do
21
+ should "have a getter/setter" do
22
+ assert @account.respond_to?(:action)
23
+ assert @account.respond_to?(:action=)
24
+ end
25
+
26
+ should "set action to :register, returns AMA01" do
27
+ @account.action = { :account => :register }
28
+ assert_equal "AMA01", @account.action
29
+ end
30
+
31
+ should "return :account_register when looking up with AMA01" do
32
+ response = Account.action_reverse_lookup("AMA01")
33
+ assert_equal :account_register, response
34
+ end
35
+ end
36
+
37
+ context "credit card interface" do
38
+ setup do
39
+ @account = Order.new
40
+ end
41
+
42
+ should "accept a CreditCard object" do
43
+ assert @account.respond_to?(:cc=)
44
+ end
45
+
46
+ should "not raise error when setting credit card object" do
47
+ @cc = mock()
48
+ @cc.expects(:is_a?).with(RubyPsigate::CreditCard).returns(true)
49
+ assert_nothing_raised do
50
+ @account.cc = @cc
51
+ end
52
+ end
53
+
54
+ should "raise error if credit card object is not RubyPsigate::CreditCard" do
55
+ assert_raises(InvalidCreditCard) do
56
+ @cc = mock()
57
+ @cc.expects(:is_a?).with(RubyPsigate::CreditCard).returns(false)
58
+ @account.cc = @cc
59
+ end
60
+ end
61
+ end
62
+
63
+ context "address" do
64
+ should "have a getter/setter" do
65
+ assert @account.respond_to?(:address)
66
+ assert @account.respond_to?(:address=)
67
+ end
68
+
69
+ should "raise error if address is not an Address object" do
70
+ assert_raises(InvalidAddress) do
71
+ @account.address = "my address"
72
+ end
73
+ end
74
+ end
75
+
76
+ should "have a email getter/setter" do
77
+ assert @account.respond_to?(:email)
78
+ assert @account.respond_to?(:email=)
79
+ end
80
+
81
+ should "have a comments getter/setter" do
82
+ assert @account.respond_to?(:comments)
83
+ assert @account.respond_to?(:comments=)
84
+ end
85
+
86
+ should "have a serial number getter/setter (used for payment method identifier)" do
87
+ assert @account.respond_to?(:serial_no)
88
+ assert @account.respond_to?(:serial_no=)
89
+ end
90
+
91
+ should "return a hash for :register" do
92
+ @expectation = {
93
+ :Action => "AMA01",
94
+ :Account => {
95
+ :AccountID => nil
96
+ }
97
+ }
98
+ @expectation[:Account].merge!(valid_address_hash)
99
+ @expectation[:Account][:CardInfo] = valid_credit_card_hash(:card_info)
100
+
101
+ @account.action = { :account => :register }
102
+ @account.account_id = nil
103
+ @account.address = valid_address
104
+ @account.cc = valid_credit_card
105
+
106
+ assert_equal @expectation, @account.to_hash(@account.action)
107
+ end
108
+
109
+ should "return a hash for :update" do
110
+ @expectation = {
111
+ :Action => "AMA02",
112
+ :Condition => {
113
+ :AccountID => "1234567890"
114
+ },
115
+ :Update => {}
116
+ }
117
+ @expectation[:Update].merge!(valid_address_hash)
118
+ @expectation[:Update].merge!(:Email => "bob@gmail.com")
119
+ @expectation[:Update].merge!(:Comments => "Some comment here")
120
+
121
+ @account.action = { :account => :update }
122
+ @account.account_id = "1234567890"
123
+ @account.address = valid_address
124
+ @account.email = "bob@gmail.com"
125
+ @account.comments = "Some comment here"
126
+
127
+ assert_equal @expectation, @account.to_hash(@account.action)
128
+ end
129
+
130
+ should "return a hash for retrieving account details" do
131
+ @expectation = {
132
+ :Action => "AMA05",
133
+ :Condition => {
134
+ :AccountID => "1234567890"
135
+ }
136
+ }
137
+
138
+ @account.action = { :account => :details }
139
+ @account.account_id = "1234567890"
140
+ assert_equal @expectation, @account.to_hash(@account.action)
141
+ end
142
+
143
+ should "return a hash for enabling account" do
144
+ @expectation = {
145
+ :Action => "AMA08",
146
+ :Condition => {
147
+ :AccountID => "1234567890"
148
+ }
149
+ }
150
+
151
+ @account.action = { :account => :enable }
152
+ @account.account_id = "1234567890"
153
+ assert_equal @expectation, @account.to_hash(@account.action)
154
+ end
155
+
156
+ should "return a hash for disabling account" do
157
+ @expectation = {
158
+ :Action => "AMA09",
159
+ :Condition => {
160
+ :AccountID => "1234567890"
161
+ }
162
+ }
163
+
164
+ @account.action = { :account => :disable }
165
+ @account.account_id = "1234567890"
166
+ assert_equal @expectation, @account.to_hash(@account.action)
167
+ end
168
+
169
+ should "return a hash for adding a new credit card" do
170
+ @expectation = {
171
+ :Action => "AMA11",
172
+ :Account => {
173
+ :AccountID => "1234567890",
174
+ :CardInfo => {}
175
+ }
176
+ }
177
+ @expectation[:Account][:CardInfo].merge!(valid_credit_card_hash(:card_info))
178
+
179
+ @account.action = { :credit_card => :add }
180
+ @account.account_id = "1234567890"
181
+ @account.cc = valid_credit_card
182
+
183
+ assert_equal @expectation, @account.to_hash(@account.action)
184
+ end
185
+
186
+ should "return a hash for deleting a credit card" do
187
+ @expectation = {
188
+ :Action => "AMA14",
189
+ :Condition => {
190
+ :AccountID => "1234567890",
191
+ :SerialNo => "99"
192
+ }
193
+ }
194
+
195
+ @account.action = { :credit_card => :delete }
196
+ @account.account_id = "1234567890"
197
+ @account.serial_no = "99"
198
+
199
+ assert_equal @expectation, @account.to_hash(@account.action)
200
+ end
201
+
202
+ should "return a hash for enabling a credit card" do
203
+ @expectation = {
204
+ :Action => "AMA18",
205
+ :Condition => {
206
+ :AccountID => "1234567890",
207
+ :SerialNo => "99"
208
+ }
209
+ }
210
+
211
+ @account.action = { :credit_card => :enable }
212
+ @account.account_id = "1234567890"
213
+ @account.serial_no = "99"
214
+
215
+ assert_equal @expectation, @account.to_hash(@account.action)
216
+ end
217
+
218
+ should "return a hash for disabling a credit card" do
219
+ @expectation = {
220
+ :Action => "AMA19",
221
+ :Condition => {
222
+ :AccountID => "1234567890",
223
+ :SerialNo => "99"
224
+ }
225
+ }
226
+
227
+ @account.action = { :credit_card => :disable }
228
+ @account.account_id = "1234567890"
229
+ @account.serial_no = "99"
230
+
231
+ assert_equal @expectation, @account.to_hash(@account.action)
232
+ end
233
+
234
+ should "return a hash for retrieval of charge summary" do
235
+ @expectation = {
236
+ :Action => "RBC00",
237
+ :Condition => {
238
+ :AccountID => "1234567890",
239
+ :StoreID => "MYSTORE"
240
+ }
241
+ }
242
+ @expectation[:Condition].merge!(valid_recurring_charge_hash)
243
+
244
+ @account.action = { :charges => :summary }
245
+ @account.rbcharge = valid_recurring_charge
246
+ @account.account_id = "1234567890"
247
+ @account.store_id = "MYSTORE"
248
+
249
+ assert_equal @expectation, @account.to_hash(@account.action)
250
+ end
251
+
252
+ should "return a hash for registering a new charge" do
253
+ @expectation = {
254
+ :Action => "RBC01",
255
+ :Charge => {
256
+ :AccountID => "1234567890",
257
+ :SerialNo => "99",
258
+ :RBCID => "9999999999",
259
+ :RBName => "Charge123",
260
+ :Interval => "M",
261
+ :RBTrigger => "25",
262
+ :StartTime => "2010.08.01",
263
+ :EndTime => "2015.12.31",
264
+ :ItemInfo => [{
265
+ :ProductID => "Newspaper",
266
+ :Description => "Toronto Star",
267
+ :Quantity => "1",
268
+ :Price => "25.00",
269
+ :Tax1 => "2.00",
270
+ :Tax2 => "1.25"
271
+ }, {
272
+ :ProductID => "Newspaper",
273
+ :Description => "Toronto Star",
274
+ :Quantity => "1",
275
+ :Price => "25.00",
276
+ :Tax1 => "2.00",
277
+ :Tax2 => "1.25"
278
+ }]
279
+ }
280
+ }
281
+
282
+ @account.action = { :charges => :add }
283
+ @account.account_id = "1234567890"
284
+ @account.serial_no = "99"
285
+ @recurring_charge = valid_recurring_charge
286
+ @recurring_charge.status = nil
287
+ @recurring_charge.processtype = nil
288
+ 2.times { @recurring_charge << valid_recurring_item }
289
+ @account.rbcharge = @recurring_charge
290
+
291
+ assert_equal @expectation, @account.to_hash(@account.action)
292
+ end
293
+
294
+ should "return a hash for updating a charge" do
295
+ @expectation = {
296
+ :Action => "RBC02",
297
+ :Condition => { :RBCID => "9999999999" },
298
+ :Update => { :RBTrigger => "25" }
299
+ }
300
+
301
+ @account.action = { :charges => :update }
302
+ @account.rbcharge = RecurringCharge.new(:rbcid => "9999999999", :rbtrigger => "25")
303
+
304
+ assert_equal @expectation, @account.to_hash(@account.action)
305
+ end
306
+
307
+ should "return a hash for deleting a charge" do
308
+ @expectation = {
309
+ :Action => "RBC04",
310
+ :Condition => { :RBCID => "9999999999" }
311
+ }
312
+
313
+ @account.action = { :charges => :delete }
314
+ @account.rbcharge = RecurringCharge.new(:rbcid => "9999999999")
315
+
316
+ assert_equal @expectation, @account.to_hash(@account.action)
317
+ end
318
+
319
+ should "return a hash for retrieving a charge" do
320
+ @expectation = {
321
+ :Action => "RBC05",
322
+ :Condition => { :RBCID => "9999999999" }
323
+ }
324
+
325
+ @account.action = { :charges => :details }
326
+ @account.rbcharge = RecurringCharge.new(:rbcid => "9999999999")
327
+
328
+ assert_equal @expectation, @account.to_hash(@account.action)
329
+ end
330
+
331
+ should "return a hash for enabling charges" do
332
+ @expectation = {
333
+ :Action => "RBC08",
334
+ :Condition => { :RBCID => "9999999999" }
335
+ }
336
+
337
+ @account.action = { :charges => :enable }
338
+ @account.rbcharge = RecurringCharge.new(:rbcid => "9999999999")
339
+
340
+ assert_equal @expectation, @account.to_hash(@account.action)
341
+ end
342
+
343
+ should "return a hash for disabling charges" do
344
+ @expectation = {
345
+ :Action => "RBC09",
346
+ :Condition => { :RBCID => "9999999999" }
347
+ }
348
+
349
+ @account.action = { :charges => :disable }
350
+ @account.rbcharge = RecurringCharge.new(:rbcid => "9999999999")
351
+
352
+ assert_equal @expectation, @account.to_hash(@account.action)
353
+ end
354
+
355
+ should "return a hash for immediate charge" do
356
+ @expectation = {
357
+ :Action => "RBC99",
358
+ :Charge => {
359
+ :AccountID => "1234567890",
360
+ :SerialNo => "1",
361
+ :RBName => "Immediate Payment",
362
+ :ItemInfo => [
363
+ {
364
+ :ProductID => "Newspaper",
365
+ :Description => "Toronto Star",
366
+ :Quantity => "1",
367
+ :Price => "25.00",
368
+ :Tax1 => "2.00",
369
+ :Tax2 => "1.25"
370
+ }
371
+ ]
372
+ }
373
+ }
374
+
375
+ @account.action = { :charges => :immediate }
376
+ @account.account_id = "1234567890"
377
+ @account.serial_no = "1"
378
+
379
+ @recurring_charge = RecurringCharge.new(:rbname => "Immediate Payment")
380
+ @recurring_charge << valid_recurring_item
381
+
382
+ @account.rbcharge = @recurring_charge
383
+
384
+ assert_equal @expectation, @account.to_hash(@account.action)
385
+ end
386
+
387
+ end
388
+ end
@@ -0,0 +1,99 @@
1
+ require 'test_helper'
2
+
3
+ module RubyPsigate
4
+ class AddressTest < Test::Unit::TestCase
5
+
6
+ def setup
7
+ @address = Address.new
8
+ end
9
+
10
+ %w( firstname lastname line1 line2 city state province country zipcode postalcode telephone fax company ).each do |field|
11
+ should "respond to #{field}" do
12
+ assert @address.respond_to?(field.downcase.to_sym)
13
+ setter = field.downcase + "="
14
+ assert @address.respond_to?(setter.to_sym)
15
+ end
16
+ end
17
+
18
+ should "when setting :state, also sets :province" do
19
+ @address.state = "Some value"
20
+ assert_equal @address.province, @address.state
21
+ end
22
+
23
+ should "when setting :province, also sets :state" do
24
+ @address.province = "Some value"
25
+ assert_equal @address.state, @address.province
26
+ end
27
+
28
+ should "when setting :zipcode, also sets :postalcode" do
29
+ @address.zipcode = "Some value"
30
+ assert_equal @address.postalcode, @address.zipcode
31
+ end
32
+
33
+ should "when setting :postalcode, also sets :zipcode" do
34
+ @address.postalcode = "Some value"
35
+ assert_equal @address.zipcode, @address.postalcode
36
+ end
37
+
38
+ should "have a method #name that combines firstname and lastname" do
39
+ @address.firstname = "Bob"
40
+ @address.lastname = "Parsons"
41
+ assert_equal "Bob Parsons", @address.name
42
+ end
43
+
44
+ should "return firstname only" do
45
+ @address.firstname = "Bob"
46
+ assert_equal "Bob", @address.name
47
+ end
48
+
49
+ should "return lastname only" do
50
+ @address.lastname = "Parsons"
51
+ assert_equal "Parsons", @address.name
52
+ end
53
+
54
+ should "have an alias address1 to line1" do
55
+ @address.line1 = "Some address"
56
+ assert_equal "Some address", @address.address1
57
+ end
58
+
59
+ should "have an alias address2 to line2" do
60
+ @address.line2 = "Some address"
61
+ assert_equal "Some address", @address.address2
62
+ end
63
+
64
+ should "return a hash of billing address attributes" do
65
+ @address = valid_address
66
+ @expectation = {
67
+ :Bname => "Bob Parsons",
68
+ :Bcompany => "Bob Parson's Co.",
69
+ :Baddress1 => "1234 West Street",
70
+ :Baddress2 => "Apt 100",
71
+ :Bcity => "Toronto",
72
+ :Bprovince => "Ontario",
73
+ :Bcountry => "CA",
74
+ :Bpostalcode => "L3N9J2",
75
+ :Phone => "416-333-3333",
76
+ :Fax => "416-322-2222"
77
+ }
78
+
79
+ assert_equal @expectation, @address.to_hash(:billing)
80
+ end
81
+
82
+ should "return a hash of shipping address attributes" do
83
+ @address = valid_address
84
+ @expectation = {
85
+ :Sname => "Bob Parsons",
86
+ :Scompany => "Bob Parson's Co.",
87
+ :Saddress1 => "1234 West Street",
88
+ :Saddress2 => "Apt 100",
89
+ :Scity => "Toronto",
90
+ :Sprovince => "Ontario",
91
+ :Scountry => "CA",
92
+ :Spostalcode => "L3N9J2"
93
+ }
94
+
95
+ assert_equal @expectation, @address.to_hash(:shipping)
96
+ end
97
+
98
+ end
99
+ end
@@ -0,0 +1,153 @@
1
+ require 'test_helper'
2
+
3
+ module RubyPsigate
4
+ class ConnectionTest < Test::Unit::TestCase
5
+
6
+ def setup
7
+ @ok = stub(:code => 200, :message => 'OK', :body => 'success')
8
+ @internal_server_error = stub(:code => 500, :message => 'Internal Server Error', :body => 'failure')
9
+
10
+ @endpoint = "https://dev.psigate.com:7989/Messenger/XMLMessenger"
11
+ @connection = RubyPsigate::Connection.new(@endpoint)
12
+ end
13
+
14
+ context "uri" do
15
+ should "be parsed from endpoint" do
16
+ assert_equal URI.parse(@endpoint), @connection.endpoint
17
+ end
18
+
19
+ should "connection parser should also accept uri directly" do
20
+ endpoint = URI.parse(@endpoint)
21
+ connection = RubyPsigate::Connection.new(endpoint)
22
+ assert_equal endpoint, connection.endpoint
23
+ end
24
+
25
+ should "raise uri error" do
26
+ assert_raises URI::InvalidURIError do
27
+ RubyPsigate::Connection.new("hello world")
28
+ end
29
+ end
30
+ end
31
+
32
+ context "making requests" do
33
+ should "be successful when making a POST request" do
34
+ Net::HTTP.any_instance.expects(:post).with('/Messenger/XMLMessenger', 'data').returns(@ok)
35
+ response = @connection.post('data')
36
+ assert_equal 'success', response
37
+ end
38
+
39
+ should "raise error when encounter internal server error" do
40
+ Net::HTTP.any_instance.stubs(:post).returns(@internal_server_error)
41
+ assert_raises(RubyPsigate::ResponseError) do
42
+ @connection.post('')
43
+ end
44
+ end
45
+ end
46
+
47
+ context "timeouts" do
48
+ should "have a read timeout" do
49
+ assert_equal RubyPsigate::Connection::READ_TIMEOUT, @connection.read_timeout
50
+ end
51
+
52
+ should "change the read timeout" do
53
+ @connection.read_timeout = 33
54
+ assert_equal @connection.read_timeout, 33
55
+ end
56
+
57
+ should "have an open timeout" do
58
+ assert_equal RubyPsigate::Connection::OPEN_TIMEOUT, @connection.open_timeout
59
+ end
60
+
61
+ should "change the open timeout" do
62
+ @connection.open_timeout = 5
63
+ assert_equal @connection.open_timeout, 5
64
+ end
65
+
66
+ should "raise error on Timeout::Error" do
67
+ Net::HTTP.any_instance.expects(:post).raises(Timeout::Error)
68
+
69
+ @connection.retry_safe = false
70
+
71
+ assert_raises(RubyPsigate::ConnectionError) do
72
+ @connection.post('')
73
+ end
74
+ end
75
+
76
+ should "raise error on Timeout::Error" do
77
+ Net::HTTP.any_instance.expects(:post).raises(Timeout::Error)
78
+
79
+ @connection.retry_safe = false
80
+
81
+ assert_raises(RubyPsigate::ConnectionError) do
82
+ @connection.post('')
83
+ end
84
+ end
85
+
86
+ should "raise error on Errno::ETIMEDOUT" do
87
+ Net::HTTP.any_instance.expects(:post).raises(Errno::ETIMEDOUT)
88
+
89
+ @connection.retry_safe = false
90
+
91
+ assert_raises(RubyPsigate::ConnectionError) do
92
+ @connection.post('')
93
+ end
94
+ end
95
+ end
96
+
97
+ context "peer verification" do
98
+ should "have a default value" do
99
+ assert_equal RubyPsigate::Connection::VERIFY_PEER, @connection.verify_peer
100
+ end
101
+
102
+ should "be overridden" do
103
+ @connection.verify_peer = false
104
+ assert_equal @connection.verify_peer, false
105
+ end
106
+
107
+ should "raise error if cacert.pem (verification file) is missing" do
108
+ File.expects(:exists?).returns(false)
109
+ assert_raises(RubyPsigate::CertVerificationFileMissingError) do
110
+ @connection.post('')
111
+ end
112
+ end
113
+ end
114
+
115
+ context "failures" do
116
+ should "raise error when met with EOFError" do
117
+ Net::HTTP.any_instance.expects(:post).raises(EOFError)
118
+
119
+ @connection.retry_safe = false
120
+
121
+ assert_raises(RubyPsigate::ConnectionError) do
122
+ @connection.post('')
123
+ end
124
+ end
125
+
126
+ should "retry after recoverable exception" do
127
+ Net::HTTP.any_instance.expects(:post).times(2).raises(Errno::ECONNREFUSED).then.returns(@ok)
128
+
129
+ assert_nothing_raised do
130
+ @connection.post('')
131
+ end
132
+ end
133
+
134
+ should "raise error when retry limit is reached" do
135
+ Net::HTTP.any_instance.expects(:post).times(RubyPsigate::Connection::MAX_RETRIES).raises(Errno::ECONNREFUSED)
136
+ assert_raises(RubyPsigate::ConnectionError) do
137
+ @connection.post('')
138
+ end
139
+ end
140
+
141
+ should "raise error after a mixture of errors raised" do
142
+ Net::HTTP.any_instance.expects(:post).times(3).raises(Errno::ECONNRESET).
143
+ raises(Errno::ECONNREFUSED).
144
+ raises(EOFError)
145
+
146
+ assert_raises(RubyPsigate::ConnectionError) do
147
+ @connection.post('')
148
+ end
149
+ end
150
+ end
151
+
152
+ end
153
+ end