Conversion from BigDecimal to PgMoney

This commit is contained in:
Julius de Bruijn 2020-07-07 19:53:43 +02:00 committed by Ryan Leckey
parent 4c394de70b
commit 99b7017d6c

View File

@ -61,6 +61,32 @@ impl PgMoney {
Self(i64::from_le_bytes(buf))
}
/// Convert a [`BigDecimal`] value into money using the correct precision
/// defined in the PostgreSQL settings. The default precision is two.
///
/// [`BigDecimal`]: ../../types/struct.BigDecimal.html
#[cfg(feature = "bigdecimal")]
pub fn from_bigdecimal(
decimal: bigdecimal::BigDecimal,
scale: u32,
) -> Result<Self, BoxDynError> {
use bigdecimal::ToPrimitive;
let multiplier =
bigdecimal::BigDecimal::new(num_bigint::BigInt::from(10i128.pow(scale)), 0);
let cents = decimal * multiplier;
let money = cents.to_i64().ok_or_else(|| {
io::Error::new(
io::ErrorKind::InvalidData,
"Provided BigDecimal could not convert to i64: overflow.",
)
})?;
Ok(Self(money))
}
}
impl Type<Postgres> for PgMoney {
@ -257,4 +283,11 @@ mod tests {
assert_eq!(PgMoney(12345), PgMoney::from_decimal(dec, 2));
}
#[cfg(feature = "bigdecimal")]
fn conversion_from_bigdecimal_works() {
let dec = bigdecimal::BigDecimal::new(num_bigint::BigInt::from(12345), 2);
assert_eq!(PgMoney(12345), PgMoney::from_bigdecimal(dec, 2).unwrap());
}
}