Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

close #229 allow filter payment method by user role #230

Open
wants to merge 1 commit into
base: develop
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,19 @@ def scope
scope = scope.where.not(vendor_id: nil) if params[:tab] == 'vendors'
scope
end

def calculate_allow_role_value(params)
params.slice(*Spree::PaymentMethod::BIT_FIELDS.keys).values.each_with_index.sum { |v, i| v.to_i * (2**i) }
end

# override
def preferences_params
key = ActiveModel::Naming.param_key(@payment_method)
return {} unless params[key]

allow_role = calculate_allow_role_value(params[key])
params.require(key).permit.except(*Spree::PaymentMethod::BIT_FIELDS.keys).merge(preferred_allow_role: allow_role)
end
end
end
end
Expand Down
14 changes: 10 additions & 4 deletions app/helpers/vpago/admin/base_helper_decorator.rb
Original file line number Diff line number Diff line change
Expand Up @@ -24,13 +24,19 @@ def available_payment_icons
def preference_field_for(form, field, options)
case field
when 'preferred_acleda_type'
return form.select(:preferred_acleda_type, form.object.class::TYPES, {}, class: 'fullwidth select2')
form.select(:preferred_acleda_type, form.object.class::TYPES, {}, class: 'fullwidth select2')
when 'preferred_acleda_payment_card'
return form.select(:preferred_acleda_payment_card, acleda_payment_card_options, {}, class: 'fullwidth select2')
form.select(:preferred_acleda_payment_card, acleda_payment_card_options, {}, class: 'fullwidth select2')
when 'preferred_icon_name'
return form.select(:preferred_icon_name, available_payment_icons, {}, class: 'fullwidth select2')
form.select(:preferred_icon_name, available_payment_icons, {}, class: 'fullwidth select2')
when 'preferred_allow_role'
Vpago::PaymentMethodDecorator::BIT_FIELDS.map do |role, bit_value|
form.check_box(role, class: 'mx-1', checked: form.object.allow_role_enabled?(bit_value)) +
form.label(role, Spree.t(role), class: 'mx-1')
end.join.html_safe
else
super
end
super
end
end
end
Expand Down
34 changes: 19 additions & 15 deletions app/models/vpago/order_decorator.rb
Original file line number Diff line number Diff line change
Expand Up @@ -56,30 +56,34 @@ def required_payway_payout?
# override
def available_payment_methods(store = nil)
payment_methods = if vendor_payment_methods.any?
available_vendor_payment_methods
vendor_payment_methods.active
else
collect_payment_methods(store)
end

@available_payment_methods ||= if required_payway_payout?
payment_methods.select(&:type_payway_v2?)
else
payment_methods
end
end
payment_methods = if required_payway_payout?
payment_methods.select(&:type_payway_v2?)
else
payment_methods
end

def available_vendor_payment_methods
if ticket_seller_user?
vendor_payment_methods
else
vendor_payment_methods.reject { |pm| pm.type == 'Spree::PaymentMethod::Check' }
@available_payment_methods ||= payment_methods.select do |payment_method|
payment_method_allowed?(payment_method)
end
end

def ticket_seller_user?
return false if user.nil?
def payment_method_allowed?(payment_method)
return true unless payment_method_set_allow_role?(payment_method)
return false if user.nil? && payment_method_set_allow_role?(payment_method)

user.role_users.any? do |role_user|
bit_field = Vpago::PaymentMethodDecorator::BIT_FIELDS[role_user.role.name.to_sym]
bit_field && (payment_method.preferred_allow_role & bit_field) != 0
end
end

user.has_spree_role?('ticket_seller')
def payment_method_set_allow_role?(payment_method)
payment_method.preferred_allow_role != 0
end

def line_items_count
Expand Down
13 changes: 12 additions & 1 deletion app/models/vpago/payment_method_decorator.rb
Original file line number Diff line number Diff line change
Expand Up @@ -6,9 +6,16 @@ module PaymentMethodDecorator
TYPE_ACLEDA = 'Spree::Gateway::Acleda'.freeze
TYPE_ACLEDA_MOBILE = 'Spree::Gateway::AcledaMobile'.freeze

BIT_FIELDS = {
admin: 0b1,
organizer: 0b10,
ticket_seller: 0b100
}.freeze

def self.prepended(base)
base.preference :icon_name, :string, default: 'cheque'
base.belongs_to :vendor, class_name: 'Spree::Vendor', optional: true, inverse_of: :payment_methods
base.preference :allow_role, :integer, default: 0

def base.vpago_payments
[
Expand All @@ -21,6 +28,10 @@ def base.vpago_payments
end
end

def allow_role_enabled?(bit_value)
preferred_allow_role & bit_value != 0
end

def support_payout?
return false unless type_payway_v2?
return false unless default_payout_profile.present? && default_payout_profile.receivable?
Expand Down Expand Up @@ -85,7 +96,7 @@ def type_payway_v2?
def type_wingsdk?
type == Spree::PaymentMethod::TYPE_WINGSDK
end

def pre_auth_service
if type_payway_v2?
Vpago::PaywayV2::PreAuthHandler.new
Expand Down
8 changes: 8 additions & 0 deletions spec/factories/user_factory.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
FactoryBot.define do
factory :organizer, parent: :user do
spree_roles { [Spree::Role.find_by(name: 'organizer') || create(:role, name: 'organizer')] }
end
factory :ticket_seller_user, parent: :user do
spree_roles { [Spree::Role.find_by(name: 'ticket_seller') || create(:role, name: 'ticket_seller')] }
end
end
56 changes: 24 additions & 32 deletions spec/models/spree/order_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -220,46 +220,38 @@
end
end

describe '#available_vendor_payment_methods' do
let(:vendor1) { create(:vendor) }
let(:vendor2) { create(:vendor) }
describe '#payment_method_allowed?' do
let(:organizer){ create(:organizer) }
let(:ticket_seller_user){ create(:ticket_seller_user) }
let(:payment_method) { create(:payment_method) }
let(:order) { create(:order) }

before do
create(:line_item, order: order, product: create(:product_in_stock, vendor: vendor1))
create(:line_item, order: order, product: create(:product_in_stock, vendor: vendor2))
it 'return true when payment_method allow role is nil' do
payment_method.preferred_allow_role = 0
result = order.payment_method_allowed?(payment_method)
expect(result).to be true
end

context 'when user is a ticket seller' do
before do
allow(order).to receive(:ticket_seller_user?).and_return(true)
end

it 'returns all vendor payment methods' do
payment_method1 = create(:payment_method, vendor: vendor1)
payment_method2 = create(:payment_method, vendor: vendor2, type: 'Spree::PaymentMethod::Check')

order.stub(:vendor_payment_methods) { [payment_method1, payment_method2] }

expect(order.available_vendor_payment_methods).to match_array([payment_method1, payment_method2])
end
it 'return true when user role match with payment_method allow role' do
payment_method.preferred_allow_role = 4 # preferred_allow_role: ticket_seller
order.user = ticket_seller_user
result = order.payment_method_allowed?(payment_method)
expect(result).to be true
end

context 'when user is not a ticket seller' do
before do
allow(order).to receive(:ticket_seller_user?).and_return(false)
end

it 'returns vendor payment methods excluding the ones of type Check' do
payment_method1 = create(:payment_method, vendor: vendor1)
payment_method2 = create(:payment_method, vendor: vendor2)
payment_method_check = create(:payment_method, vendor: vendor1, type: 'Spree::PaymentMethod::Check')
it 'return false when user is unmatch with payment_method allow role' do
payment_method.preferred_allow_role = 1 # preferred_allow_role: admin
order.user = ticket_seller_user
result = order.payment_method_allowed?(payment_method)
expect(result).to be false
end

order.stub(:vendor_payment_methods) { [payment_method1, payment_method2, payment_method_check] }
it 'returns false when user is nil and payment_method have allow role set' do
order.user = nil
payment_method.preferred_allow_role = 1 # preferred_allow_role: admin

expect(order.available_vendor_payment_methods).to match_array([payment_method1, payment_method2])
expect(order.available_vendor_payment_methods).not_to include(payment_method_check)
end
result = order.payment_method_allowed?(payment_method)
expect(result).to be false
end
end
end
Loading