gmo 0.5.6 → 0.5.8

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
  SHA256:
3
- metadata.gz: 3eff4563d164b8bd4fd39337bf7678c04385add29377da07efa075c1a322d992
4
- data.tar.gz: 709522dd504353f9c9fb346e0e924f98799be624fa306c05f08b427f60a273ab
3
+ metadata.gz: 01b3f2fbd63de33e391333dd6e1d1a2b47ee785ea330aebda9aa461e2adcf6c8
4
+ data.tar.gz: 675aa139a33705769efa1764c8176778a492da09232e8ff915b92e376d46e252
5
5
  SHA512:
6
- metadata.gz: 3a1858cea03ea2563249ed84778d8bf4f6970a5983e4c0a18debd88fd8ec8df7dd3613f3b0991a82a680dbfed5d6276831b1b8cc61c056a92df6ba2e7819f38f
7
- data.tar.gz: 7cf6f7cc0c092f34d6074bce3615752cce5432246189d9798cdc4a42d41fe35a36dfe667067ce1aa347d346efca8bb58d3f41cc8aae340eee6828a4ed9745b78
6
+ metadata.gz: '0944fb5d4702aa5a1b2e3c035125063ba484f6420c037ad775895d6af5ea99fbc55be979750e37688b78a25eb4a2ffbb9abd4dc72e3e010811ac8a1ce5d4658c'
7
+ data.tar.gz: ca482bcc26e1eda87d96c77c24165c9dbf5f4cdc63f451ae3c6ce94d7e0760d41913c4372eafc20b7b7a5c91439255e816a3d17d5ee65ba7eb9231a68228c88b
@@ -26,7 +26,7 @@ jobs:
26
26
  timeout-minutes: 10
27
27
  strategy:
28
28
  matrix:
29
- ruby-version: ['2.6', '2.7', '3.0', '3.1', '3.2']
29
+ ruby-version: ['2.6', '2.7', '3.0', '3.1', '3.2', '3.3', '3.4']
30
30
 
31
31
  steps:
32
32
  - uses: actions/checkout@v3
data/CHANGELOG.md CHANGED
@@ -1,4 +1,15 @@
1
1
  # CHANGELOG
2
+ ## 0.5.8
3
+ - クレジットカード決済の3Dセキュア2.0に対応 [#76](https://github.com/t-k/gmo-payment-ruby/pull/76)
4
+ - 3DS2.0認証実行 (`tds2_auth`)
5
+ - 3DS2.0認証結果取得 (`tds2_result`)
6
+ - 認証後決済実行 (`secure_tran_2`)
7
+ - Ruby 3.4のサポートを追加 [#74](https://github.com/t-k/gmo-payment-ruby/pull/74) (Thanks [@y-yagi](https://github.com/y-yagi))
8
+ - `ostruct`を明示的な依存関係として追加 [#74](https://github.com/t-k/gmo-payment-ruby/pull/74) (Thanks [@y-yagi](https://github.com/y-yagi))
9
+
10
+ ## 0.5.7
11
+ - Added `nkf` as a dependency. This fixes the warning that appears with Ruby 3.3.0 and later versions. [#67](https://github.com/t-k/gmo-payment-ruby/pull/69)
12
+
2
13
  ## 0.5.6
3
14
  - Support PayPal決済 [#63](https://github.com/t-k/gmo-payment-ruby/pull/63)
4
15
  - Support 銀行振込(バーチャル口座 あおぞら)[#64](https://github.com/t-k/gmo-payment-ruby/pull/64)
@@ -0,0 +1,33 @@
1
+ ---
2
+ http_interactions:
3
+ - request:
4
+ method: post
5
+ uri: https://<HOST>/payment/ExecTran.idPass
6
+ body:
7
+ encoding: UTF-8
8
+ string: AccessID=<ACCESS_ID>&AccessPass=<ACCESS_PASS>&OrderID=<ORDER_ID>&Method=1&PayTimes=&MemberID=<MEMBER_ID>&CardSeq=0&TdsType=2&Tds2Type=2&CallBackUrl=https%3A%2F%2Fexample.com%2Fcallback&Tds2RetUrl=https%3A%2F%2Fexample.com%2F3ds%2Freturn
9
+ headers:
10
+ Accept:
11
+ - "*/*"
12
+ Accept-Encoding:
13
+ - gzip;q=1.0,deflate;q=0.6,identity;q=0.3
14
+ Content-Type:
15
+ - application/x-www-form-urlencoded
16
+ User-Agent:
17
+ - Ruby
18
+ response:
19
+ status:
20
+ code: 200
21
+ message: OK
22
+ headers:
23
+ Content-Type:
24
+ - text/plain; charset=shift_jis
25
+ Date:
26
+ - Thu, 24 Jul 2025 23:15:18 GMT
27
+ Server:
28
+ - Apache
29
+ body:
30
+ encoding: UTF-8
31
+ string: OrderID=<ORDER_ID>&Forward=<FORWARD>&Method=1&PayTimes=&Approve=&TranID=<TRAN_ID>&TranDate=<TRAN_DATE>&CheckString=<CHECK_STRING>&Tds2TransResult=C&Tds2TransResultReason=01&Tds2ChallengeUrl=https://<HOST>/payment/Tds2Challenge?tds2TransID=<TDS2_TRANS_ID>&Tds2TransID=<TDS2_TRANS_ID>
32
+ recorded_at: Thu, 24 Jul 2025 23:15:18 GMT
33
+ recorded_with: VCR 6.3.1
@@ -0,0 +1,33 @@
1
+ ---
2
+ http_interactions:
3
+ - request:
4
+ method: post
5
+ uri: https://<HOST>/payment/SecureTran2.idPass
6
+ body:
7
+ encoding: UTF-8
8
+ string: AccessID=<ACCESS_ID>&AccessPass=<ACCESS_PASS>
9
+ headers:
10
+ Accept:
11
+ - "*/*"
12
+ Accept-Encoding:
13
+ - gzip;q=1.0,deflate;q=0.6,identity;q=0.3
14
+ Content-Type:
15
+ - application/x-www-form-urlencoded
16
+ User-Agent:
17
+ - Ruby
18
+ response:
19
+ status:
20
+ code: 200
21
+ message: OK
22
+ headers:
23
+ Content-Type:
24
+ - text/plain; charset=shift_jis
25
+ Date:
26
+ - Thu, 24 Jul 2025 23:15:18 GMT
27
+ Server:
28
+ - Apache
29
+ body:
30
+ encoding: UTF-8
31
+ string: OrderID=<ORDER_ID>&Forward=<FORWARD>&Method=1&PayTimes=&Approve=<APPROVE>&TranID=<TRAN_ID>&TranDate=<TRAN_DATE>&CheckString=<CHECK_STRING>
32
+ recorded_at: Thu, 24 Jul 2025 23:15:18 GMT
33
+ recorded_with: VCR 6.3.1
@@ -0,0 +1,33 @@
1
+ ---
2
+ http_interactions:
3
+ - request:
4
+ method: post
5
+ uri: https://<HOST>/payment/Tds2Auth.idPass
6
+ body:
7
+ encoding: UTF-8
8
+ string: AccessID=<ACCESS_ID>&AccessPass=<ACCESS_PASS>&Tds2Param=<TDS2_PARAM>&ShopID=<SHOP_ID>&ShopPass=<SHOP_PASS>
9
+ headers:
10
+ Accept:
11
+ - "*/*"
12
+ Accept-Encoding:
13
+ - gzip;q=1.0,deflate;q=0.6,identity;q=0.3
14
+ Content-Type:
15
+ - application/x-www-form-urlencoded
16
+ User-Agent:
17
+ - Ruby
18
+ response:
19
+ status:
20
+ code: 200
21
+ message: OK
22
+ headers:
23
+ Content-Type:
24
+ - text/plain; charset=shift_jis
25
+ Date:
26
+ - Thu, 24 Jul 2025 23:15:18 GMT
27
+ Server:
28
+ - Apache
29
+ body:
30
+ encoding: UTF-8
31
+ string: OrderID=<ORDER_ID>&Forward=<FORWARD>&Method=1&PayTimes=&Approve=&TranID=<TRAN_ID>&TranDate=<TRAN_DATE>&CheckString=<CHECK_STRING>&Tds2TransResult=Y&Tds2TransResultReason=&Tds2ChallengeUrl=https://<HOST>/payment/Tds2Challenge?tds2TransID=<TDS2_TRANS_ID>
32
+ recorded_at: Thu, 24 Jul 2025 23:15:18 GMT
33
+ recorded_with: VCR 6.3.1
@@ -0,0 +1,33 @@
1
+ ---
2
+ http_interactions:
3
+ - request:
4
+ method: post
5
+ uri: https://<HOST>/payment/Tds2Result.idPass
6
+ body:
7
+ encoding: UTF-8
8
+ string: AccessID=<ACCESS_ID>&AccessPass=<ACCESS_PASS>&ShopID=<SHOP_ID>&ShopPass=<SHOP_PASS>
9
+ headers:
10
+ Accept:
11
+ - "*/*"
12
+ Accept-Encoding:
13
+ - gzip;q=1.0,deflate;q=0.6,identity;q=0.3
14
+ Content-Type:
15
+ - application/x-www-form-urlencoded
16
+ User-Agent:
17
+ - Ruby
18
+ response:
19
+ status:
20
+ code: 200
21
+ message: OK
22
+ headers:
23
+ Content-Type:
24
+ - text/plain; charset=shift_jis
25
+ Date:
26
+ - Thu, 24 Jul 2025 23:15:18 GMT
27
+ Server:
28
+ - Apache
29
+ body:
30
+ encoding: UTF-8
31
+ string: OrderID=<ORDER_ID>&Forward=<FORWARD>&Method=1&PayTimes=&Approve=&TranID=<TRAN_ID>&TranDate=<TRAN_DATE>&CheckString=<CHECK_STRING>&Tds2TransResult=Y&Tds2TransResultReason=
32
+ recorded_at: Thu, 24 Jul 2025 23:15:18 GMT
33
+ recorded_with: VCR 6.3.1
data/gmo.gemspec CHANGED
@@ -23,8 +23,10 @@ Gem::Specification.new do |gem|
23
23
 
24
24
  gem.add_runtime_dependency "rack"
25
25
  gem.add_runtime_dependency "multi_json"
26
+ gem.add_runtime_dependency "nkf"
26
27
  gem.add_development_dependency "rspec", "~> 3"
27
28
  gem.add_development_dependency "rake"
28
29
  gem.add_development_dependency "vcr"
29
30
  gem.add_development_dependency "webmock"
31
+ gem.add_development_dependency "ostruct"
30
32
  end
data/lib/gmo/const.rb CHANGED
@@ -20,7 +20,7 @@ module GMO
20
20
  order_id: '3'
21
21
  }
22
22
 
23
- INPUT_PARAMS = {
23
+ BASE_INPUT_PARAMS = {
24
24
  :access_id => "AccessID",
25
25
  :access_pass => "AccessPass",
26
26
  :account_name => "Account_Name",
@@ -37,11 +37,13 @@ module GMO
37
37
  :auth_code_2 => "Auth_Code2",
38
38
  :auth_code_3 => "Auth_Code3",
39
39
  :amount => "Amount",
40
+ :app_mode => "AppMode",
40
41
  :bank_code => "Bank_Code",
41
42
  :bank_id => "Bank_ID",
42
43
  :branch_code => "Branch_Code",
43
44
  :branch_code_jp => "Branch_Code_Jpbank",
44
45
  :call_back_url => "Call_Back_Url",
46
+ :callback_type => "CallbackType",
45
47
  :cancel_amount => "CancelAmount",
46
48
  :cancel_tax => "CancelTax",
47
49
  :card_name => "CardName",
@@ -156,7 +158,55 @@ module GMO
156
158
  :suica_add_info_4 => "SuicaAddInfo4",
157
159
  :tax => "Tax",
158
160
  :td_flag => "TdFlag",
161
+ :tds2_type => "Tds2Type",
162
+ :td_required => "TdRequired",
159
163
  :td_tenant_name => "TdTenantName",
164
+ :tds2_ch_acc_change => "Tds2ChAccChange",
165
+ :tds2_ch_acc_date => "Tds2ChAccDate",
166
+ :tds2_ch_acc_pw_change => "Tds2ChAccPwChange",
167
+ :tds2_nb_purchase_account => "Tds2NbPurchaseAccount",
168
+ :tds2_param => "Tds2Param",
169
+ :tds2_payment_acc_age => "Tds2PaymentAccAge",
170
+ :tds2_provision_attempts_day => "Tds2ProvisionAttemptsDay",
171
+ :tds2_ship_address_usage => "Tds2ShipAddressUsage",
172
+ :tds2_ship_name_ind => "Tds2ShipNameInd",
173
+ :tds2_suspicious_acc_activity => "Tds2SuspiciousAccActivity",
174
+ :tds2_txn_activity_day => "Tds2TxnActivityDay",
175
+ :tds2_txn_activity_year => "Tds2TxnActivityYear",
176
+ :tds2_3ds_req_auth_data => "Tds2ThreeDSReqAuthData",
177
+ :tds2_3ds_req_auth_method => "Tds2ThreeDSReqAuthMethod",
178
+ :tds2_3ds_req_auth_timestamp => "Tds2ThreeDSReqAuthTimestamp",
179
+ :tds2_addr_match => "Tds2AddrMatch",
180
+ :tds2_bill_addr_city => "Tds2BillAddrCity",
181
+ :tds2_bill_addr_country => "Tds2BillAddrCountry",
182
+ :tds2_bill_addr_line1 => "Tds2BillAddrLine1",
183
+ :tds2_bill_addr_line2 => "Tds2BillAddrLine2",
184
+ :tds2_bill_addr_line3 => "Tds2BillAddrLine3",
185
+ :tds2_bill_addr_post_code => "Tds2BillAddrPostCode",
186
+ :tds2_bill_addr_state => "Tds2BillAddrState",
187
+ :tds2_email => "Tds2Email",
188
+ :tds2_home_phone_cc => "Tds2HomePhoneCC",
189
+ :tds2_home_phone_subscriber => "Tds2HomePhoneSubscriber",
190
+ :tds2_mobile_phone_cc => "Tds2MobilePhoneCC",
191
+ :tds2_mobile_phone_subscriber => "Tds2MobilePhoneSubscriber",
192
+ :tds2_work_phone_cc => "Tds2WorkPhoneCC",
193
+ :tds2_work_phone_subscriber => "Tds2WorkPhoneSubscriber",
194
+ :tds2_ship_addr_city => "Tds2ShipAddrCity",
195
+ :tds2_ship_addr_country => "Tds2ShipAddrCountry",
196
+ :tds2_ship_addr_line1 => "Tds2ShipAddrLine1",
197
+ :tds2_ship_addr_line2 => "Tds2ShipAddrLine2",
198
+ :tds2_ship_addr_line3 => "Tds2ShipAddrLine3",
199
+ :tds2_ship_addr_post_code => "Tds2ShipAddrPostCode",
200
+ :tds2_ship_addr_state => "Tds2ShipAddrState",
201
+ :tds2_delivery_email_address => "Tds2DeliveryEmailAddress",
202
+ :tds2_delivery_time_frame => "Tds2DeliveryTimeframe",
203
+ :tds2_gift_card_amount => "Tds2GiftCardAmount",
204
+ :tds2_gift_card_count => "Tds2GiftCardCount",
205
+ :tds2_gift_card_curr => "Tds2GiftCardCurr",
206
+ :tds2_pre_order_date => "Tds2PreOrderDate",
207
+ :tds2_pre_order_purchase_ind => "Tds2PreOrderPurchaseInd",
208
+ :tds2_reorder_items_ind => "Tds2ReorderItemsInd",
209
+ :tds2_ship_ind => "Tds2ShipInd",
160
210
  :tel_no => "TelNo",
161
211
  :token => "Token",
162
212
  :token_seq => "TokenSeq",
@@ -176,6 +226,21 @@ module GMO
176
226
  :trade_client_mail_address => "TradeClientMailAddress"
177
227
  }.freeze
178
228
 
229
+ # NOTE: 決済方法によってはcaseに揺らぎがあるのでここで上書きする
230
+ PAYMENT_SPECIFIC_PARAMS = {
231
+ "ExecTran.idPass" => {
232
+ ret_url: "RetUrl" # NOTE: 3Dセキュア認証後にお戻しする加盟店様側のURLになります。
233
+ },
234
+ }.freeze
235
+
236
+ def self.input_params(api_method_name)
237
+ if PAYMENT_SPECIFIC_PARAMS.key?(api_method_name)
238
+ BASE_INPUT_PARAMS.dup.merge!(PAYMENT_SPECIFIC_PARAMS[api_method_name])
239
+ else
240
+ BASE_INPUT_PARAMS
241
+ end
242
+ end
243
+
179
244
  API_ERROR_MESSAGES_EN = {
180
245
  '000' => 'Token acquisition completed normally',
181
246
  '100' => 'Card number Required check error',
data/lib/gmo/shop_api.rb CHANGED
@@ -691,6 +691,39 @@ module GMO
691
691
  post_request name, options
692
692
  end
693
693
 
694
+ ###################################################
695
+ # 3DS2.0 対応
696
+ ###################################################
697
+
698
+ # 4.3.1.7 3DS2.0認証実行(Tds2Auth)
699
+ # DS2.0認証を実行します。
700
+ # 3DS2.0認証初期化URL(RedirectUrl)のコールバックを受けたタイミングで本処理を実行してください。
701
+ def tds2_auth(options = {})
702
+ name = "Tds2Auth.idPass"
703
+ required = [:access_id, :access_pass, :tds2_param]
704
+ assert_required_options(required, options)
705
+ post_request name, options
706
+ end
707
+
708
+ # 4.3.1.8 3DS2.0認証結果取得(Tds2Result)
709
+ # 3DS2.0認証の最終的な認証結果を取得します。
710
+ # 3DS2.0認証チャレンジURL(ChallengeUrl)のコールバックを受けたタイミングで本処理を実行してください。
711
+ def tds2_result(options = {})
712
+ name = "Tds2Result.idPass"
713
+ required = [:access_id, :access_pass]
714
+ assert_required_options(required, options)
715
+ post_request name, options
716
+ end
717
+
718
+ # 4.3.1.12 3DS2.0認証後決済実行(SecureTran2)
719
+ # 3DS2.0サービスの結果を解析し、その情報を使用してカード会社と通信を行い決済を実施して結果を返します。
720
+ def secure_tran_2(options = {})
721
+ name = "SecureTran2.idPass"
722
+ required = [:access_id, :access_pass]
723
+ assert_required_options(required, options)
724
+ post_request name, options
725
+ end
726
+
694
727
  private
695
728
 
696
729
  def api_call(name, args = {}, verb = "post", options = {})
data/lib/gmo/version.rb CHANGED
@@ -1,3 +1,3 @@
1
1
  module GMO
2
- VERSION = "0.5.6"
2
+ VERSION = "0.5.8"
3
3
  end
data/lib/gmo.rb CHANGED
@@ -48,6 +48,13 @@ module GMO
48
48
  key_values = result.body.to_s.split('&').map { |str| str.split('=', 2) }.flatten
49
49
  response = Hash[*key_values]
50
50
  end
51
+ # Transform the redirect_url
52
+ # "ACS=2&RedirectUrl=https://manage.tds2gw.gmopg.jp/api/v2/brw/callback?transId=6e48e31f-2940-48e1-a702-ebba2f3373ee&t=dccc8a7ed85372c9accff576bff59b3a"
53
+ # => { "ACS" => "2", RedirectUrl => "https://manage.tds2gw.gmopg.jp/api/v2/brw/callback?transId=6e48e31f-2940-48e1-a702- ebba2f3373ee&t=dccc8a7ed85372c9accff576bff59b3a" }
54
+ if response['RedirectUrl'] && response['RedirectUrl'] != '' && response['t'] && response['t'] != '' && response.keys.index('RedirectUrl') + 1 == response.keys.index('t')
55
+ response['RedirectUrl'] = response['RedirectUrl'] + '&t=' + response['t']
56
+ response.delete('t')
57
+ end
51
58
  # converting to UTF-8
52
59
  body = response = Hash[response.map { |k,v| [k, NKF.nkf('-S -w',v)] }]
53
60
  # Check for errors if provided a error_checking_block
@@ -70,7 +77,7 @@ module GMO
70
77
  # gmo.post_request("EntryTran.idPass", {:foo => "bar"})
71
78
  # POST /EntryTran.idPass with params foo=bar
72
79
  def post_request(name, args = {}, options = {})
73
- args = associate_options_to_gmo_params args
80
+ args = associate_options_to_gmo_params(name, args)
74
81
  api_call(name, args, "post", options)
75
82
  end
76
83
  alias :post! :post_request
@@ -82,8 +89,9 @@ module GMO
82
89
  raise ArgumentError, "Required #{missing.join(', ')} were not provided." unless missing.empty?
83
90
  end
84
91
 
85
- def associate_options_to_gmo_params(options)
86
- Hash[options.map { |k, v| [GMO::Const::INPUT_PARAMS[k], v] }]
92
+ def associate_options_to_gmo_params(api_method_name, options)
93
+ params = GMO::Const.input_params(api_method_name)
94
+ Hash[options.map { |k, v| [params[k], v] }]
87
95
  end
88
96
 
89
97
  def api_call(*args)
data/spec/gmo/api_spec.rb CHANGED
@@ -29,4 +29,32 @@ describe "GMO::Payment::API" do
29
29
  end
30
30
  end
31
31
 
32
+ describe "#associate_options_to_gmo_params" do
33
+ let(:service) { GMO::Payment::API.new() }
34
+
35
+ context "with ExecTran.idPass" do
36
+ it "converts access_id and access_pass normally" do
37
+ options = {
38
+ access_id: "test_access_id",
39
+ access_pass: "test_access_pass",
40
+ ret_url: "https://example.com/callback"
41
+ }
42
+ result = service.send(:associate_options_to_gmo_params, "ExecTran.idPass", options)
43
+ expect(result).to eq({
44
+ "AccessID" => "test_access_id",
45
+ "AccessPass" => "test_access_pass",
46
+ "RetUrl" => "https://example.com/callback"
47
+ })
48
+ end
49
+ end
50
+
51
+ context "with other API methods" do
52
+ it "converts ret_url to RetURL for standard cases" do
53
+ options = { ret_url: "https://example.com/callback" }
54
+ result = service.send(:associate_options_to_gmo_params, "AnotherAPI", options)
55
+ expect(result).to eq({ "RetURL" => "https://example.com/callback" })
56
+ end
57
+ end
58
+ end
59
+
32
60
  end
@@ -1,6 +1,7 @@
1
1
  # Encoding: UTF-8
2
2
 
3
3
  require "spec_helper"
4
+ require "ostruct"
4
5
 
5
6
  describe "GMO::Payment::RemittanceAPI" do
6
7
 
@@ -328,6 +328,28 @@ describe "GMO::Payment::ShopAPI" do
328
328
  }.should_not raise_error("Required card_no, expire were not provided.")
329
329
  end
330
330
 
331
+ it "converts ret_url to RetUrl for ExecTran.idPass" do
332
+ # Test that ret_url is converted to RetUrl by associate_options_to_gmo_params
333
+ actual_params = nil
334
+ allow(@service).to receive(:api_call) do |name, args, method, options|
335
+ actual_params = args
336
+ {}
337
+ end
338
+
339
+ @service.exec_tran({
340
+ :order_id => "test_order",
341
+ :access_id => "test_access",
342
+ :access_pass => "test_pass",
343
+ :method => 1,
344
+ :pay_times => 1,
345
+ :card_no => "4111111111111111",
346
+ :expire => "1405",
347
+ :ret_url => "https://example.com/3d-secure-callback"
348
+ })
349
+
350
+ expect(actual_params).to include("RetUrl" => "https://example.com/3d-secure-callback")
351
+ end
352
+
331
353
  context "parameter contains Japanese characters" do
332
354
  before { require "kconv" unless defined?(Kconv) }
333
355
 
@@ -1170,4 +1192,94 @@ describe "GMO::Payment::ShopAPI" do
1170
1192
  end
1171
1193
  end
1172
1194
 
1195
+ describe "#exec_tran with 3DS2.0" do
1196
+ it "returns 3DS2.0 challenge flow response", :vcr do
1197
+ result = @service.exec_tran({
1198
+ :access_id => "test_access_7ed782e0e10604b31258e0d69ee3e887",
1199
+ :access_pass => "test_pass_7be5e8786e2e959d7b48ad708634dc7e",
1200
+ :order_id => "TEST_3DS_20250724231518",
1201
+ :method => 1,
1202
+ :pay_times => "",
1203
+ :card_no => "4111111111111111",
1204
+ :expire => "2512",
1205
+ :member_id => "TEST_MEMBER_5df458bc",
1206
+ :card_seq => 0,
1207
+ :tds_type => 2,
1208
+ :tds2_type => 2,
1209
+ :call_back_url => "https://example.com/callback",
1210
+ :tds2_ret_url => "https://example.com/3ds/return"
1211
+ })
1212
+
1213
+ result["OrderID"].should == "<ORDER_ID>"
1214
+ result["Forward"].should == "<FORWARD>"
1215
+ result["Method"].should == "1"
1216
+ result["TranID"].should == "<TRAN_ID>"
1217
+ result["TranDate"].should == "<TRAN_DATE>"
1218
+ result["Tds2TransResult"].should == "C"
1219
+ result["Tds2TransResultReason"].should == "01"
1220
+ result["Tds2ChallengeUrl"].should include("/payment/Tds2Challenge")
1221
+ result["Tds2TransID"].should == "<TDS2_TRANS_ID>"
1222
+ end
1223
+ end
1224
+
1225
+ describe "#tds2_auth" do
1226
+ it "executes 3DS2.0 authentication", :vcr do
1227
+ result = @service.tds2_auth({
1228
+ :access_id => "test_access_7ed782e0e10604b31258e0d69ee3e887",
1229
+ :access_pass => "test_pass_7be5e8786e2e959d7b48ad708634dc7e",
1230
+ :tds2_param => "dummy_tds2_param"
1231
+ })
1232
+
1233
+ result["OrderID"].should == "<ORDER_ID>"
1234
+ result["Forward"].should == "<FORWARD>"
1235
+ result["Method"].should == "1"
1236
+ result["PayTimes"].should == ""
1237
+ result["Approve"].should == ""
1238
+ result["TranID"].should == "<TRAN_ID>"
1239
+ result["TranDate"].should == "<TRAN_DATE>"
1240
+ result["CheckString"].should == "<CHECK_STRING>"
1241
+ result["Tds2TransResult"].should == "Y" # Authentication successful
1242
+ result["Tds2TransResultReason"].should == ""
1243
+ result["Tds2ChallengeUrl"].should_not be_nil
1244
+ result["Tds2ChallengeUrl"].should include("/payment/Tds2Challenge")
1245
+ end
1246
+ end
1247
+
1248
+ describe "#tds2_result" do
1249
+ it "gets 3DS2.0 authentication result", :vcr do
1250
+ result = @service.tds2_result({
1251
+ :access_id => "test_access_7ed782e0e10604b31258e0d69ee3e887",
1252
+ :access_pass => "test_pass_7be5e8786e2e959d7b48ad708634dc7e"
1253
+ })
1254
+
1255
+ result["OrderID"].should == "<ORDER_ID>"
1256
+ result["Forward"].should == "<FORWARD>"
1257
+ result["Method"].should == "1"
1258
+ result["PayTimes"].should == ""
1259
+ result["Approve"].should == ""
1260
+ result["TranID"].should == "<TRAN_ID>"
1261
+ result["TranDate"].should == "<TRAN_DATE>"
1262
+ result["CheckString"].should == "<CHECK_STRING>"
1263
+ result["Tds2TransResult"].should == "Y" # Authentication successful
1264
+ result["Tds2TransResultReason"].should == ""
1265
+ end
1266
+ end
1267
+
1268
+ describe "#secure_tran_2" do
1269
+ it "completes payment after 3DS2.0 challenge verification", :vcr do
1270
+ result = @service.secure_tran_2({
1271
+ :access_id => "test_access_7ed782e0e10604b31258e0d69ee3e887",
1272
+ :access_pass => "test_pass_7be5e8786e2e959d7b48ad708634dc7e"
1273
+ })
1274
+
1275
+ result["OrderID"].should == "<ORDER_ID>"
1276
+ result["Forward"].should == "<FORWARD>"
1277
+ result["Method"].should == "1"
1278
+ result["PayTimes"].should == ""
1279
+ result["Approve"].should == "<APPROVE>"
1280
+ result["TranID"].should == "<TRAN_ID>"
1281
+ result["TranDate"].should == "<TRAN_DATE>"
1282
+ result["CheckString"].should == "<CHECK_STRING>"
1283
+ end
1284
+ end
1173
1285
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: gmo
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.5.6
4
+ version: 0.5.8
5
5
  platform: ruby
6
6
  authors:
7
7
  - Tatsuo Kaniwa
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2023-11-25 00:00:00.000000000 Z
11
+ date: 2025-07-29 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rack
@@ -38,6 +38,20 @@ dependencies:
38
38
  - - ">="
39
39
  - !ruby/object:Gem::Version
40
40
  version: '0'
41
+ - !ruby/object:Gem::Dependency
42
+ name: nkf
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - ">="
46
+ - !ruby/object:Gem::Version
47
+ version: '0'
48
+ type: :runtime
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - ">="
53
+ - !ruby/object:Gem::Version
54
+ version: '0'
41
55
  - !ruby/object:Gem::Dependency
42
56
  name: rspec
43
57
  requirement: !ruby/object:Gem::Requirement
@@ -94,6 +108,20 @@ dependencies:
94
108
  - - ">="
95
109
  - !ruby/object:Gem::Version
96
110
  version: '0'
111
+ - !ruby/object:Gem::Dependency
112
+ name: ostruct
113
+ requirement: !ruby/object:Gem::Requirement
114
+ requirements:
115
+ - - ">="
116
+ - !ruby/object:Gem::Version
117
+ version: '0'
118
+ type: :development
119
+ prerelease: false
120
+ version_requirements: !ruby/object:Gem::Requirement
121
+ requirements:
122
+ - - ">="
123
+ - !ruby/object:Gem::Version
124
+ version: '0'
97
125
  description: Ruby client library for the GMO Payment Platform.
98
126
  email:
99
127
  - tatsuo@kaniwa.biz
@@ -163,13 +191,17 @@ files:
163
191
  - fixtures/vcr_cassettes/GMO_Payment_ShopAPI/_exec_tran_rakuten_id_gets_data_about_a_transaction.yml
164
192
  - fixtures/vcr_cassettes/GMO_Payment_ShopAPI/_exec_tran_suica_gets_data_about_a_transaction.yml
165
193
  - fixtures/vcr_cassettes/GMO_Payment_ShopAPI/_exec_tran_virtualaccount_gets_data_about_a_transaction.yml
194
+ - fixtures/vcr_cassettes/GMO_Payment_ShopAPI/_exec_tran_with_3DS2_0_returns_3DS2_0_challenge_flow_response.yml
166
195
  - fixtures/vcr_cassettes/GMO_Payment_ShopAPI/_refund_tran_brandtoken_gets_data_about_a_transaction.yml
167
196
  - fixtures/vcr_cassettes/GMO_Payment_ShopAPI/_sales_tran_brandtoken_gets_data_about_a_transaction.yml
168
197
  - fixtures/vcr_cassettes/GMO_Payment_ShopAPI/_search_trade_gets_data_about_order.yml
169
198
  - fixtures/vcr_cassettes/GMO_Payment_ShopAPI/_search_trade_got_error_if_missing_options.yml
170
199
  - fixtures/vcr_cassettes/GMO_Payment_ShopAPI/_search_trade_multi_gets_data_about_order.yml
171
200
  - fixtures/vcr_cassettes/GMO_Payment_ShopAPI/_search_trade_multi_got_error_if_missing_options.yml
201
+ - fixtures/vcr_cassettes/GMO_Payment_ShopAPI/_secure_tran_2_completes_payment_after_3DS2_0_challenge_verification.yml
172
202
  - fixtures/vcr_cassettes/GMO_Payment_ShopAPI/_secure_tran_gets_data_about_a_transaction.yml
203
+ - fixtures/vcr_cassettes/GMO_Payment_ShopAPI/_tds2_auth_executes_3DS2_0_authentication.yml
204
+ - fixtures/vcr_cassettes/GMO_Payment_ShopAPI/_tds2_result_gets_3DS2_0_authentication_result.yml
173
205
  - fixtures/vcr_cassettes/GMO_Payment_ShopAPI/_void_tran_brandtoken_gets_data_about_order.yml
174
206
  - fixtures/vcr_cassettes/GMO_Payment_ShopAPI/secure_tran_request_params.yml
175
207
  - fixtures/vcr_cassettes/GMO_Payment_ShopAndSiteAPI/_exec_tran_brandtoken_got_data.yml
@@ -237,7 +269,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
237
269
  - !ruby/object:Gem::Version
238
270
  version: '0'
239
271
  requirements: []
240
- rubygems_version: 3.4.1
272
+ rubygems_version: 3.4.10
241
273
  signing_key:
242
274
  specification_version: 4
243
275
  summary: 'GMO Payment API client: Ruby client library for the GMO Payment Platform.'