tiny-sharp-rb 0.0.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.
- checksums.yaml +7 -0
- data/money-7.0.2/CHANGELOG.md +843 -0
- data/money-7.0.2/LICENSE +23 -0
- data/money-7.0.2/README.md +626 -0
- data/money-7.0.2/config/currency_backwards_compatible.json +225 -0
- data/money-7.0.2/config/currency_iso.json +2750 -0
- data/money-7.0.2/config/currency_non_iso.json +146 -0
- data/money-7.0.2/lib/money/bank/base.rb +130 -0
- data/money-7.0.2/lib/money/bank/single_currency.rb +26 -0
- data/money-7.0.2/lib/money/bank/variable_exchange.rb +285 -0
- data/money-7.0.2/lib/money/currency/heuristics.rb +11 -0
- data/money-7.0.2/lib/money/currency/loader.rb +28 -0
- data/money-7.0.2/lib/money/currency.rb +477 -0
- data/money-7.0.2/lib/money/locale_backend/base.rb +9 -0
- data/money-7.0.2/lib/money/locale_backend/currency.rb +13 -0
- data/money-7.0.2/lib/money/locale_backend/errors.rb +8 -0
- data/money-7.0.2/lib/money/locale_backend/i18n.rb +28 -0
- data/money-7.0.2/lib/money/money/allocation.rb +87 -0
- data/money-7.0.2/lib/money/money/arithmetic.rb +346 -0
- data/money-7.0.2/lib/money/money/constructors.rb +86 -0
- data/money-7.0.2/lib/money/money/formatter.rb +361 -0
- data/money-7.0.2/lib/money/money/formatting_rules.rb +92 -0
- data/money-7.0.2/lib/money/money/locale_backend.rb +20 -0
- data/money-7.0.2/lib/money/money.rb +664 -0
- data/money-7.0.2/lib/money/rates_store/memory.rb +122 -0
- data/money-7.0.2/lib/money/version.rb +5 -0
- data/money-7.0.2/lib/money.rb +9 -0
- data/money-7.0.2/money.gemspec +32 -0
- data/tiny-sharp-rb.gemspec +12 -0
- metadata +69 -0
|
@@ -0,0 +1,361 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require 'money/money/formatting_rules'
|
|
4
|
+
|
|
5
|
+
class Money
|
|
6
|
+
class Formatter
|
|
7
|
+
DEFAULTS = {
|
|
8
|
+
thousands_separator: '',
|
|
9
|
+
decimal_mark: '.'
|
|
10
|
+
}.freeze
|
|
11
|
+
|
|
12
|
+
# Creates a formatted price string according to several rules.
|
|
13
|
+
#
|
|
14
|
+
# @param [Hash] rules The options used to format the string.
|
|
15
|
+
#
|
|
16
|
+
# @return [String]
|
|
17
|
+
#
|
|
18
|
+
# @option rules [Boolean, String] :display_free (false) Whether a zero
|
|
19
|
+
# amount of money should be formatted of "free" or as the supplied string.
|
|
20
|
+
#
|
|
21
|
+
# @example
|
|
22
|
+
# Money.us_dollar(0).format(display_free: true) #=> "free"
|
|
23
|
+
# Money.us_dollar(0).format(display_free: "gratis") #=> "gratis"
|
|
24
|
+
# Money.us_dollar(0).format #=> "$0.00"
|
|
25
|
+
#
|
|
26
|
+
# @option rules [Boolean] :with_currency (false) Whether the currency name
|
|
27
|
+
# should be appended to the result string.
|
|
28
|
+
#
|
|
29
|
+
# @example
|
|
30
|
+
# Money.ca_dollar(100).format #=> "$1.00"
|
|
31
|
+
# Money.ca_dollar(100).format(with_currency: true) #=> "$1.00 CAD"
|
|
32
|
+
# Money.us_dollar(85).format(with_currency: true) #=> "$0.85 USD"
|
|
33
|
+
#
|
|
34
|
+
# @option rules [Boolean] :rounded_infinite_precision (false) Whether the
|
|
35
|
+
# amount of money should be rounded when using {default_infinite_precision}
|
|
36
|
+
#
|
|
37
|
+
# @example
|
|
38
|
+
# Money.us_dollar(100.1).format #=> "$1.001"
|
|
39
|
+
# Money.us_dollar(100.1).format(rounded_infinite_precision: true) #=> "$1"
|
|
40
|
+
# Money.us_dollar(100.9).format(rounded_infinite_precision: true) #=> "$1.01"
|
|
41
|
+
#
|
|
42
|
+
# @option rules [Boolean] :no_cents (false) Whether cents should be omitted.
|
|
43
|
+
#
|
|
44
|
+
# @example
|
|
45
|
+
# Money.ca_dollar(100).format(no_cents: true) #=> "$1"
|
|
46
|
+
# Money.ca_dollar(599).format(no_cents: true) #=> "$5"
|
|
47
|
+
#
|
|
48
|
+
# @option rules [Boolean] :no_cents_if_whole (false) Whether cents should be
|
|
49
|
+
# omitted if the cent value is zero
|
|
50
|
+
#
|
|
51
|
+
# @example
|
|
52
|
+
# Money.ca_dollar(10000).format(no_cents_if_whole: true) #=> "$100"
|
|
53
|
+
# Money.ca_dollar(10034).format(no_cents_if_whole: true) #=> "$100.34"
|
|
54
|
+
#
|
|
55
|
+
# @option rules [Boolean, String, nil] :symbol (true) Whether a money symbol
|
|
56
|
+
# should be prepended to the result string. The default is true. This method
|
|
57
|
+
# attempts to pick a symbol that's suitable for the given currency.
|
|
58
|
+
#
|
|
59
|
+
# @example
|
|
60
|
+
# Money.new(100, "USD") #=> "$1.00"
|
|
61
|
+
# Money.new(100, "GBP") #=> "£1.00"
|
|
62
|
+
# Money.new(100, "EUR") #=> "€1.00"
|
|
63
|
+
#
|
|
64
|
+
# # Same thing.
|
|
65
|
+
# Money.new(100, "USD").format(symbol: true) #=> "$1.00"
|
|
66
|
+
# Money.new(100, "GBP").format(symbol: true) #=> "£1.00"
|
|
67
|
+
# Money.new(100, "EUR").format(symbol: true) #=> "€1.00"
|
|
68
|
+
#
|
|
69
|
+
# # You can specify a false expression or an empty string to disable
|
|
70
|
+
# # prepending a money symbol.§
|
|
71
|
+
# Money.new(100, "USD").format(symbol: false) #=> "1.00"
|
|
72
|
+
# Money.new(100, "GBP").format(symbol: nil) #=> "1.00"
|
|
73
|
+
# Money.new(100, "EUR").format(symbol: "") #=> "1.00"
|
|
74
|
+
#
|
|
75
|
+
# # If the symbol for the given currency isn't known, then it will default
|
|
76
|
+
# # to "¤" as symbol.
|
|
77
|
+
# Money.new(100, "AWG").format(symbol: true) #=> "¤1.00"
|
|
78
|
+
#
|
|
79
|
+
# # You can specify a string as value to enforce using a particular symbol.
|
|
80
|
+
# Money.new(100, "AWG").format(symbol: "ƒ") #=> "ƒ1.00"
|
|
81
|
+
#
|
|
82
|
+
# # You can specify a indian currency format
|
|
83
|
+
# Money.new(10000000, "INR").format(south_asian_number_formatting: true) #=> "1,00,000.00"
|
|
84
|
+
# Money.new(10000000).format(south_asian_number_formatting: true) #=> "$1,00,000.00"
|
|
85
|
+
#
|
|
86
|
+
# @option rules [Boolean, String, nil] :decimal_mark (true) Whether the
|
|
87
|
+
# currency should be separated by the specified character or '.'
|
|
88
|
+
#
|
|
89
|
+
# @example
|
|
90
|
+
# # If a string is specified, it's value is used.
|
|
91
|
+
# Money.new(100, "USD").format(decimal_mark: ",") #=> "$1,00"
|
|
92
|
+
#
|
|
93
|
+
# # If the decimal_mark for a given currency isn't known, then it will default
|
|
94
|
+
# # to "." as decimal_mark.
|
|
95
|
+
# Money.new(100, "FOO").format #=> "$1.00"
|
|
96
|
+
#
|
|
97
|
+
# @option rules [Boolean, String, nil] :thousands_separator (true) Whether
|
|
98
|
+
# the currency should be delimited by the specified character or ','
|
|
99
|
+
#
|
|
100
|
+
# @example
|
|
101
|
+
# # If a falsey value is specified, no thousands_separator is used.
|
|
102
|
+
# Money.new(100000, "USD").format(thousands_separator: false) #=> "1000.00"
|
|
103
|
+
# Money.new(100000, "USD").format(thousands_separator: nil) #=> "1000.00"
|
|
104
|
+
# Money.new(100000, "USD").format(thousands_separator: "") #=> "1000.00"
|
|
105
|
+
#
|
|
106
|
+
# # If true is specified, the locale or default thousands_separator is used.
|
|
107
|
+
# Money.new(100000, "USD").format(thousands_separator: true) #=> "1,000.00"
|
|
108
|
+
#
|
|
109
|
+
# # If a string is specified, it's value is used.
|
|
110
|
+
# Money.new(100000, "USD").format(thousands_separator: ".") #=> "$1.000.00"
|
|
111
|
+
#
|
|
112
|
+
# # If the thousands_separator for a given currency isn't known, then it will
|
|
113
|
+
# # default to "," as thousands_separator.
|
|
114
|
+
# Money.new(100000, "FOO").format #=> "$1,000.00"
|
|
115
|
+
#
|
|
116
|
+
# @option rules [Boolean] :html_wrap (false) Whether all currency parts should be HTML-formatted.
|
|
117
|
+
#
|
|
118
|
+
# @example
|
|
119
|
+
# Money.ca_dollar(570).format(html_wrap: true, with_currency: true)
|
|
120
|
+
# #=> "<span class=\"money-currency-symbol\">$</span><span class=\"money-whole\">5</span><span class=\"money-decimal-mark\">.</span><span class=\"money-decimal\">70</span> <span class=\"money-currency\">CAD</span>"
|
|
121
|
+
#
|
|
122
|
+
# @option rules [Boolean] :sign_before_symbol (false) Whether the sign should be
|
|
123
|
+
# before the currency symbol.
|
|
124
|
+
#
|
|
125
|
+
# @example
|
|
126
|
+
# # You can specify to display the sign before the symbol for negative numbers
|
|
127
|
+
# Money.new(-100, "GBP").format(sign_before_symbol: true) #=> "-£1.00"
|
|
128
|
+
# Money.new(-100, "GBP").format(sign_before_symbol: false) #=> "£-1.00"
|
|
129
|
+
# Money.new(-100, "GBP").format #=> "£-1.00"
|
|
130
|
+
#
|
|
131
|
+
# @option rules [Boolean] :sign_positive (false) Whether positive numbers should be
|
|
132
|
+
# signed, too.
|
|
133
|
+
#
|
|
134
|
+
# @example
|
|
135
|
+
# # You can specify to display the sign with positive numbers
|
|
136
|
+
# Money.new(100, "GBP").format(sign_positive: true, sign_before_symbol: true) #=> "+£1.00"
|
|
137
|
+
# Money.new(100, "GBP").format(sign_positive: true, sign_before_symbol: false) #=> "£+1.00"
|
|
138
|
+
# Money.new(100, "GBP").format(sign_positive: false, sign_before_symbol: true) #=> "£1.00"
|
|
139
|
+
# Money.new(100, "GBP").format(sign_positive: false, sign_before_symbol: false) #=> "£1.00"
|
|
140
|
+
# Money.new(100, "GBP").format #=> "£+1.00"
|
|
141
|
+
#
|
|
142
|
+
# @option rules [Boolean] :disambiguate (false) Prevents the result from being ambiguous
|
|
143
|
+
# due to equal symbols for different currencies. Uses the `disambiguate_symbol`.
|
|
144
|
+
#
|
|
145
|
+
# @example
|
|
146
|
+
# Money.new(10000, "USD").format(disambiguate: false) #=> "$100.00"
|
|
147
|
+
# Money.new(10000, "CAD").format(disambiguate: false) #=> "$100.00"
|
|
148
|
+
# Money.new(10000, "USD").format(disambiguate: true) #=> "$100.00"
|
|
149
|
+
# Money.new(10000, "CAD").format(disambiguate: true) #=> "C$100.00"
|
|
150
|
+
#
|
|
151
|
+
# @option rules [Boolean] :translate (true) `true` Checks for custom
|
|
152
|
+
# symbol definitions using I18n.
|
|
153
|
+
#
|
|
154
|
+
# @example
|
|
155
|
+
# # With the following entry in the translation files:
|
|
156
|
+
# # en:
|
|
157
|
+
# # number:
|
|
158
|
+
# # currency:
|
|
159
|
+
# # symbol:
|
|
160
|
+
# # CAD: "CAD$"
|
|
161
|
+
# Money.new(10000, "CAD").format(translate: true) #=> "CAD$100.00"
|
|
162
|
+
#
|
|
163
|
+
# @option rules [Boolean] :drop_trailing_zeros (false) Ignore trailing zeros after
|
|
164
|
+
# the decimal mark
|
|
165
|
+
#
|
|
166
|
+
# @example
|
|
167
|
+
# Money.new(89000, :btc).format(drop_trailing_zeros: true) #=> B⃦0.00089
|
|
168
|
+
# Money.new(110, :usd).format(drop_trailing_zeros: true) #=> $1.1
|
|
169
|
+
#
|
|
170
|
+
# @option rules [Boolean] :delimiter_pattern (/(\d)(?=(?:\d{3})+(?:[^\d]{1}|$))/) Regular expression to set the placement
|
|
171
|
+
# for the thousands delimiter
|
|
172
|
+
#
|
|
173
|
+
# @example
|
|
174
|
+
# Money.new(89000, :btc).format(delimiter_pattern: /(\d)(?=\d)/) #=> B⃦8,9,0.00
|
|
175
|
+
#
|
|
176
|
+
# @option rules [String] :format (nil) Provide a template for formatting. `%u` will be replaced
|
|
177
|
+
# with the symbol (if present) and `%n` will be replaced with the number.
|
|
178
|
+
#
|
|
179
|
+
# @example
|
|
180
|
+
# Money.new(10000, "USD").format(format: '%u %n') #=> "$ 100.00"
|
|
181
|
+
# Money.new(10000, "USD").format(format: '<span>%u%n</span>') #=> "<span>$100.00</span>"
|
|
182
|
+
#
|
|
183
|
+
# Note that the default rules can be defined through {Money.default_formatting_rules} hash.
|
|
184
|
+
#
|
|
185
|
+
# @see Money.default_formatting_rules Money.default_formatting_rules for more information.
|
|
186
|
+
def initialize(money, *rules)
|
|
187
|
+
@money = money
|
|
188
|
+
@currency = money.currency
|
|
189
|
+
@rules = FormattingRules.new(@currency, *rules)
|
|
190
|
+
end
|
|
191
|
+
|
|
192
|
+
def to_s
|
|
193
|
+
return free_text if show_free_text?
|
|
194
|
+
result = format_number
|
|
195
|
+
formatted = append_sign(result)
|
|
196
|
+
append_currency_symbol(formatted)
|
|
197
|
+
end
|
|
198
|
+
|
|
199
|
+
def thousands_separator
|
|
200
|
+
val = lookup :thousands_separator
|
|
201
|
+
|
|
202
|
+
return val unless val == true
|
|
203
|
+
|
|
204
|
+
lookup_default :thousands_separator
|
|
205
|
+
end
|
|
206
|
+
|
|
207
|
+
def decimal_mark
|
|
208
|
+
lookup :decimal_mark
|
|
209
|
+
end
|
|
210
|
+
|
|
211
|
+
alias_method :delimiter, :thousands_separator
|
|
212
|
+
alias_method :separator, :decimal_mark
|
|
213
|
+
|
|
214
|
+
private
|
|
215
|
+
|
|
216
|
+
attr_reader :money, :currency, :rules
|
|
217
|
+
|
|
218
|
+
def format_number
|
|
219
|
+
whole_part, decimal_part = extract_whole_and_decimal_parts
|
|
220
|
+
|
|
221
|
+
# Format whole and decimal parts separately
|
|
222
|
+
decimal_part = format_decimal_part(decimal_part)
|
|
223
|
+
whole_part = format_whole_part(whole_part)
|
|
224
|
+
|
|
225
|
+
# Assemble the final formatted amount
|
|
226
|
+
if rules[:html_wrap]
|
|
227
|
+
if decimal_part.nil?
|
|
228
|
+
html_wrap(whole_part, "whole")
|
|
229
|
+
else
|
|
230
|
+
[
|
|
231
|
+
html_wrap(whole_part, "whole"),
|
|
232
|
+
html_wrap(decimal_mark, "decimal-mark"),
|
|
233
|
+
html_wrap(decimal_part, "decimal")
|
|
234
|
+
].join
|
|
235
|
+
end
|
|
236
|
+
else
|
|
237
|
+
[whole_part, decimal_part].compact.join(decimal_mark)
|
|
238
|
+
end
|
|
239
|
+
end
|
|
240
|
+
|
|
241
|
+
def append_sign(formatted_number)
|
|
242
|
+
sign = money.negative? ? '-' : ''
|
|
243
|
+
|
|
244
|
+
if rules[:sign_positive] == true && money.positive?
|
|
245
|
+
sign = '+'
|
|
246
|
+
end
|
|
247
|
+
|
|
248
|
+
if rules[:sign_before_symbol] == true
|
|
249
|
+
sign_before = sign
|
|
250
|
+
sign = ''
|
|
251
|
+
end
|
|
252
|
+
|
|
253
|
+
symbol_value = symbol_value_from(rules)
|
|
254
|
+
|
|
255
|
+
if symbol_value && !symbol_value.empty?
|
|
256
|
+
if rules[:html_wrap]
|
|
257
|
+
symbol_value = html_wrap(symbol_value, "currency-symbol")
|
|
258
|
+
end
|
|
259
|
+
|
|
260
|
+
rules[:format]
|
|
261
|
+
.gsub('%u', [sign_before, symbol_value].join)
|
|
262
|
+
.gsub('%n', [sign, formatted_number].join)
|
|
263
|
+
else
|
|
264
|
+
formatted_number = "#{sign_before}#{sign}#{formatted_number}"
|
|
265
|
+
end
|
|
266
|
+
end
|
|
267
|
+
|
|
268
|
+
def append_currency_symbol(formatted_number)
|
|
269
|
+
if rules[:with_currency]
|
|
270
|
+
currency_part =
|
|
271
|
+
if rules[:html_wrap]
|
|
272
|
+
html_wrap(currency.to_s, "currency")
|
|
273
|
+
else
|
|
274
|
+
currency.to_s
|
|
275
|
+
end
|
|
276
|
+
|
|
277
|
+
"#{formatted_number} #{currency_part}"
|
|
278
|
+
else
|
|
279
|
+
formatted_number
|
|
280
|
+
end
|
|
281
|
+
end
|
|
282
|
+
|
|
283
|
+
def show_free_text?
|
|
284
|
+
money.zero? && rules[:display_free]
|
|
285
|
+
end
|
|
286
|
+
|
|
287
|
+
def html_wrap(string, class_name)
|
|
288
|
+
"<span class=\"money-#{class_name}\">#{string}</span>"
|
|
289
|
+
end
|
|
290
|
+
|
|
291
|
+
def free_text
|
|
292
|
+
rules[:display_free].respond_to?(:to_str) ? rules[:display_free] : 'free'
|
|
293
|
+
end
|
|
294
|
+
|
|
295
|
+
def format_whole_part(value)
|
|
296
|
+
# Apply thousands_separator
|
|
297
|
+
value.gsub(rules[:delimiter_pattern]) do |digit_to_delimit|
|
|
298
|
+
"#{digit_to_delimit}#{thousands_separator}"
|
|
299
|
+
end
|
|
300
|
+
end
|
|
301
|
+
|
|
302
|
+
def extract_whole_and_decimal_parts
|
|
303
|
+
fractional = money.fractional.abs
|
|
304
|
+
|
|
305
|
+
# Round the infinite precision part if needed
|
|
306
|
+
fractional = fractional.round if rules[:rounded_infinite_precision]
|
|
307
|
+
|
|
308
|
+
# Translate subunits into units
|
|
309
|
+
fractional_units = BigDecimal(fractional) / currency.subunit_to_unit
|
|
310
|
+
|
|
311
|
+
# Split the result and return whole and decimal parts separately
|
|
312
|
+
fractional_units.to_s('F').split('.')
|
|
313
|
+
end
|
|
314
|
+
|
|
315
|
+
def format_decimal_part(value)
|
|
316
|
+
return nil if currency.decimal_places == 0 && !Money.default_infinite_precision
|
|
317
|
+
return nil if rules[:no_cents]
|
|
318
|
+
return nil if rules[:no_cents_if_whole] && value.to_i == 0
|
|
319
|
+
|
|
320
|
+
# Pad value, making up for missing zeroes at the end
|
|
321
|
+
value = value.ljust(currency.decimal_places, '0')
|
|
322
|
+
|
|
323
|
+
# Drop trailing zeros if needed
|
|
324
|
+
value.gsub!(/0*$/, '') if rules[:drop_trailing_zeros]
|
|
325
|
+
|
|
326
|
+
value.empty? ? nil : value
|
|
327
|
+
end
|
|
328
|
+
|
|
329
|
+
def lookup(key)
|
|
330
|
+
return rules[key] || DEFAULTS[key] if rules.has_key?(key)
|
|
331
|
+
|
|
332
|
+
lookup_default key
|
|
333
|
+
end
|
|
334
|
+
|
|
335
|
+
def lookup_default(key)
|
|
336
|
+
(Money.locale_backend && Money.locale_backend.lookup(key, currency)) || DEFAULTS[key]
|
|
337
|
+
end
|
|
338
|
+
|
|
339
|
+
def symbol_value_from(rules)
|
|
340
|
+
if rules.has_key?(:symbol)
|
|
341
|
+
if rules[:symbol] === true
|
|
342
|
+
if rules[:disambiguate] && currency.disambiguate_symbol
|
|
343
|
+
currency.disambiguate_symbol
|
|
344
|
+
else
|
|
345
|
+
money.symbol
|
|
346
|
+
end
|
|
347
|
+
elsif rules[:symbol]
|
|
348
|
+
rules[:symbol]
|
|
349
|
+
else
|
|
350
|
+
""
|
|
351
|
+
end
|
|
352
|
+
elsif rules[:html_wrap]
|
|
353
|
+
currency.html_entity == '' ? currency.symbol : currency.html_entity
|
|
354
|
+
elsif rules[:disambiguate] && currency.disambiguate_symbol
|
|
355
|
+
currency.disambiguate_symbol
|
|
356
|
+
else
|
|
357
|
+
money.symbol
|
|
358
|
+
end
|
|
359
|
+
end
|
|
360
|
+
end
|
|
361
|
+
end
|
|
@@ -0,0 +1,92 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
class Money
|
|
4
|
+
class FormattingRules
|
|
5
|
+
def initialize(currency, *raw_rules)
|
|
6
|
+
@currency = currency
|
|
7
|
+
|
|
8
|
+
# support for old format parameters
|
|
9
|
+
@rules = normalize_formatting_rules(raw_rules)
|
|
10
|
+
|
|
11
|
+
@rules = default_formatting_rules.merge(@rules) unless @rules[:ignore_defaults]
|
|
12
|
+
@rules = translate_formatting_rules(@rules) if @rules[:translate]
|
|
13
|
+
@rules[:format] ||= determine_format
|
|
14
|
+
@rules[:delimiter_pattern] ||= delimiter_pattern_rule(@rules)
|
|
15
|
+
end
|
|
16
|
+
|
|
17
|
+
def [](key)
|
|
18
|
+
@rules[key]
|
|
19
|
+
end
|
|
20
|
+
|
|
21
|
+
def has_key?(key)
|
|
22
|
+
@rules.has_key? key
|
|
23
|
+
end
|
|
24
|
+
|
|
25
|
+
private
|
|
26
|
+
|
|
27
|
+
attr_reader :currency
|
|
28
|
+
|
|
29
|
+
# Cleans up formatting rules.
|
|
30
|
+
#
|
|
31
|
+
# @param [Hash] rules
|
|
32
|
+
#
|
|
33
|
+
# @return [Hash]
|
|
34
|
+
def normalize_formatting_rules(rules)
|
|
35
|
+
if rules.size == 0
|
|
36
|
+
rules = {}
|
|
37
|
+
elsif rules.size == 1
|
|
38
|
+
rules = rules.pop
|
|
39
|
+
rules = rules.dup if rules.is_a?(Hash)
|
|
40
|
+
|
|
41
|
+
if rules.is_a?(Symbol)
|
|
42
|
+
warn '[DEPRECATION] Use Hash when passing rules to Money#format.'
|
|
43
|
+
rules = { rules => true }
|
|
44
|
+
end
|
|
45
|
+
end
|
|
46
|
+
|
|
47
|
+
if !rules.include?(:decimal_mark) && rules.include?(:separator)
|
|
48
|
+
rules[:decimal_mark] = rules[:separator]
|
|
49
|
+
end
|
|
50
|
+
|
|
51
|
+
if !rules.include?(:thousands_separator) && rules.include?(:delimiter)
|
|
52
|
+
rules[:thousands_separator] = rules[:delimiter]
|
|
53
|
+
end
|
|
54
|
+
|
|
55
|
+
rules
|
|
56
|
+
end
|
|
57
|
+
|
|
58
|
+
def default_formatting_rules
|
|
59
|
+
Money.default_formatting_rules || {}
|
|
60
|
+
end
|
|
61
|
+
|
|
62
|
+
def translate_formatting_rules(rules)
|
|
63
|
+
begin
|
|
64
|
+
rules[:symbol] = I18n.t currency.iso_code, scope: "number.currency.symbol", raise: true
|
|
65
|
+
rescue I18n::MissingTranslationData
|
|
66
|
+
# Do nothing
|
|
67
|
+
end
|
|
68
|
+
rules
|
|
69
|
+
end
|
|
70
|
+
|
|
71
|
+
def determine_format
|
|
72
|
+
Money.locale_backend&.lookup(:format, @currency) || default_format
|
|
73
|
+
end
|
|
74
|
+
|
|
75
|
+
def default_format
|
|
76
|
+
if currency.format
|
|
77
|
+
currency.format
|
|
78
|
+
else
|
|
79
|
+
currency.symbol_first? ? "%u%n" : "%n %u"
|
|
80
|
+
end
|
|
81
|
+
end
|
|
82
|
+
|
|
83
|
+
def delimiter_pattern_rule(rules)
|
|
84
|
+
if rules[:south_asian_number_formatting]
|
|
85
|
+
# from https://blog.revathskumar.com/2014/11/regex-comma-seperated-indian-currency-format.html
|
|
86
|
+
/(\d+?)(?=(\d\d)+(\d)(?!\d))(\.\d+)?/
|
|
87
|
+
else
|
|
88
|
+
/(\d)(?=(?:\d{3})+(?:[^\d]{1}|$))/
|
|
89
|
+
end
|
|
90
|
+
end
|
|
91
|
+
end
|
|
92
|
+
end
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require 'money/locale_backend/errors'
|
|
4
|
+
require 'money/locale_backend/i18n'
|
|
5
|
+
require 'money/locale_backend/currency'
|
|
6
|
+
|
|
7
|
+
class Money
|
|
8
|
+
module LocaleBackend
|
|
9
|
+
BACKENDS = {
|
|
10
|
+
i18n: Money::LocaleBackend::I18n,
|
|
11
|
+
currency: Money::LocaleBackend::Currency
|
|
12
|
+
}.freeze
|
|
13
|
+
|
|
14
|
+
def self.find(name)
|
|
15
|
+
raise Unknown, "Unknown locale backend: #{name}" unless BACKENDS.key?(name)
|
|
16
|
+
|
|
17
|
+
BACKENDS[name].new
|
|
18
|
+
end
|
|
19
|
+
end
|
|
20
|
+
end
|