braintree 2.0.0 → 2.1.0

Sign up to get free protection for your applications and to get access to all the features.
@@ -199,6 +199,51 @@ describe Braintree::Transaction do
199
199
  result.success?.should == false
200
200
  result.errors.for(:transaction).on(:base)[0].code.should == Braintree::ErrorCodes::Transaction::PaymentMethodDoesNotBelongToCustomer
201
201
  end
202
+
203
+ context "new credit card for existing customer" do
204
+ it "allows a new credit card to be used for an existing customer" do
205
+ customer = Braintree::Customer.create!(
206
+ :credit_card => {
207
+ :number => Braintree::Test::CreditCardNumbers::Visa,
208
+ :expiration_date => "05/2010"
209
+ }
210
+ )
211
+ result = Braintree::Transaction.create(
212
+ :type => "sale",
213
+ :amount => Braintree::Test::TransactionAmounts::Authorize,
214
+ :customer_id => customer.id,
215
+ :credit_card => {
216
+ :number => Braintree::Test::CreditCardNumbers::Visa,
217
+ :expiration_date => "12/12"
218
+ }
219
+ )
220
+ result.success?.should == true
221
+ result.transaction.credit_card_details.masked_number.should == "401288******1881"
222
+ result.transaction.vault_credit_card.should be_nil
223
+ end
224
+
225
+ it "allows a new credit card to be used and stored in the vault" do
226
+ customer = Braintree::Customer.create!(
227
+ :credit_card => {
228
+ :number => Braintree::Test::CreditCardNumbers::Visa,
229
+ :expiration_date => "05/2010"
230
+ }
231
+ )
232
+ result = Braintree::Transaction.create(
233
+ :type => "sale",
234
+ :amount => Braintree::Test::TransactionAmounts::Authorize,
235
+ :customer_id => customer.id,
236
+ :credit_card => {
237
+ :number => Braintree::Test::CreditCardNumbers::Visa,
238
+ :expiration_date => "12/12",
239
+ },
240
+ :options => { :store_in_vault => true }
241
+ )
242
+ result.success?.should == true
243
+ result.transaction.credit_card_details.masked_number.should == "401288******1881"
244
+ result.transaction.vault_credit_card.masked_number.should == "401288******1881"
245
+ end
246
+ end
202
247
  end
203
248
 
204
249
  describe "self.create!" do
@@ -301,8 +346,8 @@ describe Braintree::Transaction do
301
346
  transaction.amount.should == BigDecimal.new("100.00")
302
347
  transaction.order_id.should == "123"
303
348
  transaction.processor_response_code.should == "1000"
304
- transaction.created_at.between?(Time.now - 5, Time.now).should == true
305
- transaction.updated_at.between?(Time.now - 5, Time.now).should == true
349
+ transaction.created_at.between?(Time.now - 60, Time.now).should == true
350
+ transaction.updated_at.between?(Time.now - 60, Time.now).should == true
306
351
  transaction.credit_card_details.bin.should == "510510"
307
352
  transaction.credit_card_details.cardholder_name.should == "The Cardholder"
308
353
  transaction.credit_card_details.last_4.should == "5100"
@@ -339,6 +384,31 @@ describe Braintree::Transaction do
339
384
  transaction.shipping_details.country_name.should == "United States of America"
340
385
  end
341
386
 
387
+ it "allows merchant account to be specified" do
388
+ result = Braintree::Transaction.sale(
389
+ :amount => Braintree::Test::TransactionAmounts::Authorize,
390
+ :merchant_account_id => SpecHelper::NonDefaultMerchantAccountId,
391
+ :credit_card => {
392
+ :number => Braintree::Test::CreditCardNumbers::Visa,
393
+ :expiration_date => "05/2009"
394
+ }
395
+ )
396
+ result.success?.should == true
397
+ result.transaction.merchant_account_id.should == SpecHelper::NonDefaultMerchantAccountId
398
+ end
399
+
400
+ it "uses default merchant account when it is not specified" do
401
+ result = Braintree::Transaction.sale(
402
+ :amount => Braintree::Test::TransactionAmounts::Authorize,
403
+ :credit_card => {
404
+ :number => Braintree::Test::CreditCardNumbers::Visa,
405
+ :expiration_date => "05/2009"
406
+ }
407
+ )
408
+ result.success?.should == true
409
+ result.transaction.merchant_account_id.should == SpecHelper::DefaultMerchantAccountId
410
+ end
411
+
342
412
  it "can store customer and credit card in the vault" do
343
413
  result = Braintree::Transaction.sale(
344
414
  :amount => "100",
@@ -660,6 +730,31 @@ describe Braintree::Transaction do
660
730
  result.params.should == {:transaction => {:type => 'credit', :amount => nil, :credit_card => {:expiration_date => "05/2009"}}}
661
731
  result.errors.for(:transaction).on(:amount)[0].code.should == Braintree::ErrorCodes::Transaction::AmountIsRequired
662
732
  end
733
+
734
+ it "allows merchant account to be specified" do
735
+ result = Braintree::Transaction.credit(
736
+ :amount => Braintree::Test::TransactionAmounts::Authorize,
737
+ :merchant_account_id => SpecHelper::NonDefaultMerchantAccountId,
738
+ :credit_card => {
739
+ :number => Braintree::Test::CreditCardNumbers::Visa,
740
+ :expiration_date => "05/2009"
741
+ }
742
+ )
743
+ result.success?.should == true
744
+ result.transaction.merchant_account_id.should == SpecHelper::NonDefaultMerchantAccountId
745
+ end
746
+
747
+ it "uses default merchant account when it is not specified" do
748
+ result = Braintree::Transaction.credit(
749
+ :amount => Braintree::Test::TransactionAmounts::Authorize,
750
+ :credit_card => {
751
+ :number => Braintree::Test::CreditCardNumbers::Visa,
752
+ :expiration_date => "05/2009"
753
+ }
754
+ )
755
+ result.success?.should == true
756
+ result.transaction.merchant_account_id.should == SpecHelper::DefaultMerchantAccountId
757
+ end
663
758
  end
664
759
 
665
760
  describe "self.credit!" do
@@ -721,6 +816,30 @@ describe Braintree::Transaction do
721
816
  transaction.credit_card_details.expiration_date.should == "05/2009"
722
817
  end
723
818
 
819
+ it "raises an error with a message if given invalid params" do
820
+ params = {
821
+ :transaction => {
822
+ :bad => "value",
823
+ :amount => Braintree::Test::TransactionAmounts::Authorize,
824
+ :credit_card => {
825
+ :number => Braintree::Test::CreditCardNumbers::Visa,
826
+ :expiration_date => "05/2009"
827
+ }
828
+ }
829
+ }
830
+ tr_data_params = {
831
+ :transaction => {
832
+ :type => "sale"
833
+ }
834
+ }
835
+ tr_data = Braintree::TransparentRedirect.transaction_data({:redirect_url => "http://example.com"}.merge(tr_data_params))
836
+ query_string_response = SpecHelper.simulate_form_post_for_tr(Braintree::Transaction.create_transaction_url, tr_data, params)
837
+
838
+ expect do
839
+ Braintree::Transaction.create_from_transparent_redirect(query_string_response)
840
+ end.to raise_error(Braintree::AuthorizationError, "Invalid params: transaction[bad]")
841
+ end
842
+
724
843
  it "can put any param in tr_data" do
725
844
  params = {
726
845
 
@@ -924,6 +1043,23 @@ describe Braintree::Transaction do
924
1043
  end
925
1044
 
926
1045
  describe "refund" do
1046
+ context "partial refunds" do
1047
+ it "allows partial refunds" do
1048
+ transaction = create_transaction_to_refund
1049
+ result = transaction.refund(transaction.amount / 2)
1050
+ result.success?.should == true
1051
+ result.new_transaction.type.should == "credit"
1052
+ end
1053
+
1054
+ it "does not all multiple refunds" do
1055
+ transaction = create_transaction_to_refund
1056
+ transaction.refund(transaction.amount / 2)
1057
+ result = transaction.refund(BigDecimal.new("1"))
1058
+ result.success?.should == false
1059
+ result.errors.for(:transaction).on(:base)[0].code.should == Braintree::ErrorCodes::Transaction::HasAlreadyBeenRefunded
1060
+ end
1061
+ end
1062
+
927
1063
  it "returns a successful result if successful" do
928
1064
  transaction = create_transaction_to_refund
929
1065
  transaction.status.should == Braintree::Transaction::Status::Settled
@@ -1044,101 +1180,6 @@ describe Braintree::Transaction do
1044
1180
  end
1045
1181
  end
1046
1182
 
1047
- describe "search" do
1048
- describe "advanced" do
1049
- it "pretty much works in one big fell swoop/hash" do
1050
- result = Braintree::Transaction.create(
1051
- :type => "sale",
1052
- :amount => Braintree::Test::TransactionAmounts::Authorize,
1053
- :credit_card => {
1054
- :number => Braintree::Test::CreditCardNumbers::Visa,
1055
- :expiration_date => "05/2009"
1056
- },
1057
- :order_id => "123",
1058
- :customer => {
1059
- :company => "Apple",
1060
- :fax => "312-555-1234",
1061
- :first_name => "Steve",
1062
- :last_name => "Jobs",
1063
- :phone => "614-555-1234",
1064
- :website => "http://www.apple.com",
1065
- },
1066
- :billing => {
1067
- :country_name => "United States of America",
1068
- :extended_address => "Apt 1F",
1069
- :locality => "Chicago",
1070
- :postal_code => "60622",
1071
- :region => "Illinois",
1072
- :street_address => "1234 W North Ave",
1073
- },
1074
- :shipping => {
1075
- :country_name => "United States of America",
1076
- :extended_address => "Apt 123",
1077
- :locality => "Bartlett",
1078
- :postal_code => "60004",
1079
- :region => "Illinois",
1080
- :street_address => "123 Main St",
1081
- }
1082
- )
1083
- result.success?.should == true
1084
- expected_transaction = result.transaction
1085
- search_criteria = {
1086
- :billing_country_name => {:is => "United States of America"},
1087
- :billing_extended_address => {:is => "Apt 1F"},
1088
- :billing_locality => {:is => "Chicago"},
1089
- :billing_postal_code => {:is => "60622"},
1090
- :billing_region => {:is => "Illinois"},
1091
- :billing_street_address => {:is => "1234 W North Ave"},
1092
- :credit_card_number => {:is => Braintree::Test::CreditCardNumbers::Visa},
1093
- :customer_company => {:is => "Apple"},
1094
- :customer_fax => {:is => "312-555-1234"},
1095
- :customer_first_name => {:is => "Steve"},
1096
- :customer_last_name => {:is => "Jobs"},
1097
- :customer_phone => {:is => "614-555-1234"},
1098
- :customer_website => {:is => "http://www.apple.com"},
1099
- :expiration_date => {:is => "05/2009"},
1100
- :order_id => {:is => "123"},
1101
- :shipping_country_name => {:is => "United States of America"},
1102
- :shipping_extended_address => {:is => "Apt 123"},
1103
- :shipping_locality => {:is => "Bartlett"},
1104
- :shipping_postal_code => {:is => "60004"},
1105
- :shipping_region => {:is => "Illinois"},
1106
- :shipping_street_address => {:is => "123 Main St"},
1107
- }
1108
- search_results = Braintree::Transaction.search(search_criteria)
1109
- search_results.should include(expected_transaction)
1110
- end
1111
-
1112
- it "properly parses the xml if only one transaction is found" do
1113
- transaction = Braintree::Transaction.create!(
1114
- :type => "sale",
1115
- :amount => Braintree::Test::TransactionAmounts::Authorize,
1116
- :credit_card => {
1117
- :number => Braintree::Test::CreditCardNumbers::Visa,
1118
- :expiration_date => "05/2009"
1119
- }
1120
- )
1121
- search_results = Braintree::Transaction.search(:transaction_id => {:is => transaction.id})
1122
- search_results.first.should == transaction
1123
- end
1124
- end
1125
-
1126
- describe "basic" do
1127
- it "returns transactions matching the given search terms" do
1128
- transactions = Braintree::Transaction.search "1111"
1129
- transactions._approximate_size.should > 0
1130
- end
1131
-
1132
- it "can iterate over the entire collection" do
1133
- transactions = Braintree::Transaction.search "411111"
1134
- transactions._approximate_size.should > 100
1135
-
1136
- transaction_ids = transactions.map {|t| t.id }.uniq.compact
1137
- transaction_ids.size.should == transactions._approximate_size
1138
- end
1139
- end
1140
- end
1141
-
1142
1183
  describe "status_history" do
1143
1184
  it "returns an array of StatusDetail" do
1144
1185
  transaction = Braintree::Transaction.sale!(
@@ -17,6 +17,10 @@ unless defined?(SPEC_HELPER_LOADED)
17
17
  Braintree::Configuration.logger.level = Logger::INFO
18
18
 
19
19
  module SpecHelper
20
+
21
+ DefaultMerchantAccountId = "sandbox_credit_card"
22
+ NonDefaultMerchantAccountId = "sandbox_credit_card_non_default"
23
+
20
24
  def self.stub_time_dot_now(desired_time)
21
25
  Time.class_eval do
22
26
  class << self
@@ -10,14 +10,56 @@ describe Braintree::CreditCard do
10
10
  end
11
11
 
12
12
  describe "self.create_signature" do
13
- it "should include customer_id" do
14
- Braintree::CreditCard._create_signature.should include(:customer_id)
13
+ it "should be what we expect" do
14
+ Braintree::CreditCard._create_signature.should == [
15
+ :cardholder_name,
16
+ :cvv,
17
+ :expiration_date,
18
+ :expiration_month,
19
+ :expiration_year,
20
+ :number,
21
+ :token,
22
+ {:options => [:make_default, :verify_card]},
23
+ {:billing_address => [
24
+ :company,
25
+ :country_name,
26
+ :extended_address,
27
+ :first_name,
28
+ :last_name,
29
+ :locality,
30
+ :postal_code,
31
+ :region,
32
+ :street_address
33
+ ]},
34
+ :customer_id
35
+ ]
15
36
  end
16
37
  end
17
38
 
18
39
  describe "self.update_signature" do
19
- it "should not include customer_id" do
20
- Braintree::CreditCard._update_signature.should_not include(:customer_id)
40
+ it "should be what we expect" do
41
+ Braintree::CreditCard._update_signature.should == [
42
+ :cardholder_name,
43
+ :cvv,
44
+ :expiration_date,
45
+ :expiration_month,
46
+ :expiration_year,
47
+ :number,
48
+ :token,
49
+ {:options => [:make_default, :verify_card]},
50
+ {:billing_address => [
51
+ :company,
52
+ :country_name,
53
+ :extended_address,
54
+ :first_name,
55
+ :last_name,
56
+ :locality,
57
+ :postal_code,
58
+ :region,
59
+ :street_address,
60
+ {:options => [:update_existing]}
61
+ ]}
62
+ ]
21
63
  end
22
64
  end
23
65
 
@@ -3,13 +3,13 @@ require File.dirname(__FILE__) + "/../spec_helper"
3
3
  describe Braintree::Subscription do
4
4
  context "price" do
5
5
  it "accepts price as either a String or a BigDecimal" do
6
- Braintree::Subscription.new(:price => "12.34", :transactions => []).price.should == BigDecimal.new("12.34")
7
- Braintree::Subscription.new(:price => BigDecimal.new("12.34"), :transactions => []).price.should == BigDecimal.new("12.34")
6
+ Braintree::Subscription._new(:price => "12.34", :transactions => []).price.should == BigDecimal.new("12.34")
7
+ Braintree::Subscription._new(:price => BigDecimal.new("12.34"), :transactions => []).price.should == BigDecimal.new("12.34")
8
8
  end
9
9
 
10
10
  it "blows up if price is not a string or BigDecimal" do
11
11
  expect {
12
- Braintree::Subscription.new(:price => 12.34, :transactions => [])
12
+ Braintree::Subscription._new(:price => 12.34, :transactions => [])
13
13
  }.to raise_error(/Argument must be a String or BigDecimal/)
14
14
  end
15
15
  end
@@ -23,4 +23,23 @@ describe Braintree::Subscription do
23
23
  end.should raise_error(ArgumentError)
24
24
  end
25
25
  end
26
+
27
+ describe "==" do
28
+ it "returns true for subscriptions with the same id" do
29
+ subscription1 = Braintree::Subscription._new(:id => "123", :transactions => [])
30
+ subscription2 = Braintree::Subscription._new(:id => "123", :transactions => [])
31
+ subscription1.should == subscription2
32
+ end
33
+
34
+ it "returns false for subscriptions with different ids" do
35
+ subscription1 = Braintree::Subscription._new(:id => "123", :transactions => [])
36
+ subscription2 = Braintree::Subscription._new(:id => "not_123", :transactions => [])
37
+ subscription1.should_not == subscription2
38
+ end
39
+
40
+ it "returns false if not comparing to a subscription" do
41
+ subscription = Braintree::Subscription._new(:id => "123", :transactions => [])
42
+ subscription.should_not == "not a subscription"
43
+ end
44
+ end
26
45
  end
@@ -0,0 +1,24 @@
1
+ require File.dirname(__FILE__) + "/../spec_helper"
2
+
3
+ describe Braintree::TransactionSearch do
4
+ it "overrides previous 'is' with new 'is' for the same field" do
5
+ search = Braintree::TransactionSearch.new
6
+ search.billing_company.is "one"
7
+ search.billing_company.is "two"
8
+ search.to_hash.should == {:billing_company => {:is => "two"}}
9
+ end
10
+
11
+ it "overrides previous 'in' with new 'in' for the same field" do
12
+ search = Braintree::TransactionSearch.new
13
+ search.status.in Braintree::Transaction::Status::Authorized
14
+ search.status.in Braintree::Transaction::Status::SubmittedForSettlement
15
+ search.to_hash.should == {:status => [Braintree::Transaction::Status::SubmittedForSettlement]}
16
+ end
17
+
18
+ it "raises if the operator 'is' is left off" do
19
+ search = Braintree::TransactionSearch.new
20
+ expect do
21
+ search.billing_company "one"
22
+ end.to raise_error(RuntimeError, "An operator is required")
23
+ end
24
+ end
@@ -127,7 +127,7 @@ describe Braintree::Transaction do
127
127
  end
128
128
 
129
129
  describe "==" do
130
- it "returns true when it should" do
130
+ it "returns true for transactions with the same id" do
131
131
  first = Braintree::Transaction._new(:id => 123)
132
132
  second = Braintree::Transaction._new(:id => 123)
133
133
 
@@ -135,13 +135,24 @@ describe Braintree::Transaction do
135
135
  second.should == first
136
136
  end
137
137
 
138
- it "returns false when it should" do
138
+ it "returns false for transactions with different ids" do
139
139
  first = Braintree::Transaction._new(:id => 123)
140
140
  second = Braintree::Transaction._new(:id => 124)
141
141
 
142
142
  first.should_not == second
143
143
  second.should_not == first
144
144
  end
145
+
146
+ it "returns false when comparing to nil" do
147
+ Braintree::Transaction._new({}).should_not == nil
148
+ end
149
+
150
+ it "returns false when comparing to non-transactions" do
151
+ same_id_different_object = Object.new
152
+ def same_id_different_object.id; 123; end
153
+ transaction = Braintree::Transaction._new(:id => 123)
154
+ transaction.should_not == same_id_different_object
155
+ end
145
156
  end
146
157
 
147
158
  describe "new" do