solidus_paypal_braintree 0.4.0 → 1.0.0
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 +4 -4
- data/.circleci/config.yml +40 -0
- data/.gem_release.yml +5 -0
- data/.github/stale.yml +17 -0
- data/.gitignore +18 -0
- data/.rspec +2 -0
- data/.rubocop.yml +68 -0
- data/CHANGELOG.md +258 -0
- data/Gemfile +43 -0
- data/LICENSE +2 -2
- data/README.md +77 -23
- data/Rakefile +4 -25
- data/app/assets/javascripts/solidus_paypal_braintree/checkout.js +32 -3
- data/app/assets/javascripts/solidus_paypal_braintree/client.js +23 -4
- data/app/assets/javascripts/solidus_paypal_braintree/constants.js +19 -0
- data/app/assets/javascripts/solidus_paypal_braintree/frontend.js +1 -0
- data/app/assets/javascripts/solidus_paypal_braintree/hosted_form.js +15 -5
- data/app/assets/javascripts/solidus_paypal_braintree/paypal_button.js +47 -20
- data/app/assets/javascripts/solidus_paypal_braintree/paypal_messaging.js +22 -0
- data/app/decorators/controllers/solidus_paypal_braintree/admin_payments_controller_decorator.rb +11 -0
- data/app/decorators/controllers/solidus_paypal_braintree/checkout_controller_decorator.rb +11 -0
- data/app/decorators/controllers/solidus_paypal_braintree/client_tokens_controller.rb +41 -0
- data/app/decorators/controllers/solidus_paypal_braintree/orders_controller_decorator.rb +11 -0
- data/app/decorators/models/solidus_paypal_braintree/spree/store_decorator.rb +20 -0
- data/app/decorators/models/solidus_paypal_braintree/spree/user_decorator.rb +13 -0
- data/app/helpers/solidus_paypal_braintree/braintree_admin_helper.rb +23 -0
- data/app/helpers/solidus_paypal_braintree/braintree_checkout_helper.rb +46 -0
- data/app/models/application_record.rb +2 -0
- data/app/models/solidus_paypal_braintree/address.rb +30 -0
- data/app/models/solidus_paypal_braintree/configuration.rb +26 -3
- data/app/models/solidus_paypal_braintree/customer.rb +7 -3
- data/app/models/solidus_paypal_braintree/gateway.rb +52 -20
- data/app/models/solidus_paypal_braintree/response.rb +3 -2
- data/app/models/solidus_paypal_braintree/source.rb +21 -7
- data/app/models/solidus_paypal_braintree/transaction.rb +2 -0
- data/app/models/solidus_paypal_braintree/transaction_address.rb +30 -12
- data/app/models/solidus_paypal_braintree/transaction_import.rb +13 -9
- data/app/views/spree/api/payments/source_views/_paypal_braintree.json.jbuilder +3 -0
- data/app/views/spree/checkout/existing_payment/_paypal_braintree.html.erb +10 -0
- data/app/views/spree/shared/_apple_pay_button.html.erb +2 -2
- data/app/views/spree/shared/_braintree_errors.html.erb +11 -17
- data/app/views/spree/shared/_braintree_hosted_fields.html.erb +24 -9
- data/app/views/spree/shared/_paypal_braintree_head_scripts.html.erb +9 -6
- data/app/views/spree/shared/_paypal_cart_button.html.erb +16 -2
- data/app/views/spree/shared/_paypal_messaging.html.erb +13 -0
- data/bin/console +17 -0
- data/bin/rails +15 -0
- data/bin/setup +8 -0
- data/config/locales/en.yml +10 -0
- data/config/locales/it.yml +51 -8
- data/config/routes.rb +2 -0
- data/db/migrate/20160906201711_create_solidus_paypal_braintree_customers.rb +3 -1
- data/db/migrate/20161125172005_add_braintree_configuration_to_stores.rb +5 -7
- data/db/migrate/20170505193712_add_null_constraint_to_sources.rb +3 -1
- data/db/migrate/20190705115327_add_paypal_button_preferences_to_braintree_configurations.rb +5 -0
- data/db/migrate/20190911141712_add_3d_secure_to_braintree_configuration.rb +5 -0
- data/lib/controllers/backend/solidus_paypal_braintree/configurations_controller.rb +20 -5
- data/lib/controllers/frontend/solidus_paypal_braintree/checkouts_controller.rb +25 -21
- data/lib/controllers/frontend/solidus_paypal_braintree/transactions_controller.rb +55 -51
- data/lib/generators/solidus_paypal_braintree/install/install_generator.rb +7 -5
- data/lib/solidus_paypal_braintree.rb +4 -0
- data/lib/solidus_paypal_braintree/country_mapper.rb +4 -2
- data/lib/solidus_paypal_braintree/engine.rb +11 -11
- data/lib/solidus_paypal_braintree/factories.rb +8 -4
- data/lib/solidus_paypal_braintree/request_protection.rb +3 -0
- data/lib/solidus_paypal_braintree/version.rb +3 -1
- data/lib/views/backend/solidus_paypal_braintree/configurations/list.html.erb +30 -5
- data/lib/views/backend/spree/admin/payments/source_forms/_paypal_braintree.html.erb +2 -2
- data/lib/views/backend/spree/admin/payments/source_views/_paypal_braintree.html.erb +2 -2
- data/lib/views/backend_v1.2/spree/admin/payments/source_forms/_paypal_braintree.html.erb +2 -2
- data/lib/views/frontend/spree/checkout/payment/_paypal_braintree.html.erb +4 -2
- data/lib/views/frontend/spree/shared/_paypal_checkout_button.html.erb +30 -0
- data/solidus_paypal_braintree.gemspec +42 -0
- data/spec/controllers/solidus_paypal_braintree/checkouts_controller_spec.rb +99 -0
- data/spec/controllers/solidus_paypal_braintree/client_tokens_controller_spec.rb +55 -0
- data/spec/controllers/solidus_paypal_braintree/configurations_controller_spec.rb +73 -0
- data/spec/controllers/solidus_paypal_braintree/transactions_controller_spec.rb +183 -0
- data/spec/features/backend/configuration_spec.rb +23 -0
- data/spec/features/backend/new_payment_spec.rb +137 -0
- data/spec/features/frontend/braintree_credit_card_checkout_spec.rb +187 -0
- data/spec/features/frontend/paypal_checkout_spec.rb +166 -0
- data/spec/fixtures/cassettes/admin/invalid_credit_card.yml +63 -0
- data/spec/fixtures/cassettes/admin/resubmit_credit_card.yml +352 -0
- data/spec/fixtures/cassettes/admin/valid_credit_card.yml +412 -0
- data/spec/fixtures/cassettes/braintree/create_profile.yml +71 -0
- data/spec/fixtures/cassettes/braintree/generate_token.yml +63 -0
- data/spec/fixtures/cassettes/braintree/token.yml +63 -0
- data/spec/fixtures/cassettes/checkout/invalid_credit_card.yml +63 -0
- data/spec/fixtures/cassettes/checkout/resubmit_credit_card.yml +216 -0
- data/spec/fixtures/cassettes/checkout/update.yml +71 -0
- data/spec/fixtures/cassettes/checkout/valid_credit_card.yml +156 -0
- data/spec/fixtures/cassettes/gateway/authorize.yml +86 -0
- data/spec/fixtures/cassettes/gateway/authorize/credit_card/address.yml +86 -0
- data/spec/fixtures/cassettes/gateway/authorize/merchant_account/EUR.yml +154 -0
- data/spec/fixtures/cassettes/gateway/authorize/paypal/EUR.yml +90 -0
- data/spec/fixtures/cassettes/gateway/authorize/paypal/address.yml +90 -0
- data/spec/fixtures/cassettes/gateway/authorized_transaction.yml +73 -0
- data/spec/fixtures/cassettes/gateway/cancel/missing.yml +63 -0
- data/spec/fixtures/cassettes/gateway/cancel/refunds.yml +272 -0
- data/spec/fixtures/cassettes/gateway/cancel/void.yml +201 -0
- data/spec/fixtures/cassettes/gateway/capture.yml +141 -0
- data/spec/fixtures/cassettes/gateway/complete.yml +157 -0
- data/spec/fixtures/cassettes/gateway/credit.yml +208 -0
- data/spec/fixtures/cassettes/gateway/purchase.yml +87 -0
- data/spec/fixtures/cassettes/gateway/settled_transaction.yml +140 -0
- data/spec/fixtures/cassettes/gateway/void.yml +137 -0
- data/spec/fixtures/cassettes/source/card_type.yml +267 -0
- data/spec/fixtures/cassettes/source/last4.yml +267 -0
- data/spec/fixtures/cassettes/transaction/import/valid.yml +71 -0
- data/spec/fixtures/cassettes/transaction/import/valid/capture.yml +224 -0
- data/spec/fixtures/views/spree/orders/edit.html.erb +50 -0
- data/spec/helpers/solidus_paypal_braintree/braintree_admin_helper_spec.rb +17 -0
- data/spec/models/solidus_paypal_braintree/address_spec.rb +51 -0
- data/spec/models/solidus_paypal_braintree/avs_result_spec.rb +317 -0
- data/spec/models/solidus_paypal_braintree/gateway_spec.rb +692 -0
- data/spec/models/solidus_paypal_braintree/response_spec.rb +280 -0
- data/spec/models/solidus_paypal_braintree/source_spec.rb +360 -0
- data/spec/models/solidus_paypal_braintree/transaction_address_spec.rb +253 -0
- data/spec/models/solidus_paypal_braintree/transaction_import_spec.rb +283 -0
- data/spec/models/solidus_paypal_braintree/transaction_spec.rb +85 -0
- data/spec/models/spree/store_spec.rb +14 -0
- data/spec/requests/spree/api/orders_controller_spec.rb +36 -0
- data/spec/spec_helper.rb +26 -0
- data/spec/support/capybara.rb +7 -0
- data/spec/support/factories.rb +2 -0
- data/spec/support/gateway_helpers.rb +29 -0
- data/spec/support/order_ready_for_payment.rb +37 -0
- data/spec/support/vcr.rb +42 -0
- data/spec/support/views.rb +1 -0
- metadata +182 -194
- data/app/controllers/solidus_paypal_braintree/client_tokens_controller.rb +0 -22
- data/app/helpers/braintree_admin_helper.rb +0 -18
- data/app/models/spree/store_decorator.rb +0 -11
- data/app/views/spree/shared/_paypal_checkout_button.html.erb +0 -27
- data/config/initializers/braintree.rb +0 -1
@@ -0,0 +1,22 @@
|
|
1
|
+
//= require solidus_paypal_braintree/constants
|
2
|
+
|
3
|
+
SolidusPaypalBraintree.PaypalMessaging = function(paypalOptions) {
|
4
|
+
this._paypalOptions = paypalOptions || {};
|
5
|
+
|
6
|
+
this._client = null;
|
7
|
+
};
|
8
|
+
|
9
|
+
SolidusPaypalBraintree.PaypalMessaging.prototype.initialize = function() {
|
10
|
+
this._client = new SolidusPaypalBraintree.createClient({usePaypal: true});
|
11
|
+
|
12
|
+
return this._client.initialize().then(this.initializeCallback.bind(this));
|
13
|
+
};
|
14
|
+
|
15
|
+
SolidusPaypalBraintree.PaypalMessaging.prototype.initializeCallback = function() {
|
16
|
+
this._paymentMethodId = this._client.paymentMethodId;
|
17
|
+
|
18
|
+
this._client.getPaypalInstance().loadPayPalSDK({
|
19
|
+
currency: this._paypalOptions.currency,
|
20
|
+
components: "messages"
|
21
|
+
})
|
22
|
+
};
|
data/app/decorators/controllers/solidus_paypal_braintree/admin_payments_controller_decorator.rb
ADDED
@@ -0,0 +1,11 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module SolidusPaypalBraintree
|
4
|
+
module AdminPaymentsControllerDecorator
|
5
|
+
def self.prepended(base)
|
6
|
+
base.helper ::SolidusPaypalBraintree::BraintreeAdminHelper
|
7
|
+
end
|
8
|
+
|
9
|
+
::Spree::Admin::PaymentsController.prepend(self)
|
10
|
+
end
|
11
|
+
end
|
@@ -0,0 +1,41 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module SolidusPaypalBraintree
|
4
|
+
class ClientTokensController < ::Spree::Api::BaseController
|
5
|
+
skip_before_action :authenticate_user
|
6
|
+
|
7
|
+
before_action :load_gateway
|
8
|
+
|
9
|
+
def create
|
10
|
+
token = @gateway.generate_token
|
11
|
+
if token
|
12
|
+
render json: { client_token: token, payment_method_id: @gateway.id }
|
13
|
+
else
|
14
|
+
render json: { error: Gateway::TOKEN_GENERATION_DISABLED_MESSAGE }, status: :unprocessable_entity
|
15
|
+
end
|
16
|
+
end
|
17
|
+
|
18
|
+
private
|
19
|
+
|
20
|
+
def load_gateway
|
21
|
+
if params[:payment_method_id]
|
22
|
+
@gateway = ::SolidusPaypalBraintree::Gateway.find(params[:payment_method_id])
|
23
|
+
else
|
24
|
+
store_payment_methods_scope =
|
25
|
+
if current_store.payment_methods.empty?
|
26
|
+
::SolidusPaypalBraintree::Gateway.all
|
27
|
+
else
|
28
|
+
::SolidusPaypalBraintree::Gateway.where(id: current_store.payment_method_ids)
|
29
|
+
end
|
30
|
+
@gateway = ::SolidusPaypalBraintree::Gateway.where(active: true).merge(store_payment_methods_scope).first!
|
31
|
+
end
|
32
|
+
end
|
33
|
+
|
34
|
+
def generate_token
|
35
|
+
@gateway.generate_token
|
36
|
+
rescue ::SolidusPaypalBraintree::Gateway::TokenGenerationDisabledError => e
|
37
|
+
Rails.logger.error e
|
38
|
+
nil
|
39
|
+
end
|
40
|
+
end
|
41
|
+
end
|
@@ -0,0 +1,20 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module SolidusPaypalBraintree
|
4
|
+
module Spree
|
5
|
+
module StoreDecorator
|
6
|
+
def self.prepended(base)
|
7
|
+
base.has_one :braintree_configuration, class_name: "SolidusPaypalBraintree::Configuration", dependent: :destroy
|
8
|
+
base.before_create :build_default_configuration
|
9
|
+
end
|
10
|
+
|
11
|
+
private
|
12
|
+
|
13
|
+
def build_default_configuration
|
14
|
+
build_braintree_configuration unless braintree_configuration
|
15
|
+
end
|
16
|
+
|
17
|
+
::Spree::Store.prepend self
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
@@ -0,0 +1,13 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module SolidusPaypalBraintree
|
4
|
+
module Spree
|
5
|
+
module UserDecorator
|
6
|
+
def self.prepended(base)
|
7
|
+
base.has_one :braintree_customer, class_name: 'SolidusPaypalBraintree::Customer', inverse_of: :user
|
8
|
+
end
|
9
|
+
|
10
|
+
::Spree.user_class.prepend self
|
11
|
+
end
|
12
|
+
end
|
13
|
+
end
|
@@ -0,0 +1,23 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module SolidusPaypalBraintree
|
4
|
+
module BraintreeAdminHelper
|
5
|
+
# Returns a link to the Braintree web UI for the given Braintree payment
|
6
|
+
def braintree_transaction_link(payment)
|
7
|
+
environment = payment.payment_method.preferred_environment == 'sandbox' ? 'sandbox' : 'www'
|
8
|
+
merchant_id = payment.payment_method.preferred_merchant_id
|
9
|
+
response_code = payment.response_code
|
10
|
+
|
11
|
+
return if response_code.blank?
|
12
|
+
return response_code if merchant_id.blank?
|
13
|
+
|
14
|
+
link_to(
|
15
|
+
response_code,
|
16
|
+
"https://#{environment}.braintreegateway.com/merchants/#{merchant_id}/transactions/#{response_code}",
|
17
|
+
title: 'Show payment on Braintree',
|
18
|
+
target: '_blank',
|
19
|
+
rel: 'noopener'
|
20
|
+
)
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
@@ -0,0 +1,46 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module SolidusPaypalBraintree
|
4
|
+
module BraintreeCheckoutHelper
|
5
|
+
def braintree_3ds_options_for(order)
|
6
|
+
ship_address = order.ship_address
|
7
|
+
bill_address = order.bill_address
|
8
|
+
|
9
|
+
{
|
10
|
+
nonce: nil, # populated after tokenization
|
11
|
+
bin: nil, # populated after tokenization
|
12
|
+
onLookupComplete: nil, # populated after tokenization
|
13
|
+
amount: order.total,
|
14
|
+
email: order.email,
|
15
|
+
billingAddress: {
|
16
|
+
givenName: bill_address.firstname,
|
17
|
+
surname: bill_address.lastname,
|
18
|
+
phoneNumber: bill_address.phone,
|
19
|
+
streetAddress: bill_address.address1,
|
20
|
+
extendedAddress: bill_address.address2,
|
21
|
+
locality: bill_address.city,
|
22
|
+
region: bill_address.state&.name,
|
23
|
+
postalCode: bill_address.zipcode,
|
24
|
+
countryCodeAlpha2: bill_address.country&.iso,
|
25
|
+
},
|
26
|
+
additionalInformation: {
|
27
|
+
shippingGivenName: ship_address.firstname,
|
28
|
+
shippingSurname: ship_address.lastname,
|
29
|
+
shippingPhone: ship_address.phone,
|
30
|
+
shippingAddress: {
|
31
|
+
streedAddress: ship_address.address1,
|
32
|
+
extendedAddress: ship_address.address2,
|
33
|
+
locality: ship_address.city,
|
34
|
+
region: ship_address.state&.name,
|
35
|
+
postalCode: ship_address.zipcode,
|
36
|
+
countryCodeAlpha2: ship_address.country&.iso,
|
37
|
+
}
|
38
|
+
}
|
39
|
+
}
|
40
|
+
end
|
41
|
+
|
42
|
+
def paypal_button_preference(key, store:)
|
43
|
+
store.braintree_configuration.preferences[key]
|
44
|
+
end
|
45
|
+
end
|
46
|
+
end
|
@@ -0,0 +1,30 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module SolidusPaypalBraintree
|
4
|
+
class Address
|
5
|
+
def initialize(spree_address)
|
6
|
+
@spree_address = spree_address
|
7
|
+
end
|
8
|
+
|
9
|
+
def to_json(*_args)
|
10
|
+
address_hash = {
|
11
|
+
line1: spree_address.address1,
|
12
|
+
line2: spree_address.address2,
|
13
|
+
city: spree_address.city,
|
14
|
+
postalCode: spree_address.zipcode,
|
15
|
+
countryCode: spree_address.country.iso,
|
16
|
+
phone: spree_address.phone,
|
17
|
+
recipientName: spree_address.full_name
|
18
|
+
}
|
19
|
+
|
20
|
+
if ::Spree::Config.address_requires_state && spree_address.country.states_required
|
21
|
+
address_hash[:state] = spree_address.state.name
|
22
|
+
end
|
23
|
+
address_hash.to_json
|
24
|
+
end
|
25
|
+
|
26
|
+
private
|
27
|
+
|
28
|
+
attr_reader :spree_address
|
29
|
+
end
|
30
|
+
end
|
@@ -1,5 +1,28 @@
|
|
1
|
-
|
2
|
-
belongs_to :store, class_name: 'Spree::Store'
|
1
|
+
# frozen_string_literal: true
|
3
2
|
|
4
|
-
|
3
|
+
module SolidusPaypalBraintree
|
4
|
+
class Configuration < ::Spree::Base
|
5
|
+
PAYPAL_BUTTON_PREFERENCES = {
|
6
|
+
color: { availables: %w[gold blue silver white black], default: 'white' },
|
7
|
+
shape: { availables: %w[pill rect], default: 'rect' },
|
8
|
+
label: { availables: %w[checkout credit pay buynow paypal installment], default: 'checkout' },
|
9
|
+
tagline: { availables: %w[true false], default: 'false' },
|
10
|
+
layout: { availables: %w[horizontal vertical], default: 'horizontal' },
|
11
|
+
messaging: { availables: %w[true false], default: 'false' }
|
12
|
+
}.freeze
|
13
|
+
|
14
|
+
belongs_to :store, class_name: 'Spree::Store'
|
15
|
+
|
16
|
+
validates :store, presence: true
|
17
|
+
|
18
|
+
# Preferences for Paypal button
|
19
|
+
PAYPAL_BUTTON_PREFERENCES.each do |name, desc|
|
20
|
+
preference_name = "paypal_button_#{name}".to_sym
|
21
|
+
attribute_name = "preferred_#{preference_name}".to_sym
|
22
|
+
|
23
|
+
preference preference_name, :string, default: desc[:default]
|
24
|
+
|
25
|
+
validates attribute_name, inclusion: desc[:availables]
|
26
|
+
end
|
27
|
+
end
|
5
28
|
end
|
@@ -1,4 +1,8 @@
|
|
1
|
-
|
2
|
-
|
3
|
-
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module SolidusPaypalBraintree
|
4
|
+
class Customer < ApplicationRecord
|
5
|
+
belongs_to :user, class_name: ::Spree::UserClassHandle.new, optional: true
|
6
|
+
has_many :sources, class_name: "SolidusPaypalBraintree::Source", inverse_of: :customer, dependent: :destroy
|
7
|
+
end
|
4
8
|
end
|
@@ -1,22 +1,26 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
require 'braintree'
|
2
4
|
|
3
5
|
module SolidusPaypalBraintree
|
4
6
|
class Gateway < ::Spree::PaymentMethod
|
5
7
|
include RequestProtection
|
6
8
|
|
9
|
+
class TokenGenerationDisabledError < StandardError; end
|
10
|
+
|
7
11
|
# Error message from Braintree that gets returned by a non voidable transaction
|
8
|
-
NON_VOIDABLE_STATUS_ERROR_REGEXP = /can only be voided if status is authorized
|
12
|
+
NON_VOIDABLE_STATUS_ERROR_REGEXP = /can only be voided if status is authorized/.freeze
|
9
13
|
|
10
14
|
TOKEN_GENERATION_DISABLED_MESSAGE = 'Token generation is disabled.' \
|
11
15
|
' To re-enable set the `token_generation_enabled` preference on the' \
|
12
|
-
' gateway to `true`.'
|
16
|
+
' gateway to `true`.'
|
13
17
|
|
14
18
|
ALLOWED_BRAINTREE_OPTIONS = [
|
15
19
|
:device_data,
|
16
20
|
:device_session_id,
|
17
21
|
:merchant_account_id,
|
18
22
|
:order_id
|
19
|
-
]
|
23
|
+
].freeze
|
20
24
|
|
21
25
|
VOIDABLE_STATUSES = [
|
22
26
|
Braintree::Transaction::Status::SubmittedForSettlement,
|
@@ -35,9 +39,22 @@ module SolidusPaypalBraintree
|
|
35
39
|
preference(:merchant_id, :string, default: nil)
|
36
40
|
preference(:public_key, :string, default: nil)
|
37
41
|
preference(:private_key, :string, default: nil)
|
42
|
+
preference(:http_open_timeout, :integer, default: 60)
|
43
|
+
preference(:http_read_timeout, :integer, default: 60)
|
38
44
|
preference(:merchant_currency_map, :hash, default: {})
|
39
45
|
preference(:paypal_payee_email_map, :hash, default: {})
|
40
46
|
|
47
|
+
# Which checkout flow to use (vault/checkout)
|
48
|
+
preference(:paypal_flow, :string, default: 'vault')
|
49
|
+
|
50
|
+
# A hash that gets passed to the `style` key when initializing the credit card fields.
|
51
|
+
# See https://developers.braintreepayments.com/guides/hosted-fields/styling/javascript/v3
|
52
|
+
preference(:credit_card_fields_style, :hash, default: {})
|
53
|
+
|
54
|
+
# A hash that gets its keys passed to the associated braintree field placeholder tag.
|
55
|
+
# Example: { number: "Enter card number", cvv: "Enter CVV", expirationDate: "mm/yy" }
|
56
|
+
preference(:placeholder_text, :hash, default: {})
|
57
|
+
|
41
58
|
def partial_name
|
42
59
|
"paypal_braintree"
|
43
60
|
end
|
@@ -57,6 +74,8 @@ module SolidusPaypalBraintree
|
|
57
74
|
merchant_id: preferred_merchant_id,
|
58
75
|
public_key: preferred_public_key,
|
59
76
|
private_key: preferred_private_key,
|
77
|
+
http_open_timeout: preferred_http_open_timeout,
|
78
|
+
http_read_timeout: preferred_http_read_timeout,
|
60
79
|
logger: logger
|
61
80
|
}
|
62
81
|
end
|
@@ -73,7 +92,7 @@ module SolidusPaypalBraintree
|
|
73
92
|
protected_request do
|
74
93
|
result = braintree.transaction.sale(
|
75
94
|
amount: dollars(money_cents),
|
76
|
-
**transaction_options(source, gateway_options, true)
|
95
|
+
**transaction_options(source, gateway_options, submit_for_settlement: true)
|
77
96
|
)
|
78
97
|
|
79
98
|
Response.build(result)
|
@@ -200,7 +219,7 @@ module SolidusPaypalBraintree
|
|
200
219
|
return if source.token.present? || source.customer.present? || source.nonce.nil?
|
201
220
|
|
202
221
|
result = braintree.customer.create(customer_profile_params(payment))
|
203
|
-
fail Spree::Core::GatewayError, result.message unless result.success?
|
222
|
+
fail ::Spree::Core::GatewayError, result.message unless result.success?
|
204
223
|
|
205
224
|
customer = result.customer
|
206
225
|
|
@@ -213,12 +232,12 @@ module SolidusPaypalBraintree
|
|
213
232
|
end
|
214
233
|
end
|
215
234
|
|
235
|
+
# @raise [TokenGenerationDisabledError]
|
236
|
+
# If `preferred_token_generation_enabled` is false
|
237
|
+
#
|
216
238
|
# @return [String]
|
217
239
|
# The token that should be used along with the Braintree js-client sdk.
|
218
240
|
#
|
219
|
-
# returns an error message if `preferred_token_generation_enabled` is
|
220
|
-
# set to false.
|
221
|
-
#
|
222
241
|
# @example
|
223
242
|
# <script>
|
224
243
|
# var token = #{Spree::Braintree::Gateway.first!.generate_token}
|
@@ -233,7 +252,10 @@ module SolidusPaypalBraintree
|
|
233
252
|
# );
|
234
253
|
# </script>
|
235
254
|
def generate_token
|
236
|
-
|
255
|
+
unless preferred_token_generation_enabled
|
256
|
+
raise TokenGenerationDisabledError, TOKEN_GENERATION_DISABLED_MESSAGE
|
257
|
+
end
|
258
|
+
|
237
259
|
braintree.client_token.generate
|
238
260
|
end
|
239
261
|
|
@@ -261,6 +283,12 @@ module SolidusPaypalBraintree
|
|
261
283
|
|
262
284
|
private
|
263
285
|
|
286
|
+
# Whether to store this payment method in the PayPal Vault. This only works when the checkout
|
287
|
+
# flow is "vault", so make sure to call +super+ if you override it.
|
288
|
+
def store_in_vault
|
289
|
+
preferred_paypal_flow == 'vault'
|
290
|
+
end
|
291
|
+
|
264
292
|
def logger
|
265
293
|
Braintree::Configuration.logger.clone.tap do |logger|
|
266
294
|
logger.level = Rails.logger.level
|
@@ -279,20 +307,24 @@ module SolidusPaypalBraintree
|
|
279
307
|
JSON.parse(preference_string.gsub("=>", ":"))
|
280
308
|
end
|
281
309
|
|
282
|
-
def convert_preference_value(value, type)
|
310
|
+
def convert_preference_value(value, type, preference_encryptor = nil)
|
283
311
|
if type == :hash && value.is_a?(String)
|
284
312
|
value = to_hash(value)
|
285
313
|
end
|
286
|
-
|
314
|
+
if method(__method__).super_method.arity == 3
|
315
|
+
super
|
316
|
+
else
|
317
|
+
super(value, type)
|
318
|
+
end
|
287
319
|
end
|
288
320
|
|
289
|
-
def transaction_options(source, options, submit_for_settlement
|
321
|
+
def transaction_options(source, options, submit_for_settlement: false)
|
290
322
|
params = options.select do |key, _|
|
291
323
|
ALLOWED_BRAINTREE_OPTIONS.include?(key)
|
292
324
|
end
|
293
325
|
|
294
326
|
params[:channel] = "Solidus"
|
295
|
-
params[:options] = { store_in_vault_on_success:
|
327
|
+
params[:options] = { store_in_vault_on_success: store_in_vault }
|
296
328
|
|
297
329
|
if submit_for_settlement
|
298
330
|
params[:options][:submit_for_settlement] = true
|
@@ -349,21 +381,21 @@ module SolidusPaypalBraintree
|
|
349
381
|
end
|
350
382
|
|
351
383
|
def merchant_account_for(_source, options)
|
352
|
-
|
353
|
-
|
354
|
-
|
384
|
+
return unless options[:currency]
|
385
|
+
|
386
|
+
preferred_merchant_currency_map[options[:currency]]
|
355
387
|
end
|
356
388
|
|
357
389
|
def paypal_payee_email_for(source, options)
|
358
|
-
|
359
|
-
|
360
|
-
|
390
|
+
return unless source.paypal?
|
391
|
+
|
392
|
+
preferred_paypal_payee_email_map[options[:currency]]
|
361
393
|
end
|
362
394
|
|
363
395
|
def customer_profile_params(payment)
|
364
396
|
params = {}
|
365
397
|
|
366
|
-
if payment.source.try(:nonce)
|
398
|
+
if store_in_vault && payment.source.try(:nonce)
|
367
399
|
params[:payment_method_nonce] = payment.source.nonce
|
368
400
|
end
|
369
401
|
|