回答:
おそらくDECIMAL
データベースで型を使用したいと思うでしょう。移行では、次のようにします。
# precision is the total number of digits
# scale is the number of digits to the right of the decimal point
add_column :items, :price, :decimal, :precision => 8, :scale => 2
Railsでは、:decimal
タイプはとして返されるBigDecimal
ため、価格計算に最適です。
整数の使用を主張する場合は、BigDecimal
どこでもs との間で手動で変換する必要がありますが、これはおそらく面倒になるだけです。
mclで指摘されているように、価格を出力するには、次のコマンドを使用します。
number_to_currency(price, :unit => "€")
#=> €1,234.01
これが活用する細かい、シンプルなアプローチです composed_of
(ValueObjectパターンを使用したActiveRecordの一部)とMoney gemを次に示します。
あなたは必要になるでしょう
Product
integer
たとえば、モデル(およびデータベース)の列:price
これをproduct.rb
ファイルに書き込みます。
class Product > ActiveRecord::Base
composed_of :price,
:class_name => 'Money',
:mapping => %w(price cents),
:converter => Proc.new { |value| Money.new(value) }
# ...
あなたが得るもの:
product.price = "$12.00"
自動的にMoneyクラスに変換しますproduct.price.to_s
10進数形式の数値を表示します( "1234.00")product.price.format
通貨の適切にフォーマットされた文字列を表示しますproduct.price.cents.to_s
composed_of
ここでの削除に関する@PeerAllanのコメントについては、その詳細と代替実装について詳しく説明しています。
通貨を処理する一般的な方法は、10進数タイプを使用することです。以下は、「Railsを使用したアジャイルWeb開発」の簡単な例です。
add_column :products, :price, :decimal, :precision => 8, :scale => 2
これにより、-999,999.99から999,999.99までの価格を処理できるようになります。次の
ようなアイテムに検証を含めることもできます。
def validate
errors.add(:price, "should be at least 0.01") if price.nil? || price < 0.01
end
値の健全性をチェックします。
money-rails gemを使用してください。それはあなたのモデルのお金と通貨をうまく処理し、あなたの価格をフォーマットするヘルパーの束も持っています。
ほんの少しの更新と、いくつかの説明のために確実にここに来るRoR開発の意欲的なジュニア/初心者のためのすべての答えのまとまり。
:decimal
@molfが示唆するように、DBにお金を格納するために使用します(そして、私の会社がお金を扱うときに黄金の標準として使用するもの)。
# precision is the total number of digits
# scale is the number of digits to the right of the decimal point
add_column :items, :price, :decimal, precision: 8, scale: 2
いくつかのポイント:
:decimal
BigDecimal
多くの問題を解決するものとして使用されます。
precision
そしてscale
、あなたが何を表しているかに応じて、調整する必要があります
支払いの受け取りと送金を処理し、最高額precision: 8
をscale: 2
提供する999,999.99
場合、90%の場合は問題ありません。
プロパティや希少車の値を表す必要がある場合は、より高い値を使用する必要がありますprecision
。
座標(経度と緯度)を扱う場合は、より高い値が必要になりscale
ます。
上記の内容で移行を生成するには、ターミナルで実行します:
bin/rails g migration AddPriceToItems price:decimal{8-2}
または
bin/rails g migration AddPriceToItems 'price:decimal{5,2}'
このブログで説明されているように投稿でます。
KISSの余分なライブラリは別れと組み込みのヘルパーを使用します。使用するnumber_to_currency
@molfおよび@facundofariasの推奨どおりに。
一緒にプレイするにはnumber_to_currency
Railsのコンソールでヘルパーに呼び出しを送るActiveSupport
さんNumberHelper
クラスにてヘルパーにアクセスします。
例えば:
ActiveSupport::NumberHelper.number_to_currency(2_500_000.61, unit: '€', precision: 2, separator: ',', delimiter: '', format: "%n%u")
次の出力を与える
2500000,61€
number_to_currencyのもう一方options
を確認してくださいヘルパー。
アプリケーションヘルパーに入れて、ビュー内で任意の量を使用できます。
module ApplicationHelper
def format_currency(amount)
number_to_currency(amount, unit: '€', precision: 2, separator: ',', delimiter: '', format: "%n%u")
end
end
またはItem
、インスタンスメソッドとしてモデルに配置し、価格をフォーマットする必要がある場所(ビューまたはヘルパー)で呼び出すことができます。
class Item < ActiveRecord::Base
def format_price
number_to_currency(price, unit: '€', precision: 2, separator: ',', delimiter: '', format: "%n%u")
end
end
そして、私number_to_currency
がコントローラの内部を使用する方法の例(negative_format
払い戻しを表すために使用されるオプションに注意してください)
def refund_information
amount_formatted =
ActionController::Base.helpers.number_to_currency(@refund.amount, negative_format: '(%u%n)')
{
# ...
amount_formatted: amount_formatted,
# ...
}
end
使用して仮想属性(改訂版(有償)Railscastへのリンクを)あなたは、整数列であなたのprice_in_centsを保存し、ゲッターとセッターとしてご使用の製品モデルに仮想属性price_in_dollarsを追加することができます。
# Add a price_in_cents integer column
$ rails g migration add_price_in_cents_to_products price_in_cents:integer
# Use virtual attributes in your Product model
# app/models/product.rb
def price_in_dollars
price_in_cents.to_d/100 if price_in_cents
end
def price_in_dollars=(dollars)
self.price_in_cents = dollars.to_d*100 if dollars.present?
end
ソース:RailsCasts#016:仮想属性:仮想属性は、データベースに直接マップしないフォームフィールドを追加するためのクリーンな方法です。ここでは、検証、関連付けなどの処理方法を示します。
私の基になるAPIはすべてセントを使ってお金を表していたので、それを変更したくありませんでした。また、私は多額のお金で働いていませんでした。だから私はこれをヘルパーメソッドに入れます:
sprintf("%03d", amount).insert(-3, ".")
これにより、整数が少なくとも3桁の文字列に変換され(必要に応じて先行ゼロが追加されます)、最後の2桁の前に小数点が挿入されFloat
ます。そこから、ユースケースに適した通貨記号を追加できます。
それは間違いなく迅速で汚いですが、時にはそれで十分です!
Ruby&Railsのシンプルなコード
<%= number_to_currency(1234567890.50) %>
OUT PUT => $1,234,567,890.50
DECIMAL(19, 4)
一般的な選択肢であるチェック、これはまた、チェック、ここでどのように多くの小数点以下の桁使用することを決定するために世界の通貨書式を、希望が役立ちます。