solidus-returnly 0.12.0 → 0.13.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/README.md +33 -5
- data/app/services/refund_payments.rb +30 -4
- data/lib/returnly.rb +1 -0
- data/lib/returnly/engine.rb +3 -1
- data/lib/returnly/gift_card.rb +21 -0
- data/lib/returnly/refund_calculator.rb +4 -0
- data/lib/returnly/refund_presenter.rb +102 -58
- data/lib/returnly/refunds_configuration.rb +8 -0
- data/lib/returnly/version.rb +1 -1
- metadata +3 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 49a3132d794c84523c95f735e48248ec39f4df2ed08650dfdc4770897b7478e4
|
4
|
+
data.tar.gz: ed416b5e72b84d710baffc1bba8103282ed3637040ceb093622414f855c50fdc
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: f73a7bcf01193de619aac70ded0b6d7b5ac85968d7e75de241d0e8d243922e1dddea96bc240207bfdee8a39ebd867291f8af176a191220348bc4deaa2e0990aa
|
7
|
+
data.tar.gz: 00fe2aac2e84fcd8f278547aadf930f112f1dc58ac20ee979c54dbe257553e58c12aa2d3602448054bfcc0af7ecdfa0fecb62630aab4a781faf7cafcfb72b2aa
|
data/README.md
CHANGED
@@ -101,11 +101,24 @@ Response:
|
|
101
101
|
"refundable_shipping_amount": "{money}",
|
102
102
|
"refundable_shipping_tax_amount": "{money}",
|
103
103
|
"max_refundable_amount": "{money}",
|
104
|
-
"
|
104
|
+
"transactions": [
|
105
105
|
{
|
106
|
-
"
|
106
|
+
"id": "{refund tx id}",
|
107
107
|
"amount": "{money}",
|
108
|
-
"
|
108
|
+
"status": "PENDING",
|
109
|
+
"type": "REFUND",
|
110
|
+
"gateway": "{gateway}",
|
111
|
+
"is_online": true,
|
112
|
+
"is_test": true,
|
113
|
+
"payment_details": {
|
114
|
+
"avs_result_code": "{code}",
|
115
|
+
"cvv_result_code": "{code}",
|
116
|
+
"credit_card_number": "{number}",
|
117
|
+
"credit_card_company": "visa",
|
118
|
+
"gift_card_id": "{voucher_id}",
|
119
|
+
"gift_card_code": "{voucher_code}"
|
120
|
+
},
|
121
|
+
"created_at": "{date}"
|
109
122
|
}
|
110
123
|
]
|
111
124
|
}
|
@@ -148,12 +161,27 @@ Response:
|
|
148
161
|
"units": 2
|
149
162
|
},
|
150
163
|
],
|
151
|
-
"transactions": [
|
164
|
+
"transactions": [
|
152
165
|
{
|
153
166
|
"id": "{refund tx id}",
|
154
|
-
"amount": "{money}"
|
167
|
+
"amount": "{money}",
|
168
|
+
"status": "PENDING",
|
169
|
+
"type": "REFUND",
|
170
|
+
"gateway": "{gateway}",
|
171
|
+
"is_online": true,
|
172
|
+
"is_test": true,
|
173
|
+
"payment_details": {
|
174
|
+
"avs_result_code": "{code}",
|
175
|
+
"cvv_result_code": "{code}",
|
176
|
+
"credit_card_number": "{number}",
|
177
|
+
"credit_card_company": "visa",
|
178
|
+
"gift_card_id": "{voucher_id}",
|
179
|
+
"gift_card_code": "{voucher_code}"
|
180
|
+
}
|
155
181
|
}
|
156
182
|
],
|
183
|
+
"created_at": "{date}",
|
184
|
+
"updated_at": "{date}",
|
157
185
|
"refund_note": "comment text",
|
158
186
|
}
|
159
187
|
```
|
@@ -3,8 +3,9 @@ class RefundPayments
|
|
3
3
|
|
4
4
|
include RefundMethods
|
5
5
|
|
6
|
-
def initialize(order)
|
6
|
+
def initialize(order, gift_card)
|
7
7
|
@order = order
|
8
|
+
@gift_card = gift_card
|
8
9
|
end
|
9
10
|
|
10
11
|
def perform!(payment_amount)
|
@@ -17,9 +18,15 @@ class RefundPayments
|
|
17
18
|
payment_amount -= allowed_amount
|
18
19
|
|
19
20
|
payments << {
|
20
|
-
|
21
|
-
amount:
|
22
|
-
|
21
|
+
id: payment.id.to_s,
|
22
|
+
amount: allowed_amount.to_s,
|
23
|
+
status: 'PENDING',
|
24
|
+
type: 'REFUND',
|
25
|
+
gateway: payment.payment_method.type.demodulize,
|
26
|
+
is_online: true,
|
27
|
+
is_test: !Rails.env.match?(/production/),
|
28
|
+
payment_details: transaction_payment_details(payment),
|
29
|
+
created_at: Time.zone.now.iso8601(3)
|
23
30
|
}
|
24
31
|
end
|
25
32
|
end
|
@@ -30,4 +37,23 @@ class RefundPayments
|
|
30
37
|
payments = payments.select { |p| eligible_refund_methods.include? p.payment_method.class }
|
31
38
|
payments.sort_by { |p| eligible_refund_methods.index(p.payment_method.class) }
|
32
39
|
end
|
40
|
+
|
41
|
+
def transaction_payment_details(payment)
|
42
|
+
details = {}
|
43
|
+
|
44
|
+
details[:avs_result_code] = payment.avs_response if payment.avs_response.present?
|
45
|
+
details[:cvv_result_code] = payment.cvv_response_code if payment.cvv_response_code.present?
|
46
|
+
|
47
|
+
source = payment.source
|
48
|
+
|
49
|
+
if source.respond_to?(:number) || source.respond_to?(:last_digits)
|
50
|
+
details[:credit_card_number] = source.number || source.last_digits if source.number.present? || source.last_digits.present?
|
51
|
+
details[:credit_card_company] = source.brand if source.brand.present?
|
52
|
+
end
|
53
|
+
|
54
|
+
details[:gift_card_id] = @gift_card.id if @gift_card.id.present?
|
55
|
+
details[:gift_card_code] = @gift_card.code if @gift_card.code.present?
|
56
|
+
|
57
|
+
details
|
58
|
+
end
|
33
59
|
end
|
data/lib/returnly.rb
CHANGED
@@ -9,6 +9,7 @@ require 'returnly/builders/return_item'
|
|
9
9
|
require 'returnly/refund_calculator'
|
10
10
|
|
11
11
|
require 'returnly/version'
|
12
|
+
require 'returnly/gift_card'
|
12
13
|
require 'returnly/refund/amount_calculator'
|
13
14
|
require 'returnly/refund/return_item_restock_policy'
|
14
15
|
require 'returnly/services/create_reimbursement'
|
data/lib/returnly/engine.rb
CHANGED
@@ -33,6 +33,10 @@ module Returnly
|
|
33
33
|
order.all_adjustments.where(source_type: 'Spree::TaxRate', adjustable_type: 'Spree::Shipment').sum(&:amount).to_d.round(2, :down)
|
34
34
|
end
|
35
35
|
|
36
|
+
def gift_card
|
37
|
+
@gift_card ||= self.class.gift_card_estimate_class.new(order)
|
38
|
+
end
|
39
|
+
|
36
40
|
protected
|
37
41
|
|
38
42
|
def available_return_items
|
@@ -1,71 +1,115 @@
|
|
1
1
|
module Returnly
|
2
2
|
class RefundPresenter
|
3
|
+
class << self
|
4
|
+
def present_refund(refunder)
|
5
|
+
customer_return = refunder.customer_return
|
6
|
+
refund = refunder.order.reload.refunds.last
|
3
7
|
|
4
|
-
|
5
|
-
|
6
|
-
|
8
|
+
{
|
9
|
+
refund_id: refund.try(:id).try(:to_s),
|
10
|
+
user_id: refunder.order.user_id,
|
11
|
+
line_items: customer_return.return_items.group_by { |ri| ri.inventory_unit.line_item.id }.map do |_, return_items|
|
12
|
+
first_return_item = return_items.first
|
13
|
+
{
|
14
|
+
refund_line_item_id: first_return_item.id.to_s,
|
15
|
+
order_line_item_id: first_return_item.inventory_unit.line_item.id.to_s,
|
16
|
+
units: return_items.size,
|
17
|
+
restock: first_return_item.resellable
|
18
|
+
}
|
19
|
+
end,
|
20
|
+
transactions: refunder.reimbursement.refunds.map do |refund|
|
21
|
+
{
|
22
|
+
id: refund.transaction_id,
|
23
|
+
amount: refund.amount.to_s,
|
24
|
+
status: transaction_status(refund.payment),
|
25
|
+
type: 'REFUND',
|
26
|
+
gateway: refund.payment.payment_method.type.demodulize,
|
27
|
+
is_online: true,
|
28
|
+
is_test: !Rails.env.match?(/production/),
|
29
|
+
payment_details: transaction_payment_details(refund.payment, refunder.gift_card_class.new(refund)),
|
30
|
+
created_at: refund.created_at.iso8601(3),
|
31
|
+
updated_at: refund.updated_at.iso8601(3)
|
32
|
+
}
|
33
|
+
end,
|
34
|
+
created_at: refund.try(:created_at).try(:iso8601, 3),
|
35
|
+
updated_at: refund.try(:updated_at).try(:iso8601, 3)
|
36
|
+
}
|
37
|
+
end
|
38
|
+
|
39
|
+
def present_estimate(calculator)
|
40
|
+
sub_total = Money.new 0
|
41
|
+
tax = Money.new 0
|
7
42
|
|
8
|
-
|
9
|
-
|
10
|
-
|
43
|
+
calculator.line_items_return_items.values.flatten.each do |return_item|
|
44
|
+
sub_total += Money.from_amount return_item.inventory_unit.line_item.price
|
45
|
+
tax += Money.from_amount calculator.line_item_tax(return_item.inventory_unit.line_item)
|
46
|
+
end
|
47
|
+
|
48
|
+
discount = Money.from_amount(calculator.discount)
|
49
|
+
total_refund_amount = sub_total + tax - (discount * -1) # discount is negative, so we multiply it by -1 to make it positive for subtraction
|
50
|
+
shipping_tax = calculator.shipping_tax
|
51
|
+
{
|
52
|
+
product_amount: sub_total.to_s,
|
53
|
+
tax_amount: tax.to_s,
|
54
|
+
discount_amount: (discount * -1).to_s,
|
55
|
+
total_refund_amount: total_refund_amount.to_s,
|
56
|
+
refundable_shipping_amount: Money.from_amount(calculator.order.shipment_total).to_s,
|
57
|
+
refundable_shipping_tax_amount: Money.from_amount(shipping_tax).to_s,
|
58
|
+
max_refundable_amount: Money.from_amount(calculator.order.total - calculator.order.refunds.reload.sum(&:amount)).to_s,
|
59
|
+
transactions: transactions_for_estimate(
|
60
|
+
calculator.order,
|
61
|
+
calculator.gift_card,
|
62
|
+
total_refund_amount.to_d + calculator.order.shipment_total + shipping_tax
|
63
|
+
)
|
64
|
+
}
|
11
65
|
end
|
12
66
|
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
67
|
+
def present_refund_with_zero_amount(refunder)
|
68
|
+
{
|
69
|
+
refund_id: '1',
|
70
|
+
line_items: refunder.line_items.map do |line_item|
|
71
|
+
{
|
72
|
+
refund_line_item_id: '1',
|
73
|
+
order_line_item_id: line_item[:order_line_item_id].to_s,
|
74
|
+
units: line_item[:units].to_i,
|
75
|
+
restock: line_item[:restock].match?(/true/)
|
76
|
+
}
|
77
|
+
end,
|
78
|
+
transactions: [],
|
79
|
+
created_at: Time.zone.now.iso8601(3)
|
80
|
+
}
|
81
|
+
end
|
82
|
+
|
83
|
+
private
|
84
|
+
|
85
|
+
def transaction_status(payment)
|
86
|
+
return 'SUCCESS' if payment.completed?
|
87
|
+
return 'FAILURE' if payment.failed? || payment.invalid?
|
88
|
+
'PENDING'
|
89
|
+
end
|
27
90
|
|
28
|
-
|
29
|
-
|
91
|
+
def transaction_payment_details(payment, gift_card)
|
92
|
+
details = {}
|
30
93
|
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
restock: first_return_item.resellable
|
40
|
-
}
|
41
|
-
end,
|
42
|
-
transactions: refunder.reimbursement.refunds.map do |refund|
|
43
|
-
{
|
44
|
-
id: refund.transaction_id,
|
45
|
-
amount: refund.amount.to_f,
|
46
|
-
code: refund.payment.source_type.constantize.model_name.human
|
47
|
-
}
|
94
|
+
details[:avs_result_code] = payment.avs_response if payment.avs_response.present?
|
95
|
+
details[:cvv_result_code] = payment.cvv_response_code if payment.cvv_response_code.present?
|
96
|
+
|
97
|
+
source = payment.source
|
98
|
+
|
99
|
+
if source.respond_to?(:number) || source.respond_to?(:last_digits)
|
100
|
+
details[:credit_card_number] = source.number || source.last_digits if source.number.present? || source.last_digits.present?
|
101
|
+
details[:credit_card_company] = source.brand if source.brand.present?
|
48
102
|
end
|
49
|
-
}
|
50
|
-
end
|
51
103
|
|
52
|
-
|
53
|
-
|
54
|
-
refund_id: '',
|
55
|
-
line_items: refunder.line_items.map do |line_item|
|
56
|
-
{
|
57
|
-
refund_line_item_id: '',
|
58
|
-
order_line_item_id: line_item[:order_line_item_id].to_s,
|
59
|
-
units: line_item[:units].to_i,
|
60
|
-
restock: !!(line_item[:restock].to_s =~ /true/)
|
61
|
-
}
|
62
|
-
end,
|
63
|
-
transactions: []
|
64
|
-
}
|
65
|
-
end
|
104
|
+
details[:gift_card_id] = gift_card.id if gift_card.id.present?
|
105
|
+
details[:gift_card_code] = gift_card.code if gift_card.code.present?
|
66
106
|
|
67
|
-
|
68
|
-
|
69
|
-
|
107
|
+
details
|
108
|
+
end
|
109
|
+
|
110
|
+
def transactions_for_estimate(order, gift_card, payment_amount)
|
111
|
+
::RefundPayments.new(order, gift_card).perform!(payment_amount)
|
112
|
+
end
|
113
|
+
end
|
70
114
|
end
|
71
115
|
end
|
@@ -24,5 +24,13 @@ module Returnly
|
|
24
24
|
def refund_presenter_class
|
25
25
|
Returnly.refund_presenter || Returnly::RefundPresenter
|
26
26
|
end
|
27
|
+
|
28
|
+
def gift_card_class
|
29
|
+
Returnly.gift_card || Returnly::NilGiftCard
|
30
|
+
end
|
31
|
+
|
32
|
+
def gift_card_estimate_class
|
33
|
+
Returnly.git_card_estimate || Returnly::NilGiftCardEstimate
|
34
|
+
end
|
27
35
|
end
|
28
36
|
end
|
data/lib/returnly/version.rb
CHANGED
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: solidus-returnly
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.13.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Returnly Technologies, Inc
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2019-05-02 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: solidus
|
@@ -387,6 +387,7 @@ files:
|
|
387
387
|
- lib/returnly/discounts/order.rb
|
388
388
|
- lib/returnly/engine.rb
|
389
389
|
- lib/returnly/factories.rb
|
390
|
+
- lib/returnly/gift_card.rb
|
390
391
|
- lib/returnly/refund/amount_calculator.rb
|
391
392
|
- lib/returnly/refund/return_item_restock_policy.rb
|
392
393
|
- lib/returnly/refund_calculator.rb
|