minting 1.7.3 → 1.8.1

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.
Files changed (40) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +31 -24
  3. data/Rakefile +15 -4
  4. data/doc/Mint/Currency.html +535 -18
  5. data/doc/Mint/Money.html +659 -185
  6. data/doc/Mint/RangeStepPatch.html +1 -1
  7. data/doc/Mint/Registry.html +19 -2
  8. data/doc/Mint/Rounding.html +495 -0
  9. data/doc/Mint/UnknownCurrency.html +1 -1
  10. data/doc/Mint.html +187 -399
  11. data/doc/Minting.html +2 -2
  12. data/doc/_index.html +8 -1
  13. data/doc/agents/api_review-2026-06-15.md +0 -13
  14. data/doc/agents/copilot-instructions.md +70 -0
  15. data/doc/class_list.html +1 -1
  16. data/doc/file.README.html +19 -9
  17. data/doc/index.html +19 -9
  18. data/doc/method_list.html +130 -42
  19. data/doc/top-level-namespace.html +1 -1
  20. data/lib/minting/currency/currency.rb +41 -2
  21. data/lib/minting/mint/dsl/numeric.rb +4 -4
  22. data/lib/minting/mint/dsl/range.rb +1 -0
  23. data/lib/minting/mint/dsl/string.rb +1 -1
  24. data/lib/minting/mint/mint.rb +10 -37
  25. data/lib/minting/mint/parser/parser.rb +50 -15
  26. data/lib/minting/mint/parser/separators.rb +10 -8
  27. data/lib/minting/mint/registry/zeros.rb +3 -1
  28. data/lib/minting/mint/rounding.rb +51 -0
  29. data/lib/minting/mint.rb +1 -0
  30. data/lib/minting/money/allocation/allocation.rb +1 -2
  31. data/lib/minting/money/allocation/split.rb +1 -1
  32. data/lib/minting/money/arithmetics/methods.rb +2 -2
  33. data/lib/minting/money/arithmetics/operators.rb +6 -6
  34. data/lib/minting/money/clamp.rb +1 -1
  35. data/lib/minting/money/coercion.rb +1 -1
  36. data/lib/minting/money/comparable.rb +6 -0
  37. data/lib/minting/money/constructors.rb +60 -12
  38. data/lib/minting/money/money.rb +0 -6
  39. data/lib/minting/version.rb +1 -1
  40. metadata +4 -1
@@ -6,29 +6,58 @@ module Mint
6
6
 
7
7
  # Parses a human-readable money string into a {Money} object.
8
8
  #
9
+ # Returns +nil+ when the input is invalid or currency cannot be determined.
10
+ #
9
11
  # @param input [String] Amount input, optionally including a currency symbol or code
10
12
  # @param currency [String, Symbol, Currency, nil] ISO code when not present in +input+
11
- # @return [Money]
12
- # @raise [ArgumentError] when +input+ is invalid or currency cannot be determined
13
+ # @return [Money, nil]
13
14
  #
14
15
  # @example With explicit currency
15
- # Money.parse('19.99', 'USD') #=> [USD 19.99]
16
- # Money.parse('1.234,56', 'EUR') #=> [EUR 1234.56]
16
+ # Mint.parse('19.99', 'USD') #=> [USD 19.99]
17
+ # Mint.parse('garbage', 'USD') #=> nil
17
18
  #
18
19
  # @example With symbol or code in the string
19
- # Money.parse('$19.99') #=> [USD 19.99]
20
- # Money.parse('19,99 €') #=> [EUR 19.99]
21
- # Money.parse('USD 1,234.56') #=> [USD 1234.56]
20
+ # Mint.parse('$19.99') #=> [USD 19.99]
21
+ # Mint.parse('USD 1,234.56') #=> [USD 1234.56]
22
22
  def parse(input, currency = nil)
23
+ return nil unless input.is_a?(String)
24
+
25
+ input = input.strip
26
+ return nil if input.empty?
27
+
28
+ currency = parse_currency(input, currency)
29
+ return nil unless currency
30
+
31
+ amount = parse_amount(input)
32
+ return nil unless amount
33
+
34
+ amount = currency.normalize_amount(amount)
35
+ Mint::Money.new(amount, currency)
36
+ end
37
+
38
+ # Like {.parse} but raises on failure.
39
+ #
40
+ # @param input [String] Amount input, optionally including a currency symbol or code
41
+ # @param currency [String, Symbol, Currency, nil] ISO code when not present in +input+
42
+ # @return [Money]
43
+ # @raise [ArgumentError] when +input+ is invalid or currency cannot be determined
44
+ #
45
+ # @example
46
+ # Mint.parse!('19.99', 'USD') #=> [USD 19.99]
47
+ # Mint.parse!('garbage', 'USD') #=> ArgumentError
48
+ def parse!(input, currency = nil)
23
49
  raise ArgumentError, 'input must be a String' unless input.is_a?(String)
24
50
 
25
51
  input = input.strip
26
52
  raise ArgumentError, 'input cannot be empty' if input.empty?
27
53
 
28
- currency = Currency.resolve(currency) || parse_currency(input)
29
- raise ArgumentError, "Currency [#{currency}] not registered" unless currency
54
+ currency = parse_currency(input, currency)
55
+ raise ArgumentError, "Currency [#{currency}] not found" unless currency
56
+
57
+ amount = parse_amount(input)
58
+ raise ArgumentError, "Could not parse [#{input}]" unless amount
30
59
 
31
- amount = currency.normalize_amount(parse_amount(input))
60
+ amount = currency.normalize_amount(amount)
32
61
  Mint::Money.new(amount, currency)
33
62
  end
34
63
 
@@ -40,8 +69,11 @@ module Mint
40
69
  accounting_negative = input.start_with?('(') && input.end_with?(')')
41
70
 
42
71
  # Remove any charater that is not a digit, comma or period
43
- numeric = input.scan(/[\d.,-]/).join
44
- amount = Rational(normalize_separators(numeric))
72
+ numeric_input = input.scan(/[\d.,-]/).join
73
+ numeric = parse_separators(numeric_input)
74
+ return nil unless numeric
75
+
76
+ amount = Rational(numeric)
45
77
  accounting_negative ? -amount : amount
46
78
  end
47
79
 
@@ -51,12 +83,15 @@ module Mint
51
83
  # back to symbol matching. This correctly handles inputs like
52
84
  # "MAX 10.00 USD" where the first uppercase word isn't a currency code.
53
85
  # @private
54
- def parse_currency(input)
86
+ def parse_currency(input, currency = nil)
87
+ currency = Currency.resolve(currency)
88
+ return currency if currency
89
+
55
90
  input.scan(/\b([A-Z_]+)\b/) do |(code)|
56
- currency = Mint.currency_for_code(code)
91
+ currency = Currency.for_code(code)
57
92
  return currency if currency
58
93
  end
59
94
 
60
- Registry.detect_currency(input) or raise ArgumentError, 'Currency could not be detected'
95
+ Registry.detect_currency(input)
61
96
  end
62
97
  end
@@ -10,24 +10,26 @@ module Mint
10
10
  # @private
11
11
  def classify_separators(numeric)
12
12
  case [numeric.count('.'), numeric.count(',')]
13
- in [0, 1] if numeric[-4] == ',' then :thousands_comma # Comma is a thousand separator
14
- in [0, 1] then :decimal_comma # Only one comma: decimal (e.g. 19,99 or 1,4 or 1,2345).
15
- in [0, 0] | [1, 0] then :decimal_period # e.g. "1500" or "34.21".
16
- in [p, c] if p > 1 && c > 1 then :ambiguous # Both separators appear multiple times
17
- in [p, c] if p > 0 && c > 0 then :mixed # Commas and dots: the rightmost one is the decimal
18
- else :thousands # Multiple of the same separator only (e.g. 1,234,567)
13
+ in [0, 1] if numeric[-4] == ',' then :thousands_comma # Comma is a thousand separator
14
+ in [0, 1] then :decimal_comma # Only one comma: decimal (e.g. 19,99 or 1,4 or 1,2345).
15
+ in [0, 0] | [1, 0] then :decimal_period # e.g. "1500" or "34.21".
16
+ in [p, c] if p > 1 && c > 1 then :invalid # Both separators appear multiple times
17
+ in [p, c] if p > 0 && c > 0 then :mixed # Commas and dots: the rightmost one is the decimal
18
+ else :thousands # Multiple of the same separator only (e.g. 1,234,567)
19
19
  end
20
20
  end
21
21
 
22
22
  # Converts locale-specific decimal/thousand separators into a plain decimal string.
23
23
  # @private
24
- def normalize_separators(numeric)
24
+ def parse_separators(numeric)
25
+ return nil unless numeric.match?(/\d/)
26
+
25
27
  case classify_separators(numeric)
26
28
  when :decimal_period then numeric # Nothing to normalize (e.g. "1500" or "34.21").
27
29
  when :decimal_comma then numeric.tr(',', '.') # Only one comma: decimal (e.g. 19,99 or 1,234).
28
30
  when :thousands_comma then numeric.delete(',')
29
31
  when :thousands then numeric.delete('.,')
30
- when :ambiguous then raise ArgumentError, "could not distinguish decimal and thousand separators in '#{numeric}'"
32
+ when :invalid then nil
31
33
  when :mixed # Commas and dots: the rightmost one is the decimal separator.
32
34
  if numeric.rindex(',') > numeric.rindex('.')
33
35
  numeric.delete('.').tr(',', '.')
@@ -9,9 +9,11 @@ module Mint
9
9
  # @return [Money] a frozen zero-Money
10
10
  # @api private
11
11
  def self.zero_for(currency)
12
+ raise ArgumentError, "Expect a Currency param. (#{currency})" unless currency.is_a?(Currency)
13
+
12
14
  MUTEX.synchronize do
13
15
  @zeros ||= {}
14
- @zeros[currency] ||= Mint::Money.send(:new, 0, currency)
16
+ @zeros[currency] ||= Mint::Money.send(:new, 0r, currency)
15
17
  end
16
18
  end
17
19
  end
@@ -0,0 +1,51 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Mint
4
+ # Rounding-mode dispatch table and block-scoped context.
5
+ # @api private
6
+ module Rounding
7
+ # Maps mode symbols to their corresponding +Rational+ rounding lambdas.
8
+ # @return [Hash{Symbol => Proc}]
9
+ # @api private
10
+ MODES = {
11
+ half_up: ->(amount, ndigits) { amount.round(ndigits, half: :up) },
12
+ half_down: ->(amount, ndigits) { amount.round(ndigits, half: :down) },
13
+ floor: ->(amount, ndigits) { amount.floor(ndigits) },
14
+ ceil: ->(amount, ndigits) { amount.ceil(ndigits) },
15
+ truncate: ->(amount, ndigits) { amount.truncate(ndigits) },
16
+ down: ->(amount, ndigits) { amount.truncate(ndigits) }
17
+ }.freeze
18
+
19
+ # Returns the currently active rounding mode, falling back to +:half_up+.
20
+ # @api private
21
+ # @return [Symbol]
22
+ def self.current_mode
23
+ Thread.current[:minting_rounding_mode] || :half_up
24
+ end
25
+
26
+ # Rounds +amount+ to +ndigits+ using the currently scoped rounding mode.
27
+ # @api private
28
+ # @param amount [Numeric]
29
+ # @param ndigits [Integer]
30
+ # @return [Rational]
31
+ def self.apply(amount, ndigits)
32
+ MODES.fetch(current_mode).call(amount.to_r, ndigits)
33
+ end
34
+
35
+ # Sets a rounding mode for the duration of a block, restoring the
36
+ # previous mode on exit (even on exception).
37
+ # @api private
38
+ # @param mode [Symbol]
39
+ # @yield block to execute with the mode active
40
+ # @raise [ArgumentError] on unknown mode
41
+ def self.with_mode(mode)
42
+ raise ArgumentError, "Unknown rounding mode: #{mode}" unless MODES.key?(mode)
43
+
44
+ prev = Thread.current[:minting_rounding_mode]
45
+ Thread.current[:minting_rounding_mode] = mode
46
+ yield
47
+ ensure
48
+ Thread.current[:minting_rounding_mode] = prev
49
+ end
50
+ end
51
+ end
data/lib/minting/mint.rb CHANGED
@@ -1,5 +1,6 @@
1
1
  # frozen_string_literal: true
2
2
 
3
+ require_relative 'mint/rounding'
3
4
  require_relative 'currency/currency'
4
5
 
5
6
  require_relative 'mint/dsl/numeric'
@@ -17,8 +17,7 @@ module Mint
17
17
  raise ArgumentError, 'Need at least 1 proportion element' if proportions.empty?
18
18
  raise ArgumentError, 'Proportions total must not be zero' if whole.zero?
19
19
 
20
- subunit = currency.subunit
21
- amounts = proportions.map { |rate| Rational(amount * rate, whole).round(subunit) }
20
+ amounts = proportions.map { |rate| currency.normalize_amount(Rational(amount * rate, whole)) }
22
21
  allocate_left_over(amounts: amounts, left_over: amount - amounts.sum)
23
22
  end
24
23
  end
@@ -17,7 +17,7 @@ module Mint
17
17
  def split(slices)
18
18
  raise ArgumentError, 'Slices quantity must be an poitive integer' unless slices.positive? && slices.integer?
19
19
 
20
- fraction = (amount / slices).round(currency.subunit)
20
+ fraction = currency.normalize_amount(amount / slices)
21
21
  allocate_left_over(amounts: Array.new(slices, fraction),
22
22
  left_over: amount - (fraction * slices))
23
23
  end
@@ -6,7 +6,7 @@ module Mint
6
6
  # Returns the absolute value of the monetary amount as a new {Money} instance.
7
7
  #
8
8
  # @return [Money] the absolute value
9
- def abs = mint(amount.abs)
9
+ def abs = copy_with(amount: amount.abs)
10
10
 
11
11
  # Returns true if the monetary amount is less than zero.
12
12
  #
@@ -22,6 +22,6 @@ module Mint
22
22
  # Enables standard ranges and stepping (e.g. `1.dollar..10.dollars`).
23
23
  #
24
24
  # @return [Money] successor Money instance
25
- def succ = mint(amount + currency.minimum_amount)
25
+ def succ = copy_with(amount: amount + currency.minimum_amount)
26
26
  end
27
27
  end
@@ -11,7 +11,7 @@ module Mint
11
11
  def +(addend)
12
12
  case addend
13
13
  in 0 then self
14
- in Money if same_currency?(addend) then mint(amount + addend.amount)
14
+ in Money if same_currency?(addend) then copy_with(amount: amount + addend.amount)
15
15
  else raise TypeError, "#{addend} can't be added to #{self}"
16
16
  end
17
17
  end
@@ -24,7 +24,7 @@ module Mint
24
24
  def -(subtrahend)
25
25
  case subtrahend
26
26
  when 0 then return self
27
- when Money then return mint(amount - subtrahend.amount) if same_currency?(subtrahend)
27
+ when Money then return copy_with(amount: amount - subtrahend.amount) if same_currency?(subtrahend)
28
28
  end
29
29
  raise TypeError, "#{subtrahend} can't be subtracted from #{self}"
30
30
  end
@@ -32,7 +32,7 @@ module Mint
32
32
  # Unary negation operator. Returns a new {Money} instance with the inverted sign.
33
33
  #
34
34
  # @return [Money] negated Money instance
35
- def -@ = mint(-amount)
35
+ def -@ = copy_with(amount: -amount)
36
36
 
37
37
  # Performs multiplication of the monetary value by a standard scalar Numeric.
38
38
  #
@@ -42,7 +42,7 @@ module Mint
42
42
  def *(multiplicand)
43
43
  raise TypeError, "#{self} can't be multiplied by #{multiplicand}" unless multiplicand.is_a?(Numeric)
44
44
 
45
- mint(amount * multiplicand)
45
+ copy_with(amount: amount * multiplicand)
46
46
  end
47
47
 
48
48
  # Performs division of the monetary value by a scalar Numeric or identical currency {Money}.
@@ -53,7 +53,7 @@ module Mint
53
53
  # @raise [ZeroDivisionError] if division by zero is attempted
54
54
  def /(divisor)
55
55
  case divisor
56
- when Numeric then return mint(amount / divisor)
56
+ when Numeric then return copy_with(amount: amount / divisor)
57
57
  when Money then return amount / divisor.amount if same_currency? divisor
58
58
  end
59
59
  raise TypeError, "#{self} can't be divided by #{divisor}"
@@ -65,7 +65,7 @@ module Mint
65
65
  # @return [Money] reult of amount ** exponent
66
66
  # @raise [TypeError] if exponent is not Numeric
67
67
  def **(exponent)
68
- return mint(amount**exponent) if exponent.is_a?(Numeric)
68
+ return copy_with(amount: amount**exponent) if exponent.is_a?(Numeric)
69
69
 
70
70
  raise TypeError, "#{self} can't be powered by #{exponent}"
71
71
  end
@@ -47,7 +47,7 @@ module Mint
47
47
  else
48
48
  min = min_or_range
49
49
  end
50
- mint(amount.clamp(normalize_boundary(min), normalize_boundary(max)))
50
+ copy_with(amount: amount.clamp(normalize_boundary(min), normalize_boundary(max)))
51
51
  end
52
52
 
53
53
  private
@@ -44,7 +44,7 @@ module Mint
44
44
  # Multiplies a Money object by the wrapped numeric value.
45
45
  # This is the standard coercion path for `Numeric * Money`.
46
46
  def *(other)
47
- other.mint(@value * other.amount)
47
+ other.copy_with(amount: @value * other.amount)
48
48
  end
49
49
 
50
50
  # @private
@@ -44,6 +44,12 @@ module Mint
44
44
  # @return [self, nil] self if amount is non-zero, nil otherwise
45
45
  def nonzero? = amount.nonzero?
46
46
 
47
+ # Helper method to verify if another Money has the identical currency.
48
+ #
49
+ # @param other [Money] the target currency to compare
50
+ # @return [Boolean] true if currencies match, false otherwise
51
+ def same_currency?(other) = other.currency == currency
52
+
47
53
  # @return [Boolean] true if amount is zero
48
54
  def zero? = amount.zero?
49
55
  end
@@ -7,13 +7,56 @@ module Mint
7
7
  # @param amount [Numeric] The monetary amount
8
8
  # @param currency [Currency, String] The currency code or currency object
9
9
  # @raise [ArgumentError] If amount is not numeric or currency is invalid
10
- def self.create(amount, currency)
10
+ def self.from(amount, currency)
11
11
  raise ArgumentError, 'amount must be Numeric' unless amount.is_a?(Numeric)
12
12
 
13
13
  currency = Currency.resolve!(currency)
14
14
  amount = currency.normalize_amount(amount)
15
15
 
16
- amount.zero? ? Mint.zero(currency) : new(amount, currency)
16
+ amount.zero? ? currency.zero : new(amount, currency)
17
+ end
18
+
19
+ # Parses a human-readable money string into a {Money} object.
20
+ #
21
+ # Returns +nil+ when the input is invalid or currency cannot be determined.
22
+ #
23
+ # @param input [String] Amount input, optionally including a currency symbol or code
24
+ # @param currency [String, Symbol, Currency, nil] ISO code when not present in +input+
25
+ # @return [Money, nil]
26
+ #
27
+ # @example With explicit currency
28
+ # Money.parse('19.99', 'USD') #=> [USD 19.99]
29
+ # Money.parse('garbage', 'USD') #=> nil
30
+ #
31
+ # @example With symbol or code in the string
32
+ # Money.parse('$19.99') #=> [USD 19.99]
33
+ # Money.parse('USD 1,234.56') #=> [USD 1234.56]
34
+ def self.parse(input, currency = nil) = Mint.parse(input, currency)
35
+
36
+ # Like {.parse} but raises on failure.
37
+ #
38
+ # @param input [String] Amount input, optionally including a currency symbol or code
39
+ # @param currency [String, Symbol, Currency, nil] ISO code when not present in +input+
40
+ # @return [Money]
41
+ # @raise [ArgumentError] when +input+ is invalid or currency cannot be determined
42
+ #
43
+ # @example
44
+ # Money.parse!('19.99', 'USD') #=> [USD 19.99]
45
+ # Money.parse!('garbage', 'USD') #=> ArgumentError
46
+ def self.parse!(input, currency = nil) = Mint.parse!(input, currency)
47
+
48
+ # Returns a frozen zero Money in the given currency.
49
+ #
50
+ # @param currency [String, Currency] a currency code or object
51
+ # @return [Money] a frozen zero-Money
52
+ # @raise [ArgumentError] if the currency can't be resolved
53
+ def self.zero(currency) = Currency.resolve!(currency).zero
54
+
55
+ # Backwards-compatible alias for previous API
56
+ # TODO: deprecate in a future major release
57
+ def self.create(amount, currency)
58
+ warn 'Money.create is now deprecated. Use Money.from'
59
+ from(amount, currency)
17
60
  end
18
61
 
19
62
  # Builds a Money from a fractional (smallest-unit) Integer amount.
@@ -39,31 +82,36 @@ module Mint
39
82
 
40
83
  currency = Currency.resolve!(currency)
41
84
  amount = Rational(fractional, currency.fractional_multiplier)
42
- amount.zero? ? Mint.zero(currency) : new(amount, currency)
85
+ amount.zero? ? currency.zero : new(amount, currency)
43
86
  end
44
87
 
45
88
  # Returns a new Money object with the specified amount, or self if unchanged.
46
89
  # This is the primary method for creating a modified copy of a Money instance
47
90
  # while preserving immutability.
48
91
  #
49
- # @param new_amount [Numeric] The new monetary amount
92
+ # @param amount [Numeric] The new monetary amount
50
93
  # @return [Money] A new Money object with the new amount, or self if the amount is unchanged
51
94
  # @example
52
95
  # price = Mint.money(10.00, 'USD')
53
- # price.mint(15.00) #=> [USD 15.00]
54
- # price.mint(10.00) #=> [USD 10.00] (returns self)
55
- def mint(new_amount)
56
- new_amount = currency.normalize_amount(new_amount)
96
+ # price.copy_with(amount: 15.00) #=> [USD 15.00]
97
+ # price.copy_with(amount: 10.00) #=> [USD 10.00] (returns self)
98
+ def copy_with(amount:)
99
+ amount = currency.normalize_amount(amount)
57
100
 
58
- if new_amount == amount
101
+ if amount == self.amount
59
102
  self
60
- elsif new_amount.zero?
61
- Mint.zero(currency)
103
+ elsif amount.zero?
104
+ currency.zero
62
105
  else
63
- Money.new(new_amount, currency)
106
+ Money.new(amount, currency)
64
107
  end
65
108
  end
66
109
 
110
+ def mint(new_amount)
111
+ warn 'Money#mint is now deprecated and will be removed in v2'
112
+ copy_with(amount: new_amount)
113
+ end
114
+
67
115
  private
68
116
 
69
117
  # Initializes a new Money object with the given amount and currency.
@@ -49,11 +49,5 @@ module Mint
49
49
  def inspect
50
50
  Kernel.format "[#{currency_code} %0.#{currency.subunit}f]", amount
51
51
  end
52
-
53
- # Helper method to verify if another object has the identical currency.
54
- #
55
- # @param other [Currency] the target currency to compare
56
- # @return [Boolean] true if currencies match, false otherwise
57
- def same_currency?(other) = other.currency == currency
58
52
  end
59
53
  end
@@ -3,5 +3,5 @@
3
3
  # Root namespace for the Minting library.
4
4
  module Minting
5
5
  # Current version of the Minting gem.
6
- VERSION = '1.7.3'
6
+ VERSION = '1.8.1'
7
7
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: minting
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.7.3
4
+ version: 1.8.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Gilson Ferraz
@@ -42,10 +42,12 @@ files:
42
42
  - doc/Mint/Money.html
43
43
  - doc/Mint/RangeStepPatch.html
44
44
  - doc/Mint/Registry.html
45
+ - doc/Mint/Rounding.html
45
46
  - doc/Mint/UnknownCurrency.html
46
47
  - doc/Minting.html
47
48
  - doc/_index.html
48
49
  - doc/agents/api_review-2026-06-15.md
50
+ - doc/agents/copilot-instructions.md
49
51
  - doc/agents/expired/AGENTS.md
50
52
  - doc/agents/expired/copilot-instructions.md
51
53
  - doc/agents/expired/gemini_gem_evaluation.md
@@ -81,6 +83,7 @@ files:
81
83
  - lib/minting/mint/registry/registry.rb
82
84
  - lib/minting/mint/registry/symbols.rb
83
85
  - lib/minting/mint/registry/zeros.rb
86
+ - lib/minting/mint/rounding.rb
84
87
  - lib/minting/money/allocation/allocation.rb
85
88
  - lib/minting/money/allocation/split.rb
86
89
  - lib/minting/money/arithmetics/methods.rb