Skip to content

Commit fd7007e

Browse files
committed
Avoid Price.toString() failing for certain values of numerator/denominator.
Fixes a regression introduced in 66cc533 (bugfix #479) in which the numerator/denominator division fails with an ArithmeticException if no MathContext is provided. BigDecimal tries to return an exact result, which is not possible when rounding and precision aren't specified. See BigDecimal javadoc: http://docs.oracle.com/javase/7/docs/api/java/math/BigDecimal.html Fixes Crashlitics issue #196 https://fabric.io/gnucash/android/apps/org.gnucash.android/issues/571b4a95ffcdc04250f98ba0
1 parent c0d00e1 commit fd7007e

2 files changed

Lines changed: 23 additions & 1 deletion

File tree

app/src/main/java/org/gnucash/android/model/Price.java

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44

55

66
import java.math.BigDecimal;
7+
import java.math.MathContext;
78
import java.sql.Timestamp;
89
import java.text.DecimalFormat;
910
import java.text.NumberFormat;
@@ -156,6 +157,6 @@ public String toString() {
156157
BigDecimal denominator = new BigDecimal(mValueDenom);
157158
DecimalFormat formatter = (DecimalFormat) NumberFormat.getNumberInstance();
158159
formatter.setMaximumFractionDigits(6);
159-
return formatter.format(numerator.divide(denominator));
160+
return formatter.format(numerator.divide(denominator, MathContext.DECIMAL32));
160161
}
161162
}

app/src/test/java/org/gnucash/android/test/unit/model/PriceTest.java

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,7 @@
2323
import java.util.Locale;
2424

2525
import static org.assertj.core.api.Assertions.assertThat;
26+
import static org.junit.Assert.fail;
2627

2728

2829
public class PriceTest {
@@ -52,6 +53,26 @@ public void toString_shouldUseDefaultLocale() {
5253
assertThat(price.toString()).isEqualTo("1,234");
5354
}
5455

56+
/**
57+
* BigDecimal throws an ArithmeticException if it can't represent exactly
58+
* a result. This can happen with divisions like 1/3 if no precision and
59+
* round mode is specified with a MathContext.
60+
*/
61+
@Test
62+
public void toString_shouldNotFailForInfinitelyLongDecimalExpansion() {
63+
long numerator = 1;
64+
long denominator = 3;
65+
Price price = new Price();
66+
67+
price.setValueNum(numerator);
68+
price.setValueDenom(denominator);
69+
try {
70+
price.toString();
71+
} catch (ArithmeticException e) {
72+
fail("The numerator/denominator division in Price.toString() should not fail.");
73+
}
74+
}
75+
5576
@Test
5677
public void getNumerator_shouldReduceAutomatically() {
5778
long numerator = 1;

0 commit comments

Comments
 (0)