Update CustomersWithBalanceQuery

This commit is contained in:
Feruz Oripov
2024-02-26 23:25:33 +05:00
parent d4f37a3daa
commit 81f40a99d9
8 changed files with 58 additions and 58 deletions

View File

@@ -70,7 +70,7 @@ module Admin
def collection
if json_request? && params[:enterprise_id].present?
CustomersWithBalance.new(customers).query.
CustomersWithBalanceQuery.new(customers).call.
includes(
:enterprise,
{ bill_address: [:state, :country] },

View File

@@ -59,7 +59,7 @@ module Api
def customer
@customer ||= if action_name == "show"
CustomersWithBalance.new(Customer.where(id: params[:id])).query.first!
CustomersWithBalanceQuery.new(Customer.where(id: params[:id])).call.first!
else
Customer.find(params[:id])
end
@@ -74,7 +74,7 @@ module Api
customers = customers.where(enterprise_id: params[:enterprise_id]) if params[:enterprise_id]
if @extra_customer_fields.include?(:balance)
customers = CustomersWithBalance.new(customers).query
customers = CustomersWithBalanceQuery.new(customers).call
end
customers.ransack(params[:q]).result.order(:id)

View File

@@ -2,12 +2,12 @@
# Adds an aggregated 'balance_value' to each customer based on their order history
#
class CustomersWithBalance
class CustomersWithBalanceQuery
def initialize(customers)
@customers = customers
end
def query
def call
@customers.
joins(left_join_complete_orders).
group("customers.id").

View File

@@ -7,7 +7,7 @@
# Alternatively, you can get the SQL by calling #statement, which is suitable for more complex
# cases.
#
# See CompleteOrdersWithBalanceQuery or CustomersWithBalance as examples.
# See CompleteOrdersWithBalanceQuery or CustomersWithBalanceQuery as examples.
#
# Note this query object and `app/models/concerns/balance.rb` should implement the same behavior
# until we find a better way. If you change one, please, change the other too.

View File

@@ -3,7 +3,7 @@
module Api
module Admin
# This serializer relies on `object` to respond to `#balance_value`. That's done in
# `CustomersWithBalance` due to the fact that ActiveRecord maps the DB result set's columns to
# `CustomersWithBalanceQuery` due to the fact that ActiveRecord maps the DB result set's columns to
# instance methods. This way, the `balance_value` alias on that class ends up being
# `object.balance_value` here.
class CustomerWithBalanceSerializer < CustomerSerializer

View File

@@ -44,12 +44,12 @@ module Admin
get :index, params:
end
it 'calls CustomersWithBalance' do
customers_with_balance = instance_double(CustomersWithBalance)
allow(CustomersWithBalance)
it 'calls CustomersWithBalanceQuery' do
customers_with_balance = instance_double(CustomersWithBalanceQuery)
allow(CustomersWithBalanceQuery)
.to receive(:new).with(customers) { customers_with_balance }
expect(customers_with_balance).to receive(:query) { Customer.none }
expect(customers_with_balance).to receive(:call) { Customer.none }
get :index, params:
end

View File

@@ -17,8 +17,6 @@ module Reporting
end
describe "fetching orders" do
let(:customers_with_balance) { instance_double(CustomersWithBalance) }
it 'calls the OutstandingBalance query object' do
outstanding_balance = instance_double(OutstandingBalance, query: Spree::Order.none)
expect(OutstandingBalance).to receive(:new).and_return(outstanding_balance)

View File

@@ -2,97 +2,99 @@
require 'spec_helper'
describe CustomersWithBalance do
subject(:customers_with_balance) { described_class.new(Customer.where(id: customer)) }
describe CustomersWithBalanceQuery do
subject(:result) { described_class.new(Customer.where(id: customers)).call }
describe '#query' do
let(:customer) { create(:customer) }
describe '#call' do
let(:customers) { create(:customer) }
let(:total) { 200.00 }
let(:order_total) { 100.00 }
let(:outstanding_balance) { instance_double(OutstandingBalance) }
it 'calls CustomersWithBalance#statement' do
it 'calls OutstandingBalance#statement' do
allow(OutstandingBalance).to receive(:new).and_return(outstanding_balance)
expect(outstanding_balance).to receive(:statement)
customers_with_balance.query
result
end
describe 'arguments' do
context 'with customers collection' do
let(:customers) { create_pair(:customer) }
it 'returns balance' do
customers = create_pair(:customer)
query = described_class.new(Customer.where(id: customers)).query
expect(query.pluck(:id).sort).to eq([customers.first.id, customers.second.id].sort)
expect(query.map(&:balance_value)).to eq([0, 0])
expect(result.pluck(:id).sort).to eq([customers.first.id, customers.second.id].sort)
expect(result.map(&:balance_value)).to eq([0, 0])
end
end
context 'with empty customers collection' do
let(:customers) { Customer.none }
it 'returns empty customers collection' do
expect(described_class.new(Customer.none).query).to eq([])
expect(result).to eq([])
end
end
end
context 'when orders are in cart state' do
before do
create(:order, customer:, total: order_total, payment_total: 0, state: 'cart')
create(:order, customer:, total: order_total, payment_total: 0, state: 'cart')
create(:order, customer: customers, total: order_total, payment_total: 0, state: 'cart')
create(:order, customer: customers, total: order_total, payment_total: 0, state: 'cart')
end
it 'returns the customer balance' do
customer = customers_with_balance.query.first
customer = result.first
expect(customer.balance_value).to eq(0)
end
end
context 'when orders are in address state' do
before do
create(:order, customer:, total: order_total, payment_total: 0, state: 'address')
create(:order, customer:, total: order_total, payment_total: 50, state: 'address')
create(:order, customer: customers, total: order_total, payment_total: 0, state: 'address')
create(:order, customer: customers, total: order_total, payment_total: 50, state: 'address')
end
it 'returns the customer balance' do
customer = customers_with_balance.query.first
customer = result.first
expect(customer.balance_value).to eq(0)
end
end
context 'when orders are in delivery state' do
before do
create(:order, customer:, total: order_total, payment_total: 0, state: 'delivery')
create(:order, customer:, total: order_total, payment_total: 50, state: 'delivery')
create(:order, customer: customers, total: order_total, payment_total: 0, state: 'delivery')
create(:order, customer: customers, total: order_total, payment_total: 50, state: 'delivery')
end
it 'returns the customer balance' do
customer = customers_with_balance.query.first
customer = result.first
expect(customer.balance_value).to eq(0)
end
end
context 'when orders are in payment state' do
before do
create(:order, customer:, total: order_total, payment_total: 0, state: 'payment')
create(:order, customer:, total: order_total, payment_total: 50, state: 'payment')
create(:order, customer: customers, total: order_total, payment_total: 0, state: 'payment')
create(:order, customer: customers, total: order_total, payment_total: 50, state: 'payment')
end
it 'returns the customer balance' do
customer = customers_with_balance.query.first
customer = result.first
expect(customer.balance_value).to eq(0)
end
end
context 'when no orders where paid' do
before do
order = create(:order, customer:, total: order_total, payment_total: 0)
order = create(:order, customer: customers, total: order_total, payment_total: 0)
order.update_attribute(:state, 'complete')
order = create(:order, customer:, total: order_total, payment_total: 0)
order = create(:order, customer: customers, total: order_total, payment_total: 0)
order.update_attribute(:state, 'complete')
end
it 'returns the customer balance' do
customer = customers_with_balance.query.first
customer = result.first
expect(customer.balance_value).to eq(-total)
end
end
@@ -101,14 +103,14 @@ describe CustomersWithBalance do
let(:payment_total) { order_total }
before do
order = create(:order, customer:, total: order_total, payment_total: 0)
order = create(:order, customer: customers, total: order_total, payment_total: 0)
order.update_attribute(:state, 'complete')
order = create(:order, customer:, total: order_total, payment_total:)
order = create(:order, customer: customers, total: order_total, payment_total:)
order.update_attribute(:state, 'complete')
end
it 'returns the customer balance' do
customer = customers_with_balance.query.first
customer = result.first
expect(customer.balance_value).to eq(payment_total - total)
end
end
@@ -118,11 +120,11 @@ describe CustomersWithBalance do
let(:non_canceled_orders_total) { order_total }
before do
order = create(:order, customer:, total: order_total, payment_total: 0)
order = create(:order, customer: customers, total: order_total, payment_total: 0)
order.update_attribute(:state, 'complete')
create(
:order,
customer:,
customer: customers,
total: order_total,
payment_total: order_total,
state: 'canceled'
@@ -130,7 +132,7 @@ describe CustomersWithBalance do
end
it 'returns the customer balance' do
customer = customers_with_balance.query.first
customer = result.first
expect(customer.balance_value).to eq(payment_total - non_canceled_orders_total)
end
end
@@ -139,14 +141,14 @@ describe CustomersWithBalance do
let(:payment_total) { order_total }
before do
order = create(:order, customer:, total: order_total, payment_total: 0)
order = create(:order, customer: customers, total: order_total, payment_total: 0)
order.update_attribute(:state, 'complete')
order = create(:order, customer:, total: order_total, payment_total:)
order = create(:order, customer: customers, total: order_total, payment_total:)
order.update_attribute(:state, 'resumed')
end
it 'returns the customer balance' do
customer = customers_with_balance.query.first
customer = result.first
expect(customer.balance_value).to eq(payment_total - total)
end
end
@@ -155,14 +157,14 @@ describe CustomersWithBalance do
let(:payment_total) { order_total }
before do
order = create(:order, customer:, total: order_total, payment_total: 0)
order = create(:order, customer: customers, total: order_total, payment_total: 0)
order.update_attribute(:state, 'complete')
order = create(:order, customer:, total: order_total, payment_total:)
order = create(:order, customer: customers, total: order_total, payment_total:)
order.update_attribute(:state, 'payment')
end
it 'returns the customer balance' do
customer = customers_with_balance.query.first
customer = result.first
expect(customer.balance_value).to eq(payment_total - total)
end
end
@@ -171,14 +173,14 @@ describe CustomersWithBalance do
let(:payment_total) { order_total }
before do
order = create(:order, customer:, total: order_total, payment_total: 0)
order = create(:order, customer: customers, total: order_total, payment_total: 0)
order.update_attribute(:state, 'complete')
order = create(:order, customer:, total: order_total, payment_total:)
order = create(:order, customer: customers, total: order_total, payment_total:)
order.update_attribute(:state, 'awaiting_return')
end
it 'returns the customer balance' do
customer = customers_with_balance.query.first
customer = result.first
expect(customer.balance_value).to eq(payment_total - total)
end
end
@@ -188,21 +190,21 @@ describe CustomersWithBalance do
let(:non_returned_orders_total) { order_total }
before do
order = create(:order, customer:, total: order_total, payment_total: 0)
order = create(:order, customer: customers, total: order_total, payment_total: 0)
order.update_attribute(:state, 'complete')
order = create(:order, customer:, total: order_total, payment_total:)
order = create(:order, customer: customers, total: order_total, payment_total:)
order.update_attribute(:state, 'returned')
end
it 'returns the customer balance' do
customer = customers_with_balance.query.first
customer = result.first
expect(customer.balance_value).to eq(payment_total - non_returned_orders_total)
end
end
context 'when there are no orders' do
it 'returns the customer balance' do
customer = customers_with_balance.query.first
customer = result.first
expect(customer.balance_value).to eq(0)
end
end