dorsale 3.9.8 → 3.10.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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 92313d3e11ca03d76f1153193497dd581e8cf4ad
4
- data.tar.gz: 4e9f7171df37fff5047abecf671cd2408affb103
3
+ metadata.gz: 99dec4abf499000f2dd5056f0ad64e158982020b
4
+ data.tar.gz: 8880c252a553956e6d24ac1723c20a9d46108a36
5
5
  SHA512:
6
- metadata.gz: e836be0347fe2fafd0bfedc565599c89ab786f58dc665ac923489cb900aaad73e5b34c9b06e4a8fff1681181ac3a81591315c9734ee424455ebb536da0380ed2
7
- data.tar.gz: 3a377cbad257367addc9a05df944d4e22608001ba8ec15624efedabb023519879e0f7160ea73032d9f30be59cf3e512cc48528deee29726a37de6c7457524835
6
+ metadata.gz: 98a8ede0dc3303cf86f0f275a153df7d4cc0fd4409dfd0faee7baf3101cb5c03c0a6bd6d0bc72e64fbec1bc3f12bd012c5c3b989935f3964e59818c0d682fb04
7
+ data.tar.gz: 29e5a4f979b8fa53a478f65a6092ac5fd5c74bb6a92618d74f4a97e6d8fabe1264e468de69cae688555ea4195287809b9852947b08772e9633ebc71f0e3b238a
@@ -2,6 +2,12 @@
2
2
 
3
3
  ## Next version
4
4
 
5
+ ## 3.10.0
6
+
7
+ - Billing Machine : fix amounts round
8
+ - Billing Machine : change ::DEFAULT_VAT_RATE to ::default_vat_rate
9
+ - Billing Machine : refactor/improve JS
10
+
5
11
  ## 3.9.8
6
12
 
7
13
  - Tasks : add increment progress buttons
@@ -1,95 +1,104 @@
1
- accounting.settings =
2
- number:
3
- precision : 2
4
- thousand: " " # nbsp
5
- decimal : ","
1
+ @BillingMachine = {}
6
2
 
7
- window.str2num = (str) ->
3
+ BillingMachine.settings =
4
+ precision : 2
5
+ thousand : " " # nbsp
6
+ decimal : ","
7
+
8
+ BillingMachine.str2num = (str) ->
8
9
  parseFloat(
9
10
  String(str)
10
11
  .replace(",", ".")
11
12
  .replace(/[^-0-9\.]+/g, "")
12
13
  ) || 0.0
13
14
 
14
- window.num2str = (num) ->
15
+ BillingMachine.num2str = (num) ->
15
16
  num = parseFloat(num)
16
- accounting.formatNumber(num)
17
+ settings = BillingMachine.settings
18
+ accounting.formatNumber(num, settings.precision, settings.thousand, settings.decimal)
19
+
20
+ BillingMachine.round2 = (num) ->
21
+ return +(Math.round(num + "e+2") + "e-2")
22
+
23
+ BillingMachine.updateTotals = ->
24
+ total_excluding_taxes = 0.0
25
+
26
+ # Update line totals
27
+ $("#billing_machine-form .line").map ->
28
+ return if parseInt($(this).find("input[name*=destroy]").val()) == 1
29
+ quantity = BillingMachine.str2num $(this).find(".line-quantity input").val()
30
+ unit_price = BillingMachine.str2num $(this).find(".line-unit_price input").val()
31
+ line_total = BillingMachine.round2(unit_price * quantity)
32
+ $(this).find(".line-total input").val BillingMachine.num2str line_total
33
+
34
+ total_excluding_taxes += line_total
35
+
36
+ # Substract discount to total excluding taxes
37
+ commercial_discount = BillingMachine.str2num $(".commercial_discount input").val()
38
+ raw_total_excluding_taxes = total_excluding_taxes
39
+ total_excluding_taxes = raw_total_excluding_taxes - commercial_discount
40
+ $(".total_excluding_taxes input").val BillingMachine.num2str total_excluding_taxes
41
+
42
+ discount_rate = commercial_discount / raw_total_excluding_taxes
43
+
44
+ # VAT amount based on each line total with discount rate
45
+ vat_amount = 0.0
46
+ $("#billing_machine-form .line").map ->
47
+ return if parseInt($(this).find("input[name*=destroy]").val()) == 1
48
+
49
+ # Per line VAT rate
50
+ if $(this).find(".line-vat_rate input").length > 0
51
+ vat_rate = BillingMachine.str2num $(this).find(".line-vat_rate input").val()
52
+ # Global VAT rate
53
+ else
54
+ vat_rate = BillingMachine.str2num $("#totals-table .vat_rate input").val()
55
+
56
+ line_total = BillingMachine.str2num $(this).find(".line-total input").val()
57
+ discounted_line_total = line_total - (line_total * discount_rate)
58
+ line_vat_amount = BillingMachine.round2(discounted_line_total * vat_rate / 100)
59
+ vat_amount += line_vat_amount
60
+ $(".vat_amount input").val BillingMachine.num2str vat_amount
61
+
62
+ total_including_taxes = total_excluding_taxes + vat_amount
63
+ $(".total_including_taxes input").val BillingMachine.num2str total_including_taxes
64
+
65
+ # Advances is for invoices only, not for quotations
66
+ if $(".advance input").length > 0 && $(".balance input").length > 0
67
+ advance = BillingMachine.str2num $(".advance input").val()
68
+ balance = total_including_taxes - advance
69
+ $(".balance input").val BillingMachine.num2str balance
70
+
71
+ BillingMachine.formatInputs = ->
72
+ $("#billing_machine-form input.number").map ->
73
+ formatted_number = BillingMachine.num2str BillingMachine.str2num $(this).val()
74
+ $(this).val formatted_number
75
+
76
+ # Empty number inputs on focus if value is 0
77
+ $(document).on "focus", "#billing_machine-form input.number", ->
78
+ $(this).val("") if BillingMachine.str2num($(this).val()) == 0
79
+
80
+ # Auto ajust line label textarea height
81
+ $(document).on "keyup", "#billing_machine-form textarea", ->
82
+ this.rows = this.value.split("\n").length
83
+ $("#billing_machine-form textarea").keyup()
84
+
85
+ # Button to delete line
86
+ $(document).on "click", "#billing_machine-form a.delete", ->
87
+ e.preventDefault()
88
+ $(this).parents("td").find("input").val(1)
89
+ $(this).parents("tr").hide()
90
+ BillingMachine.updateTotals()
17
91
 
18
92
  $(document).on "turbolinks:load cocoon:after-insert", ->
19
- $("#billing_machine-form input.number").keyup ->
20
- total_excluding_taxes = 0.0
21
-
22
- # Update line totals
23
- $("#billing_machine-form .line").map ->
24
- return if parseInt($(this).find("input[name*=destroy]").val()) == 1
25
- quantity = str2num $(this).find(".line-quantity input").val()
26
- unit_price = str2num $(this).find(".line-unit_price input").val()
27
- line_total = unit_price * quantity
28
- $(this).find(".line-total input").val num2str line_total
29
-
30
- total_excluding_taxes += line_total
31
-
32
- # Substract discount to total excluding taxes
33
- commercial_discount = str2num $(".commercial_discount input").val()
34
- raw_total_excluding_taxes = total_excluding_taxes
35
- total_excluding_taxes = raw_total_excluding_taxes - commercial_discount
36
- $(".total_excluding_taxes input").val num2str total_excluding_taxes
37
-
38
- discount_rate = commercial_discount / raw_total_excluding_taxes
39
-
40
- # VAT amount based on each line total with discount rate
41
- vat_amount = 0.0
42
- $("#billing_machine-form .line").map ->
43
- return if parseInt($(this).find("input[name*=destroy]").val()) == 1
44
-
45
- # Per line VAT rate
46
- if $(this).find(".line-vat_rate input").length > 0
47
- vat_rate = str2num $(this).find(".line-vat_rate input").val()
48
- # Global VAT rate
49
- else
50
- vat_rate = str2num $("#totals-table .vat_rate input").val()
51
-
52
- line_total = str2num $(this).find(".line-total input").val()
53
- discounted_line_total = line_total - (line_total * discount_rate)
54
- line_vat_amount = discounted_line_total * vat_rate / 100
55
- vat_amount += line_vat_amount
56
- $(".vat_amount input").val num2str vat_amount
57
-
58
- total_including_taxes = total_excluding_taxes + vat_amount
59
- $(".total_including_taxes input").val num2str total_including_taxes
60
-
61
- # Advances is for invoices only, not for quotations
62
- if $(".advance input").length > 0 && $(".balance input").length > 0
63
- advance = str2num $(".advance input").val()
64
- balance = total_including_taxes - advance
65
- $(".balance input").val num2str balance
66
-
67
- # Update amount on page load
68
- $("#billing_machine-form input").keyup()
69
-
70
- # Format all input correctly
71
- $("#billing_machine-form input.number").blur ->
72
- $("#billing_machine-form input.number").map ->
73
- formatted_number = num2str str2num $(this).val()
74
- $(this).val formatted_number
75
- $("#billing_machine-form input.number").blur()
76
-
77
- # Empty number inputs on focus if value is 0
78
- $("#billing_machine-form input.number").focus ->
79
- $(this).val("") if str2num($(this).val()) == 0
80
-
81
- # Auto ajust line label textarea height
82
- $("#billing_machine-form textarea").keyup ->
83
- this.rows = this.value.split("\n").length
84
- $("#billing_machine-form textarea").keyup()
93
+ BillingMachine.formatInputs()
94
+ BillingMachine.updateTotals()
85
95
 
86
96
  # Fix Cocoon bug
87
97
  $("#billing_machine-form .line textarea").map ->
88
98
  this.value = this.value.trim()
89
99
 
90
- # Button to delete line
91
- $("#billing_machine-form a.delete").click ->
92
- $(this).parents("td").find("input").val(1)
93
- $(this).parents("tr").hide()
94
- $("#billing_machine-form input").keyup() # Update totals
95
- return false
100
+ $(document).on "keyup", "#billing_machine-form input.number", ->
101
+ BillingMachine.updateTotals()
102
+
103
+ $(document).on "blur", "#billing_machine-form input.number", ->
104
+ BillingMachine.formatInputs()
@@ -1,6 +1,4 @@
1
1
  module Dorsale::BillingMachine
2
- DEFAULT_VAT_RATE = 20.00
3
-
4
2
  class << self
5
3
  def vat_modes
6
4
  [:single, :multiple]
@@ -28,5 +26,11 @@ module Dorsale::BillingMachine
28
26
  def default_currency
29
27
  @default_currency ||= "€"
30
28
  end
29
+
30
+ attr_writer :default_vat_rate
31
+
32
+ def default_vat_rate
33
+ @default_vat_rate ||= 20.0
34
+ end
31
35
  end
32
36
  end
@@ -71,7 +71,7 @@ class Dorsale::BillingMachine::Invoice < ::Dorsale::ApplicationRecord
71
71
 
72
72
  lines.each do |line|
73
73
  line_total = line.total - (line.total * discount_rate)
74
- self.vat_amount += (line_total * line.vat_rate / 100.0)
74
+ self.vat_amount += (line_total * line.vat_rate / 100.0).round(2)
75
75
  end
76
76
 
77
77
  self.total_including_taxes = total_excluding_taxes + vat_amount
@@ -91,7 +91,7 @@ class Dorsale::BillingMachine::Invoice < ::Dorsale::ApplicationRecord
91
91
  raise "Invoice has multiple vat rates"
92
92
  end
93
93
 
94
- vat_rates.first || ::Dorsale::BillingMachine::DEFAULT_VAT_RATE
94
+ vat_rates.first || ::Dorsale::BillingMachine.default_vat_rate
95
95
  end
96
96
 
97
97
  attr_writer :vat_rate
@@ -14,12 +14,12 @@ class Dorsale::BillingMachine::InvoiceLine < ::Dorsale::ApplicationRecord
14
14
  def assign_default_values
15
15
  assign_default :quantity, 0
16
16
  assign_default :unit_price, 0
17
- assign_default :vat_rate, ::Dorsale::BillingMachine::DEFAULT_VAT_RATE
17
+ assign_default :vat_rate, ::Dorsale::BillingMachine.default_vat_rate
18
18
  end
19
19
 
20
20
  def update_total
21
21
  assign_default_values
22
- self.total = quantity * unit_price
22
+ self.total = (quantity * unit_price).round(2)
23
23
  end
24
24
 
25
25
  after_save :update_invoice_total
@@ -76,7 +76,7 @@ class Dorsale::BillingMachine::Quotation < ::Dorsale::ApplicationRecord
76
76
 
77
77
  lines.each do |line|
78
78
  line_total = line.total - (line.total * discount_rate)
79
- self.vat_amount += (line_total * line.vat_rate / 100.0)
79
+ self.vat_amount += (line_total * line.vat_rate / 100.0).round(2)
80
80
  end
81
81
 
82
82
  self.total_including_taxes = total_excluding_taxes + vat_amount
@@ -105,7 +105,7 @@ class Dorsale::BillingMachine::Quotation < ::Dorsale::ApplicationRecord
105
105
  raise "Quotation has multiple vat rates"
106
106
  end
107
107
 
108
- vat_rates.first || ::Dorsale::BillingMachine::DEFAULT_VAT_RATE
108
+ vat_rates.first || ::Dorsale::BillingMachine.default_vat_rate
109
109
  end
110
110
 
111
111
  attr_writer :vat_rate
@@ -14,12 +14,12 @@ class Dorsale::BillingMachine::QuotationLine < ::Dorsale::ApplicationRecord
14
14
  def assign_default_values
15
15
  assign_default :quantity, 0
16
16
  assign_default :unit_price, 0
17
- assign_default :vat_rate, ::Dorsale::BillingMachine::DEFAULT_VAT_RATE
17
+ assign_default :vat_rate, ::Dorsale::BillingMachine.default_vat_rate
18
18
  end
19
19
 
20
20
  def update_total
21
21
  assign_default_values
22
- self.total = quantity * unit_price
22
+ self.total = (quantity * unit_price).round(2)
23
23
  end
24
24
 
25
25
  after_save :update_quotation_total
@@ -1,3 +1,3 @@
1
1
  module Dorsale
2
- VERSION = "3.9.8"
2
+ VERSION = "3.10.0"
3
3
  end
@@ -25,7 +25,7 @@ describe Dorsale::BillingMachine::InvoiceLine, type: :model do
25
25
  end
26
26
 
27
27
  it "vat_rate should be 0" do
28
- expect(described_class.new.vat_rate).to eq Dorsale::BillingMachine::DEFAULT_VAT_RATE
28
+ expect(described_class.new.vat_rate).to eq Dorsale::BillingMachine.default_vat_rate
29
29
  end
30
30
  end
31
31
 
@@ -41,12 +41,12 @@ describe Dorsale::BillingMachine::InvoiceLine, type: :model do
41
41
  end
42
42
 
43
43
  it "should update the total upon save" do
44
- invoice = create(:billing_machine_invoice_line, quantity: 10, unit_price: 10, total: 0)
45
- expect(invoice.total).to eq(100)
44
+ line = create(:billing_machine_invoice_line, quantity: 12.34, unit_price: 12.34, total: 0)
45
+ expect(line.total).to eq(152.28)
46
46
  end
47
47
 
48
48
  it "should update the total gracefully with invalid data" do
49
- invoice = create(:billing_machine_invoice_line, quantity: nil, unit_price: nil, total: 0)
50
- expect(invoice.total).to eq(0)
49
+ line = create(:billing_machine_invoice_line, quantity: nil, unit_price: nil, total: 0)
50
+ expect(line.total).to eq(0)
51
51
  end
52
52
  end
@@ -120,7 +120,7 @@ describe Dorsale::BillingMachine::Invoice, type: :model do
120
120
 
121
121
  describe "vat rate" do
122
122
  it "default vat rate should be 20" do
123
- expect(described_class.new.vat_rate).to eq ::Dorsale::BillingMachine::DEFAULT_VAT_RATE
123
+ expect(described_class.new.vat_rate).to eq ::Dorsale::BillingMachine.default_vat_rate
124
124
  end
125
125
 
126
126
  it "it should be specified vat rate" do
@@ -202,6 +202,31 @@ describe Dorsale::BillingMachine::Invoice, type: :model do
202
202
  expect(invoice.balance).to eq(108)
203
203
  end
204
204
 
205
+ it "should round numbers" do
206
+ invoice = create(:billing_machine_invoice,
207
+ :commercial_discount => 0,
208
+ )
209
+
210
+ create(:billing_machine_invoice_line,
211
+ :quantity => 12.34,
212
+ :unit_price => 12.34,
213
+ :vat_rate => 20,
214
+ :invoice => invoice,
215
+ ) # total 152.28
216
+
217
+ create(:billing_machine_invoice_line,
218
+ :quantity => 12.34,
219
+ :unit_price => 12.34,
220
+ :vat_rate => 20,
221
+ :invoice => invoice,
222
+ ) # total 152.28
223
+
224
+ expect(invoice.total_excluding_taxes).to eq(304.56)
225
+ expect(invoice.vat_amount).to eq(60.92)
226
+ expect(invoice.total_including_taxes).to eq(365.48)
227
+ expect(invoice.balance).to eq(365.48)
228
+ end
229
+
205
230
  it "should work fine even with empty lines" do
206
231
  invoice = create(:billing_machine_invoice)
207
232
 
@@ -25,7 +25,7 @@ describe Dorsale::BillingMachine::QuotationLine do
25
25
  end
26
26
 
27
27
  it "vat_rate should be 0" do
28
- expect(described_class.new.vat_rate).to eq ::Dorsale::BillingMachine::DEFAULT_VAT_RATE
28
+ expect(described_class.new.vat_rate).to eq ::Dorsale::BillingMachine.default_vat_rate
29
29
  end
30
30
  end
31
31
 
@@ -40,12 +40,12 @@ describe Dorsale::BillingMachine::QuotationLine do
40
40
  end
41
41
 
42
42
  it "should update the total upon save" do
43
- quotation = create(:billing_machine_quotation_line, quantity: 10, unit_price: 10, total: 0)
44
- expect(quotation.total).to eq(100)
43
+ line = create(:billing_machine_quotation_line, quantity: 12.34, unit_price: 12.34, total: 0)
44
+ expect(line.total).to eq(152.28)
45
45
  end
46
46
 
47
47
  it "should update the total gracefully with invalid data" do
48
- quotation = create(:billing_machine_quotation_line, quantity: nil, unit_price: nil, total: 0)
49
- expect(quotation.total).to eq(0)
48
+ line = create(:billing_machine_quotation_line, quantity: nil, unit_price: nil, total: 0)
49
+ expect(line.total).to eq(0)
50
50
  end
51
51
  end
@@ -74,7 +74,7 @@ describe Dorsale::BillingMachine::Quotation do
74
74
 
75
75
  describe "vat rate" do
76
76
  it "default vat rate should be 20" do
77
- expect(described_class.new.vat_rate).to eq ::Dorsale::BillingMachine::DEFAULT_VAT_RATE
77
+ expect(described_class.new.vat_rate).to eq ::Dorsale::BillingMachine.default_vat_rate
78
78
  end
79
79
 
80
80
  it "it should be specified vat rate" do
@@ -152,6 +152,31 @@ describe Dorsale::BillingMachine::Quotation do
152
152
  Dorsale::BillingMachine.vat_mode = :single
153
153
  end
154
154
 
155
+ it "should round numbers" do
156
+ quotation = create(:billing_machine_quotation,
157
+ :commercial_discount => 0,
158
+ )
159
+
160
+ create(:billing_machine_quotation_line,
161
+ :quantity => 12.34,
162
+ :unit_price => 12.34,
163
+ :vat_rate => 20,
164
+ :quotation => quotation,
165
+ ) # total 152.28
166
+
167
+ create(:billing_machine_quotation_line,
168
+ :quantity => 12.34,
169
+ :unit_price => 12.34,
170
+ :vat_rate => 20,
171
+ :quotation => quotation,
172
+ ) # total 152.28
173
+
174
+ expect(quotation.total_excluding_taxes).to eq(304.56)
175
+ expect(quotation.vat_amount).to eq(60.92)
176
+ expect(quotation.total_including_taxes).to eq(365.48)
177
+ expect(quotation.balance).to eq(365.48)
178
+ end
179
+
155
180
  it "should work fine even with empty lines" do
156
181
  quotation = create(:billing_machine_quotation, commercial_discount: nil)
157
182
 
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: dorsale
3
3
  version: !ruby/object:Gem::Version
4
- version: 3.9.8
4
+ version: 3.10.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - agilidée
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2018-07-04 00:00:00.000000000 Z
11
+ date: 2018-08-07 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rails