Class: Receptionist::CreditCardChecker
- Inherits:
-
Object
- Object
- Receptionist::CreditCardChecker
- Includes:
- ElasticAPM::SpanHelpers
- Defined in:
- app/my_lib/receptionist/credit_card_checker.rb
Overview
Manage credit card
TODO This class should be refactored by create another class that resposible to handle OmiseToken and HungryHub user relationship myabe we could name it 'CreditCardLinker'
Instance Attribute Summary collapse
-
#ip_address ⇒ Object
Returns the value of attribute ip_address.
-
#provider ⇒ Object
Returns the value of attribute provider.
-
#reservation ⇒ Object
Returns the value of attribute reservation.
-
#restaurant ⇒ Object
Returns the value of attribute restaurant.
-
#token ⇒ Object
Returns the value of attribute token.
-
#use_3d_secure ⇒ Object
Returns the value of attribute use_3d_secure.
-
#user ⇒ Object
Returns the value of attribute user.
Class Method Summary collapse
Instance Method Summary collapse
- #card_token_valid_based_on_provider? ⇒ Boolean
-
#check ⇒ Object
reservation should be saved to database in block code.
- #credit_card_given? ⇒ Boolean
-
#initialize(reservation, token = nil, use_3d_secure: false, ip_address: nil, provider: nil) ⇒ CreditCardChecker
constructor
A new instance of CreditCardChecker.
- #required? ⇒ Boolean
- #valid? ⇒ Boolean
Constructor Details
#initialize(reservation, token = nil, use_3d_secure: false, ip_address: nil, provider: nil) ⇒ CreditCardChecker
Returns a new instance of CreditCardChecker.
14 15 16 17 18 19 20 21 22 23 24 25 |
# File 'app/my_lib/receptionist/credit_card_checker.rb', line 14 def initialize(reservation, token = nil, use_3d_secure: false, ip_address: nil, provider: nil) @reservation = reservation @restaurant = reservation.restaurant @user = reservation.user @token = token @ip_address = ip_address @provider = provider # TODO: REMOVE use_3d_secure later @use_3d_secure = use_3d_secure.to_s == 'true' BUSINESS_LOGGER.set_business_context({ reservation_id: reservation.id }) end |
Instance Attribute Details
#ip_address ⇒ Object
Returns the value of attribute ip_address.
12 13 14 |
# File 'app/my_lib/receptionist/credit_card_checker.rb', line 12 def ip_address @ip_address end |
#provider ⇒ Object
Returns the value of attribute provider.
12 13 14 |
# File 'app/my_lib/receptionist/credit_card_checker.rb', line 12 def provider @provider end |
#reservation ⇒ Object
Returns the value of attribute reservation.
12 13 14 |
# File 'app/my_lib/receptionist/credit_card_checker.rb', line 12 def reservation @reservation end |
#restaurant ⇒ Object
Returns the value of attribute restaurant.
12 13 14 |
# File 'app/my_lib/receptionist/credit_card_checker.rb', line 12 def restaurant @restaurant end |
#token ⇒ Object
Returns the value of attribute token.
12 13 14 |
# File 'app/my_lib/receptionist/credit_card_checker.rb', line 12 def token @token end |
#use_3d_secure ⇒ Object
Returns the value of attribute use_3d_secure.
12 13 14 |
# File 'app/my_lib/receptionist/credit_card_checker.rb', line 12 def use_3d_secure @use_3d_secure end |
#user ⇒ Object
Returns the value of attribute user.
12 13 14 |
# File 'app/my_lib/receptionist/credit_card_checker.rb', line 12 def user @user end |
Class Method Details
.execute(reservation, token, use_3d_secure: false, ip_address: nil, provider: nil, &block) ⇒ Object
138 139 140 141 |
# File 'app/my_lib/receptionist/credit_card_checker.rb', line 138 def self.execute(reservation, token, use_3d_secure: false, ip_address: nil, provider: nil, &block) rcpt = new(reservation, token, use_3d_secure: use_3d_secure, ip_address: ip_address, provider: provider) rcpt.check(&block) end |
Instance Method Details
#card_token_valid_based_on_provider? ⇒ Boolean
41 42 43 |
# File 'app/my_lib/receptionist/credit_card_checker.rb', line 41 def card_token_valid_based_on_provider? reservation.restaurant.selected_cc_payment_provider.to_sym == provider&.to_sym end |
#check ⇒ Object
reservation should be saved to database in block code
::Receptionist::CreditCardChecker.execute(reservation, token) do
reservation.save
end
50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 |
# File 'app/my_lib/receptionist/credit_card_checker.rb', line 50 def check if not_confirmed? BUSINESS_LOGGER.info( 'Reject to charge reservation because the status is not confirmed yet. ', reservation_id: reservation.id, ) raise CreditCardInvalid, "Sorry we can't confirm your booking with restaurant. Please contact #{SUPPORT_EMAIL}" end unless required? yield if block_given? return true end raise CreditCardInvalid, 'This reservation requires credit card' unless valid? validate_card_provider! result = false = "failed to charge Reservation ID: #{reservation.id}" ActiveRecord::Base.transaction do raise ActiveRecord::Rollback, 'Failed to process reservation' if block_given? && !yield if reservation.using_charge_directly_channel? my_merchant = setup_my_merchant my_merchant.store_card(token) charge_amount = reservation.charge_amount.presence || Money.new(reservation.restaurant.cc_hold_amount, reservation.restaurant.default_currency).amount money_amount = Money.from_amount(charge_amount, reservation.restaurant.default_currency) if reservation.charges.present? && reservation.charges.select(&:persisted?).present? BUSINESS_LOGGER.info('Reservation has been charged before', reservation_id: reservation.id) return true end if charge_amount.positive? && !my_merchant.charge(money_amount, use_3d_secure: use_3d_secure, ip_address: ip_address) = my_merchant. = I18n.t('errors.use_different_card') if .include?('fraud') BUSINESS_LOGGER.error(, reservation_id: reservation.id) # send error to rollbar for monitoring in staging err_msg = "failed to charge Reservation ID: #{reservation.id}" Rollbar.error(err_msg, reservation_id: reservation.id, original_error_message: my_merchant., kind: 'using_charge_directly') raise ActiveRecord::Rollback, end elsif reservation.using_on_hold_channel? my_merchant = setup_my_merchant my_merchant.store_card(token) unless my_merchant.hold = my_merchant. BUSINESS_LOGGER.error(, reservation_id: reservation.id) # send error to rollbar for monitoring in staging err_msg = "failed to charge Reservation ID: #{reservation.id}" Rollbar.error(err_msg, reservation_id: reservation.id, original_error_message: , kind: 'using_on_hold') raise ActiveRecord::Rollback, end else BUSINESS_LOGGER.error('Package has wrong charge setting', reservation_id: reservation.id) raise ActiveRecord::Rollback, 'Package has wrong charge setting' end BUSINESS_LOGGER.info("Reservation has been charged with 3d secure #{use_3d_secure}", reservation_id: reservation.id) result = true end raise CreditCardInvalid, unless result result rescue ActiveRecord::RecordInvalid, CreditCardInvalid => e # send error to APM for monitoring APMErrorHandler.report("Credit Card Invalid for Reservation ID: #{reservation.id}", e: e) raise(CreditCardInvalid, e.) rescue StandardError => e APMErrorHandler.report e raise(CreditCardError, 'Sorry, something went wrong') end |
#credit_card_given? ⇒ Boolean
31 32 33 34 35 |
# File 'app/my_lib/receptionist/credit_card_checker.rb', line 31 def credit_card_given? return true if token.present? false end |
#required? ⇒ Boolean
27 28 29 |
# File 'app/my_lib/receptionist/credit_card_checker.rb', line 27 def required? reservation.require_prepayment? end |
#valid? ⇒ Boolean
37 38 39 |
# File 'app/my_lib/receptionist/credit_card_checker.rb', line 37 def valid? required? && credit_card_given? end |